验证中...
本周日【珠海源创会】一起聊聊:PingCAP分布式事务、支付宝移动端实践、GSBN技术框架选型,点此报名占座
JvmUtil.java
原始数据 复制代码
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.lang.management.LockInfo;
import java.lang.management.ManagementFactory;
import java.lang.management.MonitorInfo;
import java.lang.management.ThreadInfo;
import java.lang.management.ThreadMXBean;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
/**
* jvm数据
*
*/
public class JvmUtil {
private transient static Log log = LogFactory.getLog(JvmUtil.class);
/**
* 打印线程堆栈深度
*/
private static final int STACK_DEPP = 32;
public final static int DUMP_MOD_FACT = Integer.valueOf(System.getProperty(
"dump_mod_fact", "10080" /* 7 * 24 * 60 */));
public final static String DUMP_DIR = System.getProperty("dump_dir",
System.getProperty("user.home") + "/.appmonitor/stacks");
public final static float DUMP_THRESHOLD = Float.valueOf(System
.getProperty("dump_threshold", "0.5f"));
public static void jstack(OutputStream stream) throws Exception {
ThreadMXBean threadMxBean = ManagementFactory.getThreadMXBean();
for (ThreadInfo threadInfo : threadMxBean.dumpAllThreads(true, true)) {
stream.write(getThreadDumpString(threadInfo).getBytes());
}
}
public static float computeThreadPrecent(long totalThreads, long busiThreads) {
float threadPercent = 0f;
if (totalThreads > 0)
threadPercent = (float) Math
.round(((float) busiThreads / totalThreads) * 100) / 100;
return threadPercent;
}
public static boolean isNeedDump(long totalThreads, long busiThreads) {
return computeThreadPrecent(totalThreads, busiThreads) > DUMP_THRESHOLD;
}
public static void dump(String serverName, long serverId,
ThreadInfo[] appThreadInfos) {
String dumpFileName = dumpFileName(serverName, serverId);
File file = new File(DUMP_DIR, dumpFileName);
String msg = String.format("dump stack from %s-%s to path %s",
serverName, serverId, file.getAbsolutePath());
log.warn("start " + msg);
File parentFile = file.getParentFile();
if (!parentFile.exists())
parentFile.mkdirs();
if (file.exists())
file.delete();
try {
file.createNewFile();
JvmUtil.dumpStack(file, appThreadInfos);
log.warn(String.format("start dump stack from %s-%s to path %s",
serverName, serverId, file.getAbsolutePath()));
log.warn("finish " + msg);
} catch (IOException e) {
log.error("error " + msg, e);
}
}
private static String dumpFileName(String serverName, long serverId) {
return String.format("%s-%d-%d", serverName, serverId,
System.currentTimeMillis() / 60000 % DUMP_MOD_FACT);
}
public static void dumpStack(File file, ThreadInfo[] threadInfos) {
if (threadInfos == null || threadInfos.length == 0)
return;
FileOutputStream fos = null;
try {
fos = new FileOutputStream(file);
jstack(fos, threadInfos);
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
} finally {
if (fos != null)
try {
fos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
public static void jstack(OutputStream stream, ThreadInfo[] threadInfos)
throws Exception {
if (threadInfos == null)
return;
for (ThreadInfo threadInfo : threadInfos) {
stream.write(getThreadDumpString(threadInfo).getBytes());
}
}
private static String getThreadDumpString(ThreadInfo threadInfo) {
StringBuilder sb = new StringBuilder("\"" + threadInfo.getThreadName()
+ "\"" + " Id=" + threadInfo.getThreadId() + " "
+ threadInfo.getThreadState());
if (threadInfo.getLockName() != null) {
sb.append(" on " + threadInfo.getLockName());
}
if (threadInfo.getLockOwnerName() != null) {
sb.append(" owned by \"" + threadInfo.getLockOwnerName() + "\" Id="
+ threadInfo.getLockOwnerId());
}
if (threadInfo.isSuspended()) {
sb.append(" (suspended)");
}
if (threadInfo.isInNative()) {
sb.append(" (in native)");
}
sb.append('\n');
int i = 0;
StackTraceElement[] stackTrace = threadInfo.getStackTrace();
MonitorInfo[] lockedMonitors = threadInfo.getLockedMonitors();
for (; i < stackTrace.length && i < STACK_DEPP; i++) {
StackTraceElement ste = stackTrace[i];
sb.append("\tat " + ste.toString());
sb.append('\n');
if (i == 0 && threadInfo.getLockInfo() != null) {
Thread.State ts = threadInfo.getThreadState();
switch (ts) {
case BLOCKED:
sb.append("\t- blocked on " + threadInfo.getLockInfo());
sb.append('\n');
break;
case WAITING:
sb.append("\t- waiting on " + threadInfo.getLockInfo());
sb.append('\n');
break;
case TIMED_WAITING:
sb.append("\t- waiting on " + threadInfo.getLockInfo());
sb.append('\n');
break;
default:
}
}
for (MonitorInfo mi : lockedMonitors) {
if (mi.getLockedStackDepth() == i) {
sb.append("\t- locked " + mi);
sb.append('\n');
}
}
}
if (i < stackTrace.length) {
sb.append("\t...");
sb.append('\n');
}
LockInfo[] locks = threadInfo.getLockedSynchronizers();
if (locks.length > 0) {
sb.append("\n\tNumber of locked synchronizers = " + locks.length);
sb.append('\n');
for (LockInfo li : locks) {
sb.append("\t- " + li);
sb.append('\n');
}
}
sb.append('\n');
return sb.toString();
}
}

评论列表( 0 )

你可以在登录后,发表评论

搜索帮助

12_float_left_people 12_float_left_close