This is an archive of the discontinued LLVM Phabricator instance.

[CodeView][clang] Add flag to disable emitting command line into CodeView
ClosedPublic

Authored by aeubanks on Oct 21 2022, 11:08 AM.

Details

Summary

In https://reviews.llvm.org/D80833, there were concerns about
determinism emitting the commandline into CodeView. We're actually
hitting these when running clang-cl on Linux (cross compiling) versus on
Windows (e.g. -fmessage-length being inferred on terminals).

Add -g[no-]codeview-command-line to enable/disable this feature.
It's still on by default to preserve the current state of clang.

Diff Detail

Event Timeline

aeubanks created this revision.Oct 21 2022, 11:08 AM
Herald added a project: Restricted Project. · View Herald TranscriptOct 21 2022, 11:08 AM
aeubanks requested review of this revision.Oct 21 2022, 11:08 AM
Herald added a project: Restricted Project. · View Herald TranscriptOct 21 2022, 11:08 AM
MaskRay added inline comments.Oct 21 2022, 11:10 AM
clang/lib/Driver/ToolChains/Clang.cpp
4319

This needs a test in clang/test/Driver/

Use addOptInFlag

Thanks for the patch @aeubanks and apologies for this oversight. I am wondering however if it wouldn’t make more sense to just strip this flag (-fmessage-length) from the emitted cmd-line? The goal is to provide a reproducer, this flag does not matter for that purpose.

There will be other problems like this. We don't care about having the command in the debug info and we'd rather get rid of this class of bugs Once And For All :)

aeubanks updated this revision to Diff 469733.Oct 21 2022, 1:01 PM

add driver test

Thanks for the patch @aeubanks and apologies for this oversight. I am wondering however if it wouldn’t make more sense to just strip this flag (-fmessage-length) from the emitted cmd-line? The goal is to provide a reproducer, this flag does not matter for that purpose.

+1 to what @thakis said, and doing this can cause more cache hits with slightly different flags that don't affect codegen

clang/lib/Driver/ToolChains/Clang.cpp
4319

addOptIn/OutFlag doesn't work here with the semantics I want

For -cc1, -gcodeview-command-line should control whether or not we use this feature, defaulting to not performing this feature.
But on the driver level, not specifying anything should pass -gcodeview-command-line by default (assuming EmitCodeView).

But perhaps this is confusing and we should default to -gcodeview-command-line everywhere?

aganea added inline comments.
clang/lib/Driver/ToolChains/Clang.cpp
4319

Is there a reason for having divergent initial values? true below but -gcodeview-command-line being false? They should be the same. The other question is, MSVC emits LF_BUILDINFO by default (if /Z7 is on). Not sure if we should be compatible out-of-the-box or if we should favor good cache hits? I have no problem specifying the flag on the cmd-line if it isn't on by default.

+@stefan_reinalter

aeubanks updated this revision to Diff 469954.Oct 22 2022, 8:34 PM

default to off

aeubanks added inline comments.Oct 22 2022, 8:37 PM
clang/lib/Driver/ToolChains/Clang.cpp
4319

the reason was to keep compatibility with msvc by emitting the command line by default, but I also wanted the -cc1 value to determine whether or not we actually did this

anyway, I've turned this feature off by default for now, open to reverting back to turning it on by default if people want that

thakis accepted this revision.Oct 25 2022, 10:07 AM

Thanks!

Please mention the default value of the flag in the commit message.

This revision is now accepted and ready to land.Oct 25 2022, 10:07 AM
aeubanks retitled this revision from [CodeView][clang] Add flag to disable emitting command line into CodeView to [CodeView][clang] Disable emitting command line into CodeView by default and add flag to enable.Oct 25 2022, 10:10 AM
aeubanks edited the summary of this revision. (Show Details)

We have tooling that uses this command line from the PDB. I think the conservative approach is to emit the command line by default since this is how MSVC behaves. I don't mind this flag now that I know about it, but I think we should keep the default to what MSVC does for clang-cl.

Also this should have a release note.

FWIW we do have precedent of deviating from cl.exe for determinism reasons. I think having deterministic output is a good default.

rnk added a comment.Oct 25 2022, 2:29 PM

FWIW we do have precedent of deviating from cl.exe for determinism reasons. I think having deterministic output is a good default.

This is true, but the cc1 flag isn't inherently non-deterministic. I would prefer to fix the determinism bugs instead of adding flags and more divergence.

Can we use the grecord-command-line flag here instead of adding a new one?
https://clang.llvm.org/docs/ClangCommandLineReference.html#cmdoption-clang-grecord-command-line
I understand it has different semantics. We'd record the command line differently depending on whether codeview or DWARF is in use, and potentially both ways when both are in use (🙄 ).

This is true, but the cc1 flag isn't inherently non-deterministic. I would prefer to fix the determinism bugs instead of adding flags and more divergence.

See https://reviews.llvm.org/D136474#3875546

(In other words, all known people who care about clang's determinism do not care about having the command recorded in the debug data -- and some (me :) ) mentioned concerns about determinism about the patch adding that feature. It seems weird to put those people on the hook to fix the bugs, then.)

rnk added a comment.Oct 26 2022, 8:45 AM

This is true, but the cc1 flag isn't inherently non-deterministic. I would prefer to fix the determinism bugs instead of adding flags and more divergence.

See https://reviews.llvm.org/D136474#3875546

I read that, and I'm indicating that I don't agree. Chromium's requirements are driven by its particular usage of a cross-compiling distributed build system, which may not represent the average user's needs. Ubisoft's use case is also somewhat specialized, but IMO we really ought to write down the command line in the debug info. IMO it's useful. Sorry I don't have time to construct a more persuasive argument.

If you are still set on this course and don't want to try to address the determinism other ways, this flag seems fine to me, but I don't think it should be the default behavior. Does that provide a way forward?

I read that, and I'm indicating that I don't agree. Chromium's requirements are driven by its particular usage of a cross-compiling distributed build system, which may not represent the average user's needs.

Are you saying that it's a good thing if clang produces different output on different hosts?

If you are still set on this course and don't want to try to address the determinism other ways, this flag seems fine to me, but I don't think it should be the default behavior. Does that provide a way forward?

I'm fine with not toggling the default in this patch. I'm a fan of doing one thing per patch anyways.

I read that, and I'm indicating that I don't agree. Chromium's requirements are driven by its particular usage of a cross-compiling distributed build system, which may not represent the average user's needs.

Are you saying that it's a good thing if clang produces different output on different hosts?

Objectively speaking, flags that change the terminal output, or more generally don't affect the output artifact, shouldn't be part of the reproducer. It was an oversight on my end when I initially implemented the feature. Back at Ubisoft we had the same goal as you do, ie. build for a given platform and end up with the same results, regardless of the host. But that was never completed after I left. My view is that we should first add the flag to allow disabling the reproducer, and then in subsequent patches try to remove irrelevant flags from the reproducer.

I read that, and I'm indicating that I don't agree. Chromium's requirements are driven by its particular usage of a cross-compiling distributed build system, which may not represent the average user's needs.

Are you saying that it's a good thing if clang produces different output on different hosts?

Objectively speaking, flags that change the terminal output, or more generally don't affect the output artifact, shouldn't be part of the reproducer. It was an oversight on my end when I initially implemented the feature. Back at Ubisoft we had the same goal as you do, ie. build for a given platform and end up with the same results, regardless of the host. But that was never completed after I left. My view is that we should first add the flag to allow disabling the reproducer, and then in subsequent patches try to remove irrelevant flags from the reproducer.

That sounds good to me, assuming that you have someone concrete in mind for who "we" is who's removing the irrelevant flags :) But if nobody's in charge of that at the moment, imho it makes sense to make this default-off until it no longer regresses determinism.

rnk added a comment.Oct 27 2022, 8:27 AM

That sounds good to me, assuming that you have someone concrete in mind for who "we" is who's removing the irrelevant flags :) But if nobody's in charge of that at the moment, imho it makes sense to make this default-off until it no longer regresses determinism.

That works for me, I just want to make it clear that the long term goal for the project is that we emit the command line in LF_BUILDINFO by default, rather than disabling it once and for all. If it's not ready yet, great, let's disable it and continue.

Over on Linux, this was a frequently requested feature, and you can see that we have -f and -g flags for it.

FWIW, we could probably move the terminal detection to the cc1 job. It inherits the TTY, right, so it can do the detection? I would look at how we handle fcolor-diagnostics here as reference, is that in the cc1 line or not?

That works for me, I just want to make it clear that the long term goal for the project is that we emit the command line in LF_BUILDINFO by default, rather than disabling it once and for all. If it's not ready yet, great, let's disable it and continue.

Fully on board with this :)

FWIW, we could probably move the terminal detection to the cc1 job. It inherits the TTY, right, so it can do the detection? I would look at how we handle fcolor-diagnostics here as reference, is that in the cc1 line or not?

I am fine with this plan as well. And I am willing to chip in and try to fix the issues with the current implementation since we actually use the feature.

@thakis do you mind explaining the issues you see and how to replicate them and I can have a look.

thakis added a comment.Nov 1 2022, 9:05 AM

Just to be clear, in any case, this patch here is ready to go as long as it doesn't flip the default, yes?

@thakis do you mind explaining the issues you see and how to replicate them and I can have a look.

See above (-fmessage-length gets embedded and is machine-dependent).

aeubanks updated this revision to Diff 472351.Nov 1 2022, 10:38 AM

on by default

aeubanks retitled this revision from [CodeView][clang] Disable emitting command line into CodeView by default and add flag to enable to [CodeView][clang] Add flag to disable emitting command line into CodeView.Nov 1 2022, 10:38 AM
aeubanks edited the summary of this revision. (Show Details)
rnk accepted this revision.Nov 1 2022, 12:01 PM

I'm happy with this if it works for everyone else.

thieta added a comment.Nov 3 2022, 2:41 AM

I posted https://reviews.llvm.org/D137322 to remove -fmessage-length