Deixe-me ver se entendi. Você atualizou o cliente com base em um palpite e um único benchmark?
Isso é um erro. Os benchmarks são inteiramente artificiais e não refletem como os programas do mundo real irão funcionar. No entanto, direi que eles fornecem uma indicação do desempenho potencial.
Em primeiro lugar, há muito mais para que os aplicativos tenham um bom desempenho em vários núcleos e para usar toda a memória disponível com eficiência.
Muitos aplicativos não são gravados com grande simultaneidade e nem todos os domínios de problemas se prestam a soluções simultâneas. O gargalo no seu aplicativo pode ser bloqueado pela memória compartilhada.
Por exemplo, vi gráficos de aplicativos simultâneos que parecem dimensionar muito bem até quatro segmentos, mas, sem motivo aparente, o desempenho cai linearmente à medida que o número de segmentos é aumentado. Esta é uma indicação de fome de um recurso. Bloqueios são muito caros. Considere o uso de estruturas livres de bloqueio ou minimize a quantidade de recursos compartilhados e a interação entre os threads.
Outra lentidão pode estar em volta dos caches. Um exemplo realmente interessante é o compressor lz4. Versões anteriores eram muito rápidas, mas outro compressor mais complexo (mal-humorado) dava desempenho semelhante. O motivo foi devido à maneira como os caches são usados. Não subestime isso. Se você sabe o que está fazendo, pode acelerar alguns algoritmos e estruturas de dados por muitos múltiplos, o que é exatamente o que o autor do LZ4 fez.
Veja o link a seguir em favor do interesse: link
A primeira coisa que eu faço é rodar o seu código no sistema 32 core e ver se você pode criar um perfil para ter uma idéia de onde ele está gastando seu tempo. Provavelmente é com fechaduras. Além disso, tente reduzir o número de threads e o benchmarking novamente. Você pode encontrar aumentos de desempenho - na verdade, eu diria que é provável.