@@ -96,7 +96,7 @@ pub const Request = struct {
96
96
int64 ("HTTP/1.1" ) = > .@"HTTP/1.1" ,
97
97
else = > return error .BadHttpVersion ,
98
98
};
99
- if (first_line [8 ] != ' ' ) return error .InvalidHttpHeaders ;
99
+ if (first_line [8 ] != ' ' ) return error .HttpHeadersInvalid ;
100
100
const status = @intToEnum (http .Status , parseInt3 (first_line [9.. 12].* ));
101
101
102
102
var headers : Response.Headers = .{
@@ -105,12 +105,19 @@ pub const Request = struct {
105
105
};
106
106
107
107
while (it .next ()) | line | {
108
+ if (line .len == 0 ) return error .HttpHeadersInvalid ;
109
+ switch (line [0 ]) {
110
+ ' ' , '\t ' = > return error .HttpHeaderContinuationsUnsupported ,
111
+ else = > {},
112
+ }
108
113
var line_it = mem .split (u8 , line , ": " );
109
114
const header_name = line_it .first ();
110
115
const header_value = line_it .rest ();
111
116
if (std .ascii .eqlIgnoreCase (header_name , "location" )) {
117
+ if (headers .location != null ) return error .HttpHeadersInvalid ;
112
118
headers .location = header_value ;
113
119
} else if (std .ascii .eqlIgnoreCase (header_name , "content-length" )) {
120
+ if (headers .content_length != null ) return error .HttpHeadersInvalid ;
114
121
headers .content_length = try std .fmt .parseInt (u64 , header_value , 10 );
115
122
}
116
123
}
@@ -131,6 +138,29 @@ pub const Request = struct {
131
138
return error .TestFailed );
132
139
try testing .expectEqual (@as (? u64 , 220 ), parsed .content_length );
133
140
}
141
+
142
+ test "header continuation" {
143
+ const example =
144
+ "HTTP/1.0 200 OK\r \n " ++
145
+ "Content-Type: text/html;\r \n charset=UTF-8\r \n " ++
146
+ "Content-Length: 220\r \n \r \n " ;
147
+ try testing .expectError (
148
+ error .HttpHeaderContinuationsUnsupported ,
149
+ Response .Headers .parse (example ),
150
+ );
151
+ }
152
+
153
+ test "extra content length" {
154
+ const example =
155
+ "HTTP/1.0 200 OK\r \n " ++
156
+ "Content-Length: 220\r \n " ++
157
+ "Content-Type: text/html; charset=UTF-8\r \n " ++
158
+ "content-length: 220\r \n \r \n " ;
159
+ try testing .expectError (
160
+ error .HttpHeadersInvalid ,
161
+ Response .Headers .parse (example ),
162
+ );
163
+ }
134
164
};
135
165
136
166
pub const State = enum {
@@ -442,7 +472,7 @@ pub const Request = struct {
442
472
const amt = try req .connection .read (buffer );
443
473
const data = buffer [0.. amt ];
444
474
const i = req .response .findHeadersEnd (data );
445
- if (req .response .state == .invalid ) return error .InvalidHttpHeaders ;
475
+ if (req .response .state == .invalid ) return error .HttpHeadersInvalid ;
446
476
447
477
const headers_data = data [0.. i ];
448
478
if (req .response .header_bytes .items .len + headers_data .len > req .response .max_header_bytes ) {
0 commit comments