Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 762afb73 authored by FUJITA Tomonori's avatar FUJITA Tomonori Committed by Benjamin Herrenschmidt
Browse files

powerpc: Remove addr_needs_map in struct dma_mapping_ops

This patch adds max_direct_dma_addr to struct dev_archdata to remove
addr_needs_map in struct dma_mapping_ops. It also converts
dma_capable() to use max_direct_dma_addr.

max_direct_dma_addr is initialized in pci_dma_dev_setup_swiotlb(),
called via ppc_md.pci_dma_dev_setup hook.

For further information:
http://marc.info/?t=124719060200001&r=1&w=2



Signed-off-by: default avatarFUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>
Acked-by: default avatarBecky Bruce <beckyb@kernel.crashing.org>
Signed-off-by: default avatarBenjamin Herrenschmidt <benh@kernel.crashing.org>
parent 2864697c
Loading
Loading
Loading
Loading
+3 −0
Original line number Diff line number Diff line
@@ -16,6 +16,9 @@ struct dev_archdata {
	/* DMA operations on that device */
	struct dma_mapping_ops	*dma_ops;
	void			*dma_data;
#ifdef CONFIG_SWIOTLB
	dma_addr_t		max_direct_dma_addr;
#endif
};

static inline void dev_archdata_set_node(struct dev_archdata *ad,
+4 −4
Original line number Diff line number Diff line
@@ -87,8 +87,6 @@ struct dma_mapping_ops {
				dma_addr_t dma_address, size_t size,
				enum dma_data_direction direction,
				struct dma_attrs *attrs);
	int		(*addr_needs_map)(struct device *dev, dma_addr_t addr,
				size_t size);
#ifdef CONFIG_PPC_NEED_DMA_SYNC_OPS
	void            (*sync_single_range_for_cpu)(struct device *hwdev,
				dma_addr_t dma_handle, unsigned long offset,
@@ -426,10 +424,12 @@ static inline int dma_mapping_error(struct device *dev, dma_addr_t dma_addr)

static inline bool dma_capable(struct device *dev, dma_addr_t addr, size_t size)
{
	struct dma_mapping_ops *ops = get_dma_ops(dev);
#ifdef CONFIG_SWIOTLB
	struct dev_archdata *sd = &dev->archdata;

	if (ops->addr_needs_map && ops->addr_needs_map(dev, addr, size))
	if (sd->max_direct_dma_addr && addr + size > sd->max_direct_dma_addr)
		return 0;
#endif

	if (!dev->dma_mask)
		return 0;
+2 −3
Original line number Diff line number Diff line
@@ -16,12 +16,11 @@
extern struct dma_mapping_ops swiotlb_dma_ops;
extern struct dma_mapping_ops swiotlb_pci_dma_ops;

int swiotlb_arch_address_needs_mapping(struct device *, dma_addr_t,
				       size_t size);

static inline void dma_mark_clean(void *addr, size_t size) {}

extern unsigned int ppc_swiotlb_enable;
int __init swiotlb_setup_bus_notifier(void);

extern void pci_dma_dev_setup_swiotlb(struct pci_dev *pdev);

#endif /* __ASM_SWIOTLB_H */
+15 −21
Original line number Diff line number Diff line
@@ -24,26 +24,6 @@
int swiotlb __read_mostly;
unsigned int ppc_swiotlb_enable;

/*
 * Determine if an address is reachable by a pci device, or if we must bounce.
 */
static int
swiotlb_pci_addr_needs_map(struct device *hwdev, dma_addr_t addr, size_t size)
{
	dma_addr_t max;
	struct pci_controller *hose;
	struct pci_dev *pdev = to_pci_dev(hwdev);

	hose = pci_bus_to_host(pdev->bus);
	max = hose->dma_window_base_cur + hose->dma_window_size;

	/* check that we're within mapped pci window space */
	if ((addr + size > max) | (addr < hose->dma_window_base_cur))
		return 1;

	return 0;
}

/*
 * At the moment, all platforms that use this code only require
 * swiotlb to be used if we're operating on HIGHMEM.  Since
@@ -73,22 +53,36 @@ struct dma_mapping_ops swiotlb_pci_dma_ops = {
	.dma_supported = swiotlb_dma_supported,
	.map_page = swiotlb_map_page,
	.unmap_page = swiotlb_unmap_page,
	.addr_needs_map = swiotlb_pci_addr_needs_map,
	.sync_single_range_for_cpu = swiotlb_sync_single_range_for_cpu,
	.sync_single_range_for_device = swiotlb_sync_single_range_for_device,
	.sync_sg_for_cpu = swiotlb_sync_sg_for_cpu,
	.sync_sg_for_device = swiotlb_sync_sg_for_device
};

void pci_dma_dev_setup_swiotlb(struct pci_dev *pdev)
{
	struct pci_controller *hose;
	struct dev_archdata *sd;

	hose = pci_bus_to_host(pdev->bus);
	sd = &pdev->dev.archdata;
	sd->max_direct_dma_addr =
		hose->dma_window_base_cur + hose->dma_window_size;
}

static int ppc_swiotlb_bus_notify(struct notifier_block *nb,
				  unsigned long action, void *data)
{
	struct device *dev = data;
	struct dev_archdata *sd;

	/* We are only intereted in device addition */
	if (action != BUS_NOTIFY_ADD_DEVICE)
		return 0;

	sd = &dev->archdata;
	sd->max_direct_dma_addr = 0;

	/* May need to bounce if the device can't address all of DRAM */
	if (dma_get_mask(dev) < lmb_end_of_DRAM())
		set_dma_ops(dev, &swiotlb_dma_ops);
+1 −0
Original line number Diff line number Diff line
@@ -97,6 +97,7 @@ static void __init mpc8536_ds_setup_arch(void)
	if (lmb_end_of_DRAM() > max) {
		ppc_swiotlb_enable = 1;
		set_pci_dma_ops(&swiotlb_pci_dma_ops);
		ppc_md.pci_dma_dev_setup = pci_dma_dev_setup_swiotlb;
	}
#endif

Loading