X-Git-Url: https://git.lttng.org/?p=lttng-tools.git;a=blobdiff_plain;f=src%2Fcommon%2Fbytecode%2Fbytecode.c;h=aadfc17a173ccf528182a023532b701f8c73e716;hp=b8edd6913e18fa9fe1b4f7dbb753380c05a59e89;hb=1cbd136b2479ef142bfb339b13d3d25aa772dda5;hpb=0ae3cfc61fedae38ef31fe5a99458c4f2161c3b5 diff --git a/src/common/bytecode/bytecode.c b/src/common/bytecode/bytecode.c index b8edd6913..aadfc17a1 100644 --- a/src/common/bytecode/bytecode.c +++ b/src/common/bytecode/bytecode.c @@ -13,7 +13,8 @@ #define INIT_ALLOC_SIZE 4 -static inline int get_count_order(unsigned int count) +static inline +int get_count_order(unsigned int count) { int order; @@ -23,12 +24,11 @@ static inline int get_count_order(unsigned int count) return order; } -LTTNG_HIDDEN -int bytecode_init(struct lttng_filter_bytecode_alloc **fb) +int bytecode_init(struct lttng_bytecode_alloc **fb) { uint32_t alloc_len; - alloc_len = sizeof(struct lttng_filter_bytecode_alloc) + INIT_ALLOC_SIZE; + alloc_len = sizeof(struct lttng_bytecode_alloc) + INIT_ALLOC_SIZE; *fb = calloc(alloc_len, 1); if (!*fb) { return -ENOMEM; @@ -38,20 +38,20 @@ int bytecode_init(struct lttng_filter_bytecode_alloc **fb) } } -LTTNG_HIDDEN -int32_t bytecode_reserve(struct lttng_filter_bytecode_alloc **fb, uint32_t align, uint32_t len) +static +int32_t bytecode_reserve(struct lttng_bytecode_alloc **fb, uint32_t align, uint32_t len) { int32_t ret; - uint32_t padding = offset_align((*fb)->b.len, align); + uint32_t padding = lttng_offset_align((*fb)->b.len, align); uint32_t new_len = (*fb)->b.len + padding + len; - uint32_t new_alloc_len = sizeof(struct lttng_filter_bytecode_alloc) + new_len; + uint32_t new_alloc_len = sizeof(struct lttng_bytecode_alloc) + new_len; uint32_t old_alloc_len = (*fb)->alloc_len; if (new_len > LTTNG_FILTER_MAX_LEN) return -EINVAL; if (new_alloc_len > old_alloc_len) { - struct lttng_filter_bytecode_alloc *newptr; + struct lttng_bytecode_alloc *newptr; new_alloc_len = max_t(uint32_t, 1U << get_count_order(new_alloc_len), old_alloc_len << 1); @@ -69,8 +69,7 @@ int32_t bytecode_reserve(struct lttng_filter_bytecode_alloc **fb, uint32_t align return ret; } -LTTNG_HIDDEN -int bytecode_push(struct lttng_filter_bytecode_alloc **fb, const void *data, +int bytecode_push(struct lttng_bytecode_alloc **fb, const void *data, uint32_t align, uint32_t len) { int32_t offset; @@ -82,8 +81,7 @@ int bytecode_push(struct lttng_filter_bytecode_alloc **fb, const void *data, return 0; } -LTTNG_HIDDEN -int bytecode_push_logical(struct lttng_filter_bytecode_alloc **fb, +int bytecode_push_logical(struct lttng_bytecode_alloc **fb, struct logical_op *data, uint32_t align, uint32_t len, uint16_t *skip_offset) @@ -99,3 +97,168 @@ int bytecode_push_logical(struct lttng_filter_bytecode_alloc **fb, - (void *) &(*fb)->b.data[0]; return 0; } + +int bytecode_push_get_payload_root(struct lttng_bytecode_alloc **bytecode) +{ + int ret; + struct load_op *insn; + const uint32_t insn_len = sizeof(struct load_op); + + insn = calloc(insn_len, 1); + if (!insn) { + ret = -ENOMEM; + goto end; + } + + insn->op = BYTECODE_OP_GET_PAYLOAD_ROOT; + ret = bytecode_push(bytecode, insn, 1, insn_len); + free(insn); +end: + return ret; +} + +int bytecode_push_get_context_root(struct lttng_bytecode_alloc **bytecode) +{ + int ret; + struct load_op *insn; + const uint32_t insn_len = sizeof(struct load_op); + + insn = calloc(insn_len, 1); + if (!insn) { + ret = -ENOMEM; + goto end; + } + + insn->op = BYTECODE_OP_GET_CONTEXT_ROOT; + ret = bytecode_push(bytecode, insn, 1, insn_len); + free(insn); +end: + return ret; +} + +int bytecode_push_get_app_context_root(struct lttng_bytecode_alloc **bytecode) +{ + int ret; + struct load_op *insn; + const uint32_t insn_len = sizeof(struct load_op); + + insn = calloc(insn_len, 1); + if (!insn) { + ret = -ENOMEM; + goto end; + } + + insn->op = BYTECODE_OP_GET_APP_CONTEXT_ROOT; + ret = bytecode_push(bytecode, insn, 1, insn_len); + free(insn); +end: + return ret; +} + +int bytecode_push_get_index_u64(struct lttng_bytecode_alloc **bytecode, + uint64_t index) +{ + int ret; + struct load_op *insn; + struct get_index_u64 index_op_data; + const uint32_t insn_len = + sizeof(struct load_op) + sizeof(struct get_index_u64); + + insn = calloc(insn_len, 1); + if (!insn) { + ret = -ENOMEM; + goto end; + } + + insn->op = BYTECODE_OP_GET_INDEX_U64; + index_op_data.index = index; + memcpy(insn->data, &index_op_data, sizeof(index)); + ret = bytecode_push(bytecode, insn, 1, insn_len); + + free(insn); +end: + return ret; +} + +int bytecode_push_get_symbol(struct lttng_bytecode_alloc **bytecode, + struct lttng_bytecode_alloc **bytecode_reloc, + const char *symbol) +{ + int ret; + struct load_op *insn; + struct get_symbol symbol_offset; + uint32_t reloc_offset_u32; + uint16_t reloc_offset; + uint32_t bytecode_reloc_offset_u32; + const uint32_t insn_len = + sizeof(struct load_op) + sizeof(struct get_symbol); + + insn = calloc(insn_len, 1); + if (!insn) { + ret = -ENOMEM; + goto end; + } + + insn->op = BYTECODE_OP_GET_SYMBOL; + + /* + * Get offset in the reloc portion at which the symbol name + * will end up at (GET_SYMBOL's operand points there). + */ + bytecode_reloc_offset_u32 = bytecode_get_len(&(*bytecode_reloc)->b) + + sizeof(reloc_offset); + symbol_offset.offset = (uint16_t) bytecode_reloc_offset_u32; + memcpy(insn->data, &symbol_offset, sizeof(symbol_offset)); + + /* + * Get offset in the bytecode where the opcode will end up at, + * the reloc offset points to it. + */ + reloc_offset_u32 = bytecode_get_len(&(*bytecode)->b); + if (reloc_offset_u32 > LTTNG_FILTER_MAX_LEN - 1) { + ret = -EINVAL; + goto end; + } + reloc_offset = (uint16_t) reloc_offset_u32; + + /* Append op in bytecode. */ + ret = bytecode_push(bytecode, insn, 1, insn_len); + if (ret) { + goto end; + } + + /* Append reloc offset. */ + ret = bytecode_push(bytecode_reloc, &reloc_offset, + 1, sizeof(reloc_offset)); + if (ret) { + goto end; + } + + /* Append symbol name. */ + ret = bytecode_push(bytecode_reloc, symbol, 1, strlen(symbol) + 1); + +end: + free(insn); + return ret; +} + +/* + * Allocate an lttng_bytecode object and copy the given original bytecode. + * + * Return allocated bytecode or NULL on error. + */ +struct lttng_bytecode *lttng_bytecode_copy( + const struct lttng_bytecode *orig_f) +{ + struct lttng_bytecode *bytecode = NULL; + + bytecode = zmalloc(sizeof(*bytecode) + orig_f->len); + if (!bytecode) { + goto error; + } + + memcpy(bytecode, orig_f, sizeof(*bytecode) + orig_f->len); + +error: + return bytecode; +}