From aa8f3937471137854e50c98607c311ca1ef6186b Mon Sep 17 00:00:00 2001 From: Stephan Bosch <stephan@rename-it.nl> Date: Sun, 30 Dec 2007 02:23:24 +0100 Subject: [PATCH] Added support for adding new types operands to the engine. --- src/lib-sieve/sieve-actions.c | 10 +- src/lib-sieve/sieve-address-parts.c | 10 +- src/lib-sieve/sieve-code.c | 143 ++++++++++++++++------------ src/lib-sieve/sieve-code.h | 7 +- src/lib-sieve/sieve-comparators.c | 10 +- src/lib-sieve/sieve-extensions.h | 2 + src/lib-sieve/sieve-match-types.c | 11 ++- 7 files changed, 116 insertions(+), 77 deletions(-) diff --git a/src/lib-sieve/sieve-actions.c b/src/lib-sieve/sieve-actions.c index 5fb3ee44b..12f336bcf 100644 --- a/src/lib-sieve/sieve-actions.c +++ b/src/lib-sieve/sieve-actions.c @@ -89,14 +89,18 @@ static bool seffect_binary_load(struct sieve_binary *sbin) static struct sieve_operand_class side_effect_class = { "side-effect", NULL }; -struct sieve_operand side_effect_operand = - { "side-effect", &side_effect_class, FALSE }; + +struct sieve_operand side_effect_operand = { + "side-effect", + NULL, SIEVE_OPERAND_SIDE_EFFECT, + &side_effect_class +}; void sieve_opr_side_effect_emit (struct sieve_binary *sbin, const struct sieve_side_effect *seffect, int ext_id) { - (void) sieve_operand_emit_code(sbin, SIEVE_OPERAND_SIDE_EFFECT); + (void) sieve_operand_emit_code(sbin, &side_effect_operand, -1); (void) sieve_extension_emit_obj (sbin, &seff_default_reg, seffect, side_effects, ext_id); diff --git a/src/lib-sieve/sieve-address-parts.c b/src/lib-sieve/sieve-address-parts.c index bf6f70ddd..6e1474372 100644 --- a/src/lib-sieve/sieve-address-parts.c +++ b/src/lib-sieve/sieve-address-parts.c @@ -198,8 +198,12 @@ static bool addrp_binary_load(struct sieve_binary *sbin) struct sieve_operand_class address_part_class = { "address-part", NULL }; -struct sieve_operand address_part_operand = - { "address-part", &address_part_class, FALSE }; + +struct sieve_operand address_part_operand = { + "address-part", + NULL, SIEVE_OPERAND_ADDRESS_PART, + &address_part_class +}; /* * Address-part tag @@ -252,7 +256,7 @@ static bool tag_address_part_validate static void opr_address_part_emit (struct sieve_binary *sbin, const struct sieve_address_part *addrp, int ext_id) { - (void) sieve_operand_emit_code(sbin, SIEVE_OPERAND_ADDRESS_PART); + (void) sieve_operand_emit_code(sbin, &address_part_operand, -1); (void) sieve_extension_emit_obj (sbin, &addrp_default_reg, addrp, address_parts, ext_id); diff --git a/src/lib-sieve/sieve-code.c b/src/lib-sieve/sieve-code.c index 603a35770..f6c14515f 100644 --- a/src/lib-sieve/sieve-code.c +++ b/src/lib-sieve/sieve-code.c @@ -119,9 +119,68 @@ bool sieve_coded_stringlist_read_all } /* - * Operand functions + * Operands */ +/* Core operands */ + +const struct sieve_operand number_operand; +const struct sieve_operand string_operand; +const struct sieve_operand stringlist_operand; +extern const struct sieve_operand comparator_operand; +extern const struct sieve_operand match_type_operand; +extern const struct sieve_operand address_part_operand; +extern const struct sieve_operand side_effect_operand; + +const struct sieve_operand *sieve_operands[] = { + NULL, /* SIEVE_OPERAND_OPTIONAL */ + &number_operand, + &string_operand, + &stringlist_operand, + &comparator_operand, + &match_type_operand, + &address_part_operand, + &side_effect_operand +}; + +const unsigned int sieve_operand_count = + N_ELEMENTS(sieve_operands); + +static struct sieve_extension_obj_registry oprd_default_reg = + SIEVE_EXT_DEFINE_OPERANDS(sieve_operands); + +/* Operand functions */ + +inline sieve_size_t sieve_operand_emit_code + (struct sieve_binary *sbin, const struct sieve_operand *opr, int ext_id) +{ + return sieve_extension_emit_obj + (sbin, &oprd_default_reg, opr, operands, ext_id); +} + +static const struct sieve_extension_obj_registry * + sieve_operand_registry_get +(struct sieve_binary *sbin, unsigned int ext_index) +{ + int ext_id = -1; + const struct sieve_extension *ext; + + if ( (ext=sieve_binary_extension_get_by_index(sbin, ext_index, &ext_id)) + == NULL ) + return NULL; + + return &(ext->operands); +} + +const struct sieve_operand *sieve_operand_read + (struct sieve_binary *sbin, sieve_size_t *address) +{ + return sieve_extension_read_obj + (struct sieve_operand, sbin, address, &oprd_default_reg, + sieve_operand_registry_get); +} + +/* inline sieve_size_t sieve_operand_emit_code (struct sieve_binary *sbin, int operand) { @@ -142,20 +201,20 @@ const struct sieve_operand *sieve_operand_read else return NULL; } else { -/* int ext_id = -1; +/ * int ext_id = -1; const struct sieve_extension *ext = sieve_binary_extension_get_by_index (sbin, operand - SIEVE_OPERAND_CUSTOM, &ext_id); if ( ext != NULL ) return ext->operand; - else*/ + else * / return NULL; } } return NULL; -} +}*/ bool sieve_operand_optional_present (struct sieve_binary *sbin, sieve_size_t *address) @@ -202,8 +261,11 @@ const struct sieve_opr_number_interface number_interface = { const struct sieve_operand_class number_class = { "number", &number_interface }; -const struct sieve_operand number_operand = - { "@number", &number_class, TRUE }; +const struct sieve_operand number_operand = { + "@number", + NULL, SIEVE_OPERAND_NUMBER, + &number_class +}; /* String */ @@ -220,9 +282,11 @@ const struct sieve_opr_string_interface string_interface ={ const struct sieve_operand_class string_class = { "string", &string_interface }; -const struct sieve_operand string_operand = - { "@string", &string_class, TRUE }; - +const struct sieve_operand string_operand = { + "@string", + NULL, SIEVE_OPERAND_STRING, + &string_class +}; /* String List */ @@ -239,29 +303,11 @@ const struct sieve_opr_stringlist_interface stringlist_interface = { const struct sieve_operand_class stringlist_class = { "string-list", &stringlist_interface }; -const struct sieve_operand stringlist_operand = - { "@string-list", &stringlist_class, TRUE }; - -/* Core operands */ - -extern struct sieve_operand comparator_operand; -extern struct sieve_operand match_type_operand; -extern struct sieve_operand address_part_operand; -extern struct sieve_operand side_effect_operand; - -const struct sieve_operand *sieve_operands[] = { - NULL, /* SIEVE_OPERAND_OPTIONAL */ - &number_operand, - &string_operand, - &stringlist_operand, - &comparator_operand, - &match_type_operand, - &address_part_operand, - &side_effect_operand -}; - -const unsigned int sieve_operand_count = - N_ELEMENTS(sieve_operands); +const struct sieve_operand stringlist_operand = { + "@string-list", + NULL, SIEVE_OPERAND_STRING_LIST, + &stringlist_class +}; /* * Operand implementations @@ -271,7 +317,7 @@ const unsigned int sieve_operand_count = void sieve_opr_number_emit(struct sieve_binary *sbin, sieve_size_t number) { - (void) sieve_operand_emit_code(sbin, SIEVE_OPERAND_NUMBER); + (void) sieve_operand_emit_code(sbin, &number_operand, -1); (void) sieve_binary_emit_integer(sbin, number); } @@ -337,7 +383,7 @@ static bool opr_number_read void sieve_opr_string_emit(struct sieve_binary *sbin, string_t *str) { - (void) sieve_operand_emit_code(sbin, SIEVE_OPERAND_STRING); + (void) sieve_operand_emit_code(sbin, &string_operand, -1); (void) sieve_binary_emit_string(sbin, str); } @@ -417,7 +463,7 @@ void sieve_opr_stringlist_emit_start sieve_size_t *end_offset = t_new(sieve_size_t, 1); /* Emit byte identifying the type of operand */ - (void) sieve_operand_emit_code(sbin, SIEVE_OPERAND_STRING_LIST); + (void) sieve_operand_emit_code(sbin, &stringlist_operand, -1); /* Give the interpreter an easy way to skip over this string list */ *end_offset = sieve_binary_emit_offset(sbin, 0); @@ -672,34 +718,7 @@ const struct sieve_operation *sieve_operation_read return sieve_extension_read_obj (struct sieve_operation, sbin, address, &oprt_default_reg, sieve_operation_registry_get); - -/* unsigned int opcode; - - if ( sieve_binary_read_byte(sbin, address, &opcode) ) { - if ( opcode < SIEVE_OPERATION_CUSTOM ) { - if ( opcode < sieve_operations_count ) - return sieve_operations[opcode]; - else - return NULL; - } else { - struct sieve_operation *op; - int ext_id = -1; - const struct sieve_extension *ext; - - if ( (ext=sieve_binary_extension_get_by_index - (sbin, opcode - SIEVE_OPERATION_CUSTOM, &ext_id)) == NULL ) - return NULL; - - sieve_extension_read_object - (ext, struct sieve_operation, opcodes, sbin, address, op) - - return op; - } - } - - return NULL;*/ } - /* Code dump for core commands */ diff --git a/src/lib-sieve/sieve-code.h b/src/lib-sieve/sieve-code.h index 1c817c222..a05d9074c 100644 --- a/src/lib-sieve/sieve-code.h +++ b/src/lib-sieve/sieve-code.h @@ -38,9 +38,10 @@ struct sieve_operand_class { struct sieve_operand { const char *name; + struct sieve_extension *extension; + unsigned int code; + const struct sieve_operand_class *class; - - unsigned int positional:1; }; struct sieve_opr_number_interface { @@ -81,7 +82,7 @@ extern const struct sieve_operand *sieve_operands[]; extern const unsigned int sieve_operand_count; inline sieve_size_t sieve_operand_emit_code - (struct sieve_binary *sbin, int operand); + (struct sieve_binary *sbin, const struct sieve_operand *opr, int ext_id); const struct sieve_operand *sieve_operand_read (struct sieve_binary *sbin, sieve_size_t *address); diff --git a/src/lib-sieve/sieve-comparators.c b/src/lib-sieve/sieve-comparators.c index 644247f2d..e018663d8 100644 --- a/src/lib-sieve/sieve-comparators.c +++ b/src/lib-sieve/sieve-comparators.c @@ -201,8 +201,12 @@ static bool cmp_binary_load(struct sieve_binary *sbin) struct sieve_operand_class comparator_class = { "comparator", NULL }; -struct sieve_operand comparator_operand = - { "comparator", &comparator_class, FALSE }; + +struct sieve_operand comparator_operand = { + "comparator", + NULL, SIEVE_OPERAND_COMPARATOR, + &comparator_class +}; /* * Comparator tag @@ -305,7 +309,7 @@ inline const struct sieve_comparator *sieve_comparator_tag_get static void opr_comparator_emit (struct sieve_binary *sbin, const struct sieve_comparator *cmp, int ext_id) { - (void) sieve_operand_emit_code(sbin, SIEVE_OPERAND_COMPARATOR); + (void) sieve_operand_emit_code(sbin, &comparator_operand, -1); (void) sieve_extension_emit_obj (sbin, &cmp_default_reg, cmp, comparators, ext_id); diff --git a/src/lib-sieve/sieve-extensions.h b/src/lib-sieve/sieve-extensions.h index 1db54d10f..e952ef1b5 100644 --- a/src/lib-sieve/sieve-extensions.h +++ b/src/lib-sieve/sieve-extensions.h @@ -44,6 +44,8 @@ struct sieve_extension { #define SIEVE_EXT_DEFINE_OPERATIONS(OPS) SIEVE_EXT_DEFINE_OBJECTS(OPS) #define SIEVE_EXT_DEFINE_NO_OPERANDS SIEVE_EXT_DEFINE_NO_OBJECTS +#define SIEVE_EXT_DEFINE_OPERAND(OP) SIEVE_EXT_DEFINE_OBJECT(OP) +#define SIEVE_EXT_DEFINE_OPERANDS(OPS) SIEVE_EXT_DEFINE_OBJECTS(OPS) /* Pre-loaded extensions */ diff --git a/src/lib-sieve/sieve-match-types.c b/src/lib-sieve/sieve-match-types.c index edd79cfba..1cf22c434 100644 --- a/src/lib-sieve/sieve-match-types.c +++ b/src/lib-sieve/sieve-match-types.c @@ -195,8 +195,13 @@ static bool mtch_binary_load(struct sieve_binary *sbin) struct sieve_operand_class match_type_class = { "match-type", NULL }; -struct sieve_operand match_type_operand = - { "match-type", &match_type_class, FALSE }; + +struct sieve_operand match_type_operand = { + "match-type", + NULL, + SIEVE_OPERAND_MATCH_TYPE, + &match_type_class +}; /* * Match-type tag @@ -295,7 +300,7 @@ bool sieve_match_type_validate static void opr_match_type_emit (struct sieve_binary *sbin, const struct sieve_match_type *mtch, int ext_id) { - (void) sieve_operand_emit_code(sbin, SIEVE_OPERAND_MATCH_TYPE); + (void) sieve_operand_emit_code(sbin, &match_type_operand, -1); (void) sieve_extension_emit_obj (sbin, &mtch_default_reg, mtch, match_types, ext_id); -- GitLab