After upgrading to 15.4, one of our custom portlets is taking upwards of 20 minutes to return data on the first time its loaded after a recycle occurs. Subsequent loads are much faster.
The problem due to there not being enough memory available at the OS level. The JVM memory was set to 24GB and the machine only had 25GB total. This was not leaving enough memory for the OS to be able to efficiently execute threads.
After lowering the JVM memory to 2GB, the portlet generated the query within a reasonable timeframe. The JVM memory should never exceed 70% of the total memory on the server.