Вопрос

Я пытаюсь прочитать из основной памяти, используя сборку masm32, и для этого я создал (как было рекомендовано ранее в ответе на другой из моих вопросов здесь) массив, который будет содержать сильно разделенные области памяти (во избежание чтения из кэш).Мне удалось создать массив и прочитать его, однако у меня возникла проблема.Этот массив, который я уже сделал и протестировал, работает с данными, которые я ему дал (т.цифры) и все работает.Но мне нужны места воспоминаний, и я нигде не могу найти ни карты, ни ссылок на них.Я имею в виду, мне нужно что-то вроде:

my_arr db 5, 2, 8, 9, 1, 7, 3, 0, 4, 6

но вместо использования чисел я должен использовать соответствующие зарезервированные слова ячейки памяти.Но я не могу их найти =( или даже понятия не имею, что еще искать.


Редактировать

Позвольте мне просто проверить, правильно ли я понял, а затем вы скажете мне, что я мог бы (вместо использования массива использовать переменные со всем пространством между ними, чтобы принудительно читать из основной памяти, верно?

Это было полезно?

Решение

Как вы сказали, это массив (непрерывных) байтов:

my_arr db 5, 2, 8, 9, 1, 7, 3, 0, 4, 6

Это переменная, занимающая 10 МБ (что много относительно кэша ЦП):

wasted_space BYTE 10485760 DUP(?)

Вот несколько переменных, между которыми много лишнего места:

my_var_1 db 5
spacer_1 BYTE 10485760 DUP(?)
my_var_2 db 2
spacer_2 BYTE 10485760 DUP(?)
my_var_3 db 8
spacer_3 BYTE 10485760 DUP(?)
my_var_4 db 9
spacer_4 BYTE 10485760 DUP(?)
my_var_5 db 1
spacer_5 BYTE 10485760 DUP(?)
my_var_6 db 7
spacer_6 BYTE 10485760 DUP(?)
my_var_7 db 3
spacer_7 BYTE 10485760 DUP(?)
my_var_8 db 0
spacer_8 BYTE 10485760 DUP(?)
my_var_9 db 4
spacer_8 BYTE 10485760 DUP(?)
my_var_10 db 6

Это (создание переменных в вашем сегменте данных) — один из способов получить некоторые адреса памяти данных (переменные не содержат адрес...скорее, переменные находятся по адресам).

Другой способ получить адреса памяти — вызвать API-интерфейсы операционной системы, которые выделяют память из кучи и возвращают адрес этой выделенной памяти, например API-интерфейсы HeapAlloc или VirtualAlloc.


Я не знаю, зачем вы это делаете в ASM (кроме изучения ассемблера).Если вам нужно изучить кэширование, я думаю, вы могли бы сделать это так же хорошо (и проще), используя C.

В любом случае, мне стало интересно по поводу кеширования:сколько места достаточно, чтобы вызвать промах кэша?Сколько различных переменных необходимо, чтобы начать вызывать промахи (учитывая, что кэш разделен и поэтому может содержать несколько (но только несколько) широко расположенных кэшей памяти)?

Очевидно, что с годами это (кэширование) стало сложной темой. http://lwn.net/Articles/252125/ это статья, связанная с Википедией.Эта статья включает в себя некоторые графики, например. Рисунок 3.11:Последовательное чтение для нескольких размеров.

Другие советы

Косвенный доступ к памяти в ассемблере

Чтобы рассматривать байты массива как адреса памяти, вам необходимо загрузить их в регистр, который может служить базовым адресом, а затем получить доступ к памяти, на которую указывает этот регистр:

MOV AX, [MY_ARR+3]  ; Element 3 in array, that is 9
MOV BX, [AX]        ; Read from that address

О кэшах

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

Кроме того, учтите, что ваш кеш, вероятно, ассоциативен, а это означает, что адреса, находящиеся очень далеко друг от друга, могут помещаться в кеш вместе, если они не находятся в одних и тех же (полных) строках кеша.

Чтобы фактически исчерпать кеш и гарантировать, что вам придется обращаться к памяти напрямую, вы должны получить доступ (в цикле) к набору последовательных ячеек памяти, превышающих ваш кеш.Т.е.создайте массив размером с ваш кеш.Также учтите, что, вероятно, существует несколько уровней кеша (L1, L2, возможно, L3 и далее), поэтому размер вашего кэша зависит от того, какой кеш вы хотите переполнить.


Однажды я написал программу на языке C для расчета времени доступа к памяти и кэшу, как эта, и с некоторыми статистическими вычислениями и компенсацией накладных расходов на измерение времени (которыми нельзя пренебрегать в таких коротких промежутках времени) получил действительно точные результаты (которые могут быть можно сделать настолько точным, насколько это необходимо, если проводить тест дольше и ждать, пока стандартное отклонение уменьшится).

Моя программа, однако, была не самым эффективным способом сделать это, а также не особо намекала на ассоциативность кэша (мне пришлось бы измерять это отдельно, зная схему раскраски).Однако оба были сделаны довольно эффективно, относительно независимо от архитектуры, с несколькими продуманными приемами в SIGMETRICS 2005, работа Ларри Маквоя и Карла Сталина..

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top