2019-06-03 07:44:50 +02:00
// SPDX-License-Identifier: GPL-2.0-only
2012-03-05 11:49:30 +00:00
/*
* Copyright ( C ) 2012 ARM Ltd .
* Author : Catalin Marinas < catalin . marinas @ arm . com >
*/
# include <linux/gfp.h>
2016-08-15 14:45:46 +08:00
# include <linux/cache.h>
2020-09-22 15:31:03 +02:00
# include <linux/dma-map-ops.h>
2019-05-20 09:29:29 +02:00
# include <linux/dma-iommu.h>
2019-07-24 14:07:28 +02:00
# include <xen/xen.h>
2012-03-05 11:49:30 +00:00
# include <asm/cacheflush.h>
2022-06-02 22:23:46 +03:00
# include <asm/xen/xen-ops.h>
2012-03-05 11:49:30 +00:00
2019-11-07 18:03:11 +01:00
void arch_sync_dma_for_device ( phys_addr_t paddr , size_t size ,
2022-06-10 16:12:28 +01:00
enum dma_data_direction dir )
2013-05-21 17:35:19 +01:00
{
2022-06-10 16:12:28 +01:00
unsigned long start = ( unsigned long ) phys_to_virt ( paddr ) ;
dcache_clean_poc ( start , start + size ) ;
2013-05-21 17:35:19 +01:00
}
2019-11-07 18:03:11 +01:00
void arch_sync_dma_for_cpu ( phys_addr_t paddr , size_t size ,
2022-06-10 16:12:28 +01:00
enum dma_data_direction dir )
2013-05-21 17:35:19 +01:00
{
2022-06-10 16:12:28 +01:00
unsigned long start = ( unsigned long ) phys_to_virt ( paddr ) ;
if ( dir = = DMA_TO_DEVICE )
return ;
dcache_inval_poc ( start , start + size ) ;
2013-05-21 17:35:19 +01:00
}
2018-11-04 20:29:28 +01:00
void arch_dma_prep_coherent ( struct page * page , size_t size )
{
2022-06-10 16:12:28 +01:00
unsigned long start = ( unsigned long ) page_address ( page ) ;
dcache_clean_inval_poc ( start , start + size ) ;
2018-11-04 20:29:28 +01:00
}
2015-10-01 20:13:59 +01:00
# ifdef CONFIG_IOMMU_DMA
2015-10-01 20:14:00 +01:00
void arch_teardown_dma_ops ( struct device * dev )
{
2017-01-20 13:04:02 -08:00
dev - > dma_ops = NULL ;
2015-10-01 20:14:00 +01:00
}
2019-05-20 09:29:29 +02:00
# endif
2015-10-01 20:13:59 +01:00
2015-10-01 20:14:00 +01:00
void arch_setup_dma_ops ( struct device * dev , u64 dma_base , u64 size ,
2016-04-07 18:42:05 +01:00
const struct iommu_ops * iommu , bool coherent )
2015-10-01 20:14:00 +01:00
{
2019-06-14 09:11:41 -04:00
int cls = cache_line_size_of_cpu ( ) ;
WARN_TAINT ( ! coherent & & cls > ARCH_DMA_MINALIGN ,
TAINT_CPU_OUT_OF_SPEC ,
" %s %s: ARCH_DMA_MINALIGN smaller than CTR_EL0.CWG (%d < %d) " ,
dev_driver_string ( dev ) , dev_name ( dev ) ,
ARCH_DMA_MINALIGN , cls ) ;
2018-10-08 09:12:01 +02:00
dev - > dma_coherent = coherent ;
2019-05-20 09:29:29 +02:00
if ( iommu )
2021-06-18 17:20:59 +02:00
iommu_setup_dma_ops ( dev , dma_base , dma_base + size - 1 ) ;
2017-04-13 14:04:21 -07:00
2022-06-02 22:23:46 +03:00
xen_setup_dma_ops ( dev ) ;
2015-10-01 20:14:00 +01:00
}