diff --git a/src/main/java/com/google/devtools/build/lib/rules/java/JavaStarlarkCommon.java b/src/main/java/com/google/devtools/build/lib/rules/java/JavaStarlarkCommon.java index 8067ab895de109..4dfdd2a0b95f3f 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/java/JavaStarlarkCommon.java +++ b/src/main/java/com/google/devtools/build/lib/rules/java/JavaStarlarkCommon.java @@ -22,6 +22,7 @@ import com.google.common.collect.ImmutableMap; import com.google.common.collect.Iterables; import com.google.devtools.build.lib.actions.Artifact; +import com.google.devtools.build.lib.analysis.BazelRuleAnalysisThreadContext; import com.google.devtools.build.lib.analysis.ConfiguredTarget; import com.google.devtools.build.lib.analysis.Expander; import com.google.devtools.build.lib.analysis.RuleContext; @@ -300,7 +301,7 @@ public Sequence collectNativeLibsDirs(Depset libraries, StarlarkThread t } return true; }) - .map(artifact -> artifact.getRootRelativePath().getParentDirectory().getPathString()) + .map(artifact -> artifact.getRunfilesPath().getParentDirectory().getPathString()) .distinct() .collect(toImmutableList()); return StarlarkList.immutableCopyOf(uniqueDirs); diff --git a/src/test/shell/bazel/bazel_java_test.sh b/src/test/shell/bazel/bazel_java_test.sh index 09b82deedc93c1..fe7fdab5a6b846 100755 --- a/src/test/shell/bazel/bazel_java_test.sh +++ b/src/test/shell/bazel/bazel_java_test.sh @@ -1573,32 +1573,33 @@ EOF # Build and run a java_binary that calls a C++ function through JNI. # This test exercises the built-in @bazel_tools//tools/jdk:jni target. # -# The java_binary wrapper script specifies -Djava.library.path=$runfiles/test, +# The java_binary wrapper script specifies -Djava.library.path=$runfiles/jni, # and the Java program expects to find a DSO there---except on MS Windows, # which lacks support for symbolic links. Really there needs to # be a cleaner mechanism for finding and loading the JNI library (and better # hygiene around the library namespace). By contrast, Blaze links all the # native code and the JVM into a single executable, which is an elegant solution. # -function test_jni() { - # Skip on MS Windows, as Bazel does not create a runfiles symlink tree. - # (MSYS_NT is the system name reported by MinGW uname.) - # TODO(adonovan): make this work. - uname -s | grep -q MSYS_NT && return - - # Skip on Darwin, as System.loadLibrary looks for a file named - # .dylib, not .so, and that's not what the file is called. - # TODO(adonovan): make this just work. - uname -s | grep -q Darwin && return - - mkdir -p test/ - cat > test/BUILD <<'EOF' -java_binary( - name = "app", +function setup_jni_targets() { + repo="${1:-.}" + if [ "$repo" != "." ]; then + mkdir $repo + touch $repo/REPO.bazel + cat > $(setup_module_dot_bazel) < $repo/jni/BUILD < test/App.java <<'EOF' + cat > ${repo}/jni/App.java <<'EOF' package foo; public class App { @@ -1616,7 +1617,7 @@ public class App { private static native void f(int x); } EOF - cat > test/native.cc <<'EOF' + cat > ${repo}/jni/native.cc <<'EOF' #include #include @@ -1624,7 +1625,61 @@ extern "C" JNIEXPORT void JNICALL Java_foo_App_f(JNIEnv *env, jclass clazz, jint printf("hello %d\n", x); } EOF - bazel run //test:app > $TEST_log || { + + mkdir -p test/ + cat > test/BUILD <> $TEST_log || { + find bazel-bin/ | native # helpful for debugging + fail "bazel run command failed" + } + expect_log "hello 123" +} + +function test_jni_external_repo_legacy_external_runfiles() { + # Skip on MS Windows, see details in test_jni + uname -s | grep -q MSYS_NT && return + # Skip on Darwin, see details in test_jni + uname -s | grep -q Darwin && return + + setup_jni_targets "my_other_repo" + + bazel run --legacy_external_runfiles //test:app >> $TEST_log || { + find bazel-bin/ | native # helpful for debugging + fail "bazel run command failed" + } + expect_log "hello 123" +} + +function test_jni_external_repo_no_legacy_external_runfiles() { + # Skip on MS Windows, see details in test_jni + uname -s | grep -q MSYS_NT && return + # Skip on Darwin, see details in test_jni + uname -s | grep -q Darwin && return + + setup_jni_targets "my_other_repo" + + bazel run --nolegacy_external_runfiles //test:app >> $TEST_log || { find bazel-bin/ | native # helpful for debugging fail "bazel run command failed" }