1 /*
2 * Copyright (c) 2020 HiSilicon (Shanghai) Technologies CO., LIMITED.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15 /**
16 * @defgroup scatterlist Scatterlist
17 * @ingroup linux
18 */
19
20 #ifndef _LINUX_SCATTERLIST_H
21 #define _LINUX_SCATTERLIST_H
22
23 #include "linux/string.h"
24 #include "linux/kernel.h"
25 #include "types.h"
26 #include "asm/bug.h"
27 #include "los_printf.h"
28
29 #ifdef __cplusplus
30 extern "C" {
31 #endif /* __cplusplus */
32
33 typedef unsigned long dma_addr_t;
34 typedef unsigned int uint;
35
36 typedef struct scatterlist {
37 #ifdef CONFIG_DEBUG_SG
38 ulong sg_magic; /**< Used for memory exception check. */
39 #endif
40 ulong page_link; /**< Indicates the page on which the memory block resides. */
41 uint offset; /**< Indicates the offset of the memory block in the page. */
42 uint length; /**< Length of the memory block. */
43 dma_addr_t dma_address; /**< Actual start address of the memory block. */
44 #ifdef CONFIG_NEED_SG_DMA_LENGTH
45 uint dma_length; /**< The length information of a memory block.(not used) */
46 #endif
47 } scatterlist_t;
48
49 /* Used for memory exception check. */
50 #define COMPAT_SG_MAGIC 0x87654321
51 #define SG_MAGIC COMPAT_SG_MAGIC
52
53 /**
54 * @ingroup scatterlist
55 * @brief Mark the end of the scatterlist.
56 *
57 * @par Description:
58 * This API is used to mark the end of the scatterlist.
59 * @attention
60 * <ul>
61 * <li> The parameter passed in should be a legal pointer. </li>
62 * </ul>
63 *
64 * @param psg [IN/OUT] SG entryScatterlist.
65 *
66 * @retval None.
67 * @par Dependency:
68 * <ul><li>scatterlist.h: the header file that contains the API declaration.</li></ul>
69 * @see None.
70 */
sg_mark_end(scatterlist_t * psg)71 static inline void sg_mark_end(scatterlist_t *psg)
72 {
73 #ifdef CONFIG_DEBUG_SG
74 BUG_ON(psg->sg_magic != COMPAT_SG_MAGIC);
75 #endif
76 /* Set termination bit, clear potential chain bit */
77 psg->page_link |= 0x02U;
78 psg->page_link &= ~0x01U;
79 }
80
81 /**
82 * @ingroup scatterlist
83 * @brief Initialize the sg table.
84 *
85 * @par Description:
86 * This API is used to initialize the sg table.
87 * @attention
88 * <ul>
89 * <li> The parameter passed in should be a legal pointer. </li>
90 * </ul>
91 *
92 * @param psgl [IN/OUT] The SG table.
93 * @param nents [IN] Number of entries in table.
94 *
95 * @retval None.
96 * @par Dependency:
97 * <ul><li>scatterlist.h: the header file that contains the API declaration.</li></ul>
98 * @see None.
99 */
sg_init_table(scatterlist_t * psgl,unsigned int nents)100 static inline void sg_init_table(scatterlist_t *psgl, unsigned int nents)
101 {
102 (void)memset(psgl, 0, sizeof(scatterlist_t) * nents);
103
104 sg_mark_end(&psgl[nents - 1]);
105 }
106
107 /**
108 * @ingroup scatterlist
109 * @brief Point the #dma_address of the SG table to the #buf.
110 *
111 * @par Description:
112 * This API is used to point the #dma_address of the SG table to the #buf.
113 * @attention
114 * <ul>
115 * <li> The parameter passed in should be a legal pointer. </li>
116 * </ul>
117 *
118 * @param psg [IN/OUT] The SG table.
119 * @param buf [IN] Point to the data.
120 * @param buflen [IN] Length of buf.
121 *
122 * @retval None.
123 * @par Dependency:
124 * <ul><li>scatterlist.h: the header file that contains the API declaration.</li></ul>
125 * @see None.
126 */
sg_set_buf(scatterlist_t * psg,const void * buf,unsigned int buflen)127 static inline void sg_set_buf(scatterlist_t *psg, const void *buf, unsigned int buflen)
128 {
129 psg->dma_address = (uintptr_t)buf;
130 psg->offset = 0;
131 psg->length = buflen;
132 }
133
134 /**
135 * @ingroup scatterlist
136 * @brief Initialize the sg table and set SG table point at #buf.
137 *
138 * @par Description:
139 * This API is used to initialize the sg table and set SG table point at #buf.
140 * @attention
141 * <ul>
142 * <li> The parameter passed in should be a legal pointer. </li>
143 * </ul>
144 *
145 * @param psg [IN/OUT] The SG table.
146 * @param buf [IN] Point to the data.
147 * @param buflen [IN] Length of buf.
148 *
149 * @retval None.
150 * @par Dependency:
151 * <ul><li>scatterlist.h: the header file that contains the API declaration.</li></ul>
152 * @see None.
153 */
sg_init_one(scatterlist_t * psg,const void * buf,unsigned int buflen)154 static inline void sg_init_one(scatterlist_t *psg, const void *buf, unsigned int buflen)
155 {
156 sg_init_table(psg, 1);
157 sg_set_buf(psg, buf, buflen);
158 }
159
160 #ifdef __cplusplus
161 }
162 #endif /* __cplusplus */
163
164 #endif /* _LINUX_SCATTERLIST_H */
165