Search in sources :

Example 1 with MovingAverage

use of com.biglybt.core.util.average.MovingAverage in project BiglyBT by BiglySoftware.

the class AEThreadMonitor method monitor15.

private static void monitor15() {
    AEDiagnosticsLogger log = AEDiagnostics.getLogger("thread");
    int num_processors = Runtime.getRuntime().availableProcessors();
    if (num_processors < 1) {
        num_processors = 1;
    }
    ThreadMXBean bean = ManagementFactory.getThreadMXBean();
    log.log("Monitoring starts (processors =" + num_processors + ")");
    if (!bean.isThreadCpuTimeSupported()) {
        log.log("ThreadCpuTime not supported");
        return;
    }
    if (!bean.isThreadCpuTimeEnabled()) {
        log.log("Enabling ThreadCpuTime");
        bean.setThreadCpuTimeEnabled(true);
    }
    Map<Long, Long> last_times = new HashMap<>();
    final int time_available = 10 * 1000;
    long start_mono = SystemTime.getMonotonousTime();
    MovingAverage high_usage_history = AverageFactory.MovingAverage(2 * 60 * 1000 / time_available);
    boolean huh_mon_active = false;
    while (true) {
        long start = System.currentTimeMillis();
        try {
            Thread.sleep(time_available);
        } catch (Throwable e) {
            log.log(e);
        }
        long end = System.currentTimeMillis();
        long elapsed = end - start;
        long[] ids = bean.getAllThreadIds();
        long[] diffs = new long[ids.length];
        long total_diffs = 0;
        long biggest_diff = 0;
        int biggest_index = 0;
        Map<Long, Long> new_times = new HashMap<>();
        for (int i = 0; i < ids.length; i++) {
            long id = ids[i];
            // nanos -> millis
            long time = bean.getThreadCpuTime(id) / 1000000;
            Long old_time = last_times.get(id);
            if (old_time != null) {
                long diff = time - old_time.longValue();
                if (diff > biggest_diff) {
                    biggest_diff = diff;
                    biggest_index = i;
                }
                diffs[i] = diff;
                total_diffs += diff;
            }
            new_times.put(id, time);
        }
        ThreadInfo info = bean.getThreadInfo(ids[biggest_index]);
        String thread_name = info == null ? "<dead>" : info.getThreadName();
        int percent = (int) (100 * biggest_diff / time_available);
        Runtime rt = Runtime.getRuntime();
        log.log("Thread state: elapsed=" + elapsed + ",cpu=" + total_diffs + ",max=" + thread_name + "(" + biggest_diff + "/" + percent + "%),mem:max=" + (rt.maxMemory() / 1024) + ",tot=" + (rt.totalMemory() / 1024) + ",free=" + (rt.freeMemory() / 1024));
        if (huh_mon_active) {
            // ESET version 8 seems to be triggering high CPU in this thread
            boolean interesting = percent > 5 && thread_name.equals("PRUDPPacketHandler:sender");
            double temp = high_usage_history.update(interesting ? 1 : 0);
            if (temp >= 0.5) {
                Logger.log(new LogAlert(false, LogAlert.AT_WARNING, "High CPU usage detected in networking code - see <a href=\"" + Constants.URL_WIKI + "/w/High_CPU_Usage\">The Wiki</a> for possible solutions"));
            }
        } else {
            huh_mon_active = SystemTime.getMonotonousTime() - start_mono > 2 * 60 * 1000;
        }
        if (biggest_diff > time_available / 4) {
            info = bean.getThreadInfo(ids[biggest_index], 255);
            if (info == null) {
                log.log("    no info for max thread");
            } else {
                StackTraceElement[] elts = info.getStackTrace();
                StringBuilder str = new StringBuilder(elts.length * 20);
                str.append("    ");
                for (int i = 0; i < elts.length; i++) {
                    if (i != 0)
                        str.append(", ");
                    str.append(elts[i]);
                }
                log.log(str.toString());
            }
        }
        last_times = new_times;
    }
}
Also used : MovingAverage(com.biglybt.core.util.average.MovingAverage) ThreadMXBean(java.lang.management.ThreadMXBean) LogAlert(com.biglybt.core.logging.LogAlert) ThreadInfo(java.lang.management.ThreadInfo)

Aggregations

LogAlert (com.biglybt.core.logging.LogAlert)1 MovingAverage (com.biglybt.core.util.average.MovingAverage)1 ThreadInfo (java.lang.management.ThreadInfo)1 ThreadMXBean (java.lang.management.ThreadMXBean)1