我们的 Java 系统已经运行了 2 年多,从未出现过系统挂起的情况。我们有 2 台物理服务器运行类似的 Java 软件(每台服务器上有 2 个 JVM),以形成一个集群。据我所知,只有当我们在其中一台服务器上引入核心固定和 Mappedbus.io 以在 2 个 JVM 之间进行共享内存访问时,才会开始崩溃。系统挂起在 2 周内只发生过 4 次,而且只发生在我们配置了核心固定和 JVM 之间的内存映射文件访问的机器上。我们禁用了该配置,因此我们不会固定核心以旋转读取内存映射文件,也不会固定我们的主要应用线程。注意,当我说固定时,我们也忙于旋转在固定核心上运行的线程。
不过这完全是传闻。由于系统并非每天都挂起,我不能肯定地说这与核心固定或共享内存访问有关。但是,在禁用固定(和忙旋转)并使用 LockSupport.parkNanos(5000) 循环访问共享内存的情况下,我们似乎没有遇到任何系统挂起的情况。
延迟对我们来说至关重要,因此这种“非繁忙”设置只是一种临时解决办法。
另外,请注意,我已将应用程序移至相同的服务器,并且也遇到了整个系统挂起的情况。因此,我不认为这是硬件故障。
因此,从崩溃前后的日志中挖掘,这似乎与我有关。有好几个这样的堆栈。我只是在这里发布第一个(即我不相信这与 postgres 本身有任何关系)
kernel: [25738.874778] INFO: task postgres:2155 blocked for more than 120 seconds.
kernel: [25738.874833] Not tainted 5.4.0-050400-generic #201911242031
kernel: [25738.874878] "echo 0 > /proc/sys/kernel/hung_task_timeout_secs" disables this message.
kernel: [25738.874928] postgres D 0 2155 2056 0x00004000
kernel: [25738.874931] Call Trace:
kernel: [25738.874942] __schedule+0x2e3/0x740
kernel: [25738.874948] ? __wake_up_common_lock+0x8a/0xc0
kernel: [25738.874951] schedule+0x42/0xb0
kernel: [25738.874957] jbd2_log_wait_commit+0xaf/0x120
kernel: [25738.874961] ? wait_woken+0x80/0x80
kernel: [25738.874965] jbd2_complete_transaction+0x5c/0x90
kernel: [25738.874969] ext4_sync_file+0x38c/0x3e0
kernel: [25738.874974] vfs_fsync_range+0x49/0x80
kernel: [25738.874977] do_fsync+0x3d/0x70
kernel: [25738.874980] __x64_sys_fsync+0x14/0x20
kernel: [25738.874985] do_syscall_64+0x57/0x190
kernel: [25738.874991] entry_SYSCALL_64_after_hwframe+0x44/0xa9
kernel: [25738.874993] RIP: 0033:0x7f96dc24b214
kernel: [25738.875002] Code: Bad RIP value.
kernel: [25738.875003] RSP: 002b:00007fffb2abd868 EFLAGS: 00000246 ORIG_RAX: 000000000000004a
kernel: [25738.875006] RAX: ffffffffffffffda RBX: 00007fffb2abd874 RCX: 00007f96dc24b214
kernel: [25738.875007] RDX: 00005635889ba238 RSI: 00005635889a1490 RDI: 0000000000000003
kernel: [25738.875009] RBP: 00007fffb2abd930 R08: 00005635889a1480 R09: 00007f96cc1e1200
kernel: [25738.875010] R10: 0000000000000000 R11: 0000000000000246 R12: 0000000000000000
kernel: [25738.875011] R13: 0000000000000000 R14: 000056358899c5a0 R15: 0000000000000001
附言:这也发生在 16.04 和内核 4.15 上。升级到 18.04 和 5.0 是为了解决系统挂起问题,但没有任何效果。
我考虑的另一件事是,也许这个跟踪只是一种症状,而不是问题。也就是说,我的应用程序绑定了服务器,导致其他进程在 io 上阻塞并收到这些错误。但由于服务器完全冻结,我无法知道当时我的应用程序的状态