Получение трассировки стека для всех потоков параллельного доступа: - PullRequest
0 голосов
/ 10 октября 2018

У нас, кажется, есть параллельный доступ к методу в нашем коде.Обходной путь должен был бы синхронизировать этот метод.Но это не решило бы основную причину: такого одновременного доступа не должно быть вообще.

Как получить трассировку стека всех потоков, которые обращаются к этому методу, но только в случае одновременного доступадоступ?

Другим вариантом будет обнаружение того, что синхронизация заблокируется - до того, как она фактически заблокируется.

Ответы [ 2 ]

0 голосов
/ 12 октября 2018

Здесь есть несколько вариантов.

Основной код:

    Lock lock = new ReentrantLock();

    if(!lock.tryLock()) {
        Map<Thread, StackTraceElement[]> threads = Thread.getAllStackTraces();
    }
    try {
        ///your code
    }
    finally {
        lock.unlock();
    }

Так что, если вы можете подключить отладчик к вашему приложению, вы можете установить точку останова на

Map<Thread, StackTraceElement[]> threads = Thread.getAllStackTraces();

строка, которая приостановит все потоки.Затем вы можете увидеть все потоки и их трассировки стека в этой карте

Если вы не можете подключить отладчик, просто выполните итерацию по этой карте и получите все трассировки стека.

Другой способ без использованияблокировка может быть такой:

private Set<Thread> threads = new HashSet<>();

public void yourMethodInQuestion() {
    threads.add(Thread.currentThread());
    if( threads.size() >= 2 ) {
        //iterate and get all the threads information
    }
    ....
}

Надеюсь, это поможет.

Майкл, автор многопоточности, параллелизма и оптимизации производительности Java курс

https://www.udemy.com/java-multithreading-concurrency-performance-optimization/?couponCode=CONCURRENCY

0 голосов
/ 10 октября 2018

Попробуйте использовать реентрантный замок, чтобы соответствовать цели.Вот пример кода:

private final ReentrantLock lock = new ReentrantLock();

      public void sampleLock() {
        lock.lock();
        try {
          Thread.sleep(5000);
        } catch (InterruptedException e) {
          System.out.println(Thread.currentThread().getName() + "interrupted");
        }
        lock.unlock();
      }

Если любой другой метод хочет получить доступ к методу sampleLock(), тогда lock.isLocked() скажет, используется ли он каким-либо другим потоком.Пожалуйста, ознакомьтесь с документацией Oracle для того же.https://docs.oracle.com/javase/7/docs/api/java/util/concurrent/locks/ReentrantLock.html

...