Действительно ли возможно выделить, в пространстве пользователя, не кэшируемом блоке памяти на Linux?

Я использовал следующее решение для этого:

findAllByStartDateLessThanEqualAndEndDateGreaterThanEqual(OffsetDateTime endDate, OffsetDateTime startDate);
7
задан dicroce 20 May 2009 в 00:20
поделиться

4 ответа

Как избежать загрязнения кешей такими данными, описано в Что каждый программист должен знать о памяти (PDF) - Это написано с точки зрения разработки Red Hat. так идеально подходит для вас. Однако по большей части он кроссплатформенный.

То, что вы хотите, называется «Non-Temporal Access» и сообщает процессору ожидать, что значение, которое вы сейчас читаете, не понадобится снова какое-то время. Затем процессор избегает кэширования этого значения.

См. Страницу 49 PDF-файла, который я указал выше. Он использует встроенные средства Intel для потоковой передачи данных вокруг кеша.

На стороне чтения - процессоры, пока в последнее время не хватало поддержки, кроме слабые подсказки, использующие невременной доступ (NTA) инструкции предварительной выборки. Там есть нет эквивалента объединению записи для читает, что особенно плохо для некэшируемая память, такая как ввод-вывод с отображением памяти. Intel с Расширения SSE4.1, представил NTA нагрузки. Они реализованы с использованием небольшое количество потоковой нагрузки буферы; каждый буфер содержит кеш линия. Первая инструкция movntdqa для данной строки кэша загрузит строка кэша в буфер, возможно замена другой строки кэша. Последующие 16-байтовые обращения к будет обслуживаться та же строка кэша из буфера загрузки за небольшую плату. Если нет других причин делать так что строка кеша не будет загружена в кеш, что позволяет загрузка больших объемов памяти не загрязняя тайники. В компилятор предоставляет встроенную функцию для эта инструкция:

#include <smmintrin.h>
__m128i _mm_stream_load_si128 (__m128i *p); 

Эту встроенную функцию следует использовать несколько раз с адресами 16-байтовые блоки, переданные как параметр, пока каждая строка кэша не будет читать. Только тогда следующий кеш линия будет запущена. Поскольку есть несколько буферы потокового чтения это может быть можно читать из двух ячеек location at once

Было бы идеально, если бы при чтении буферы считывались в линейном порядке через память. Для этого вы используете потоковое чтение. Когда вы хотите их изменить, буферы изменяются в линейном порядке, и вы можете использовать для этого потоковую запись, если вы не ожидаете, что в ближайшее время их снова прочитаете из того же потока.

9
ответ дан 6 December 2019 в 21:18
поделиться

Frequently updated data actually is the perfect application of cache. As jdt mentioned, modern CPU caches are quite large, and 0.5mb might well fit in cache. More importantly, though, read-modify-write to uncached memory is VERY slow - the initial read has to block on memory, then the write operation ALSO has to block on memory in order to commit. And just to add insult to injury, the CPU might implement no-cache memory by loading the data into cache, then immediately invalidating the cache line - thus leaving you in a position which is guaranteed to be worse than before.

Before you try outsmarting the CPU like this, you really should benchmark the entire program, and see where the real slowdown is. Modern profilers such as valgrind's cachegrind can measure cache misses, so you can find if that is a significant source of slowdown as well.

On another, more practical note, if you're doing 30 RMWs per second, this is at the worst case something on the order of 1920 bytes of cache footprint. This is only 1/16 of the L1 size of a modern Core 2 processor, and likely to be lost in the general noise of the system. So don't worry about it too much :)

That said, if by 'accessed simultaneously' you mean 'accessed by multiple threads simultaneously', be careful about cache lines bouncing between CPUs. This wouldn't be helped by uncached RAM - if anything it'd be worse, as the data would have to travel all the way back to physical RAM each time instead of possibly passing through the faster inter-CPU bus - and the only way to avoid it as a problem is to minimize the frequency of access to shared data. For more about this, see http://www.ddj.com/hpc-high-performance-computing/217500206

2
ответ дан 6 December 2019 в 21:18
поделиться

Вы также можете изучить сходство процессора, чтобы уменьшить перегрузку кэша.

1
ответ дан 6 December 2019 в 21:18
поделиться

На некоторых архитектурах процессоров есть специальные инструкции, которые можно использовать для пометки определенных строк кэша как отключенных. Однако они обычно зависят от архитектуры и от некоторых инструкций по сборке. Итак, я бы посоветовал вам обратиться к документации по архитектуре процессора и разобраться, как это сделать в сборке. Затем вы можете использовать встроенную сборку с GCC, чтобы активировать ее. Однако это снизило бы производительность.

PS: Если вы можете, вы можете подумать о другом способе обработки данных?

0
ответ дан 6 December 2019 в 21:18
поделиться
Другие вопросы по тегам:

Похожие вопросы: