Commit 4a631b5
committed
fix: don't truncate compressed packets that outgrow the output reserve
The existing code assumes a compressed packet is always smaller than the
uncompressed one: Compress::compress_into sizes zlib's output buffer at
input.len() + 10 bytes and works from there. That isn't true when the
data is already compressed. For pack files, encrypted blobs or media,
zlib has nothing left to squeeze out, so it wraps the bytes in a stored
block and hands back slightly more than it was given. Past 32 KiB the
stored-block overhead is more than the 10 bytes of slack.
Overflowing is supposed to be recoverable, but the loop grew the buffer
only on flate2::Status::BufError, and zlib returns BufError only when it
is completely stuck. Filling the buffer while still making progress
comes back as Status::Ok, which the loop read as done, so it sent the
packet with the tail still inside zlib. The packet went out short and
the leftover bytes desynced the stream for every later packet, which
OpenSSH reports as channel 0: get data: incomplete message.
Ask whether zlib left any room instead of whether it is stuck. Room to
spare means it emitted everything; a buffer filled to the brim means
there may be more, so grow and call again. compress now delegates to
compress_into so the two copies of the loop cannot drift apart again.
The regression tests round-trip packets that outgrow the reserve,
including through compress_into at a non-zero start_len, the shape the
packet writer uses, which the existing compressible under-4096-byte
tests don't cover.1 parent dbe2234 commit 4a631b5
1 file changed
Lines changed: 86 additions & 26 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
236 | 236 | | |
237 | 237 | | |
238 | 238 | | |
| 239 | + | |
| 240 | + | |
| 241 | + | |
| 242 | + | |
| 243 | + | |
| 244 | + | |
| 245 | + | |
| 246 | + | |
| 247 | + | |
| 248 | + | |
| 249 | + | |
| 250 | + | |
| 251 | + | |
| 252 | + | |
| 253 | + | |
| 254 | + | |
| 255 | + | |
| 256 | + | |
| 257 | + | |
| 258 | + | |
| 259 | + | |
| 260 | + | |
| 261 | + | |
| 262 | + | |
| 263 | + | |
| 264 | + | |
| 265 | + | |
| 266 | + | |
| 267 | + | |
| 268 | + | |
| 269 | + | |
| 270 | + | |
| 271 | + | |
| 272 | + | |
| 273 | + | |
| 274 | + | |
| 275 | + | |
| 276 | + | |
| 277 | + | |
| 278 | + | |
| 279 | + | |
| 280 | + | |
| 281 | + | |
| 282 | + | |
| 283 | + | |
| 284 | + | |
| 285 | + | |
| 286 | + | |
| 287 | + | |
| 288 | + | |
| 289 | + | |
| 290 | + | |
| 291 | + | |
| 292 | + | |
| 293 | + | |
| 294 | + | |
| 295 | + | |
| 296 | + | |
| 297 | + | |
| 298 | + | |
| 299 | + | |
| 300 | + | |
| 301 | + | |
| 302 | + | |
| 303 | + | |
| 304 | + | |
| 305 | + | |
| 306 | + | |
| 307 | + | |
| 308 | + | |
| 309 | + | |
239 | 310 | | |
240 | 311 | | |
241 | 312 | | |
| |||
249 | 320 | | |
250 | 321 | | |
251 | 322 | | |
252 | | - | |
253 | | - | |
254 | | - | |
255 | | - | |
256 | | - | |
257 | | - | |
258 | | - | |
259 | | - | |
260 | | - | |
261 | | - | |
262 | | - | |
263 | | - | |
264 | | - | |
265 | | - | |
266 | | - | |
267 | | - | |
268 | | - | |
269 | | - | |
270 | | - | |
271 | | - | |
272 | | - | |
273 | | - | |
274 | | - | |
275 | | - | |
| 323 | + | |
| 324 | + | |
276 | 325 | | |
| 326 | + | |
| 327 | + | |
| 328 | + | |
277 | 329 | | |
278 | 330 | | |
279 | 331 | | |
| |||
300 | 352 | | |
301 | 353 | | |
302 | 354 | | |
| 355 | + | |
| 356 | + | |
| 357 | + | |
| 358 | + | |
| 359 | + | |
| 360 | + | |
| 361 | + | |
| 362 | + | |
303 | 363 | | |
304 | | - | |
305 | | - | |
| 364 | + | |
| 365 | + | |
306 | 366 | | |
307 | 367 | | |
308 | 368 | | |
| |||
0 commit comments