-
Notifications
You must be signed in to change notification settings - Fork 1.6k
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
missingdeps tool, take 2 #1331
missingdeps tool, take 2 #1331
Conversation
Thanks for the sugesstions so far. I'm also uploading example output of this tool, when run on a fairly recent chrome-linux build for the chrome target: missingdeps-chrome-output.gz The summary is:
There's one case that's arguably a false-positive: I also would like to have some sort of test for this, but don't really know where such a test (that needs an after-a-build state, basically) would hae tobe. |
Ping? |
Ping? I still believe this would be useful to have in ninja. |
Ping? This could help fix a lot of rare clean-build build flakes in the chrome gn/ninja build, see https://bugs.chromium.org/p/chromium/issues/detail?id=655123 for a list of issues found. |
I'm just a random web developer wanting to try building chromium on macOS 10.12.6 using the instructions at https://chromium.googlesource.com/chromium/src/+/67.0.3360.2/docs/mac_build_instructions.md, and running into issues. Hoping that any efforts to reduce flakiness / missing deps can be merged, so +1 on the ping. (note: this was not enough to help me fix my issue - error was specifically |
I just ran into missing mojom.h files in a Chromium build and I wonder if this tool would have caught the problem when it was introduced. This seems like a good thing to have so I hope some maintainer can take a look. |
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.
Can I ask you to add some tests showing the behavior of this new tool?
Thanks for taking a look. What would be the preferred form of these tests? My initial idea was that to show the behavior, I'd need several build directories with manually written ninja files for some types of mistakes. Then from some runner script I'd build in each of these and then run the tool to make sure I get the expected diagnostic. Would that be okay? I don't recall anything quite like it in the repo, so I'm not quite sure where I'd put it. Something like this, assuming there's a generator for foo.h but foo.o doesn't dep on it:
then repeated for a few other cases. |
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.
I'd rather to have more unittest like test.
Not sure if this is what you're looking for, but there's https://github.com/ninja-build/ninja/blob/master/misc/output_test.py which runs the ninja binary on a temporary file and checks its output. |
Admittedly, the timing is not great with regards to me being able to spend as much time as I'd like on this. That said, I've rebased to master and fixed some minor issues, but will need a while for the tests. The "main" obstacle is that the code uses classes like ImplicitDepLoader which want to load a real file and aren't triviallyfed test data; I guess I can use a temp file for now as I see some tests do that. |
This comment was marked as abuse.
This comment was marked as abuse.
I'm working on this and should have something this week. It will be simplifies without the "files that lack a generator target" part (-g switch) because that adds a lot of complexity that's not needed to see the primary feature of the tool. |
20da95a
to
33c25d0
Compare
Highlights from the update:
Removing -g and extracting to a separate source file simplified things a lot, and as a bonus now Windows should be able to build this without excessive ifdeffery or build config. I never found the -g tool to be very useful, it can be added later if there's a serious need. Please take a look |
Thanks for the comments so far, should be all addressed. Please let me know what I can do next to get this into a merge-able state. |
Friendly ping |
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.
Sorry, I don't have time right now to give this a closer look. I'm not sure if it's gonna make 1.10.
Thanks for replying, I understand. While I think this can be very useful, it's not something I have to rush to any particular version. I'll try to ping again in a week or a couple, maybe clean-up the branch history in the meantime (unless that's not welcome at this stage; I'm not sure how helpful/disruptive it'd be in the middle of a pull request). |
ping? |
Nice tool. Looking forward to use it when it gets merged into master. |
@jhasse friendly ping |
This PR is on the 1.11.0 milestone, I will definitely have a look at it before doing that release. Currently I'm working on 1.10.2 though, please be patient. |
That's good to hear, I'll be waitng. |
Can you rebase on master? I think I found a crash in the unit test due to an assert. |
The test crash seems to be because the test code that writes a depfile needs to be adjusted after cc79afb changed some bits in deps_log.cc |
f366f4b
to
aea49f6
Compare
ping -- this should be better now, the macos failure looks like a infra issue |
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.
Thanks! The code looks good :) There's one performance impact though:
While implicit_dep
is still preallocated, the new temporary vector depfile_deps
will grow on the fly. It's also now two loops because of the temporary vector.
Either
- show that this has no significant performance impact with an appropriate benchmark,
- or pass a callback to
LoadDepfileDeps
instead of a pointer to a vector. Call it and pass the node instead of doingdepfile_deps->push_back(node);
.
@jhasse thanks, with all the quaint pre-C++11 support going on "use a callback" is a bit less enticing than it should otherwise be but I'll probably end up doing that. I may follow up with some perf experiments later if I find the time because I do feel like one extra vector and some pointer copies there should be immaterial. |
I hope it's okay I've tried the "Allow changes from maintainers" feature of GitHub and pushed to your branch 🙈 It isn't pretty, especially |
I think the virtual function approach works out better now, especially when viewed vs the base branch. Should be little effectively no changes on the main code path now. |
friendly ping |
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.
That's a good solution :)
Extract an usable helper to load depfile dependencies without adding them to the graph.
The tool looks for targets that depend on a generated file, but do not properly specify a dependency on the generator. It needs to be run after a successful build, and will list all potential flakes that may have broken the build, but didn't due to accidental build step ordering. The search relies on the correctness of depfile and generator output information, but these are usually easier to get right than dependencies. The errors found can usually be verified as actual build flakes by trying to build the listed problematic files alone in a clean build directory. Such builds usually fail with a compile job lacking a generated file. There is some overlap between this tool and 'gn check', but not everyone uses gn, not everyone using gn uses gn check, and most importantly, gn check is more about modularity, and less about actual build-time deps without flakes. The tool needs to be run after a build completes and depfile data is collected. It may take several seconds to process, up to a dozen or two on a large, chromium-sized build.
A "missing dep path" to build.ninja is a false positive, skip reporting it.
In my tests, nested maps outperform a large map of pairs by 10-20% on a sample Chromium missingdeps run, and are arguably simpler due to fewer ifdefs needed.
release 1.11 This release adds Validation Nodes which are a new way to add jobs like linters or static analyzers to the build graph. They are added using |@ and don't produce any outputs. You can read more about the motivation and the syntax here: ninja-build/ninja#1800 Another big change is that Ninja now uses UTF-8 on Windows. This means that while previous versions of Ninja used the local ANSI encoding it will now always use UTF-8 allowing filenames and output with special characters. For this to work you'll need Windows 10 Version 1903 or newer. And for the console output to show Unicode characters you'll need to set the codepage to 65001. More information at: ninja-build/ninja#1915 Note that this is a breaking change if you relied on non-ASCII characters of the local codepage! If you want to query Ninja what codepage it uses in your generator, call `ninja -t wincodepage` and act accordingly. There are also two new tools: missingdeps: ninja-build/ninja#1331 inputs: ninja-build/ninja#1730 And as it was often requested, ninja now has a --quiet flag :) For a complete list of changes see https://github.com/ninja-build/ninja/milestone/3?closed=1
This is a tool that detects some classes of random build failure causes around generated files (in Chrome, these are usually generated headers for C/C++). It takes several seconds to run, (more if the optional scan for files with no generator is used), and allows fixing a significant number of build system issues before they happen to randomly break someone's build.
The check relies on the correctness of depfile information, and on having all generator outputs listed. These things are usually easier to get right than proper deps. There's some overlap between this and gn check, but unlike gn check, this checks the actual ninja build graph and sees all issues.
This is a redo of #1031, it's been a while so I think it maybe better to start from scratch.