Skip to content
Snippets Groups Projects
Commit cb095ead authored by Stephan Bosch's avatar Stephan Bosch
Browse files

Finished i;ascii-numeric comparator and fixed a segfault bug in the process.

parent 84c99223
No related branches found
No related tags found
No related merge requests found
...@@ -50,7 +50,7 @@ Extensions and their implementation status: ...@@ -50,7 +50,7 @@ Extensions and their implementation status:
Other RFCs/drafts: Other RFCs/drafts:
subaddress: full subaddress: full
comparator-i;ascii-numeric: full, but fails to handle leading zeros comparator-i;ascii-numeric: full
relational: full relational: full
regex: full, but suboptimal regex: full, but suboptimal
vacation: validation, generation and interpretation; no execution vacation: validation, generation and interpretation; no execution
......
...@@ -165,7 +165,7 @@ static bool cmd_if_generate ...@@ -165,7 +165,7 @@ static bool cmd_if_generate
* anyway. * anyway.
*/ */
if ( !sieve_command_block_exits_unconditionally(ctx) ) { if ( !sieve_command_block_exits_unconditionally(ctx) ) {
sieve_operation_emit_code(sbin, SIEVE_OPCODE_JMP); sieve_operation_emit_code(sbin, &sieve_jmp_opcode);
ctx_data->exit_jump = sieve_binary_emit_offset(sbin, 0); ctx_data->exit_jump = sieve_binary_emit_offset(sbin, 0);
ctx_data->jump_generated = TRUE; ctx_data->jump_generated = TRUE;
} }
......
...@@ -3,7 +3,7 @@ ...@@ -3,7 +3,7 @@
* *
* Author: Stephan Bosch * Author: Stephan Bosch
* Specification: RFC 2244 * Specification: RFC 2244
* Implementation: full, but fails to handle leading zeros. * Implementation: full
* Status: experimental, largely untested * Status: experimental, largely untested
* *
*/ */
...@@ -97,35 +97,40 @@ static bool ext_cmp_i_ascii_numeric_interpreter_load ...@@ -97,35 +97,40 @@ static bool ext_cmp_i_ascii_numeric_interpreter_load
static int cmp_i_ascii_numeric_compare static int cmp_i_ascii_numeric_compare
(const struct sieve_comparator *cmp ATTR_UNUSED, (const struct sieve_comparator *cmp ATTR_UNUSED,
const char *val1, size_t val1_size, const char *val2, size_t val2_size) const char *val, size_t val_size, const char *key, size_t key_size)
{ {
unsigned int i = 0; const char *vend = val + val_size;
int result = 0; const char *kend = key + key_size;
const char *nval1 = (const char *) val1, *nval2 = (const char *) val2; const char *vp = val;
const char *kp = key;
while ( i < val1_size && i < val2_size ) {
if ( isdigit(nval1[i]) ) { /* Ignore leading zeros */
if ( isdigit(nval2[i]) ) {
if ( result == 0 && nval1[i] != nval2[i] ) { while ( *vp == '0' && vp < vend )
if ( nval1[i] > nval2[i] ) vp++;
result = 1;
else while ( *kp == '0' && kp < kend )
result = 0; kp++;
}
} else { while ( vp < vend && kp < kend ) {
return 1; if ( !isdigit(*vp) || !isdigit(*kp) )
} break;
} else {
if ( isdigit(nval2[i]) ) { if ( *vp != *kp )
return -1; break;
} else {
return result; vp++;
} kp++;
}
i++;
} }
if ( vp == vend || !isdigit(*vp) ) {
if ( kp == kend || !isdigit(*kp) )
return 0;
else
return -1;
} else if ( kp == kend || !isdigit(*kp) )
return 1;
return result; return (*vp > *kp);
} }
require ["comparator-i;ascii-numeric", "relational"]; require ["comparator-i;ascii-numeric", "relational", "fileinto"];
if header :value "eq" :comparator "i;ascii-numeric" "x-spam-score" "2" { if header :value "eq" :comparator "i;ascii-numeric" "x-spam-score" "2" {
discard; fileinto "INBOX.fail";
stop; } else {
fileinto "INBOX.succeed";
} }
if header :value "lt" :comparator "i;ascii-numeric" "x-spam-score" "2" { if header :value "lt" :comparator "i;ascii-numeric" "x-spam-score" "2" {
discard; fileinto "INBOX.fail";
stop; } else {
fileinto "INBOX.succeed";
} }
if header :value "lt" :comparator "i;ascii-numeric" "x-spam-score" "2" { if header :value "lt" :comparator "i;ascii-numeric" "x-spam-score" "2" {
discard; fileinto "INBOX.fail";
stop; } else {
fileinto "INBOX.succeed";
}
if header :value "le" :comparator "i;ascii-numeric" "x-spam-score" "300" {
fileinto "INBOX.succeed";
} else {
fileinto "INBOX.fail";
}
if header :value "le" :comparator "i;ascii-numeric" "x-spam-score" "302" {
fileinto "INBOX.succeed";
} else {
fileinto "INBOX.fail";
}
if header :value "le" :comparator "i;ascii-numeric" "x-spam-score" "00302" {
fileinto "INBOX.succeed";
} else {
fileinto "INBOX.fail";
} }
if header :count "ne" :comparator "i;ascii-numeric" "to" "2" { if header :count "ne" :comparator "i;ascii-numeric" "to" "2" {
discard; fileinto "INBOX.fail";
stop; } else {
fileinto "INBOX.succeed";
} }
if header :count "ge" :comparator "i;ascii-numeric" "to" "2" { if header :count "ge" :comparator "i;ascii-numeric" "to" "2" {
discard; fileinto "INBOX.succeed";
stop; } else {
fileinto "INBOX.fail";
}
if header :count "ge" :comparator "i;ascii-numeric" "to" "002" {
fileinto "INBOX.succeed";
} else {
fileinto "INBOX.fail";
} }
keep; keep;
...@@ -56,7 +56,7 @@ static bool tst_allof_generate ...@@ -56,7 +56,7 @@ static bool tst_allof_generate
if ( jump_true ) { if ( jump_true ) {
/* All tests succeeded, jump to case TRUE */ /* All tests succeeded, jump to case TRUE */
sieve_generator_emit_opcode(generator, SIEVE_OPCODE_JMP); sieve_generator_emit_opcode(generator, &sieve_jmp_opcode);
sieve_jumplist_add(jumps, sieve_binary_emit_offset(sbin, 0)); sieve_jumplist_add(jumps, sieve_binary_emit_offset(sbin, 0));
/* All false exits jump here */ /* All false exits jump here */
......
...@@ -54,7 +54,7 @@ static bool tst_anyof_generate ...@@ -54,7 +54,7 @@ static bool tst_anyof_generate
if ( !jump_true ) { if ( !jump_true ) {
/* All tests failed, jump to case FALSE */ /* All tests failed, jump to case FALSE */
sieve_operation_emit_code(sbin, SIEVE_OPCODE_JMP); sieve_operation_emit_code(sbin, &sieve_jmp_opcode);
sieve_jumplist_add(jumps, sieve_binary_emit_offset(sbin, 0)); sieve_jumplist_add(jumps, sieve_binary_emit_offset(sbin, 0));
/* All true exits jump here */ /* All true exits jump here */
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment

Consent

On this website, we use the web analytics service Matomo to analyze and review the use of our website. Through the collected statistics, we can improve our offerings and make them more appealing for you. Here, you can decide whether to allow us to process your data and set corresponding cookies for these purposes, in addition to technically necessary cookies. Further information on data protection—especially regarding "cookies" and "Matomo"—can be found in our privacy policy. You can withdraw your consent at any time.