aboutsummaryrefslogtreecommitdiff
path: root/src/microhttpd
diff options
context:
space:
mode:
authorEvgeny Grin (Karlson2k) <k2k@narod.ru>2021-06-23 10:47:41 +0300
committerEvgeny Grin (Karlson2k) <k2k@narod.ru>2021-07-05 17:01:21 +0300
commited3daed30580e6c4ae62d4114c58e38b6f0f9f85 (patch)
tree80add64a4a4083bdcb67d0591b149867760135c2 /src/microhttpd
parentada4c2ed55dd14f68430e9518f2882226a7b07cd (diff)
downloadlibmicrohttpd-ed3daed30580e6c4ae62d4114c58e38b6f0f9f85.tar.gz
libmicrohttpd-ed3daed30580e6c4ae62d4114c58e38b6f0f9f85.zip
Added MHD_str_remove_tokens_caseless_() function
Diffstat (limited to 'src/microhttpd')
-rw-r--r--src/microhttpd/.gitignore1
-rw-r--r--src/microhttpd/Makefile.am4
-rw-r--r--src/microhttpd/mhd_str.c166
-rw-r--r--src/microhttpd/mhd_str.h30
-rw-r--r--src/microhttpd/test_str_tokens_remove.c282
5 files changed, 483 insertions, 0 deletions
diff --git a/src/microhttpd/.gitignore b/src/microhttpd/.gitignore
index 83e8fb33..0ff01aac 100644
--- a/src/microhttpd/.gitignore
+++ b/src/microhttpd/.gitignore
@@ -54,6 +54,7 @@ test_http_reasons
54/test_start_stop 54/test_start_stop
55/test_str_token 55/test_str_token
56/test_str_token_remove 56/test_str_token_remove
57/test_str_tokens_remove
57test_shutdown_poll 58test_shutdown_poll
58test_shutdown_select 59test_shutdown_select
59test_md5 60test_md5
diff --git a/src/microhttpd/Makefile.am b/src/microhttpd/Makefile.am
index 2bdd9496..369e5554 100644
--- a/src/microhttpd/Makefile.am
+++ b/src/microhttpd/Makefile.am
@@ -159,6 +159,7 @@ check_PROGRAMS = \
159 test_str_to_value \ 159 test_str_to_value \
160 test_str_token \ 160 test_str_token \
161 test_str_token_remove \ 161 test_str_token_remove \
162 test_str_tokens_remove \
162 test_http_reasons \ 163 test_http_reasons \
163 test_md5 \ 164 test_md5 \
164 test_sha1 \ 165 test_sha1 \
@@ -357,6 +358,9 @@ test_str_token_SOURCES = \
357test_str_token_remove_SOURCES = \ 358test_str_token_remove_SOURCES = \
358 test_str_token_remove.c mhd_str.c mhd_str.h mhd_assert.h mhd_options.h 359 test_str_token_remove.c mhd_str.c mhd_str.h mhd_assert.h mhd_options.h
359 360
361test_str_tokens_remove_SOURCES = \
362 test_str_tokens_remove.c mhd_str.c mhd_str.h mhd_assert.h mhd_options.h
363
360test_http_reasons_SOURCES = \ 364test_http_reasons_SOURCES = \
361 test_http_reasons.c \ 365 test_http_reasons.c \
362 reason_phrase.c mhd_str.c mhd_str.h 366 reason_phrase.c mhd_str.c mhd_str.h
diff --git a/src/microhttpd/mhd_str.c b/src/microhttpd/mhd_str.c
index 5eddacaa..60c198bc 100644
--- a/src/microhttpd/mhd_str.c
+++ b/src/microhttpd/mhd_str.c
@@ -688,6 +688,172 @@ MHD_str_remove_token_caseless_ (const char *str,
688} 688}
689 689
690 690
691/**
692 * Perform in-place case-insensitive removal of @a tokens from the @a str.
693 *
694 * Token could be surrounded by spaces and tabs and delimited by comma.
695 * The token match succeed if substring between start, end (of string) or
696 * comma contains only case-insensitive token and optional spaces and tabs.
697 * The quoted strings and comments are not supported by this function.
698 *
699 * The input string must be normalised: empty tokens and repeated whitespaces
700 * are removed, no whitespaces before commas, exactly one space is used after
701 * each comma. The string is updated in-place.
702 *
703 * Behavior is undefined is input string in not normalised.
704 *
705 * @param[in,out] str the string to update
706 * @param[in,out] str_len the length of the @a str, not including optional
707 * terminating null-character, not null-terminated
708 * @param tokens the token to find
709 * @param tokens_len the length of @a tokens, not including optional
710 * terminating null-character.
711 * @return 'true' if any token has been removed,
712 * 'false' otherwise.
713 */
714bool
715MHD_str_remove_tokens_caseless_ (char *str,
716 size_t *str_len,
717 const char *const tokens,
718 const size_t tokens_len)
719{
720 const char *t; /**< position in the @a tokens string */
721 bool token_removed;
722
723 mhd_assert (NULL == memchr (tokens, 0, tokens_len));
724
725 token_removed = false;
726 t = tokens;
727
728 while ((size_t) (t - tokens) < tokens_len && *str_len != 0)
729 {
730 const char *tkn; /**< the current token */
731 size_t tkn_len;
732
733 /* Skip any initial whitespaces and empty tokens in 'tokens' */
734 while ( ((size_t) (t - tokens) < tokens_len) &&
735 ((' ' == *t) || ('\t' == *t) || (',' == *t)) )
736 t++;
737
738 if ((size_t) (t - tokens) >= tokens_len)
739 break; /* No more tokens, nothing to remove */
740
741 /* Found non-whitespace char which is not a comma */
742 tkn = t;
743 do
744 {
745 do
746 {
747 t++;
748 } while ((size_t) (t - tokens) < tokens_len && (' ' != *t && '\t' != *t &&
749 ',' != *t));
750 /* Found end of token string, space, tab, or comma */
751 tkn_len = t - tkn;
752
753 /* Skip all spaces and tabs */
754 while ((size_t) (t - tokens) < tokens_len && (' ' == *t || '\t' == *t))
755 t++;
756 /* Found end of token string or non-whitespace char */
757 } while((size_t) (t - tokens) < tokens_len && ',' != *t);
758
759 /* 'tkn' is the input token with 'tkn_len' chars */
760 mhd_assert (0 != tkn_len);
761
762 if (*str_len == tkn_len)
763 {
764 if (MHD_str_equal_caseless_bin_n_ (str, tkn, tkn_len))
765 {
766 *str_len = 0;
767 token_removed = true;
768 }
769 continue;
770 }
771 if (*str_len > tkn_len + 2)
772 { /* Remove 'tkn' from the input string */
773 const char *s1; /**< the "input" string / character */
774 char *s2; /**< the "output" string / character */
775
776 s1 = str;
777 s2 = str;
778
779 do
780 {
781 mhd_assert (s1 >= s2);
782 mhd_assert ((str + *str_len) >= (s1 + tkn_len));
783 if ( ( ((str + *str_len) == (s1 + tkn_len)) || (',' == s1[tkn_len]) ) &&
784 MHD_str_equal_caseless_bin_n_ (s1, tkn, tkn_len) )
785 {
786 /* current token in the input string matches the 'tkn', skip it */
787 mhd_assert ((str + *str_len == s1 + tkn_len) || \
788 (',' == s1[tkn_len]));
789 mhd_assert ((str + *str_len == s1 + tkn_len) || \
790 (' ' == s1[tkn_len + 1]));
791 token_removed = true;
792 /* Advance to the next token in the input string or beyond
793 * the end of the input string. */
794 s1 += tkn_len + 2;
795 }
796 else
797 {
798 /* current token in the input string does not match the 'tkn',
799 * copy to the output */
800 if (str != s2)
801 { /* not the first output token, add ", " to separate */
802 if (s1 != s2 + 2)
803 {
804 *(s2++) = ',';
805 *(s2++) = ' ';
806 }
807 else
808 s2 += 2;
809 }
810 do
811 {
812 if (s1 != s2)
813 *s2 = *s1;
814 s1++;
815 s2++;
816 } while (s1 < str + *str_len && ',' != *s1);
817 /* Advance to the next token in the input string or beyond
818 * the end of the input string. */
819 s1 += 2;
820 }
821 /* s1 should point to the next token in the input string or beyond
822 * the end of the input string */
823 if ((str + *str_len) < (s1 + tkn_len))
824 { /* The rest of the 's1' is too small to match 'tkn' */
825 if ((str + *str_len) > s1)
826 { /* Copy the rest of the string */
827 size_t copy_size;
828 copy_size = *str_len - (size_t) (s1 - str);
829 if (str != s2)
830 { /* not the first output token, add ", " to separate */
831 if (s1 != s2 + 2)
832 {
833 *(s2++) = ',';
834 *(s2++) = ' ';
835 }
836 else
837 s2 += 2;
838 }
839 if (s1 != s2)
840 memmove (s2, s1, copy_size);
841 s2 += copy_size;
842 }
843 *str_len = s2 - str;
844 break;
845 }
846 mhd_assert ((' ' != s1[0]) && ('\t' != s1[0]));
847 mhd_assert ((s1 == str) || (' ' == *(s1 - 1)));
848 mhd_assert ((s1 == str) || (',' == *(s1 - 2)));
849 } while (1);
850 }
851 }
852
853 return token_removed;
854}
855
856
691#ifndef MHD_FAVOR_SMALL_CODE 857#ifndef MHD_FAVOR_SMALL_CODE
692/* Use individual function for each case */ 858/* Use individual function for each case */
693 859
diff --git a/src/microhttpd/mhd_str.h b/src/microhttpd/mhd_str.h
index c49b11ed..33f91086 100644
--- a/src/microhttpd/mhd_str.h
+++ b/src/microhttpd/mhd_str.h
@@ -168,6 +168,36 @@ MHD_str_remove_token_caseless_ (const char *str,
168 ssize_t *buf_size); 168 ssize_t *buf_size);
169 169
170 170
171/**
172 * Perform in-place case-insensitive removal of @a tokens from the @a str.
173 *
174 * Token could be surrounded by spaces and tabs and delimited by comma.
175 * The token match succeed if substring between start, end (of string) or
176 * comma contains only case-insensitive token and optional spaces and tabs.
177 * The quoted strings and comments are not supported by this function.
178 *
179 * The input string must be normalised: empty tokens and repeated whitespaces
180 * are removed, no whitespaces before commas, exactly one space is used after
181 * each comma. The string is updated in-place.
182 *
183 * Behavior is undefined is input string in not normalised.
184 *
185 * @param[in,out] str the string to update
186 * @param[in,out] str_len the length of the @a str, not including optional
187 * terminating null-character, not null-terminated
188 * @param tokens the token to find
189 * @param tokens_len the length of @a tokens, not including optional
190 * terminating null-character.
191 * @return 'true' if any token has been removed,
192 * 'false' otherwise.
193 */
194bool
195MHD_str_remove_tokens_caseless_ (char *str,
196 size_t *str_len,
197 const char *const tokens,
198 const size_t tokens_len);
199
200
171#ifndef MHD_FAVOR_SMALL_CODE 201#ifndef MHD_FAVOR_SMALL_CODE
172/* Use individual function for each case to improve speed */ 202/* Use individual function for each case to improve speed */
173 203
diff --git a/src/microhttpd/test_str_tokens_remove.c b/src/microhttpd/test_str_tokens_remove.c
new file mode 100644
index 00000000..bc38e2cd
--- /dev/null
+++ b/src/microhttpd/test_str_tokens_remove.c
@@ -0,0 +1,282 @@
1/*
2 This file is part of libmicrohttpd
3 Copyright (C) 2017 Karlson2k (Evgeny Grin)
4
5 This test tool is free software; you can redistribute it and/or
6 modify it under the terms of the GNU General Public License as
7 published by the Free Software Foundation; either version 2, or
8 (at your option) any later version.
9
10 This test tool is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
14
15 You should have received a copy of the GNU Lesser General Public
16 License along with this library; if not, write to the Free Software
17 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18*/
19
20/**
21 * @file microhttpd/test_str_token.c
22 * @brief Unit tests for some mhd_str functions
23 * @author Karlson2k (Evgeny Grin)
24 */
25
26#include <string.h>
27#include <stdio.h>
28#include "mhd_options.h"
29#include "mhd_str.h"
30#include "mhd_assert.h"
31
32
33static int
34expect_result_n (const char *str, size_t str_len,
35 const char *tokens, size_t tokens_len,
36 const char *expected, size_t expected_len,
37 const bool expected_removed)
38{
39 char buf_in[1024];
40 char buf_tokens[256];
41 bool res;
42 size_t result_len;
43
44 mhd_assert (sizeof(buf_in) > str_len + 2);
45 mhd_assert (sizeof(buf_tokens) > tokens_len + 2);
46
47 memset (buf_tokens, '#', sizeof(buf_tokens));
48 memcpy (buf_tokens, tokens, tokens_len); /* Copy without zero-termination */
49 memset (buf_in, '$', sizeof(buf_in));
50 memcpy (buf_in, str, str_len); /* Copy without zero-termination */
51
52 result_len = str_len;
53
54 res = MHD_str_remove_tokens_caseless_ (buf_in, &result_len,
55 buf_tokens, tokens_len);
56
57 if ( (expected_removed != res) ||
58 (expected_len != result_len) ||
59 ((0 != result_len) && (0 != memcmp (expected, buf_in, result_len))) ||
60 ('$' != buf_in[str_len]))
61 {
62 fprintf (stderr,
63 "MHD_str_remove_tokens_caseless_() FAILED:\n"
64 "\tRESULT: "
65 "\tMHD_str_remove_token_caseless_(\"%s\"->\"%.*s\", &(%lu->%lu),"
66 " \"%.*s\", %lu) returned %s\n",
67 str,
68 (int) result_len, buf_in,
69 (unsigned long) str_len, (unsigned long) result_len,
70 (int) tokens_len, buf_tokens, (unsigned long) tokens_len,
71 res ? "true" : "false");
72 fprintf (stderr,
73 "\tEXPECTED: "
74 "\tMHD_str_remove_token_caseless_(\"%s\"->\"%s\", &(%lu->%lu),"
75 " \"%.*s\", %lu) returned %s\n",
76 str,
77 expected,
78 (unsigned long) str_len, (unsigned long) expected_len,
79 (int) tokens_len, buf_tokens, (unsigned long) tokens_len,
80 expected_removed ? "true" : "false");
81 return 1;
82 }
83 return 0;
84}
85
86
87#define expect_result(s,t,e,found) \
88 expect_result_n ((s),MHD_STATICSTR_LEN_ (s), \
89 (t),MHD_STATICSTR_LEN_ (t), \
90 (e),MHD_STATICSTR_LEN_ (e), found)
91
92int
93check_result (void)
94{
95 int errcount = 0;
96 errcount += expect_result ("string", "string", "", true);
97 errcount += expect_result ("String", "string", "", true);
98 errcount += expect_result ("string", "String", "", true);
99 errcount += expect_result ("strinG", "String", "", true);
100 errcount += expect_result ("strinG", "String\t", "", true);
101 errcount += expect_result ("strinG", "\tString", "", true);
102 errcount += expect_result ("tOkEn", " \t toKEN ", "", true);
103 errcount += expect_result ("not-token, tOkEn", "token", "not-token",
104 true);
105 errcount += expect_result ("not-token, tOkEn, toke", "token",
106 "not-token, toke",
107 true);
108 errcount += expect_result ("toke, tOkEn", "token", "toke",
109 true);
110 errcount += expect_result ("not-token, tOkEn", " \t toKEN", "not-token",
111 true);
112 errcount += expect_result ("not-token, tOkEn, more-token", "toKEN\t",
113 "not-token, more-token", true);
114 errcount += expect_result ("not-token, tOkEn, more-token", "\t toKEN,,,,,",
115 "not-token, more-token", true);
116 errcount += expect_result ("a, b, c, d", ",,,,,a", "b, c, d", true);
117 errcount += expect_result ("a, b, c, d", "a,,,,,,", "b, c, d", true);
118 errcount += expect_result ("a, b, c, d", ",,,,a,,,,,,", "b, c, d", true);
119 errcount += expect_result ("a, b, c, d", "\t \t,,,,a,, , ,,,\t",
120 "b, c, d", true);
121 errcount += expect_result ("a, b, c, d", "b, c, d", "a", true);
122 errcount += expect_result ("a, b, c, d", "a, b, c, d", "", true);
123 errcount += expect_result ("a, b, c, d", "d, c, b, a", "", true);
124 errcount += expect_result ("a, b, c, d", "b, d, a, c", "", true);
125 errcount += expect_result ("a, b, c, d, e", "b, d, a, c", "e", true);
126 errcount += expect_result ("e, a, b, c, d", "b, d, a, c", "e", true);
127 errcount += expect_result ("e, a, b, c, d, e", "b, d, a, c", "e, e", true);
128 errcount += expect_result ("a, b, c, d", "b,c,d", "a", true);
129 errcount += expect_result ("a, b, c, d", "a,b,c,d", "", true);
130 errcount += expect_result ("a, b, c, d", "d,c,b,a", "", true);
131 errcount += expect_result ("a, b, c, d", "b,d,a,c", "", true);
132 errcount += expect_result ("a, b, c, d, e", "b,d,a,c", "e", true);
133 errcount += expect_result ("e, a, b, c, d", "b,d,a,c", "e", true);
134 errcount += expect_result ("e, a, b, c, d, e", "b,d,a,c", "e, e", true);
135 errcount += expect_result ("a, b, c, d", "d,,,,,,,,,c,b,a", "", true);
136 errcount += expect_result ("a, b, c, d", "b,d,a,c,,,,,,,,,,", "", true);
137 errcount += expect_result ("a, b, c, d, e", ",,,,\t,,,,b,d,a,c,\t", "e",
138 true);
139 errcount += expect_result ("e, a, b, c, d", "b,d,a,c", "e", true);
140 errcount += expect_result ("token, a, b, c, d", "token", "a, b, c, d", true);
141 errcount += expect_result ("token1, a, b, c, d", "token1", "a, b, c, d",
142 true);
143 errcount += expect_result ("token12, a, b, c, d", "token12", "a, b, c, d",
144 true);
145 errcount += expect_result ("token123, a, b, c, d", "token123", "a, b, c, d",
146 true);
147 errcount += expect_result ("token1234, a, b, c, d", "token1234", "a, b, c, d",
148 true);
149 errcount += expect_result ("token12345, a, b, c, d", "token12345",
150 "a, b, c, d", true);
151 errcount += expect_result ("token123456, a, b, c, d", "token123456",
152 "a, b, c, d", true);
153 errcount += expect_result ("token1234567, a, b, c, d", "token1234567",
154 "a, b, c, d", true);
155 errcount += expect_result ("token12345678, a, b, c, d", "token12345678",
156 "a, b, c, d", true);
157
158 errcount += expect_result ("", "a", "", false);
159 errcount += expect_result ("", "", "", false);
160 errcount += expect_result ("a, b, c, d", "bb, dd, aa, cc", "a, b, c, d",
161 false);
162 errcount += expect_result ("a, b, c, d, e", "bb, dd, aa, cc", "a, b, c, d, e",
163 false);
164 errcount += expect_result ("e, a, b, c, d", "bb, dd, aa, cc", "e, a, b, c, d",
165 false);
166 errcount += expect_result ("e, a, b, c, d, e", "bb, dd, aa, cc",
167 "e, a, b, c, d, e", false);
168 errcount += expect_result ("aa, bb, cc, dd", "b, d, a, c", "aa, bb, cc, dd",
169 false);
170 errcount += expect_result ("aa, bb, cc, dd, ee", "b, d, a, c",
171 "aa, bb, cc, dd, ee", false);
172 errcount += expect_result ("ee, aa, bb, cc, dd", "b, d, a, c",
173 "ee, aa, bb, cc, dd", false);
174 errcount += expect_result ("ee, aa, bb, cc, dd, ee", "b, d, a, c",
175 "ee, aa, bb, cc, dd, ee", false);
176
177 errcount += expect_result ("TESt", ",,,,,,test,,,,", "", true);
178 errcount += expect_result ("TESt", ",,,,,\t,test,,,,", "", true);
179 errcount += expect_result ("TESt", ",,,,,,test, ,,,", "", true);
180 errcount += expect_result ("TESt", ",,,,,, test,,,,", "", true);
181 errcount += expect_result ("TESt", ",,,,,, test-not,test,,", "",
182 true);
183 errcount += expect_result ("TESt", ",,,,,, test-not,,test,,", "",
184 true);
185 errcount += expect_result ("TESt", ",,,,,, test-not ,test,,", "",
186 true);
187 errcount += expect_result ("TESt", ",,,,,, test", "", true);
188 errcount += expect_result ("TESt", ",,,,,, test ", "", true);
189 errcount += expect_result ("TESt", "no-test,,,,,, test ", "",
190 true);
191
192 errcount += expect_result ("the-token, a, the-token, b, the-token, " \
193 "the-token, c, the-token", "the-token", "a, b, c",
194 true);
195 errcount += expect_result ("aa, the-token, bb, the-token, cc, the-token, " \
196 "the-token, dd, the-token", "the-token",
197 "aa, bb, cc, dd", true);
198 errcount += expect_result ("the-token, a, the-token, b, the-token, " \
199 "the-token, c, the-token, e", "the-token",
200 "a, b, c, e", true);
201 errcount += expect_result ("aa, the-token, bb, the-token, cc, the-token, " \
202 "the-token, dd, the-token, ee", "the-token",
203 "aa, bb, cc, dd, ee", true);
204 errcount += expect_result ("the-token, the-token, the-token, " \
205 "the-token, the-token", "the-token", "", true);
206 errcount += expect_result ("the-token, a, the-token, the-token, b, " \
207 "the-token, c, the-token, a", "c,a,b",
208 "the-token, the-token, the-token, the-token, the-token",
209 true);
210 errcount += expect_result ("the-token, xx, the-token, the-token, zz, " \
211 "the-token, yy, the-token, ww", "ww,zz,yy",
212 "the-token, xx, the-token, the-token, the-token, the-token",
213 true);
214 errcount += expect_result ("the-token, a, the-token, the-token, b, " \
215 "the-token, c, the-token, a", " c,\t a,b,,,",
216 "the-token, the-token, the-token, the-token, the-token",
217 true);
218 errcount += expect_result ("the-token, xx, the-token, the-token, zz, " \
219 "the-token, yy, the-token, ww",
220 ",,,,ww,\t zz, yy",
221 "the-token, xx, the-token, the-token, the-token, the-token",
222 true);
223 errcount += expect_result ("the-token, a, the-token, the-token, b, " \
224 "the-token, c, the-token, a", ",,,,c,\t a,b",
225 "the-token, the-token, the-token, the-token, the-token",
226 true);
227 errcount += expect_result ("the-token, xx, the-token, the-token, zz, " \
228 "the-token, yy, the-token, ww", " ww,\t zz,yy,,,,",
229 "the-token, xx, the-token, the-token, the-token, the-token",
230 true);
231 errcount += expect_result ("close, 2", "close",
232 "2", true);
233 errcount += expect_result ("close, 22", "close",
234 "22", true);
235 errcount += expect_result ("close, nothing", "close",
236 "nothing", true);
237 errcount += expect_result ("close, 2", "2",
238 "close", true);
239 errcount += expect_result ("close", "close",
240 "", true);
241 errcount += expect_result ("close, nothing", "close, token",
242 "nothing", true);
243 errcount += expect_result ("close, nothing", "nothing, token",
244 "close", true);
245 errcount += expect_result ("close, 2", "close, 10, 12, 22, nothing",
246 "2", true);
247
248 errcount += expect_result ("strin", "string", "strin", false);
249 errcount += expect_result ("Stringer", "string", "Stringer", false);
250 errcount += expect_result ("sstring", "String", "sstring", false);
251 errcount += expect_result ("string", "Strin", "string", false);
252 errcount += expect_result ("String", "\t(-strinG", "String", false);
253 errcount += expect_result ("String", ")strinG\t ", "String", false);
254 errcount += expect_result ("not-token, tOkEner", "toKEN",
255 "not-token, tOkEner", false);
256 errcount += expect_result ("not-token, tOkEns, more-token", "toKEN",
257 "not-token, tOkEns, more-token", false);
258 errcount += expect_result ("tests, quest", "TESt", "tests, quest",
259 false);
260 errcount += expect_result ("testы", "TESt", "testы", false);
261 errcount += expect_result ("test-not, хtest", "TESt",
262 "test-not, хtest", false);
263 errcount += expect_result ("testing, test not, test2", "TESt",
264 "testing, test not, test2", false);
265 errcount += expect_result ("", ",,,,,,,,,,,,,,,,,,,the-token", "", false);
266 errcount += expect_result ("a1, b1, c1, d1, e1, f1, g1", "",
267 "a1, b1, c1, d1, e1, f1, g1", false);
268
269 return errcount;
270}
271
272
273int
274main (int argc, char *argv[])
275{
276 int errcount = 0;
277 (void) argc; (void) argv; /* Unused. Silent compiler warning. */
278 errcount += check_result ();
279 if (0 == errcount)
280 printf ("All tests were passed without errors.\n");
281 return errcount == 0 ? 0 : 1;
282}