From acae512191ef18394f909d165b2720164de9f996 Mon Sep 17 00:00:00 2001 From: Jamiras Date: Wed, 12 Dec 2018 15:59:02 -0700 Subject: [PATCH 01/11] separate RC_MEMSIZE_ enum from RC_OPERAND_ enum --- include/rcheevos.h | 28 ++-- src/rcheevos/operand.c | 58 ++++---- src/rcheevos/term.c | 30 ++--- test/test.c | 300 ++++++++++++++++++++--------------------- 4 files changed, 208 insertions(+), 208 deletions(-) diff --git a/include/rcheevos.h b/include/rcheevos.h index 898ed984..5ee846e7 100644 --- a/include/rcheevos.h +++ b/include/rcheevos.h @@ -88,20 +88,20 @@ typedef unsigned (*rc_peek_t)(unsigned address, unsigned num_bytes, void* ud); /* Sizes. */ enum { - RC_OPERAND_BIT_0, - RC_OPERAND_BIT_1, - RC_OPERAND_BIT_2, - RC_OPERAND_BIT_3, - RC_OPERAND_BIT_4, - RC_OPERAND_BIT_5, - RC_OPERAND_BIT_6, - RC_OPERAND_BIT_7, - RC_OPERAND_LOW, - RC_OPERAND_HIGH, - RC_OPERAND_8_BITS, - RC_OPERAND_16_BITS, - RC_OPERAND_24_BITS, - RC_OPERAND_32_BITS + RC_MEMSIZE_BIT_0, + RC_MEMSIZE_BIT_1, + RC_MEMSIZE_BIT_2, + RC_MEMSIZE_BIT_3, + RC_MEMSIZE_BIT_4, + RC_MEMSIZE_BIT_5, + RC_MEMSIZE_BIT_6, + RC_MEMSIZE_BIT_7, + RC_MEMSIZE_LOW, + RC_MEMSIZE_HIGH, + RC_MEMSIZE_8_BITS, + RC_MEMSIZE_16_BITS, + RC_MEMSIZE_24_BITS, + RC_MEMSIZE_32_BITS }; /* types */ diff --git a/src/rcheevos/operand.c b/src/rcheevos/operand.c index 941ab75f..1d5df49a 100644 --- a/src/rcheevos/operand.c +++ b/src/rcheevos/operand.c @@ -97,24 +97,24 @@ static int rc_parse_operand_memory(rc_operand_t* self, const char** memaddr) { aux++; switch (*aux++) { - case 'm': case 'M': self->size = RC_OPERAND_BIT_0; break; - case 'n': case 'N': self->size = RC_OPERAND_BIT_1; break; - case 'o': case 'O': self->size = RC_OPERAND_BIT_2; break; - case 'p': case 'P': self->size = RC_OPERAND_BIT_3; break; - case 'q': case 'Q': self->size = RC_OPERAND_BIT_4; break; - case 'r': case 'R': self->size = RC_OPERAND_BIT_5; break; - case 's': case 'S': self->size = RC_OPERAND_BIT_6; break; - case 't': case 'T': self->size = RC_OPERAND_BIT_7; break; - case 'l': case 'L': self->size = RC_OPERAND_LOW; break; - case 'u': case 'U': self->size = RC_OPERAND_HIGH; break; - case 'h': case 'H': self->size = RC_OPERAND_8_BITS; break; - case 'w': case 'W': self->size = RC_OPERAND_24_BITS; break; - case 'x': case 'X': self->size = RC_OPERAND_32_BITS; break; + case 'm': case 'M': self->size = RC_MEMSIZE_BIT_0; break; + case 'n': case 'N': self->size = RC_MEMSIZE_BIT_1; break; + case 'o': case 'O': self->size = RC_MEMSIZE_BIT_2; break; + case 'p': case 'P': self->size = RC_MEMSIZE_BIT_3; break; + case 'q': case 'Q': self->size = RC_MEMSIZE_BIT_4; break; + case 'r': case 'R': self->size = RC_MEMSIZE_BIT_5; break; + case 's': case 'S': self->size = RC_MEMSIZE_BIT_6; break; + case 't': case 'T': self->size = RC_MEMSIZE_BIT_7; break; + case 'l': case 'L': self->size = RC_MEMSIZE_LOW; break; + case 'u': case 'U': self->size = RC_MEMSIZE_HIGH; break; + case 'h': case 'H': self->size = RC_MEMSIZE_8_BITS; break; + case 'w': case 'W': self->size = RC_MEMSIZE_24_BITS; break; + case 'x': case 'X': self->size = RC_MEMSIZE_32_BITS; break; default: /* fall through */ aux--; case ' ': - self->size = RC_OPERAND_16_BITS; + self->size = RC_MEMSIZE_16_BITS; break; } @@ -289,7 +289,7 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, lua_S } int rc_parse_operand(rc_operand_t* self, const char** memaddr, int is_trigger, lua_State* L, int funcs_ndx) { - self->size = RC_OPERAND_8_BITS; + self->size = RC_MEMSIZE_8_BITS; self->is_bcd = 0; self->previous = 0; self->prior = 0; @@ -371,47 +371,47 @@ unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_S case RC_OPERAND_DELTA: case RC_OPERAND_PRIOR: switch (self->size) { - case RC_OPERAND_BIT_0: + case RC_MEMSIZE_BIT_0: value = (peek(self->value, 1, ud) >> 0) & 1; break; - case RC_OPERAND_BIT_1: + case RC_MEMSIZE_BIT_1: value = (peek(self->value, 1, ud) >> 1) & 1; break; - case RC_OPERAND_BIT_2: + case RC_MEMSIZE_BIT_2: value = (peek(self->value, 1, ud) >> 2) & 1; break; - case RC_OPERAND_BIT_3: + case RC_MEMSIZE_BIT_3: value = (peek(self->value, 1, ud) >> 3) & 1; break; - case RC_OPERAND_BIT_4: + case RC_MEMSIZE_BIT_4: value = (peek(self->value, 1, ud) >> 4) & 1; break; - case RC_OPERAND_BIT_5: + case RC_MEMSIZE_BIT_5: value = (peek(self->value, 1, ud) >> 5 ) & 1; break; - case RC_OPERAND_BIT_6: + case RC_MEMSIZE_BIT_6: value = (peek(self->value, 1, ud) >> 6) & 1; break; - case RC_OPERAND_BIT_7: + case RC_MEMSIZE_BIT_7: value = (peek(self->value, 1, ud) >> 7) & 1; break; - case RC_OPERAND_LOW: + case RC_MEMSIZE_LOW: value = peek(self->value, 1, ud) & 0x0f; break; - case RC_OPERAND_HIGH: + case RC_MEMSIZE_HIGH: value = (peek(self->value, 1, ud) >> 4) & 0x0f; break; - case RC_OPERAND_8_BITS: + case RC_MEMSIZE_8_BITS: value = peek(self->value, 1, ud); if (self->is_bcd) { @@ -420,7 +420,7 @@ unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_S break; - case RC_OPERAND_16_BITS: + case RC_MEMSIZE_16_BITS: value = peek(self->value, 2, ud); if (self->is_bcd) { @@ -432,7 +432,7 @@ unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_S break; - case RC_OPERAND_24_BITS: + case RC_MEMSIZE_24_BITS: value = peek(self->value, 4, ud); if (self->is_bcd) { @@ -446,7 +446,7 @@ unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_S break; - case RC_OPERAND_32_BITS: + case RC_MEMSIZE_32_BITS: value = peek(self->value, 4, ud); if (self->is_bcd) { diff --git a/src/rcheevos/term.c b/src/rcheevos/term.c index 33019fa5..767976a8 100644 --- a/src/rcheevos/term.c +++ b/src/rcheevos/term.c @@ -33,35 +33,35 @@ rc_term_t* rc_parse_term(int* ret, void* buffer, rc_scratch_t* scratch, const ch if (self->invert) { switch (self->operand2.size) { - case RC_OPERAND_BIT_0: - case RC_OPERAND_BIT_1: - case RC_OPERAND_BIT_2: - case RC_OPERAND_BIT_3: - case RC_OPERAND_BIT_4: - case RC_OPERAND_BIT_5: - case RC_OPERAND_BIT_6: - case RC_OPERAND_BIT_7: + case RC_MEMSIZE_BIT_0: + case RC_MEMSIZE_BIT_1: + case RC_MEMSIZE_BIT_2: + case RC_MEMSIZE_BIT_3: + case RC_MEMSIZE_BIT_4: + case RC_MEMSIZE_BIT_5: + case RC_MEMSIZE_BIT_6: + case RC_MEMSIZE_BIT_7: /* invert is already 1 */ break; - case RC_OPERAND_LOW: - case RC_OPERAND_HIGH: + case RC_MEMSIZE_LOW: + case RC_MEMSIZE_HIGH: self->invert = 0xf; break; - case RC_OPERAND_8_BITS: + case RC_MEMSIZE_8_BITS: self->invert = 0xffU; break; - case RC_OPERAND_16_BITS: + case RC_MEMSIZE_16_BITS: self->invert = 0xffffU; break; - case RC_OPERAND_24_BITS: + case RC_MEMSIZE_24_BITS: self->invert = 0xffffffU; break; - case RC_OPERAND_32_BITS: + case RC_MEMSIZE_32_BITS: self->invert = 0xffffffffU; break; } @@ -69,7 +69,7 @@ rc_term_t* rc_parse_term(int* ret, void* buffer, rc_scratch_t* scratch, const ch } else { self->operand2.type = RC_OPERAND_FP; - self->operand2.size = RC_OPERAND_8_BITS; + self->operand2.size = RC_MEMSIZE_8_BITS; self->operand2.fp_value = 1.0; } diff --git a/test/test.c b/test/test.c index dbebe736..7b18961c 100644 --- a/test/test.c +++ b/test/test.c @@ -91,41 +91,41 @@ static void test_operand(void) { ------------------------------------------------------------------------*/ /* sizes */ - parse_comp_operand("0xH1234", RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U); - parse_comp_operand("0x 1234", RC_OPERAND_ADDRESS, RC_OPERAND_16_BITS, 0x1234U); - parse_comp_operand("0x1234", RC_OPERAND_ADDRESS, RC_OPERAND_16_BITS, 0x1234U); - parse_comp_operand("0xW1234", RC_OPERAND_ADDRESS, RC_OPERAND_24_BITS, 0x1234U); - parse_comp_operand("0xX1234", RC_OPERAND_ADDRESS, RC_OPERAND_32_BITS, 0x1234U); - parse_comp_operand("0xL1234", RC_OPERAND_ADDRESS, RC_OPERAND_LOW, 0x1234U); - parse_comp_operand("0xU1234", RC_OPERAND_ADDRESS, RC_OPERAND_HIGH, 0x1234U); - parse_comp_operand("0xM1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_0, 0x1234U); - parse_comp_operand("0xN1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_1, 0x1234U); - parse_comp_operand("0xO1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_2, 0x1234U); - parse_comp_operand("0xP1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_3, 0x1234U); - parse_comp_operand("0xQ1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_4, 0x1234U); - parse_comp_operand("0xR1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_5, 0x1234U); - parse_comp_operand("0xS1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_6, 0x1234U); - parse_comp_operand("0xT1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_7, 0x1234U); + parse_comp_operand("0xH1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U); + parse_comp_operand("0x 1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_16_BITS, 0x1234U); + parse_comp_operand("0x1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_16_BITS, 0x1234U); + parse_comp_operand("0xW1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_24_BITS, 0x1234U); + parse_comp_operand("0xX1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_32_BITS, 0x1234U); + parse_comp_operand("0xL1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_LOW, 0x1234U); + parse_comp_operand("0xU1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_HIGH, 0x1234U); + parse_comp_operand("0xM1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_0, 0x1234U); + parse_comp_operand("0xN1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_1, 0x1234U); + parse_comp_operand("0xO1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_2, 0x1234U); + parse_comp_operand("0xP1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_3, 0x1234U); + parse_comp_operand("0xQ1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_4, 0x1234U); + parse_comp_operand("0xR1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_5, 0x1234U); + parse_comp_operand("0xS1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_6, 0x1234U); + parse_comp_operand("0xT1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_7, 0x1234U); /* sizes (ignore case) */ - parse_comp_operand("0Xh1234", RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U); - parse_comp_operand("0xx1234", RC_OPERAND_ADDRESS, RC_OPERAND_32_BITS, 0x1234U); - parse_comp_operand("0xl1234", RC_OPERAND_ADDRESS, RC_OPERAND_LOW, 0x1234U); - parse_comp_operand("0xu1234", RC_OPERAND_ADDRESS, RC_OPERAND_HIGH, 0x1234U); - parse_comp_operand("0xm1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_0, 0x1234U); - parse_comp_operand("0xn1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_1, 0x1234U); - parse_comp_operand("0xo1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_2, 0x1234U); - parse_comp_operand("0xp1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_3, 0x1234U); - parse_comp_operand("0xq1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_4, 0x1234U); - parse_comp_operand("0xr1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_5, 0x1234U); - parse_comp_operand("0xs1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_6, 0x1234U); - parse_comp_operand("0xt1234", RC_OPERAND_ADDRESS, RC_OPERAND_BIT_7, 0x1234U); + parse_comp_operand("0Xh1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U); + parse_comp_operand("0xx1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_32_BITS, 0x1234U); + parse_comp_operand("0xl1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_LOW, 0x1234U); + parse_comp_operand("0xu1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_HIGH, 0x1234U); + parse_comp_operand("0xm1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_0, 0x1234U); + parse_comp_operand("0xn1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_1, 0x1234U); + parse_comp_operand("0xo1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_2, 0x1234U); + parse_comp_operand("0xp1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_3, 0x1234U); + parse_comp_operand("0xq1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_4, 0x1234U); + parse_comp_operand("0xr1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_5, 0x1234U); + parse_comp_operand("0xs1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_6, 0x1234U); + parse_comp_operand("0xt1234", RC_OPERAND_ADDRESS, RC_MEMSIZE_BIT_7, 0x1234U); /* addresses */ - parse_comp_operand("0xH0000", RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x0000U); - parse_comp_operand("0xH12345678", RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x12345678U); - parse_comp_operand("0xHABCD", RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0xABCDU); - parse_comp_operand("0xhabcd", RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0xABCDU); + parse_comp_operand("0xH0000", RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x0000U); + parse_comp_operand("0xH12345678", RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x12345678U); + parse_comp_operand("0xHABCD", RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0xABCDU); + parse_comp_operand("0xhabcd", RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0xABCDU); } { @@ -134,30 +134,30 @@ static void test_operand(void) { ------------------------------------------------------------------------*/ /* sizes */ - parse_comp_operand("d0xH1234", RC_OPERAND_DELTA, RC_OPERAND_8_BITS, 0x1234U); - parse_comp_operand("d0x 1234", RC_OPERAND_DELTA, RC_OPERAND_16_BITS, 0x1234U); - parse_comp_operand("d0x1234", RC_OPERAND_DELTA, RC_OPERAND_16_BITS, 0x1234U); - parse_comp_operand("d0xW1234", RC_OPERAND_DELTA, RC_OPERAND_24_BITS, 0x1234U); - parse_comp_operand("d0xX1234", RC_OPERAND_DELTA, RC_OPERAND_32_BITS, 0x1234U); - parse_comp_operand("d0xL1234", RC_OPERAND_DELTA, RC_OPERAND_LOW, 0x1234U); - parse_comp_operand("d0xU1234", RC_OPERAND_DELTA, RC_OPERAND_HIGH, 0x1234U); - parse_comp_operand("d0xM1234", RC_OPERAND_DELTA, RC_OPERAND_BIT_0, 0x1234U); - parse_comp_operand("d0xN1234", RC_OPERAND_DELTA, RC_OPERAND_BIT_1, 0x1234U); - parse_comp_operand("d0xO1234", RC_OPERAND_DELTA, RC_OPERAND_BIT_2, 0x1234U); - parse_comp_operand("d0xP1234", RC_OPERAND_DELTA, RC_OPERAND_BIT_3, 0x1234U); - parse_comp_operand("d0xQ1234", RC_OPERAND_DELTA, RC_OPERAND_BIT_4, 0x1234U); - parse_comp_operand("d0xR1234", RC_OPERAND_DELTA, RC_OPERAND_BIT_5, 0x1234U); - parse_comp_operand("d0xS1234", RC_OPERAND_DELTA, RC_OPERAND_BIT_6, 0x1234U); - parse_comp_operand("d0xT1234", RC_OPERAND_DELTA, RC_OPERAND_BIT_7, 0x1234U); + parse_comp_operand("d0xH1234", RC_OPERAND_DELTA, RC_MEMSIZE_8_BITS, 0x1234U); + parse_comp_operand("d0x 1234", RC_OPERAND_DELTA, RC_MEMSIZE_16_BITS, 0x1234U); + parse_comp_operand("d0x1234", RC_OPERAND_DELTA, RC_MEMSIZE_16_BITS, 0x1234U); + parse_comp_operand("d0xW1234", RC_OPERAND_DELTA, RC_MEMSIZE_24_BITS, 0x1234U); + parse_comp_operand("d0xX1234", RC_OPERAND_DELTA, RC_MEMSIZE_32_BITS, 0x1234U); + parse_comp_operand("d0xL1234", RC_OPERAND_DELTA, RC_MEMSIZE_LOW, 0x1234U); + parse_comp_operand("d0xU1234", RC_OPERAND_DELTA, RC_MEMSIZE_HIGH, 0x1234U); + parse_comp_operand("d0xM1234", RC_OPERAND_DELTA, RC_MEMSIZE_BIT_0, 0x1234U); + parse_comp_operand("d0xN1234", RC_OPERAND_DELTA, RC_MEMSIZE_BIT_1, 0x1234U); + parse_comp_operand("d0xO1234", RC_OPERAND_DELTA, RC_MEMSIZE_BIT_2, 0x1234U); + parse_comp_operand("d0xP1234", RC_OPERAND_DELTA, RC_MEMSIZE_BIT_3, 0x1234U); + parse_comp_operand("d0xQ1234", RC_OPERAND_DELTA, RC_MEMSIZE_BIT_4, 0x1234U); + parse_comp_operand("d0xR1234", RC_OPERAND_DELTA, RC_MEMSIZE_BIT_5, 0x1234U); + parse_comp_operand("d0xS1234", RC_OPERAND_DELTA, RC_MEMSIZE_BIT_6, 0x1234U); + parse_comp_operand("d0xT1234", RC_OPERAND_DELTA, RC_MEMSIZE_BIT_7, 0x1234U); /* ignores case */ - parse_comp_operand("D0Xh1234", RC_OPERAND_DELTA, RC_OPERAND_8_BITS, 0x1234U); + parse_comp_operand("D0Xh1234", RC_OPERAND_DELTA, RC_MEMSIZE_8_BITS, 0x1234U); /* addresses */ - parse_comp_operand("d0xH0000", RC_OPERAND_DELTA, RC_OPERAND_8_BITS, 0x0000U); - parse_comp_operand("d0xH12345678", RC_OPERAND_DELTA, RC_OPERAND_8_BITS, 0x12345678U); - parse_comp_operand("d0xHABCD", RC_OPERAND_DELTA, RC_OPERAND_8_BITS, 0xABCDU); - parse_comp_operand("d0xhabcd", RC_OPERAND_DELTA, RC_OPERAND_8_BITS, 0xABCDU); + parse_comp_operand("d0xH0000", RC_OPERAND_DELTA, RC_MEMSIZE_8_BITS, 0x0000U); + parse_comp_operand("d0xH12345678", RC_OPERAND_DELTA, RC_MEMSIZE_8_BITS, 0x12345678U); + parse_comp_operand("d0xHABCD", RC_OPERAND_DELTA, RC_MEMSIZE_8_BITS, 0xABCDU); + parse_comp_operand("d0xhabcd", RC_OPERAND_DELTA, RC_MEMSIZE_8_BITS, 0xABCDU); } { @@ -166,30 +166,30 @@ static void test_operand(void) { ------------------------------------------------------------------------*/ /* sizes */ - parse_comp_operand("p0xH1234", RC_OPERAND_PRIOR, RC_OPERAND_8_BITS, 0x1234U); - parse_comp_operand("p0x 1234", RC_OPERAND_PRIOR, RC_OPERAND_16_BITS, 0x1234U); - parse_comp_operand("p0x1234", RC_OPERAND_PRIOR, RC_OPERAND_16_BITS, 0x1234U); - parse_comp_operand("p0xW1234", RC_OPERAND_PRIOR, RC_OPERAND_24_BITS, 0x1234U); - parse_comp_operand("p0xX1234", RC_OPERAND_PRIOR, RC_OPERAND_32_BITS, 0x1234U); - parse_comp_operand("p0xL1234", RC_OPERAND_PRIOR, RC_OPERAND_LOW, 0x1234U); - parse_comp_operand("p0xU1234", RC_OPERAND_PRIOR, RC_OPERAND_HIGH, 0x1234U); - parse_comp_operand("p0xM1234", RC_OPERAND_PRIOR, RC_OPERAND_BIT_0, 0x1234U); - parse_comp_operand("p0xN1234", RC_OPERAND_PRIOR, RC_OPERAND_BIT_1, 0x1234U); - parse_comp_operand("p0xO1234", RC_OPERAND_PRIOR, RC_OPERAND_BIT_2, 0x1234U); - parse_comp_operand("p0xP1234", RC_OPERAND_PRIOR, RC_OPERAND_BIT_3, 0x1234U); - parse_comp_operand("p0xQ1234", RC_OPERAND_PRIOR, RC_OPERAND_BIT_4, 0x1234U); - parse_comp_operand("p0xR1234", RC_OPERAND_PRIOR, RC_OPERAND_BIT_5, 0x1234U); - parse_comp_operand("p0xS1234", RC_OPERAND_PRIOR, RC_OPERAND_BIT_6, 0x1234U); - parse_comp_operand("p0xT1234", RC_OPERAND_PRIOR, RC_OPERAND_BIT_7, 0x1234U); + parse_comp_operand("p0xH1234", RC_OPERAND_PRIOR, RC_MEMSIZE_8_BITS, 0x1234U); + parse_comp_operand("p0x 1234", RC_OPERAND_PRIOR, RC_MEMSIZE_16_BITS, 0x1234U); + parse_comp_operand("p0x1234", RC_OPERAND_PRIOR, RC_MEMSIZE_16_BITS, 0x1234U); + parse_comp_operand("p0xW1234", RC_OPERAND_PRIOR, RC_MEMSIZE_24_BITS, 0x1234U); + parse_comp_operand("p0xX1234", RC_OPERAND_PRIOR, RC_MEMSIZE_32_BITS, 0x1234U); + parse_comp_operand("p0xL1234", RC_OPERAND_PRIOR, RC_MEMSIZE_LOW, 0x1234U); + parse_comp_operand("p0xU1234", RC_OPERAND_PRIOR, RC_MEMSIZE_HIGH, 0x1234U); + parse_comp_operand("p0xM1234", RC_OPERAND_PRIOR, RC_MEMSIZE_BIT_0, 0x1234U); + parse_comp_operand("p0xN1234", RC_OPERAND_PRIOR, RC_MEMSIZE_BIT_1, 0x1234U); + parse_comp_operand("p0xO1234", RC_OPERAND_PRIOR, RC_MEMSIZE_BIT_2, 0x1234U); + parse_comp_operand("p0xP1234", RC_OPERAND_PRIOR, RC_MEMSIZE_BIT_3, 0x1234U); + parse_comp_operand("p0xQ1234", RC_OPERAND_PRIOR, RC_MEMSIZE_BIT_4, 0x1234U); + parse_comp_operand("p0xR1234", RC_OPERAND_PRIOR, RC_MEMSIZE_BIT_5, 0x1234U); + parse_comp_operand("p0xS1234", RC_OPERAND_PRIOR, RC_MEMSIZE_BIT_6, 0x1234U); + parse_comp_operand("p0xT1234", RC_OPERAND_PRIOR, RC_MEMSIZE_BIT_7, 0x1234U); /* ignores case */ - parse_comp_operand("P0Xh1234", RC_OPERAND_PRIOR, RC_OPERAND_8_BITS, 0x1234U); + parse_comp_operand("P0Xh1234", RC_OPERAND_PRIOR, RC_MEMSIZE_8_BITS, 0x1234U); /* addresses */ - parse_comp_operand("p0xH0000", RC_OPERAND_PRIOR, RC_OPERAND_8_BITS, 0x0000U); - parse_comp_operand("p0xH12345678", RC_OPERAND_PRIOR, RC_OPERAND_8_BITS, 0x12345678U); - parse_comp_operand("p0xHABCD", RC_OPERAND_PRIOR, RC_OPERAND_8_BITS, 0xABCDU); - parse_comp_operand("p0xhabcd", RC_OPERAND_PRIOR, RC_OPERAND_8_BITS, 0xABCDU); + parse_comp_operand("p0xH0000", RC_OPERAND_PRIOR, RC_MEMSIZE_8_BITS, 0x0000U); + parse_comp_operand("p0xH12345678", RC_OPERAND_PRIOR, RC_MEMSIZE_8_BITS, 0x12345678U); + parse_comp_operand("p0xHABCD", RC_OPERAND_PRIOR, RC_MEMSIZE_8_BITS, 0xABCDU); + parse_comp_operand("p0xhabcd", RC_OPERAND_PRIOR, RC_MEMSIZE_8_BITS, 0xABCDU); } { @@ -197,31 +197,31 @@ static void test_operand(void) { TestParseVariableValue ------------------------------------------------------------------------*/ - /* decimal - values don't actually have size, default is RC_OPERAND_8_BITS */ - parse_comp_operand("123", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 123U); - parse_comp_operand("123456", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 123456U); - parse_comp_operand("0", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 0U); - parse_comp_operand("0000000000", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 0U); - parse_comp_operand("4294967295", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 4294967295U); + /* decimal - values don't actually have size, default is RC_MEMSIZE_8_BITS */ + parse_comp_operand("123", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 123U); + parse_comp_operand("123456", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 123456U); + parse_comp_operand("0", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 0U); + parse_comp_operand("0000000000", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 0U); + parse_comp_operand("4294967295", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 4294967295U); /* hex - 'H' prefix, not '0x'! */ - parse_comp_operand("H123", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 0x123U); - parse_comp_operand("HABCD", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 0xABCDU); - parse_comp_operand("h123", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 0x123U); - parse_comp_operand("habcd", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 0xABCDU); - parse_comp_operand("HFFFFFFFF", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 4294967295U); + parse_comp_operand("H123", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 0x123U); + parse_comp_operand("HABCD", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 0xABCDU); + parse_comp_operand("h123", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 0x123U); + parse_comp_operand("habcd", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 0xABCDU); + parse_comp_operand("HFFFFFFFF", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 4294967295U); /* '0x' is an address */ - parse_comp_operand("0x123", RC_OPERAND_ADDRESS, RC_OPERAND_16_BITS, 0x123U); + parse_comp_operand("0x123", RC_OPERAND_ADDRESS, RC_MEMSIZE_16_BITS, 0x123U); /* hex without prefix */ parse_error_operand("ABCD", 0); /* more than 32-bits (error), will be constrained to 32-bits */ - parse_comp_operand("4294967296", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 4294967295U); + parse_comp_operand("4294967296", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 4294967295U); /* negative value (error), will be "wrapped around": -1 = 0x100000000 - 1 = 0xFFFFFFFF = 4294967295 */ - parse_comp_operand("-1", RC_OPERAND_CONST, RC_OPERAND_8_BITS, 4294967295U); + parse_comp_operand("-1", RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 4294967295U); } { @@ -404,63 +404,63 @@ static void test_condition(void) { parse_comp_condition( "0xH1234=8", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "0xH1234==8", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "0xH1234!=8", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_NE, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "0xH1234<8", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_LT, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "0xH1234<=8", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_LE, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "0xH1234>8", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_GT, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "0xH1234>=8", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_GE, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); @@ -468,9 +468,9 @@ static void test_condition(void) { parse_comp_condition( "d0xH1234=8", RC_CONDITION_STANDARD, - RC_OPERAND_DELTA, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_DELTA, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); @@ -478,45 +478,45 @@ static void test_condition(void) { parse_comp_condition( "R:0xH1234=8", RC_CONDITION_RESET_IF, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "P:0xH1234=8", RC_CONDITION_PAUSE_IF, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "A:0xH1234=8", RC_CONDITION_ADD_SOURCE, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "B:0xH1234=8", RC_CONDITION_SUB_SOURCE, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); parse_comp_condition( "C:0xH1234=8", RC_CONDITION_ADD_HITS, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 0 ); @@ -524,27 +524,27 @@ static void test_condition(void) { parse_comp_condition( "0xH1234=8(1)", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 1 ); parse_comp_condition( "0xH1234=8.1.", /* legacy format */ RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 1 ); parse_comp_condition( "0xH1234=8(100)", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_CONST, RC_OPERAND_8_BITS, 8U, + RC_OPERAND_CONST, RC_MEMSIZE_8_BITS, 8U, 100 ); } @@ -558,9 +558,9 @@ static void test_condition(void) { parse_comp_condition( "0xH1234=0x80", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_8_BITS, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_8_BITS, 0x1234U, RC_CONDITION_EQ, - RC_OPERAND_ADDRESS, RC_OPERAND_16_BITS, 0x80U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_16_BITS, 0x80U, 0 ); } @@ -573,9 +573,9 @@ static void test_condition(void) { parse_comp_condition( "0xL1234!=0xU3456", RC_CONDITION_STANDARD, - RC_OPERAND_ADDRESS, RC_OPERAND_LOW, 0x1234U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_LOW, 0x1234U, RC_CONDITION_NE, - RC_OPERAND_ADDRESS, RC_OPERAND_HIGH, 0x3456U, + RC_OPERAND_ADDRESS, RC_MEMSIZE_HIGH, 0x3456U, 0 ); } @@ -1840,7 +1840,7 @@ static void parse_comp_term(const char* memaddr, char expected_var_size, unsigne assert(self.operand1.value == expected_address); assert(self.operand1.is_bcd == is_bcd); assert(self.invert == 0); - assert(self.operand2.size == RC_OPERAND_8_BITS); + assert(self.operand2.size == RC_MEMSIZE_8_BITS); assert(self.operand2.value == 0U); assert(!is_const || self.operand1.type == RC_OPERAND_CONST); } @@ -1897,26 +1897,26 @@ static void test_term(void) { ------------------------------------------------------------------------*/ /* sizes */ - parse_comp_term("0xH1234", RC_OPERAND_8_BITS, 0x1234U, 0, 0); - parse_comp_term("0x 1234", RC_OPERAND_16_BITS, 0x1234U, 0, 0); - parse_comp_term("0x1234", RC_OPERAND_16_BITS, 0x1234U, 0, 0); - parse_comp_term("0xW1234", RC_OPERAND_24_BITS, 0x1234U, 0, 0); - parse_comp_term("0xX1234", RC_OPERAND_32_BITS, 0x1234U, 0, 0); - parse_comp_term("0xL1234", RC_OPERAND_LOW, 0x1234U, 0, 0); - parse_comp_term("0xU1234", RC_OPERAND_HIGH, 0x1234U, 0, 0); - parse_comp_term("0xM1234", RC_OPERAND_BIT_0, 0x1234U, 0, 0); - parse_comp_term("0xN1234", RC_OPERAND_BIT_1, 0x1234U, 0, 0); - parse_comp_term("0xO1234", RC_OPERAND_BIT_2, 0x1234U, 0, 0); - parse_comp_term("0xP1234", RC_OPERAND_BIT_3, 0x1234U, 0, 0); - parse_comp_term("0xQ1234", RC_OPERAND_BIT_4, 0x1234U, 0, 0); - parse_comp_term("0xR1234", RC_OPERAND_BIT_5, 0x1234U, 0, 0); - parse_comp_term("0xS1234", RC_OPERAND_BIT_6, 0x1234U, 0, 0); - parse_comp_term("0xT1234", RC_OPERAND_BIT_7, 0x1234U, 0, 0); + parse_comp_term("0xH1234", RC_MEMSIZE_8_BITS, 0x1234U, 0, 0); + parse_comp_term("0x 1234", RC_MEMSIZE_16_BITS, 0x1234U, 0, 0); + parse_comp_term("0x1234", RC_MEMSIZE_16_BITS, 0x1234U, 0, 0); + parse_comp_term("0xW1234", RC_MEMSIZE_24_BITS, 0x1234U, 0, 0); + parse_comp_term("0xX1234", RC_MEMSIZE_32_BITS, 0x1234U, 0, 0); + parse_comp_term("0xL1234", RC_MEMSIZE_LOW, 0x1234U, 0, 0); + parse_comp_term("0xU1234", RC_MEMSIZE_HIGH, 0x1234U, 0, 0); + parse_comp_term("0xM1234", RC_MEMSIZE_BIT_0, 0x1234U, 0, 0); + parse_comp_term("0xN1234", RC_MEMSIZE_BIT_1, 0x1234U, 0, 0); + parse_comp_term("0xO1234", RC_MEMSIZE_BIT_2, 0x1234U, 0, 0); + parse_comp_term("0xP1234", RC_MEMSIZE_BIT_3, 0x1234U, 0, 0); + parse_comp_term("0xQ1234", RC_MEMSIZE_BIT_4, 0x1234U, 0, 0); + parse_comp_term("0xR1234", RC_MEMSIZE_BIT_5, 0x1234U, 0, 0); + parse_comp_term("0xS1234", RC_MEMSIZE_BIT_6, 0x1234U, 0, 0); + parse_comp_term("0xT1234", RC_MEMSIZE_BIT_7, 0x1234U, 0, 0); /* BCD */ - parse_comp_term("B0xH1234", RC_OPERAND_8_BITS, 0x1234U, 1, 0); - parse_comp_term("B0xX1234", RC_OPERAND_32_BITS, 0x1234U, 1, 0); - parse_comp_term("b0xH1234", RC_OPERAND_8_BITS, 0x1234U, 1, 0); + parse_comp_term("B0xH1234", RC_MEMSIZE_8_BITS, 0x1234U, 1, 0); + parse_comp_term("B0xX1234", RC_MEMSIZE_32_BITS, 0x1234U, 1, 0); + parse_comp_term("b0xH1234", RC_MEMSIZE_8_BITS, 0x1234U, 1, 0); /* Value */ parse_comp_term("V1234", 0, 1234, 0, 1); @@ -1930,12 +1930,12 @@ static void test_term(void) { TestClauseParseFromStringMultiply ------------------------------------------------------------------------*/ - parse_comp_term_fp("0xH1234", RC_OPERAND_8_BITS, 0x1234U, 1.0); - parse_comp_term_fp("0xH1234*1", RC_OPERAND_8_BITS, 0x1234U, 1.0); - parse_comp_term_fp("0xH1234*3", RC_OPERAND_8_BITS, 0x1234U, 3.0); - parse_comp_term_fp("0xH1234*0.5", RC_OPERAND_8_BITS, 0x1234U, 0.5); - parse_comp_term_fp("0xH1234*.5", RC_OPERAND_8_BITS, 0x1234U, 0.5); - parse_comp_term_fp("0xH1234*-1", RC_OPERAND_8_BITS, 0x1234U, -1.0); + parse_comp_term_fp("0xH1234", RC_MEMSIZE_8_BITS, 0x1234U, 1.0); + parse_comp_term_fp("0xH1234*1", RC_MEMSIZE_8_BITS, 0x1234U, 1.0); + parse_comp_term_fp("0xH1234*3", RC_MEMSIZE_8_BITS, 0x1234U, 3.0); + parse_comp_term_fp("0xH1234*0.5", RC_MEMSIZE_8_BITS, 0x1234U, 0.5); + parse_comp_term_fp("0xH1234*.5", RC_MEMSIZE_8_BITS, 0x1234U, 0.5); + parse_comp_term_fp("0xH1234*-1", RC_MEMSIZE_8_BITS, 0x1234U, -1.0); } { @@ -1943,10 +1943,10 @@ static void test_term(void) { TestClauseParseFromStringMultiplyAddress ------------------------------------------------------------------------*/ - parse_comp_term_mem("0xH1234", RC_OPERAND_8_BITS, 0x1234U, RC_OPERAND_8_BITS, 0U); - parse_comp_term_mem("0xH1234*0xH3456", RC_OPERAND_8_BITS, 0x1234U, RC_OPERAND_8_BITS, 0x3456U); - parse_comp_term_mem("0xH1234*0xL2222", RC_OPERAND_8_BITS, 0x1234U, RC_OPERAND_LOW, 0x2222U); - parse_comp_term_mem("0xH1234*0x1111", RC_OPERAND_8_BITS, 0x1234U, RC_OPERAND_16_BITS, 0x1111U); + parse_comp_term_mem("0xH1234", RC_MEMSIZE_8_BITS, 0x1234U, RC_MEMSIZE_8_BITS, 0U); + parse_comp_term_mem("0xH1234*0xH3456", RC_MEMSIZE_8_BITS, 0x1234U, RC_MEMSIZE_8_BITS, 0x3456U); + parse_comp_term_mem("0xH1234*0xL2222", RC_MEMSIZE_8_BITS, 0x1234U, RC_MEMSIZE_LOW, 0x2222U); + parse_comp_term_mem("0xH1234*0x1111", RC_MEMSIZE_8_BITS, 0x1234U, RC_MEMSIZE_16_BITS, 0x1111U); } { From 9757b4667a5f1da318691ac462a8cd067d96c8ac Mon Sep 17 00:00:00 2001 From: Jamiras Date: Wed, 12 Dec 2018 16:42:58 -0700 Subject: [PATCH 02/11] add rc_parse_state_t --- src/rcheevos/alloc.c | 18 ++- src/rcheevos/condition.c | 20 +-- src/rcheevos/condset.c | 10 +- src/rcheevos/expression.c | 8 +- src/rcheevos/internal.h | 36 +++-- src/rcheevos/lboard.c | 70 +++++----- src/rcheevos/operand.c | 30 ++-- src/rcheevos/richpresence.c | 102 +++++++------- src/rcheevos/term.c | 12 +- src/rcheevos/trigger.c | 36 ++--- src/rcheevos/value.c | 32 +++-- test/test.c | 267 ++++++++++++++++-------------------- 12 files changed, 325 insertions(+), 316 deletions(-) diff --git a/src/rcheevos/alloc.c b/src/rcheevos/alloc.c index 09da6e65..90cbca03 100644 --- a/src/rcheevos/alloc.c +++ b/src/rcheevos/alloc.c @@ -1,6 +1,6 @@ #include "internal.h" -#include +#include void* rc_alloc(void* pointer, int* offset, int size, int alignment, rc_scratch_t* scratch) { void* ptr; @@ -18,10 +18,10 @@ void* rc_alloc(void* pointer, int* offset, int size, int alignment, rc_scratch_t return ptr; } -char* rc_alloc_str(void* pointer, int* offset, const char* text, int length) { +char* rc_alloc_str(rc_parse_state_t* parse, const char* text, int length) { char* ptr; - ptr = (char*)rc_alloc(pointer, offset, length + 1, RC_ALIGNOF(char), 0); + ptr = (char*)rc_alloc(parse->buffer, &parse->offset, length + 1, RC_ALIGNOF(char), 0); if (ptr) { memcpy(ptr, text, length); ptr[length] = '\0'; @@ -29,3 +29,15 @@ char* rc_alloc_str(void* pointer, int* offset, const char* text, int length) { return ptr; } + +void rc_init_parse_state(rc_parse_state_t* parse, void* buffer, lua_State* L, int funcs_ndx) +{ + parse->offset = 0; + parse->L = L; + parse->funcs_ndx = funcs_ndx; + parse->buffer = buffer; +} + +void rc_destroy_parse_state(rc_parse_state_t* parse) +{ +} \ No newline at end of file diff --git a/src/rcheevos/condition.c b/src/rcheevos/condition.c index d97cb9db..efd172a6 100644 --- a/src/rcheevos/condition.c +++ b/src/rcheevos/condition.c @@ -2,13 +2,13 @@ #include -rc_condition_t* rc_parse_condition(int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx) { +rc_condition_t* rc_parse_condition(const char** memaddr, rc_parse_state_t* parse) { rc_condition_t* self; const char* aux; int ret2; aux = *memaddr; - self = RC_ALLOC(rc_condition_t, buffer, ret, scratch); + self = RC_ALLOC(rc_condition_t, parse); self->current_hits = 0; if (*aux != 0 && aux[1] == ':') { @@ -19,7 +19,7 @@ rc_condition_t* rc_parse_condition(int* ret, void* buffer, rc_scratch_t* scratch case 'b': case 'B': self->type = RC_CONDITION_SUB_SOURCE; break; case 'c': case 'C': self->type = RC_CONDITION_ADD_HITS; break; case 'n': case 'N': self->type = RC_CONDITION_AND_NEXT; break; - default: *ret = RC_INVALID_CONDITION_TYPE; return 0; + default: parse->offset = RC_INVALID_CONDITION_TYPE; return 0; } aux += 2; @@ -28,10 +28,10 @@ rc_condition_t* rc_parse_condition(int* ret, void* buffer, rc_scratch_t* scratch self->type = RC_CONDITION_STANDARD; } - ret2 = rc_parse_operand(&self->operand1, &aux, 1, L, funcs_ndx); + ret2 = rc_parse_operand(&self->operand1, &aux, 1, parse); if (ret2 < 0) { - *ret = ret2; + parse->offset = ret2; return 0; } @@ -45,7 +45,7 @@ rc_condition_t* rc_parse_condition(int* ret, void* buffer, rc_scratch_t* scratch if (*aux++ != '=') { /* fall through */ default: - *ret = RC_INVALID_OPERATOR; + parse->offset = RC_INVALID_OPERATOR; return 0; } @@ -73,10 +73,10 @@ rc_condition_t* rc_parse_condition(int* ret, void* buffer, rc_scratch_t* scratch break; } - ret2 = rc_parse_operand(&self->operand2, &aux, 1, L, funcs_ndx); + ret2 = rc_parse_operand(&self->operand2, &aux, 1, parse); if (ret2 < 0) { - *ret = ret2; + parse->offset = ret2; return 0; } @@ -85,7 +85,7 @@ rc_condition_t* rc_parse_condition(int* ret, void* buffer, rc_scratch_t* scratch self->required_hits = (unsigned)strtoul(++aux, &end, 10); if (end == aux || *end != ')') { - *ret = RC_INVALID_REQUIRED_HITS; + parse->offset = RC_INVALID_REQUIRED_HITS; return 0; } @@ -96,7 +96,7 @@ rc_condition_t* rc_parse_condition(int* ret, void* buffer, rc_scratch_t* scratch self->required_hits = (unsigned)strtoul(++aux, &end, 10); if (end == aux || *end != '.') { - *ret = RC_INVALID_REQUIRED_HITS; + parse->offset = RC_INVALID_REQUIRED_HITS; return 0; } diff --git a/src/rcheevos/condset.c b/src/rcheevos/condset.c index 13d086f9..e5eafc1f 100644 --- a/src/rcheevos/condset.c +++ b/src/rcheevos/condset.c @@ -23,19 +23,19 @@ static void rc_update_condition_pause(rc_condition_t* condition, int* in_pause) } } -rc_condset_t* rc_parse_condset(int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx) { +rc_condset_t* rc_parse_condset(const char** memaddr, rc_parse_state_t* parse) { rc_condset_t* self; rc_condition_t** next; int in_pause; - self = RC_ALLOC(rc_condset_t, buffer, ret, scratch); + self = RC_ALLOC(rc_condset_t, parse); self->has_pause = 0; next = &self->conditions; for (;;) { - *next = rc_parse_condition(ret, buffer, scratch, memaddr, L, funcs_ndx); + *next = rc_parse_condition(memaddr, parse); - if (*ret < 0) { + if (parse->offset < 0) { return 0; } @@ -52,7 +52,7 @@ rc_condset_t* rc_parse_condset(int* ret, void* buffer, rc_scratch_t* scratch, co *next = 0; - if (buffer != 0) { + if (parse->buffer != 0) { in_pause = 0; rc_update_condition_pause(self->conditions, &in_pause); } diff --git a/src/rcheevos/expression.c b/src/rcheevos/expression.c index 87e45874..f2fca1e8 100644 --- a/src/rcheevos/expression.c +++ b/src/rcheevos/expression.c @@ -1,16 +1,16 @@ #include "internal.h" -rc_expression_t* rc_parse_expression(int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx) { +rc_expression_t* rc_parse_expression(const char** memaddr, rc_parse_state_t* parse) { rc_expression_t* self; rc_term_t** next; - self = RC_ALLOC(rc_expression_t, buffer, ret, scratch); + self = RC_ALLOC(rc_expression_t, parse); next = &self->terms; for (;;) { - *next = rc_parse_term(ret, buffer, scratch, memaddr, L, funcs_ndx); + *next = rc_parse_term(memaddr, parse); - if (*ret < 0) { + if (parse->offset < 0) { return 0; } diff --git a/src/rcheevos/internal.h b/src/rcheevos/internal.h index 5968aafe..8145f40d 100644 --- a/src/rcheevos/internal.h +++ b/src/rcheevos/internal.h @@ -8,7 +8,7 @@ #define RC_OFFSETOF(s, f) ((int)(long long)(&((s*)0)->f)) #define RC_ALIGNOF(t) RC_OFFSETOF(struct RC_TAG(_unnamed, __LINE__) {char c; t d;}, d) -#define RC_ALLOC(t, p, o, s) ((t*)rc_alloc(p, o, sizeof(t), RC_ALIGNOF(t), s)) +#define RC_ALLOC(t, p) ((t*)rc_alloc((p)->buffer, &(p)->offset, sizeof(t), RC_ALIGNOF(t), &(p)->scratch)) typedef union { rc_operand_t operand; @@ -26,32 +26,46 @@ typedef union { } rc_scratch_t; +typedef struct { + int offset; + + lua_State* L; + int funcs_ndx; + + void* buffer; + rc_scratch_t scratch; +} +rc_parse_state_t; + +void rc_init_parse_state(rc_parse_state_t* parse, void* buffer, lua_State* L, int funcs_ndx); +void rc_destroy_parse_state(rc_parse_state_t* parse); + void* rc_alloc(void* pointer, int* offset, int size, int alignment, rc_scratch_t* scratch); -char* rc_alloc_str(void* pointer, int* offset, const char* text, int length); +char* rc_alloc_str(rc_parse_state_t* parse, const char* text, int length); -void rc_parse_trigger_internal(rc_trigger_t* self, int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx); +void rc_parse_trigger_internal(rc_trigger_t* self, const char** memaddr, rc_parse_state_t* parse); -rc_condset_t* rc_parse_condset(int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx); +rc_condset_t* rc_parse_condset(const char** memaddr, rc_parse_state_t* parse); int rc_test_condset(rc_condset_t* self, int* reset, rc_peek_t peek, void* ud, lua_State* L); void rc_reset_condset(rc_condset_t* self); -rc_condition_t* rc_parse_condition(int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx); +rc_condition_t* rc_parse_condition(const char** memaddr, rc_parse_state_t* parse); int rc_test_condition(rc_condition_t* self, unsigned add_buffer, rc_peek_t peek, void* ud, lua_State* L); -int rc_parse_operand(rc_operand_t* self, const char** memaddr, int is_trigger, lua_State* L, int funcs_ndx); +int rc_parse_operand(rc_operand_t* self, const char** memaddr, int is_trigger, rc_parse_state_t* parse); unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_State* L); -rc_term_t* rc_parse_term(int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx); +rc_term_t* rc_parse_term(const char** memaddr, rc_parse_state_t* parse); unsigned rc_evaluate_term(rc_term_t* self, rc_peek_t peek, void* ud, lua_State* L); -rc_expression_t* rc_parse_expression(int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx); +rc_expression_t* rc_parse_expression(const char** memaddr, rc_parse_state_t* parse); unsigned rc_evaluate_expression(rc_expression_t* self, rc_peek_t peek, void* ud, lua_State* L); -void rc_parse_value_internal(rc_value_t* self, int* ret, void* buffer, void* scratch, const char** memaddr, lua_State* L, int funcs_ndx); +void rc_parse_value_internal(rc_value_t* self, const char** memaddr, rc_parse_state_t* parse); -void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* scratch, const char* memaddr, lua_State* L, int funcs_ndx); +void rc_parse_lboard_internal(rc_lboard_t* self, const char* memaddr, rc_parse_state_t* parse); const char* rc_parse_line(const char* line, const char** end); -void rc_parse_richpresence_internal(rc_richpresence_t* self, int* ret, void* buffer, void* scratch, const char* script, lua_State* L, int funcs_ndx); +void rc_parse_richpresence_internal(rc_richpresence_t* self, const char* script, rc_parse_state_t* parse); #endif /* INTERNAL_H */ diff --git a/src/rcheevos/lboard.c b/src/rcheevos/lboard.c index 56b216cd..6dc523ad 100644 --- a/src/rcheevos/lboard.c +++ b/src/rcheevos/lboard.c @@ -9,7 +9,7 @@ enum { RC_LBOARD_COMPLETE = RC_LBOARD_START | RC_LBOARD_CANCEL | RC_LBOARD_SUBMIT | RC_LBOARD_VALUE }; -void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* scratch, const char* memaddr, lua_State* L, int funcs_ndx) { +void rc_parse_lboard_internal(rc_lboard_t* self, const char* memaddr, rc_parse_state_t* parse) { int found; self->progress = 0; @@ -21,15 +21,15 @@ void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* s (memaddr[1] == 't' || memaddr[1] == 'T') && (memaddr[2] == 'a' || memaddr[2] == 'A') && memaddr[3] == ':') { if ((found & RC_LBOARD_START) != 0) { - *ret = RC_DUPLICATED_START; + parse->offset = RC_DUPLICATED_START; return; } found |= RC_LBOARD_START; memaddr += 4; - rc_parse_trigger_internal(&self->start, ret, buffer, scratch, &memaddr, L, funcs_ndx); + rc_parse_trigger_internal(&self->start, &memaddr, parse); - if (*ret < 0) { + if (parse->offset < 0) { return; } } @@ -37,15 +37,15 @@ void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* s (memaddr[1] == 'a' || memaddr[1] == 'A') && (memaddr[2] == 'n' || memaddr[2] == 'N') && memaddr[3] == ':') { if ((found & RC_LBOARD_CANCEL) != 0) { - *ret = RC_DUPLICATED_CANCEL; + parse->offset = RC_DUPLICATED_CANCEL; return; } found |= RC_LBOARD_CANCEL; memaddr += 4; - rc_parse_trigger_internal(&self->cancel, ret, buffer, scratch, &memaddr, L, funcs_ndx); + rc_parse_trigger_internal(&self->cancel, &memaddr, parse); - if (*ret < 0) { + if (parse->offset < 0) { return; } } @@ -53,15 +53,15 @@ void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* s (memaddr[1] == 'u' || memaddr[1] == 'U') && (memaddr[2] == 'b' || memaddr[2] == 'B') && memaddr[3] == ':') { if ((found & RC_LBOARD_SUBMIT) != 0) { - *ret = RC_DUPLICATED_SUBMIT; + parse->offset = RC_DUPLICATED_SUBMIT; return; } found |= RC_LBOARD_SUBMIT; memaddr += 4; - rc_parse_trigger_internal(&self->submit, ret, buffer, scratch, &memaddr, L, funcs_ndx); + rc_parse_trigger_internal(&self->submit, &memaddr, parse); - if (*ret < 0) { + if (parse->offset < 0) { return; } } @@ -69,15 +69,15 @@ void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* s (memaddr[1] == 'a' || memaddr[1] == 'A') && (memaddr[2] == 'l' || memaddr[2] == 'L') && memaddr[3] == ':') { if ((found & RC_LBOARD_VALUE) != 0) { - *ret = RC_DUPLICATED_VALUE; + parse->offset = RC_DUPLICATED_VALUE; return; } found |= RC_LBOARD_VALUE; memaddr += 4; - rc_parse_value_internal(&self->value, ret, buffer, scratch, &memaddr, L, funcs_ndx); + rc_parse_value_internal(&self->value, &memaddr, parse); - if (*ret < 0) { + if (parse->offset < 0) { return; } } @@ -85,22 +85,22 @@ void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* s (memaddr[1] == 'r' || memaddr[1] == 'R') && (memaddr[2] == 'o' || memaddr[2] == 'O') && memaddr[3] == ':') { if ((found & RC_LBOARD_PROGRESS) != 0) { - *ret = RC_DUPLICATED_PROGRESS; + parse->offset = RC_DUPLICATED_PROGRESS; return; } found |= RC_LBOARD_PROGRESS; memaddr += 4; - self->progress = RC_ALLOC(rc_value_t, buffer, ret, scratch); - rc_parse_value_internal(self->progress, ret, buffer, scratch, &memaddr, L, funcs_ndx); + self->progress = RC_ALLOC(rc_value_t, parse); + rc_parse_value_internal(self->progress, &memaddr, parse); - if (*ret < 0) { + if (parse->offset < 0) { return; } } else { - *ret = RC_INVALID_LBOARD_FIELD; + parse->offset = RC_INVALID_LBOARD_FIELD; return; } @@ -113,16 +113,16 @@ void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* s if ((found & RC_LBOARD_COMPLETE) != RC_LBOARD_COMPLETE) { if ((found & RC_LBOARD_START) == 0) { - *ret = RC_MISSING_START; + parse->offset = RC_MISSING_START; } else if ((found & RC_LBOARD_CANCEL) == 0) { - *ret = RC_MISSING_CANCEL; + parse->offset = RC_MISSING_CANCEL; } else if ((found & RC_LBOARD_SUBMIT) == 0) { - *ret = RC_MISSING_SUBMIT; + parse->offset = RC_MISSING_SUBMIT; } else if ((found & RC_LBOARD_VALUE) == 0) { - *ret = RC_MISSING_VALUE; + parse->offset = RC_MISSING_VALUE; } return; @@ -132,25 +132,27 @@ void rc_parse_lboard_internal(rc_lboard_t* self, int* ret, void* buffer, void* s } int rc_lboard_size(const char* memaddr) { - int ret; rc_lboard_t* self; - rc_scratch_t scratch; + rc_parse_state_t parse; + rc_init_parse_state(&parse, 0, 0, 0); - ret = 0; - self = RC_ALLOC(rc_lboard_t, 0, &ret, &scratch); - rc_parse_lboard_internal(self, &ret, 0, &scratch, memaddr, 0, 0); - return ret; + self = RC_ALLOC(rc_lboard_t, &parse); + rc_parse_lboard_internal(self, memaddr, &parse); + + rc_destroy_parse_state(&parse); + return parse.offset; } rc_lboard_t* rc_parse_lboard(void* buffer, const char* memaddr, lua_State* L, int funcs_ndx) { - int ret; rc_lboard_t* self; - rc_scratch_t scratch; + rc_parse_state_t parse; + rc_init_parse_state(&parse, buffer, L, funcs_ndx); - ret = 0; - self = RC_ALLOC(rc_lboard_t, buffer, &ret, &scratch); - rc_parse_lboard_internal(self, &ret, buffer, 0, memaddr, L, funcs_ndx); - return ret >= 0 ? self : 0; + self = RC_ALLOC(rc_lboard_t, &parse); + rc_parse_lboard_internal(self, memaddr, &parse); + + rc_destroy_parse_state(&parse); + return parse.offset >= 0 ? self : 0; } int rc_evaluate_lboard(rc_lboard_t* self, unsigned* value, rc_peek_t peek, void* peek_ud, lua_State* L) { diff --git a/src/rcheevos/operand.c b/src/rcheevos/operand.c index 1d5df49a..61ab1770 100644 --- a/src/rcheevos/operand.c +++ b/src/rcheevos/operand.c @@ -18,7 +18,7 @@ extern "C" { #endif /* RC_DISABLE_LUA */ -static int rc_parse_operand_lua(rc_operand_t* self, const char** memaddr, lua_State* L, int funcs_ndx) { +static int rc_parse_operand_lua(rc_operand_t* self, const char** memaddr, rc_parse_state_t* parse) { const char* aux = *memaddr; const char* id; @@ -38,20 +38,20 @@ static int rc_parse_operand_lua(rc_operand_t* self, const char** memaddr, lua_St #ifndef RC_DISABLE_LUA - if (L != 0) { - if (!lua_istable(L, funcs_ndx)) { + if (parse->L != 0) { + if (!lua_istable(parse->L, parse->funcs_ndx)) { return RC_INVALID_LUA_OPERAND; } - lua_pushlstring(L, id, aux - id); - lua_gettable(L, funcs_ndx); + lua_pushlstring(parse->L, id, aux - id); + lua_gettable(parse->L, parse->funcs_ndx); - if (!lua_isfunction(L, -1)) { - lua_pop(L, 1); + if (!lua_isfunction(parse->L, -1)) { + lua_pop(parse->L, 1); return RC_INVALID_LUA_OPERAND; } - self->function_ref = luaL_ref(L, LUA_REGISTRYINDEX); + self->function_ref = luaL_ref(parse->L, LUA_REGISTRYINDEX); } #endif /* RC_DISABLE_LUA */ @@ -134,7 +134,7 @@ static int rc_parse_operand_memory(rc_operand_t* self, const char** memaddr) { return RC_OK; } -static int rc_parse_operand_trigger(rc_operand_t* self, const char** memaddr, lua_State* L, int funcs_ndx) { +static int rc_parse_operand_trigger(rc_operand_t* self, const char** memaddr, rc_parse_state_t* parse) { const char* aux = *memaddr; char* end; int ret; @@ -192,7 +192,7 @@ static int rc_parse_operand_trigger(rc_operand_t* self, const char** memaddr, lu break; case '@': - ret = rc_parse_operand_lua(self, &aux, L, funcs_ndx); + ret = rc_parse_operand_lua(self, &aux, parse); if (ret < 0) { return ret; @@ -205,7 +205,7 @@ static int rc_parse_operand_trigger(rc_operand_t* self, const char** memaddr, lu return RC_OK; } -static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, lua_State* L, int funcs_ndx) { +static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, rc_parse_state_t* parse) { const char* aux = *memaddr; char* end; int ret; @@ -275,7 +275,7 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, lua_S break; case '@': - ret = rc_parse_operand_lua(self, &aux, L, funcs_ndx); + ret = rc_parse_operand_lua(self, &aux, parse); if (ret < 0) { return ret; @@ -288,17 +288,17 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, lua_S return RC_OK; } -int rc_parse_operand(rc_operand_t* self, const char** memaddr, int is_trigger, lua_State* L, int funcs_ndx) { +int rc_parse_operand(rc_operand_t* self, const char** memaddr, int is_trigger, rc_parse_state_t* parse) { self->size = RC_MEMSIZE_8_BITS; self->is_bcd = 0; self->previous = 0; self->prior = 0; if (is_trigger) { - return rc_parse_operand_trigger(self, memaddr, L, funcs_ndx); + return rc_parse_operand_trigger(self, memaddr, parse); } else { - return rc_parse_operand_term(self, memaddr, L, funcs_ndx); + return rc_parse_operand_term(self, memaddr, parse); } } diff --git a/src/rcheevos/richpresence.c b/src/rcheevos/richpresence.c index 910e66af..a8157d12 100644 --- a/src/rcheevos/richpresence.c +++ b/src/rcheevos/richpresence.c @@ -11,7 +11,7 @@ enum { RC_FORMAT_LOOKUP = 102 }; -const char* rc_parse_line(const char* line, const char** end) { +static const char* rc_parse_line(const char* line, const char** end) { const char* nextline; const char* endline; @@ -42,7 +42,7 @@ const char* rc_parse_line(const char* line, const char** end) { return nextline; } -rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, int* ret, rc_scratch_t* scratch, const char* line, const char* endline, lua_State* L, int funcs_ndx, rc_richpresence_t* richpresence) { +static rc_richpresence_display_t* rc_parse_richpresence_display_internal(const char* line, const char* endline, rc_parse_state_t* parse, rc_richpresence_t* richpresence) { rc_richpresence_display_t* self; rc_richpresence_display_part_t* part; rc_richpresence_display_part_t** next; @@ -55,7 +55,7 @@ rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, return 0; { - self = RC_ALLOC(rc_richpresence_display_t, buffer, ret, scratch); + self = RC_ALLOC(rc_richpresence_display_t, parse); memset(self, 0, sizeof(rc_richpresence_display_t)); next = &self->display; } @@ -71,14 +71,14 @@ rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, } if (ptr > line) { - part = RC_ALLOC(rc_richpresence_display_part_t, buffer, ret, scratch); + part = RC_ALLOC(rc_richpresence_display_part_t, parse); memset(part, 0, sizeof(rc_richpresence_display_part_t)); *next = part; next = &part->next; /* handle string part */ part->display_type = RC_FORMAT_STRING; - part->text = rc_alloc_str(buffer, ret, line, ptr - line); + part->text = rc_alloc_str(parse, line, ptr - line); if (part->text) { /* remove backslashes used for escaping */ in = part->text; @@ -104,16 +104,16 @@ rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, ++ptr; if (ptr > line) { - if (!buffer) { + if (!parse->buffer) { /* just calculating size, can't confirm lookup exists */ - part = RC_ALLOC(rc_richpresence_display_part_t, buffer, ret, scratch); + part = RC_ALLOC(rc_richpresence_display_part_t, parse); line = ++ptr; while (ptr < endline && *ptr != ')') ++ptr; if (*ptr == ')') { - rc_parse_value_internal(&part->value, ret, buffer, scratch, &line, L, funcs_ndx); - if (ret < 0) + rc_parse_value_internal(&part->value, &line, parse); + if (parse->offset < 0) return 0; ++ptr; } @@ -123,7 +123,7 @@ rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, lookup = richpresence->first_lookup; while (lookup) { if (strncmp(lookup->name, line, ptr - line) == 0 && lookup->name[ptr - line] == '\0') { - part = RC_ALLOC(rc_richpresence_display_part_t, buffer, ret, scratch); + part = RC_ALLOC(rc_richpresence_display_part_t, parse); *next = part; next = &part->next; @@ -135,8 +135,8 @@ rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, while (ptr < endline && *ptr != ')') ++ptr; if (*ptr == ')') { - rc_parse_value_internal(&part->value, ret, buffer, scratch, &line, L, funcs_ndx); - if (ret < 0) + rc_parse_value_internal(&part->value, &line, parse); + if (parse->offset < 0) return 0; ++ptr; } @@ -148,7 +148,7 @@ rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, } if (!lookup) { - part = RC_ALLOC(rc_richpresence_display_part_t, buffer, ret, scratch); + part = RC_ALLOC(rc_richpresence_display_part_t, parse); memset(part, 0, sizeof(rc_richpresence_display_part_t)); *next = part; next = &part->next; @@ -156,7 +156,7 @@ rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, ptr = line; part->display_type = RC_FORMAT_STRING; - part->text = rc_alloc_str(buffer, ret, "[Unknown macro]", 15); + part->text = rc_alloc_str(parse, "[Unknown macro]", 15); } } } @@ -170,7 +170,7 @@ rc_richpresence_display_t* rc_parse_richpresence_display_internal(void* buffer, return self; } -const char* rc_parse_richpresence_lookup(rc_richpresence_lookup_t* lookup, const char* nextline, int* ret, void* buffer, void* scratch, lua_State* L, int funcs_ndx) +static const char* rc_parse_richpresence_lookup(rc_richpresence_lookup_t* lookup, const char* nextline, rc_parse_state_t* parse) { rc_richpresence_lookup_item_t** next; rc_richpresence_lookup_item_t* item; @@ -202,7 +202,7 @@ const char* rc_parse_richpresence_lookup(rc_richpresence_lookup_t* lookup, const line += chars + 1; if (chars == 1 && number[0] == '*') { - defaultlabel = rc_alloc_str(buffer, ret, line, endline - line); + defaultlabel = rc_alloc_str(parse, line, endline - line); continue; } @@ -211,18 +211,18 @@ const char* rc_parse_richpresence_lookup(rc_richpresence_lookup_t* lookup, const else key = strtoul(&number[0], 0, 10); - item = RC_ALLOC(rc_richpresence_lookup_item_t, buffer, ret, scratch); + item = RC_ALLOC(rc_richpresence_lookup_item_t, parse); item->value = key; - item->label = rc_alloc_str(buffer, ret, line, endline - line); + item->label = rc_alloc_str(parse, line, endline - line); *next = item; next = &item->next_item; } } while (1); if (!defaultlabel) - defaultlabel = rc_alloc_str(buffer, ret, "", 0); + defaultlabel = rc_alloc_str(parse, "", 0); - item = RC_ALLOC(rc_richpresence_lookup_item_t, buffer, ret, scratch); + item = RC_ALLOC(rc_richpresence_lookup_item_t, parse); item->value = 0; item->label = defaultlabel; item->next_item = 0; @@ -231,10 +231,11 @@ const char* rc_parse_richpresence_lookup(rc_richpresence_lookup_t* lookup, const return nextline; } -void rc_parse_richpresence_internal(rc_richpresence_t* self, int* ret, void* buffer, void* scratch, const char* script, lua_State* L, int funcs_ndx) { +void rc_parse_richpresence_internal(rc_richpresence_t* self, const char* script, rc_parse_state_t* parse) { rc_richpresence_display_t** nextdisplay; rc_richpresence_lookup_t** nextlookup; rc_richpresence_lookup_t* lookup; + rc_trigger_t* trigger; char format[64]; const char* display = 0; const char* line; @@ -254,26 +255,26 @@ void rc_parse_richpresence_internal(rc_richpresence_t* self, int* ret, void* buf if (strncmp(line, "Lookup:", 7) == 0) { line += 7; - lookup = RC_ALLOC(rc_richpresence_lookup_t, buffer, ret, scratch); - lookup->name = rc_alloc_str(buffer, ret, line, endline - line); + lookup = RC_ALLOC(rc_richpresence_lookup_t, parse); + lookup->name = rc_alloc_str(parse, line, endline - line); lookup->format = RC_FORMAT_LOOKUP; *nextlookup = lookup; nextlookup = &lookup->next; - nextline = rc_parse_richpresence_lookup(lookup, nextline, ret, buffer, scratch, L, funcs_ndx); + nextline = rc_parse_richpresence_lookup(lookup, nextline, parse); } else if (strncmp(line, "Format:", 7) == 0) { line += 7; - lookup = RC_ALLOC(rc_richpresence_lookup_t, buffer, ret, scratch); - lookup->name = rc_alloc_str(buffer, ret, line, endline - line); + lookup = RC_ALLOC(rc_richpresence_lookup_t, parse); + lookup->name = rc_alloc_str(parse, line, endline - line); lookup->first_item = 0; *nextlookup = lookup; nextlookup = &lookup->next; line = nextline; nextline = rc_parse_line(line, &endline); - if (buffer && strncmp(line, "FormatType=", 11) == 0) { + if (parse->buffer && strncmp(line, "FormatType=", 11) == 0) { line += 11; chars = endline - line; @@ -313,11 +314,12 @@ void rc_parse_richpresence_internal(rc_richpresence_t* self, int* ret, void* buf ++ptr; if (ptr < endline) { - *nextdisplay = rc_parse_richpresence_display_internal(buffer, ret, scratch, ptr + 1, endline, L, funcs_ndx, self); - rc_parse_trigger_internal(&((*nextdisplay)->trigger), ret, buffer, scratch, &line, L, funcs_ndx); - if (*ret < 0) + *nextdisplay = rc_parse_richpresence_display_internal(ptr + 1, endline, parse, self); + trigger = &((*nextdisplay)->trigger); + rc_parse_trigger_internal(trigger, &line, parse); + if (parse->offset < 0) return; - if (buffer) + if (parse->buffer) nextdisplay = &((*nextdisplay)->next); } @@ -326,39 +328,41 @@ void rc_parse_richpresence_internal(rc_richpresence_t* self, int* ret, void* buf } /* non-conditional display: string */ - *nextdisplay = rc_parse_richpresence_display_internal(buffer, ret, scratch, line, endline, L, funcs_ndx, self); - hasdisplay = (*nextdisplay != NULL); - if (buffer) + *nextdisplay = rc_parse_richpresence_display_internal(line, endline, parse, self); + if (*nextdisplay) { + hasdisplay = 1; nextdisplay = &((*nextdisplay)->next); + } } /* finalize */ *nextdisplay = 0; - if (!hasdisplay && ret > 0) - *ret = RC_MISSING_DISPLAY_STRING; + if (!hasdisplay && parse->offset > 0) { + parse->offset = RC_MISSING_DISPLAY_STRING; + } } int rc_richpresence_size(const char* script) { - int ret; rc_richpresence_t* self; - rc_scratch_t scratch; - - ret = 0; - self = RC_ALLOC(rc_richpresence_t, 0, &ret, &scratch); - rc_parse_richpresence_internal(self, &ret, 0, &scratch, script, 0, 0); - return ret; + rc_parse_state_t parse; + rc_init_parse_state(&parse, 0, 0, 0); + + self = RC_ALLOC(rc_richpresence_t, &parse); + rc_parse_richpresence_internal(self, script, &parse); + + rc_destroy_parse_state(&parse); + return parse.offset; } rc_richpresence_t* rc_parse_richpresence(void* buffer, const char* script, lua_State* L, int funcs_ndx) { - int ret; rc_richpresence_t* self; - rc_scratch_t scratch; + rc_parse_state_t parse; + rc_init_parse_state(&parse, buffer, L, funcs_ndx); - ret = 0; - self = RC_ALLOC(rc_richpresence_t, buffer, &ret, &scratch); - rc_parse_richpresence_internal(self, &ret, buffer, 0, script, L, funcs_ndx); - return ret >= 0 ? self : 0; + self = RC_ALLOC(rc_richpresence_t, &parse); + rc_parse_richpresence_internal(self, script, &parse); + return parse.offset >= 0 ? self : 0; } int rc_evaluate_richpresence(rc_richpresence_t* richpresence, char* buffer, unsigned buffersize, rc_peek_t peek, void* peek_ud, lua_State* L) { diff --git a/src/rcheevos/term.c b/src/rcheevos/term.c index 767976a8..138a8a19 100644 --- a/src/rcheevos/term.c +++ b/src/rcheevos/term.c @@ -1,18 +1,18 @@ #include "internal.h" -rc_term_t* rc_parse_term(int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx) { +rc_term_t* rc_parse_term(const char** memaddr, rc_parse_state_t* parse) { rc_term_t* self; const char* aux; int ret2; aux = *memaddr; - self = RC_ALLOC(rc_term_t, buffer, ret, scratch); + self = RC_ALLOC(rc_term_t, parse); self->invert = 0; - ret2 = rc_parse_operand(&self->operand1, &aux, 0, L, funcs_ndx); + ret2 = rc_parse_operand(&self->operand1, &aux, 0, parse); if (ret2 < 0) { - *ret = ret2; + parse->offset = ret2; return 0; } @@ -24,10 +24,10 @@ rc_term_t* rc_parse_term(int* ret, void* buffer, rc_scratch_t* scratch, const ch self->invert = 1; } - ret2 = rc_parse_operand(&self->operand2, &aux, 0, L, funcs_ndx); + ret2 = rc_parse_operand(&self->operand2, &aux, 0, parse); if (ret2 < 0) { - *ret = ret2; + parse->offset = ret2; return 0; } diff --git a/src/rcheevos/trigger.c b/src/rcheevos/trigger.c index 77113938..28723bc6 100644 --- a/src/rcheevos/trigger.c +++ b/src/rcheevos/trigger.c @@ -2,7 +2,7 @@ #include -void rc_parse_trigger_internal(rc_trigger_t* self, int* ret, void* buffer, rc_scratch_t* scratch, const char** memaddr, lua_State* L, int funcs_ndx) { +void rc_parse_trigger_internal(rc_trigger_t* self, const char** memaddr, rc_parse_state_t* parse) { rc_condset_t** next; const char* aux; @@ -13,9 +13,9 @@ void rc_parse_trigger_internal(rc_trigger_t* self, int* ret, void* buffer, rc_sc self->requirement = 0; } else { - self->requirement = rc_parse_condset(ret, buffer, scratch, &aux, L, funcs_ndx); + self->requirement = rc_parse_condset(&aux, parse); - if (*ret < 0) { + if (parse->offset < 0) { return; } @@ -24,9 +24,9 @@ void rc_parse_trigger_internal(rc_trigger_t* self, int* ret, void* buffer, rc_sc while (*aux == 's' || *aux == 'S') { aux++; - *next = rc_parse_condset(ret, buffer, scratch, &aux, L, funcs_ndx); + *next = rc_parse_condset(&aux, parse); - if (*ret < 0) { + if (parse->offset < 0) { return; } @@ -38,25 +38,27 @@ void rc_parse_trigger_internal(rc_trigger_t* self, int* ret, void* buffer, rc_sc } int rc_trigger_size(const char* memaddr) { - int ret; rc_trigger_t* self; - rc_scratch_t scratch; + rc_parse_state_t parse; + rc_init_parse_state(&parse, 0, 0, 0); - ret = 0; - self = RC_ALLOC(rc_trigger_t, 0, &ret, &scratch); - rc_parse_trigger_internal(self, &ret, 0, &scratch, &memaddr, 0, 0); - return ret; + self = RC_ALLOC(rc_trigger_t, &parse); + rc_parse_trigger_internal(self, &memaddr, &parse); + + rc_destroy_parse_state(&parse); + return parse.offset; } rc_trigger_t* rc_parse_trigger(void* buffer, const char* memaddr, lua_State* L, int funcs_ndx) { - int ret; rc_trigger_t* self; - rc_scratch_t scratch; + rc_parse_state_t parse; + rc_init_parse_state(&parse, buffer, L, funcs_ndx); - ret = 0; - self = RC_ALLOC(rc_trigger_t, buffer, &ret, &scratch); - rc_parse_trigger_internal(self, &ret, buffer, 0, &memaddr, L, funcs_ndx); - return ret >= 0 ? self : 0; + self = RC_ALLOC(rc_trigger_t, &parse); + rc_parse_trigger_internal(self, &memaddr, &parse); + + rc_destroy_parse_state(&parse); + return parse.offset >= 0 ? self : 0; } int rc_test_trigger(rc_trigger_t* self, rc_peek_t peek, void* ud, lua_State* L) { diff --git a/src/rcheevos/value.c b/src/rcheevos/value.c index 538088c6..412017ea 100644 --- a/src/rcheevos/value.c +++ b/src/rcheevos/value.c @@ -1,14 +1,14 @@ #include "internal.h" -void rc_parse_value_internal(rc_value_t* self, int* ret, void* buffer, void* scratch, const char** memaddr, lua_State* L, int funcs_ndx) { +void rc_parse_value_internal(rc_value_t* self, const char** memaddr, rc_parse_state_t* parse) { rc_expression_t** next; next = &self->expressions; for (;;) { - *next = rc_parse_expression(ret, buffer, scratch, memaddr, L, funcs_ndx); + *next = rc_parse_expression(memaddr, parse); - if (*ret < 0) { + if (parse->offset < 0) { return; } @@ -25,25 +25,27 @@ void rc_parse_value_internal(rc_value_t* self, int* ret, void* buffer, void* scr } int rc_value_size(const char* memaddr) { - int ret; rc_value_t* self; - rc_scratch_t scratch; + rc_parse_state_t parse; + rc_init_parse_state(&parse, 0, 0, 0); - ret = 0; - self = RC_ALLOC(rc_value_t, 0, &ret, &scratch); - rc_parse_value_internal(self, &ret, 0, &scratch, &memaddr, 0, 0); - return ret; + self = RC_ALLOC(rc_value_t, &parse); + rc_parse_value_internal(self, &memaddr, &parse); + + rc_destroy_parse_state(&parse); + return parse.offset; } rc_value_t* rc_parse_value(void* buffer, const char* memaddr, lua_State* L, int funcs_ndx) { - int ret; rc_value_t* self; - rc_scratch_t scratch; + rc_parse_state_t parse; + rc_init_parse_state(&parse, buffer, L, funcs_ndx); - ret = 0; - self = RC_ALLOC(rc_value_t, buffer, &ret, &scratch); - rc_parse_value_internal(self, &ret, buffer, 0, &memaddr, L, funcs_ndx); - return ret >= 0 ? self : 0; + self = RC_ALLOC(rc_value_t, &parse); + rc_parse_value_internal(self, &memaddr, &parse); + + rc_destroy_parse_state(&parse); + return parse.offset >= 0 ? self : 0; } unsigned rc_evaluate_value(rc_value_t* self, rc_peek_t peek, void* ud, lua_State* L) { diff --git a/test/test.c b/test/test.c index 7b18961c..30dfa5e1 100644 --- a/test/test.c +++ b/test/test.c @@ -40,47 +40,53 @@ static unsigned peek(unsigned address, unsigned num_bytes, void* ud) { } static void parse_operand(rc_operand_t* self, const char** memaddr) { - int ret = rc_parse_operand(self, memaddr, 1, NULL, 0); + rc_parse_state_t parse; + int ret; + + rc_init_parse_state(&parse, 0, 0, 0); + ret = rc_parse_operand(self, memaddr, 1, &parse); + rc_destroy_parse_state(&parse); + assert(ret >= 0); assert(**memaddr == 0); - self->previous = 0; - self->prior = 0; } -static void comp_operand(rc_operand_t* self, char expected_type, char expected_size, unsigned expected_value) { +static void comp_operand(rc_operand_t* self, char expected_type, char expected_size, unsigned expected_address) { assert(expected_type == self->type); assert(expected_size == self->size); - assert(expected_value == self->value); + assert(expected_address == self->value); } static void parse_comp_operand(const char* memaddr, char expected_type, char expected_size, unsigned expected_value) { rc_operand_t self; - int ret; - - ret = rc_parse_operand(&self, &memaddr, 1, NULL, 0); - assert(ret >= 0); - assert(*memaddr == 0); - + parse_operand(&self, &memaddr); comp_operand(&self, expected_type, expected_size, expected_value); } static void parse_error_operand(const char* memaddr, int valid_chars) { rc_operand_t self; + rc_parse_state_t parse; int ret; const char* begin = memaddr; - ret = rc_parse_operand(&self, &memaddr, 1, NULL, 0); + rc_init_parse_state(&parse, 0, 0, 0); + ret = rc_parse_operand(&self, &memaddr, 1, &parse); + rc_destroy_parse_state(&parse); + assert(ret < 0); assert(memaddr - begin == valid_chars); } static void parse_comp_operand_value(const char* memaddr, memory_t* memory, unsigned expected_value) { rc_operand_t self; + rc_parse_state_t parse; unsigned value; - rc_parse_operand(&self, &memaddr, 1, NULL, 0); - value = rc_evaluate_operand(&self, peek, memory, NULL); + rc_init_parse_state(&parse, 0, 0, 0); + rc_parse_operand(&self, &memaddr, 1, &parse); + rc_destroy_parse_state(&parse); + value = rc_evaluate_operand(&self, peek, memory, NULL); assert(value == expected_value); } @@ -286,12 +292,15 @@ static void test_operand(void) { memory_t memory; rc_operand_t op; const char* memaddr; + rc_parse_state_t parse; memory.ram = ram; memory.size = sizeof(ram); memaddr = "d0xh1"; - parse_operand(&op, &memaddr); + rc_init_parse_state(&parse, 0, 0, 0); + rc_parse_operand(&op, &memaddr, 1, &parse); + rc_destroy_parse_state(&parse); assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x00); /* first call gets uninitialized value */ assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x12); /* second gets current value */ @@ -322,12 +331,15 @@ static void test_operand(void) { memory_t memory; rc_operand_t op; const char* memaddr; + rc_parse_state_t parse; memory.ram = ram; memory.size = sizeof(ram); memaddr = "p0xh1"; - parse_operand(&op, &memaddr); + rc_init_parse_state(&parse, 0, 0, 0); + rc_parse_operand(&op, &memaddr, 1, &parse); + rc_destroy_parse_state(&parse); /* RC_OPERAND_PRIOR only updates when the memory value changes */ assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x00); /* first call gets uninitialized value */ @@ -353,12 +365,13 @@ static void test_operand(void) { } static void parse_condition(rc_condition_t* self, const char* memaddr) { - int ret; - rc_scratch_t scratch; + rc_parse_state_t parse; - ret = 0; - rc_parse_condition(&ret, self, &scratch, &memaddr, NULL, 0); - assert(ret >= 0); + rc_init_parse_state(&parse, 0, 0, 0); + rc_parse_condition(&memaddr, &parse); + rc_destroy_parse_state(&parse); + + assert(parse.offset >= 0); assert(*memaddr == 0); } @@ -369,27 +382,33 @@ static void parse_comp_condition( char expected_right_type, char expected_right_size, unsigned expected_right_value, int expected_required_hits ) { - rc_condition_t self; - parse_condition(&self, memaddr); - - assert(self.type == expected_type); - comp_operand(&self.operand1, expected_left_type, expected_left_size, expected_left_value); - assert(self.oper == expected_operator); - comp_operand(&self.operand2, expected_right_type, expected_right_size, expected_right_value); - assert(self.required_hits == expected_required_hits); + rc_condition_t* self; + rc_parse_state_t parse; + + rc_init_parse_state(&parse, 0, 0, 0); + self = rc_parse_condition(&memaddr, &parse); + rc_destroy_parse_state(&parse); + + assert(self->type == expected_type); + comp_operand(&self->operand1, expected_left_type, expected_left_size, expected_left_value); + assert(self->oper == expected_operator); + comp_operand(&self->operand2, expected_right_type, expected_right_size, expected_right_value); + assert(self->required_hits == expected_required_hits); } static void parse_test_condition(const char* memaddr, memory_t* memory, int value) { - rc_condition_t self; + rc_condition_t* self; + rc_parse_state_t parse; int ret; - rc_scratch_t scratch; - ret = 0; - rc_parse_condition(&ret, &self, &scratch, &memaddr, NULL, 0); - assert(ret >= 0); + rc_init_parse_state(&parse, 0, 0, 0); + self = rc_parse_condition(&memaddr, &parse); + rc_destroy_parse_state(&parse); + + assert(parse.offset >= 0); assert(*memaddr == 0); - ret = rc_test_condition(&self, 0, peek, memory, NULL); + ret = rc_test_condition(self, 0, peek, memory, NULL); assert((ret && value) || (!ret && !value)); } @@ -615,26 +634,32 @@ static void test_condition(void) { unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; memory_t memory; - rc_condition_t cond; + rc_condition_t* cond; + rc_parse_state_t parse; + const char* cond_str = "0xH0001>d0xH0001"; + rc_init_parse_state(&parse, 0, 0, 0); + cond = rc_parse_condition(&cond_str, &parse); + rc_destroy_parse_state(&parse); + + assert(parse.offset >= 0); + assert(*cond_str == 0); memory.ram = ram; memory.size = sizeof(ram); - parse_condition(&cond, "0xH0001>d0xH0001"); - /* initial delta value is 0, 0x12 > 0 */ - assert(rc_test_condition(&cond, 0, peek, &memory, NULL) == 1); + assert(rc_test_condition(cond, 0, peek, &memory, NULL) == 1); /* delta value is now 0x12, 0x12 = 0x12 */ - assert(rc_test_condition(&cond, 0, peek, &memory, NULL) == 0); + assert(rc_test_condition(cond, 0, peek, &memory, NULL) == 0); /* delta value is now 0x12, 0x11 < 0x12 */ ram[1] = 0x11; - assert(rc_test_condition(&cond, 0, peek, &memory, NULL) == 0); + assert(rc_test_condition(cond, 0, peek, &memory, NULL) == 0); /* delta value is now 0x13, 0x12 > 0x11 */ ram[1] = 0x12; - assert(rc_test_condition(&cond, 0, peek, &memory, NULL) == 1); + assert(rc_test_condition(cond, 0, peek, &memory, NULL) == 1); } } @@ -1390,7 +1415,6 @@ static void test_trigger(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_trigger_t* trigger; - char buffer[2048]; memory.ram = ram; memory.size = sizeof(ram); @@ -1553,7 +1577,6 @@ static void test_trigger(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_trigger_t* trigger; - char buffer[2048]; rc_condset_t* condset; @@ -1641,7 +1664,6 @@ static void test_trigger(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_trigger_t* trigger; - char buffer[2048]; memory.ram = ram; memory.size = sizeof(ram); @@ -1675,7 +1697,6 @@ static void test_trigger(void) { unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; memory_t memory; rc_trigger_t* trigger; - char buffer[2048]; memory.ram = ram; memory.size = sizeof(ram); @@ -1722,7 +1743,6 @@ static void test_trigger(void) { unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; memory_t memory; rc_trigger_t* trigger; - char buffer[2048]; memory.ram = ram; memory.size = sizeof(ram); @@ -1761,7 +1781,6 @@ static void test_trigger(void) { unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; memory_t memory; rc_trigger_t* trigger; - char buffer[2048]; memory.ram = ram; memory.size = sizeof(ram); @@ -1799,7 +1818,6 @@ static void test_trigger(void) { unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; memory_t memory; rc_trigger_t* trigger; - char buffer[2048]; memory.ram = ram; memory.size = sizeof(ram); @@ -1827,67 +1845,74 @@ static void test_trigger(void) { } static void parse_comp_term(const char* memaddr, char expected_var_size, unsigned expected_address, int is_bcd, int is_const) { - rc_term_t self; - rc_scratch_t scratch; - int ret; + rc_term_t* self; + rc_parse_state_t parse; - ret = 0; - rc_parse_term(&ret, &self, &scratch, &memaddr, NULL, 0); - assert(ret >= 0); + rc_init_parse_state(&parse, 0, 0, 0); + self = rc_parse_term(&memaddr, &parse); + rc_destroy_parse_state(&parse); + + assert(parse.offset >= 0); assert(*memaddr == 0); - assert(is_const || self.operand1.size == expected_var_size); - assert(self.operand1.value == expected_address); - assert(self.operand1.is_bcd == is_bcd); - assert(self.invert == 0); - assert(self.operand2.size == RC_MEMSIZE_8_BITS); - assert(self.operand2.value == 0U); - assert(!is_const || self.operand1.type == RC_OPERAND_CONST); + if (is_const) { + assert(self->operand1.type == RC_OPERAND_CONST); + } + else { + assert(self->operand1.size == expected_var_size); + assert(self->operand1.value == expected_address); + assert(self->operand1.is_bcd == is_bcd); + } + assert(self->invert == 0); + assert(self->operand2.value == 0U); } static void parse_comp_term_fp(const char* memaddr, char expected_var_size, unsigned expected_address, double fp) { - rc_term_t self; - rc_scratch_t scratch; - int ret; - - ret = 0; - rc_parse_term(&ret, &self, &scratch, &memaddr, NULL, 0); - assert(ret >= 0); + rc_term_t* self; + rc_parse_state_t parse; + + rc_init_parse_state(&parse, 0, 0, 0); + self = rc_parse_term(&memaddr, &parse); + rc_destroy_parse_state(&parse); + + assert(parse.offset >= 0); assert(*memaddr == 0); - assert(self.operand1.size == expected_var_size); - assert(self.operand1.value == expected_address); - assert(self.operand2.type == RC_OPERAND_FP); - assert(self.operand2.fp_value == fp); + assert(self->operand1.size == expected_var_size); + assert(self->operand1.value == expected_address); + assert(self->operand2.type == RC_OPERAND_FP); + assert(self->operand2.fp_value == fp); } static void parse_comp_term_mem(const char* memaddr, char expected_size_1, unsigned expected_address_1, char expected_size_2, unsigned expected_address_2) { - rc_term_t self; - rc_scratch_t scratch; - int ret; - - ret = 0; - rc_parse_term(&ret, &self, &scratch, &memaddr, NULL, 0); - assert(ret >= 0); + rc_term_t* self; + rc_parse_state_t parse; + + rc_init_parse_state(&parse, 0, 0, 0); + self = rc_parse_term(&memaddr, &parse); + rc_destroy_parse_state(&parse); + + assert(parse.offset >= 0); assert(*memaddr == 0); - assert(self.operand1.size == expected_size_1); - assert(self.operand1.value == expected_address_1); - assert(self.operand2.size == expected_size_2); - assert(self.operand2.value == expected_address_2); + assert(self->operand1.size == expected_size_1); + assert(self->operand1.value == expected_address_1); + assert(self->operand2.size == expected_size_2); + assert(self->operand2.value == expected_address_2); } static void parse_comp_term_value(const char* memaddr, memory_t* memory, unsigned value) { - rc_term_t self; - rc_scratch_t scratch; - int ret; - - ret = 0; - rc_parse_term(&ret, &self, &scratch, &memaddr, NULL, 0); - assert(ret >= 0); + rc_term_t* self; + rc_parse_state_t parse; + + rc_init_parse_state(&parse, 0, 0, 0); + self = rc_parse_term(&memaddr, &parse); + rc_destroy_parse_state(&parse); + + assert(parse.offset >= 0); assert(*memaddr == 0); - assert(rc_evaluate_term(&self, peek, memory, NULL) == value); + assert(rc_evaluate_term(self, peek, memory, NULL) == value); } static void test_term(void) { @@ -1943,7 +1968,6 @@ static void test_term(void) { TestClauseParseFromStringMultiplyAddress ------------------------------------------------------------------------*/ - parse_comp_term_mem("0xH1234", RC_MEMSIZE_8_BITS, 0x1234U, RC_MEMSIZE_8_BITS, 0U); parse_comp_term_mem("0xH1234*0xH3456", RC_MEMSIZE_8_BITS, 0x1234U, RC_MEMSIZE_8_BITS, 0x3456U); parse_comp_term_mem("0xH1234*0xL2222", RC_MEMSIZE_8_BITS, 0x1234U, RC_MEMSIZE_LOW, 0x2222U); parse_comp_term_mem("0xH1234*0x1111", RC_MEMSIZE_8_BITS, 0x1234U, RC_MEMSIZE_16_BITS, 0x1111U); @@ -2482,6 +2506,9 @@ static rc_richpresence_t* parse_richpresence(const char* script, void* buffer) { } static void test_richpresence(void) { + char buffer[2048]; + char output[128]; + { /*------------------------------------------------------------------------ TestStaticDisplayString @@ -2489,8 +2516,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2509,8 +2534,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2529,8 +2552,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2549,8 +2570,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2569,8 +2588,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2589,8 +2606,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2619,8 +2634,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2647,8 +2660,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; memory.ram = ram; memory.size = sizeof(ram); @@ -2687,8 +2698,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; memory.ram = ram; memory.size = sizeof(ram); @@ -2717,8 +2726,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2742,8 +2749,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2767,8 +2772,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2792,8 +2795,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2812,8 +2813,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2832,8 +2831,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2862,8 +2859,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2892,8 +2887,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2922,8 +2915,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2952,8 +2943,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -2982,8 +2971,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -3012,8 +2999,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -3042,8 +3027,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -3072,8 +3055,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -3102,8 +3083,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; int result; memory.ram = ram; @@ -3132,8 +3111,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; memory.ram = ram; memory.size = sizeof(ram); @@ -3160,8 +3137,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; memory.ram = ram; memory.size = sizeof(ram); @@ -3186,8 +3161,6 @@ static void test_richpresence(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_richpresence_t* richpresence; - char buffer[2048]; - char output[128]; memory.ram = ram; memory.size = sizeof(ram); From 839c381272a9796c27636af644bf970842dea05e Mon Sep 17 00:00:00 2001 From: Jamiras Date: Wed, 12 Dec 2018 17:09:12 -0700 Subject: [PATCH 03/11] add rc_memref_t --- include/rcheevos.h | 61 ++++-- src/rcheevos/alloc.c | 11 +- src/rcheevos/internal.h | 41 ++-- src/rcheevos/lboard.c | 9 + src/rcheevos/memref.c | 204 ++++++++++++++++++ src/rcheevos/operand.c | 167 +++----------- src/rcheevos/richpresence.c | 8 + src/rcheevos/term.c | 15 +- src/rcheevos/trigger.c | 4 + src/rcheevos/value.c | 4 + test/rcheevos-test.vcxproj | 1 + test/rcheevos-test.vcxproj.filters | 3 + test/test.c | 336 +++++++++++++++++++++++++---- 13 files changed, 654 insertions(+), 210 deletions(-) create mode 100644 src/rcheevos/memref.c diff --git a/include/rcheevos.h b/include/rcheevos.h index 5ee846e7..2fefb9ca 100644 --- a/include/rcheevos.h +++ b/include/rcheevos.h @@ -30,7 +30,8 @@ enum { RC_MISSING_SUBMIT = -15, RC_MISSING_VALUE = -16, RC_INVALID_LBOARD_FIELD = -17, - RC_MISSING_DISPLAY_STRING = -18 + RC_MISSING_DISPLAY_STRING = -18, + RC_OUT_OF_MEMORY = -19 }; /*****************************************************************************\ @@ -83,7 +84,7 @@ enum { typedef unsigned (*rc_peek_t)(unsigned address, unsigned num_bytes, void* ud); /*****************************************************************************\ -| Operands | +| Memory References | \*****************************************************************************/ /* Sizes. */ @@ -104,6 +105,36 @@ enum { RC_MEMSIZE_32_BITS }; +typedef struct { + /* The memory address of this variable. */ + unsigned address; + /* The size of the variable. */ + char size; + /* True if the value is in BCD. */ + char is_bcd; +} rc_memref_t; + +typedef struct rc_memref_value_t rc_memref_value_t; + +struct rc_memref_value_t { + /* The value of this memory reference. */ + unsigned value; + /* The previous value of this memory reference. */ + unsigned previous; + /* The last differing value of this memory reference. */ + unsigned prior; + + /* The referenced memory */ + rc_memref_t memref; + + /* The next memory reference in the chain */ + rc_memref_value_t* next; +}; + +/*****************************************************************************\ +| Operands | +\*****************************************************************************/ + /* types */ enum { RC_OPERAND_ADDRESS, /* Compare to the value of a live address in RAM. */ @@ -117,20 +148,10 @@ enum { typedef struct { union { /* A value read from memory. */ - struct { - /* The memory address or constant value of this variable. */ - unsigned value; - /* The previous memory contents if RC_OPERAND_DELTA or RC_OPERAND_PRIOR. */ - unsigned previous; - /* The last differing value if RC_OPERAND_PRIOR. */ - unsigned prior; - - /* The size of the variable. */ - char size; - /* True if the value is in BCD. */ - char is_bcd; - /* The type of the variable. */ - }; + rc_memref_value_t* memref; + + /* A value. */ + unsigned value; /* A floating point value. */ double fp_value; @@ -222,6 +243,9 @@ typedef struct { /* The list of sub condition sets in this test. */ rc_condset_t* alternative; + + /* The memory references required by the trigger. */ + rc_memref_value_t* memrefs; } rc_trigger_t; @@ -262,6 +286,9 @@ struct rc_expression_t { typedef struct { /* The list of expression to evaluate. */ rc_expression_t* expressions; + + /* The memory references required by the value. */ + rc_memref_value_t* memrefs; } rc_value_t; @@ -288,6 +315,7 @@ typedef struct { rc_trigger_t cancel; rc_value_t value; rc_value_t* progress; + rc_memref_value_t* memrefs; char started; char submitted; @@ -358,6 +386,7 @@ struct rc_richpresence_display_t { typedef struct { rc_richpresence_display_t* first_display; rc_richpresence_lookup_t* first_lookup; + rc_memref_value_t* memrefs; } rc_richpresence_t; diff --git a/src/rcheevos/alloc.c b/src/rcheevos/alloc.c index 90cbca03..f5fcf33c 100644 --- a/src/rcheevos/alloc.c +++ b/src/rcheevos/alloc.c @@ -10,8 +10,11 @@ void* rc_alloc(void* pointer, int* offset, int size, int alignment, rc_scratch_t if (pointer != 0) { ptr = (void*)((char*)pointer + *offset); } + else if (scratch != 0) { + ptr = &scratch->obj; + } else { - ptr = scratch; + ptr = 0; } *offset += size; @@ -36,8 +39,14 @@ void rc_init_parse_state(rc_parse_state_t* parse, void* buffer, lua_State* L, in parse->L = L; parse->funcs_ndx = funcs_ndx; parse->buffer = buffer; + parse->scratch.memref = parse->scratch.memref_buffer; + parse->scratch.memref_size = sizeof(parse->scratch.memref_buffer) / sizeof(parse->scratch.memref_buffer[0]); + parse->scratch.memref_count = 0; + parse->first_memref = 0; } void rc_destroy_parse_state(rc_parse_state_t* parse) { + if (parse->scratch.memref != parse->scratch.memref_buffer) + free(parse->scratch.memref); } \ No newline at end of file diff --git a/src/rcheevos/internal.h b/src/rcheevos/internal.h index 8145f40d..a27c5e97 100644 --- a/src/rcheevos/internal.h +++ b/src/rcheevos/internal.h @@ -10,19 +10,28 @@ #define RC_ALLOC(t, p) ((t*)rc_alloc((p)->buffer, &(p)->offset, sizeof(t), RC_ALIGNOF(t), &(p)->scratch)) -typedef union { - rc_operand_t operand; - rc_condition_t condition; - rc_condset_t condset; - rc_trigger_t trigger; - rc_term_t term; - rc_expression_t expression; - rc_lboard_t lboard; - rc_richpresence_t richpresence; - rc_richpresence_display_t richpresence_display; - rc_richpresence_display_part_t richpresence_part; - rc_richpresence_lookup_t richpresence_lookup; - rc_richpresence_lookup_item_t richpresence_lookup_item; +typedef struct { + rc_memref_t memref_buffer[16]; + rc_memref_t *memref; + int memref_count; + int memref_size; + + union + { + rc_operand_t operand; + rc_condition_t condition; + rc_condset_t condset; + rc_trigger_t trigger; + rc_term_t term; + rc_expression_t expression; + rc_lboard_t lboard; + rc_memref_value_t memref_value; + rc_richpresence_t richpresence; + rc_richpresence_display_t richpresence_display; + rc_richpresence_display_part_t richpresence_part; + rc_richpresence_lookup_t richpresence_lookup; + rc_richpresence_lookup_item_t richpresence_lookup_item; + } obj; } rc_scratch_t; @@ -34,15 +43,21 @@ typedef struct { void* buffer; rc_scratch_t scratch; + + rc_memref_value_t** first_memref; } rc_parse_state_t; void rc_init_parse_state(rc_parse_state_t* parse, void* buffer, lua_State* L, int funcs_ndx); +void rc_init_parse_state_memrefs(rc_parse_state_t* parse, rc_memref_value_t** memrefs); void rc_destroy_parse_state(rc_parse_state_t* parse); void* rc_alloc(void* pointer, int* offset, int size, int alignment, rc_scratch_t* scratch); char* rc_alloc_str(rc_parse_state_t* parse, const char* text, int length); +rc_memref_value_t* rc_alloc_memref_value(rc_parse_state_t* parse, unsigned address, char size, char is_bcd); +void rc_update_memref_values(rc_memref_value_t* memref, rc_peek_t peek, void* ud); + void rc_parse_trigger_internal(rc_trigger_t* self, const char** memaddr, rc_parse_state_t* parse); rc_condset_t* rc_parse_condset(const char** memaddr, rc_parse_state_t* parse); diff --git a/src/rcheevos/lboard.c b/src/rcheevos/lboard.c index 6dc523ad..a0e8334d 100644 --- a/src/rcheevos/lboard.c +++ b/src/rcheevos/lboard.c @@ -28,6 +28,7 @@ void rc_parse_lboard_internal(rc_lboard_t* self, const char* memaddr, rc_parse_s found |= RC_LBOARD_START; memaddr += 4; rc_parse_trigger_internal(&self->start, &memaddr, parse); + self->start.memrefs = 0; if (parse->offset < 0) { return; @@ -44,6 +45,7 @@ void rc_parse_lboard_internal(rc_lboard_t* self, const char* memaddr, rc_parse_s found |= RC_LBOARD_CANCEL; memaddr += 4; rc_parse_trigger_internal(&self->cancel, &memaddr, parse); + self->cancel.memrefs = 0; if (parse->offset < 0) { return; @@ -60,6 +62,7 @@ void rc_parse_lboard_internal(rc_lboard_t* self, const char* memaddr, rc_parse_s found |= RC_LBOARD_SUBMIT; memaddr += 4; rc_parse_trigger_internal(&self->submit, &memaddr, parse); + self->submit.memrefs = 0; if (parse->offset < 0) { return; @@ -76,6 +79,7 @@ void rc_parse_lboard_internal(rc_lboard_t* self, const char* memaddr, rc_parse_s found |= RC_LBOARD_VALUE; memaddr += 4; rc_parse_value_internal(&self->value, &memaddr, parse); + self->value.memrefs = 0; if (parse->offset < 0) { return; @@ -94,6 +98,7 @@ void rc_parse_lboard_internal(rc_lboard_t* self, const char* memaddr, rc_parse_s self->progress = RC_ALLOC(rc_value_t, parse); rc_parse_value_internal(self->progress, &memaddr, parse); + self->progress->memrefs = 0; if (parse->offset < 0) { return; @@ -149,6 +154,8 @@ rc_lboard_t* rc_parse_lboard(void* buffer, const char* memaddr, lua_State* L, in rc_init_parse_state(&parse, buffer, L, funcs_ndx); self = RC_ALLOC(rc_lboard_t, &parse); + rc_init_parse_state_memrefs(&parse, &self->memrefs); + rc_parse_lboard_internal(self, memaddr, &parse); rc_destroy_parse_state(&parse); @@ -159,6 +166,8 @@ int rc_evaluate_lboard(rc_lboard_t* self, unsigned* value, rc_peek_t peek, void* int start_ok, cancel_ok, submit_ok; int action = -1; + rc_update_memref_values(self->memrefs, peek, peek_ud); + /* ASSERT: these are always tested once every frame, to ensure delta variables work properly */ start_ok = rc_test_trigger(&self->start, peek, peek_ud, L); cancel_ok = rc_test_trigger(&self->cancel, peek, peek_ud, L); diff --git a/src/rcheevos/memref.c b/src/rcheevos/memref.c new file mode 100644 index 00000000..ff6622f2 --- /dev/null +++ b/src/rcheevos/memref.c @@ -0,0 +1,204 @@ +#include "internal.h" + +#include // malloc/realloc +#include // memcpy + +rc_memref_value_t* rc_alloc_memref_value(rc_parse_state_t* parse, unsigned address, char size, char is_bcd) { + rc_memref_value_t** next_memref_value; + rc_memref_value_t* memref_value; + rc_memref_t* memref; + int i; + + if (!parse->first_memref) { + /* sizing mode - have to track unique address/size/bcd combinations */ + for (i = 0; i < parse->scratch.memref_count; ++i) { + memref = &parse->scratch.memref[i]; + if (memref->address == address && memref->size == size && memref->is_bcd == is_bcd) { + return &parse->scratch.obj.memref_value; + } + } + + /* resize unique tracking buffer if necessary */ + if (parse->scratch.memref_count == parse->scratch.memref_size) { + if (parse->scratch.memref == parse->scratch.memref_buffer) { + parse->scratch.memref_size += 16; + memref = malloc(parse->scratch.memref_size * sizeof(parse->scratch.memref_buffer[0])); + if (memref) { + parse->scratch.memref = memref; + memcpy(memref, parse->scratch.memref_buffer, parse->scratch.memref_count * sizeof(parse->scratch.memref_buffer[0])); + } + else { + parse->offset = RC_OUT_OF_MEMORY; + return 0; + } + } + else { + parse->scratch.memref_size += 32; + memref = realloc(parse->scratch.memref, parse->scratch.memref_size * sizeof(parse->scratch.memref_buffer[0])); + if (memref) { + parse->scratch.memref = memref; + } + else { + parse->offset = RC_OUT_OF_MEMORY; + return 0; + } + } + } + + /* add new unique tracking entry */ + if (parse->scratch.memref) { + memref = &parse->scratch.memref[parse->scratch.memref_count++]; + memref->address = address; + memref->size = size; + memref->is_bcd = is_bcd; + } + + /* allocate memory but don't actually populate, as it might overwrite the self object referencing the rc_memref_value_t */ + return RC_ALLOC(rc_memref_value_t, parse); + } + + /* construction mode - find or create the appropriate rc_memref_value_t */ + next_memref_value = parse->first_memref; + while (*next_memref_value) { + memref_value = *next_memref_value; + if (memref_value->memref.address == address && memref_value->memref.size == size && memref_value->memref.is_bcd == is_bcd) { + return memref_value; + } + + next_memref_value = &memref_value->next; + } + + memref_value = RC_ALLOC(rc_memref_value_t, parse); + memref_value->memref.address = address; + memref_value->memref.size = size; + memref_value->memref.is_bcd = is_bcd; + memref_value->value = 0; + memref_value->previous = 0; + memref_value->prior = 0; + memref_value->next = 0; + + *next_memref_value = memref_value; + + return memref_value; +} + +static unsigned rc_memref_get_value(rc_memref_t* self, rc_peek_t peek, void* ud) { + unsigned value; + + switch (self->size) + { + case RC_MEMSIZE_BIT_0: + value = (peek(self->address, 1, ud) >> 0) & 1; + break; + + case RC_MEMSIZE_BIT_1: + value = (peek(self->address, 1, ud) >> 1) & 1; + break; + + case RC_MEMSIZE_BIT_2: + value = (peek(self->address, 1, ud) >> 2) & 1; + break; + + case RC_MEMSIZE_BIT_3: + value = (peek(self->address, 1, ud) >> 3) & 1; + break; + + case RC_MEMSIZE_BIT_4: + value = (peek(self->address, 1, ud) >> 4) & 1; + break; + + case RC_MEMSIZE_BIT_5: + value = (peek(self->address, 1, ud) >> 5) & 1; + break; + + case RC_MEMSIZE_BIT_6: + value = (peek(self->address, 1, ud) >> 6) & 1; + break; + + case RC_MEMSIZE_BIT_7: + value = (peek(self->address, 1, ud) >> 7) & 1; + break; + + case RC_MEMSIZE_LOW: + value = peek(self->address, 1, ud) & 0x0f; + break; + + case RC_MEMSIZE_HIGH: + value = (peek(self->address, 1, ud) >> 4) & 0x0f; + break; + + case RC_MEMSIZE_8_BITS: + value = peek(self->address, 1, ud); + + if (self->is_bcd) { + value = ((value >> 4) & 0x0f) * 10 + (value & 0x0f); + } + + break; + + case RC_MEMSIZE_16_BITS: + value = peek(self->address, 2, ud); + + if (self->is_bcd) { + value = ((value >> 12) & 0x0f) * 1000 + + ((value >> 8) & 0x0f) * 100 + + ((value >> 4) & 0x0f) * 10 + + ((value >> 0) & 0x0f) * 1; + } + + break; + + case RC_MEMSIZE_24_BITS: + value = peek(self->address, 4, ud); + + if (self->is_bcd) { + value = ((value >> 20) & 0x0f) * 100000 + + ((value >> 16) & 0x0f) * 10000 + + ((value >> 12) & 0x0f) * 1000 + + ((value >> 8) & 0x0f) * 100 + + ((value >> 4) & 0x0f) * 10 + + ((value >> 0) & 0x0f) * 1; + } + + break; + + case RC_MEMSIZE_32_BITS: + value = peek(self->address, 4, ud); + + if (self->is_bcd) { + value = ((value >> 28) & 0x0f) * 10000000 + + ((value >> 24) & 0x0f) * 1000000 + + ((value >> 20) & 0x0f) * 100000 + + ((value >> 16) & 0x0f) * 10000 + + ((value >> 12) & 0x0f) * 1000 + + ((value >> 8) & 0x0f) * 100 + + ((value >> 4) & 0x0f) * 10 + + ((value >> 0) & 0x0f) * 1; + } + + break; + + default: + value = 0; + break; + } + + return value; +} + +void rc_update_memref_values(rc_memref_value_t* memref, rc_peek_t peek, void* ud) { + while (memref) { + memref->previous = memref->value; + memref->value = rc_memref_get_value(&memref->memref, peek, ud); + if (memref->value != memref->previous) + memref->prior = memref->previous; + + memref = memref->next; + } +} + +void rc_init_parse_state_memrefs(rc_parse_state_t* parse, rc_memref_value_t** memrefs) +{ + parse->first_memref = memrefs; + *memrefs = 0; +} diff --git a/src/rcheevos/operand.c b/src/rcheevos/operand.c index 61ab1770..46932cb8 100644 --- a/src/rcheevos/operand.c +++ b/src/rcheevos/operand.c @@ -61,10 +61,12 @@ static int rc_parse_operand_lua(rc_operand_t* self, const char** memaddr, rc_par return RC_OK; } -static int rc_parse_operand_memory(rc_operand_t* self, const char** memaddr) { +static int rc_parse_operand_memory(rc_operand_t* self, const char** memaddr, rc_parse_state_t* parse) { const char* aux = *memaddr; char* end; - unsigned long value; + unsigned long address; + char is_bcd = 0; + char size; switch (*aux++) { case 'd': case 'D': @@ -73,7 +75,7 @@ static int rc_parse_operand_memory(rc_operand_t* self, const char** memaddr) { case 'b': case 'B': self->type = RC_OPERAND_ADDRESS; - self->is_bcd = 1; + is_bcd = 1; break; case 'p': case 'P': @@ -97,38 +99,40 @@ static int rc_parse_operand_memory(rc_operand_t* self, const char** memaddr) { aux++; switch (*aux++) { - case 'm': case 'M': self->size = RC_MEMSIZE_BIT_0; break; - case 'n': case 'N': self->size = RC_MEMSIZE_BIT_1; break; - case 'o': case 'O': self->size = RC_MEMSIZE_BIT_2; break; - case 'p': case 'P': self->size = RC_MEMSIZE_BIT_3; break; - case 'q': case 'Q': self->size = RC_MEMSIZE_BIT_4; break; - case 'r': case 'R': self->size = RC_MEMSIZE_BIT_5; break; - case 's': case 'S': self->size = RC_MEMSIZE_BIT_6; break; - case 't': case 'T': self->size = RC_MEMSIZE_BIT_7; break; - case 'l': case 'L': self->size = RC_MEMSIZE_LOW; break; - case 'u': case 'U': self->size = RC_MEMSIZE_HIGH; break; - case 'h': case 'H': self->size = RC_MEMSIZE_8_BITS; break; - case 'w': case 'W': self->size = RC_MEMSIZE_24_BITS; break; - case 'x': case 'X': self->size = RC_MEMSIZE_32_BITS; break; + case 'm': case 'M': size = RC_MEMSIZE_BIT_0; break; + case 'n': case 'N': size = RC_MEMSIZE_BIT_1; break; + case 'o': case 'O': size = RC_MEMSIZE_BIT_2; break; + case 'p': case 'P': size = RC_MEMSIZE_BIT_3; break; + case 'q': case 'Q': size = RC_MEMSIZE_BIT_4; break; + case 'r': case 'R': size = RC_MEMSIZE_BIT_5; break; + case 's': case 'S': size = RC_MEMSIZE_BIT_6; break; + case 't': case 'T': size = RC_MEMSIZE_BIT_7; break; + case 'l': case 'L': size = RC_MEMSIZE_LOW; break; + case 'u': case 'U': size = RC_MEMSIZE_HIGH; break; + case 'h': case 'H': size = RC_MEMSIZE_8_BITS; break; + case 'w': case 'W': size = RC_MEMSIZE_24_BITS; break; + case 'x': case 'X': size = RC_MEMSIZE_32_BITS; break; default: /* fall through */ aux--; case ' ': - self->size = RC_MEMSIZE_16_BITS; + size = RC_MEMSIZE_16_BITS; break; } - value = (unsigned)strtoul(aux, &end, 16); + address = (unsigned)strtoul(aux, &end, 16); if (end == aux) { return RC_INVALID_MEMORY_OPERAND; } - if (value > 0xffffffffU) { - value = 0xffffffffU; + if (address > 0xffffffffU) { + address = 0xffffffffU; } - self->value = (unsigned)value; + self->memref = rc_alloc_memref_value(parse, address, size, is_bcd); + if (parse->offset < 0) + return parse->offset; *memaddr = end; return RC_OK; @@ -162,7 +166,7 @@ static int rc_parse_operand_trigger(rc_operand_t* self, const char** memaddr, rc if (aux[1] == 'x' || aux[1] == 'X') { /* fall through */ default: - ret = rc_parse_operand_memory(self, &aux); + ret = rc_parse_operand_memory(self, &aux, parse); if (ret < 0) { return ret; @@ -250,7 +254,7 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, rc_pa if (aux[1] == 'x' || aux[1] == 'X') { /* fall through */ default: - ret = rc_parse_operand_memory(self, &aux); + ret = rc_parse_operand_memory(self, &aux, parse); if (ret < 0) { return ret; @@ -289,11 +293,6 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, rc_pa } int rc_parse_operand(rc_operand_t* self, const char** memaddr, int is_trigger, rc_parse_state_t* parse) { - self->size = RC_MEMSIZE_8_BITS; - self->is_bcd = 0; - self->previous = 0; - self->prior = 0; - if (is_trigger) { return rc_parse_operand_trigger(self, memaddr, parse); } @@ -368,113 +367,15 @@ unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_S break; case RC_OPERAND_ADDRESS: - case RC_OPERAND_DELTA: - case RC_OPERAND_PRIOR: - switch (self->size) { - case RC_MEMSIZE_BIT_0: - value = (peek(self->value, 1, ud) >> 0) & 1; - break; - - case RC_MEMSIZE_BIT_1: - value = (peek(self->value, 1, ud) >> 1) & 1; - break; - - case RC_MEMSIZE_BIT_2: - value = (peek(self->value, 1, ud) >> 2) & 1; - break; - - case RC_MEMSIZE_BIT_3: - value = (peek(self->value, 1, ud) >> 3) & 1; - break; - - case RC_MEMSIZE_BIT_4: - value = (peek(self->value, 1, ud) >> 4) & 1; - break; - - case RC_MEMSIZE_BIT_5: - value = (peek(self->value, 1, ud) >> 5 ) & 1; - break; - - case RC_MEMSIZE_BIT_6: - value = (peek(self->value, 1, ud) >> 6) & 1; - break; - - case RC_MEMSIZE_BIT_7: - value = (peek(self->value, 1, ud) >> 7) & 1; - break; - - case RC_MEMSIZE_LOW: - value = peek(self->value, 1, ud) & 0x0f; - break; - - case RC_MEMSIZE_HIGH: - value = (peek(self->value, 1, ud) >> 4) & 0x0f; - break; - - case RC_MEMSIZE_8_BITS: - value = peek(self->value, 1, ud); - - if (self->is_bcd) { - value = ((value >> 4) & 0x0f) * 10 + (value & 0x0f); - } - - break; - - case RC_MEMSIZE_16_BITS: - value = peek(self->value, 2, ud); - - if (self->is_bcd) { - value = ((value >> 12) & 0x0f) * 1000 - + ((value >> 8) & 0x0f) * 100 - + ((value >> 4) & 0x0f) * 10 - + ((value >> 0) & 0x0f) * 1; - } - - break; - - case RC_MEMSIZE_24_BITS: - value = peek(self->value, 4, ud); - - if (self->is_bcd) { - value = ((value >> 20) & 0x0f) * 100000 - + ((value >> 16) & 0x0f) * 10000 - + ((value >> 12) & 0x0f) * 1000 - + ((value >> 8) & 0x0f) * 100 - + ((value >> 4) & 0x0f) * 10 - + ((value >> 0) & 0x0f) * 1; - } - - break; - - case RC_MEMSIZE_32_BITS: - value = peek(self->value, 4, ud); - - if (self->is_bcd) { - value = ((value >> 28) & 0x0f) * 10000000 - + ((value >> 24) & 0x0f) * 1000000 - + ((value >> 20) & 0x0f) * 100000 - + ((value >> 16) & 0x0f) * 10000 - + ((value >> 12) & 0x0f) * 1000 - + ((value >> 8) & 0x0f) * 100 - + ((value >> 4) & 0x0f) * 10 - + ((value >> 0) & 0x0f) * 1; - } - - break; - } + value = self->memref->value; + break; - if (self->type == RC_OPERAND_DELTA) { - unsigned previous = self->previous; - self->previous = value; - value = previous; - } else if (self->type == RC_OPERAND_PRIOR) { - if (self->previous != value) { - self->prior = self->previous; - self->previous = value; - } - value = self->prior; - } + case RC_OPERAND_DELTA: + value = self->memref->previous; + break; + case RC_OPERAND_PRIOR: + value = self->memref->prior; break; } diff --git a/src/rcheevos/richpresence.c b/src/rcheevos/richpresence.c index a8157d12..85a7a51f 100644 --- a/src/rcheevos/richpresence.c +++ b/src/rcheevos/richpresence.c @@ -136,6 +136,7 @@ static rc_richpresence_display_t* rc_parse_richpresence_display_internal(const c ++ptr; if (*ptr == ')') { rc_parse_value_internal(&part->value, &line, parse); + part->value.memrefs = 0; if (parse->offset < 0) return 0; ++ptr; @@ -317,6 +318,7 @@ void rc_parse_richpresence_internal(rc_richpresence_t* self, const char* script, *nextdisplay = rc_parse_richpresence_display_internal(ptr + 1, endline, parse, self); trigger = &((*nextdisplay)->trigger); rc_parse_trigger_internal(trigger, &line, parse); + trigger->memrefs = 0; if (parse->offset < 0) return; if (parse->buffer) @@ -361,7 +363,11 @@ rc_richpresence_t* rc_parse_richpresence(void* buffer, const char* script, lua_S rc_init_parse_state(&parse, buffer, L, funcs_ndx); self = RC_ALLOC(rc_richpresence_t, &parse); + rc_init_parse_state_memrefs(&parse, &self->memrefs); + rc_parse_richpresence_internal(self, script, &parse); + + rc_destroy_parse_state(&parse); return parse.offset >= 0 ? self : 0; } @@ -373,6 +379,8 @@ int rc_evaluate_richpresence(rc_richpresence_t* richpresence, char* buffer, unsi int chars; unsigned value; + rc_update_memref_values(richpresence->memrefs, peek, peek_ud); + ptr = buffer; display = richpresence->first_display; while (display) { diff --git a/src/rcheevos/term.c b/src/rcheevos/term.c index 138a8a19..3030ee84 100644 --- a/src/rcheevos/term.c +++ b/src/rcheevos/term.c @@ -3,6 +3,7 @@ rc_term_t* rc_parse_term(const char** memaddr, rc_parse_state_t* parse) { rc_term_t* self; const char* aux; + char size; int ret2; aux = *memaddr; @@ -32,7 +33,18 @@ rc_term_t* rc_parse_term(const char** memaddr, rc_parse_state_t* parse) { } if (self->invert) { - switch (self->operand2.size) { + switch (self->operand2.type) { + case RC_OPERAND_ADDRESS: + case RC_OPERAND_DELTA: + case RC_OPERAND_PRIOR: + size = self->operand2.memref->memref.size; + break; + default: + size = RC_MEMSIZE_32_BITS; + break; + } + + switch (size) { case RC_MEMSIZE_BIT_0: case RC_MEMSIZE_BIT_1: case RC_MEMSIZE_BIT_2: @@ -69,7 +81,6 @@ rc_term_t* rc_parse_term(const char** memaddr, rc_parse_state_t* parse) { } else { self->operand2.type = RC_OPERAND_FP; - self->operand2.size = RC_MEMSIZE_8_BITS; self->operand2.fp_value = 1.0; } diff --git a/src/rcheevos/trigger.c b/src/rcheevos/trigger.c index 28723bc6..90c33881 100644 --- a/src/rcheevos/trigger.c +++ b/src/rcheevos/trigger.c @@ -55,6 +55,8 @@ rc_trigger_t* rc_parse_trigger(void* buffer, const char* memaddr, lua_State* L, rc_init_parse_state(&parse, buffer, L, funcs_ndx); self = RC_ALLOC(rc_trigger_t, &parse); + rc_init_parse_state_memrefs(&parse, &self->memrefs); + rc_parse_trigger_internal(self, &memaddr, &parse); rc_destroy_parse_state(&parse); @@ -65,6 +67,8 @@ int rc_test_trigger(rc_trigger_t* self, rc_peek_t peek, void* ud, lua_State* L) int ret, reset; rc_condset_t* condset; + rc_update_memref_values(self->memrefs, peek, ud); + reset = 0; ret = self->requirement != 0 ? rc_test_condset(self->requirement, &reset, peek, ud, L) : 1; condset = self->alternative; diff --git a/src/rcheevos/value.c b/src/rcheevos/value.c index 412017ea..7320414a 100644 --- a/src/rcheevos/value.c +++ b/src/rcheevos/value.c @@ -42,6 +42,8 @@ rc_value_t* rc_parse_value(void* buffer, const char* memaddr, lua_State* L, int rc_init_parse_state(&parse, buffer, L, funcs_ndx); self = RC_ALLOC(rc_value_t, &parse); + rc_init_parse_state_memrefs(&parse, &self->memrefs); + rc_parse_value_internal(self, &memaddr, &parse); rc_destroy_parse_state(&parse); @@ -52,6 +54,8 @@ unsigned rc_evaluate_value(rc_value_t* self, rc_peek_t peek, void* ud, lua_State rc_expression_t* exp; unsigned value, max; + rc_update_memref_values(self->memrefs, peek, ud); + exp = self->expressions; max = rc_evaluate_expression(exp, peek, ud, L); diff --git a/test/rcheevos-test.vcxproj b/test/rcheevos-test.vcxproj index 1c2d7a4c..cc52c846 100644 --- a/test/rcheevos-test.vcxproj +++ b/test/rcheevos-test.vcxproj @@ -127,6 +127,7 @@ + diff --git a/test/rcheevos-test.vcxproj.filters b/test/rcheevos-test.vcxproj.filters index 078377a7..42fc026f 100644 --- a/test/rcheevos-test.vcxproj.filters +++ b/test/rcheevos-test.vcxproj.filters @@ -142,6 +142,9 @@ rcheevos + + rcheevos + diff --git a/test/test.c b/test/test.c index 30dfa5e1..22ae82d2 100644 --- a/test/test.c +++ b/test/test.c @@ -41,9 +41,12 @@ static unsigned peek(unsigned address, unsigned num_bytes, void* ud) { static void parse_operand(rc_operand_t* self, const char** memaddr) { rc_parse_state_t parse; + char buffer[256]; + rc_memref_value_t* memrefs; int ret; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); ret = rc_parse_operand(self, memaddr, 1, &parse); rc_destroy_parse_state(&parse); @@ -53,8 +56,14 @@ static void parse_operand(rc_operand_t* self, const char** memaddr) { static void comp_operand(rc_operand_t* self, char expected_type, char expected_size, unsigned expected_address) { assert(expected_type == self->type); - assert(expected_size == self->size); - assert(expected_address == self->value); + switch (expected_type) { + case RC_OPERAND_ADDRESS: + case RC_OPERAND_DELTA: + case RC_OPERAND_PRIOR: + assert(expected_size == self->memref->memref.size); + assert(expected_address == self->memref->memref.address); + break; + } } static void parse_comp_operand(const char* memaddr, char expected_type, char expected_size, unsigned expected_value) { @@ -68,8 +77,10 @@ static void parse_error_operand(const char* memaddr, int valid_chars) { rc_parse_state_t parse; int ret; const char* begin = memaddr; + rc_memref_value_t* memrefs; rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); ret = rc_parse_operand(&self, &memaddr, 1, &parse); rc_destroy_parse_state(&parse); @@ -80,16 +91,214 @@ static void parse_error_operand(const char* memaddr, int valid_chars) { static void parse_comp_operand_value(const char* memaddr, memory_t* memory, unsigned expected_value) { rc_operand_t self; rc_parse_state_t parse; + rc_memref_value_t* memrefs; + char buffer[512]; unsigned value; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); rc_parse_operand(&self, &memaddr, 1, &parse); rc_destroy_parse_state(&parse); + rc_update_memref_values(memrefs, peek, memory); value = rc_evaluate_operand(&self, peek, memory, NULL); assert(value == expected_value); } +static unsigned evaluate_operand(rc_operand_t* op, memory_t* memory, rc_memref_value_t* memrefs) +{ + rc_update_memref_values(memrefs, peek, memory); + return rc_evaluate_operand(op, peek, memory, NULL); +} + +static void test_memref(void) { + char buffer[512]; + { + /*------------------------------------------------------------------------ + TestAllocMemrefValueDuplicatesSizing + ------------------------------------------------------------------------*/ + rc_parse_state_t parse; + rc_init_parse_state(&parse, buffer, 0, 0); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 0); + assert(parse.scratch.memref_count == 1); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 1); /* BCD will not match */ + assert(parse.scratch.memref_count == 2); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_16_BITS, 0); /* differing size will not match */ + assert(parse.scratch.memref_count == 3); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_LOW, 0); /* differing size will not match */ + assert(parse.scratch.memref_count == 4); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_BIT_2, 0); /* differing size will not match */ + assert(parse.scratch.memref_count == 5); + + rc_alloc_memref_value(&parse, 2, RC_MEMSIZE_8_BITS, 0); /* differing address will not match */ + assert(parse.scratch.memref_count == 6); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 0); /* match */ + assert(parse.scratch.memref_count == 6); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 1); /* match */ + assert(parse.scratch.memref_count == 6); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_16_BITS, 0); /* match */ + assert(parse.scratch.memref_count == 6); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_BIT_2, 0); /* match */ + assert(parse.scratch.memref_count == 6); + + rc_alloc_memref_value(&parse, 2, RC_MEMSIZE_8_BITS, 0); /* match */ + assert(parse.scratch.memref_count == 6); + + rc_destroy_parse_state(&parse); + } + + { + /*------------------------------------------------------------------------ + TestAllocMemrefValueGrowthSizing + ------------------------------------------------------------------------*/ + int i; + rc_parse_state_t parse; + rc_init_parse_state(&parse, buffer, 0, 0); + + for (i = 0; i < 100; i++) { + rc_alloc_memref_value(&parse, i, RC_MEMSIZE_8_BITS, 0); + } + assert(parse.scratch.memref_count == 100); + + rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 0); + assert(parse.scratch.memref_count == 100); + + rc_alloc_memref_value(&parse, 25, RC_MEMSIZE_8_BITS, 0); + assert(parse.scratch.memref_count == 100); + + rc_alloc_memref_value(&parse, 50, RC_MEMSIZE_8_BITS, 0); + assert(parse.scratch.memref_count == 100); + + rc_alloc_memref_value(&parse, 75, RC_MEMSIZE_8_BITS, 0); + assert(parse.scratch.memref_count == 100); + + rc_alloc_memref_value(&parse, 99, RC_MEMSIZE_8_BITS, 0); + assert(parse.scratch.memref_count == 100); + + rc_destroy_parse_state(&parse); + } + + { + /*------------------------------------------------------------------------ + TestAllocMemrefValueDuplicates + ------------------------------------------------------------------------*/ + rc_parse_state_t parse; + rc_memref_value_t* memrefs; + rc_memref_value_t* memref1; + rc_memref_value_t* memref2; + rc_memref_value_t* memref3; + rc_memref_value_t* memref4; + rc_memref_value_t* memref5; + rc_memref_value_t* memref6; + rc_memref_value_t* memrefX; + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); + + memref1 = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 0); + assert(memref1->memref.address == 1); + assert(memref1->memref.size == RC_MEMSIZE_8_BITS); + assert(memref1->memref.is_bcd == 0); + assert(memref1->value == 0); + assert(memref1->previous == 0); + assert(memref1->prior == 0); + assert(memref1->next == 0); + + memref2 = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 1); /* BCD will not match */ + memref3 = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_16_BITS, 0); /* differing size will not match */ + memref4 = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_LOW, 0); /* differing size will not match */ + memref5 = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_BIT_2, 0); /* differing size will not match */ + memref6 = rc_alloc_memref_value(&parse, 2, RC_MEMSIZE_8_BITS, 0); /* differing address will not match */ + + memrefX = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 0); /* match */ + assert(memrefX == memref1); + + memrefX = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 1); /* match */ + assert(memrefX == memref2); + + memrefX = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_16_BITS, 0); /* match */ + assert(memrefX == memref3); + + memrefX = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_BIT_2, 0); /* match */ + assert(memrefX == memref5); + + memrefX = rc_alloc_memref_value(&parse, 2, RC_MEMSIZE_8_BITS, 0); /* match */ + assert(memrefX == memref6); + + rc_destroy_parse_state(&parse); + } + + { + /*------------------------------------------------------------------------ + TestUpdateMemrefValues + ------------------------------------------------------------------------*/ + rc_parse_state_t parse; + rc_memref_value_t* memrefs; + rc_memref_value_t* memref1; + rc_memref_value_t* memref2; + + unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; + memory_t memory; + memory.ram = ram; + memory.size = sizeof(ram); + + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); + + memref1 = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_8_BITS, 0); + memref2 = rc_alloc_memref_value(&parse, 2, RC_MEMSIZE_8_BITS, 0); + + rc_update_memref_values(memrefs, peek, &memory); + + assert(memref1->value == 0x12); + assert(memref1->previous == 0); + assert(memref1->prior == 0); + assert(memref2->value == 0x34); + assert(memref2->previous == 0); + assert(memref2->prior == 0); + + ram[1] = 3; + rc_update_memref_values(memrefs, peek, &memory); + + assert(memref1->value == 3); + assert(memref1->previous == 0x12); + assert(memref1->prior == 0x12); + assert(memref2->value == 0x34); + assert(memref2->previous == 0x34); + assert(memref2->prior == 0); + + ram[1] = 5; + rc_update_memref_values(memrefs, peek, &memory); + + assert(memref1->value == 5); + assert(memref1->previous == 3); + assert(memref1->prior == 3); + assert(memref2->value == 0x34); + assert(memref2->previous == 0x34); + assert(memref2->prior == 0); + + ram[2] = 7; + rc_update_memref_values(memrefs, peek, &memory); + + assert(memref1->value == 5); + assert(memref1->previous == 5); + assert(memref1->prior == 3); + assert(memref2->value == 7); + assert(memref2->previous == 0x34); + assert(memref2->prior == 0x34); + + rc_destroy_parse_state(&parse); + } +} + static void test_operand(void) { { /*------------------------------------------------------------------------ @@ -293,33 +502,36 @@ static void test_operand(void) { rc_operand_t op; const char* memaddr; rc_parse_state_t parse; + char buffer[256]; + rc_memref_value_t* memrefs; memory.ram = ram; memory.size = sizeof(ram); memaddr = "d0xh1"; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); rc_parse_operand(&op, &memaddr, 1, &parse); rc_destroy_parse_state(&parse); - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x00); /* first call gets uninitialized value */ - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x12); /* second gets current value */ + assert(evaluate_operand(&op, &memory, memrefs) == 0x00); /* first call gets uninitialized value */ + assert(evaluate_operand(&op, &memory, memrefs) == 0x12); /* second gets current value */ /* RC_OPERAND_DELTA is always one frame behind */ ram[1] = 0x13; - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x12U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x12U); ram[1] = 0x14; - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x13U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x13U); ram[1] = 0x15; - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x14U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x14U); ram[1] = 0x16; - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x15U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x15U); - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x16U); - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x16U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x16U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x16U); } { @@ -332,35 +544,38 @@ static void test_operand(void) { rc_operand_t op; const char* memaddr; rc_parse_state_t parse; + char buffer[256]; + rc_memref_value_t* memrefs; memory.ram = ram; memory.size = sizeof(ram); memaddr = "p0xh1"; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); rc_parse_operand(&op, &memaddr, 1, &parse); rc_destroy_parse_state(&parse); /* RC_OPERAND_PRIOR only updates when the memory value changes */ - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x00); /* first call gets uninitialized value */ - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x00); /* value only changes when memory changes */ + assert(evaluate_operand(&op, &memory, memrefs) == 0x00); /* first call gets uninitialized value */ + assert(evaluate_operand(&op, &memory, memrefs) == 0x00); /* value only changes when memory changes */ ram[1] = 0x13; - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x12U); - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x12U); - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x12U); - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x12U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x12U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x12U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x12U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x12U); ram[1] = 0x14; - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x13U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x13U); ram[1] = 0x15; - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x14U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x14U); ram[1] = 0x16; - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x15U); - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x15U); - assert(rc_evaluate_operand(&op, peek, &memory, NULL) == 0x15U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x15U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x15U); + assert(evaluate_operand(&op, &memory, memrefs) == 0x15U); } } @@ -384,8 +599,11 @@ static void parse_comp_condition( ) { rc_condition_t* self; rc_parse_state_t parse; + rc_memref_value_t* memrefs; + char buffer[512]; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); self = rc_parse_condition(&memaddr, &parse); rc_destroy_parse_state(&parse); @@ -399,20 +617,29 @@ static void parse_comp_condition( static void parse_test_condition(const char* memaddr, memory_t* memory, int value) { rc_condition_t* self; rc_parse_state_t parse; + char buffer[512]; + rc_memref_value_t* memrefs; int ret; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); self = rc_parse_condition(&memaddr, &parse); rc_destroy_parse_state(&parse); assert(parse.offset >= 0); assert(*memaddr == 0); + rc_update_memref_values(memrefs, peek, memory); ret = rc_test_condition(self, 0, peek, memory, NULL); assert((ret && value) || (!ret && !value)); } +static int evaluate_condition(rc_condition_t* cond, memory_t* memory, rc_memref_value_t* memrefs) { + rc_update_memref_values(memrefs, peek, memory); + return rc_test_condition(cond, 0, peek, memory, NULL); +} + static void test_condition(void) { { /*------------------------------------------------------------------------ @@ -636,9 +863,12 @@ static void test_condition(void) { memory_t memory; rc_condition_t* cond; rc_parse_state_t parse; + char buffer[512]; + rc_memref_value_t* memrefs; const char* cond_str = "0xH0001>d0xH0001"; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); cond = rc_parse_condition(&cond_str, &parse); rc_destroy_parse_state(&parse); @@ -648,18 +878,18 @@ static void test_condition(void) { memory.size = sizeof(ram); /* initial delta value is 0, 0x12 > 0 */ - assert(rc_test_condition(cond, 0, peek, &memory, NULL) == 1); + assert(evaluate_condition(cond, &memory, memrefs) == 1); /* delta value is now 0x12, 0x12 = 0x12 */ - assert(rc_test_condition(cond, 0, peek, &memory, NULL) == 0); + assert(evaluate_condition(cond, &memory, memrefs) == 0); /* delta value is now 0x12, 0x11 < 0x12 */ ram[1] = 0x11; - assert(rc_test_condition(cond, 0, peek, &memory, NULL) == 0); + assert(evaluate_condition(cond, &memory, memrefs) == 0); /* delta value is now 0x13, 0x12 > 0x11 */ ram[1] = 0x12; - assert(rc_test_condition(cond, 0, peek, &memory, NULL) == 1); + assert(evaluate_condition(cond, &memory, memrefs) == 1); } } @@ -1415,6 +1645,7 @@ static void test_trigger(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_trigger_t* trigger; + char buffer[2048]; memory.ram = ram; memory.size = sizeof(ram); @@ -1577,6 +1808,7 @@ static void test_trigger(void) { unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; memory_t memory; rc_trigger_t* trigger; + char buffer[2048]; rc_condset_t* condset; @@ -1847,8 +2079,11 @@ static void test_trigger(void) { static void parse_comp_term(const char* memaddr, char expected_var_size, unsigned expected_address, int is_bcd, int is_const) { rc_term_t* self; rc_parse_state_t parse; + rc_memref_value_t* memrefs; + char buffer[512]; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); self = rc_parse_term(&memaddr, &parse); rc_destroy_parse_state(&parse); @@ -1859,9 +2094,9 @@ static void parse_comp_term(const char* memaddr, char expected_var_size, unsigne assert(self->operand1.type == RC_OPERAND_CONST); } else { - assert(self->operand1.size == expected_var_size); - assert(self->operand1.value == expected_address); - assert(self->operand1.is_bcd == is_bcd); + assert(self->operand1.memref->memref.size == expected_var_size); + assert(self->operand1.memref->memref.address == expected_address); + assert(self->operand1.memref->memref.is_bcd == is_bcd); } assert(self->invert == 0); assert(self->operand2.value == 0U); @@ -1870,16 +2105,19 @@ static void parse_comp_term(const char* memaddr, char expected_var_size, unsigne static void parse_comp_term_fp(const char* memaddr, char expected_var_size, unsigned expected_address, double fp) { rc_term_t* self; rc_parse_state_t parse; + rc_memref_value_t* memrefs; + char buffer[512]; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); self = rc_parse_term(&memaddr, &parse); rc_destroy_parse_state(&parse); assert(parse.offset >= 0); assert(*memaddr == 0); - assert(self->operand1.size == expected_var_size); - assert(self->operand1.value == expected_address); + assert(self->operand1.memref->memref.size == expected_var_size); + assert(self->operand1.memref->memref.address == expected_address); assert(self->operand2.type == RC_OPERAND_FP); assert(self->operand2.fp_value == fp); } @@ -1887,31 +2125,38 @@ static void parse_comp_term_fp(const char* memaddr, char expected_var_size, unsi static void parse_comp_term_mem(const char* memaddr, char expected_size_1, unsigned expected_address_1, char expected_size_2, unsigned expected_address_2) { rc_term_t* self; rc_parse_state_t parse; + rc_memref_value_t* memrefs; + char buffer[512]; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); self = rc_parse_term(&memaddr, &parse); rc_destroy_parse_state(&parse); assert(parse.offset >= 0); assert(*memaddr == 0); - assert(self->operand1.size == expected_size_1); - assert(self->operand1.value == expected_address_1); - assert(self->operand2.size == expected_size_2); - assert(self->operand2.value == expected_address_2); + assert(self->operand1.memref->memref.size == expected_size_1); + assert(self->operand1.memref->memref.address == expected_address_1); + assert(self->operand2.memref->memref.size == expected_size_2); + assert(self->operand2.memref->memref.address == expected_address_2); } static void parse_comp_term_value(const char* memaddr, memory_t* memory, unsigned value) { rc_term_t* self; rc_parse_state_t parse; + rc_memref_value_t* memrefs; + char buffer[512]; - rc_init_parse_state(&parse, 0, 0, 0); + rc_init_parse_state(&parse, buffer, 0, 0); + rc_init_parse_state_memrefs(&parse, &memrefs); self = rc_parse_term(&memaddr, &parse); rc_destroy_parse_state(&parse); assert(parse.offset >= 0); assert(*memaddr == 0); + rc_update_memref_values(memrefs, peek, memory); assert(rc_evaluate_term(self, peek, memory, NULL) == value); } @@ -3216,6 +3461,7 @@ static void test_lua(void) { } int main(void) { + test_memref(); test_operand(); test_condition(); test_trigger(); From b27890258a4b9d66864f3178e2e183abaacf1470 Mon Sep 17 00:00:00 2001 From: Jamiras Date: Wed, 12 Dec 2018 19:17:56 -0700 Subject: [PATCH 04/11] add unit test --- include/rcheevos.h | 6 +++--- src/rcheevos/alloc.c | 1 + src/rcheevos/internal.h | 1 - test/Makefile | 2 +- test/test.c | 48 ++++++++++++++++++++++++++++++----------- 5 files changed, 41 insertions(+), 17 deletions(-) diff --git a/include/rcheevos.h b/include/rcheevos.h index 2fefb9ca..c15f7259 100644 --- a/include/rcheevos.h +++ b/include/rcheevos.h @@ -192,9 +192,6 @@ enum { typedef struct rc_condition_t rc_condition_t; struct rc_condition_t { - /* The next condition in the chain. */ - rc_condition_t* next; - /* The condition's operands. */ rc_operand_t operand1; rc_operand_t operand2; @@ -204,6 +201,9 @@ struct rc_condition_t { /* Number of hits so far. */ unsigned current_hits; + /* The next condition in the chain. */ + rc_condition_t* next; + /** * Set if the condition needs to processed as part of the "check if paused" * pass diff --git a/src/rcheevos/alloc.c b/src/rcheevos/alloc.c index f5fcf33c..83b9ec71 100644 --- a/src/rcheevos/alloc.c +++ b/src/rcheevos/alloc.c @@ -1,6 +1,7 @@ #include "internal.h" #include +#include void* rc_alloc(void* pointer, int* offset, int size, int alignment, rc_scratch_t* scratch) { void* ptr; diff --git a/src/rcheevos/internal.h b/src/rcheevos/internal.h index a27c5e97..abdb3983 100644 --- a/src/rcheevos/internal.h +++ b/src/rcheevos/internal.h @@ -80,7 +80,6 @@ void rc_parse_value_internal(rc_value_t* self, const char** memaddr, rc_parse_st void rc_parse_lboard_internal(rc_lboard_t* self, const char* memaddr, rc_parse_state_t* parse); -const char* rc_parse_line(const char* line, const char** end); void rc_parse_richpresence_internal(rc_richpresence_t* self, const char* script, rc_parse_state_t* parse); #endif /* INTERNAL_H */ diff --git a/test/Makefile b/test/Makefile index 4dc28dd1..65d11297 100644 --- a/test/Makefile +++ b/test/Makefile @@ -4,7 +4,7 @@ LUA_SRC=lua/src OBJ=$(RC_SRC)/trigger.o $(RC_SRC)/condset.o $(RC_SRC)/condition.o $(RC_SRC)/operand.o \ $(RC_SRC)/term.o $(RC_SRC)/expression.o $(RC_SRC)/value.o $(RC_SRC)/lboard.o \ - $(RC_SRC)/alloc.o $(RC_SRC)/format.o $(RC_SRC)/richpresence.o \ + $(RC_SRC)/alloc.o $(RC_SRC)/memref.o $(RC_SRC)/format.o $(RC_SRC)/richpresence.o \ $(RC_URL_SRC)/url.o \ $(LUA_SRC)/lapi.o $(LUA_SRC)/lcode.o $(LUA_SRC)/lctype.o $(LUA_SRC)/ldebug.o \ $(LUA_SRC)/ldo.o $(LUA_SRC)/ldump.o $(LUA_SRC)/lfunc.o $(LUA_SRC)/lgc.o $(LUA_SRC)/llex.o \ diff --git a/test/test.c b/test/test.c index 22ae82d2..e7e4488d 100644 --- a/test/test.c +++ b/test/test.c @@ -227,6 +227,9 @@ static void test_memref(void) { memrefX = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_16_BITS, 0); /* match */ assert(memrefX == memref3); + memrefX = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_LOW, 0); /* match */ + assert(memrefX == memref4); + memrefX = rc_alloc_memref_value(&parse, 1, RC_MEMSIZE_BIT_2, 0); /* match */ assert(memrefX == memref5); @@ -579,17 +582,6 @@ static void test_operand(void) { } } -static void parse_condition(rc_condition_t* self, const char* memaddr) { - rc_parse_state_t parse; - - rc_init_parse_state(&parse, 0, 0, 0); - rc_parse_condition(&memaddr, &parse); - rc_destroy_parse_state(&parse); - - assert(parse.offset >= 0); - assert(*memaddr == 0); -} - static void parse_comp_condition( const char* memaddr, char expected_type, char expected_left_type, char expected_left_size, unsigned expected_left_value, @@ -2074,6 +2066,38 @@ static void test_trigger(void) { ram[0] = 2; /* trigger win condition. alt group has no normal conditions, it should be considered false */ comp_trigger(trigger, &memory, 0); } + + { + /*------------------------------------------------------------------------ + TestDeltaUpdatedInPauseIf + ------------------------------------------------------------------------*/ + + unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; + memory_t memory; + rc_trigger_t* trigger; + + memory.ram = ram; + memory.size = sizeof(ram); + + parse_trigger(&trigger, buffer, "P:0xH0001=18_d0xH0002=52"); + comp_trigger(trigger, &memory, 0); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 1U); /* PauseIf true */ + assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 0U); /* delta = 0, not true */ + + ram[2] = 52; + comp_trigger(trigger, &memory, 0); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 2U); /* PauseIf true */ + assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 0U); /* delta = 0, but paused */ + + comp_trigger(trigger, &memory, 0); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 3U); /* PauseIf true */ + assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 0U); /* delta = 52, but paused */ + + ram[1] = 0; + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 0U); /* PauseIf false */ + assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 1U); /* delta = 52, count it */ + } } static void parse_comp_term(const char* memaddr, char expected_var_size, unsigned expected_address, int is_bcd, int is_const) { @@ -2099,7 +2123,7 @@ static void parse_comp_term(const char* memaddr, char expected_var_size, unsigne assert(self->operand1.memref->memref.is_bcd == is_bcd); } assert(self->invert == 0); - assert(self->operand2.value == 0U); + assert(self->operand2.fp_value == 1.0); } static void parse_comp_term_fp(const char* memaddr, char expected_var_size, unsigned expected_address, double fp) { From 98aafb12ebfbbd544d69101ddd1263fddf096ee6 Mon Sep 17 00:00:00 2001 From: Jamiras Date: Thu, 13 Dec 2018 16:23:45 -0700 Subject: [PATCH 05/11] use integer terms for non-rational floats --- src/rcheevos/operand.c | 9 ++++++++- src/rcheevos/term.c | 6 +++--- test/test.c | 13 ++++++++++--- 3 files changed, 21 insertions(+), 7 deletions(-) diff --git a/src/rcheevos/operand.c b/src/rcheevos/operand.c index 46932cb8..e0a328b3 100644 --- a/src/rcheevos/operand.c +++ b/src/rcheevos/operand.c @@ -2,6 +2,7 @@ #include #include +#include #ifndef RC_DISABLE_LUA @@ -268,13 +269,19 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, rc_pa case '+': case '-': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': - self->type = RC_OPERAND_FP; self->fp_value = strtod(aux, &end); if (end == aux) { return RC_INVALID_FP_OPERAND; } + if (floor(self->fp_value) == self->fp_value) { + self->type = RC_OPERAND_CONST; + self->value = (unsigned)floor(self->fp_value); + } + else { + self->type = RC_OPERAND_FP; + } aux = end; break; diff --git a/src/rcheevos/term.c b/src/rcheevos/term.c index 3030ee84..de4e01e0 100644 --- a/src/rcheevos/term.c +++ b/src/rcheevos/term.c @@ -80,8 +80,8 @@ rc_term_t* rc_parse_term(const char** memaddr, rc_parse_state_t* parse) { } } else { - self->operand2.type = RC_OPERAND_FP; - self->operand2.fp_value = 1.0; + self->operand2.type = RC_OPERAND_CONST; + self->operand2.value = 1; } *memaddr = aux; @@ -95,5 +95,5 @@ unsigned rc_evaluate_term(rc_term_t* self, rc_peek_t peek, void* ud, lua_State* return value * (rc_evaluate_operand(&self->operand2, peek, ud, L) ^ self->invert); } - return (unsigned)(value * self->operand2.fp_value); + return (unsigned)((double)value * self->operand2.fp_value); } diff --git a/test/test.c b/test/test.c index e7e4488d..653474ef 100644 --- a/test/test.c +++ b/test/test.c @@ -2123,7 +2123,8 @@ static void parse_comp_term(const char* memaddr, char expected_var_size, unsigne assert(self->operand1.memref->memref.is_bcd == is_bcd); } assert(self->invert == 0); - assert(self->operand2.fp_value == 1.0); + assert(self->operand2.type == RC_OPERAND_CONST); + assert(self->operand2.value == 1); } static void parse_comp_term_fp(const char* memaddr, char expected_var_size, unsigned expected_address, double fp) { @@ -2142,8 +2143,14 @@ static void parse_comp_term_fp(const char* memaddr, char expected_var_size, unsi assert(self->operand1.memref->memref.size == expected_var_size); assert(self->operand1.memref->memref.address == expected_address); - assert(self->operand2.type == RC_OPERAND_FP); - assert(self->operand2.fp_value == fp); + if (self->operand2.type == RC_OPERAND_CONST) { + assert(self->operand2.type == RC_OPERAND_CONST); + assert(self->operand2.value == (int)fp); + } + else { + assert(self->operand2.type == RC_OPERAND_FP); + assert(self->operand2.fp_value == fp); + } } static void parse_comp_term_mem(const char* memaddr, char expected_size_1, unsigned expected_address_1, char expected_size_2, unsigned expected_address_2) { From 465bc3c31bd0cd4a4abd0af33ad6d272cb1479cf Mon Sep 17 00:00:00 2001 From: Jamiras Date: Wed, 13 Feb 2019 19:11:17 -0700 Subject: [PATCH 06/11] support empty alt groups --- src/rcheevos/condset.c | 6 ++ test/test.c | 140 +++++++++++++++++++++++++++++++++++++++++ 2 files changed, 146 insertions(+) diff --git a/src/rcheevos/condset.c b/src/rcheevos/condset.c index 13d086f9..30a15926 100644 --- a/src/rcheevos/condset.c +++ b/src/rcheevos/condset.c @@ -32,6 +32,12 @@ rc_condset_t* rc_parse_condset(int* ret, void* buffer, rc_scratch_t* scratch, co self->has_pause = 0; next = &self->conditions; + if (**memaddr == 'S' || **memaddr == 's' || !**memaddr) { + // empty group - editor allows it, so we have to support it + *next = 0; + return self; + } + for (;;) { *next = rc_parse_condition(ret, buffer, scratch, memaddr, L, funcs_ndx); diff --git a/test/test.c b/test/test.c index dbebe736..d25f84c1 100644 --- a/test/test.c +++ b/test/test.c @@ -1325,6 +1325,24 @@ static void test_trigger(void) { assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 3U); } + { + /*------------------------------------------------------------------------ + TestAddSourceAddHits + ------------------------------------------------------------------------*/ + + unsigned char ram[] = { 0x00, 0x12, 0x34, 0xAB, 0x56 }; + memory_t memory; + rc_trigger_t* trigger; + + memory.ram = ram; + memory.size = sizeof(ram); + + parse_trigger(&trigger, buffer, "A:0xH0001=0_C:0xH0002=70_0xH0000=0(2)"); /* repeated(2, (byte(1) + byte(2) == 70) || byte(0) == 0) */ + comp_trigger(trigger, &memory, 1); // both conditions are true - addhits should match required 2 hits + assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 1U); // 0x12+0x34 = 0x46 - true! + assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 1U); // 0 = 0 - true! + } + { /*------------------------------------------------------------------------ TestAndNext @@ -1713,6 +1731,128 @@ static void test_trigger(void) { assert(condset_get_cond(trigger_get_set(trigger, 2), 0)->current_hits == 3U); } + { + /*------------------------------------------------------------------------ + TestEmptyCore + ------------------------------------------------------------------------*/ + + unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; + memory_t memory; + rc_trigger_t* trigger; + char buffer[2048]; + + memory.ram = ram; + memory.size = sizeof(ram); + + parse_trigger(&trigger, buffer, "S0xH0002=2S0xL0004=4"); + + /* core implicitly true, neither alt true */ + comp_trigger(trigger, &memory, 0); + assert(condset_get_cond(trigger_get_set(trigger, 1), 0)->current_hits == 0U); + assert(condset_get_cond(trigger_get_set(trigger, 2), 0)->current_hits == 0U); + + ram[2] = 2; /* core and first alt true */ + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 1), 0)->current_hits == 1U); + assert(condset_get_cond(trigger_get_set(trigger, 2), 0)->current_hits == 0U); + + ram[4] = 4; /* core and both alts true */ + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 1), 0)->current_hits == 2U); + assert(condset_get_cond(trigger_get_set(trigger, 2), 0)->current_hits == 1U); + + ram[2] = 0; /* core and second alt true */ + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 1), 0)->current_hits == 2U); + assert(condset_get_cond(trigger_get_set(trigger, 2), 0)->current_hits == 2U); + } + + { + /*------------------------------------------------------------------------ + TestEmptyAlt + ------------------------------------------------------------------------*/ + + unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; + memory_t memory; + rc_trigger_t* trigger; + char buffer[2048]; + + memory.ram = ram; + memory.size = sizeof(ram); + + parse_trigger(&trigger, buffer, "0xH0002=2SS0xL0004=4"); + + /* core false, first alt implicitly true */ + comp_trigger(trigger, &memory, 0); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 0U); + assert(condset_get_cond(trigger_get_set(trigger, 2), 0)->current_hits == 0U); + + ram[2] = 2; /* core and first alt true */ + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 1U); + assert(condset_get_cond(trigger_get_set(trigger, 2), 0)->current_hits == 0U); + + ram[4] = 4; /* core and both alts true */ + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 2U); + assert(condset_get_cond(trigger_get_set(trigger, 2), 0)->current_hits == 1U); + } + + { + /*------------------------------------------------------------------------ + TestEmptyLastAlt + ------------------------------------------------------------------------*/ + + unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; + memory_t memory; + rc_trigger_t* trigger; + char buffer[2048]; + + memory.ram = ram; + memory.size = sizeof(ram); + + parse_trigger(&trigger, buffer, "0xH0002=2S0xL0004=4S"); + + /* core false, second alt implicitly true */ + comp_trigger(trigger, &memory, 0); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 0U); + assert(condset_get_cond(trigger_get_set(trigger, 1), 0)->current_hits == 0U); + + ram[2] = 2; /* core and second alt true */ + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 1U); + assert(condset_get_cond(trigger_get_set(trigger, 1), 0)->current_hits == 0U); + + ram[4] = 4; /* core and both alts true */ + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 2U); + assert(condset_get_cond(trigger_get_set(trigger, 1), 0)->current_hits == 1U); + } + + { + /*------------------------------------------------------------------------ + TestEmptyAllAlts + ------------------------------------------------------------------------*/ + + unsigned char ram[] = {0x00, 0x12, 0x34, 0xAB, 0x56}; + memory_t memory; + rc_trigger_t* trigger; + char buffer[2048]; + + memory.ram = ram; + memory.size = sizeof(ram); + + parse_trigger(&trigger, buffer, "0xH0002=2SS"); + + /* core false, all alts implicitly true */ + comp_trigger(trigger, &memory, 0); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 0U); + + ram[2] = 2; /* core and all alts true */ + comp_trigger(trigger, &memory, 1); + assert(condset_get_cond(trigger_get_set(trigger, 0), 0)->current_hits == 1U); + } + { /*------------------------------------------------------------------------ TestResetIfInAltGroup From 25dc737f15dce7b06232a84d4cdf418fe90788fa Mon Sep 17 00:00:00 2001 From: meleu Date: Sun, 24 Mar 2019 19:38:43 -0300 Subject: [PATCH 07/11] prevent "always false" alerts When I submitted PR https://github.com/libretro/RetroArch/pull/8501 the LGTM tool triggered some "always false" alerts. https://lgtm.com/projects/g/libretro/RetroArch/rev/pr-24ba548ca61b83099b7119300b3a4b5d07a0cd63 --- src/rcheevos/operand.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/rcheevos/operand.c b/src/rcheevos/operand.c index 941ab75f..4843641f 100644 --- a/src/rcheevos/operand.c +++ b/src/rcheevos/operand.c @@ -118,7 +118,7 @@ static int rc_parse_operand_memory(rc_operand_t* self, const char** memaddr) { break; } - value = (unsigned)strtoul(aux, &end, 16); + value = strtoul(aux, &end, 16); if (end == aux) { return RC_INVALID_MEMORY_OPERAND; @@ -213,7 +213,7 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, lua_S switch (*aux) { case 'h': case 'H': - value = (unsigned)strtoul(++aux, &end, 16); + value = strtoul(++aux, &end, 16); if (end == aux) { return RC_INVALID_CONST_OPERAND; @@ -230,7 +230,7 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, lua_S break; case 'v': case 'V': - value = (unsigned)strtoul(++aux, &end, 10); + value = strtoul(++aux, &end, 10); if (end == aux) { return RC_INVALID_CONST_OPERAND; From 61fb774c66ee76546487237aceafff14e92b2a67 Mon Sep 17 00:00:00 2001 From: Jamiras Date: Tue, 26 Mar 2019 07:17:05 -0600 Subject: [PATCH 08/11] change to c-style comments --- src/rcheevos/condset.c | 2 +- src/rcheevos/memref.c | 4 ++-- test/test.c | 6 +++--- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/rcheevos/condset.c b/src/rcheevos/condset.c index e89eab2c..c2d59a26 100644 --- a/src/rcheevos/condset.c +++ b/src/rcheevos/condset.c @@ -33,7 +33,7 @@ rc_condset_t* rc_parse_condset(const char** memaddr, rc_parse_state_t* parse) { next = &self->conditions; if (**memaddr == 'S' || **memaddr == 's' || !**memaddr) { - // empty group - editor allows it, so we have to support it + /* empty group - editor allows it, so we have to support it */ *next = 0; return self; } diff --git a/src/rcheevos/memref.c b/src/rcheevos/memref.c index ff6622f2..b4565bb6 100644 --- a/src/rcheevos/memref.c +++ b/src/rcheevos/memref.c @@ -1,7 +1,7 @@ #include "internal.h" -#include // malloc/realloc -#include // memcpy +#include /* malloc/realloc */ +#include /* memcpy */ rc_memref_value_t* rc_alloc_memref_value(rc_parse_state_t* parse, unsigned address, char size, char is_bcd) { rc_memref_value_t** next_memref_value; diff --git a/test/test.c b/test/test.c index fa2b068f..02f69e1b 100644 --- a/test/test.c +++ b/test/test.c @@ -1585,9 +1585,9 @@ static void test_trigger(void) { memory.size = sizeof(ram); parse_trigger(&trigger, buffer, "A:0xH0001=0_C:0xH0002=70_0xH0000=0(2)"); /* repeated(2, (byte(1) + byte(2) == 70) || byte(0) == 0) */ - comp_trigger(trigger, &memory, 1); // both conditions are true - addhits should match required 2 hits - assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 1U); // 0x12+0x34 = 0x46 - true! - assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 1U); // 0 = 0 - true! + comp_trigger(trigger, &memory, 1); /* both conditions are true - addhits should match required 2 hits */ + assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 1U); /* 0x12+0x34 = 0x46 - true! */ + assert(condset_get_cond(trigger_get_set(trigger, 0), 1)->current_hits == 1U); /* 0 = 0 - true! */ } { From 39b47dbeb333cf4ec43dc0a19584abf615beaa15 Mon Sep 17 00:00:00 2001 From: Jamiras Date: Sat, 20 Apr 2019 09:14:09 -0600 Subject: [PATCH 09/11] C89 support --- include/rcheevos.h | 10 +++++----- src/rcheevos/operand.c | 32 ++++++++++++++++++-------------- src/rcheevos/term.c | 6 +++--- test/test.c | 28 ++++++++++++++-------------- 4 files changed, 40 insertions(+), 36 deletions(-) diff --git a/include/rcheevos.h b/include/rcheevos.h index c15f7259..423be5e6 100644 --- a/include/rcheevos.h +++ b/include/rcheevos.h @@ -150,15 +150,15 @@ typedef struct { /* A value read from memory. */ rc_memref_value_t* memref; - /* A value. */ - unsigned value; + /* An integer value. */ + unsigned num; /* A floating point value. */ - double fp_value; + double dbl; /* A reference to the Lua function that provides the value. */ - int function_ref; - }; + int luafunc; + } value; char type; } diff --git a/src/rcheevos/operand.c b/src/rcheevos/operand.c index 85502fbd..f968e0e1 100644 --- a/src/rcheevos/operand.c +++ b/src/rcheevos/operand.c @@ -21,7 +21,9 @@ extern "C" { static int rc_parse_operand_lua(rc_operand_t* self, const char** memaddr, rc_parse_state_t* parse) { const char* aux = *memaddr; +#ifndef RC_DISABLE_LUA const char* id; +#endif if (*aux++ != '@') { return RC_INVALID_LUA_OPERAND; @@ -31,7 +33,9 @@ static int rc_parse_operand_lua(rc_operand_t* self, const char** memaddr, rc_par return RC_INVALID_LUA_OPERAND; } +#ifndef RC_DISABLE_LUA id = aux; +#endif while (isalnum(*aux) || *aux == '_') { aux++; @@ -52,7 +56,7 @@ static int rc_parse_operand_lua(rc_operand_t* self, const char** memaddr, rc_par return RC_INVALID_LUA_OPERAND; } - self->function_ref = luaL_ref(parse->L, LUA_REGISTRYINDEX); + self->value.luafunc = luaL_ref(parse->L, LUA_REGISTRYINDEX); } #endif /* RC_DISABLE_LUA */ @@ -131,7 +135,7 @@ static int rc_parse_operand_memory(rc_operand_t* self, const char** memaddr, rc_ address = 0xffffffffU; } - self->memref = rc_alloc_memref_value(parse, address, size, is_bcd); + self->value.memref = rc_alloc_memref_value(parse, address, size, is_bcd); if (parse->offset < 0) return parse->offset; @@ -158,7 +162,7 @@ static int rc_parse_operand_trigger(rc_operand_t* self, const char** memaddr, rc } self->type = RC_OPERAND_CONST; - self->value = (unsigned)value; + self->value.num = (unsigned)value; aux = end; break; @@ -191,7 +195,7 @@ static int rc_parse_operand_trigger(rc_operand_t* self, const char** memaddr, rc } self->type = RC_OPERAND_CONST; - self->value = (unsigned)value; + self->value.num = (unsigned)value; aux = end; break; @@ -229,7 +233,7 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, rc_pa } self->type = RC_OPERAND_CONST; - self->value = (unsigned)value; + self->value.num = (unsigned)value; aux = end; break; @@ -246,7 +250,7 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, rc_pa } self->type = RC_OPERAND_CONST; - self->value = (unsigned)value; + self->value.num = (unsigned)value; aux = end; break; @@ -269,15 +273,15 @@ static int rc_parse_operand_term(rc_operand_t* self, const char** memaddr, rc_pa case '+': case '-': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': - self->fp_value = strtod(aux, &end); + self->value.dbl = strtod(aux, &end); if (end == aux) { return RC_INVALID_FP_OPERAND; } - if (floor(self->fp_value) == self->fp_value) { + if (floor(self->value.dbl) == self->value.dbl) { self->type = RC_OPERAND_CONST; - self->value = (unsigned)floor(self->fp_value); + self->value.num = (unsigned)floor(self->value.dbl); } else { self->type = RC_OPERAND_FP; @@ -338,7 +342,7 @@ unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_S switch (self->type) { case RC_OPERAND_CONST: - value = self->value; + value = self->value.num; break; case RC_OPERAND_FP: @@ -349,7 +353,7 @@ unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_S #ifndef RC_DISABLE_LUA if (L != 0) { - lua_rawgeti(L, LUA_REGISTRYINDEX, self->function_ref); + lua_rawgeti(L, LUA_REGISTRYINDEX, self->value.luafunc); lua_pushcfunction(L, rc_luapeek); luapeek.peek = peek; @@ -374,15 +378,15 @@ unsigned rc_evaluate_operand(rc_operand_t* self, rc_peek_t peek, void* ud, lua_S break; case RC_OPERAND_ADDRESS: - value = self->memref->value; + value = self->value.memref->value; break; case RC_OPERAND_DELTA: - value = self->memref->previous; + value = self->value.memref->previous; break; case RC_OPERAND_PRIOR: - value = self->memref->prior; + value = self->value.memref->prior; break; } diff --git a/src/rcheevos/term.c b/src/rcheevos/term.c index de4e01e0..3356a1ee 100644 --- a/src/rcheevos/term.c +++ b/src/rcheevos/term.c @@ -37,7 +37,7 @@ rc_term_t* rc_parse_term(const char** memaddr, rc_parse_state_t* parse) { case RC_OPERAND_ADDRESS: case RC_OPERAND_DELTA: case RC_OPERAND_PRIOR: - size = self->operand2.memref->memref.size; + size = self->operand2.value.memref->memref.size; break; default: size = RC_MEMSIZE_32_BITS; @@ -81,7 +81,7 @@ rc_term_t* rc_parse_term(const char** memaddr, rc_parse_state_t* parse) { } else { self->operand2.type = RC_OPERAND_CONST; - self->operand2.value = 1; + self->operand2.value.num = 1; } *memaddr = aux; @@ -95,5 +95,5 @@ unsigned rc_evaluate_term(rc_term_t* self, rc_peek_t peek, void* ud, lua_State* return value * (rc_evaluate_operand(&self->operand2, peek, ud, L) ^ self->invert); } - return (unsigned)((double)value * self->operand2.fp_value); + return (unsigned)((double)value * self->operand2.value.dbl); } diff --git a/test/test.c b/test/test.c index 02f69e1b..5ac01bed 100644 --- a/test/test.c +++ b/test/test.c @@ -60,8 +60,8 @@ static void comp_operand(rc_operand_t* self, char expected_type, char expected_s case RC_OPERAND_ADDRESS: case RC_OPERAND_DELTA: case RC_OPERAND_PRIOR: - assert(expected_size == self->memref->memref.size); - assert(expected_address == self->memref->memref.address); + assert(expected_size == self->value.memref->memref.size); + assert(expected_address == self->value.memref->memref.address); break; } } @@ -2258,13 +2258,13 @@ static void parse_comp_term(const char* memaddr, char expected_var_size, unsigne assert(self->operand1.type == RC_OPERAND_CONST); } else { - assert(self->operand1.memref->memref.size == expected_var_size); - assert(self->operand1.memref->memref.address == expected_address); - assert(self->operand1.memref->memref.is_bcd == is_bcd); + assert(self->operand1.value.memref->memref.size == expected_var_size); + assert(self->operand1.value.memref->memref.address == expected_address); + assert(self->operand1.value.memref->memref.is_bcd == is_bcd); } assert(self->invert == 0); assert(self->operand2.type == RC_OPERAND_CONST); - assert(self->operand2.value == 1); + assert(self->operand2.value.num == 1); } static void parse_comp_term_fp(const char* memaddr, char expected_var_size, unsigned expected_address, double fp) { @@ -2281,15 +2281,15 @@ static void parse_comp_term_fp(const char* memaddr, char expected_var_size, unsi assert(parse.offset >= 0); assert(*memaddr == 0); - assert(self->operand1.memref->memref.size == expected_var_size); - assert(self->operand1.memref->memref.address == expected_address); + assert(self->operand1.value.memref->memref.size == expected_var_size); + assert(self->operand1.value.memref->memref.address == expected_address); if (self->operand2.type == RC_OPERAND_CONST) { assert(self->operand2.type == RC_OPERAND_CONST); - assert(self->operand2.value == (int)fp); + assert(self->operand2.value.num == (int)fp); } else { assert(self->operand2.type == RC_OPERAND_FP); - assert(self->operand2.fp_value == fp); + assert(self->operand2.value.dbl == fp); } } @@ -2307,10 +2307,10 @@ static void parse_comp_term_mem(const char* memaddr, char expected_size_1, unsig assert(parse.offset >= 0); assert(*memaddr == 0); - assert(self->operand1.memref->memref.size == expected_size_1); - assert(self->operand1.memref->memref.address == expected_address_1); - assert(self->operand2.memref->memref.size == expected_size_2); - assert(self->operand2.memref->memref.address == expected_address_2); + assert(self->operand1.value.memref->memref.size == expected_size_1); + assert(self->operand1.value.memref->memref.address == expected_address_1); + assert(self->operand2.value.memref->memref.size == expected_size_2); + assert(self->operand2.value.memref->memref.address == expected_address_2); } static void parse_comp_term_value(const char* memaddr, memory_t* memory, unsigned value) { From 18619093e8b034afd6a7a24b09631dc596c665d3 Mon Sep 17 00:00:00 2001 From: Jamiras Date: Sat, 20 Apr 2019 14:19:10 -0600 Subject: [PATCH 10/11] RetroArch CXX_BUILD support --- src/rcheevos/internal.h | 5 +++-- src/rcheevos/memref.c | 4 ++-- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/src/rcheevos/internal.h b/src/rcheevos/internal.h index abdb3983..18b123e8 100644 --- a/src/rcheevos/internal.h +++ b/src/rcheevos/internal.h @@ -3,10 +3,11 @@ #include "rcheevos.h" +#include + #define RC_TAG2(x,y) x ## y #define RC_TAG(x,y) RC_TAG2(x,y) -#define RC_OFFSETOF(s, f) ((int)(long long)(&((s*)0)->f)) -#define RC_ALIGNOF(t) RC_OFFSETOF(struct RC_TAG(_unnamed, __LINE__) {char c; t d;}, d) +#define RC_ALIGNOF(t) offsetof(struct RC_TAG(_unnamed, __LINE__) {char c; t d;}, d) #define RC_ALLOC(t, p) ((t*)rc_alloc((p)->buffer, &(p)->offset, sizeof(t), RC_ALIGNOF(t), &(p)->scratch)) diff --git a/src/rcheevos/memref.c b/src/rcheevos/memref.c index b4565bb6..01ab2692 100644 --- a/src/rcheevos/memref.c +++ b/src/rcheevos/memref.c @@ -22,7 +22,7 @@ rc_memref_value_t* rc_alloc_memref_value(rc_parse_state_t* parse, unsigned addre if (parse->scratch.memref_count == parse->scratch.memref_size) { if (parse->scratch.memref == parse->scratch.memref_buffer) { parse->scratch.memref_size += 16; - memref = malloc(parse->scratch.memref_size * sizeof(parse->scratch.memref_buffer[0])); + memref = (rc_memref_t*)malloc(parse->scratch.memref_size * sizeof(parse->scratch.memref_buffer[0])); if (memref) { parse->scratch.memref = memref; memcpy(memref, parse->scratch.memref_buffer, parse->scratch.memref_count * sizeof(parse->scratch.memref_buffer[0])); @@ -34,7 +34,7 @@ rc_memref_value_t* rc_alloc_memref_value(rc_parse_state_t* parse, unsigned addre } else { parse->scratch.memref_size += 32; - memref = realloc(parse->scratch.memref, parse->scratch.memref_size * sizeof(parse->scratch.memref_buffer[0])); + memref = (rc_memref_t*)realloc(parse->scratch.memref, parse->scratch.memref_size * sizeof(parse->scratch.memref_buffer[0])); if (memref) { parse->scratch.memref = memref; } From 4a3c406421e918f10e5086929fe547ff72dd8de2 Mon Sep 17 00:00:00 2001 From: Jamiras Date: Sat, 20 Apr 2019 17:32:12 -0600 Subject: [PATCH 11/11] modify alignof calculation to not use inline structures (see RetroArch issue 8610) --- src/rcheevos/alloc.c | 2 +- src/rcheevos/internal.h | 23 ++++++++++++++++++----- 2 files changed, 19 insertions(+), 6 deletions(-) diff --git a/src/rcheevos/alloc.c b/src/rcheevos/alloc.c index 83b9ec71..56d8f8ac 100644 --- a/src/rcheevos/alloc.c +++ b/src/rcheevos/alloc.c @@ -50,4 +50,4 @@ void rc_destroy_parse_state(rc_parse_state_t* parse) { if (parse->scratch.memref != parse->scratch.memref_buffer) free(parse->scratch.memref); -} \ No newline at end of file +} diff --git a/src/rcheevos/internal.h b/src/rcheevos/internal.h index 18b123e8..ef5262f4 100644 --- a/src/rcheevos/internal.h +++ b/src/rcheevos/internal.h @@ -3,11 +3,24 @@ #include "rcheevos.h" -#include - -#define RC_TAG2(x,y) x ## y -#define RC_TAG(x,y) RC_TAG2(x,y) -#define RC_ALIGNOF(t) offsetof(struct RC_TAG(_unnamed, __LINE__) {char c; t d;}, d) +#define RC_ALLOW_ALIGN(T) struct __align_ ## T { char ch; T t; }; +RC_ALLOW_ALIGN(rc_condition_t) +RC_ALLOW_ALIGN(rc_condset_t) +RC_ALLOW_ALIGN(rc_expression_t) +RC_ALLOW_ALIGN(rc_lboard_t) +RC_ALLOW_ALIGN(rc_memref_value_t) +RC_ALLOW_ALIGN(rc_operand_t) +RC_ALLOW_ALIGN(rc_richpresence_t) +RC_ALLOW_ALIGN(rc_richpresence_display_t) +RC_ALLOW_ALIGN(rc_richpresence_display_part_t) +RC_ALLOW_ALIGN(rc_richpresence_lookup_t) +RC_ALLOW_ALIGN(rc_richpresence_lookup_item_t) +RC_ALLOW_ALIGN(rc_term_t) +RC_ALLOW_ALIGN(rc_trigger_t) +RC_ALLOW_ALIGN(rc_value_t) +RC_ALLOW_ALIGN(char) + +#define RC_ALIGNOF(T) (sizeof(struct __align_ ## T) - sizeof(T)) #define RC_ALLOC(t, p) ((t*)rc_alloc((p)->buffer, &(p)->offset, sizeof(t), RC_ALIGNOF(t), &(p)->scratch))