Commit afdc243
committed
http: declare unsigned-char alphabet in ragel parsers
ragel 6.10 -G2 generates incorrect code for the obs_text = 0x80..0xff
range when the build host's default `char` is unsigned (notably
aarch64). The state machine collapses byte 127 (DEL) and the
legitimately allowed obs_text range into a single forbidden interval
(`127 <= *p -> goto error`), so any HTTP field value containing
bytes 0x80..0xff is rejected even though RFC 7230 §3.2.6 permits
them.
x86_64 happens to produce correct code via a different range-merging
path. The .rl source is identical; only the host's signed-or-
unsigned-char default flips ragel's codegen.
The fix uses two ragel directives per machine:
alphtype unsigned char; # picks the correct codegen path
getkey ((unsigned char)(*p)); # forces fetched bytes unsigned
`alphtype unsigned char;` is the load-bearing fix: it makes ragel
treat the alphabet as 0..255 regardless of host, picking the
correct emit that lists `case 127: goto st0` plus a 0..31 ctrl-range
check while leaving 0x80..0xff fall through to the accept branch.
`getkey ((unsigned char)(*p))` is required because ragel now emits
character literals with the `u` suffix (e.g. `case 13u:`). On x86 the
input pointer's `*p` is signed char, and comparing a signed-char to an
unsigned literal triggers -Wsign-compare which seastar promotes to an
error. The getkey directive casts the fetched byte to unsigned so the
comparisons are unsigned on both sides.
Affects seastar's HTTP server (http_request_parser via httpd.hh) and
HTTP client (http_response_parser via client.cc) on arm64; the
chunked-transfer trailer parser (http_chunk_trailer_parser) inherits
the same fix.
Unblocks three existing tests that fail on aarch64 once the obs_text
input is exercised:
- tests/unit/chunk_parsers_test.cc :: test_trailer_headers_parsing
- tests/unit/request_parser_test.cc :: test_header_parsing
- tests/unit/httpd_test.cc :: test_full_chunk_format
Fixes scylladb#3413.1 parent 510f314 commit afdc243
3 files changed
Lines changed: 12 additions & 0 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
32 | 32 | | |
33 | 33 | | |
34 | 34 | | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
35 | 38 | | |
36 | 39 | | |
37 | 40 | | |
| |||
152 | 155 | | |
153 | 156 | | |
154 | 157 | | |
| 158 | + | |
| 159 | + | |
| 160 | + | |
155 | 161 | | |
156 | 162 | | |
157 | 163 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
33 | 33 | | |
34 | 34 | | |
35 | 35 | | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
36 | 39 | | |
37 | 40 | | |
38 | 41 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
35 | 35 | | |
36 | 36 | | |
37 | 37 | | |
| 38 | + | |
| 39 | + | |
| 40 | + | |
38 | 41 | | |
39 | 42 | | |
40 | 43 | | |
| |||
0 commit comments