Skip to content

Fix crash when reading non-UTF16 files - #1149

Merged
dail8859 merged 3 commits into
dail8859:masterfrom
amirkiarafiei:fix-file-loading-crash
Sep 26, 2026
Merged

dail8859 merged 3 commits into
dail8859:masterfrom
amirkiarafiei:fix-file-loading-crash

Conversation

@amirkiarafiei

@amirkiarafiei amirkiarafiei commented Sep 24, 2026 •

Copy link
Copy Markdown
Contributor

Problem

  1. The application crashes with a segmentation fault when a user opens an ASCII or UTF-8 text file.
  2. UTF-16 files larger than 4MB are truncated on load (UTF-16 files larger than 4MB are silently truncated on load (regression from #1139) #1142).

Cause

Commit a74152a added UTF-16 support. It also introduced an unconditional call to decoder(input) in src/ScintillaNext.cpp.

When the file is not UTF-16, decoder is not initialized. Invoking an uninitialized QStringDecoder on Qt 6 dereferences a null pointer.

Additionally, decoder was declared inside the chunk loop. On files larger than 4MB, decoder was re-instantiated on every chunk.

Solution

  1. Remove the unconditional call to decoder(input) outside the UTF-16 conditional block.
  2. Move QStringDecoder decoder before the chunk loop to maintain decoder state across chunks.

Fixes #1142

Note

This change is applied by the AI Gemini 3.8 Flash of Antigravity-CLI harness and the responsibility is for the author (Amirkia RAFIEI OSKOOEI).

@amirkiarafiei

Copy link
Copy Markdown
Contributor Author

Hello.
I am the author of the commit. The fix was applied with the help of Code Agents, based on the project's architecture and conventions.

@amirkiarafiei

Copy link
Copy Markdown
Contributor Author

I have updated the PR to pair QStringDecoder with a persistent QStringEncoder(QStringEncoder::Utf8).

Because chunk 1 subtracts the 2-byte BOM, it ends on an offset boundary (4194302 % 4 == 2) that can split a 4-byte UTF-16 surrogate pair across the 4MB chunk boundary. Stateless toUtf8() on chunk 1 would turn an unmatched high surrogate into replacement characters, whereas a persistent QStringEncoder buffers and carries the pending surrogate into the next chunk seamlessly.

@dail8859

Copy link
Copy Markdown
Owner

Appreciate the help with this and identifying these potentially nasty issues :)

I pushed a small tweak to the code. It goes ahead and instantiates the encoder. I would foresee the overhead of creating the encoder even when not needed would be miniscule compared to the rest of the disk read, encoding, and processing by Scintilla.

@dail8859
dail8859 merged commit b123ea2 into dail8859:master Sep 26, 2026
17 checks passed
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.

UTF-16 files larger than 4MB are silently truncated on load (regression from #1139)

2 participants