Commit | Line | Data |
---|---|---|
c7eee084 | 1 | /* |
0235b0db | 2 | * SPDX-License-Identifier: MIT |
c7eee084 | 3 | * |
0235b0db | 4 | * Copyright (C) 2010-2019 EfficiOS Inc. and Linux Foundation |
c7eee084 PP |
5 | */ |
6 | ||
0235b0db MJ |
7 | #ifndef BABELTRACE2_GRAPH_QUERY_EXECUTOR_H |
8 | #define BABELTRACE2_GRAPH_QUERY_EXECUTOR_H | |
9 | ||
f38da6ca SM |
10 | /* IWYU pragma: private, include <babeltrace2/babeltrace.h> */ |
11 | ||
4fa90f32 PP |
12 | #ifndef __BT_IN_BABELTRACE_H |
13 | # error "Please include <babeltrace2/babeltrace.h> instead." | |
14 | #endif | |
15 | ||
3fadfbc0 | 16 | #include <babeltrace2/types.h> |
f4e38e70 PP |
17 | #include <babeltrace2/logging.h> |
18 | ||
c7eee084 PP |
19 | #ifdef __cplusplus |
20 | extern "C" { | |
21 | #endif | |
22 | ||
43c59509 PP |
23 | /*! |
24 | @defgroup api-qexec Query executor | |
25 | @ingroup api-graph | |
26 | ||
27 | @brief | |
28 | Executor of \bt_comp_cls object queries. | |
29 | ||
30 | A <strong><em>query executor</em></strong> is an executor of | |
31 | \bt_comp_cls object queries. | |
32 | ||
33 | A component class can implement a query method to offer one or more | |
34 | \em objects depending on the query parameters. | |
35 | ||
36 | Both the query parameters and the returned objects are \bt_p_val. | |
37 | ||
fb23741c | 38 | The query operation feature exists so that you can benefit from a |
43c59509 PP |
39 | component class's implementation to get information about a trace, a |
40 | stream, a distant server, and so on. For example, the | |
41 | <code>source.ctf.lttng-live</code> component class (see | |
42 | \bt_man{babeltrace2-source.ctf.lttng-live,7}) offers the \c sessions | |
43 | object to list the available | |
44 | <a href="https://lttng.org/docs/#doc-lttng-live">LTTng live</a> | |
45 | tracing session names and other properties. | |
46 | ||
47 | The semantics of the query parameters and the returned object are | |
48 | completely defined by the component class implementation: the library | |
49 | does not enforce or suggest any layout. The best way to know which | |
50 | objects you can query from a component class, what are the expected and | |
51 | optional parameters, and what the returned object contains is to read | |
52 | this component class's documentation. | |
53 | ||
54 | The purpose of the query executor itself is to keep some state for a | |
55 | specific query operation. For example, you can set a query executor's | |
56 | logging level with bt_query_executor_set_logging_level(); then a | |
57 | component class's query method can get the executor's current logging | |
58 | level with bt_query_executor_get_logging_level(). | |
59 | ||
60 | Also, the query executor is an interruptible object: a long or blocking | |
61 | query operation can run, checking whether the executor is interrupted | |
62 | periodically, while another thread or a signal handler can interrupt the | |
63 | executor. | |
64 | ||
65 | A query executor is a | |
66 | \ref api-fund-shared-object "shared object": get a new reference with | |
67 | bt_query_executor_get_ref() and put an existing reference with | |
68 | bt_query_executor_put_ref(). | |
69 | ||
70 | The type of a query executor is #bt_query_executor. | |
71 | ||
72 | Create a query executor with bt_query_executor_create() or | |
73 | bt_query_executor_create_with_method_data(). When you do so, you set the | |
74 | name of the object to query, from which component class to query the | |
75 | object, and what are the query parameters. You cannot change those | |
76 | properties once the query executor is created. With | |
77 | bt_query_executor_create_with_method_data(), you can also pass | |
78 | a custom, \bt_voidp pointer to the component class's | |
79 | query method. | |
80 | ||
81 | Perform a query operation with bt_query_executor_query(). This function | |
82 | can return #BT_QUERY_EXECUTOR_QUERY_STATUS_AGAIN, in which case you can | |
83 | try to perform a query operation again later. It can also return | |
84 | #BT_QUERY_EXECUTOR_QUERY_STATUS_UNKNOWN_OBJECT, which means the | |
85 | component class does not offer the requested object. | |
86 | ||
87 | To interrupt a running query operation, either: | |
88 | ||
89 | - Borrow the query executor's default \bt_intr with | |
90 | bt_query_executor_borrow_default_interrupter() and set it with | |
91 | bt_interrupter_set(). | |
92 | ||
93 | When you call bt_query_executor_create() or | |
94 | bt_query_executor_create_with_method_data(), the returned query | |
95 | executor has a default interrupter. | |
96 | ||
97 | - Add your own interrupter with bt_query_executor_add_interrupter() | |
98 | \em before you perform the query operation with | |
99 | bt_query_executor_query(). | |
100 | ||
101 | Then, set the interrupter with bt_interrupter_set(). | |
102 | ||
103 | <h1>Property</h1> | |
104 | ||
105 | A query executor has the following property: | |
106 | ||
107 | <dl> | |
108 | <dt> | |
109 | \anchor api-qexec-prop-log-lvl | |
110 | Logging level | |
111 | </dt> | |
112 | <dd> | |
113 | Logging level of the query executor's query operations. | |
114 | ||
115 | Use bt_query_executor_set_logging_level() and | |
116 | bt_query_executor_get_logging_level(). | |
117 | </dd> | |
118 | </dl> | |
119 | */ | |
120 | ||
121 | /*! @{ */ | |
122 | ||
123 | /*! | |
124 | @name Type | |
125 | @{ | |
126 | ||
127 | @typedef struct bt_query_executor bt_query_executor; | |
128 | ||
129 | @brief | |
130 | Query executor. | |
131 | ||
132 | @} | |
133 | */ | |
134 | ||
135 | /*! | |
136 | @name Creation | |
137 | @{ | |
138 | */ | |
139 | ||
140 | /*! | |
141 | @brief | |
142 | Alias of bt_query_executor_create_with_method_data() | |
143 | with the \bt_p{method_data} parameter set to \c NULL. | |
144 | */ | |
0d72b8c3 | 145 | extern |
3c729b9a | 146 | bt_query_executor *bt_query_executor_create( |
43c59509 PP |
147 | const bt_component_class *component_class, |
148 | const char *object_name, const bt_value *params); | |
149 | ||
150 | /*! | |
151 | @brief | |
152 | Creates a query executor to query the object named | |
153 | \bt_p{object_name} from the \bt_comp_cls \bt_p{component_class} with | |
154 | the parameters \bt_p{params} and the query user data | |
155 | \bt_p{method_data}. | |
156 | ||
157 | When you call bt_query_executor_query() with the returned query | |
158 | executor, the query method of \bt_p{component_class} receives: | |
159 | ||
160 | - \bt_p{object_name} as its own \bt_p{object_name} parameter. | |
0d72b8c3 | 161 | |
43c59509 PP |
162 | - \bt_p{params} as its own \bt_p{params} parameter |
163 | (or #bt_value_null if \bt_p{params} is \c NULL). | |
164 | ||
165 | - \bt_p{method_data} as its own \bt_p{method_data} parameter. | |
166 | ||
167 | @param[in] component_class | |
168 | Component class from which to query the object named | |
169 | \bt_p{object_name}. | |
170 | @param[in] object_name | |
171 | Name of the object to query from \bt_p{component_class}. | |
172 | @param[in] params | |
173 | @parblock | |
174 | Parameters for the query operation performed by the query executor | |
175 | to create. | |
176 | ||
177 | Unlike the \bt_p{params} parameter of | |
97346400 | 178 | the <code>bt_graph_add_*_component*()</code> |
43c59509 PP |
179 | functions (see \ref api-graph), this parameter does not need to |
180 | be a \bt_map_val. | |
181 | ||
182 | Can be \c NULL (equivalent to passing #bt_value_null). | |
183 | @endparblock | |
184 | @param[in] method_data | |
185 | User data passed as is to the query method of \bt_p{component_class} | |
186 | when you call bt_query_executor_query(). | |
187 | ||
188 | @returns | |
189 | New query executor reference, or \c NULL on memory error. | |
190 | ||
191 | @bt_pre_not_null{component_class} | |
192 | @bt_pre_not_null{object} | |
193 | ||
194 | @bt_post_success_frozen{component_class} | |
195 | @bt_post_success_frozen{params} | |
196 | */ | |
7c14d641 PP |
197 | extern |
198 | bt_query_executor *bt_query_executor_create_with_method_data( | |
43c59509 PP |
199 | const bt_component_class *component_class, |
200 | const char *object_name, const bt_value *params, | |
201 | void *method_data); | |
202 | ||
203 | /*! @} */ | |
7c14d641 | 204 | |
43c59509 PP |
205 | /*! |
206 | @name Query operation | |
207 | @{ | |
208 | */ | |
209 | ||
210 | /*! | |
211 | @brief | |
212 | Status codes for bt_query_executor_query(). | |
213 | */ | |
d24d5663 | 214 | typedef enum bt_query_executor_query_status { |
43c59509 PP |
215 | /*! |
216 | @brief | |
217 | Success. | |
218 | */ | |
d24d5663 | 219 | BT_QUERY_EXECUTOR_QUERY_STATUS_OK = __BT_FUNC_STATUS_OK, |
43c59509 PP |
220 | |
221 | /*! | |
222 | @brief | |
223 | Unknown object to query. | |
224 | */ | |
225 | BT_QUERY_EXECUTOR_QUERY_STATUS_UNKNOWN_OBJECT = __BT_FUNC_STATUS_UNKNOWN_OBJECT, | |
226 | ||
227 | /*! | |
228 | @brief | |
229 | Try again. | |
230 | */ | |
d24d5663 | 231 | BT_QUERY_EXECUTOR_QUERY_STATUS_AGAIN = __BT_FUNC_STATUS_AGAIN, |
43c59509 PP |
232 | |
233 | /*! | |
234 | @brief | |
235 | Out of memory. | |
236 | */ | |
d24d5663 | 237 | BT_QUERY_EXECUTOR_QUERY_STATUS_MEMORY_ERROR = __BT_FUNC_STATUS_MEMORY_ERROR, |
43c59509 PP |
238 | |
239 | /*! | |
240 | @brief | |
241 | Other error. | |
242 | */ | |
243 | BT_QUERY_EXECUTOR_QUERY_STATUS_ERROR = __BT_FUNC_STATUS_ERROR, | |
d24d5663 PP |
244 | } bt_query_executor_query_status; |
245 | ||
43c59509 PP |
246 | /*! |
247 | @brief | |
248 | Performs a query operation using the query executor | |
249 | \bt_p{query_executor}, setting \bt_p{*result} to the operation's | |
250 | result on success. | |
251 | ||
252 | This function calls the query executor's target \bt_comp_cls's | |
253 | query method, passing: | |
254 | ||
255 | - The object name of \bt_p{query_executor} as the | |
256 | \bt_p{object_name} parameter. | |
257 | ||
258 | - The query parameters of \bt_p{query_executor} as the | |
259 | \bt_p{params} parameter. | |
260 | ||
261 | - The query user data of \bt_p{query_executor} as the \bt_p{method_data} | |
262 | parameter. | |
263 | ||
264 | The three items above were set when you created \bt_p{query_executor} | |
265 | with bt_query_executor_create() or | |
266 | bt_query_executor_create_with_method_data(). | |
267 | ||
268 | @param[in] query_executor | |
269 | Query executor to use to execute the query operation. | |
270 | @param[out] result | |
271 | <strong>On success</strong>, \bt_p{*result} is a \em strong | |
272 | reference of the query operation's result. | |
273 | ||
274 | @retval #BT_QUERY_EXECUTOR_QUERY_STATUS_OK | |
275 | Success. | |
276 | @retval #BT_QUERY_EXECUTOR_QUERY_STATUS_UNKNOWN_OBJECT | |
277 | Unknown object to query. | |
278 | @retval #BT_QUERY_EXECUTOR_QUERY_STATUS_AGAIN | |
279 | Try again. | |
280 | @retval #BT_QUERY_EXECUTOR_QUERY_STATUS_MEMORY_ERROR | |
281 | Out of memory. | |
282 | @retval #BT_QUERY_EXECUTOR_QUERY_STATUS_ERROR | |
283 | Other error. | |
284 | ||
285 | @bt_pre_not_null{query_executor} | |
286 | @bt_pre_not_null{result} | |
287 | */ | |
0d72b8c3 | 288 | extern |
d24d5663 | 289 | bt_query_executor_query_status bt_query_executor_query( |
3c729b9a | 290 | bt_query_executor *query_executor, const bt_value **result); |
c7eee084 | 291 | |
43c59509 PP |
292 | /*! @} */ |
293 | ||
294 | /*! | |
295 | @name Property | |
296 | @{ | |
297 | */ | |
298 | ||
299 | /*! | |
300 | @brief | |
301 | Status codes for bt_query_executor_set_logging_level(). | |
302 | */ | |
303 | typedef enum bt_query_executor_set_logging_level_status { | |
304 | /*! | |
305 | @brief | |
306 | Success. | |
307 | */ | |
308 | BT_QUERY_EXECUTOR_SET_LOGGING_LEVEL_STATUS_OK = __BT_FUNC_STATUS_OK, | |
309 | } bt_query_executor_set_logging_level_status; | |
310 | ||
311 | /*! | |
312 | @brief | |
313 | Sets the logging level of the query executor \bt_p{query_executor} | |
314 | to \bt_p{logging_level}. | |
315 | ||
316 | See the \ref api-qexec-prop-log-lvl "logging level" property. | |
317 | ||
318 | @param[in] query_executor | |
319 | Query executor of which to set the logging level to | |
320 | \bt_p{logging_level}. | |
321 | @param[in] logging_level | |
322 | New logging level of \bt_p{query_executor}. | |
323 | ||
324 | @retval #BT_QUERY_EXECUTOR_SET_LOGGING_LEVEL_STATUS_OK | |
325 | Success. | |
326 | ||
327 | @bt_pre_not_null{query_executor} | |
328 | ||
329 | @sa bt_stream_class_get_logging_level() — | |
330 | Returns the logging level of a query executor. | |
331 | */ | |
332 | extern bt_query_executor_set_logging_level_status | |
333 | bt_query_executor_set_logging_level(bt_query_executor *query_executor, | |
334 | bt_logging_level logging_level); | |
335 | ||
336 | /*! | |
337 | @brief | |
338 | Returns the logging level of the query executor | |
339 | \bt_p{query_executor}. | |
340 | ||
341 | See the \ref api-qexec-prop-log-lvl "logging level" property. | |
342 | ||
343 | @param[in] query_executor | |
344 | Query executor of which to get the logging level. | |
345 | ||
346 | @returns | |
347 | Logging level of \bt_p{query_executor}. | |
348 | ||
349 | @bt_pre_not_null{query_executor} | |
350 | ||
351 | @sa bt_query_executor_set_logging_level() — | |
352 | Sets the logging level of a query executor. | |
353 | */ | |
354 | extern bt_logging_level bt_query_executor_get_logging_level( | |
355 | const bt_query_executor *query_executor); | |
356 | ||
357 | /*! @} */ | |
358 | ||
359 | /*! | |
360 | @name Interruption | |
361 | @{ | |
362 | */ | |
363 | ||
364 | /*! | |
365 | @brief | |
366 | Status codes for bt_query_executor_add_interrupter(). | |
367 | */ | |
9b4f9b42 | 368 | typedef enum bt_query_executor_add_interrupter_status { |
43c59509 PP |
369 | /*! |
370 | @brief | |
371 | Success. | |
372 | */ | |
2c938e2f | 373 | BT_QUERY_EXECUTOR_ADD_INTERRUPTER_STATUS_OK = __BT_FUNC_STATUS_OK, |
43c59509 PP |
374 | |
375 | /*! | |
376 | @brief | |
377 | Out of memory. | |
378 | */ | |
2c938e2f | 379 | BT_QUERY_EXECUTOR_ADD_INTERRUPTER_STATUS_MEMORY_ERROR = __BT_FUNC_STATUS_MEMORY_ERROR, |
9b4f9b42 | 380 | } bt_query_executor_add_interrupter_status; |
d24d5663 | 381 | |
43c59509 PP |
382 | /*! |
383 | @brief | |
384 | Adds the \bt_intr \bt_p{interrupter} to the query executor | |
385 | \bt_p{query_executor}. | |
386 | ||
387 | A \bt_comp_cls query method can check whether or not its executor is | |
388 | interrupted (any of its interrupters, including its default interrupter, | |
389 | is set) with bt_query_executor_is_interrupted(). | |
390 | ||
391 | @note | |
392 | @parblock | |
393 | bt_query_executor_create() and | |
394 | bt_query_executor_create_with_method_data() return a query executor | |
395 | which comes with its own <em>default interrupter</em>. | |
396 | ||
397 | Instead of adding your own interrupter to \bt_p{query_executor}, you | |
398 | can set its default interrupter with | |
399 | ||
400 | @code | |
401 | bt_interrupter_set(bt_query_executor_borrow_default_interrupter()); | |
402 | @endcode | |
403 | @endparblock | |
404 | ||
405 | @param[in] query_executor | |
406 | Query executor to which to add \bt_p{interrupter}. | |
407 | @param[in] interrupter | |
408 | Interrupter to add to \bt_p{query_executor}. | |
409 | ||
410 | @retval #BT_QUERY_EXECUTOR_ADD_INTERRUPTER_STATUS_OK | |
411 | Success. | |
412 | @retval #BT_QUERY_EXECUTOR_ADD_INTERRUPTER_STATUS_MEMORY_ERROR | |
413 | Out of memory. | |
414 | ||
415 | @bt_pre_not_null{query_executor} | |
416 | @bt_pre_not_null{interrupter} | |
417 | ||
418 | @sa bt_query_executor_borrow_default_interrupter() — | |
419 | Borrows the default interrupter from a query executor. | |
420 | */ | |
9b4f9b42 PP |
421 | extern bt_query_executor_add_interrupter_status |
422 | bt_query_executor_add_interrupter(bt_query_executor *query_executor, | |
423 | const bt_interrupter *interrupter); | |
424 | ||
43c59509 PP |
425 | /*! |
426 | @brief | |
427 | Borrows the default \bt_intr from the query executor | |
428 | \bt_p{query_executor}. | |
429 | ||
430 | @param[in] query_executor | |
431 | Query executor from which to borrow the default interrupter. | |
432 | ||
433 | @returns | |
434 | @parblock | |
435 | \em Borrowed reference of the default interrupter of | |
436 | \bt_p{query_executor}. | |
437 | ||
438 | The returned pointer remains valid as long as \bt_p{query_executor} | |
439 | exists. | |
440 | @endparblock | |
441 | ||
442 | @bt_pre_not_null{query_executor} | |
443 | ||
444 | @sa bt_query_executor_add_interrupter() — | |
445 | Adds an interrupter to a query executor. | |
446 | */ | |
88d1a0b7 SM |
447 | extern bt_interrupter *bt_query_executor_borrow_default_interrupter( |
448 | bt_query_executor *query_executor); | |
c7eee084 | 449 | |
43c59509 PP |
450 | /*! |
451 | @brief | |
452 | Returns whether or not the query executor \bt_p{query_executor} | |
453 | is interrupted, that is, whether or not any of its \bt_p_intr, | |
454 | including its default interrupter, is set. | |
3c729b9a | 455 | |
43c59509 PP |
456 | @param[in] query_executor |
457 | Query executor to check. | |
458 | ||
459 | @returns | |
460 | #BT_TRUE if \bt_p{query_executor} is interrupted (any of its | |
461 | interrupters is set). | |
462 | ||
463 | @bt_pre_not_null{query_executor} | |
464 | */ | |
465 | extern bt_bool bt_query_executor_is_interrupted( | |
466 | const bt_query_executor *query_executor); | |
467 | ||
468 | /*! @} */ | |
469 | ||
470 | /*! | |
471 | @name Reference count | |
472 | @{ | |
473 | */ | |
474 | ||
475 | /*! | |
476 | @brief | |
477 | Increments the \ref api-fund-shared-object "reference count" of | |
478 | the query executor \bt_p{query_executor}. | |
479 | ||
480 | @param[in] query_executor | |
481 | @parblock | |
482 | Query executor of which to increment the reference count. | |
483 | ||
484 | Can be \c NULL. | |
485 | @endparblock | |
486 | ||
487 | @sa bt_query_executor_put_ref() — | |
488 | Decrements the reference count of a query executor. | |
489 | */ | |
490 | extern void bt_query_executor_get_ref(const bt_query_executor *query_executor); | |
491 | ||
492 | /*! | |
493 | @brief | |
494 | Decrements the \ref api-fund-shared-object "reference count" of | |
495 | the query executor \bt_p{query_executor}. | |
496 | ||
497 | @param[in] query_executor | |
498 | @parblock | |
499 | Query executor of which to decrement the reference count. | |
500 | ||
501 | Can be \c NULL. | |
502 | @endparblock | |
503 | ||
504 | @sa bt_query_executor_get_ref() — | |
505 | Increments the reference count of a query executor. | |
506 | */ | |
507 | extern void bt_query_executor_put_ref(const bt_query_executor *query_executor); | |
508 | ||
509 | /*! | |
510 | @brief | |
511 | Decrements the reference count of the query executor | |
512 | \bt_p{_query_executor}, and then sets \bt_p{_query_executor} to \c NULL. | |
513 | ||
514 | @param _query_executor | |
515 | @parblock | |
516 | Query executor of which to decrement the reference count. | |
517 | ||
518 | Can contain \c NULL. | |
519 | @endparblock | |
520 | ||
521 | @bt_pre_assign_expr{_query_executor} | |
522 | */ | |
523 | #define BT_QUERY_EXECUTOR_PUT_REF_AND_RESET(_query_executor) \ | |
524 | do { \ | |
525 | bt_query_executor_put_ref(_query_executor); \ | |
526 | (_query_executor) = NULL; \ | |
527 | } while (0) | |
528 | ||
529 | /*! | |
530 | @brief | |
531 | Decrements the reference count of the query executor \bt_p{_dst}, sets | |
532 | \bt_p{_dst} to \bt_p{_src}, and then sets \bt_p{_src} to \c NULL. | |
533 | ||
534 | This macro effectively moves a query executor reference from the expression | |
535 | \bt_p{_src} to the expression \bt_p{_dst}, putting the existing | |
536 | \bt_p{_dst} reference. | |
537 | ||
538 | @param _dst | |
539 | @parblock | |
540 | Destination expression. | |
541 | ||
542 | Can contain \c NULL. | |
543 | @endparblock | |
544 | @param _src | |
545 | @parblock | |
546 | Source expression. | |
547 | ||
548 | Can contain \c NULL. | |
549 | @endparblock | |
550 | ||
551 | @bt_pre_assign_expr{_dst} | |
552 | @bt_pre_assign_expr{_src} | |
553 | */ | |
554 | #define BT_QUERY_EXECUTOR_MOVE_REF(_dst, _src) \ | |
555 | do { \ | |
556 | bt_query_executor_put_ref(_dst); \ | |
557 | (_dst) = (_src); \ | |
558 | (_src) = NULL; \ | |
559 | } while (0) | |
560 | ||
561 | /*! @} */ | |
562 | ||
563 | /*! @} */ | |
3c729b9a | 564 | |
c7eee084 PP |
565 | #ifdef __cplusplus |
566 | } | |
567 | #endif | |
568 | ||
924dc299 | 569 | #endif /* BABELTRACE2_GRAPH_QUERY_EXECUTOR_H */ |