Комментарии 15
у старших ядер (big) размер кэш-линий составляет 128 байт, а младших (LITTLE) — 64
Вот так поворот! Можно уточнить — речь идет о размере кеш линий инструкций или инструкций и данных?
PS: Спасибо за статью
+2
Я понимаю, что глупо общаться с переводом, но всё же хочу прояснить несколько деталей.
У ARMv8 нет инструкции, которая получает размер кеша. Вводить отдельную инструкцию для такой операции было бы глупо. Вместо этого есть регистры которые описывают структуру кеша. Они описаны в ARM Architecture Reference Manual ARMv8 в разделе D3.4.2 Cache identification. И первым делом там сказано вот что:
PE — это Processing Element, т.е. просто процессор. Короче, регистры описывают структуру кеша на конкретном процессоре. Что, в принципе абсолютно логично.
То что шедуллер ОС может перекидывать код с одного ядра на другое, это не проблема архитектуры процессора. Пользовательский код должен учитывать это и например просить шедуллер не делать так.
Поэтому, я сильно не согласен с вот этой фразой:
Это просто ошибка в имплементации libgcc.
У ARMv8 нет инструкции, которая получает размер кеша. Вводить отдельную инструкцию для такой операции было бы глупо. Вместо этого есть регистры которые описывают структуру кеша. Они описаны в ARM Architecture Reference Manual ARMv8 в разделе D3.4.2 Cache identification. И первым делом там сказано вот что:
The ARMv8 cache identification registers describe the implemented caches that are affected by cache maintenance
instructions executed on the PE
PE — это Processing Element, т.е. просто процессор. Короче, регистры описывают структуру кеша на конкретном процессоре. Что, в принципе абсолютно логично.
То что шедуллер ОС может перекидывать код с одного ядра на другое, это не проблема архитектуры процессора. Пользовательский код должен учитывать это и например просить шедуллер не делать так.
Поэтому, я сильно не согласен с вот этой фразой:
Хуже того, даже набор инструкций ARM не готов к этому.
Это просто ошибка в имплементации libgcc.
+2
Пользовательский код должен учитывать это и например просить шедуллер не делать так.
Такое возможно сделать в юзерспейсе?
+2
Ага. Системный вызов sched_setaffinity() позволит прибить поток к конкретному ядру.
+3
>> set_affinity()
ОС может работать в режиме Cluster Migration или CPU Migration, когда пара ядер (большое и маленькое) видны как одно.
Старые Exynos типа 5410 могут работать лишь в первом режиме.
Аффинити тут не поможет.
Собственно это и была фишка big.LITTLE. Например Apple A10 работает так.
Более того — переключение может происходить без участия ОС, аппаратно.
Правильней таки получать минимальный размер строчки кеша откуда нибудь из ОС.
ОС может работать в режиме Cluster Migration или CPU Migration, когда пара ядер (большое и маленькое) видны как одно.
Старые Exynos типа 5410 могут работать лишь в первом режиме.
Аффинити тут не поможет.
Собственно это и была фишка big.LITTLE. Например Apple A10 работает так.
Более того — переключение может происходить без участия ОС, аппаратно.
Правильней таки получать минимальный размер строчки кеша откуда нибудь из ОС.
+3
что-то типа?
foreach core
set_affinity
get_cache_line_size
0
Мне кажется эта тема уже поднималась на Хабре.
То есть как бы сам факт такой необычной реализации уже не является новым, интереснее другое — как все-таки с этим жить? Не будет ли многопоточный код ломаться непредвиденно? И так на ARM более мягкие правила reordering'а, чем на x86, и плюс еще дополнительная нестабильность.
То есть как бы сам факт такой необычной реализации уже не является новым, интереснее другое — как все-таки с этим жить? Не будет ли многопоточный код ломаться непредвиденно? И так на ARM более мягкие правила reordering'а, чем на x86, и плюс еще дополнительная нестабильность.
0
Судя по изменениям, баг просто сделали более сложным в воспроизведении, но не избавились полностью. И даже сами признают, что может произойти, просто гораздо менее вероятно.
0
Вспомнил про эту историю, поглядел на код, почитал документацию…
В исправлении используют значение размера кэш-линии из регистра CTR_EL0, где лежит, собственно, размер самой короткой кэш-линии кэша инструкций. Более того, в документации ARM есть пример инвалидации кэша инструкций и для размера кэш-линии как раз берётся то значение. Так что, должно работать исправно.
В исправлении используют значение размера кэш-линии из регистра CTR_EL0, где лежит, собственно, размер самой короткой кэш-линии кэша инструкций. Более того, в документации ARM есть пример инвалидации кэша инструкций и для размера кэш-линии как раз берётся то значение. Так что, должно работать исправно.
0
Поправка (подразумевалось при написании комментария выше, но было упущено): там лежит не сам размер, а двоичный логарифм размера в словах, которые, соответственно, 4 байта, отсюда и берётся затем побитовый сдвиг 4 влево на эту величину.
0
Зарегистрируйтесь на Хабре , чтобы оставить комментарий
Повесть о невозможном баге: big.LITTLE и кэширование