Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: thread/stack add limit stacktrace lines by --stacktrace-max/-smax #2782

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ public class ThreadModel extends ResultModel {
private Map<Thread.State, Integer> threadStateCount;
private boolean all;

private int stacktraceMax;

public ThreadModel() {
}

Expand Down Expand Up @@ -98,4 +100,19 @@ public boolean isAll() {
public void setAll(boolean all) {
this.all = all;
}

/**
* @return int return the stacktraceMax
*/
public int getStacktraceMax() {
return stacktraceMax;
}

/**
* @param stacktraceMax the stacktraceMax to set
*/
public void setStacktraceMax(int stacktraceMax) {
this.stacktraceMax = stacktraceMax;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ public class ThreadCommand extends AnnotatedCommand {
private boolean lockedMonitors = false;
private boolean lockedSynchronizers = false;
private boolean all = false;
private int stacktraceMax;

static {
states = new HashSet<String>(State.values().length);
Expand All @@ -71,6 +72,12 @@ public void setId(long id) {
this.id = id;
}

@Option(longName = "stacktrace-max", shortName = "smax")
@Description("limit stacktrace max number")
public void setStacktraceMax(int stacktraceMax) {
this.stacktraceMax = stacktraceMax;
}

@Option(longName = "all", flag = true)
@Description("Display all thread results instead of the first page")
public void setAll(boolean all) {
Expand Down Expand Up @@ -168,7 +175,9 @@ private ExitStatus processAllThreads(CommandProcess process) {
threadSampler.pause(sampleInterval);
List<ThreadVO> threadStats = threadSampler.sample(resultThreads);

process.appendResult(new ThreadModel(threadStats, stateCountMap, all));
final ThreadModel model = new ThreadModel(threadStats, stateCountMap, all);
model.setStacktraceMax(stacktraceMax);
process.appendResult(model);
return ExitStatus.success();
}

Expand All @@ -177,7 +186,9 @@ private ExitStatus processBlockingThread(CommandProcess process) {
if (blockingLockInfo.getThreadInfo() == null) {
return ExitStatus.failure(1, "No most blocking thread found!");
}
process.appendResult(new ThreadModel(blockingLockInfo));
final ThreadModel model = new ThreadModel(blockingLockInfo);
model.setStacktraceMax(stacktraceMax);
process.appendResult(model);
return ExitStatus.success();
}

Expand Down Expand Up @@ -215,7 +226,9 @@ private ExitStatus processTopBusyThreads(CommandProcess process) {
BusyThreadInfo busyThread = new BusyThreadInfo(thread, threadInfo);
busyThreadInfos.add(busyThread);
}
process.appendResult(new ThreadModel(busyThreadInfos));
final ThreadModel model = new ThreadModel(busyThreadInfos);
model.setStacktraceMax(stacktraceMax);
process.appendResult(model);
return ExitStatus.success();
}

Expand All @@ -235,7 +248,9 @@ private ExitStatus processThread(CommandProcess process) {
return ExitStatus.failure(1, "thread do not exist! id: " + id);
}

process.appendResult(new ThreadModel(threadInfos[0]));
final ThreadModel model = new ThreadModel(threadInfos[0]);
model.setStacktraceMax(stacktraceMax);
process.appendResult(model);
return ExitStatus.success();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -21,18 +21,19 @@ public class ThreadView extends ResultView<ThreadModel> {

@Override
public void draw(CommandProcess process, ThreadModel result) {
final int stacktraceMax = result.getStacktraceMax();
if (result.getThreadInfo() != null) {
// no cpu usage info
String content = ThreadUtil.getFullStacktrace(result.getThreadInfo());
String content = ThreadUtil.getFullStacktrace(result.getThreadInfo(), stacktraceMax);
process.write(content);
} else if (result.getBusyThreads() != null) {
List<BusyThreadInfo> threadInfos = result.getBusyThreads();
for (BusyThreadInfo info : threadInfos) {
String stacktrace = ThreadUtil.getFullStacktrace(info, -1, -1);
String stacktrace = ThreadUtil.getFullStacktrace(info, -1, -1, stacktraceMax);
process.write(stacktrace).write("\n");
}
} else if (result.getBlockingLockInfo() != null) {
String stacktrace = ThreadUtil.getFullStacktrace(result.getBlockingLockInfo());
String stacktrace = ThreadUtil.getFullStacktrace(result.getBlockingLockInfo(), stacktraceMax);
process.write(stacktrace);

} else if (result.getThreadStateCount() != null) {
Expand Down
27 changes: 25 additions & 2 deletions core/src/main/java/com/taobao/arthas/core/util/ThreadUtil.java
Original file line number Diff line number Diff line change
Expand Up @@ -158,16 +158,23 @@ public static BlockingLockInfo findMostBlockingLock() {
return blockingLockInfo;
}


public static String getFullStacktrace(ThreadInfo threadInfo) {
return getFullStacktrace(threadInfo, -1, -1, -1, 0, 0);
}

public static String getFullStacktrace(final ThreadInfo threadInfo, final int stacktraceMax) {
return getFullStacktrace(threadInfo, -1, -1, -1, 0, 0, stacktraceMax);
}

public static String getFullStacktrace(BlockingLockInfo blockingLockInfo) {
return getFullStacktrace(blockingLockInfo.getThreadInfo(), -1, -1, -1, blockingLockInfo.getLockIdentityHashCode(),
blockingLockInfo.getBlockingThreadCount());
}

public static String getFullStacktrace(final BlockingLockInfo blockingLockInfo, final int stacktraceMax) {
return getFullStacktrace(blockingLockInfo.getThreadInfo(), -1, -1, -1, blockingLockInfo.getLockIdentityHashCode(),
blockingLockInfo.getBlockingThreadCount(), stacktraceMax);
}

/**
* 完全从 ThreadInfo 中 copy 过来
Expand All @@ -179,6 +186,11 @@ public static String getFullStacktrace(BlockingLockInfo blockingLockInfo) {
*/
public static String getFullStacktrace(ThreadInfo threadInfo, double cpuUsage, long deltaTime, long time, int lockIdentityHashCode,
int blockingThreadCount) {
return getFullStacktrace(threadInfo, cpuUsage, deltaTime, time, lockIdentityHashCode, blockingThreadCount, 0);
}

public static String getFullStacktrace(ThreadInfo threadInfo, double cpuUsage, long deltaTime, long time,
int lockIdentityHashCode, int blockingThreadCount, final int stacktraceMax) {
StringBuilder sb = new StringBuilder("\"" + threadInfo.getThreadName() + "\"" + " Id="
+ threadInfo.getThreadId());

Expand Down Expand Up @@ -242,6 +254,9 @@ public static String getFullStacktrace(ThreadInfo threadInfo, double cpuUsage, l
}
}
++i;
if (stacktraceMax > 0 && i >= stacktraceMax) {
break;
}
}
if (i < threadInfo.getStackTrace().length) {
sb.append("\t...");
Expand All @@ -265,7 +280,11 @@ public static String getFullStacktrace(ThreadInfo threadInfo, double cpuUsage, l
return sb.toString().replace("\t", " ");
}

public static String getFullStacktrace(BusyThreadInfo threadInfo, int lockIdentityHashCode, int blockingThreadCount) {
public static String getFullStacktrace(BusyThreadInfo threadInfo, int lockIdentityHashCode, int blockingThreadCount) {
return getFullStacktrace(threadInfo, lockIdentityHashCode, blockingThreadCount, 0);
}

public static String getFullStacktrace(BusyThreadInfo threadInfo, int lockIdentityHashCode, int blockingThreadCount, int stacktraceMax) {
StringBuilder sb = new StringBuilder("\"" + threadInfo.getName() + "\"");
if (threadInfo.getId() > 0) {
sb.append(" Id=").append(threadInfo.getId());
Expand Down Expand Up @@ -338,6 +357,10 @@ public static String getFullStacktrace(BusyThreadInfo threadInfo, int lockIdenti
sb.append('\n');
}
}

if (stacktraceMax > 0 && i > stacktraceMax) {
break;
}
}
if (i < threadInfo.getStackTrace().length) {
sb.append("\t...");
Expand Down