xref: /linux-6.15/include/linux/swiotlb.h (revision 73f62095)
1b2441318SGreg Kroah-Hartman /* SPDX-License-Identifier: GPL-2.0 */
21648993fSJoerg Roedel #ifndef __LINUX_SWIOTLB_H
31648993fSJoerg Roedel #define __LINUX_SWIOTLB_H
41648993fSJoerg Roedel 
538674442SThierry Reding #include <linux/dma-direction.h>
638674442SThierry Reding #include <linux/init.h>
71648993fSJoerg Roedel #include <linux/types.h>
8f51778dbSStephen Rothwell #include <linux/limits.h>
9*73f62095SClaire Chang #include <linux/spinlock.h>
101648993fSJoerg Roedel 
111648993fSJoerg Roedel struct device;
1238674442SThierry Reding struct page;
131648993fSJoerg Roedel struct scatterlist;
141648993fSJoerg Roedel 
15ae7871beSGeert Uytterhoeven enum swiotlb_force {
16ae7871beSGeert Uytterhoeven 	SWIOTLB_NORMAL,		/* Default - depending on HW DMA mask etc. */
17ae7871beSGeert Uytterhoeven 	SWIOTLB_FORCE,		/* swiotlb=force */
18fff5d992SGeert Uytterhoeven 	SWIOTLB_NO_FORCE,	/* swiotlb=noforce */
19ae7871beSGeert Uytterhoeven };
20ae7871beSGeert Uytterhoeven 
210016fdeeSIan Campbell /*
220016fdeeSIan Campbell  * Maximum allowable number of contiguous slabs to map,
230016fdeeSIan Campbell  * must be a power of 2.  What is the appropriate value ?
240016fdeeSIan Campbell  * The complexity of {map,unmap}_single is linearly dependent on this value.
250016fdeeSIan Campbell  */
260016fdeeSIan Campbell #define IO_TLB_SEGSIZE	128
270016fdeeSIan Campbell 
280016fdeeSIan Campbell /*
290016fdeeSIan Campbell  * log of the size of each IO TLB slab.  The number of slabs is command line
300016fdeeSIan Campbell  * controllable.
310016fdeeSIan Campbell  */
320016fdeeSIan Campbell #define IO_TLB_SHIFT 11
33b5d7ccb7SChristoph Hellwig #define IO_TLB_SIZE (1 << IO_TLB_SHIFT)
340016fdeeSIan Campbell 
35e998879dSAshish Kalra /* default to 64MB */
36e998879dSAshish Kalra #define IO_TLB_DEFAULT_SIZE (64UL<<20)
37e998879dSAshish Kalra 
38ad32e8cbSFUJITA Tomonori extern void swiotlb_init(int verbose);
39ac2cbab2SYinghai Lu int swiotlb_init_with_tbl(char *tlb, unsigned long nslabs, int verbose);
40f21ffe9fSKonrad Rzeszutek Wilk extern unsigned long swiotlb_nr_tbl(void);
41c729de8fSYinghai Lu unsigned long swiotlb_size_or_default(void);
4274838b75SKonrad Rzeszutek Wilk extern int swiotlb_late_init_with_tbl(char *tlb, unsigned long nslabs);
4361b82bbfSAndy Shevchenko extern int swiotlb_late_init_with_default_size(size_t default_size);
44c7753208STom Lendacky extern void __init swiotlb_update_mem_attributes(void);
451648993fSJoerg Roedel 
46fc0021aaSChristoph Hellwig phys_addr_t swiotlb_tbl_map_single(struct device *hwdev, phys_addr_t phys,
47fc0021aaSChristoph Hellwig 		size_t mapping_size, size_t alloc_size,
48fc0021aaSChristoph Hellwig 		enum dma_data_direction dir, unsigned long attrs);
49d7ef1533SKonrad Rzeszutek Wilk 
5061ca08c3SAlexander Duyck extern void swiotlb_tbl_unmap_single(struct device *hwdev,
5161ca08c3SAlexander Duyck 				     phys_addr_t tlb_addr,
523fc1ca00SLu Baolu 				     size_t mapping_size,
533fc1ca00SLu Baolu 				     enum dma_data_direction dir,
540443fa00SAlexander Duyck 				     unsigned long attrs);
55d7ef1533SKonrad Rzeszutek Wilk 
5680808d27SChristoph Hellwig void swiotlb_sync_single_for_device(struct device *dev, phys_addr_t tlb_addr,
5780808d27SChristoph Hellwig 		size_t size, enum dma_data_direction dir);
5880808d27SChristoph Hellwig void swiotlb_sync_single_for_cpu(struct device *dev, phys_addr_t tlb_addr,
5980808d27SChristoph Hellwig 		size_t size, enum dma_data_direction dir);
604a47cbaeSChristoph Hellwig dma_addr_t swiotlb_map(struct device *dev, phys_addr_t phys,
614a47cbaeSChristoph Hellwig 		size_t size, enum dma_data_direction dir, unsigned long attrs);
624a47cbaeSChristoph Hellwig 
635740afdbSFUJITA Tomonori #ifdef CONFIG_SWIOTLB
6455897af6SChristoph Hellwig extern enum swiotlb_force swiotlb_force;
65*73f62095SClaire Chang 
66*73f62095SClaire Chang /**
67*73f62095SClaire Chang  * struct io_tlb_mem - IO TLB Memory Pool Descriptor
68*73f62095SClaire Chang  *
69*73f62095SClaire Chang  * @start:	The start address of the swiotlb memory pool. Used to do a quick
70*73f62095SClaire Chang  *		range check to see if the memory was in fact allocated by this
71*73f62095SClaire Chang  *		API.
72*73f62095SClaire Chang  * @end:	The end address of the swiotlb memory pool. Used to do a quick
73*73f62095SClaire Chang  *		range check to see if the memory was in fact allocated by this
74*73f62095SClaire Chang  *		API.
75*73f62095SClaire Chang  * @nslabs:	The number of IO TLB blocks (in groups of 64) between @start and
76*73f62095SClaire Chang  *		@end. This is command line adjustable via setup_io_tlb_npages.
77*73f62095SClaire Chang  * @used:	The number of used IO TLB block.
78*73f62095SClaire Chang  * @list:	The free list describing the number of free entries available
79*73f62095SClaire Chang  *		from each index.
80*73f62095SClaire Chang  * @index:	The index to start searching in the next round.
81*73f62095SClaire Chang  * @orig_addr:	The original address corresponding to a mapped entry.
82*73f62095SClaire Chang  * @alloc_size:	Size of the allocated buffer.
83*73f62095SClaire Chang  * @lock:	The lock to protect the above data structures in the map and
84*73f62095SClaire Chang  *		unmap calls.
85*73f62095SClaire Chang  * @debugfs:	The dentry to debugfs.
86*73f62095SClaire Chang  * @late_alloc:	%true if allocated using the page allocator
87*73f62095SClaire Chang  */
88*73f62095SClaire Chang struct io_tlb_mem {
89*73f62095SClaire Chang 	phys_addr_t start;
90*73f62095SClaire Chang 	phys_addr_t end;
91*73f62095SClaire Chang 	unsigned long nslabs;
92*73f62095SClaire Chang 	unsigned long used;
93*73f62095SClaire Chang 	unsigned int *list;
94*73f62095SClaire Chang 	unsigned int index;
95*73f62095SClaire Chang 	phys_addr_t *orig_addr;
96*73f62095SClaire Chang 	size_t *alloc_size;
97*73f62095SClaire Chang 	spinlock_t lock;
98*73f62095SClaire Chang 	struct dentry *debugfs;
99*73f62095SClaire Chang 	bool late_alloc;
100*73f62095SClaire Chang };
101*73f62095SClaire Chang extern struct io_tlb_mem io_tlb_default_mem;
10255897af6SChristoph Hellwig 
10355897af6SChristoph Hellwig static inline bool is_swiotlb_buffer(phys_addr_t paddr)
10455897af6SChristoph Hellwig {
105*73f62095SClaire Chang 	struct io_tlb_mem *mem = &io_tlb_default_mem;
106*73f62095SClaire Chang 
107*73f62095SClaire Chang 	return paddr >= mem->start && paddr < mem->end;
10855897af6SChristoph Hellwig }
10955897af6SChristoph Hellwig 
11055897af6SChristoph Hellwig void __init swiotlb_exit(void);
1117453c549SKonrad Rzeszutek Wilk unsigned int swiotlb_max_segment(void);
112abe420bfSJoerg Roedel size_t swiotlb_max_mapping_size(struct device *dev);
113492366f7SJoerg Roedel bool is_swiotlb_active(void);
114e998879dSAshish Kalra void __init swiotlb_adjust_size(unsigned long new_size);
1155740afdbSFUJITA Tomonori #else
11655897af6SChristoph Hellwig #define swiotlb_force SWIOTLB_NO_FORCE
11755897af6SChristoph Hellwig static inline bool is_swiotlb_buffer(phys_addr_t paddr)
11855897af6SChristoph Hellwig {
11955897af6SChristoph Hellwig 	return false;
12055897af6SChristoph Hellwig }
12155897af6SChristoph Hellwig static inline void swiotlb_exit(void)
12255897af6SChristoph Hellwig {
12355897af6SChristoph Hellwig }
12455897af6SChristoph Hellwig static inline unsigned int swiotlb_max_segment(void)
12555897af6SChristoph Hellwig {
12655897af6SChristoph Hellwig 	return 0;
12755897af6SChristoph Hellwig }
128abe420bfSJoerg Roedel static inline size_t swiotlb_max_mapping_size(struct device *dev)
129abe420bfSJoerg Roedel {
130abe420bfSJoerg Roedel 	return SIZE_MAX;
131abe420bfSJoerg Roedel }
132492366f7SJoerg Roedel 
133492366f7SJoerg Roedel static inline bool is_swiotlb_active(void)
134492366f7SJoerg Roedel {
135492366f7SJoerg Roedel 	return false;
136492366f7SJoerg Roedel }
137e998879dSAshish Kalra 
138e998879dSAshish Kalra static inline void swiotlb_adjust_size(unsigned long new_size)
139e998879dSAshish Kalra {
140e998879dSAshish Kalra }
14155897af6SChristoph Hellwig #endif /* CONFIG_SWIOTLB */
1425740afdbSFUJITA Tomonori 
143ad32e8cbSFUJITA Tomonori extern void swiotlb_print_info(void);
1447453c549SKonrad Rzeszutek Wilk extern void swiotlb_set_max_segment(unsigned int);
1459c5a3621SAkinobu Mita 
1461648993fSJoerg Roedel #endif /* __LINUX_SWIOTLB_H */
147