-
Notifications
You must be signed in to change notification settings - Fork 533
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
[Xamarin.Android.Build.Tasks] Quote Aot Paths (again) #5979
Conversation
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 think we could make a test that uses this to create a symbolic link to the NDK:
https://github.com/xamarin/xamarin-android/blob/main/tools/xabuild/SymbolicLink.cs
And use a path with spaces.
Did we change something that broke this?
Might also fix #5764 |
src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/AotTests.cs
Outdated
Show resolved
Hide resolved
Fixes dotnet#5964 We missed a few paths which might need to be quoted in order to handle spaces in the paths. ``` 2021-05-28T22:15:09.3191452Z [aot-compiler stdout] Executing the native linker: "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE" -Bsymbolic -shared -o obj\Release\110\aot\armeabi-v7a\libaot-Xamarin.AndroidX.CardView.dll.so.tmp "obj\Release\110\aot\armeabi-v7a\Xamarin.AndroidX.CardView.dll\temp-llvm.o" obj\Release\110\aot\armeabi-v7a\Xamarin.AndroidX.CardView.dll\temp.s.o -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\..\sysroot\usr\lib\arm-linux-androideabi "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x\libgcc.a" "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib\libc.so" "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib\libm.so" 2021-05-28T22:15:09.3195848Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory 2021-05-28T22:15:09.3197593Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x: No such file or directory 2021-05-28T22:15:09.3199375Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory 2021-05-28T22:15:09.3200935Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib: No such file or directory 2021-05-28T22:15:09.3202549Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory 2021-05-28T22:15:09.3204244Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\..\sysroot\usr\lib\arm-linux-androideabi: No such file or directory 2021-05-28T22:15:09.3205865Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lunwind 2021-05-28T22:15:09.3207138Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lcompiler_rt-extras 2021-05-28T22:15:09.3208785Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lgcc_real 2021-05-28T22:15:09.3210086Z [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -ldl ``` So lets quote ALL the things.
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.
Tested this locally, and it seems to be working:
Task Aot 26.276s
...
AndroidNdkDirectory = C:\src\xamarin-android\bin\TestDebug\temp\SDK Ümläüts\ndk\
EnableLLVM = True
...
Build succeeded.
Duration = 36.598 s
Fixes: https://github.com/xamarin/xamarin-android/issues/5964
Context: https://devdiv.visualstudio.com/DevDiv/_workitems/edit/1336413
Context: accc846e35ccc2b21e2a472d51ab58ed0682643a
Context: 8923c11b04ef52bbf238955cefdb9995c5b5ed38
Context: 9b928f9f5fb097d8c98b7a389dbfa76846ed7ed3
Customers report that when building a project:
1. On Windows
2. With Visual Studio 16.10, *not* 16.9 or earlier
3. In Release configuration
4. With `$(AotAssemblies)`=True *and* `$(EnableLLVM)`=True
5. With the NDK installed into a directory containing spaces
then the app fails to build:
[aot-compiler stdout] Executing the native linker: "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE" -Bsymbolic -shared -o obj\Release\110\aot\armeabi-v7a\libaot-Xamarin.AndroidX.CardView.dll.so.tmp "obj\Release\110\aot\armeabi-v7a\Xamarin.AndroidX.CardView.dll\temp-llvm.o" obj\Release\110\aot\armeabi-v7a\Xamarin.AndroidX.CardView.dll\temp.s.o -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\..\sysroot\usr\lib\arm-linux-androideabi "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x\libgcc.a" "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib\libc.so" "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib\libm.so"
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x: No such file or directory
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib: No such file or directory
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\..\sysroot\usr\lib\arm-linux-androideabi: No such file or directory
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lunwind
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lcompiler_rt-extras
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lgcc_real
[aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -ldl
The *immediate* cause of the failure is path quoting: the
`arm-linux-androideabi-ld.EXE` invocation contains:
-LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x
This value is not quoted, and parts of that path are seen in the
error messages:
error: cannot open Files: No such file or directory
error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x: No such file or directory
"So", we say, "let's quote those paths!"
Update the `<Aot/>` task so that *all* the paths passed to Mono in the
`ld-flags` parameter are quoted, not just `libgcc.a`, `libc.so`, and
`libm.so`. This fixes the above linker invocation.
Additionally, update the `AotTests` test fixture so that when the
tests run on Windows, Android SDK and NDK installation locations are
symlinked into a directory containing spaces and Ümläüts.
These "SDK Ümläüts" directories are then used by the unit tests.
This helps *ensure* that we're appropriately wrapping paths, by
ensuring that the SDK & NDK are in a directory with spaces.
We don't (yet) use these "SDK Ümläüts" for macOS unit tests because
the Android NDK `aarch64-linux-android21-clang` & related scripts
don't properly quote paths either:
`dirname $0`/clang --target=aarch64-linux-android21 "$@"
which means an `SDK Ümläüts/ndk/…/aarch64-linux-android21-clang`
invocation fails with:
usage: dirname path
TODO: address this shortcoming, by skipping
`aarch64-linux-android21-clang` and instead directly executing
`…/clang --target=aarch64-linux-android21`.
---
…except. Except.
Except a lot of this doesn't *quite* make sense.
Lack of path quoting, *in and of itself*, is readily explainable and
plainly observed here.
The problem is that `ld-flags` construction hasn't changed much since
commit 8923c11b, in 2019-Sep-4 (21 months ago!), in particular the
`libs.Add($"-L{toolchainLibDir}")` and
`libs.Add($"-L{androidLibPath}")` statements. Commit 9b928f9f
changed this slightly, wrapping `libgcc.a`/etc. with quotes, but did
*not* touch `toolchainLibDir` or `androidLibPath`, both of which are
responsible for the `-L…` values implicated in the above errors.
Thus, we are getting customer complaints related to AOT path quoting
when none of the relevant code has changed between d16-9 and d16-10.
The only AOT-related change is accc846e, which added support to pass
the new-to-mono `ld-name` option for AOT. `ld-name` *doesn't*
involve the directory name, and thus doesn't seem relevant here.
We *know* `ld-flags` is *involved*, because updating the `ld-flags`
value we provide to mono fixes the issue. However, is this a
*fix* or a *workaround*? ¯\_(ツ)_/¯
Additionally, *why* did this start failing with d16-10?
* Xamarin.Android change that isn't "obviously" related to AOT?
* Mono changes?
https://github.com/mono/mono/compare/5e9cb6d1c1de430965312927d5aed7fcb27bfa73...b4a385816ed4f1398d0184c38f19f560e868fd80
There are no "obvious" changes in behavior related to `ld-flags`
or `ld_flags`, nor anything else "obvious" that would alter
behavior.
* "Environment" change, e.g. in d16-9 the NDK was installed into a
directory that lacked spaces, while in d16-10 the NDK is now
installed into a directory containing spaces?
There *may* be something here, but it's hard to say.
The [GitHub Actions Microsoft Windows Server 2019 Datacenter][0]
environment lists the NDK installation location as a path with
*no* spaces:
C:\Android\android-sdk\ndk\22.1.7171670
Yet we have a report of the same "path quoting" failure happening
["on Github actions"][1], referencing a path that differs from
the documented path:
C:\Program Files (x86)\Android\android-sdk\ndk\21.4.7075529\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x
Why does the documentation mention `C:\Android`, while
`C:\Program Files (x86)` is used?
Did our NDK path lookup logic change?
We don't currently know why things started blowing up in
Visual Studio 16.10. Investigation is ongoing.
[0]: https://github.com/actions/virtual-environments/blob/2823a3cb6a62cc74961527bdf7623b4b9afb4107/images/win/Windows2019-Readme.md
[1]: https://github.com/xamarin/xamarin-android/issues/5964#issuecomment-853068001
|
Fixes: #5964 Context: https://devdiv.visualstudio.com/DevDiv/_workitems/edit/1336413 Context: accc846 Context: 8923c11 Context: 9b928f9 Customers report that when building a project: 1. On Windows 2. With Visual Studio 16.10, *not* 16.9 or earlier 3. In Release configuration 4. With `$(AotAssemblies)`=True *and* `$(EnableLLVM)`=True 5. With the NDK installed into a directory containing spaces then the app fails to build: [aot-compiler stdout] Executing the native linker: "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE" -Bsymbolic -shared -o obj\Release\110\aot\armeabi-v7a\libaot-Xamarin.AndroidX.CardView.dll.so.tmp "obj\Release\110\aot\armeabi-v7a\Xamarin.AndroidX.CardView.dll\temp-llvm.o" obj\Release\110\aot\armeabi-v7a\Xamarin.AndroidX.CardView.dll\temp.s.o -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\..\sysroot\usr\lib\arm-linux-androideabi "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x\libgcc.a" "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib\libc.so" "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib\libm.so" [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\..\sysroot\usr\lib\arm-linux-androideabi: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lunwind [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lcompiler_rt-extras [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lgcc_real [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -ldl The *immediate* cause of the failure is path quoting: the `arm-linux-androideabi-ld.EXE` invocation contains: -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x This value is not quoted, and parts of that path are seen in the error messages: error: cannot open Files: No such file or directory error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x: No such file or directory "So", we say, "let's quote those paths!" Update the `<Aot/>` task so that *all* the paths passed to Mono in the `ld-flags` parameter are quoted, not just `libgcc.a`, `libc.so`, and `libm.so`. This fixes the above linker invocation. Additionally, update the `AotTests` test fixture so that when the tests run on Windows, Android SDK and NDK installation locations are symlinked into a directory containing spaces and Ümläüts. These "SDK Ümläüts" directories are then used by the unit tests. This helps *ensure* that we're appropriately wrapping paths, by ensuring that the SDK & NDK are in a directory with spaces. We don't (yet) use these "SDK Ümläüts" for macOS unit tests because the Android NDK `aarch64-linux-android21-clang` & related scripts don't properly quote paths either: `dirname $0`/clang --target=aarch64-linux-android21 "$@" which means an `SDK Ümläüts/ndk/…/aarch64-linux-android21-clang` invocation fails with: usage: dirname path TODO: address this shortcoming, by skipping `aarch64-linux-android21-clang` and instead directly executing `…/clang --target=aarch64-linux-android21`. --- …except. Except. Except a lot of this doesn't *quite* make sense. Lack of path quoting, *in and of itself*, is readily explainable and plainly observed here. The problem is that `ld-flags` construction hasn't changed much since commit 8923c11, in 2019-Sep-4 (21 months ago!), in particular the `libs.Add($"-L{toolchainLibDir}")` and `libs.Add($"-L{androidLibPath}")` statements. Commit 9b928f9 changed this slightly, wrapping `libgcc.a`/etc. with quotes, but did *not* touch `toolchainLibDir` or `androidLibPath`, both of which are responsible for the `-L…` values implicated in the above errors. Thus, we are getting customer complaints related to AOT path quoting when none of the relevant code has changed between d16-9 and d16-10. The only AOT-related change is accc846, which added support to pass the new-to-mono `ld-name` option for AOT. `ld-name` *doesn't* involve the directory name, and thus doesn't seem relevant here. We *know* `ld-flags` is *involved*, because updating the `ld-flags` value we provide to mono fixes the issue. However, is this a *fix* or a *workaround*? ¯\_(ツ)_/¯ Additionally, *why* did this start failing with d16-10? * Xamarin.Android change that isn't "obviously" related to AOT? * Mono changes? mono/mono@5e9cb6d...b4a3858 There are no "obvious" changes in behavior related to `ld-flags` or `ld_flags`, nor anything else "obvious" that would alter behavior. * "Environment" change, e.g. in d16-9 the NDK was installed into a directory that lacked spaces, while in d16-10 the NDK is now installed into a directory containing spaces? There *may* be something here, but it's hard to say. The [GitHub Actions Microsoft Windows Server 2019 Datacenter][0] environment lists the NDK installation location as a path with *no* spaces: C:\Android\android-sdk\ndk\22.1.7171670 Yet we have a report of the same "path quoting" failure happening ["on Github actions"][1], referencing a path that differs from the documented path: C:\Program Files (x86)\Android\android-sdk\ndk\21.4.7075529\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x Why does the documentation mention `C:\Android`, while `C:\Program Files (x86)` is used? Did our NDK path lookup logic change? We don't currently know why things started blowing up in Visual Studio 16.10. Investigation is ongoing. [0]: https://github.com/actions/virtual-environments/blob/2823a3cb6a62cc74961527bdf7623b4b9afb4107/images/win/Windows2019-Readme.md [1]: #5964 (comment)
Fixes: #5964 Context: https://devdiv.visualstudio.com/DevDiv/_workitems/edit/1336413 Context: accc846 Context: 8923c11 Context: 9b928f9 Customers report that when building a project: 1. On Windows 2. With Visual Studio 16.10, *not* 16.9 or earlier 3. In Release configuration 4. With `$(AotAssemblies)`=True *and* `$(EnableLLVM)`=True 5. With the NDK installed into a directory containing spaces then the app fails to build: [aot-compiler stdout] Executing the native linker: "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE" -Bsymbolic -shared -o obj\Release\110\aot\armeabi-v7a\libaot-Xamarin.AndroidX.CardView.dll.so.tmp "obj\Release\110\aot\armeabi-v7a\Xamarin.AndroidX.CardView.dll\temp-llvm.o" obj\Release\110\aot\armeabi-v7a\Xamarin.AndroidX.CardView.dll\temp.s.o -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\..\sysroot\usr\lib\arm-linux-androideabi "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x\libgcc.a" "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib\libc.so" "C:\Program Files (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib\libm.so" [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\platforms\android-21\arch-arm\usr\lib: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open Files: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\..\sysroot\usr\lib\arm-linux-androideabi: No such file or directory [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lunwind [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lcompiler_rt-extras [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -lgcc_real [aot-compiler stderr] C:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\bin\arm-linux-androideabi-ld.EXE: error: cannot find -ldl The *immediate* cause of the failure is path quoting: the `arm-linux-androideabi-ld.EXE` invocation contains: -LC:\Program Files (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x This value is not quoted, and parts of that path are seen in the error messages: error: cannot open Files: No such file or directory error: cannot open (x86)\Android\android-sdk\ndk-bundle\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x: No such file or directory "So", we say, "let's quote those paths!" Update the `<Aot/>` task so that *all* the paths passed to Mono in the `ld-flags` parameter are quoted, not just `libgcc.a`, `libc.so`, and `libm.so`. This fixes the above linker invocation. Additionally, update the `AotTests` test fixture so that when the tests run on Windows, Android SDK and NDK installation locations are symlinked into a directory containing spaces and Ümläüts. These "SDK Ümläüts" directories are then used by the unit tests. This helps *ensure* that we're appropriately wrapping paths, by ensuring that the SDK & NDK are in a directory with spaces. We don't (yet) use these "SDK Ümläüts" for macOS unit tests because the Android NDK `aarch64-linux-android21-clang` & related scripts don't properly quote paths either: `dirname $0`/clang --target=aarch64-linux-android21 "$@" which means an `SDK Ümläüts/ndk/…/aarch64-linux-android21-clang` invocation fails with: usage: dirname path TODO: address this shortcoming, by skipping `aarch64-linux-android21-clang` and instead directly executing `…/clang --target=aarch64-linux-android21`. --- …except. Except. Except a lot of this doesn't *quite* make sense. Lack of path quoting, *in and of itself*, is readily explainable and plainly observed here. The problem is that `ld-flags` construction hasn't changed much since commit 8923c11, in 2019-Sep-4 (21 months ago!), in particular the `libs.Add($"-L{toolchainLibDir}")` and `libs.Add($"-L{androidLibPath}")` statements. Commit 9b928f9 changed this slightly, wrapping `libgcc.a`/etc. with quotes, but did *not* touch `toolchainLibDir` or `androidLibPath`, both of which are responsible for the `-L…` values implicated in the above errors. Thus, we are getting customer complaints related to AOT path quoting when none of the relevant code has changed between d16-9 and d16-10. The only AOT-related change is accc846, which added support to pass the new-to-mono `ld-name` option for AOT. `ld-name` *doesn't* involve the directory name, and thus doesn't seem relevant here. We *know* `ld-flags` is *involved*, because updating the `ld-flags` value we provide to mono fixes the issue. However, is this a *fix* or a *workaround*? ¯\_(ツ)_/¯ Additionally, *why* did this start failing with d16-10? * Xamarin.Android change that isn't "obviously" related to AOT? * Mono changes? mono/mono@5e9cb6d...b4a3858 There are no "obvious" changes in behavior related to `ld-flags` or `ld_flags`, nor anything else "obvious" that would alter behavior. * "Environment" change, e.g. in d16-9 the NDK was installed into a directory that lacked spaces, while in d16-10 the NDK is now installed into a directory containing spaces? There *may* be something here, but it's hard to say. The [GitHub Actions Microsoft Windows Server 2019 Datacenter][0] environment lists the NDK installation location as a path with *no* spaces: C:\Android\android-sdk\ndk\22.1.7171670 Yet we have a report of the same "path quoting" failure happening ["on Github actions"][1], referencing a path that differs from the documented path: C:\Program Files (x86)\Android\android-sdk\ndk\21.4.7075529\toolchains\llvm\prebuilt\windows-x86_64\lib\gcc\arm-linux-androideabi\4.9.x Why does the documentation mention `C:\Android`, while `C:\Program Files (x86)` is used? Did our NDK path lookup logic change? We don't currently know why things started blowing up in Visual Studio 16.10. Investigation is ongoing. [0]: https://github.com/actions/virtual-environments/blob/2823a3cb6a62cc74961527bdf7623b4b9afb4107/images/win/Windows2019-Readme.md [1]: #5964 (comment)
Fixes #5964
In commit accc846 we missed a few paths which might need to be quoted in order to handle
spaces in the paths. As a result users are seeing errors like the one below.
So lets quote ALL the things. Also update the Aot Unit tests to use Sdk/Ndk paths with spaces in them. We do this
by creating a symlink to the existing Sdk/Ndk directories in the Unit Test temp directory.
This highlighted a bug in the MacOS ndk were the
aarch64-linux-android21-clang
script would return the followingerror
This is because the bash script on MacOS does not support paths with spaces... very similar to many of the .bat files
on Windows. So for now we are disabling the use of Sdk/Ndk paths with spaces on non windows platforms until a
fix can be found. These changes should allow windows users to use Aot again though since its mostly windows users
who have the Sdk/Ndk directories in locations where spaces are in the path.