1 /*!
2 * ======== Registry ========
3 * Register modules that are not statically configured
4 *
5 * This module provides a mechanism by which legacy C code can have its own
6 * module logging support, including having a name and its own diags mask.
7 *
8 * Without the `Registry`, all logging done by legacy C code is handled by the
9 * `xdc.runtime.Main` module. This means that all `{@link Log}` events will
10 * be marked as coming from "`xdc.runtime.Main`", and there is only a single
11 * diagnostics mask for the runtime control of logging across all legacy C
12 * code. The `Registry` module allows legacy C code to have the same granular
13 * control over logging as statically defined RTSC modules.
14 *
15 * To use the `Registry` module, legacy code must define the symbol
16 * `Registry_CURDESC` to be the name of an externally declared
17 * `Registery_Desc` structure. This symbol must be defined before the
18 * inclusion of any `xdc/runtime` header files. If any `xdc/runtime` header
19 * files are included before the definition of this symbol, the `Registry`
20 * module may not function properly.
21 *
22 * Note: by defining this symbol on the compile line, rather than in the
23 * file, one can easily compile code to be used in one of two environments:
24 * @p(nlist) 25 * - a fixed configuration environment where modules are registered
26 * via `{@link #addModule Registry_addModule()}`, or
27 *
28 * - a "normal" configurable environment in which this code is
29 * assumed to be part of the `{@link Main}` module.
30 * @p 31 * The `Registry_Desc` structure must then be registered by calling
32 * `{@link #addModule Registry_addModule()}`. The structure is typically
33 * registered and initialized within `main()`.
34 *
35 * For example:
36 *
37 * @p(code) 38 * //Define the required symbol, Registry_CURDESC, to this file's
39 * //Registry_Desc object
40 * #define Registry_CURDESC mainDesc
41 * #include <xdc/runtime/Registry.h>
42 *
43 * //Declare the Registry_Desc object, the name is unimportant
44 * Registry_Desc mainDesc;
45 *
46 * Int main(Int argc, String argv[]) {
47 *
48 * //Register this file as a module "main"
49 * Registry_addModule(&mainDesc, "main");
50 * @p 51 *
52 * Once registered, the legacy code may call `{@link Log}` APIs without any
53 * other change and the formatted `Log` events will show as coming from the
54 * registered modules. Also, the logging by the legacy code is now filtered
55 * by its own diagnostic mask. The bits of this mask can be set using
56 * `{@link Diags#setMask Diags_setMask}`.
57 *
58 * Continuing the previous example:
59 * @p(code) 60 * //Initialize the legacy code's diags mask to enable USER1.
61 * Diags_setMask("main=1");
62 * @p 63 *
64 * All events logged registered modules will be sent to the logger configured
65 * for the `Registry` module. For example, to configure the logger for use by
66 * all modules managed by `Registry`:
67 * @p(code) 68 * Registry.common$.logger = LoggerBuf.create();
69 * @p 70 *
71 * Since the registered modules are not known until runtime, it is not
72 * possible to statically configure the diagnostics masks for individual
73 * registered modules. However, it is possible to configure diagnostics
74 * categories to be permanently off or on for ALL registered modules. This
75 * is done by configuring the diagnostic mask for the `Registry` module.
76 * Diagnostic categories set to `{@link Diags#ALWAYS_OFF Diags.ALWAYS_OFF}`
77 * will be permanently off for all `Registry` modules. Categories set to
78 * `{@link Diags#ALWAYS_ON Diags.ALWAYS_ON}` will be
79 * permanently on for all modules managed by `Registry`.
80 *
81 * In order to enable runtime configuration of individual `Registry` module
82 * masks, all relevant diagnostic categories must be set to
83 * `{@link Diags#RUNTIME_OFF Diags.RUNTIME_OFF}` or
84 * `{@link Diags#RUNTIME_ON Diags.RUNTIME_ON}` in the `Registry` module's
85 * mask.
86 */
87 @CustomHeader
88 module Registry
89 {
90 /*!
91 * ======== Result ========
92 * Status codes
93 */
94 enum Result {
95 SUCCESS, /*! The module was added successfully */
96 ALLOC_FAILED, /*! reserved */
97 ALREADY_ADDED, /*! The module has already been added or another
98 * module with the same name is present
99 */
100 ALL_IDS_USED /*! No more module ids available for new modules */
101 };
102
103 /*!
104 * ======== RegDesc ========
105 * Registry module descriptor
106 */
107 typedef Types.RegDesc Desc;
108
109 /*!
110 * ======== addModule ========
111 * Add a runtime module to the registry with the specified name
112 *
113 * The `desc` parameter and the `modName` string provided must both be
114 * permanent since the `Registry` will maintain references to both of
115 * these.
116 *
117 * @param(desc) non-`NULL` pointer to a `{#Desc Registry_Desc}`
118 * structure.
119 * @param(modName) non-`NULL` string name of the module being registered.
120 *
121 * @a(returns) 122 * `Registry_addModule` returns one of the following
123 * `{@link #Result Result}` status values indicating success or the
124 * cause of failure:
125 * @p(blist) 126 * - `{@link #SUCCESS SUCCESS}`
127 * - `{@link #ALREADY_ADDED ALREADY_ADDED}`
128 * - `{@link #ALL_IDS_USED ALL_IDS_USED}` There are a total of 16,384 - 1
129 * module ids available for use by `Registry`.
130 * @p 131 */
132 Result addModule(Desc *desc, String modName);
133
134 /*!
135 * ======== findByName ========
136 * Find the registered module with the given name
137 *
138 * @param(modName) non-`NULL` string name of a registered module
139 *
140 * @a(returns) 141 * If the name `modName` is registered via
142 * `{@link #addModule Registry_addModule()}`, this function
143 * returns the pointer to the registered `Registry_Desc` structure;
144 * otherwise it returns `NULL`.
145 */
146 Desc *findByName(String modName);
147
148 /*!
149 * ======== findByNamePattern ========
150 * @_nodoc 151 * Find all registered modules matching the specified pattern.
152 *
153 * This API is intended for use by Diags_setMask.
154 *
155 * The name pattern can be an exact module name or it can contain '%'
156 * as a wildcard. The `len` parameter is the string length of the pattern.
157 *
158 * This function returns one module at a time, but can be called
159 * repeatedly to find all modules matching the pattern. On the first
160 * call, pass `NULL` as the `prev` parameter. In all following calls,
161 * pass the last returned descriptor. This function returns `NULL` when
162 * it can't find any more modules matching the name pattern.
163 */
164 Desc *findByNamePattern(String namePat, Int len, Desc *prev);
165
166 /*!
167 * ======== findById ========
168 * Find registered module's descriptor from it's module ID
169 *
170 * @param(mid) any module id
171 *
172 * @a(returns) 173 * If the ID `mid` is registered via
174 * `{@link #addModule Registry_addModule()}`, this function
175 * returns the pointer to the registered `Registry_Desc` structure;
176 * otherwise it returns `NULL`.
177 */
178 Desc *findById(Types.ModuleId mid);
179
180 /*!
181 * ======== getMask ========
182 * Get the specified module's diagnostic mask
183 *
184 * @param(modName) non-`NULL` string name of a registered module
185 * @param(mask) non-`NULL` pointer to a mask to be initialized
186 * to the the current state of the diagnostics mask
187 * associated with `modName`
188 *
189 * @a(returns) 190 * The function returns `TRUE` if `name` identifies a registered module;
191 * otherwise, it return `FALSE`.
192 */
193 Bool getMask(String name, Types.DiagsMask *mask);
194
195 /*!
196 * ======== isMember ========
197 * Determines if the specified module ID belongs to a registered module
198 *
199 * @param(mid) any module id
200 *
201 * @a(returns) 202 * This function returns `TRUE` if and only if the specified module id
203 * is a valid `Registry` module id. It does not search registered
204 * module ids, but simply checks if the id is within the range of valid
205 * `Registry` module ids.
206 */
207 Bool isMember(Types.ModuleId mid);
208
209 /*!
210 * ======== getNextModule ========
211 * Scan the current list of registered modules
212 *
213 * This function used to scan the list of all `Registry_Desc` structures
214 * currently being managed by the `Registry` module.
215 *
216 * @param(desc) optionally `NULL` pointer to a `Registry_Desc`
217 * structure. If `desc` is `NULL`, a pointer to the
218 * first structure is returned. If `desc` is non-`NULL`
219 * and equal to a previous return value of this function,
220 * a pointer to the "next" `Registry_Desc` structure
221 * is returned.
222 *
223 * @a(returns) 224 * This function returns a non-`NULL` pointer to one of the
225 * `Registry_Desc` structures added via `Registry_Desc` structures or
226 * `NULL` in the case that
227 * @p(blist) 228 * - there are no more module's in the list after `desc`, or
229 * - there are no modules registered
230 * @p 231 */
232 Desc *getNextModule(Desc *desc);
233
234 /*!
235 * ======== getModuleName ========
236 * Get the module name associated with a specified module descriptor
237 *
238 * @param(desc) non-`NULL` pointer to a `{#Desc Registry_Desc}`
239 * structure.
240 *
241 * @a(returns) 242 * If the specified module descriptor has been initialized via a
243 * successful call to `{@link #addModule Registry_addModule()}`, this
244 * function returns the module name passed `Registry_addModule()`;
245 * otherwise, its return value is indeterminate.
246 */
247 String getModuleName(Desc *desc);
248
249 /*!
250 * ======== getModuleId ========
251 * Get the module id associated with a specified module descriptor
252 *
253 * @param(desc) non-`NULL` pointer to a `{#Desc Registry_Desc}`
254 * structure.
255 *
256 * @a(returns) 257 * If the specified module descriptor has been initialized via a
258 * successful call to `{@link #addModule Registry_addModule()}`, this
259 * function returns the module id assigned by `Registry_addModule()`;
260 * otherwise, its return value is indeterminate.
261 */
262 Types.ModuleId getModuleId(Desc *desc);
263
264 internal:
265
266 Desc *findByNameInList(String name, Desc *listHead);
267 Void newModule(Desc *desc, String modName);
268 Bool matchPattern(String pattern, Int len, String modName);
269
270 /*
271 * ======== Module_State ========
272 */
273 struct Module_State {
274 Desc *listHead;
275 Types.ModuleId curId;
276 }
277 }
278 /*
279 * @(#) xdc.runtime; 2, 1, 0,296; 11-16-2010 11:20:24; /db/ztree/library/trees/xdc/xdc-v53x/src/packages/
280 */
281