eclipse-openj9 / openj9

Eclipse OpenJ9: A Java Virtual Machine for OpenJDK that's optimized for small footprint, fast start-up, and high throughput. Builds on Eclipse OMR (https://github.com/eclipse/omr) and combines with the Extensions for OpenJDK for OpenJ9 repo.
Other
3.27k stars 721 forks source link

Path length issue on windows when using CMake #7932

Open dnakamura opened 4 years ago

dnakamura commented 4 years ago

For source files which are not under the source directory of the current project (ie referencing openj9 source files from omr, or vice versa). CMake encodes the full path in the object name. This is an issue on windows as we currently use the openjdk fixpath program to launch the compiler. Fixpath indiscriminately replaces /cygdrive/X/ with X:/, even if it appears in the middle of a string. This yields an invalid path, since it has a : in the middle of it.

However if the source tree path is long enough, the full path to the object becomes very long, and in order to avoid PATH_MAX, cmake will abbreviate the path by replacing the common directory ie /cygdrive/c/path/to/jdk by its string hash, thus removing the /cygdrive/c meaning we no longer have an valid path

pshipton commented 4 years ago

@keithc-ca

keithc-ca commented 4 years ago

an invalid path, since it has a : in the middle of it

If the argument did reference a path (e.g. -I/cygdrive/c/...) that mapping (to -IC:/...) is correct. We don't have any files or directories named 'cygdrive' and can think of no good reason to change that. I don't see a problem.

removing the /cygdrive/c meaning we no longer have an invalid path

I assume you meant to say 'valid' instead of 'invalid'.

@dnakamura Can you share an example of a path using its 'string hash'?

dnakamura commented 4 years ago

We don't have any files or directories named 'cygdrive'

We don't however under some circumstances cmake will use the full path to the source file as part of the output object path. Object files for a target get generated into <CMAKE_CURRENT_BINARY_DIR>/CMakeFiles/<TARGET_NAME>.dir. Object files are given paths that reflect the relative path between the source file and the source dir. eg foo.c will be <OBJECT_DIR>/foo.c.o bar/baz.c -> <OBJECT_DIR>/bar/baz.c.o.

However, for source files outside of the project source tree the full path is used instead. so /usr/share/src/foo.c -> <OBJECT_DIR>/usr/share/src/foo.c.o

Example: If JDK extensions are checked out in /cygdrive/c/Users/Devin/source/jdk/openj9-openjdk-jdk11 The CMAKE_CURRENT_BINARY_DIR for the omrcore library is: /cygdrive/c/Users/Devin/source/jdk/openj9-openjdk-jdk11/build/vm/runtime/omr/omr and the object files get generated into <BINARY_DIR>/CMakeFiles/omrcore.dir. The object file for LanguageVMGlue.c from openj9 is: <OBJECT_DIR>/cygdrive/c/Users/Devin/source/jdk/openj9-openjdk-jdk11/openj9/gc_glue_java/LanguageVMGlue.c.o. However if we change the directory where the jdk is checked out to be: /cygdrive/c/Users/Devin/source/jdk-with-longer-path-name/openj9-openjdk-jdk11, the name of the object file becomes: <OBJECT_DIR>/c01690375b6d0e807acbed968d0b5991/runtime/gc_glue_java/LanguageVMGlue.c.o

keithc-ca commented 4 years ago

Is there a way to force cmake to always use string hashes for derived files? That would avoid the problem of cygdrive appearing as a path segment other than at the beginning.