-
Notifications
You must be signed in to change notification settings - Fork 412
io: Fix checksum seek at end #10341
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
io: Fix checksum seek at end #10341
Conversation
Signed-off-by: Lloyd-Pottiger <yan1579196623@gmail.com>
|
/check-issue-triage-complete |
|
/hold |
| if (offset_ < cur_offset) | ||
| { | ||
| cur_offset = offset_; | ||
| if (!initialize()) | ||
| { | ||
| return S3StreamError; | ||
| } | ||
| return cur_offset; | ||
| } |
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.
why do we need to seek backward?
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.
// If we have already seek to EOF, then working_buffer was cleared
if (target_frame == current_frame && working_buffer.size() > 0)
{
if (unlikely(target_offset > working_buffer.size()))
pos = working_buffer.end();
else
pos = working_buffer.begin() + target_offset;
return offset;
}
If the same target frame is seeked again it is seeked in backward.
BTW it would be great if we could figure out some ways to avoid seeking backward.
|
/unhold |
Signed-off-by: JaySon-Huang <tshent@qq.com>
JaySon-Huang
left a comment
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.
highlight what is changed
| if (unlikely(target_offset > working_buffer.size())) | ||
| pos = working_buffer.end(); | ||
| else | ||
| pos = working_buffer.begin() + target_offset; |
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.
The main change in here is to change
pos = working_buffer.begin() + target_offset;
to
if (unlikely(target_offset > working_buffer.size()))
pos = working_buffer.end();
else
pos = working_buffer.begin() + target_offset;
| // If we have already seek to EOF, then working_buffer was cleared | ||
| if (target_frame == current_frame && working_buffer.size() > 0) | ||
| { | ||
| if (unlikely(target_offset > working_buffer.size())) | ||
| pos = working_buffer.end(); | ||
| else | ||
| pos = working_buffer.begin() + target_offset; | ||
| return offset; | ||
| } |
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.
The change in here is change
if (target_frame == current_frame)
{
pos = working_buffer.begin() + target_offset;
return offset;
}
to
// If we have already seek to EOF, then working_buffer was cleared
if (target_frame == current_frame && working_buffer.size() > 0)
{
if (unlikely(target_offset > working_buffer.size()))
pos = working_buffer.end();
else
pos = working_buffer.begin() + target_offset;
return offset;
}
Signed-off-by: JaySon-Huang <tshent@qq.com>
Signed-off-by: JaySon-Huang <tshent@qq.com>
Signed-off-by: JaySon-Huang <tshent@qq.com>
JaySon-Huang
left a comment
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.
LGTM
|
/retest |
|
[APPROVALNOTIFIER] This PR is APPROVED This pull-request has been approved by: JaySon-Huang, JinheLin The full list of commands accepted by this bot can be found here. The pull request process is described here DetailsNeeds approval from an approver in each of these files:
Approvers can indicate their approval by writing |
[LGTM Timeline notifier]Timeline:
|
|
In response to a cherrypick label: new pull request created to branch |
Signed-off-by: ti-chi-bot <ti-community-prow-bot@tidb.io>
|
In response to a cherrypick label: new pull request created to branch |
close #10340 1. In `FramedChecksumReadBuffer::doSeek`, add guard check for `working_buffer` size and `target_offset`. If the working_buffer is cleared, then re-seek the working buffer according to the offset and load data from the underlying file again. 2. In order to support the behavior above, `S3RandomAccessFile::seekImpl` support seek backward, which is implemented by reopening the file again 3. Add retry when reading from S3 meet errno=115, EINPROGRESS Signed-off-by: JaySon-Huang <tshent@qq.com> Co-authored-by: JaySon <tshent@qq.com> Co-authored-by: JaySon-Huang <tshent@qq.com>
What problem does this PR solve?
Issue Number: close #10340
Problem Summary:
When there are multiple NULL rows of Strings-like column or vector-like column, TiFlash may save some "empty blocks" into the DMFile. And it happen to be the "empty blocks" are stored at the end of the DMFile.
When TiFlash try to read data from disk,
DMFileReader::readFromDiskwill first callFramedChecksumReadBuffer::doSeekand seek to the "empty block" at the file end. The working_buffer will be release because we read to the end of the file. When TiFlash try to seek to the next "empty block",posmove forward the released working_buffer, leading to reading random data and cause random failure.tiflash/dbms/src/Storages/DeltaMerge/File/DMFileReader.cpp
Lines 542 to 555 in 76a4ec4
tiflash/dbms/src/IO/Checksum/ChecksumBuffer.h
Lines 436 to 440 in dce9588
What is changed and how it works?
Check List
Tests
Side effects
Documentation
Release note