nx_css_tokenize_test.nx source
↩ module page · 188 lines · 6021 B
1// nx_css_tokenize_test.nx -- smoke for the CSS tokenizer Phase-2 seed.
2//
3// Tokenizes a small fixture CSS document and asserts each expected
4// token kind + body extraction. No allocation beyond the caller's
5// buffers per the tokenizer contract.
6
7import "nx_syscalls.nx"
8import "nx_css_tokenize.nx"
9
10func _put_byte(buf: *u8, i: i64, v: i64) -> i64 {
11 buf[i] = v as u8
12 return 0
13}
14
15// Build the fixture CSS into a heap buffer and return (buf, len).
16// Source:
17// "body { color: #ff0000; font-size: 16px; }\n.head { margin: 8px; }\n"
18// bytes laid out manually so the test is self-contained.
19func _build_fixture(out_len: *i64) -> *u8 {
20 let s: *u8 = (sys_mmap(128)) as *u8
21 var i: i64 = 0
22 // "body { color: #ff0000; font-size: 16px; }\n"
23 _put_byte(s, i, 98); i = i + 1 // b
24 _put_byte(s, i, 111); i = i + 1 // o
25 _put_byte(s, i, 100); i = i + 1 // d
26 _put_byte(s, i, 121); i = i + 1 // y
27 _put_byte(s, i, 32); i = i + 1 // ' '
28 _put_byte(s, i, 123); i = i + 1 // '{'
29 _put_byte(s, i, 32); i = i + 1 // ' '
30 _put_byte(s, i, 99); i = i + 1 // c
31 _put_byte(s, i, 111); i = i + 1 // o
32 _put_byte(s, i, 108); i = i + 1 // l
33 _put_byte(s, i, 111); i = i + 1 // o
34 _put_byte(s, i, 114); i = i + 1 // r
35 _put_byte(s, i, 58); i = i + 1 // ':'
36 _put_byte(s, i, 32); i = i + 1 // ' '
37 _put_byte(s, i, 35); i = i + 1 // '#'
38 _put_byte(s, i, 102); i = i + 1 // f
39 _put_byte(s, i, 102); i = i + 1 // f
40 _put_byte(s, i, 48); i = i + 1 // 0
41 _put_byte(s, i, 48); i = i + 1 // 0
42 _put_byte(s, i, 48); i = i + 1 // 0
43 _put_byte(s, i, 48); i = i + 1 // 0
44 _put_byte(s, i, 59); i = i + 1 // ';'
45 _put_byte(s, i, 32); i = i + 1 // ' '
46 _put_byte(s, i, 102); i = i + 1 // f
47 _put_byte(s, i, 111); i = i + 1 // o
48 _put_byte(s, i, 110); i = i + 1 // n
49 _put_byte(s, i, 116); i = i + 1 // t
50 _put_byte(s, i, 45); i = i + 1 // '-'
51 _put_byte(s, i, 115); i = i + 1 // s
52 _put_byte(s, i, 105); i = i + 1 // i
53 _put_byte(s, i, 122); i = i + 1 // z
54 _put_byte(s, i, 101); i = i + 1 // e
55 _put_byte(s, i, 58); i = i + 1 // ':'
56 _put_byte(s, i, 32); i = i + 1 // ' '
57 _put_byte(s, i, 49); i = i + 1 // '1'
58 _put_byte(s, i, 54); i = i + 1 // '6'
59 _put_byte(s, i, 112); i = i + 1 // p
60 _put_byte(s, i, 120); i = i + 1 // x
61 _put_byte(s, i, 59); i = i + 1 // ';'
62 _put_byte(s, i, 32); i = i + 1 // ' '
63 _put_byte(s, i, 125); i = i + 1 // '}'
64 out_len[0] = i
65 return s
66}
67
68func main() -> i64 {
69 let len_box: *i64 = (sys_mmap(8)) as *i64
70 let src: *u8 = _build_fixture(len_box)
71 let src_len: i64 = len_box[0]
72
73 let cur: *CssCursor = (sys_mmap(NX_CSS_CURSOR_BYTES as nx_size)) as *CssCursor
74 nx_css_cursor_init(cur, src, src_len)
75
76 let tok: *CssToken = (sys_mmap(NX_CSS_TOKEN_BYTES as nx_size)) as *CssToken
77
78 // Expected stream (using ' ' as WS, all single-space runs collapse
79 // into one WHITESPACE token):
80 // 1 IDENT "body"
81 // 2 WS
82 // 3 LBRACE
83 // 4 WS
84 // 5 IDENT "color"
85 // 6 COLON
86 // 7 WS
87 // 8 HEXCOLOR "ff0000"
88 // 9 SEMI
89 // 10 WS
90 // 11 IDENT "font-size"
91 // 12 COLON
92 // 13 WS
93 // 14 NUMBER "16"
94 // 15 IDENT "px"
95 // 16 SEMI
96 // 17 WS
97 // 18 RBRACE
98 // 19 EOF (since fixture ends at '}')
99
100 // 1: IDENT "body"
101 nx_css_next_token(cur, tok)
102 if tok.kind != NX_CSS_TOK_IDENT { return 1 }
103 if tok.body_len != 4 { return 2 }
104 if (src[tok.body_off] as i64) & 255 != 98 { return 3 } // 'b'
105
106 // 2: WS
107 nx_css_next_token(cur, tok)
108 if tok.kind != NX_CSS_TOK_WHITESPACE { return 4 }
109
110 // 3: LBRACE
111 nx_css_next_token(cur, tok)
112 if tok.kind != NX_CSS_TOK_LBRACE { return 5 }
113
114 // 4: WS
115 nx_css_next_token(cur, tok)
116 if tok.kind != NX_CSS_TOK_WHITESPACE { return 6 }
117
118 // 5: IDENT "color"
119 nx_css_next_token(cur, tok)
120 if tok.kind != NX_CSS_TOK_IDENT { return 7 }
121 if tok.body_len != 5 { return 8 }
122
123 // 6: COLON
124 nx_css_next_token(cur, tok)
125 if tok.kind != NX_CSS_TOK_COLON { return 9 }
126
127 // 7: WS
128 nx_css_next_token(cur, tok)
129 if tok.kind != NX_CSS_TOK_WHITESPACE { return 10 }
130
131 // 8: HEXCOLOR "ff0000"
132 nx_css_next_token(cur, tok)
133 if tok.kind != NX_CSS_TOK_HEXCOLOR { return 11 }
134 if tok.body_len != 6 { return 12 }
135 if (src[tok.body_off] as i64) & 255 != 102 { return 13 } // 'f'
136
137 // 9: SEMI
138 nx_css_next_token(cur, tok)
139 if tok.kind != NX_CSS_TOK_SEMI { return 14 }
140
141 // 10: WS
142 nx_css_next_token(cur, tok)
143 if tok.kind != NX_CSS_TOK_WHITESPACE { return 15 }
144
145 // 11: IDENT "font-size"
146 nx_css_next_token(cur, tok)
147 if tok.kind != NX_CSS_TOK_IDENT { return 16 }
148 if tok.body_len != 9 { return 17 }
149
150 // 12: COLON
151 nx_css_next_token(cur, tok)
152 if tok.kind != NX_CSS_TOK_COLON { return 18 }
153
154 // 13: WS
155 nx_css_next_token(cur, tok)
156 if tok.kind != NX_CSS_TOK_WHITESPACE { return 19 }
157
158 // 14: NUMBER "16"
159 nx_css_next_token(cur, tok)
160 if tok.kind != NX_CSS_TOK_NUMBER { return 20 }
161 if tok.body_len != 2 { return 21 }
162 if (src[tok.body_off] as i64) & 255 != 49 { return 22 } // '1'
163
164 // 15: IDENT "px" (unit-shaped; parser layer pairs with prior NUMBER)
165 nx_css_next_token(cur, tok)
166 if tok.kind != NX_CSS_TOK_IDENT { return 23 }
167 if tok.body_len != 2 { return 24 }
168 if (src[tok.body_off] as i64) & 255 != 112 { return 25 } // 'p'
169
170 // 16: SEMI
171 nx_css_next_token(cur, tok)
172 if tok.kind != NX_CSS_TOK_SEMI { return 26 }
173
174 // 17: WS
175 nx_css_next_token(cur, tok)
176 if tok.kind != NX_CSS_TOK_WHITESPACE { return 27 }
177
178 // 18: RBRACE
179 nx_css_next_token(cur, tok)
180 if tok.kind != NX_CSS_TOK_RBRACE { return 28 }
181
182 // 19: EOF
183 let rc: i64 = nx_css_next_token(cur, tok)
184 if rc != 0 { return 29 }
185 if tok.kind != NX_CSS_TOK_EOF { return 30 }
186
187 return 0
188}