1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
|
/* SPDX-License-Identifier: GPL-2.0 */
/*
* Copyright (C) 2020 Marvell International Ltd.
*
* Interface to the hardware Free Pool Allocator.
*/
#ifndef __CVMX_FPA_H__
#define __CVMX_FPA_H__
#include "cvmx-scratch.h"
#include "cvmx-fpa-defs.h"
#include "cvmx-fpa1.h"
#include "cvmx-fpa3.h"
#define CVMX_FPA_MIN_BLOCK_SIZE 128
#define CVMX_FPA_ALIGNMENT 128
#define CVMX_FPA_POOL_NAME_LEN 16
/* On CN78XX in backward-compatible mode, pool is mapped to AURA */
#define CVMX_FPA_NUM_POOLS \
(octeon_has_feature(OCTEON_FEATURE_FPA3) ? cvmx_fpa3_num_auras() : CVMX_FPA1_NUM_POOLS)
/**
* Structure to store FPA pool configuration parameters.
*/
struct cvmx_fpa_pool_config {
s64 pool_num;
u64 buffer_size;
u64 buffer_count;
};
typedef struct cvmx_fpa_pool_config cvmx_fpa_pool_config_t;
/**
* Return the name of the pool
*
* @param pool_num Pool to get the name of
* Return: The name
*/
const char *cvmx_fpa_get_name(int pool_num);
/**
* Initialize FPA per node
*/
int cvmx_fpa_global_init_node(int node);
/**
* Enable the FPA
*/
static inline void cvmx_fpa_enable(void)
{
if (!octeon_has_feature(OCTEON_FEATURE_FPA3))
cvmx_fpa1_enable();
else
cvmx_fpa_global_init_node(cvmx_get_node_num());
}
/**
* Disable the FPA
*/
static inline void cvmx_fpa_disable(void)
{
if (!octeon_has_feature(OCTEON_FEATURE_FPA3))
cvmx_fpa1_disable();
/* FPA3 does not have a disable function */
}
/**
* @INTERNAL
* @deprecated OBSOLETE
*
* Kept for transition assistance only
*/
static inline void cvmx_fpa_global_initialize(void)
{
cvmx_fpa_global_init_node(cvmx_get_node_num());
}
/**
* @INTERNAL
*
* Convert FPA1 style POOL into FPA3 AURA in
* backward compatibility mode.
*/
static inline cvmx_fpa3_gaura_t cvmx_fpa1_pool_to_fpa3_aura(cvmx_fpa1_pool_t pool)
{
if ((octeon_has_feature(OCTEON_FEATURE_FPA3))) {
unsigned int node = cvmx_get_node_num();
cvmx_fpa3_gaura_t aura = __cvmx_fpa3_gaura(node, pool);
return aura;
}
return CVMX_FPA3_INVALID_GAURA;
}
/**
* Get a new block from the FPA
*
* @param pool Pool to get the block from
* Return: Pointer to the block or NULL on failure
*/
static inline void *cvmx_fpa_alloc(u64 pool)
{
/* FPA3 is handled differently */
if ((octeon_has_feature(OCTEON_FEATURE_FPA3))) {
return cvmx_fpa3_alloc(cvmx_fpa1_pool_to_fpa3_aura(pool));
} else {
return cvmx_fpa1_alloc(pool);
}
}
/**
* Asynchronously get a new block from the FPA
*
* The result of cvmx_fpa_async_alloc() may be retrieved using
* cvmx_fpa_async_alloc_finish().
*
* @param scr_addr Local scratch address to put response in. This is a byte
* address but must be 8 byte aligned.
* @param pool Pool to get the block from
*/
static inline void cvmx_fpa_async_alloc(u64 scr_addr, u64 pool)
{
if ((octeon_has_feature(OCTEON_FEATURE_FPA3))) {
return cvmx_fpa3_async_alloc(scr_addr, cvmx_fpa1_pool_to_fpa3_aura(pool));
} else
return cvmx_fpa1_async_alloc(scr_addr, pool);
}
/**
* Retrieve the result of cvmx_fpa_async_alloc
*
* @param scr_addr The Local scratch address. Must be the same value
* passed to cvmx_fpa_async_alloc().
*
* @param pool Pool the block came from. Must be the same value
* passed to cvmx_fpa_async_alloc.
*
* Return: Pointer to the block or NULL on failure
*/
static inline void *cvmx_fpa_async_alloc_finish(u64 scr_addr, u64 pool)
{
if ((octeon_has_feature(OCTEON_FEATURE_FPA3)))
return cvmx_fpa3_async_alloc_finish(scr_addr, cvmx_fpa1_pool_to_fpa3_aura(pool));
else
return cvmx_fpa1_async_alloc_finish(scr_addr, pool);
}
/**
* Free a block allocated with a FPA pool.
* Does NOT provide memory ordering in cases where the memory block was
* modified by the core.
*
* @param ptr Block to free
* @param pool Pool to put it in
* @param num_cache_lines
* Cache lines to invalidate
*/
static inline void cvmx_fpa_free_nosync(void *ptr, u64 pool, u64 num_cache_lines)
{
/* FPA3 is handled differently */
if ((octeon_has_feature(OCTEON_FEATURE_FPA3)))
cvmx_fpa3_free_nosync(ptr, cvmx_fpa1_pool_to_fpa3_aura(pool), num_cache_lines);
else
cvmx_fpa1_free_nosync(ptr, pool, num_cache_lines);
}
/**
* Free a block allocated with a FPA pool. Provides required memory
* ordering in cases where memory block was modified by core.
*
* @param ptr Block to free
* @param pool Pool to put it in
* @param num_cache_lines
* Cache lines to invalidate
*/
static inline void cvmx_fpa_free(void *ptr, u64 pool, u64 num_cache_lines)
{
if ((octeon_has_feature(OCTEON_FEATURE_FPA3)))
cvmx_fpa3_free(ptr, cvmx_fpa1_pool_to_fpa3_aura(pool), num_cache_lines);
else
cvmx_fpa1_free(ptr, pool, num_cache_lines);
}
/**
* Setup a FPA pool to control a new block of memory.
* This can only be called once per pool. Make sure proper
* locking enforces this.
*
* @param pool Pool to initialize
* @param name Constant character string to name this pool.
* String is not copied.
* @param buffer Pointer to the block of memory to use. This must be
* accessible by all processors and external hardware.
* @param block_size Size for each block controlled by the FPA
* @param num_blocks Number of blocks
*
* Return: the pool number on Success,
* -1 on failure
*/
int cvmx_fpa_setup_pool(int pool, const char *name, void *buffer, u64 block_size, u64 num_blocks);
int cvmx_fpa_shutdown_pool(int pool);
/**
* Gets the block size of buffer in specified pool
* @param pool Pool to get the block size from
* Return: Size of buffer in specified pool
*/
unsigned int cvmx_fpa_get_block_size(int pool);
int cvmx_fpa_is_pool_available(int pool_num);
u64 cvmx_fpa_get_pool_owner(int pool_num);
int cvmx_fpa_get_max_pools(void);
int cvmx_fpa_get_current_count(int pool_num);
int cvmx_fpa_validate_pool(int pool);
#endif /* __CVM_FPA_H__ */
|