| #include "unity/unity.h" |
| #define PCRE2_CODE_UNIT_WIDTH 8 |
| #include "pcre2.h" |
|
|
| #include <string.h> |
| #include <stdint.h> |
| #include <stdbool.h> |
|
|
| |
| extern BOOL test_read_repeat_counts(PCRE2_SPTR *ptrptr, PCRE2_SPTR ptrend, |
| uint32_t *minp, uint32_t *maxp, |
| int *errorcodeptr); |
|
|
| static BOOL call_rrc(const char *s, uint32_t *minp, uint32_t *maxp, int *errp, PCRE2_SPTR *pvar_out, PCRE2_SPTR *pend_out) |
| { |
| |
| TEST_ASSERT_NOT_NULL(s); |
| const char *open = strchr(s, '{'); |
| TEST_ASSERT_NOT_NULL_MESSAGE(open, "Test pattern must contain '{'"); |
|
|
| PCRE2_SPTR p = (PCRE2_SPTR)(open + 1); |
| PCRE2_SPTR pend = (PCRE2_SPTR)(s + strlen(s)); |
| BOOL rc = test_read_repeat_counts(&p, pend, minp, maxp, errp); |
|
|
| if (pvar_out) *pvar_out = p; |
| if (pend_out) *pend_out = pend; |
| return rc; |
| } |
|
|
| void setUp(void) { } |
| void tearDown(void) { } |
|
|
| |
| void test_read_repeat_counts_exact_n(void) |
| { |
| const char *pat = "{5}"; |
| uint32_t minv = 0, maxv = 0; |
| int err = -1; |
| PCRE2_SPTR p_after = NULL; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, &p_after, NULL); |
| TEST_ASSERT_TRUE(ok); |
| TEST_ASSERT_EQUAL_INT(0, err); |
| TEST_ASSERT_EQUAL_UINT32(5u, minv); |
| TEST_ASSERT_EQUAL_UINT32(5u, maxv); |
|
|
| const char *close = strchr(pat, '}'); |
| TEST_ASSERT_NOT_NULL(close); |
| TEST_ASSERT_EQUAL_PTR(close + 1, p_after); |
| } |
|
|
| |
| void test_read_repeat_counts_n_m(void) |
| { |
| const char *pat = "{2,4}"; |
| uint32_t minv = 0, maxv = 0; |
| int err = -1; |
| PCRE2_SPTR p_after = NULL; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, &p_after, NULL); |
| TEST_ASSERT_TRUE(ok); |
| TEST_ASSERT_EQUAL_INT(0, err); |
| TEST_ASSERT_EQUAL_UINT32(2u, minv); |
| TEST_ASSERT_EQUAL_UINT32(4u, maxv); |
|
|
| const char *close = strchr(pat, '}'); |
| TEST_ASSERT_EQUAL_PTR(close + 1, p_after); |
| } |
|
|
| |
| void test_read_repeat_counts_n_unlimited(void) |
| { |
| const char *pat = "{7,}"; |
| uint32_t minv = 0, maxv = 0; |
| int err = -1; |
| PCRE2_SPTR p_after = NULL; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, &p_after, NULL); |
| TEST_ASSERT_TRUE(ok); |
| TEST_ASSERT_EQUAL_INT(0, err); |
| TEST_ASSERT_EQUAL_UINT32(7u, minv); |
| |
| TEST_ASSERT_TRUE(maxv >= minv); |
|
|
| const char *close = strchr(pat, '}'); |
| TEST_ASSERT_EQUAL_PTR(close + 1, p_after); |
| } |
|
|
| |
| void test_read_repeat_counts_unbounded_m(void) |
| { |
| const char *pat = "{,9}"; |
| uint32_t minv = 12345, maxv = 12345; |
| int err = -1; |
| PCRE2_SPTR p_after = NULL; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, &p_after, NULL); |
| TEST_ASSERT_TRUE(ok); |
| TEST_ASSERT_EQUAL_INT(0, err); |
| TEST_ASSERT_EQUAL_UINT32(0u, minv); |
| TEST_ASSERT_EQUAL_UINT32(9u, maxv); |
|
|
| const char *close = strchr(pat, '}'); |
| TEST_ASSERT_EQUAL_PTR(close + 1, p_after); |
| } |
|
|
| |
| void test_read_repeat_counts_whitespace(void) |
| { |
| const char *pat = "{ \t3 \t , \t 6 \t }"; |
| uint32_t minv = 0, maxv = 0; |
| int err = -1; |
| PCRE2_SPTR p_after = NULL; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, &p_after, NULL); |
| TEST_ASSERT_TRUE(ok); |
| TEST_ASSERT_EQUAL_INT(0, err); |
| TEST_ASSERT_EQUAL_UINT32(3u, minv); |
| TEST_ASSERT_EQUAL_UINT32(6u, maxv); |
|
|
| const char *close = strrchr(pat, '}'); |
| TEST_ASSERT_EQUAL_PTR(close + 1, p_after); |
| } |
|
|
| |
| void test_read_repeat_counts_not_quantifier_returns_false_no_error(void) |
| { |
| const char *pat = "{,}"; |
| uint32_t minv = 111, maxv = 222; |
| int err = -1; |
| PCRE2_SPTR p_initial = NULL, p_after = NULL, pend = NULL; |
|
|
| |
| const char *open = strchr(pat, '{'); |
| TEST_ASSERT_NOT_NULL(open); |
| p_initial = (PCRE2_SPTR)(open + 1); |
|
|
| (void)test_read_repeat_counts(&p_initial, (PCRE2_SPTR)(pat + strlen(pat)), &minv, &maxv, &err); |
| |
| err = -1; minv = 0; maxv = 0; |
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, &p_after, &pend); |
| TEST_ASSERT_FALSE(ok); |
| TEST_ASSERT_EQUAL_INT(0, err); |
|
|
| |
| TEST_ASSERT_EQUAL_PTR(open + 1, p_after); |
| } |
|
|
| |
| void test_read_repeat_counts_invalid_order_sets_error(void) |
| { |
| const char *pat = "{5,3}"; |
| uint32_t minv = 0, maxv = 0; |
| int err = 0; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, NULL, NULL); |
| TEST_ASSERT_FALSE(ok); |
| TEST_ASSERT_NOT_EQUAL(0, err); |
| } |
|
|
| |
| void test_read_repeat_counts_overlarge_min_sets_error(void) |
| { |
| const char *pat = "{70000}"; |
| uint32_t minv = 0, maxv = 0; |
| int err = 0; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, NULL, NULL); |
| TEST_ASSERT_FALSE(ok); |
| TEST_ASSERT_NOT_EQUAL(0, err); |
| } |
|
|
| |
| void test_read_repeat_counts_overlarge_max_sets_error(void) |
| { |
| const char *pat = "{1,70000}"; |
| uint32_t minv = 0, maxv = 0; |
| int err = 0; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, NULL, NULL); |
| TEST_ASSERT_FALSE(ok); |
| TEST_ASSERT_NOT_EQUAL(0, err); |
| } |
|
|
| |
| void test_read_repeat_counts_missing_closing_brace_returns_false(void) |
| { |
| const char *pat = "{3,4"; |
| uint32_t minv = 0, maxv = 0; |
| int err = -1; |
| PCRE2_SPTR p_after = NULL; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, &p_after, NULL); |
| TEST_ASSERT_FALSE(ok); |
| TEST_ASSERT_EQUAL_INT(0, err); |
|
|
| const char *open = strchr(pat, '{'); |
| TEST_ASSERT_EQUAL_PTR(open + 1, p_after); |
| } |
|
|
| |
| void test_read_repeat_counts_pointer_advances_to_after_brace(void) |
| { |
| const char *pat = "{2,3}ABC"; |
| uint32_t minv = 0, maxv = 0; |
| int err = -1; |
| PCRE2_SPTR p_after = NULL; |
|
|
| BOOL ok = call_rrc(pat, &minv, &maxv, &err, &p_after, NULL); |
| TEST_ASSERT_TRUE(ok); |
| TEST_ASSERT_EQUAL_INT(0, err); |
| const char *close = strchr(pat, '}'); |
| TEST_ASSERT_EQUAL_PTR(close + 1, p_after); |
| } |
|
|
| |
| void test_read_repeat_counts_zero_bounds(void) |
| { |
| const char *pat1 = "{0,}"; |
| const char *pat2 = "{,0}"; |
| uint32_t minv = 123, maxv = 456; |
| int err = -1; |
|
|
| BOOL ok1 = call_rrc(pat1, &minv, &maxv, &err, NULL, NULL); |
| TEST_ASSERT_TRUE(ok1); |
| TEST_ASSERT_EQUAL_INT(0, err); |
| TEST_ASSERT_EQUAL_UINT32(0u, minv); |
|
|
| err = -1; minv = 123; maxv = 456; |
| BOOL ok2 = call_rrc(pat2, &minv, &maxv, &err, NULL, NULL); |
| TEST_ASSERT_TRUE(ok2); |
| TEST_ASSERT_EQUAL_INT(0, err); |
| TEST_ASSERT_EQUAL_UINT32(0u, minv); |
| TEST_ASSERT_EQUAL_UINT32(0u, maxv); |
| } |
|
|
| int main(void) |
| { |
| UNITY_BEGIN(); |
|
|
| RUN_TEST(test_read_repeat_counts_exact_n); |
| RUN_TEST(test_read_repeat_counts_n_m); |
| RUN_TEST(test_read_repeat_counts_n_unlimited); |
| RUN_TEST(test_read_repeat_counts_unbounded_m); |
| RUN_TEST(test_read_repeat_counts_whitespace); |
| RUN_TEST(test_read_repeat_counts_not_quantifier_returns_false_no_error); |
| RUN_TEST(test_read_repeat_counts_invalid_order_sets_error); |
| RUN_TEST(test_read_repeat_counts_overlarge_min_sets_error); |
| RUN_TEST(test_read_repeat_counts_overlarge_max_sets_error); |
| RUN_TEST(test_read_repeat_counts_missing_closing_brace_returns_false); |
| RUN_TEST(test_read_repeat_counts_pointer_advances_to_after_brace); |
| RUN_TEST(test_read_repeat_counts_zero_bounds); |
|
|
| return UNITY_END(); |
| } |