1

我认为这在这里也是一个难题。反正我想试试。

我实现了一个小型项目 JNI,它在 Java 中移植了本地 boost 光纤。

这是JNI接口

inline void execute(JNIEnv * env,jobject runnable,jmethodID mid){
 cout <<  " 31---"  << endl;
 env->CallVoidMethod(runnable, mid);
  cout <<  " 32---"  << endl;
}

/*
 * Class:     java_ext_concurrent_fiber_NativeFiber
 * Method:    run
 * Signature: (Ljava/lang/Runnable;)J
 */
JNIEXPORT void JNICALL Java_ext_concurrent_fiber_NativeFiber_run
  (JNIEnv * env, jclass clazz, jobject runnable){
cout <<  " 1---"  << endl;
   jclass cls = env->GetObjectClass( runnable);
   cout <<  " 2---"  << endl;
   jmethodID mid = env->GetMethodID( cls, "run", "()V");
cout <<  " 3---"  << endl;

env->CallVoidMethod(runnable, mid);
  boost::fibers::fiber fiber(execute,env,runnable,mid);

  cout <<  " 3---"  << endl;

  }

这是java测试

public class Test {
    public static void main(String[] args) throws InterruptedException {

        NativeFiber fiber=new NativeFiber(new Runnable() {
            @Override
            public void run() {


                System.out.println("hello");
            }
        });
        fiber.start();


    }
}

如果我执行此代码

throws StackOverflowException

如果我删除了 fiber.join() 并添加了 fiber.detach();

#
# A fatal error has been detected by the Java Runtime Environment:
#
#  SIGSEGV (0xb) at pc=0x00007f5a37017f1f, pid=16559, tid=0x00007f5a38522700
#
# JRE version: Java(TM) SE Runtime Environment (8.0_131-b11) (build 1.8.0_131-b11)
# Java VM: Java HotSpot(TM) 64-Bit Server VM (25.131-b11 mixed mode linux-amd64 compressed oops)
# Problematic frame:
# V  [libjvm.so+0x6d7f1f]  jni_CallVoidMethodV+0x3f
#
# Failed to write core dump. Core dumps have been disabled. To enable core dumping, try "ulimit -c unlimited" before starting Java again
#
# An error report file with more information is saved as:
# /data/git/concurrent/hs_err_pid16559.log
#
# If you would like to submit a bug report, please visit:
#   http://bugreport.java.com/bugreport/crash.jsp
4

1 回答 1

0

可能是因为 Fiber 堆栈对于 Java 来说太小了。

但是,在没有明确支持的情况下在纤程上运行 JVM/JRE 代码确实是不明智的。

如果您发现了明确允许它的 JVM 规范的一部分,并且您知道您所依赖的 JRE 的所有部分都可以安全地用于纤程,那么您显然可以忽略这些警告

碰巧的是,JVM/JRE 可能包含基于线程模型的任意数量的假设。例如使用线程本地静态实例对非同步访问是安全的。这将打破假设,因此导致未指定的行为。

如果您需要 Fibers,请查看一种支持 JVM 的方法来实现它们(我无法想象没有流行的库可以做到这一点)。

于 2017-12-24T14:05:14.017 回答