最近,由于段错误,我们的某些服务器已崩溃。尽管我没有得到证实的根本原因,但我确实有一种直觉,它与我们的应用程序如何进行垃圾回收,我们完成的GC调整以及内存配置文件有关。
调查这些崩溃的多次发生,我从JVM的角度确定了一种模式:
# dataframe is named f
company month year_ly bookings_ly year_ty bookings_ty
0 a 1 2018 432 2019 253.0
1 a 2 2018 265 2019 635.0
2 a 3 2018 345 2019 525.0
3 a 4 2018 233 2019 NaN
4 a 5 2018 7664 2019 NaN
5 a 12 2018 224 2019 321.0
6 b 1 2018 543 2019 576.0
7 b 2 2018 23 2019 43.0
8 b 3 2018 64 2019 156.0
9 b 4 2018 143 2019 NaN
10 b 5 2018 41 2019 NaN
11 b 6 2018 90 2019 NaN
f.reset_index(inplace=True)
def aggFunct(row, df, last=3):
series = df.loc[(df['index'] < row['index']) & (df['index'] >= row['index'] - last), 'bookings_ty'].fillna(0)
ssum = series.sum()
return ssum
f.loc[f['bookings_ty'].isna(),'bookings_ty'] = f[f['bookings_ty'].isna()].apply(aggFunct, df=f, axis=1)
f.drop('index',axis=1,inplace=True)
f
company month year_ly bookings_ly year_ty bookings_ty
0 a 1 2018 432 2019 253.0
1 a 2 2018 265 2019 635.0
2 a 3 2018 345 2019 525.0
3 a 4 2018 233 2019 1413.0
4 a 5 2018 7664 2019 1160.0
5 a 12 2018 224 2019 321.0
6 b 1 2018 543 2019 576.0
7 b 2 2018 23 2019 43.0
8 b 3 2018 64 2019 156.0
9 b 4 2018 143 2019 775.0
10 b 5 2018 41 2019 199.0
11 b 6 2018 90 2019 156.0
虽然我没有看到发生内存不足的确凿证据,但我认为我们确实为应用程序用尽了堆空间。如果G1GC无法在撤离或提升前将年轻物体复制到幸存者空间,那么从逻辑上讲,它没有足够的空间来这样做。在分析GC日志时,我认为Humongous对象没有太多关系,因为我认为它们并没有占用堆空间。
查看内存配置文件,我的直觉是我应该将copy_to_survivor_space
减小到接近默认值45的水平,以便更早触发收集周期。在我看来,尤其是考虑到老一代的规模不断扩大,混合/完整GC的触发需要更频繁或更短的触发时间。 如何启动完整/混合收藏?
根据所提供的信息,关于我如何尽快触发收款还有其他想法或意见吗?我是否误解了段错误消息并走错了路?我还能做些什么来收集可能使我能够解决崩溃根本原因的信息?
InitiatingHeapOccupancyPercent
JVM选项:
Detail
# A fatal error has been detected by the Java Runtime Environment:
#
# SIGSEGV (0xb) at pc=0x00007f38aa2655f5, pid=6293, tid=0x00007f3894efe700
#
# JRE version: Java(TM) SE Runtime Environment (8.0_162-b12) (build 1.8.0_162-b12)
# Java VM: Java HotSpot(TM) 64-Bit Server VM (25.162-b12 mixed mode linux-amd64 compressed oops)
# Problematic frame:
# V [libjvm.so+0x5c85f5] G1ParScanThreadState::copy_to_survivor_space(InCSetState, oopDesc*, markOopDesc*)+0x45
#
答案 0 :(得分:1)
我误解了段错误消息并走错了路吗?
是的,堆OOM绝不应导致段错误,而应仅通过异常/可抛出机制触发out of memory errors。崩溃签名指向JVM错误或由外部因素(JVM进程中加载的本地库,内存损坏,对Unsafe
的错误使用)引起的堆损坏。
尝试升级JVM,并查看原因是否已在较新版本中解决。如果这样做没有帮助,请尝试删除部分应用程序,依赖项,Java代理等或在其他硬件上运行。