Repository navigation
build.sh fails when run in a directory that contains spaces #73327
Description
Activity
- ghost addeduntriagedNew issue has not been triaged by the area ownerNew issue has not been triaged by the area owner
on Aug 3, 2022 It seems like fixing that line leads to more errors later on.
Thanks for brining this to our attention. Would you mind submitting a PR with the fix? And can you please post the failures that happen when this line is fixed?
Thanks for brining this to our attention. Would you mind submitting a PR with the fix? And can you please post the failures that happen when this line is fixed?
I've already moved my repo to a path without spaces and closed the terminal so I can't tell exactly but it was an error when invoking
msbuild, so changing that one line for sure is not enough. I'll try fixing it again tomorrow.- removeduntriagedNew issue has not been triaged by the area ownerNew issue has not been triaged by the area owner
on Aug 10, 2022 Thanks for brining this to our attention. Would you mind submitting a PR with the fix? And can you please post the failures that happen when this line is fixed?
Looked into this again, the following error appears after fixing the first one, I don't really know how to fix it though:
MSBUILD : error MSB1008: Only one project can be specified. Full command line: „/media/ewa/Samsung USB/runtime/.dotnet/sdk/7.0.100-preview.7.22377.5/MSBuild.dll -maxcpucount -verbosity:m /m /nologo /clp:Summary /v:minimal /nr:true /warnaserror /p:TreatWarningsAsErrors=true /p:ContinuousIntegrationBuild=false /home/ewa/.nuget/packages/microsoft.dotnet.arcade.sdk/7.0.0-beta.22416.1/tools/Build.proj /p:Configuration=Release /p:RepoRoot=/media/ewa/Samsung USB/runtime/ /p:Restore=true /p:Build=true /p:ArcadeBuildFromSource=false /p:Rebuild=false /p:Test=false /p:Pack=false /p:IntegrationTest=false /p:PerformanceTest=false /p:Sign=false /p:Publish=false /p:Subset=clr+libs /p:TargetArchitecture=x64 /p:BuildArchitecture=x64 /p:CMakeArgs="" -distributedlogger:Microsoft.DotNet.Tools.MSBuild.MSBuildLogger,/media/ewa/Samsung USB/runtime/.dotnet/sdk/7.0.100-preview.7.22377.5/dotnet.dll*Microsoft.DotNet.Tools.MSBuild.MSBuildForwardingLogger,/media/ewa/Samsung USB/runtime/.dotnet/sdk/7.0.100-preview.7.22377.5/dotnet.dll“ Switches appended by response files: Switch: USB/runtime/ For switch syntax, type "MSBuild -help"
Try to wrap
Line 113 in 57bfe47
/p:RepoRoot=$RepoRoot ` in quotes, like
"/p:RepoRoot=$RepoRoot"Already tried, the same error.
14 remaining items
This is a bottomless Pandora's box. Manish also spent some time on this but to my knowledge no-one has yet made this work end to end. I think that in general it's a worthwhile effort so if you have some fixes that let the build proceed further, just get them merged in; once we're sure we're no longer able to make progress due to internal issues in components like MSBuild, we can follow up with the partner teams.
Alright then it's settled! I'll get a PR with fixes on our part, i.e. until the failure falls onto MSBuild.
It's possible the machine is locked down such that they can't do that kind of thing?
This is a thing in some companies so unfortunately that workaround wouldn't work for them. It's not a huge amount of places, but there are some locked down out there.
This has been quiet for a while, but I hit this exact issue today on my box and checked to see if it was documented, which brought me here. It seemed interesting, so I dug into it to see how far the rabbit hole gets.
Everything you see below was reproduced locally on linux-x64 (Fedora 44), in a worktree at a path containing a space. Take all of this with a grain of salt, since I didn't test any fixes on windows or macOS at all. Also as a side note, the line referenced in the discussion above is outdated, now
eng/build.sh:169rather than 156.In the time I spent digging, I was able to find 5 failure points downstream, and locally fix the first four, which gets
./build.sh -subset libs.native -c Releaseto exit 0 at a path with a space. Here's the gist of it:# Location Cause 1 eng/build.sh:169unquoted source $scriptroot/...2 eng/common/build.sh:277MSBuild $_InitializeToolsetword-splits, givingMSB1008: Only one project can be specified3 eng/native/functions.cmake:265-276unquoted ${exports_filename}inset_exports_linker_option4 System.IO.Compression.Native/CMakeLists.txt:95LINK_FLAGScannot carry a path with spaces5 src/coreclr/build-runtime.sh:176path is quoted, but evalre-parses the string and splits on the spaceIn light of this, I think I now get why this hasn't moved forward in a while:
-
Part of the fix is not in this repo, specifically, Item 2. It lives in
eng/common/, which afaik is mirrored fromdotnet/arcadeand is explicitly off limits here. So even the minimal path to a workinglibs.nativeneeds an arcade PR and a version flow before the runtime side can be completed. I did not see this mentioned anywhere in the thread. -
Item 4 is actually not a quoting problem.
LINK_FLAGSis a raw string that CMake passes to the linker as is, so quoting the variable in CMake source changes nothing. I confirmed that and got the identicalclang: no such file or directoryerror. What does work is switching totarget_link_options, which CMake escapes properly:-set_property(TARGET X APPEND_STRING PROPERTY LINK_FLAGS ${EXPORTS_LINKER_OPTION}) +target_link_options(X PRIVATE "${EXPORTS_LINKER_OPTION}")
I'm mentioning this specifically for anyone who tried solving this before, since quoting looks like the obvious fix and produces no visible change as far as I could tell. On top of that, I confirmed 10 sites using this exact exports pattern and 23
APPEND_STRING PROPERTY LINK_FLAGSuses in total.Is it a pandora's box like @trylek said? Kinda, but the scope isn't insane. The fix seems to be a finite set of mechanical patterns, spread across two repos and most native components. The pattern was unquoted
$varin shell, unquoted${VAR}in CMake, and theLINK_FLAGStotarget_link_optionsmigration.@ivdiazsa is still assigned from 2022. I wonder whether anyone is actively on this? Given @trylek's earlier point about landing partial fixes that let the build proceed further, I would be happy to help out incrementally, starting with the
libs.nativefix above, if that is still the preferred approach and nobody else has it in flight.What I am most worried about is regressions and testing, especially since this could be breaking. @danmoseley already said that nothing in CI covers this, so it will keep regressing regardless of how far the fixes get.
-
@ApparentlyPlus we can make incremental progress :) the first two are easy ones and can be just fixed, one in dotnet/runtime and one in dotnet/arcade. Feel free to send a PR.
@ApparentlyPlus we can make incremental progress :) the first two are easy ones and can be just fixed, one in dotnet/runtime and one in dotnet/arcade. Feel free to send a PR.
Awesome. I'll take this up asap. I'll draft a PR either tonight or tomorrow morning.
Jesus christ. I was completely wrong, and @trylek was right in 2022. This is a pandora's box. Forget everything I said above. This goes way deeper than I gave it credit for. I'm waiting to coordinate on the open PRs first before I dive deeper.
- added a commit that references this issue
on Sep 10, 2026 Howdy again, and thanks for merging both PRs @akoeplinger! Shorter comment this time, I promise. I deleted my prior ones because they were absolute and misleading, so here's a revised, hopefully better assessment.
Since iterating is back on the table, I mapped the rest of it by fixing faults one at a time, until I managed to make it compile locally. I got a full
./build.sh -c Releaseto complete from scratch at a path with a space on linux-x64 and macos-arm64. This is good news, but I am not gonna claim what I have is the full scope. Every time I did so far, more things surfaced.Turns out, this is almost purely a quoting problem. Every failure downstream is the same mistake repeated: a path handed off as a bare
$var/$(Prop)/%(Meta)into something that word splits, and each one eluded me until the one before it was fixed. That's why the file count skyrocketed.A full fix breaks down in 3 steps:
1. We need another arcade PR, this time for the installers package
Still a quoting problem, and macOS needs this. When the build packages the product on macOS it shells out to
pkgbuildandproductbuild. Those are macOS system tools, but the targets driving them aren't in this repo, they ship inside theMicrosoft.DotNet.Build.Tasks.InstallersNuGet package, which comes from arcade. Both assemble a flat command string and hand it toExec, so every path in it needs quoting:installer.build.targets:449-455,pkgbuildbundle.targets:177-183,productbuild
Important
This is not
eng/common, so there is no mirror. It has to merge in arcade, get a package release, and then that version has to flow back into runtime before macOS CI can go green. That's gonna take a while (I'd love it if someone shed some light on how long), and nothing else waits on it, so it should go up first while the rest moves.2. The
evalinbuild-commons.shshould changebuild-commons.sh:209plus the four callers. It's different in kind from the rest, and it has to happen before the other quoting fixes.The script builds the whole
gen-buildsys.shinvocation as a string and runs it througheval, so it gets parsed twice and$cmakeArgssplits on that second pass. You can't fix it from the calling side either, since a caller's quotes get eaten by the first parse. The fix is to drop the string,cmakeArgsbecomes a bash array andgen-buildsys.shis invoked directly with"${cmakeArgs[@]}".Btw, this is the only real behaviour change in the set, since some values leaned on that second parse. The iOS
armv7;armv7sone splits on the;and would have taken out the armv7 leg if I hadn't re-quoted it. It's risky, but anything I miss, the current CI will catch.I built both halves separately to check the order. Quoting without this dies at CMake configure before a single object compiles, on a line that is already quoted correctly, because the
evalate the-Dbefore CMake saw it. Theevalalone gets 1100 of 2877 objects in and dies at link. So, quoting first would look like it did nothing.3. Quotes everywhere, a full sweep of the same thing
This is 21 files, but they're all the same fix:
- CMake
LINK_FLAGS/COMMAND, 14 files (eg. one of them) - MSBuild
Exec, 6 files:crossgen-corelib.projtwice (mibc merge, then crossgen2),externals.csproj:81,Crossgen2.sfxproj:17,dotnet-host.proj:174,mono.projandnative-library.targets dotnet.sh, three bugs in 24 lines
Oh, and coincidentally,
sdk-task.sh:37-41is the same$binaryLogArgbug dotnet/arcade#17509 fixed inbuild.shthis morning, sitting one file over. I didn't see it before, otherwise I'd have fixed that too. Again, quotes.So, the arcade PR should go up next, along with the
evalfix here. If you green light it, that's another 2 relatively small PRs, then the quoting sweep and some patience until the arcade package flows into runtime. Bear in mind that green CI only confirms no regressions, not the fix itself. The fix can only be tested locally, and it will break again unless we add CI after everything.Waiting on the okay and I'm on it.
- arcade changes look reasonable to me, feel free to open a PR. once the change is merged there it will flow to dotnet/dotnet and then to dotnet/runtime, you can watch for codeflow PRs like [main] Source code updates from dotnet/dotnet #133655
- sounds reasonable. About the armv7/armv7s, that's actually dead code since we no longer build for ios/iossimulator for those platforms or i386 anymore. Logic like that can be cleaned up separately.
- sure
@akoeplinger First 2 are up, one in arcade and one in runtime. I'll do the third one once these two are green and land. Thanks for the quick replies!
Metadata
Metadata
Assignees
Labels
Type
Projects
- StatusShow more project fieldsNo status
Running in such directory results in:
It looks like this line is the cause:
https://github.com/dotnet/runtime/blob/main/eng/build.sh#L156