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

CMake C compiler ABI detection fails with GCC #6960

Closed
Leif-W opened this issue Jun 5, 2021 · 7 comments · Fixed by #14437
Closed

CMake C compiler ABI detection fails with GCC #6960

Leif-W opened this issue Jun 5, 2021 · 7 comments · Fixed by #14437
Labels
bug report Something is not working properly

Comments

@Leif-W
Copy link

Leif-W commented Jun 5, 2021

Problem description

Trying to get cmake to use gcc rather than clang fails with Platform/Android/abi--GNU can't be found, due to empty ${CMAKE_ANDROID_ARCH_ABI}.

Steps to reproduce

  • Install cmake from termux repo.
  • Install gcc from its-pointless repo.
  • cmake always seems to prefer clang by default.
  • Change usr/bin/gcc to link to gcc-10 rather than clang-12.
  • Run the setup-parchforgcc script from its-pontless.
  • Simple hello-world project dir, with src/hello-world.c and src/CMakeLists.txt files.
  • Call cmake with either CC=gcc ... or ... -DCMAKE_C_COMPILER=/full/path/to/gcc, same fail result.
  • Error in Android-GNU.cmake saying Platform/Android/abi--GNU can't be found.
  • ${CMAKE_ANDROID_ARCH_ABI} empty when trying to specify gcc.
  • Using clang with either method builds the build system.

Not sure of root cause at this point. Seeking clarification.

Expected behavior

Expect to be able to freely switch between gcc, clang, or any other compiler.

Additional information

Create project:

mkdir -p hello-world/{src,bin}
cd hello-world
echo -e '#include <stdio.h>

int main(void) {
\tprintf("Hello, World!\\n");
\treturn 0;
}' > src/hello-world.c
echo 'cmake_minimum_required(VERSION 3.20)
project(hello-world LANGUAGES C)
add_executable(hello-world hello-world.c)' > src/CMakeLists.txt

Build:

rm -rf bin/*
cmake -DCMAKE_C_COMPILER=`which gcc` -S src -B bin -DCMAKE_BUILD_TYPE=Release

Output:

-- The C compiler identification is GNU 10.2.0
CMake Error at /data/data/com.termux/files/usr/share/cmake-3.20/Modules/Platform/Android-GNU.cmake:29 (include):
  include could not find requested file:

    Platform/Android/abi--GNU
Call Stack (most recent call first):
  /data/data/com.termux/files/usr/share/cmake-3.20/Modules/Platform/Android-GNU-C.cmake:1 (include)
  /data/data/com.termux/files/usr/share/cmake-3.20/Modules/CMakeCInformation.cmake:48 (include)
  CMakeLists.txt:2 (project)


-- Detecting C compiler ABI info
CMake Error at /data/data/com.termux/files/usr/share/cmake-3.20/Modules/Platform/Android-GNU.cmake:29 (include):
  include could not find requested file:

    Platform/Android/abi--GNU
Call Stack (most recent call first):
  /data/data/com.termux/files/usr/share/cmake-3.20/Modules/Platform/Android-GNU-C.cmake:1 (include)
  /data/data/com.termux/files/usr/share/cmake-3.20/Modules/CMakeCInformation.cmake:48 (include)
  /data/data/com.termux/files/home/hello-world/bin/CMakeFiles/CMakeTmp/CMakeLists.txt:2 (project)


CMake Error at /data/data/com.termux/files/usr/share/cmake-3.20/Modules/CMakeDetermineCompilerABI.cmake:49 (try_compile):
  Failed to configure test project build system.
Call Stack (most recent call first):
  /data/data/com.termux/files/usr/share/cmake-3.20/Modules/CMakeTestCCompiler.cmake:26 (CMAKE_DETERMINE_COMPILER_ABI)
  CMakeLists.txt:2 (project)


-- Configuring incomplete, errors occurred!
See also "/data/data/com.termux/files/home/hello-world/bin/CMakeFiles/CMakeOutput.log".

@Grimler91 Grimler91 added the bug report Something is not working properly label Jun 5, 2021
@Grimler91
Copy link
Member

Until we have a proper fix you can edit $PREFIX/share/cmake-3.20/Modules/Platform/Android-GNU.cmake and replace

include(Platform/Android/abi-${CMAKE_ANDROID_ARCH_ABI}-GNU)

with

include(Platform/Android/abi-arm64-v8a-GNU)

(change arm64-v8a to armeabi-v7a, x86 or x86_64 if you are on arm, i686 or x86_64, respectively)

@Leif-W
Copy link
Author

Leif-W commented Jun 5, 2021

Not sure if I understand the cmake modules. Reading the errors, I started with the first error, first file mentioned, Android-GNU.cmake. Yes, CMAKE_ANDROID_ARCH_ABI isn't set there. Looking at all files that set CMAKE_ANDROID_ARCH_ABI, only Android-Determine.cmake sets it. I started at the top, moved down one statement at a time, throwing "HERE" messages message("HERE: ${CMAKE_ANDROID_ARCH_ABI}"), and this value is not set at the beginning, as expected, but then doesn't call HERE messages rather soon, because it return()s. The only clue is a comment.

# Natively compiling on an Android host doesn't use the NDK cross-compilation
# tools.
if(CMAKE_HOST_SYSTEM_NAME STREQUAL "Android")
  return()
endif()

The thing is, I don't understand yet why Android-Clang.cmake works, as it is very similar. Maybe I was looking into the wrong file? But Android-GNU.cmake is the only file looking for files of the pattern regexp: abi-.*-GNU.cmake. So it has to be here somewhere.

This calls (include()s) Android-Common.cmake, which references CMAKE_ANDROID_ARCH_ABI just once, though seemingly unrelated. But it occurs after a macro() call, possibly setting it? Seems unrelated.

Also looked in CMakeTestCCompiler.cmake and CMakeDetermineCompilerABI.cmake, but not sure if I see anything.

Hard coded value might work-around, but it bugs me not understanding how Clang works, seemingly bypassing the search for arch abi. Maybe the GNU script is called in error or something? Seems like it shouldn't be called unless cross-compiling... Hmm, but Android-Clang.cmake is included twice.

There's a lot of extra NDK related code in the Clang module vs the GNU module. Not sure yet what it all does.

Edit:

Basically, I just copy/pasted Android-Clang.cmake to Android-GNU.cmake, replaced text Clang with GNU, clang with gnu, and commented out an if() block referencing LLVM TRIPLE, whatever that is. CMake appears to build the build system properly. Not sure if right or clean, but seems to work, nothing hard coded.

@finagolfin
Copy link
Member

The solution is very simple, Android-Clang.cmake currently does nothing in Termux. I didn't bother adding that for Android-GNU as neither Termux or the NDK use gcc, feel free to add it yourself and submit a patch.

@Leif-W
Copy link
Author

Leif-W commented Jun 6, 2021

@buttaface

The solution is very simple, Android-Clang.cmake currently does nothing in Termux.

Exit early, and so no include any Platform/Android/abi--.cmake files, is that the idea? Will submit a patch soon.

@stale

This comment has been minimized.

@stale stale bot added the wontfix Issue won't be fixed label Nov 18, 2021
@thunder-coding thunder-coding added not stale and removed wontfix Issue won't be fixed labels Nov 19, 2021
@yxj-github-437
Copy link

In Android-Clang.cmake
line 46-49

if(CMAKE_HOST_SYSTEM_NAME STREQUAL "Android")
  macro(__android_compiler_clang lang)
  endmacro()
  return()
endif()

so in Android-GNU.cmake
line 27-31
I write

if(CMAKE_HOST_SYSTEM_NAME STREQUAL "Android")
  macro(__android_compiler_gnu lang)
  endmacro()
  return()
endif()

@finagolfin
Copy link
Member

Yep, that's all that's needed, feel free to submit a pull.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug report Something is not working properly
Projects
None yet
Development

Successfully merging a pull request may close this issue.

6 participants