1 /***********************license start***************
2 * Copyright (c) 2003-2010 Cavium Inc. ([email protected]). All rights
3 * reserved.
4 *
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions are
8 * met:
9 *
10 * * Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 *
13 * * Redistributions in binary form must reproduce the above
14 * copyright notice, this list of conditions and the following
15 * disclaimer in the documentation and/or other materials provided
16 * with the distribution.
17
18 * * Neither the name of Cavium Inc. nor the names of
19 * its contributors may be used to endorse or promote products
20 * derived from this software without specific prior written
21 * permission.
22
23 * This Software, including technical data, may be subject to U.S. export control
24 * laws, including the U.S. Export Administration Act and its associated
25 * regulations, and may be subject to export or import regulations in other
26 * countries.
27
28 * TO THE MAXIMUM EXTENT PERMITTED BY LAW, THE SOFTWARE IS PROVIDED "AS IS"
29 * AND WITH ALL FAULTS AND CAVIUM INC. MAKES NO PROMISES, REPRESENTATIONS OR
30 * WARRANTIES, EITHER EXPRESS, IMPLIED, STATUTORY, OR OTHERWISE, WITH RESPECT TO
31 * THE SOFTWARE, INCLUDING ITS CONDITION, ITS CONFORMITY TO ANY REPRESENTATION OR
32 * DESCRIPTION, OR THE EXISTENCE OF ANY LATENT OR PATENT DEFECTS, AND CAVIUM
33 * SPECIFICALLY DISCLAIMS ALL IMPLIED (IF ANY) WARRANTIES OF TITLE,
34 * MERCHANTABILITY, NONINFRINGEMENT, FITNESS FOR A PARTICULAR PURPOSE, LACK OF
35 * VIRUSES, ACCURACY OR COMPLETENESS, QUIET ENJOYMENT, QUIET POSSESSION OR
36 * CORRESPONDENCE TO DESCRIPTION. THE ENTIRE RISK ARISING OUT OF USE OR
37 * PERFORMANCE OF THE SOFTWARE LIES WITH YOU.
38 ***********************license end**************************************/
39
40
41
42
43
44
45
46 /**
47 * @file
48 *
49 * Helper functions for FPA setup.
50 *
51 * <hr>$Revision: 70030 $<hr>
52 */
53 #include "cvmx.h"
54 #include "cvmx-bootmem.h"
55 #include "cvmx-fpa.h"
56 #include "cvmx-helper-fpa.h"
57
58 /**
59 * @INTERNAL
60 * Allocate memory for and initialize a single FPA pool.
61 *
62 * @param pool Pool to initialize
63 * @param buffer_size Size of buffers to allocate in bytes
64 * @param buffers Number of buffers to put in the pool. Zero is allowed
65 * @param name String name of the pool for debugging purposes
66 * @return Zero on success, non-zero on failure
67 */
__cvmx_helper_initialize_fpa_pool(int pool,uint64_t buffer_size,uint64_t buffers,const char * name)68 static int __cvmx_helper_initialize_fpa_pool(int pool, uint64_t buffer_size,
69 uint64_t buffers, const char *name)
70 {
71 uint64_t current_num;
72 void *memory;
73 uint64_t align = CVMX_CACHE_LINE_SIZE;
74
75 /* Align the allocation so that power of 2 size buffers are naturally aligned */
76 while (align < buffer_size)
77 align = align << 1;
78
79 if (buffers == 0)
80 return 0;
81
82 current_num = cvmx_read_csr(CVMX_FPA_QUEX_AVAILABLE(pool));
83 if (current_num)
84 {
85 cvmx_dprintf("Fpa pool %d(%s) already has %llu buffers. Skipping setup.\n",
86 pool, name, (unsigned long long)current_num);
87 return 0;
88 }
89
90 memory = cvmx_bootmem_alloc(buffer_size * buffers, align);
91 if (memory == NULL)
92 {
93 cvmx_dprintf("Out of memory initializing fpa pool %d(%s).\n", pool, name);
94 return -1;
95 }
96 cvmx_fpa_setup_pool(pool, name, memory, buffer_size, buffers);
97 return 0;
98 }
99
100
101 /**
102 * @INTERNAL
103 * Allocate memory and initialize the FPA pools using memory
104 * from cvmx-bootmem. Specifying zero for the number of
105 * buffers will cause that FPA pool to not be setup. This is
106 * useful if you aren't using some of the hardware and want
107 * to save memory. Use cvmx_helper_initialize_fpa instead of
108 * this function directly.
109 *
110 * @param pip_pool Should always be CVMX_FPA_PACKET_POOL
111 * @param pip_size Should always be CVMX_FPA_PACKET_POOL_SIZE
112 * @param pip_buffers
113 * Number of packet buffers.
114 * @param wqe_pool Should always be CVMX_FPA_WQE_POOL
115 * @param wqe_size Should always be CVMX_FPA_WQE_POOL_SIZE
116 * @param wqe_entries
117 * Number of work queue entries
118 * @param pko_pool Should always be CVMX_FPA_OUTPUT_BUFFER_POOL
119 * @param pko_size Should always be CVMX_FPA_OUTPUT_BUFFER_POOL_SIZE
120 * @param pko_buffers
121 * PKO Command buffers. You should at minimum have two per
122 * each PKO queue.
123 * @param tim_pool Should always be CVMX_FPA_TIMER_POOL
124 * @param tim_size Should always be CVMX_FPA_TIMER_POOL_SIZE
125 * @param tim_buffers
126 * TIM ring buffer command queues. At least two per timer bucket
127 * is recommended.
128 * @param dfa_pool Should always be CVMX_FPA_DFA_POOL
129 * @param dfa_size Should always be CVMX_FPA_DFA_POOL_SIZE
130 * @param dfa_buffers
131 * DFA command buffer. A relatively small (32 for example)
132 * number should work.
133 * @return Zero on success, non-zero if out of memory
134 */
__cvmx_helper_initialize_fpa(int pip_pool,int pip_size,int pip_buffers,int wqe_pool,int wqe_size,int wqe_entries,int pko_pool,int pko_size,int pko_buffers,int tim_pool,int tim_size,int tim_buffers,int dfa_pool,int dfa_size,int dfa_buffers)135 static int __cvmx_helper_initialize_fpa(int pip_pool, int pip_size, int pip_buffers,
136 int wqe_pool, int wqe_size, int wqe_entries,
137 int pko_pool, int pko_size, int pko_buffers,
138 int tim_pool, int tim_size, int tim_buffers,
139 int dfa_pool, int dfa_size, int dfa_buffers)
140 {
141 int status;
142
143 cvmx_fpa_enable();
144
145 if ((pip_buffers > 0) && (pip_buffers <= 64))
146 cvmx_dprintf("Warning: %d packet buffers may not be enough for hardware"
147 " prefetch. 65 or more is recommended.\n", pip_buffers);
148
149 if (pip_pool >= 0)
150 {
151 status = __cvmx_helper_initialize_fpa_pool(pip_pool, pip_size, pip_buffers,
152 "Packet Buffers");
153 if (status)
154 return status;
155 }
156
157 if (wqe_pool >= 0)
158 {
159 status = __cvmx_helper_initialize_fpa_pool(wqe_pool, wqe_size, wqe_entries,
160 "Work Queue Entries");
161 if (status)
162 return status;
163 }
164
165 if (pko_pool >= 0)
166 {
167 status = __cvmx_helper_initialize_fpa_pool(pko_pool, pko_size, pko_buffers,
168 "PKO Command Buffers");
169 if (status)
170 return status;
171 }
172
173 if (tim_pool >= 0)
174 {
175 status = __cvmx_helper_initialize_fpa_pool(tim_pool, tim_size, tim_buffers,
176 "TIM Command Buffers");
177 if (status)
178 return status;
179 }
180
181 if (dfa_pool >= 0)
182 {
183 status = __cvmx_helper_initialize_fpa_pool(dfa_pool, dfa_size, dfa_buffers,
184 "DFA Command Buffers");
185 if (status)
186 return status;
187 }
188
189 return 0;
190 }
191
192
193 /**
194 * Allocate memory and initialize the FPA pools using memory
195 * from cvmx-bootmem. Sizes of each element in the pools is
196 * controlled by the cvmx-config.h header file. Specifying
197 * zero for any parameter will cause that FPA pool to not be
198 * setup. This is useful if you aren't using some of the
199 * hardware and want to save memory.
200 *
201 * @param packet_buffers
202 * Number of packet buffers to allocate
203 * @param work_queue_entries
204 * Number of work queue entries
205 * @param pko_buffers
206 * PKO Command buffers. You should at minimum have two per
207 * each PKO queue.
208 * @param tim_buffers
209 * TIM ring buffer command queues. At least two per timer bucket
210 * is recommended.
211 * @param dfa_buffers
212 * DFA command buffer. A relatively small (32 for example)
213 * number should work.
214 * @return Zero on success, non-zero if out of memory
215 */
cvmx_helper_initialize_fpa(int packet_buffers,int work_queue_entries,int pko_buffers,int tim_buffers,int dfa_buffers)216 int cvmx_helper_initialize_fpa(int packet_buffers, int work_queue_entries,
217 int pko_buffers, int tim_buffers, int dfa_buffers)
218 {
219 #ifndef CVMX_FPA_PACKET_POOL
220 #define CVMX_FPA_PACKET_POOL -1
221 #define CVMX_FPA_PACKET_POOL_SIZE 0
222 #endif
223 #ifndef CVMX_FPA_WQE_POOL
224 #define CVMX_FPA_WQE_POOL -1
225 #define CVMX_FPA_WQE_POOL_SIZE 0
226 #endif
227 #ifndef CVMX_FPA_OUTPUT_BUFFER_POOL
228 #define CVMX_FPA_OUTPUT_BUFFER_POOL -1
229 #define CVMX_FPA_OUTPUT_BUFFER_POOL_SIZE 0
230 #endif
231 #ifndef CVMX_FPA_TIMER_POOL
232 #define CVMX_FPA_TIMER_POOL -1
233 #define CVMX_FPA_TIMER_POOL_SIZE 0
234 #endif
235 #ifndef CVMX_FPA_DFA_POOL
236 #define CVMX_FPA_DFA_POOL -1
237 #define CVMX_FPA_DFA_POOL_SIZE 0
238 #endif
239 return __cvmx_helper_initialize_fpa(
240 CVMX_FPA_PACKET_POOL, CVMX_FPA_PACKET_POOL_SIZE, packet_buffers,
241 CVMX_FPA_WQE_POOL, CVMX_FPA_WQE_POOL_SIZE, work_queue_entries,
242 CVMX_FPA_OUTPUT_BUFFER_POOL, CVMX_FPA_OUTPUT_BUFFER_POOL_SIZE, pko_buffers,
243 CVMX_FPA_TIMER_POOL, CVMX_FPA_TIMER_POOL_SIZE, tim_buffers,
244 CVMX_FPA_DFA_POOL, CVMX_FPA_DFA_POOL_SIZE, dfa_buffers);
245 }
246
247