Java:计数/分析同步调用

Til*_*fer 5 java performance multithreading profiling synchronization

我正在寻找一种方法来列出正在运行的并行Java应用程序的所有同步调用,以便检测可伸缩性问题(就线程/核心而言)。据我了解,每次进入同步块时,机器都需要同步缓存。即使未通过输入同步区域来阻止正在运行的任务,这也会影响所有正在运行的CPU(以几种方式,例如内存带宽)。

那个设定:

我有一个大型应用程序,它在较高级别上并行化,即它具有并行执行的复杂任务。并行化的术语是,所有内核都处于负载状态,并且我没有阻塞线程。性能仍然无法随内核扩展,这可能有几个原因。我感兴趣的特定可能原因是,是否存在大量同步调用(例如,输入同步块,使用锁等)。

任务

我想找出我的代码中(实际执行的)哪些地方进行了这样的同步调用,以及每次同步实际执行的频率。有很多引用的库,因此不可能仅对synced关键字或类似内容使用常规代码搜索,因为这将搜索很多从未执行的代码并带来很多误报。完美的解决方案是拥有一个探查器,该探查器列出所有已执行的同步位置和调用次数。但是,我尝试过的探查器仅允许对方法调用进行计数。因此,这里的问题是找到实际上相关的所有方法。

或者,如果我能找到某个入口点(主要方法)所引用的同步位置,这也将有所帮助。即,通过递归地遍历代码并检查所有引用的方法,类等进行此类同步。在这种情况下,以后可以使用常规探查器找出频率。

问题

是否有工具或工作流,可以将上述任务归档用于较大的项目。

THX提前为您解答。

apa*_*gin 3

进入和离开同步块是相当便宜的操作,除非该块上存在争用。在无竞争的情况下,synchronized如果优化成功,则只是一个原子 CAS 或几乎无操作UseBiasedLocking。尽管看起来可以使用 Instrumentation API 进行同步分析器,但这没有多大意义。

多线程应用程序的问题是竞争同步。JVM 有一些内部计数器来监视锁争用(请参阅此问题)。或者,您甚至可以编写一个简单的临时工具来使用JVMTI 事件跟踪所有争用锁。

然而,不仅仅是锁会导致争用。即使是非阻塞算法也会受到共享资源竞争的影响。这是此类可扩展性问题的一个很好的例子。因此,我同意 @PeterLawrey 的观点,最好从 CPU 分析器开始,因为它通常更容易发现性能问题。