Skip to content
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

test/log: fix for crash with libc++ #20233

Merged
merged 1 commit into from
Feb 6, 2018
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/log/test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ TEST(Log, ReuseBad)
{
auto e = log.create_entry(l, 1);
auto& out = e->get_ostream();
out << (const char*)nullptr;
out << (std::streambuf*)nullptr;
Copy link
Contributor

@tchaikov tchaikov Feb 1, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@cbodley after a second thought, i feel that we are covering potential bugs. if we fail to print a logging message because of the badbit set by previous logging message printed using this TLS stream instance, it is a sign that we have a programming error when printing logging messages. because we should not print a (std::streambuf*)nullptr, should we?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As the person who noticed this bug, and having thought about this line of reasoning, I'd prefer that we reset the stream. The fact that in libstdc++ environments "nothing happens" other than recoverable stream failure after sending the nullptr, means that attention may not be drawn to a future case where we send bad data. If a case does slip in, the stream reset makes it easier to find, as well as remediating the damage.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Performance cost of the reset would be a strong reason not to do it, though. I suspect that's not an issue though?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@mattbenjamin badbit denotes irrecoverable error. so all following logging messages won't be printed. so i guess it'd be relatively easy to track back to the offending log line which was not printed?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@mattbenjamin @tchaikov
Without clear() on stream:
[ RUN ] Log.Speed_gather
[ OK ] Log.Speed_gather (1222 ms)
[ RUN ] Log.Speed_nogather
[ OK ] Log.Speed_nogather (46 ms)

With clear() on stream:
[ RUN ] Log.Speed_gather
[ OK ] Log.Speed_gather (1247 ms)
[ RUN ] Log.Speed_nogather
[ OK ] Log.Speed_nogather (45 ms)

Before TLS optimizations:
[ RUN ] Log.Speed_gather
[ OK ] Log.Speed_gather (1636 ms)
[ RUN ] Log.Speed_nogather
[ OK ] Log.Speed_nogather (49 ms)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@aclamk thank you for profiling this change. i don't feel strong either way then.

EXPECT_TRUE(out.bad()); // writing nullptr to a stream sets its badbit
log.submit_entry(e);
}
Expand Down