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

Attempting to cross-compile for Windows on a Linux system fails when following the instructions in BUILDING.md #641

Closed
Stevie-O opened this issue Jan 12, 2023 · 6 comments
Assignees

Comments

@Stevie-O
Copy link

Have you searched the existing issues (both open and closed) in the libjpeg-turbo issue tracker to ensure that this bug report is not a duplicate?

Yes

Does this bug report describe one of the two known and unsolvable issues with the JPEG format?

No, but reading that was quite enlightening.

Clear and concise description of the bug:

Following the instructions in BUILDING.md for building a Windows version of the library on a Linux system results in an error message from CMake, rather than the desired Makefiles.

This appears to be caused by something getting confused about "the resulting code will run on a Windows system" and "the resulting files will be placed on a Windows system", so it tries to generate Makefiles that will install to drive C: on the Linux system. (More details at the bottom.)

Steps to reproduce the bug (using only libjpeg-turbo):

  1. Install x86_64-w64-ming32
  2. Install nasm
  3. Pull down libjpeg-turbo source
  4. Set up a toolchain.cmake file as specified in BUILDING.md
  5. Execute the cmake command as specified by BUILDING.md to generate the Makefiles

Image(s) needed in order to reproduce the bug (if applicable):

n/a

Expected behavior:

I get some Makefiles I can use to run make with (the next step from BUILDING.md)

Observed behavior:

I get an error:

CMake Error at /usr/share/cmake-3.18/Modules/CMakePackageConfigHelpers.cmake:261 (file):
  file RELATIVE_PATH must be passed a full path to the directory:
  c:/libjpeg-turbo-gcc64/lib/cmake/libjpeg-turbo
Call Stack (most recent call first):
  cmakescripts/BuildPackages.cmake:174 (configure_package_config_file)
  CMakeLists.txt:1554 (include)

Platform(s) (compiler version, operating system version, CPU) on which the bug was observed:

  • Debian bullseye
  • x86-64
  • cmake 3.18.4

libjpeg-turbo release(s), commit(s), or branch(es) in which the bug was observed (always test the tip of the main branch or the latest stable pre-release to verify that the bug hasn't already been fixed):

dc4a93f (current HEAD)

If the bug is a regression, the specific commit that introduced the regression (use git bisect to determine this):

n/a

Additional information:

I noticed this at the beginning of the CMake output:

-- CMAKE_INSTALL_PREFIX = c:/libjpeg-turbo-gcc64
-- CMAKE_INSTALL_BINDIR = bin (c:/libjpeg-turbo-gcc64/bin)
-- CMAKE_INSTALL_DATAROOTDIR =  (c:/libjpeg-turbo-gcc64)
-- CMAKE_INSTALL_DOCDIR = doc (c:/libjpeg-turbo-gcc64/doc)
-- CMAKE_INSTALL_INCLUDEDIR = include (c:/libjpeg-turbo-gcc64/include)
-- CMAKE_INSTALL_LIBDIR = lib (c:/libjpeg-turbo-gcc64/lib)

What appears to be happening is this:

  1. Some part of the process says "oh we're building for Windows, stuff needs to be installed to drive C:"
  2. Later on, when trying to define make install, it says "okay files go c:/libjpeg-turbo-gcc64/whatever, use that"
  3. CMake treats that path as a Unix path; since it doesn't start with '/' it considers it to be a non-absolute path and errors out

When I added the following line my toolchain.cmake, everything was happy:

set(CMAKE_INSTALL_PREFIX /home/stevie/libjpeg-turbo-git/build)

CMake ran without errors. make ran without errors. I got some DLLs and EXEs and static libraries. (Haven't tested them yet, though. Still more to go before I can do that one.)

Since the current setup doesn't work at all, I would argue that if you're building Unix Makefiles, the "install" directory should probably be a Unix-type path, since it probably means you're cross-compiling a library to link to another cross-compiled library/application (that's what I'm trying to do, anyway.)

@Stevie-O
Copy link
Author

additional oddity I just noticed:

My toolchain.cmake set CMAKE_INSTALL_PREFIX to be /home/stevie/libjpeg-turbo-git/build, but when I ran CMake, it said CMAKE_INSTALL_PREFIX was "/usr/local". Curious.

@dcommander
Copy link
Member

Since the current setup doesn't work at all, I would argue that if you're building Unix Makefiles, the "install" directory should probably be a Unix-type path, since it probably means you're cross-compiling a library to link to another cross-compiled library/application (that's what I'm trying to do, anyway.)

I'll look into it. I think it's possible to use Unix Makefiles on Windows, via MSYS, so your assumption might not be valid. Ideally the build system should detect whether MinGW is being used on a non-Windows platform and set the install prefix accordingly.

@Stevie-O
Copy link
Author

I'll look into it. I think it's possible to use Unix Makefiles on Windows, via MSYS

  1. BUILDING.md says that if you're building under MSYS, to use "MSYS Makefiles", not "Unix Makefiles".
  2. If you're doing Unixy stuff via MSYS, I'm pretty sure paths would still need to start with /. MSYS treats drive letters as mounts like /drive/c/blah/blah/blah. (I've got an MSYS setup elsewhere; I'll check that later tonight.)

@dcommander
Copy link
Member

I'll look into it. I think it's possible to use Unix Makefiles on Windows, via MSYS

  1. BUILDING.md says that if you're building under MSYS, to use "MSYS Makefiles", not "Unix Makefiles".
  2. If you're doing Unixy stuff via MSYS, I'm pretty sure paths would still need to start with /. MSYS treats drive letters as mounts like /drive/c/blah/blah/blah. (I've got an MSYS setup elsewhere; I'll check that later tonight.)

MSYS Makefiles are the preferred method, but if I recall, you can still use Unix Makefiles. Please give me a chance to look into the issue so that I can fully understand it before discussing further.

@Stevie-O
Copy link
Author

MSYS Makefiles are the preferred method, but if I recall, you can still use Unix Makefiles. Please give me a chance to look into the issue so that I can fully understand it before discussing further.

Sure. I will leave it with this:

I tried it on a (very!) clean install of MSYS2 and using Unix Makefiles worked. Note that I didn't use a toolchain.cmake file, I just followed the steps in "Build Procedure" for "Un*x".

The result was no error, but the CMake output showed this:

-- CMAKE_INSTALL_PREFIX = /opt/libjpeg-turbo
-- CMAKE_INSTALL_BINDIR = bin (/opt/libjpeg-turbo/bin)
-- CMAKE_INSTALL_DATAROOTDIR =  (/opt/libjpeg-turbo)
-- CMAKE_INSTALL_DOCDIR = doc (/opt/libjpeg-turbo/doc)
-- CMAKE_INSTALL_INCLUDEDIR = include (/opt/libjpeg-turbo/include)
-- CMAKE_INSTALL_LIBDIR = lib64 (/opt/libjpeg-turbo/lib64)
-- CMAKE_INSTALL_MANDIR = man (/opt/libjpeg-turbo/man)

So even on MSYS2, using "Unix Makefiles" uses Unix-type paths, not Windows paths.

@dcommander
Copy link
Member

Your observations above are very odd, because the build system will never set CMAKE_INSTALL_PREFIX to /opt/libjpeg-turbo unless the WIN32 CMake variable is undefined. In my testing, using both MSYS Makefiles and Unix Makefiles under MSYS2 on Windows produces the same result, as I would expect. (The CMake generator should never affect the platform variables, such as WIN32, that our build system uses to pick the default value for CMAKE_INSTALL_PREFIX.) I was hoping that the MSYS CMake variable would identify whether I was building in an MSYS environment, but no such luck.

The CMAKE_CROSSCOMPILING variable does detect the difference (it is TRUE when building with MinGW on Linux and FALSE when building with MinGW on Windows), but that variable is unreliable. You could use the same toolchain file on a Windows machine, and because CMAKE_SYSTEM_NAME was set manually, CMAKE_CROSSCOMPILING would be TRUE even though you aren't actually cross-compiling. I think the safest bet would simply be to modify BUILDING.md so that the build recipes in question specify a Un*x-ish path for CMAKE_INSTALL_PREFIX. MinGW builds on Linux are a special case, anyhow, and any default prefix we chose would likely not be the one the user wants.

dcommander added a commit that referenced this issue Jan 28, 2023
The default install prefix when building under MinGW is chosen based on
the needs of the official build system, which uses MSYS2 to generate
Windows installer packages that install under c:\libjpeg-turbo-gcc[64].
However, attempting to configure the build with that install prefix on
a Un*x machine causes a CMake error.

Fixes #641
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants