Fix: filter validator: refuse string and star glob input to bitwise operation
[lttng-modules.git] / src / lttng-filter-validator.c
1 /* SPDX-License-Identifier: MIT
2 *
3 * lttng-filter-validator.c
4 *
5 * LTTng modules filter bytecode validator.
6 *
7 * Copyright (C) 2010-2016 Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
8 */
9
10 #include <linux/types.h>
11 #include <linux/jhash.h>
12 #include <linux/slab.h>
13
14 #include <wrapper/list.h>
15 #include <lttng/filter.h>
16
17 #define MERGE_POINT_TABLE_BITS 7
18 #define MERGE_POINT_TABLE_SIZE (1U << MERGE_POINT_TABLE_BITS)
19
20 /* merge point table node */
21 struct mp_node {
22 struct hlist_node node;
23
24 /* Context at merge point */
25 struct vstack stack;
26 unsigned long target_pc;
27 };
28
29 struct mp_table {
30 struct hlist_head mp_head[MERGE_POINT_TABLE_SIZE];
31 };
32
33 static
34 int lttng_hash_match(struct mp_node *mp_node, unsigned long key_pc)
35 {
36 if (mp_node->target_pc == key_pc)
37 return 1;
38 else
39 return 0;
40 }
41
42 static
43 int merge_points_compare(const struct vstack *stacka,
44 const struct vstack *stackb)
45 {
46 int i, len;
47
48 if (stacka->top != stackb->top)
49 return 1;
50 len = stacka->top + 1;
51 WARN_ON_ONCE(len < 0);
52 for (i = 0; i < len; i++) {
53 if (stacka->e[i].type != stackb->e[i].type)
54 return 1;
55 }
56 return 0;
57 }
58
59 static
60 int merge_point_add_check(struct mp_table *mp_table, unsigned long target_pc,
61 const struct vstack *stack)
62 {
63 struct mp_node *mp_node;
64 unsigned long hash = jhash_1word(target_pc, 0);
65 struct hlist_head *head;
66 struct mp_node *lookup_node;
67 int found = 0;
68
69 dbg_printk("Filter: adding merge point at offset %lu, hash %lu\n",
70 target_pc, hash);
71 mp_node = kzalloc(sizeof(struct mp_node), GFP_KERNEL);
72 if (!mp_node)
73 return -ENOMEM;
74 mp_node->target_pc = target_pc;
75 memcpy(&mp_node->stack, stack, sizeof(mp_node->stack));
76
77 head = &mp_table->mp_head[hash & (MERGE_POINT_TABLE_SIZE - 1)];
78 lttng_hlist_for_each_entry(lookup_node, head, node) {
79 if (lttng_hash_match(lookup_node, target_pc)) {
80 found = 1;
81 break;
82 }
83 }
84 if (found) {
85 /* Key already present */
86 dbg_printk("Filter: compare merge points for offset %lu, hash %lu\n",
87 target_pc, hash);
88 kfree(mp_node);
89 if (merge_points_compare(stack, &lookup_node->stack)) {
90 printk(KERN_WARNING "LTTng: filter: Merge points differ for offset %lu\n",
91 target_pc);
92 return -EINVAL;
93 }
94 } else {
95 hlist_add_head(&mp_node->node, head);
96 }
97 return 0;
98 }
99
100 /*
101 * Binary comparators use top of stack and top of stack -1.
102 */
103 static
104 int bin_op_compare_check(struct vstack *stack, const filter_opcode_t opcode,
105 const char *str)
106 {
107 if (unlikely(!vstack_ax(stack) || !vstack_bx(stack)))
108 goto error_empty;
109
110 switch (vstack_ax(stack)->type) {
111 default:
112 case REG_DOUBLE:
113 goto error_type;
114
115 case REG_STRING:
116 switch (vstack_bx(stack)->type) {
117 default:
118 case REG_DOUBLE:
119 goto error_type;
120 case REG_TYPE_UNKNOWN:
121 goto unknown;
122 case REG_STRING:
123 break;
124 case REG_STAR_GLOB_STRING:
125 if (opcode != FILTER_OP_EQ && opcode != FILTER_OP_NE) {
126 goto error_mismatch;
127 }
128 break;
129 case REG_S64:
130 goto error_mismatch;
131 }
132 break;
133 case REG_STAR_GLOB_STRING:
134 switch (vstack_bx(stack)->type) {
135 default:
136 case REG_DOUBLE:
137 goto error_type;
138 case REG_TYPE_UNKNOWN:
139 goto unknown;
140 case REG_STRING:
141 if (opcode != FILTER_OP_EQ && opcode != FILTER_OP_NE) {
142 goto error_mismatch;
143 }
144 break;
145 case REG_STAR_GLOB_STRING:
146 case REG_S64:
147 goto error_mismatch;
148 }
149 break;
150 case REG_S64:
151 switch (vstack_bx(stack)->type) {
152 default:
153 case REG_DOUBLE:
154 goto error_type;
155 case REG_TYPE_UNKNOWN:
156 goto unknown;
157 case REG_STRING:
158 case REG_STAR_GLOB_STRING:
159 goto error_mismatch;
160 case REG_S64:
161 break;
162 }
163 break;
164 case REG_TYPE_UNKNOWN:
165 switch (vstack_bx(stack)->type) {
166 default:
167 case REG_DOUBLE:
168 goto error_type;
169 case REG_TYPE_UNKNOWN:
170 case REG_STRING:
171 case REG_STAR_GLOB_STRING:
172 case REG_S64:
173 goto unknown;
174 }
175 break;
176 }
177 return 0;
178
179 unknown:
180 return 1;
181
182 error_empty:
183 printk(KERN_WARNING "LTTng: filter: empty stack for '%s' binary operator\n", str);
184 return -EINVAL;
185
186 error_mismatch:
187 printk(KERN_WARNING "LTTng: filter: type mismatch for '%s' binary operator\n", str);
188 return -EINVAL;
189
190 error_type:
191 printk(KERN_WARNING "LTTng: filter: unknown type for '%s' binary operator\n", str);
192 return -EINVAL;
193 }
194
195 /*
196 * Binary bitwise operators use top of stack and top of stack -1.
197 * Return 0 if typing is known to match, 1 if typing is dynamic
198 * (unknown), negative error value on error.
199 */
200 static
201 int bin_op_bitwise_check(struct vstack *stack, filter_opcode_t opcode,
202 const char *str)
203 {
204 if (unlikely(!vstack_ax(stack) || !vstack_bx(stack)))
205 goto error_empty;
206
207 switch (vstack_ax(stack)->type) {
208 default:
209 case REG_DOUBLE:
210 goto error_type;
211
212 case REG_TYPE_UNKNOWN:
213 switch (vstack_bx(stack)->type) {
214 default:
215 case REG_DOUBLE:
216 goto error_type;
217 case REG_TYPE_UNKNOWN:
218 case REG_S64:
219 goto unknown;
220 }
221 break;
222 case REG_S64:
223 switch (vstack_bx(stack)->type) {
224 default:
225 case REG_DOUBLE:
226 goto error_type;
227 case REG_TYPE_UNKNOWN:
228 goto unknown;
229 case REG_S64:
230 break;
231 }
232 break;
233 }
234 return 0;
235
236 unknown:
237 return 1;
238
239 error_empty:
240 printk(KERN_WARNING "LTTng: filter: empty stack for '%s' binary operator\n", str);
241 return -EINVAL;
242
243 error_type:
244 printk(KERN_WARNING "LTTng: filter: unknown type for '%s' binary operator\n", str);
245 return -EINVAL;
246 }
247
248 static
249 int validate_get_symbol(struct bytecode_runtime *bytecode,
250 const struct get_symbol *sym)
251 {
252 const char *str, *str_limit;
253 size_t len_limit;
254
255 if (sym->offset >= bytecode->p.bc->bc.len - bytecode->p.bc->bc.reloc_offset)
256 return -EINVAL;
257
258 str = bytecode->p.bc->bc.data + bytecode->p.bc->bc.reloc_offset + sym->offset;
259 str_limit = bytecode->p.bc->bc.data + bytecode->p.bc->bc.len;
260 len_limit = str_limit - str;
261 if (strnlen(str, len_limit) == len_limit)
262 return -EINVAL;
263 return 0;
264 }
265
266 /*
267 * Validate bytecode range overflow within the validation pass.
268 * Called for each instruction encountered.
269 */
270 static
271 int bytecode_validate_overflow(struct bytecode_runtime *bytecode,
272 char *start_pc, char *pc)
273 {
274 int ret = 0;
275
276 switch (*(filter_opcode_t *) pc) {
277 case FILTER_OP_UNKNOWN:
278 default:
279 {
280 printk(KERN_WARNING "LTTng: filter: unknown bytecode op %u\n",
281 (unsigned int) *(filter_opcode_t *) pc);
282 ret = -EINVAL;
283 break;
284 }
285
286 case FILTER_OP_RETURN:
287 case FILTER_OP_RETURN_S64:
288 {
289 if (unlikely(pc + sizeof(struct return_op)
290 > start_pc + bytecode->len)) {
291 ret = -ERANGE;
292 }
293 break;
294 }
295
296 /* binary */
297 case FILTER_OP_MUL:
298 case FILTER_OP_DIV:
299 case FILTER_OP_MOD:
300 case FILTER_OP_PLUS:
301 case FILTER_OP_MINUS:
302 case FILTER_OP_EQ_DOUBLE:
303 case FILTER_OP_NE_DOUBLE:
304 case FILTER_OP_GT_DOUBLE:
305 case FILTER_OP_LT_DOUBLE:
306 case FILTER_OP_GE_DOUBLE:
307 case FILTER_OP_LE_DOUBLE:
308 /* Floating point */
309 case FILTER_OP_EQ_DOUBLE_S64:
310 case FILTER_OP_NE_DOUBLE_S64:
311 case FILTER_OP_GT_DOUBLE_S64:
312 case FILTER_OP_LT_DOUBLE_S64:
313 case FILTER_OP_GE_DOUBLE_S64:
314 case FILTER_OP_LE_DOUBLE_S64:
315 case FILTER_OP_EQ_S64_DOUBLE:
316 case FILTER_OP_NE_S64_DOUBLE:
317 case FILTER_OP_GT_S64_DOUBLE:
318 case FILTER_OP_LT_S64_DOUBLE:
319 case FILTER_OP_GE_S64_DOUBLE:
320 case FILTER_OP_LE_S64_DOUBLE:
321 case FILTER_OP_LOAD_FIELD_REF_DOUBLE:
322 case FILTER_OP_GET_CONTEXT_REF_DOUBLE:
323 case FILTER_OP_LOAD_DOUBLE:
324 case FILTER_OP_CAST_DOUBLE_TO_S64:
325 case FILTER_OP_UNARY_PLUS_DOUBLE:
326 case FILTER_OP_UNARY_MINUS_DOUBLE:
327 case FILTER_OP_UNARY_NOT_DOUBLE:
328 {
329 printk(KERN_WARNING "LTTng: filter: unsupported bytecode op %u\n",
330 (unsigned int) *(filter_opcode_t *) pc);
331 ret = -EINVAL;
332 break;
333 }
334
335 case FILTER_OP_EQ:
336 case FILTER_OP_NE:
337 case FILTER_OP_GT:
338 case FILTER_OP_LT:
339 case FILTER_OP_GE:
340 case FILTER_OP_LE:
341 case FILTER_OP_EQ_STRING:
342 case FILTER_OP_NE_STRING:
343 case FILTER_OP_GT_STRING:
344 case FILTER_OP_LT_STRING:
345 case FILTER_OP_GE_STRING:
346 case FILTER_OP_LE_STRING:
347 case FILTER_OP_EQ_STAR_GLOB_STRING:
348 case FILTER_OP_NE_STAR_GLOB_STRING:
349 case FILTER_OP_EQ_S64:
350 case FILTER_OP_NE_S64:
351 case FILTER_OP_GT_S64:
352 case FILTER_OP_LT_S64:
353 case FILTER_OP_GE_S64:
354 case FILTER_OP_LE_S64:
355 case FILTER_OP_BIT_RSHIFT:
356 case FILTER_OP_BIT_LSHIFT:
357 case FILTER_OP_BIT_AND:
358 case FILTER_OP_BIT_OR:
359 case FILTER_OP_BIT_XOR:
360 {
361 if (unlikely(pc + sizeof(struct binary_op)
362 > start_pc + bytecode->len)) {
363 ret = -ERANGE;
364 }
365 break;
366 }
367
368 /* unary */
369 case FILTER_OP_UNARY_PLUS:
370 case FILTER_OP_UNARY_MINUS:
371 case FILTER_OP_UNARY_NOT:
372 case FILTER_OP_UNARY_PLUS_S64:
373 case FILTER_OP_UNARY_MINUS_S64:
374 case FILTER_OP_UNARY_NOT_S64:
375 case FILTER_OP_UNARY_BIT_NOT:
376 {
377 if (unlikely(pc + sizeof(struct unary_op)
378 > start_pc + bytecode->len)) {
379 ret = -ERANGE;
380 }
381 break;
382 }
383
384 /* logical */
385 case FILTER_OP_AND:
386 case FILTER_OP_OR:
387 {
388 if (unlikely(pc + sizeof(struct logical_op)
389 > start_pc + bytecode->len)) {
390 ret = -ERANGE;
391 }
392 break;
393 }
394
395 /* load field ref */
396 case FILTER_OP_LOAD_FIELD_REF:
397 {
398 printk(KERN_WARNING "LTTng: filter: Unknown field ref type\n");
399 ret = -EINVAL;
400 break;
401 }
402
403 /* get context ref */
404 case FILTER_OP_GET_CONTEXT_REF:
405 {
406 printk(KERN_WARNING "LTTng: filter: Unknown field ref type\n");
407 ret = -EINVAL;
408 break;
409 }
410 case FILTER_OP_LOAD_FIELD_REF_STRING:
411 case FILTER_OP_LOAD_FIELD_REF_SEQUENCE:
412 case FILTER_OP_LOAD_FIELD_REF_USER_STRING:
413 case FILTER_OP_LOAD_FIELD_REF_USER_SEQUENCE:
414 case FILTER_OP_LOAD_FIELD_REF_S64:
415 case FILTER_OP_GET_CONTEXT_REF_STRING:
416 case FILTER_OP_GET_CONTEXT_REF_S64:
417 {
418 if (unlikely(pc + sizeof(struct load_op) + sizeof(struct field_ref)
419 > start_pc + bytecode->len)) {
420 ret = -ERANGE;
421 }
422 break;
423 }
424
425 /* load from immediate operand */
426 case FILTER_OP_LOAD_STRING:
427 case FILTER_OP_LOAD_STAR_GLOB_STRING:
428 {
429 struct load_op *insn = (struct load_op *) pc;
430 uint32_t str_len, maxlen;
431
432 if (unlikely(pc + sizeof(struct load_op)
433 > start_pc + bytecode->len)) {
434 ret = -ERANGE;
435 break;
436 }
437
438 maxlen = start_pc + bytecode->len - pc - sizeof(struct load_op);
439 str_len = strnlen(insn->data, maxlen);
440 if (unlikely(str_len >= maxlen)) {
441 /* Final '\0' not found within range */
442 ret = -ERANGE;
443 }
444 break;
445 }
446
447 case FILTER_OP_LOAD_S64:
448 {
449 if (unlikely(pc + sizeof(struct load_op) + sizeof(struct literal_numeric)
450 > start_pc + bytecode->len)) {
451 ret = -ERANGE;
452 }
453 break;
454 }
455
456 case FILTER_OP_CAST_TO_S64:
457 case FILTER_OP_CAST_NOP:
458 {
459 if (unlikely(pc + sizeof(struct cast_op)
460 > start_pc + bytecode->len)) {
461 ret = -ERANGE;
462 }
463 break;
464 }
465
466 /*
467 * Instructions for recursive traversal through composed types.
468 */
469 case FILTER_OP_GET_CONTEXT_ROOT:
470 case FILTER_OP_GET_APP_CONTEXT_ROOT:
471 case FILTER_OP_GET_PAYLOAD_ROOT:
472 case FILTER_OP_LOAD_FIELD:
473 case FILTER_OP_LOAD_FIELD_S8:
474 case FILTER_OP_LOAD_FIELD_S16:
475 case FILTER_OP_LOAD_FIELD_S32:
476 case FILTER_OP_LOAD_FIELD_S64:
477 case FILTER_OP_LOAD_FIELD_U8:
478 case FILTER_OP_LOAD_FIELD_U16:
479 case FILTER_OP_LOAD_FIELD_U32:
480 case FILTER_OP_LOAD_FIELD_U64:
481 case FILTER_OP_LOAD_FIELD_STRING:
482 case FILTER_OP_LOAD_FIELD_SEQUENCE:
483 case FILTER_OP_LOAD_FIELD_DOUBLE:
484 if (unlikely(pc + sizeof(struct load_op)
485 > start_pc + bytecode->len)) {
486 ret = -ERANGE;
487 }
488 break;
489
490 case FILTER_OP_GET_SYMBOL:
491 {
492 struct load_op *insn = (struct load_op *) pc;
493 struct get_symbol *sym = (struct get_symbol *) insn->data;
494
495 if (unlikely(pc + sizeof(struct load_op) + sizeof(struct get_symbol)
496 > start_pc + bytecode->len)) {
497 ret = -ERANGE;
498 break;
499 }
500 ret = validate_get_symbol(bytecode, sym);
501 break;
502 }
503
504 case FILTER_OP_GET_SYMBOL_FIELD:
505 printk(KERN_WARNING "LTTng: filter: Unexpected get symbol field\n");
506 ret = -EINVAL;
507 break;
508
509 case FILTER_OP_GET_INDEX_U16:
510 if (unlikely(pc + sizeof(struct load_op) + sizeof(struct get_index_u16)
511 > start_pc + bytecode->len)) {
512 ret = -ERANGE;
513 }
514 break;
515
516 case FILTER_OP_GET_INDEX_U64:
517 if (unlikely(pc + sizeof(struct load_op) + sizeof(struct get_index_u64)
518 > start_pc + bytecode->len)) {
519 ret = -ERANGE;
520 }
521 break;
522 }
523
524 return ret;
525 }
526
527 static
528 unsigned long delete_all_nodes(struct mp_table *mp_table)
529 {
530 struct mp_node *mp_node;
531 struct hlist_node *tmp;
532 unsigned long nr_nodes = 0;
533 int i;
534
535 for (i = 0; i < MERGE_POINT_TABLE_SIZE; i++) {
536 struct hlist_head *head;
537
538 head = &mp_table->mp_head[i];
539 lttng_hlist_for_each_entry_safe(mp_node, tmp, head, node) {
540 kfree(mp_node);
541 nr_nodes++;
542 }
543 }
544 return nr_nodes;
545 }
546
547 /*
548 * Return value:
549 * >=0: success
550 * <0: error
551 */
552 static
553 int validate_instruction_context(struct bytecode_runtime *bytecode,
554 struct vstack *stack,
555 char *start_pc,
556 char *pc)
557 {
558 int ret = 0;
559 const filter_opcode_t opcode = *(filter_opcode_t *) pc;
560
561 switch (opcode) {
562 case FILTER_OP_UNKNOWN:
563 default:
564 {
565 printk(KERN_WARNING "LTTng: filter: unknown bytecode op %u\n",
566 (unsigned int) *(filter_opcode_t *) pc);
567 ret = -EINVAL;
568 goto end;
569 }
570
571 case FILTER_OP_RETURN:
572 case FILTER_OP_RETURN_S64:
573 {
574 goto end;
575 }
576
577 /* binary */
578 case FILTER_OP_MUL:
579 case FILTER_OP_DIV:
580 case FILTER_OP_MOD:
581 case FILTER_OP_PLUS:
582 case FILTER_OP_MINUS:
583 /* Floating point */
584 case FILTER_OP_EQ_DOUBLE:
585 case FILTER_OP_NE_DOUBLE:
586 case FILTER_OP_GT_DOUBLE:
587 case FILTER_OP_LT_DOUBLE:
588 case FILTER_OP_GE_DOUBLE:
589 case FILTER_OP_LE_DOUBLE:
590 case FILTER_OP_EQ_DOUBLE_S64:
591 case FILTER_OP_NE_DOUBLE_S64:
592 case FILTER_OP_GT_DOUBLE_S64:
593 case FILTER_OP_LT_DOUBLE_S64:
594 case FILTER_OP_GE_DOUBLE_S64:
595 case FILTER_OP_LE_DOUBLE_S64:
596 case FILTER_OP_EQ_S64_DOUBLE:
597 case FILTER_OP_NE_S64_DOUBLE:
598 case FILTER_OP_GT_S64_DOUBLE:
599 case FILTER_OP_LT_S64_DOUBLE:
600 case FILTER_OP_GE_S64_DOUBLE:
601 case FILTER_OP_LE_S64_DOUBLE:
602 case FILTER_OP_UNARY_PLUS_DOUBLE:
603 case FILTER_OP_UNARY_MINUS_DOUBLE:
604 case FILTER_OP_UNARY_NOT_DOUBLE:
605 case FILTER_OP_LOAD_FIELD_REF_DOUBLE:
606 case FILTER_OP_LOAD_DOUBLE:
607 case FILTER_OP_CAST_DOUBLE_TO_S64:
608 case FILTER_OP_GET_CONTEXT_REF_DOUBLE:
609 {
610 printk(KERN_WARNING "LTTng: filter: unsupported bytecode op %u\n",
611 (unsigned int) *(filter_opcode_t *) pc);
612 ret = -EINVAL;
613 goto end;
614 }
615
616 case FILTER_OP_EQ:
617 {
618 ret = bin_op_compare_check(stack, opcode, "==");
619 if (ret < 0)
620 goto end;
621 break;
622 }
623 case FILTER_OP_NE:
624 {
625 ret = bin_op_compare_check(stack, opcode, "!=");
626 if (ret < 0)
627 goto end;
628 break;
629 }
630 case FILTER_OP_GT:
631 {
632 ret = bin_op_compare_check(stack, opcode, ">");
633 if (ret < 0)
634 goto end;
635 break;
636 }
637 case FILTER_OP_LT:
638 {
639 ret = bin_op_compare_check(stack, opcode, "<");
640 if (ret < 0)
641 goto end;
642 break;
643 }
644 case FILTER_OP_GE:
645 {
646 ret = bin_op_compare_check(stack, opcode, ">=");
647 if (ret < 0)
648 goto end;
649 break;
650 }
651 case FILTER_OP_LE:
652 {
653 ret = bin_op_compare_check(stack, opcode, "<=");
654 if (ret < 0)
655 goto end;
656 break;
657 }
658
659 case FILTER_OP_EQ_STRING:
660 case FILTER_OP_NE_STRING:
661 case FILTER_OP_GT_STRING:
662 case FILTER_OP_LT_STRING:
663 case FILTER_OP_GE_STRING:
664 case FILTER_OP_LE_STRING:
665 {
666 if (!vstack_ax(stack) || !vstack_bx(stack)) {
667 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
668 ret = -EINVAL;
669 goto end;
670 }
671 if (vstack_ax(stack)->type != REG_STRING
672 || vstack_bx(stack)->type != REG_STRING) {
673 printk(KERN_WARNING "LTTng: filter: Unexpected register type for string comparator\n");
674 ret = -EINVAL;
675 goto end;
676 }
677 break;
678 }
679
680
681 case FILTER_OP_EQ_STAR_GLOB_STRING:
682 case FILTER_OP_NE_STAR_GLOB_STRING:
683 {
684 if (!vstack_ax(stack) || !vstack_bx(stack)) {
685 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
686 ret = -EINVAL;
687 goto end;
688 }
689 if (vstack_ax(stack)->type != REG_STAR_GLOB_STRING
690 && vstack_bx(stack)->type != REG_STAR_GLOB_STRING) {
691 printk(KERN_WARNING "LTTng: filter: Unexpected register type for globbing pattern comparator\n");
692 ret = -EINVAL;
693 goto end;
694 }
695 break;
696 }
697
698 case FILTER_OP_EQ_S64:
699 case FILTER_OP_NE_S64:
700 case FILTER_OP_GT_S64:
701 case FILTER_OP_LT_S64:
702 case FILTER_OP_GE_S64:
703 case FILTER_OP_LE_S64:
704 {
705 if (!vstack_ax(stack) || !vstack_bx(stack)) {
706 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
707 ret = -EINVAL;
708 goto end;
709 }
710 if (vstack_ax(stack)->type != REG_S64
711 || vstack_bx(stack)->type != REG_S64) {
712 printk(KERN_WARNING "LTTng: filter: Unexpected register type for s64 comparator\n");
713 ret = -EINVAL;
714 goto end;
715 }
716 break;
717 }
718
719 case FILTER_OP_BIT_RSHIFT:
720 ret = bin_op_bitwise_check(stack, opcode, ">>");
721 if (ret < 0)
722 goto end;
723 break;
724 case FILTER_OP_BIT_LSHIFT:
725 ret = bin_op_bitwise_check(stack, opcode, "<<");
726 if (ret < 0)
727 goto end;
728 break;
729 case FILTER_OP_BIT_AND:
730 ret = bin_op_bitwise_check(stack, opcode, "&");
731 if (ret < 0)
732 goto end;
733 break;
734 case FILTER_OP_BIT_OR:
735 ret = bin_op_bitwise_check(stack, opcode, "|");
736 if (ret < 0)
737 goto end;
738 break;
739 case FILTER_OP_BIT_XOR:
740 ret = bin_op_bitwise_check(stack, opcode, "^");
741 if (ret < 0)
742 goto end;
743 break;
744
745 /* unary */
746 case FILTER_OP_UNARY_PLUS:
747 case FILTER_OP_UNARY_MINUS:
748 case FILTER_OP_UNARY_NOT:
749 {
750 if (!vstack_ax(stack)) {
751 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
752 ret = -EINVAL;
753 goto end;
754 }
755 switch (vstack_ax(stack)->type) {
756 default:
757 case REG_DOUBLE:
758 printk(KERN_WARNING "LTTng: filter: unknown register type\n");
759 ret = -EINVAL;
760 goto end;
761
762 case REG_STRING:
763 case REG_STAR_GLOB_STRING:
764 printk(KERN_WARNING "LTTng: filter: Unary op can only be applied to numeric or floating point registers\n");
765 ret = -EINVAL;
766 goto end;
767 case REG_S64:
768 case REG_TYPE_UNKNOWN:
769 break;
770 }
771 break;
772 }
773 case FILTER_OP_UNARY_BIT_NOT:
774 {
775 if (!vstack_ax(stack)) {
776 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
777 ret = -EINVAL;
778 goto end;
779 }
780 switch (vstack_ax(stack)->type) {
781 default:
782 printk(KERN_WARNING "LTTng: filter: unknown register type\n");
783 ret = -EINVAL;
784 goto end;
785
786 case REG_STRING:
787 case REG_STAR_GLOB_STRING:
788 case REG_DOUBLE:
789 printk(KERN_WARNING "LTTng: filter: Unary bitwise op can only be applied to numeric registers\n");
790 ret = -EINVAL;
791 goto end;
792 case REG_S64:
793 break;
794 case REG_TYPE_UNKNOWN:
795 break;
796 }
797 break;
798 }
799
800 case FILTER_OP_UNARY_PLUS_S64:
801 case FILTER_OP_UNARY_MINUS_S64:
802 case FILTER_OP_UNARY_NOT_S64:
803 {
804 if (!vstack_ax(stack)) {
805 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
806 ret = -EINVAL;
807 goto end;
808 }
809 if (vstack_ax(stack)->type != REG_S64) {
810 printk(KERN_WARNING "LTTng: filter: Invalid register type\n");
811 ret = -EINVAL;
812 goto end;
813 }
814 break;
815 }
816
817 /* logical */
818 case FILTER_OP_AND:
819 case FILTER_OP_OR:
820 {
821 struct logical_op *insn = (struct logical_op *) pc;
822
823 if (!vstack_ax(stack)) {
824 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
825 ret = -EINVAL;
826 goto end;
827 }
828 if (vstack_ax(stack)->type != REG_S64) {
829 printk(KERN_WARNING "LTTng: filter: Logical comparator expects S64 register\n");
830 ret = -EINVAL;
831 goto end;
832 }
833
834 dbg_printk("Validate jumping to bytecode offset %u\n",
835 (unsigned int) insn->skip_offset);
836 if (unlikely(start_pc + insn->skip_offset <= pc)) {
837 printk(KERN_WARNING "LTTng: filter: Loops are not allowed in bytecode\n");
838 ret = -EINVAL;
839 goto end;
840 }
841 break;
842 }
843
844 /* load field ref */
845 case FILTER_OP_LOAD_FIELD_REF:
846 {
847 printk(KERN_WARNING "LTTng: filter: Unknown field ref type\n");
848 ret = -EINVAL;
849 goto end;
850 }
851 case FILTER_OP_LOAD_FIELD_REF_STRING:
852 case FILTER_OP_LOAD_FIELD_REF_SEQUENCE:
853 case FILTER_OP_LOAD_FIELD_REF_USER_STRING:
854 case FILTER_OP_LOAD_FIELD_REF_USER_SEQUENCE:
855 {
856 struct load_op *insn = (struct load_op *) pc;
857 struct field_ref *ref = (struct field_ref *) insn->data;
858
859 dbg_printk("Validate load field ref offset %u type string\n",
860 ref->offset);
861 break;
862 }
863 case FILTER_OP_LOAD_FIELD_REF_S64:
864 {
865 struct load_op *insn = (struct load_op *) pc;
866 struct field_ref *ref = (struct field_ref *) insn->data;
867
868 dbg_printk("Validate load field ref offset %u type s64\n",
869 ref->offset);
870 break;
871 }
872
873 /* load from immediate operand */
874 case FILTER_OP_LOAD_STRING:
875 case FILTER_OP_LOAD_STAR_GLOB_STRING:
876 {
877 break;
878 }
879
880 case FILTER_OP_LOAD_S64:
881 {
882 break;
883 }
884
885 case FILTER_OP_CAST_TO_S64:
886 {
887 struct cast_op *insn = (struct cast_op *) pc;
888
889 if (!vstack_ax(stack)) {
890 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
891 ret = -EINVAL;
892 goto end;
893 }
894 switch (vstack_ax(stack)->type) {
895 default:
896 case REG_DOUBLE:
897 printk(KERN_WARNING "LTTng: filter: unknown register type\n");
898 ret = -EINVAL;
899 goto end;
900
901 case REG_STRING:
902 case REG_STAR_GLOB_STRING:
903 printk(KERN_WARNING "LTTng: filter: Cast op can only be applied to numeric or floating point registers\n");
904 ret = -EINVAL;
905 goto end;
906 case REG_S64:
907 break;
908 }
909 if (insn->op == FILTER_OP_CAST_DOUBLE_TO_S64) {
910 if (vstack_ax(stack)->type != REG_DOUBLE) {
911 printk(KERN_WARNING "LTTng: filter: Cast expects double\n");
912 ret = -EINVAL;
913 goto end;
914 }
915 }
916 break;
917 }
918 case FILTER_OP_CAST_NOP:
919 {
920 break;
921 }
922
923 /* get context ref */
924 case FILTER_OP_GET_CONTEXT_REF:
925 {
926 printk(KERN_WARNING "LTTng: filter: Unknown get context ref type\n");
927 ret = -EINVAL;
928 goto end;
929 }
930 case FILTER_OP_GET_CONTEXT_REF_STRING:
931 {
932 struct load_op *insn = (struct load_op *) pc;
933 struct field_ref *ref = (struct field_ref *) insn->data;
934
935 dbg_printk("Validate get context ref offset %u type string\n",
936 ref->offset);
937 break;
938 }
939 case FILTER_OP_GET_CONTEXT_REF_S64:
940 {
941 struct load_op *insn = (struct load_op *) pc;
942 struct field_ref *ref = (struct field_ref *) insn->data;
943
944 dbg_printk("Validate get context ref offset %u type s64\n",
945 ref->offset);
946 break;
947 }
948
949 /*
950 * Instructions for recursive traversal through composed types.
951 */
952 case FILTER_OP_GET_CONTEXT_ROOT:
953 {
954 dbg_printk("Validate get context root\n");
955 break;
956 }
957 case FILTER_OP_GET_APP_CONTEXT_ROOT:
958 {
959 dbg_printk("Validate get app context root\n");
960 break;
961 }
962 case FILTER_OP_GET_PAYLOAD_ROOT:
963 {
964 dbg_printk("Validate get payload root\n");
965 break;
966 }
967 case FILTER_OP_LOAD_FIELD:
968 {
969 /*
970 * We tolerate that field type is unknown at validation,
971 * because we are performing the load specialization in
972 * a phase after validation.
973 */
974 dbg_printk("Validate load field\n");
975 break;
976 }
977 case FILTER_OP_LOAD_FIELD_S8:
978 {
979 dbg_printk("Validate load field s8\n");
980 break;
981 }
982 case FILTER_OP_LOAD_FIELD_S16:
983 {
984 dbg_printk("Validate load field s16\n");
985 break;
986 }
987 case FILTER_OP_LOAD_FIELD_S32:
988 {
989 dbg_printk("Validate load field s32\n");
990 break;
991 }
992 case FILTER_OP_LOAD_FIELD_S64:
993 {
994 dbg_printk("Validate load field s64\n");
995 break;
996 }
997 case FILTER_OP_LOAD_FIELD_U8:
998 {
999 dbg_printk("Validate load field u8\n");
1000 break;
1001 }
1002 case FILTER_OP_LOAD_FIELD_U16:
1003 {
1004 dbg_printk("Validate load field u16\n");
1005 break;
1006 }
1007 case FILTER_OP_LOAD_FIELD_U32:
1008 {
1009 dbg_printk("Validate load field u32\n");
1010 break;
1011 }
1012 case FILTER_OP_LOAD_FIELD_U64:
1013 {
1014 dbg_printk("Validate load field u64\n");
1015 break;
1016 }
1017 case FILTER_OP_LOAD_FIELD_STRING:
1018 {
1019 dbg_printk("Validate load field string\n");
1020 break;
1021 }
1022 case FILTER_OP_LOAD_FIELD_SEQUENCE:
1023 {
1024 dbg_printk("Validate load field sequence\n");
1025 break;
1026 }
1027 case FILTER_OP_LOAD_FIELD_DOUBLE:
1028 {
1029 dbg_printk("Validate load field double\n");
1030 break;
1031 }
1032
1033 case FILTER_OP_GET_SYMBOL:
1034 {
1035 struct load_op *insn = (struct load_op *) pc;
1036 struct get_symbol *sym = (struct get_symbol *) insn->data;
1037
1038 dbg_printk("Validate get symbol offset %u\n", sym->offset);
1039 break;
1040 }
1041
1042 case FILTER_OP_GET_SYMBOL_FIELD:
1043 {
1044 struct load_op *insn = (struct load_op *) pc;
1045 struct get_symbol *sym = (struct get_symbol *) insn->data;
1046
1047 dbg_printk("Validate get symbol field offset %u\n", sym->offset);
1048 break;
1049 }
1050
1051 case FILTER_OP_GET_INDEX_U16:
1052 {
1053 struct load_op *insn = (struct load_op *) pc;
1054 struct get_index_u16 *get_index = (struct get_index_u16 *) insn->data;
1055
1056 dbg_printk("Validate get index u16 index %u\n", get_index->index);
1057 break;
1058 }
1059
1060 case FILTER_OP_GET_INDEX_U64:
1061 {
1062 struct load_op *insn = (struct load_op *) pc;
1063 struct get_index_u64 *get_index = (struct get_index_u64 *) insn->data;
1064
1065 dbg_printk("Validate get index u64 index %llu\n",
1066 (unsigned long long) get_index->index);
1067 break;
1068 }
1069 }
1070 end:
1071 return ret;
1072 }
1073
1074 /*
1075 * Return value:
1076 * 0: success
1077 * <0: error
1078 */
1079 static
1080 int validate_instruction_all_contexts(struct bytecode_runtime *bytecode,
1081 struct mp_table *mp_table,
1082 struct vstack *stack,
1083 char *start_pc,
1084 char *pc)
1085 {
1086 int ret, found = 0;
1087 unsigned long target_pc = pc - start_pc;
1088 unsigned long hash;
1089 struct hlist_head *head;
1090 struct mp_node *mp_node;
1091
1092 /* Validate the context resulting from the previous instruction */
1093 ret = validate_instruction_context(bytecode, stack, start_pc, pc);
1094 if (ret < 0)
1095 return ret;
1096
1097 /* Validate merge points */
1098 hash = jhash_1word(target_pc, 0);
1099 head = &mp_table->mp_head[hash & (MERGE_POINT_TABLE_SIZE - 1)];
1100 lttng_hlist_for_each_entry(mp_node, head, node) {
1101 if (lttng_hash_match(mp_node, target_pc)) {
1102 found = 1;
1103 break;
1104 }
1105 }
1106 if (found) {
1107 dbg_printk("Filter: validate merge point at offset %lu\n",
1108 target_pc);
1109 if (merge_points_compare(stack, &mp_node->stack)) {
1110 printk(KERN_WARNING "LTTng: filter: Merge points differ for offset %lu\n",
1111 target_pc);
1112 return -EINVAL;
1113 }
1114 /* Once validated, we can remove the merge point */
1115 dbg_printk("Filter: remove merge point at offset %lu\n",
1116 target_pc);
1117 hlist_del(&mp_node->node);
1118 }
1119 return 0;
1120 }
1121
1122 /*
1123 * Return value:
1124 * >0: going to next insn.
1125 * 0: success, stop iteration.
1126 * <0: error
1127 */
1128 static
1129 int exec_insn(struct bytecode_runtime *bytecode,
1130 struct mp_table *mp_table,
1131 struct vstack *stack,
1132 char **_next_pc,
1133 char *pc)
1134 {
1135 int ret = 1;
1136 char *next_pc = *_next_pc;
1137
1138 switch (*(filter_opcode_t *) pc) {
1139 case FILTER_OP_UNKNOWN:
1140 default:
1141 {
1142 printk(KERN_WARNING "LTTng: filter: unknown bytecode op %u\n",
1143 (unsigned int) *(filter_opcode_t *) pc);
1144 ret = -EINVAL;
1145 goto end;
1146 }
1147
1148 case FILTER_OP_RETURN:
1149 {
1150 if (!vstack_ax(stack)) {
1151 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
1152 ret = -EINVAL;
1153 goto end;
1154 }
1155 switch (vstack_ax(stack)->type) {
1156 case REG_S64:
1157 case REG_TYPE_UNKNOWN:
1158 break;
1159 default:
1160 printk(KERN_WARNING "LTTng: filter: Unexpected register type %d at end of bytecode\n",
1161 (int) vstack_ax(stack)->type);
1162 ret = -EINVAL;
1163 goto end;
1164 }
1165
1166 ret = 0;
1167 goto end;
1168 }
1169
1170 case FILTER_OP_RETURN_S64:
1171 {
1172 if (!vstack_ax(stack)) {
1173 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
1174 ret = -EINVAL;
1175 goto end;
1176 }
1177 switch (vstack_ax(stack)->type) {
1178 case REG_S64:
1179 break;
1180 default:
1181 case REG_TYPE_UNKNOWN:
1182 printk(KERN_WARNING "LTTng: filter: Unexpected register type %d at end of bytecode\n",
1183 (int) vstack_ax(stack)->type);
1184 ret = -EINVAL;
1185 goto end;
1186 }
1187
1188 ret = 0;
1189 goto end;
1190 }
1191
1192 /* binary */
1193 case FILTER_OP_MUL:
1194 case FILTER_OP_DIV:
1195 case FILTER_OP_MOD:
1196 case FILTER_OP_PLUS:
1197 case FILTER_OP_MINUS:
1198 /* Floating point */
1199 case FILTER_OP_EQ_DOUBLE:
1200 case FILTER_OP_NE_DOUBLE:
1201 case FILTER_OP_GT_DOUBLE:
1202 case FILTER_OP_LT_DOUBLE:
1203 case FILTER_OP_GE_DOUBLE:
1204 case FILTER_OP_LE_DOUBLE:
1205 case FILTER_OP_EQ_DOUBLE_S64:
1206 case FILTER_OP_NE_DOUBLE_S64:
1207 case FILTER_OP_GT_DOUBLE_S64:
1208 case FILTER_OP_LT_DOUBLE_S64:
1209 case FILTER_OP_GE_DOUBLE_S64:
1210 case FILTER_OP_LE_DOUBLE_S64:
1211 case FILTER_OP_EQ_S64_DOUBLE:
1212 case FILTER_OP_NE_S64_DOUBLE:
1213 case FILTER_OP_GT_S64_DOUBLE:
1214 case FILTER_OP_LT_S64_DOUBLE:
1215 case FILTER_OP_GE_S64_DOUBLE:
1216 case FILTER_OP_LE_S64_DOUBLE:
1217 case FILTER_OP_UNARY_PLUS_DOUBLE:
1218 case FILTER_OP_UNARY_MINUS_DOUBLE:
1219 case FILTER_OP_UNARY_NOT_DOUBLE:
1220 case FILTER_OP_LOAD_FIELD_REF_DOUBLE:
1221 case FILTER_OP_GET_CONTEXT_REF_DOUBLE:
1222 case FILTER_OP_LOAD_DOUBLE:
1223 case FILTER_OP_CAST_DOUBLE_TO_S64:
1224 {
1225 printk(KERN_WARNING "LTTng: filter: unsupported bytecode op %u\n",
1226 (unsigned int) *(filter_opcode_t *) pc);
1227 ret = -EINVAL;
1228 goto end;
1229 }
1230
1231 case FILTER_OP_EQ:
1232 case FILTER_OP_NE:
1233 case FILTER_OP_GT:
1234 case FILTER_OP_LT:
1235 case FILTER_OP_GE:
1236 case FILTER_OP_LE:
1237 case FILTER_OP_EQ_STRING:
1238 case FILTER_OP_NE_STRING:
1239 case FILTER_OP_GT_STRING:
1240 case FILTER_OP_LT_STRING:
1241 case FILTER_OP_GE_STRING:
1242 case FILTER_OP_LE_STRING:
1243 case FILTER_OP_EQ_STAR_GLOB_STRING:
1244 case FILTER_OP_NE_STAR_GLOB_STRING:
1245 case FILTER_OP_EQ_S64:
1246 case FILTER_OP_NE_S64:
1247 case FILTER_OP_GT_S64:
1248 case FILTER_OP_LT_S64:
1249 case FILTER_OP_GE_S64:
1250 case FILTER_OP_LE_S64:
1251 case FILTER_OP_BIT_RSHIFT:
1252 case FILTER_OP_BIT_LSHIFT:
1253 case FILTER_OP_BIT_AND:
1254 case FILTER_OP_BIT_OR:
1255 case FILTER_OP_BIT_XOR:
1256 {
1257 /* Pop 2, push 1 */
1258 if (vstack_pop(stack)) {
1259 ret = -EINVAL;
1260 goto end;
1261 }
1262 if (!vstack_ax(stack)) {
1263 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
1264 ret = -EINVAL;
1265 goto end;
1266 }
1267 switch (vstack_ax(stack)->type) {
1268 case REG_S64:
1269 case REG_DOUBLE:
1270 case REG_STRING:
1271 case REG_STAR_GLOB_STRING:
1272 case REG_TYPE_UNKNOWN:
1273 break;
1274 default:
1275 printk(KERN_WARNING "LTTng: filter: Unexpected register type %d for operation\n",
1276 (int) vstack_ax(stack)->type);
1277 ret = -EINVAL;
1278 goto end;
1279 }
1280
1281 vstack_ax(stack)->type = REG_S64;
1282 next_pc += sizeof(struct binary_op);
1283 break;
1284 }
1285
1286 /* unary */
1287 case FILTER_OP_UNARY_PLUS:
1288 case FILTER_OP_UNARY_MINUS:
1289 {
1290 /* Pop 1, push 1 */
1291 if (!vstack_ax(stack)) {
1292 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1293 ret = -EINVAL;
1294 goto end;
1295 }
1296 switch (vstack_ax(stack)->type) {
1297 case REG_S64:
1298 case REG_TYPE_UNKNOWN:
1299 break;
1300 default:
1301 printk(KERN_WARNING "LTTng: filter: Unexpected register type %d for operation\n",
1302 (int) vstack_ax(stack)->type);
1303 ret = -EINVAL;
1304 goto end;
1305 }
1306
1307 vstack_ax(stack)->type = REG_TYPE_UNKNOWN;
1308 next_pc += sizeof(struct unary_op);
1309 break;
1310 }
1311
1312 case FILTER_OP_UNARY_PLUS_S64:
1313 case FILTER_OP_UNARY_MINUS_S64:
1314 case FILTER_OP_UNARY_NOT_S64:
1315 {
1316 /* Pop 1, push 1 */
1317 if (!vstack_ax(stack)) {
1318 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1319 ret = -EINVAL;
1320 goto end;
1321 }
1322 switch (vstack_ax(stack)->type) {
1323 case REG_S64:
1324 break;
1325 default:
1326 printk(KERN_WARNING "LTTng: filter: Unexpected register type %d for operation\n",
1327 (int) vstack_ax(stack)->type);
1328 ret = -EINVAL;
1329 goto end;
1330 }
1331
1332 vstack_ax(stack)->type = REG_S64;
1333 next_pc += sizeof(struct unary_op);
1334 break;
1335 }
1336
1337 case FILTER_OP_UNARY_NOT:
1338 {
1339 /* Pop 1, push 1 */
1340 if (!vstack_ax(stack)) {
1341 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1342 ret = -EINVAL;
1343 goto end;
1344 }
1345 switch (vstack_ax(stack)->type) {
1346 case REG_S64:
1347 case REG_TYPE_UNKNOWN:
1348 break;
1349 default:
1350 printk(KERN_WARNING "LTTng: filter: Unexpected register type %d for operation\n",
1351 (int) vstack_ax(stack)->type);
1352 ret = -EINVAL;
1353 goto end;
1354 }
1355
1356 vstack_ax(stack)->type = REG_S64;
1357 next_pc += sizeof(struct unary_op);
1358 break;
1359 }
1360
1361 case FILTER_OP_UNARY_BIT_NOT:
1362 {
1363 /* Pop 1, push 1 */
1364 if (!vstack_ax(stack)) {
1365 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
1366 ret = -EINVAL;
1367 goto end;
1368 }
1369 switch (vstack_ax(stack)->type) {
1370 case REG_S64:
1371 case REG_TYPE_UNKNOWN:
1372 break;
1373 case REG_DOUBLE:
1374 default:
1375 printk(KERN_WARNING "LTTng: filter: Unexpected register type %d for operation\n",
1376 (int) vstack_ax(stack)->type);
1377 ret = -EINVAL;
1378 goto end;
1379 }
1380
1381 vstack_ax(stack)->type = REG_S64;
1382 next_pc += sizeof(struct unary_op);
1383 break;
1384 }
1385
1386 /* logical */
1387 case FILTER_OP_AND:
1388 case FILTER_OP_OR:
1389 {
1390 struct logical_op *insn = (struct logical_op *) pc;
1391 int merge_ret;
1392
1393 /* Add merge point to table */
1394 merge_ret = merge_point_add_check(mp_table,
1395 insn->skip_offset, stack);
1396 if (merge_ret) {
1397 ret = merge_ret;
1398 goto end;
1399 }
1400
1401 if (!vstack_ax(stack)) {
1402 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1403 ret = -EINVAL;
1404 goto end;
1405 }
1406 /* There is always a cast-to-s64 operation before a or/and op. */
1407 switch (vstack_ax(stack)->type) {
1408 case REG_S64:
1409 break;
1410 default:
1411 printk(KERN_WARNING "LTTng: filter: Incorrect register type %d for operation\n",
1412 (int) vstack_ax(stack)->type);
1413 ret = -EINVAL;
1414 goto end;
1415 }
1416
1417 /* Continue to next instruction */
1418 /* Pop 1 when jump not taken */
1419 if (vstack_pop(stack)) {
1420 ret = -EINVAL;
1421 goto end;
1422 }
1423 next_pc += sizeof(struct logical_op);
1424 break;
1425 }
1426
1427 /* load field ref */
1428 case FILTER_OP_LOAD_FIELD_REF:
1429 {
1430 printk(KERN_WARNING "LTTng: filter: Unknown field ref type\n");
1431 ret = -EINVAL;
1432 goto end;
1433 }
1434 /* get context ref */
1435 case FILTER_OP_GET_CONTEXT_REF:
1436 {
1437 printk(KERN_WARNING "LTTng: filter: Unknown get context ref type\n");
1438 ret = -EINVAL;
1439 goto end;
1440 }
1441 case FILTER_OP_LOAD_FIELD_REF_STRING:
1442 case FILTER_OP_LOAD_FIELD_REF_SEQUENCE:
1443 case FILTER_OP_GET_CONTEXT_REF_STRING:
1444 case FILTER_OP_LOAD_FIELD_REF_USER_STRING:
1445 case FILTER_OP_LOAD_FIELD_REF_USER_SEQUENCE:
1446 {
1447 if (vstack_push(stack)) {
1448 ret = -EINVAL;
1449 goto end;
1450 }
1451 vstack_ax(stack)->type = REG_STRING;
1452 next_pc += sizeof(struct load_op) + sizeof(struct field_ref);
1453 break;
1454 }
1455 case FILTER_OP_LOAD_FIELD_REF_S64:
1456 case FILTER_OP_GET_CONTEXT_REF_S64:
1457 {
1458 if (vstack_push(stack)) {
1459 ret = -EINVAL;
1460 goto end;
1461 }
1462 vstack_ax(stack)->type = REG_S64;
1463 next_pc += sizeof(struct load_op) + sizeof(struct field_ref);
1464 break;
1465 }
1466
1467 /* load from immediate operand */
1468 case FILTER_OP_LOAD_STRING:
1469 {
1470 struct load_op *insn = (struct load_op *) pc;
1471
1472 if (vstack_push(stack)) {
1473 ret = -EINVAL;
1474 goto end;
1475 }
1476 vstack_ax(stack)->type = REG_STRING;
1477 next_pc += sizeof(struct load_op) + strlen(insn->data) + 1;
1478 break;
1479 }
1480
1481 case FILTER_OP_LOAD_STAR_GLOB_STRING:
1482 {
1483 struct load_op *insn = (struct load_op *) pc;
1484
1485 if (vstack_push(stack)) {
1486 ret = -EINVAL;
1487 goto end;
1488 }
1489 vstack_ax(stack)->type = REG_STAR_GLOB_STRING;
1490 next_pc += sizeof(struct load_op) + strlen(insn->data) + 1;
1491 break;
1492 }
1493
1494 case FILTER_OP_LOAD_S64:
1495 {
1496 if (vstack_push(stack)) {
1497 ret = -EINVAL;
1498 goto end;
1499 }
1500 vstack_ax(stack)->type = REG_S64;
1501 next_pc += sizeof(struct load_op)
1502 + sizeof(struct literal_numeric);
1503 break;
1504 }
1505
1506 case FILTER_OP_CAST_TO_S64:
1507 {
1508 /* Pop 1, push 1 */
1509 if (!vstack_ax(stack)) {
1510 printk(KERN_WARNING "LTTng: filter: Empty stack\n");
1511 ret = -EINVAL;
1512 goto end;
1513 }
1514 switch (vstack_ax(stack)->type) {
1515 case REG_S64:
1516 case REG_DOUBLE:
1517 case REG_TYPE_UNKNOWN:
1518 break;
1519 default:
1520 printk(KERN_WARNING "LTTng: filter: Incorrect register type %d for cast\n",
1521 (int) vstack_ax(stack)->type);
1522 ret = -EINVAL;
1523 goto end;
1524 }
1525 vstack_ax(stack)->type = REG_S64;
1526 next_pc += sizeof(struct cast_op);
1527 break;
1528 }
1529 case FILTER_OP_CAST_NOP:
1530 {
1531 next_pc += sizeof(struct cast_op);
1532 break;
1533 }
1534
1535 /*
1536 * Instructions for recursive traversal through composed types.
1537 */
1538 case FILTER_OP_GET_CONTEXT_ROOT:
1539 case FILTER_OP_GET_APP_CONTEXT_ROOT:
1540 case FILTER_OP_GET_PAYLOAD_ROOT:
1541 {
1542 if (vstack_push(stack)) {
1543 ret = -EINVAL;
1544 goto end;
1545 }
1546 vstack_ax(stack)->type = REG_PTR;
1547 next_pc += sizeof(struct load_op);
1548 break;
1549 }
1550
1551 case FILTER_OP_LOAD_FIELD:
1552 {
1553 /* Pop 1, push 1 */
1554 if (!vstack_ax(stack)) {
1555 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1556 ret = -EINVAL;
1557 goto end;
1558 }
1559 if (vstack_ax(stack)->type != REG_PTR) {
1560 printk(KERN_WARNING "LTTng: filter: Expecting pointer on top of stack\n\n");
1561 ret = -EINVAL;
1562 goto end;
1563 }
1564 vstack_ax(stack)->type = REG_TYPE_UNKNOWN;
1565 next_pc += sizeof(struct load_op);
1566 break;
1567 }
1568
1569 case FILTER_OP_LOAD_FIELD_S8:
1570 case FILTER_OP_LOAD_FIELD_S16:
1571 case FILTER_OP_LOAD_FIELD_S32:
1572 case FILTER_OP_LOAD_FIELD_S64:
1573 case FILTER_OP_LOAD_FIELD_U8:
1574 case FILTER_OP_LOAD_FIELD_U16:
1575 case FILTER_OP_LOAD_FIELD_U32:
1576 case FILTER_OP_LOAD_FIELD_U64:
1577 {
1578 /* Pop 1, push 1 */
1579 if (!vstack_ax(stack)) {
1580 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1581 ret = -EINVAL;
1582 goto end;
1583 }
1584 if (vstack_ax(stack)->type != REG_PTR) {
1585 printk(KERN_WARNING "LTTng: filter: Expecting pointer on top of stack\n\n");
1586 ret = -EINVAL;
1587 goto end;
1588 }
1589 vstack_ax(stack)->type = REG_S64;
1590 next_pc += sizeof(struct load_op);
1591 break;
1592 }
1593
1594 case FILTER_OP_LOAD_FIELD_STRING:
1595 case FILTER_OP_LOAD_FIELD_SEQUENCE:
1596 {
1597 /* Pop 1, push 1 */
1598 if (!vstack_ax(stack)) {
1599 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1600 ret = -EINVAL;
1601 goto end;
1602 }
1603 if (vstack_ax(stack)->type != REG_PTR) {
1604 printk(KERN_WARNING "LTTng: filter: Expecting pointer on top of stack\n\n");
1605 ret = -EINVAL;
1606 goto end;
1607 }
1608 vstack_ax(stack)->type = REG_STRING;
1609 next_pc += sizeof(struct load_op);
1610 break;
1611 }
1612
1613 case FILTER_OP_LOAD_FIELD_DOUBLE:
1614 {
1615 /* Pop 1, push 1 */
1616 if (!vstack_ax(stack)) {
1617 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1618 ret = -EINVAL;
1619 goto end;
1620 }
1621 if (vstack_ax(stack)->type != REG_PTR) {
1622 printk(KERN_WARNING "LTTng: filter: Expecting pointer on top of stack\n\n");
1623 ret = -EINVAL;
1624 goto end;
1625 }
1626 vstack_ax(stack)->type = REG_DOUBLE;
1627 next_pc += sizeof(struct load_op);
1628 break;
1629 }
1630
1631 case FILTER_OP_GET_SYMBOL:
1632 case FILTER_OP_GET_SYMBOL_FIELD:
1633 {
1634 /* Pop 1, push 1 */
1635 if (!vstack_ax(stack)) {
1636 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1637 ret = -EINVAL;
1638 goto end;
1639 }
1640 if (vstack_ax(stack)->type != REG_PTR) {
1641 printk(KERN_WARNING "LTTng: filter: Expecting pointer on top of stack\n\n");
1642 ret = -EINVAL;
1643 goto end;
1644 }
1645 next_pc += sizeof(struct load_op) + sizeof(struct get_symbol);
1646 break;
1647 }
1648
1649 case FILTER_OP_GET_INDEX_U16:
1650 {
1651 /* Pop 1, push 1 */
1652 if (!vstack_ax(stack)) {
1653 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1654 ret = -EINVAL;
1655 goto end;
1656 }
1657 if (vstack_ax(stack)->type != REG_PTR) {
1658 printk(KERN_WARNING "LTTng: filter: Expecting pointer on top of stack\n\n");
1659 ret = -EINVAL;
1660 goto end;
1661 }
1662 next_pc += sizeof(struct load_op) + sizeof(struct get_index_u16);
1663 break;
1664 }
1665
1666 case FILTER_OP_GET_INDEX_U64:
1667 {
1668 /* Pop 1, push 1 */
1669 if (!vstack_ax(stack)) {
1670 printk(KERN_WARNING "LTTng: filter: Empty stack\n\n");
1671 ret = -EINVAL;
1672 goto end;
1673 }
1674 if (vstack_ax(stack)->type != REG_PTR) {
1675 printk(KERN_WARNING "LTTng: filter: Expecting pointer on top of stack\n\n");
1676 ret = -EINVAL;
1677 goto end;
1678 }
1679 next_pc += sizeof(struct load_op) + sizeof(struct get_index_u64);
1680 break;
1681 }
1682
1683 }
1684 end:
1685 *_next_pc = next_pc;
1686 return ret;
1687 }
1688
1689 /*
1690 * Never called concurrently (hash seed is shared).
1691 */
1692 int lttng_filter_validate_bytecode(struct bytecode_runtime *bytecode)
1693 {
1694 struct mp_table *mp_table;
1695 char *pc, *next_pc, *start_pc;
1696 int ret = -EINVAL;
1697 struct vstack stack;
1698
1699 vstack_init(&stack);
1700
1701 mp_table = kzalloc(sizeof(*mp_table), GFP_KERNEL);
1702 if (!mp_table) {
1703 printk(KERN_WARNING "LTTng: filter: Error allocating hash table for bytecode validation\n");
1704 return -ENOMEM;
1705 }
1706 start_pc = &bytecode->code[0];
1707 for (pc = next_pc = start_pc; pc - start_pc < bytecode->len;
1708 pc = next_pc) {
1709 ret = bytecode_validate_overflow(bytecode, start_pc, pc);
1710 if (ret != 0) {
1711 if (ret == -ERANGE)
1712 printk(KERN_WARNING "LTTng: filter: filter bytecode overflow\n");
1713 goto end;
1714 }
1715 dbg_printk("Validating op %s (%u)\n",
1716 lttng_filter_print_op((unsigned int) *(filter_opcode_t *) pc),
1717 (unsigned int) *(filter_opcode_t *) pc);
1718
1719 /*
1720 * For each instruction, validate the current context
1721 * (traversal of entire execution flow), and validate
1722 * all merge points targeting this instruction.
1723 */
1724 ret = validate_instruction_all_contexts(bytecode, mp_table,
1725 &stack, start_pc, pc);
1726 if (ret)
1727 goto end;
1728 ret = exec_insn(bytecode, mp_table, &stack, &next_pc, pc);
1729 if (ret <= 0)
1730 goto end;
1731 }
1732 end:
1733 if (delete_all_nodes(mp_table)) {
1734 if (!ret) {
1735 printk(KERN_WARNING "LTTng: filter: Unexpected merge points\n");
1736 ret = -EINVAL;
1737 }
1738 }
1739 kfree(mp_table);
1740 return ret;
1741 }
This page took 0.096892 seconds and 4 git commands to generate.