java - 当我在 Java 中创建多个线程时,为什么没有调用系统调用来创建线程?

标签 java multithreading

以下代码创建 100 个新的 java 线程并运行它们。

class ThreadTest {
    public static void main(String[] args) {
        for (int i = 0; i < 100; i++) {
            final int tNo = i;
            new Thread(new Runnable() {
                @Override
                public void run() {
                    System.out.println("thread #" + tNo);
                }
            }).start();
        }
    }
}

当我运行上面的代码并使用 strace 记录由此执行的系统调用时,我找不到任何正在创建新线程的系统调用(可能是 clone())。

但是当我使用 ps -eLf 命令检查上述进程的线程时,它会列出 (>100) 个具有不同线程 ID 的线程。

这些线程是如何在没有任何系统调用的情况下创建的?如果 jvm 在用户空间中创建线程,那么这些线程不应该被 ps -eLf 列出。

strace 命令的输出结果

mprotect(0xf95000, 8876032, PROT_READ|PROT_EXEC) = 0
munmap(0xf7762000, 92395)               = 0
mmap2(NULL, 331776, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS|MAP_STACK, -1, 0) = 0xfffffffff770f000
mprotect(0xf770f000, 4096, PROT_NONE)   = 0
clone(child_stack=0xf775f494, flags=CLONE_VM|CLONE_FS|CLONE_FILES|CLONE_SIGHAND|CLONE_THREAD|CLONE_SYSVSEM|CLONE_SETTLS|CLONE_PARENT_SETTID|CLONE_CHILD_CLEARTID, parent_tidptr=0xf775fbd8, tls=0xf775fbd8, child_tidptr=0xffdb53d0) = 31692
futex(0xf775fbd8, FUTEX_WAIT, 31692, NULLthread #1
thread #5
thread #4
thread #3
.....
) = 0
exit_group(0)                           = ?

我删除了启动 jvm 所需的初始系统调用。显示的唯一克隆系统调用是用于创建主线程的调用。

最佳答案

在我运行 Oracle Java 8u5 的机器上,我看到与运行 strace java ThreadTest 非常相似的输出。但是,当我启用 -f 标志以跟随子进程时,我看到进行了数十次 clone() 调用。

您对 strace 的调用告诉它只关注直接启动的进程(JVM 引导线程)​​,并且它只生成主线程。然后 that 线程就是调用 clone() 来创建所有 worker 的线程。

关于java - 当我在 Java 中创建多个线程时,为什么没有调用系统调用来创建线程?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24485255/

相关文章:

python - 使用 for 循环和多线程 python

java - 按下按钮时调用 AsyncTask 的问题

java - HttpClient 发布请求 URL 的问题,Java 中没有变化

java - textArea 格式问题上的控制台输出

android - 如何在android中设置循环延迟?

linux - gcc 4.8.1 中 c++11 线程的奇怪行为

multithreading - 硬件线程与软线程?

c++ - 单例死引用问题

java - 自定义标签不计算表达式; c 和 fmt 标签正在评估表达式

java - 除非另有明确说明,有什么方法可以使其假定为 transient 吗?