"Логика Черного лебедя делает то, чего вы не знаете, гораздо более важным, чем то, что вы знаете. Ведь если вдуматься, то многие Черные лебеди явились в мир и потрясли его именно потому, что их никто не ожидал."
Нассим Талеб
«Время всегда против нас».
Весна 2020 года была очень активной на фондовых рынках, количество сделок в некоторые дни вырастало в 2 раза от нормы, закрытие дня в финансовом учете было близко к предельным срокам. Клиенты боролись с Черным Лебедем Covid-19 по всем фронтам. К этому моменту конфигурация уже 7 лет работала на одном и том же оборудовании, которое было заложено с запасом под горизонтальное маштабирование. Даже то горизонтальное маштабирование, которое можно сделать в 1С (см статью https://habr.com/ru/post/674282/ ) позволяет решать проблемы роста объемов оборудованием, и вот настал тот момент когда уже пора расширять оборудование.
Случайное совпадение - наши системные администраторы предложили попробовать новый виртуальный кластер, который недавно развернули в компании. Кластер на основе VMWare. Перспективы были заманчивые, вместо покупки новых серверов, отдельных дисковых хранилищ, обоснований бюджета – создаются виртуальные машины с нужными параметрами, а в бюджет аллоцируются расходы из общего пула. Будущее рисует нам картины, когда системный администратор скоро не сможет потрогать сервер рукой, и будет видеть только операционную систему и прайс лист за использование J от провайдера. Однако виртуальная реальность оказалась не такой радужной.
Мне выделили контур с примерно таким же числом ядер, памяти как на рабочем. Версии программ и операционной системы поставили идентичные, настройки тоже. Параметры оборудования по виртуализацию были лучше, но не сильно ведь гонка тактовых частот заканчивается по физическим ограничениям. Запустил перерасчет за месяц с распараллеливанием… и ушел спать.
«Что есть реальность?» В виртуальной среде
Утром первым делом посмотрел на результаты, они были странные – замедление 60% на виртуальном кластере. Даже ФИФО который параллелится только по бумагам и не создает большой нагрузке посчитался медленней на 30%
Кликайте на картинки для большего разрешения!
Хорошо, что мне есть с чем сравнивать, и я могу просто сказать «А вот на железном кластере с той же конфигурацией гораздо быстрее» или сравнить счетчики MS SQL на быстром и медленном кластере. Но допустим, кому-то дали облако под проект с якобы заявленными параметрами, как ему понять что кластер (1С MSSQL Hardware) работает на полную мощность?
Тут можно обратится к принципу непротиворечивости логичной системы аксиом. В логике предикатов это изложено детально, но по простому можно сказать: Вы можете построить любую систему аксиом для своей алгебры, геометрии, теории множеств – важно чтобы она была непротиворечивой при выводе теорем и утверждений. Там, где есть противоречие 2 варианта либо система аксиом плоха, либо вы что-то не знаете и не учитываете и именно там истина. Математика, физические постоянные существуют в мире не просто так любые противоречия разрушили бы вселенную. Напр путешествие во времени назад вызывает кучу противоречий, значит оно невозможно, а вот в будущее без возврата в прошлое вполне возможно.
Значит решено - снимаем показатели и ищем противоречия. ИТ технологии сложны, но это гораздо проще тензорного исчисления J. Производительность какого-то компонента кластера снижается по одной из трех причин.
Ресурс перегружен, это сразу видно на счетчиках производительности.
Ресурс частично свободен, но ждет снятия какой-то блокировки (Это может быть блокировка строк в СУБД, ресурсов памяти Latch, и т.д.).
Ресурс частично свободен, но у него скопилась очередь (Это может быть очередь к дисковой системе, минимально необходимые задержки на передачу пакета по сети).
Комбинация этих причин приводит к тому что все утыкается в бутылочное горлышко и остальные ресурсы просто не нагружаются.
Настроил счетчики, я не будут описывать нужные - так как в разных ситуациях нужно искать разные. Принцип простой – из всех счетчиков ищите счетчики очередей, ожиданий, миллисекунд на трансфер. Счетчики на % загрузки как правило не дают сделать выводы напр. Передача по сети множества мелких пакетов не создает 100% траффика, но за счет задержек сети упирается в потолок производительности (см. мою старую статью на эту тему)
Для оборудования настроил Perfomance Monitor с записью, то что называется Data collection set. Странно, но оно работало только после перезагрузки сервера.
Для SQL Server сбросил счетчики статистики и кэши:
DBCC SQLPERF("sys.dm_os_wait_stats",CLEAR);
DBCC FREEPROCCACHE ;
DBCC DROPCLEANBUFFERS;
Анализ перегруженности ресурсов не показал ничего критичного.
На кластере 1С за счет горизонтального маштабирования, загрузка плотная больше 50% (что считается с точки зрения Microsoft значительной нагрузкой).
Небольшая странность, бывают очереди на процессор (Processor queue length).
На сервере базы данных нагрузка небольшая, значит можно увеличить еще, но видны противоречия:
Видны всплески очередей на диск (Current disk queue length больше 100), когда активность превышает 10 тыс IOPS . Причем видно что очередь держится по несколько секунд. Это странно, ведь SSD должен переваривать такой траффик легко.
Попросил администраторов проверить со стороны гипервизора, получил ответ.
«В данной конфигурации Ваш виртуальный сервер может спокойно потреблять до 50k iops при минимальном latency. Разумеется, если от него этого требуют.
На Ваших графиках видно, что нагрузка почти нулевая с периодическими кратковременными скачками. Я посмотрел - в эти пиковые моменты сервер потреблял всего до 20k iops. Latency в эти моменты достигала 15-20 мс, что безусловно не мало, но и не катастрофично, учитывая, что эти всплески длятся доли секунды.
Latency растет, т.к. Вы периодически упираетесь в одно единственно ограничение - одновременное количество потоков данных от виртуального сервера к дисковой системе (максимум 64) в текущей конфигурации.
Параметр queue lentgh и все его производные имеет смысл рассматривать только на однодисковых десктопах. На серверах и в виртуализации он не показывает абсолютно ничего. »
Вот первый звоночек оказывается VMWare ограничивает одновременное количество потоков данных от сервера к дисковой подсистеме, неужели придется еще VWWare изучать J чтобы знать ее узкие места. Про очереди не согласен, если они возникают значит что-то не так. А так «Все хорошо прекрасная маркиза, все хорошо, все хорошо».
«Если бы ты не мог проснуться, как бы ты узнал, что сон, а что действительность?»
Очень просто – надо так пошалить в системе, что бы агент Смит мигом прибежал успокаивать прозревающего Нео и попытаться уложить его в кроватку. В ИТ это называется стресс тест, у водопроводчиков опрессовка. Если хотите проверить качество работы сантехника, пригласите опрессовщика, он создаст избыточное давление и все недоработки потоком польются вам на пол.
Горизонтальное маштабирование позволяет легко увеличить количество параллельных процессов обработки и тем самым увеличить нагрузку. Поэтому свой тест я запускал увеличив количество параллельных процессов обработки с 40 до 60, если % загрузки не дают внятного ответа, смотрим анализ ожиданий.
Результат интересные, ожидание на логгирование Transaction log вылезло в топ, да еще Memory waits появились.
Еще сетевые задержки между кластером 1С и СУБД великоваты они действительно отличались от продуктивного контура, если применить анализ задержек через hrping. Это исправили, результат улучшился, но не существенно для текущей проблемы.
На продуктивном сервере топ ожиданий совсем другой, скажем так логичный – больше ждешь записи\чтения в базу нежели transaction log и памяти.
Далее смотрим детально ожидания на Transaction log он находится на отдельном SSD диске, но там нет проблем с производительностью дисковой системы.
Администраторы мне это подтвердили.
«На графике ниже 3 параметра: lock wait, log write wait, disk latency.
Хорошо видно, что несмотря на высокий уровень Log write waits, запись данных на диск происходит с приемлемой latency. Следовательно, проблема тут не в дисках.
Решение проблем с задержками сети улучшило результат до 1233 мин против 1492, но это не 937 мин на рабочем.
Анонс. Анализ сетевых задержек это отдельная тема. В устаревшем варианте есть моя статья, но ее можно уже обновить учитывая новые кейсы.
«Часть меня чувствует, будто я всю жизнь ждала тебя.» Ожидания наше все.
Если отбросить диск, то анализ задержек на уровне процессор память наиболее сложная тема, поскольку это уже нужно лезть в анализ процессов операционной системы и с пониманием использовать ProcessExplorer. Многоядерность, Numa nodes усложняют задачу.
Я уже подошел к моменту, когда анализ счетчиков увеличивает глубину НЕ знания, поскольку даже внутри кластера видно, что для tempdb при сопоставимых объемах записи, таких проблем нет, а для базы СУБД есть. Интуитивно было понятно что, что-то не так с виртуальными ядрами, Numa nodes, а не с реальным железом.
Если есть теория значит нужно искать ей подтверждение! Ок Google?
Не помню какой правильно был сформулированный вопрос, который содержит половину ответа, но я нашел эту статью про spinlock в MS SQL.
Тема сложная поскольку это уже системная архитектура СУБД, до которой не каждый SQL администратор доберется, а Эксперт по технологическим вопросам 1С вообще не должен столкнутся с подобным, учитывая проблемы 1С горизонтальным маштабированием см тут . Приведу лишь несколько цитат для понимания.
«Spinlocks are lightweight synchronization primitives which are used to protect access to data structures. Spinlocks are not unique to SQL Server. They are generally used when it is expected that access to a given data structure will need to be held for a very short period of time. When a thread attempting to acquire a spinlock is unable to obtain access it executes in a loop periodically checking to determine if the resource is available instead of immediately yielding. After some period of time a thread waiting on a spinlock will yield before it is able to acquire the resource in order to allow other threads running on the same CPU to execute. This is known as a backoff and will be discussed in more depth later in this paper.
SQL Server utilizes spinlocks to protect access to some of its internal data structures. These are used within the engine to serialize access to certain data structures in a similar fashion to latches. The main difference between a latch and a spinlock is the fact that spinlocks will spin (execute a loop) for a period of time checking for availability of a data structure while a thread attempting to acquire access to a structure protected by a latch will immediately yield if the resource is not available. Yielding requires context switching of a thread off the CPU so that another thread can execute. This is a relatively expensive operation and for resources that are held for a very short duration it is more efficient overall to allow a thread to execute in a loop periodically checking for availability of the resource.»
Проще говоря это блокировки для структур памяти, которые работают по принципу циклического ожидания.
«Ты всю жизнь ощущал, что мир не в порядке. Странная мысль, но её не отогнать. Она — как заноза в мозгу. Она сводит с ума, не даёт покоя. Это и привело тебя ко мне...» Морфеус
Предположил, что проблема в физическом распределении по Numa Node потоков MS SQL, которое влечет задержки при доступе к памяти (ведь spinlock это структуры памяти) , видимо на физическом уровне WriteLog висит на тех же ядрах что и другие потоки MS SQL и Numa Nodes фактически не работают. С приходом многоядерности требуется внимательно смотреть на загрузку отдельных ядер, ведь там может висеть процесс или поток, который становится узким местом для всей системы.
Классический пример из 1С – rmanager со всеми сервисами висит на одном ядре, если он управляет 40 рабочими процессами, загрузка этого ядра на 100% уже влияет на всю систему самым отрицательным образом. Поэтому в 8.3 есть флажок «Менеджер под каждый сервис», а в 8.2 нужно сделать несколько менеджеров кластера и распределить по ним сервисы.
Ложки не существует. Что не так с ядрами виртуальной машины?
— Не пытайся согнуть ложку. Это невозможно. Для начала нужно понять главное.
— Что главное?
— Ложки не существует.
— Не существует?
— Знаешь, это не ложка гнётся. Всё — обман. Дело в тебе.
С какими ядрами работает SQL Server - можно увидеть в Affinity mask логе SQL Server
Вот что было на виртуальном кластере:
А это на рабочем:
Почувствовали разницу? SQL сервер по другому видит и Numa node и количество ядер. Хотя там все одинаково с точки зрения количества
Что такое Numa node хорошо объяснено тут.
«Each group of processors has its own memory and possibly its own I/O channels. However, each CPU can access memory associated with the other groups in a coherent way. Each group is called a NUMA node. The number of CPUs within a NUMA node depends on the hardware vendor. It is faster to access local memory than the memory associated with other NUMA nodes»
Дальше все становится понятным - SQL Server не будет есть виртуальную … . Любая виртуальная … приведет к самым экзотическим эффектам в производительности. Выход один – выровнять виртуальную машину с физической. В VMWare такое возможно, с другой стороны, а зачем она нам вообще тогда нужна J . Все варианты например: дадим половину реальной машины или 2 реальных машины объединенных в одну приведут к непредсказуемым эффектам в производительности.
Проверка через CoreInfo показала такое распределение ядер на виртуальном сервере:
Logical to Physical Processor Map:
*----------------------- Physical Processor 0
-*---------------------- Physical Processor 1
--*--------------------- Physical Processor 2
---*-------------------- Physical Processor 3
----*------------------- Physical Processor 4
-----*------------------ Physical Processor 5
------*----------------- Physical Processor 6
-------*---------------- Physical Processor 7
--------*--------------- Physical Processor 8
---------*-------------- Physical Processor 9
----------*------------- Physical Processor 10
-----------*------------ Physical Processor 11
------------*----------- Physical Processor 12
-------------*---------- Physical Processor 13
--------------*--------- Physical Processor 14
---------------*-------- Physical Processor 15
----------------*------- Physical Processor 16
-----------------*------ Physical Processor 17
------------------*----- Physical Processor 18
-------------------*---- Physical Processor 19
--------------------*--- Physical Processor 20
---------------------*-- Physical Processor 21
----------------------*- Physical Processor 22
-----------------------* Physical Processor 23
Logical Processor to Socket Map:
*----------------------- Socket 0
-*---------------------- Socket 1
--*--------------------- Socket 2
---*-------------------- Socket 3
----*------------------- Socket 4
-----*------------------ Socket 5
------*----------------- Socket 6
-------*---------------- Socket 7
--------*--------------- Socket 8
---------*-------------- Socket 9
----------*------------- Socket 10
-----------*------------ Socket 11
------------*----------- Socket 12
-------------*---------- Socket 13
--------------*--------- Socket 14
---------------*-------- Socket 15
----------------*------- Socket 16
-----------------*------ Socket 17
------------------*----- Socket 18
-------------------*---- Socket 19
--------------------*--- Socket 20
---------------------*-- Socket 21
----------------------*- Socket 22
-----------------------* Socket 23
Logical Processor to NUMA Node Map:
************------------ NUMA Node 0
------------************ NUMA Node 1
Approximate Cross-NUMA Node Access Cost (relative to fastest):
00 01
00: 1.0 1.2
01: 1.2 1.1
На рабочем сервере:
Logical to Physical Processor Map:
**------------------------------ Physical Processor 0 (Hyperthreaded)
--**---------------------------- Physical Processor 1 (Hyperthreaded)
----**-------------------------- Physical Processor 2 (Hyperthreaded)
------**------------------------ Physical Processor 3 (Hyperthreaded)
--------**---------------------- Physical Processor 4 (Hyperthreaded)
----------**-------------------- Physical Processor 5 (Hyperthreaded)
------------**------------------ Physical Processor 6 (Hyperthreaded)
--------------**---------------- Physical Processor 7 (Hyperthreaded)
----------------**-------------- Physical Processor 8 (Hyperthreaded)
------------------**------------ Physical Processor 9 (Hyperthreaded)
--------------------**---------- Physical Processor 10 (Hyperthreaded)
----------------------**-------- Physical Processor 11 (Hyperthreaded)
------------------------**------ Physical Processor 12 (Hyperthreaded)
--------------------------**---- Physical Processor 13 (Hyperthreaded)
----------------------------**-- Physical Processor 14 (Hyperthreaded)
------------------------------** Physical Processor 15 (Hyperthreaded)
Logical Processor to Socket Map:
****************---------------- Socket 0
----------------**************** Socket 1
Logical Processor to NUMA Node Map:
****************---------------- NUMA Node 0
----------------**************** NUMA Node 1
Approximate Cross-NUMA Node Access Cost (relative to fastest):
00 01
00: 1.0 1.3
01: 1.5 1.0
Разница понятна. На виртуальном якобы физические сокеты 24 шт, а на рабочем сервере 2 сокета и 32 ядра Hyperthread.
Прошу администраторов выровнять виртуальные машины по физическим на SQL сервере и кластере 1С, запускаю тест повторно. Урааа 1162 минуты против 937 это еще не победа, вообще результат должен быть лучше все-таки оборудование более новое. Но направление борьбы с Матрицей понятно – нужно везде разоблачать виртуальные ресурсы и отображать их на реальные физические один к одному.
Зачем нам тогда Матрица? Для белых воротничков, которые сидят в браузере и Word, для малого бизнеса которому лишние железки только лишняя нагрузка, а в браузере он выглядит даже средним бизнесом, менеджерам для экономии - кому угодно только не тем кому нужна реальная производительность.
Кто-то скажет: Вы не умеете готовить виртуальную среду?
Я отвечу: Я что - шеф повару должен объяснять как ему готовить? Да ну такой ресторан, лучше сделать свой.
Уже по идеологии виртуализации видно, что вопросы производительности там на последнем месте и все заточено на «эффективное использование ресурсов», никогда не знаешь где и когда тебе подрежут ресурсы. Самое плохое, что никто из специалистов 1С не станет изучать гипервизор и VMWare, а системные администраторы не будут глубоко лезть в архитектуру SQL сервера. В итоге любые проблемы придется решать мозговым штурмом Эксперта по тех вопросам 1С, Администратора SQL , Системного администратора и еще других занятых сотрудников только ради того чтобы убрать ограничения виртуальной среды.
Забегая вперед могу сказать, что равной производительности (и даже большей) на виртуальном кластере мы достигли, в следующей серии Матрицы.
Как изменились счетчики после выравнивания виртуальной машины можно посмотреть ниже.
Скрипты для запросов с источниками происхождения я прилагаю.
На тестовом кластере зафиксировано до оптимизации:
После выравнивания виртуальных машин с физическими сокетами и ядрами картина резко улучшилась.
Задержка по Writelog сократилась в два раза.
Как работает spinlock описано выше, но нам сейчас важно понимать, что при коллизии доступа к logbuffer значение spin увеличивается циклически пока другой поток не отпустит ресурс. Т.е чем выше значение spins_per_collision тем хуже работает связка процессор
У нас – они уменьшились на logflushq, но увеличились на logcashe_access – последнее считается признаком более интенсивной работой writelog . Замечу что на рабочем кластере статистика еще лучше, но там повышенную нагрузку не давали при измерениях. О том, что еще влияло на производительность виртуального кластера – в следующей статье. Первыми статьи появляются на нашем канале t.me/Chat1CUnlimited + дополнительная информация.
«Я не сказал, что будет легко. Я лишь обещал открыть правду.» Морфеус
Комментарии (13)
DikSoft
06.07.2022 19:13Попробуйте повторить опыт с отключением гипертрединга в BIOS на гипервизоре. Раньше у 1С сервера была серьёзная такая просадка по производительности с включенным гипертредингом. Интересно, как оно сейчас?
1CUnlimited Автор
06.07.2022 22:16Если рассматривать случай который описан в статье, дело было не в HyperThreading. Хотя да VMWare накладывает свои ограничения Hyperthreading and ESXi Hosts (vmware.com) Вообще в данном тесте проблемы вылезли больше на MS SQL сервере чем на 1С. Потому что 1С согласно документации 1С в многоядерной среде ведет себя более просто чем MS SQL
Hidden text
Следует иметь в виду, что поддержка NUMA в кластере серверов "1С:Предприятия" полноценно пока не реализована.
Сервер 1С не управляет распределением ресурсов по NUMA узлам, полностью полагаясь в этом на операционную систему, что не всегда даёт оптимальный результат.
Поэтому при работе на многопроцессорных системах (все современные многопроцессорные системы Intel и AMD имеют NUMA архитектуру), в зависимости от характера нагрузки, может наблюдаться неравномерная загрузка процессоров/ядер. В некоторых случаях может оказаться загружена только какая-то часть доступных ядер CPU, при этом другая часть будет простаивать. В таких случаях рекомендуется использовать лимит числа соединений на рабочий процесс, установленный из расчета:
ЧислоСоединенийНаПроцесс = РасчетноеМаксимальноеКоличествоСоединений/КоличествоNUMAНод.
При этом все равно возможна ситуация при которой будет перегружена только какая-то часть CPU (это можно можно увидеть в диспетчере задач 100% длительная 100% нагрузка на некоторые CPU при том, что остальные свободны). В таком случае лимит соединений на процесс следует уменьшать из расчета:
ЧислоСоединенийНаПроцесс = РасчетноеМаксимальноеКоличествоСоединений/(КоличествоNUMAНод * Коэффициент),
где коэффициент равен 2, и увеличивать его на 1 при каждой подстройке при наблюдении небалансированной нагрузки на NUMA нодах.
DikSoft
06.07.2022 22:28+1Да, это понятно. Просто имел дело с оригинальным поведением именно серверов 1С. Мы держали MS SQL в AlwaysOn на двух своих кластерах Hyper-V, а под сервера 1С специально выделили другой кластер на старых E5-2693 (v0) с отключённым HyperThreading. Только так получилось выжать максимум производительности.
А так да, всё написанное про оптимизацию MS SQL почти подходит и под случай, когда гипервизор не от VmWare. Плюс пришлось обратить пристальное внимание на тонкие настройки виртуальных свитчей и сетевых адаптеров.
1CUnlimited Автор
06.07.2022 22:46Кому интересено какие еще есть варианты болевых точек на VMWare и подобных системах можете посмотреть статью Гилева Производительность «1С» в виртуальной машине | Gilev.ru | Ускоряем 1С:Предприятие . См раздел (Ошибки выбора облаков). Но надо понимать что разработчики виртуальных систем "улучшают" и дают "новые возможности" поэтому знание 101 способа снизить производительность в виртуальной среде, не избавляет от умения найти 102 способ который еще не знаете. Я старался акцентировать внимание именно на методах поиска причин в таких ситуациях
NKulikov
06.07.2022 23:30+3"болевые точки VMware" в 95% случаев — это отсутствие базовых знаний по работе с продуктом и отсутствие навыков чтения документации и Best Practices. Если прям очень-очень надо полностью исключить переподписку и все прочее связанное с виртуализацией (обычно не надо), то для получения 99%+ процентов производительности ВМ по CPU/RAM по сравнению с bare-metal достаточно нажать несколько кнопок в GUI, которые, по сути, выключают scheduler и переключение контекста (см. настройки Latency Sensitivity). Для тюнинга вывода-вывода делает еще несколько настроек (см. pvSCSI, HPP, LRO, InterruptThrottle, Coalescing), которые обычно описаны в документах под названием "Best Practices for XXX". Принципы работы гипервизора с ресурсами, а также многое другое, подробно объяснено и разжёвано в замечательной книге VMware Host Resources Deep Dive (которая доступна в том числе бесплатно вот тут - https://www.rubrik.com/resources/white-papers/19/host-resources-deep-dive-ebook)
hadsunn
07.07.2022 15:51+1Цитата из статьи
Пример подтверждения замедлений виртуализации: Первое с чего начинается описание преимуществ «контейнеров»: Контейнеры требуют значительно меньше ресурсов для своей работы чем виртуализация, что положительно сказывается на производительности и бюджете. Т.е. виртуализация требует больше ресурсов.
А потом ещё удивляются, почему админы не уважают 1Сников...
1CUnlimited Автор
07.07.2022 15:56Мне например не очень понятно в чем проблема цитаты из статьи Гилева, но у него большой практический опыт ... В целом даже мне без знаний VMWare понятно что система на создание максимальной производительности не ориентирована, раз допускает неэффективные конфигурации и не ограничивает в этом администратора VMWare
max_rip
08.07.2022 22:29Тоже самое можно сказать и про 1с, она тоже позволяет писать код который работает неэффективно.
webhamster
07.07.2022 09:00-1Хм, VmWare, MS Sql Server, в которые упорно запихивают 1С. В свете последних событий статья несколько неактуальна?
kauksi
07.07.2022 16:00вот хорошая статьи про numa и параметр cores per socket https://www.nakivo.com/blog/the-number-of-cores-per-cpu-in-a-virtual-machine/ https://blogs.vmware.com/performance/2017/03/virtual-machine-vcpu-and-vnuma-rightsizing-rules-of-thumb.html ... А выводы как то мутно сделаны...
Speccyfan
Старайтесь не создавать машины гиганты, уж точно не больше половины ядер физического хоста (не учитывайте гипиртрейдинг), большие машины часто попадают в состояние COSTOP, когда шедулер ждет освобождения всех необходимых ядер, что бы ВМ перешла в состояние READY и RUN соответственно.
Tzimie
Люто плюсую
NKulikov
COSTOP у вас возникнет в таком случае, только если на одном хосте работает несколько таких больших ВМ, и поэтому они поочередно ждут выполнения друг друга (точнее высвобождения нужного числа ядер). Если же у вас ВМ одна, то ничего не мешает сделать её больше одного физического CPU (да, понятно, что там возникнут задержки из-за NUMA, но они ровно так же возникнут и на физике). Тут скорее рекомендация несколько другая - не надо делать ВМ больше, чем её реально требуется (например, выдавая 36 ядер при том, что приклад реально потребляет, скажем, 12, в надежде, что "ну так мы точно узкого места в CPU сможем избежать") + не надо делать ВМ размером во весь хост, ибо на части ядер работает сам гипервизор и его ядерные процессы, а на другой части ядер обрабатывается ввод-вывод самой ВМ (vNIC, pvSCSI, etc).