@@ -47,3 +47,44 @@ const testResBody = 'response content\n';
|
47 | 47 | req.on('information', common.mustNotCall()); |
48 | 48 | })); |
49 | 49 | } |
| 50 | + |
| 51 | +{ |
| 52 | +const server = http.createServer(common.mustCall((req, res) => { |
| 53 | +debug('Server sending early hints with CRLF injection...'); |
| 54 | + |
| 55 | +assert.throws(() => { |
| 56 | +res.writeEarlyHints({ |
| 57 | +'link': '</styles.css>; rel=preload; as=style', |
| 58 | +'X-Custom': 'valid\r\nSet-Cookie: session=evil', |
| 59 | +}); |
| 60 | +}, (err) => err.code === 'ERR_INVALID_CHAR'); |
| 61 | + |
| 62 | +assert.throws(() => { |
| 63 | +res.writeEarlyHints({ |
| 64 | +'link': '</styles.css>; rel=preload; as=style', |
| 65 | +'X-Custom\r\nSet-Cookie: session=evil': 'value', |
| 66 | +}); |
| 67 | +}, (err) => err.code === 'ERR_INVALID_HTTP_TOKEN'); |
| 68 | + |
| 69 | +assert.throws(() => { |
| 70 | +res.writeEarlyHints({ |
| 71 | +link: '</styles.css\r\nSet-Cookie: session=evil>; rel=preload; as=style', |
| 72 | +}); |
| 73 | +}, (err) => err.code === 'ERR_INVALID_ARG_VALUE'); |
| 74 | + |
| 75 | +debug('Server sending full response...'); |
| 76 | +res.end(testResBody); |
| 77 | +server.close(); |
| 78 | +})); |
| 79 | + |
| 80 | +server.listen(0, common.mustCall(() => { |
| 81 | +const req = http.request({ |
| 82 | +port: server.address().port, path: '/' |
| 83 | +}); |
| 84 | + |
| 85 | +req.end(); |
| 86 | +debug('Client sending request...'); |
| 87 | + |
| 88 | +req.on('information', common.mustNotCall()); |
| 89 | +})); |
| 90 | +} |