Skip to content

Bound the multiplayer map preview against the block it arrives in - #144

Open
gunnarbeutner wants to merge 1 commit into
OpenTS-Developers:mainfrom
gunnarbeutner:preview-hardening
Open

Bound the multiplayer map preview against the block it arrives in#144
gunnarbeutner wants to merge 1 commit into
OpenTS-Developers:mainfrom
gunnarbeutner:preview-hardening

Conversation

@gunnarbeutner

Copy link
Copy Markdown
Contributor

Invalid preview data from a multiplayer host could cause out-of-bounds reads, overflow the allocation size calculation, or leave partially uninitialised data to be parsed.

This PR validates the received data before creating a preview:

  • Check the downloaded block and decompression result.

    Receive_Random_Map_Preview now checks that the file contains its length field and bounds the expanded size. BufferStraw receives the number of bytes remaining after that field, fixing a four-byte overread.

    The caller allocates exactly the requested size, removing the unchecked 2 * preview_size calculation, and checks that decompression returned the full block before parsing it.

  • Check the image fits within the block.

    MapPreviewClass::Create_Preview_Surface now takes the block length and returns whether it created a surface. It validates the dimensions and colour count before reading the image, using 64-bit arithmetic for the offset + width * height check. Palette indices are bounded by the colour count.

  • Keep the limits alongside the format definition.

    Both limits live in preview.h beside the header they describe and are well above anything Create_Paletted_Preview produces.

@github-actions

github-actions Bot commented Sep 7, 2026

Copy link
Copy Markdown

Development builds of 7cdf613:

The links work without a GitHub account. Artifacts expire after 90 days, and this comment follows the latest successful build.

@tomsons26

Copy link
Copy Markdown
Contributor

Receive_Random_Map_Preview should be refactored to use a bool, say valid to always reach the one and only cleanup instead of copying the cleanups

@tomsons26

tomsons26 commented Sep 7, 2026

Copy link
Copy Markdown
Contributor

The print terminology is very weird..
IMO
DebugString("Preview file size %d is too small\n", size);
DebugString("Preview decompressed size is %d bytes\n", preview_size);
DebugString("Preview decompressed size %d doesn't match expected %d bytes\n", decompressed_size, preview_size);
DebugString("Preview surface could not be created\n");
clear, concise, no expanded,promisses, claims or descriptions

@gunnarbeutner

Copy link
Copy Markdown
Contributor Author

I've updated the log messages, replaced the buffers with std::vector and split the function into two parts so there's no need for (repeated) clean-up or valid at all.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants