File size: 4,601 Bytes
78d2150
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
#include "../../unity/unity.h"
#include <string.h>
#include <stdlib.h>

/* Unity requires these even if empty. */
void setUp(void) { }
void tearDown(void) { }

/* Helpers for assertions in tests. */

/* Assert that mpz_t 'actual' equals the base-10 integer given by 'dec_str'. */
static void assert_mpz_equals_str(mpz_t actual, const char *dec_str)
{
    mpz_t expected;
    int rc;
    mpz_init(expected);
    rc = mpz_init_set_str(expected, dec_str, 10);
    /* mpz_init_set_str only returns nonzero on invalid string; test input must be valid. */
    TEST_ASSERT_EQUAL_INT(0, rc);
    TEST_ASSERT_EQUAL_INT(0, mpz_cmp(expected, actual));
    mpz_clear(expected);
}

/* Assert that toarith fails and the VALUE remains an unmodified string. */
static void assert_toarith_fails_preserves_string(const char *s)
{
    VALUE *v = str_value(s);
    char *orig_ptr = v->u.s;
    /* copy of content to verify it doesn't change */
    char *copy = strdup(orig_ptr);
    TEST_ASSERT_NOT_NULL(copy);

    bool ok = toarith(v);
    TEST_ASSERT_FALSE(ok);
    TEST_ASSERT_EQUAL_INT(string, v->type);
    TEST_ASSERT_TRUE(orig_ptr == v->u.s);
    TEST_ASSERT_EQUAL_INT(0, strcmp(copy, v->u.s));

    free(copy);
    freev(v);
}

/* Assert that toarith succeeds and converts to the expected integer value. */
static void assert_toarith_succeeds_to(const char *input, const char *expected_dec)
{
    VALUE *v = str_value(input);
    bool ok = toarith(v);
    TEST_ASSERT_TRUE(ok);
    TEST_ASSERT_EQUAL_INT(integer, v->type);
    assert_mpz_equals_str(v->u.i, expected_dec);
    freev(v);
}

/* Tests */

static void test_toarith_integer_nochange(void)
{
    VALUE *v = int_value(123UL);
    /* Make a copy of the mpz before calling toarith */
    mpz_t before;
    mpz_init_set(before, v->u.i);

    bool ok = toarith(v);
    TEST_ASSERT_TRUE(ok);
    TEST_ASSERT_EQUAL_INT(integer, v->type);
    TEST_ASSERT_EQUAL_INT(0, mpz_cmp(before, v->u.i));

    mpz_clear(before);
    freev(v);
}

static void test_toarith_integer_zero_nochange(void)
{
    VALUE *v = int_value(0UL);
    mpz_t before;
    mpz_init_set(before, v->u.i);

    bool ok = toarith(v);
    TEST_ASSERT_TRUE(ok);
    TEST_ASSERT_EQUAL_INT(integer, v->type);
    TEST_ASSERT_EQUAL_INT(0, mpz_cmp(before, v->u.i));

    mpz_clear(before);
    freev(v);
}

static void test_toarith_valid_decimal_string_positive(void)
{
    assert_toarith_succeeds_to("12345", "12345");
}

static void test_toarith_valid_decimal_string_negative(void)
{
    assert_toarith_succeeds_to("-987654321", "-987654321");
}

static void test_toarith_valid_decimal_string_leading_zeros(void)
{
    assert_toarith_succeeds_to("000123", "123");
}

static void test_toarith_valid_decimal_string_minus_zero(void)
{
    assert_toarith_succeeds_to("-0", "0");
}

static void test_toarith_valid_very_large_integer(void)
{
    /* Big integer to ensure arbitrary precision and sign handled */
    const char *bigneg =
        "-123456789012345678901234567890123456789012345678901234567890";
    assert_toarith_succeeds_to(bigneg, bigneg);
}

static void test_toarith_invalid_empty_string(void)
{
    assert_toarith_fails_preserves_string("");
}

static void test_toarith_invalid_just_minus(void)
{
    assert_toarith_fails_preserves_string("-");
}

static void test_toarith_invalid_plus_sign(void)
{
    assert_toarith_fails_preserves_string("+1");
}

static void test_toarith_invalid_embedded_non_digit(void)
{
    assert_toarith_fails_preserves_string("12x");
}

static void test_toarith_invalid_leading_space(void)
{
    assert_toarith_fails_preserves_string(" 1");
}

static void test_toarith_invalid_trailing_space(void)
{
    assert_toarith_fails_preserves_string("1 ");
}

static void test_toarith_invalid_double_minus(void)
{
    assert_toarith_fails_preserves_string("--1");
}

int main(void)
{
    UNITY_BEGIN();

    RUN_TEST(test_toarith_integer_nochange);
    RUN_TEST(test_toarith_integer_zero_nochange);

    RUN_TEST(test_toarith_valid_decimal_string_positive);
    RUN_TEST(test_toarith_valid_decimal_string_negative);
    RUN_TEST(test_toarith_valid_decimal_string_leading_zeros);
    RUN_TEST(test_toarith_valid_decimal_string_minus_zero);
    RUN_TEST(test_toarith_valid_very_large_integer);

    RUN_TEST(test_toarith_invalid_empty_string);
    RUN_TEST(test_toarith_invalid_just_minus);
    RUN_TEST(test_toarith_invalid_plus_sign);
    RUN_TEST(test_toarith_invalid_embedded_non_digit);
    RUN_TEST(test_toarith_invalid_leading_space);
    RUN_TEST(test_toarith_invalid_trailing_space);
    RUN_TEST(test_toarith_invalid_double_minus);

    return UNITY_END();
}