-
Notifications
You must be signed in to change notification settings - Fork 219
Fix aligned buffer write #11861
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix aligned buffer write #11861
Conversation
This is a particularly subtle bug that requires a chunk (or remaining bit of a chunk) and the destination buffer being _exactly_ the same size. When this happens, the following sequence occurs: 1. `source.Length` and `destination.Length` are exactly aligned. This means that we do not enter the `if` on line 450, and `endOfChunkWritten` will be true. 2. We slice `destination` by `source.Length`. This leaves us with a `destination` that has 0 elements, and `IsEmpty` is true. 3. Because `endOfChunkWritten` is true, we enter the `if` on line 466. This increments us to the next chunk. 4. On line 472 (in the before diff), `destination.IsEmpty` is true, so we enter the `if`, and break out of the loop, never reseting `charIndex` to 0. 5. 4 happens again, this time on line 480 (in the before diff). Again, we do not reset `charIndex` to 0. To fix this, we want to unconditionally reset `charIndex` when we increment a chunk, not wait until after the destination has been checked for empty.
| Assert.Equal(output, FirstLine.AsSpan()); | ||
| Array.Clear(output); | ||
|
|
||
| testWriter.Read(output, 0, output.Length); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Verified that without the charIndex change, this line fails.
| } | ||
|
|
||
| [Fact] | ||
| public void ReaderOnlyReadsAsMuchAsRequested() |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This issue is not directly related to the main bug, but is something that @jaredpar noticed when just looking over the code.
src/Compiler/Microsoft.AspNetCore.Razor.Language/test/CodeGeneration/CSharpCodeWriterTest.cs
Outdated
Show resolved
Hide resolved
src/Compiler/Microsoft.AspNetCore.Razor.Language/test/CodeGeneration/CSharpCodeWriterTest.cs
Outdated
Show resolved
Hide resolved
|
/backport to release/dev17.14 |
|
Started backporting to release/dev17.14: https://github.com/dotnet/razor/actions/runs/15034407725 |
This is a particularly subtle bug that requires a chunk (or remaining bit of a chunk) and the destination buffer being exactly the same size. When this happens, the following sequence occurs:
source.Lengthanddestination.Lengthare exactly aligned. This means that we do not enter theifon line 450, andendOfChunkWrittenwill be true.destinationbysource.Length. This leaves us with adestinationthat has 0 elements, andIsEmptyis true.endOfChunkWrittenis true, we enter theifon line 466. This increments us to the next chunk.destination.IsEmptyis true, so we enter theif, and break out of the loop, never resetingcharIndexto 0.charIndexto 0.To fix this, we want to unconditionally reset
charIndexwhen we increment a chunk, not wait until after the destination has been checked for empty.