feat: add info.

This commit is contained in:
tqcq 2024-10-21 01:33:09 +00:00
parent 686a3664d9
commit b13cd88d57
3 changed files with 378 additions and 377 deletions

4
.gitignore vendored
View File

@ -0,0 +1,4 @@
.cache
compile_commands.json
obj
.obj

View File

@ -4,7 +4,7 @@ LDIR=lib
BUILD=obj BUILD=obj
ODIR=src/.obj ODIR=src/.obj
CFLAGS=-I$(IDIR) -O3 #-ggdb CFLAGS=-I$(IDIR) #-ggdb
# CXX=g++ # CXX=g++
LDFLAGS= LDFLAGS=

View File

@ -1,27 +1,27 @@
#include <stdbool.h>
#include <time.h>
#include <stdlib.h>
#include <sched.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <assert.h> #include <assert.h>
#include <fcntl.h>
#include <inttypes.h> #include <inttypes.h>
#include <sched.h>
#include <stdbool.h>
#include <stdlib.h>
#include <string.h> #include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <time.h>
#include <vector>
#include <set>
#include <functional>
#include <algorithm> #include <algorithm>
#include <bitset> #include <bitset>
#include <functional>
#include <set>
#include <vector>
#include "rev-mc.h" #include "rev-mc.h"
#define BOOL_XOR(a,b) ((a) != (b)) #define BOOL_XOR(a, b) ((a) != (b))
#define O_HEADER "base,probe,time\n" #define O_HEADER "base,probe,time\n"
#define ALIGN_TO(X, Y) ((X) & (~((1LL<<(Y))-1LL))) // Mask out the lower Y bits #define ALIGN_TO(X, Y) \
#define LS_BITMASK(X) ((1LL<<(X))-1LL) // Mask only the lower X bits ((X) & (~((1LL << (Y)) - 1LL))) // Mask out the lower Y bits
#define LS_BITMASK(X) ((1LL << (X)) - 1LL) // Mask only the lower X bits
#define SET_SIZE 40 // elements per set #define SET_SIZE 40 // elements per set
#define VALID_THRESH 0.75f #define VALID_THRESH 0.75f
@ -29,28 +29,35 @@
#define BITSET_SIZE 256 // bitset used to exploit bitwise operations #define BITSET_SIZE 256 // bitset used to exploit bitwise operations
#define ROW_SET_CNT 5 #define ROW_SET_CNT 5
// from https://stackoverflow.com/questions/1644868/define-macro-for-debug-printing-in-c // from
// https://stackoverflow.com/questions/1644868/define-macro-for-debug-printing-in-c
#define verbose_printerr(fmt, ...) \ #define verbose_printerr(fmt, ...) \
do { if (flags & F_VERBOSE) { fprintf(stderr, fmt, ##__VA_ARGS__); } } while(0) do { \
if (flags & F_VERBOSE) { \
fprintf(stderr, fmt, ##__VA_ARGS__); \
} \
} while (0)
typedef std::vector<addr_tuple> set_t; typedef std::vector<addr_tuple> set_t;
//------------------------------------------- //-------------------------------------------
bool is_in(char* val, std::set<char*> arr); bool is_in(char *val, std::set<char *> arr);
bool is_in(char* val, std::vector<char*> arr); bool is_in(char *val, std::vector<char *> arr);
bool found_enough(std::vector<set_t> sets, uint64_t set_cnt, size_t set_size); bool found_enough(std::vector<set_t> sets, uint64_t set_cnt, size_t set_size);
void filter_sets(std::vector<set_t>& sets, size_t set_size); void filter_sets(std::vector<set_t> &sets, size_t set_size);
void print_sets(std::vector<set_t> sets); void print_sets(std::vector<set_t> sets);
void verify_sets(std::vector<set_t>& sets, uint64_t threshold, size_t rounds); void verify_sets(std::vector<set_t> &sets, uint64_t threshold, size_t rounds);
//------------------------------------------- //-------------------------------------------
#pragma push_options
#pragma optimize("O0")
static std::vector<uint64_t> time_vals; static std::vector<uint64_t> time_vals;
uint64_t time_tuple(volatile char* a1, volatile char* a2, size_t rounds) { uint64_t time_tuple(volatile char *a1, volatile char *a2, size_t rounds) {
// uint64_t* time_vals = (uint64_t*) calloc(rounds, sizeof(uint64_t)); // uint64_t* time_vals = (uint64_t*) calloc(rounds, sizeof(uint64_t));
if (rounds > time_vals.size())
time_vals.resize(rounds); time_vals.resize(rounds);
uint64_t t0; uint64_t t0;
sched_yield(); sched_yield();
for (size_t i = 0; i < rounds; i++) { for (size_t i = 0; i < rounds; i++) {
@ -62,33 +69,27 @@ uint64_t time_tuple(volatile char* a1, volatile char* a2, size_t rounds) {
lfence(); lfence();
clflush(a1); clflush(a1);
clflush(a2); clflush(a2);
} }
uint64_t mdn = median(time_vals.data(), rounds); uint64_t mdn = median(time_vals.data(), rounds);
// free(time_vals); // free(time_vals);
return mdn; return mdn;
} }
#pragma pop_options
//---------------------------------------------------------- //----------------------------------------------------------
char* get_rnd_addr(char* base, size_t m_size, size_t align) { char *get_rnd_addr(char *base, size_t m_size, size_t align) {
return (char*) ALIGN_TO((uint64_t) base, (uint64_t) align) + ALIGN_TO(rand() % m_size, (uint64_t) align); return (char *)ALIGN_TO((uint64_t)base, (uint64_t)align) +
} ALIGN_TO(rand() % m_size, (uint64_t)align);
//----------------------------------------------------------
uint64_t get_pfn(uint64_t entry) {
return ((entry) & 0x3fffffffffffff);
} }
//---------------------------------------------------------- //----------------------------------------------------------
uint64_t get_phys_addr(uint64_t v_addr) uint64_t get_pfn(uint64_t entry) { return ((entry) & 0x3fffffffffffff); }
{
//----------------------------------------------------------
uint64_t get_phys_addr(uint64_t v_addr) {
uint64_t entry; uint64_t entry;
uint64_t offset = (v_addr/4096) * sizeof(entry); uint64_t offset = (v_addr / 4096) * sizeof(entry);
uint64_t pfn; uint64_t pfn;
int fd = open("/proc/self/pagemap", O_RDONLY); int fd = open("/proc/self/pagemap", O_RDONLY);
assert(fd >= 0); assert(fd >= 0);
@ -97,19 +98,15 @@ uint64_t get_phys_addr(uint64_t v_addr)
assert(bytes_read == 8); assert(bytes_read == 8);
assert(entry & (1ULL << 63)); assert(entry & (1ULL << 63));
pfn = get_pfn(entry); pfn = get_pfn(entry);
assert(pfn != 0); assert(pfn != 0 && "pfn is zero !!!!!");
return (pfn*4096) | (v_addr & 4095); return (pfn * 4096) | (v_addr & 4095);
} }
//---------------------------------------------------------- //----------------------------------------------------------
addr_tuple gen_addr_tuple(char* v_addr) { addr_tuple gen_addr_tuple(char *v_addr) {
return (addr_tuple) { v_addr, get_phys_addr((uint64_t) v_addr)}; return (addr_tuple){v_addr, get_phys_addr((uint64_t)v_addr)};
} }
//---------------------------------------------------------- //----------------------------------------------------------
// https://www.cs.umd.edu/~gasarch/TOPICS/factoring/fastgauss.pdf // https://www.cs.umd.edu/~gasarch/TOPICS/factoring/fastgauss.pdf
// gaussian elimination in GF2 // gaussian elimination in GF2
@ -120,9 +117,9 @@ std::vector<uint64_t> reduce_masks(std::vector<uint64_t> masks) {
height = masks.size(); height = masks.size();
width = 0; width = 0;
for (auto m:masks) { for (auto m : masks) {
uint64_t max_one = 64 - __builtin_clzl(m); uint64_t max_one = 64 - __builtin_clzl(m);
width = (max_one > width)? max_one:width; width = (max_one > width) ? max_one : width;
} }
height_t = width; height_t = width;
@ -132,14 +129,14 @@ std::vector<uint64_t> reduce_masks(std::vector<uint64_t> masks) {
std::vector<std::vector<bool>> mtx_t(height_t, std::vector<bool>(width_t)); std::vector<std::vector<bool>> mtx_t(height_t, std::vector<bool>(width_t));
std::vector<uint64_t> filtered_masks; std::vector<uint64_t> filtered_masks;
for (size_t i =0; i<height;i++) { for (size_t i = 0; i < height; i++) {
for (size_t j=0; j<width; j++) { for (size_t j = 0; j < width; j++) {
mtx[i][width - j - 1] = (masks[i] & (1ULL<<(j))); mtx[i][width - j - 1] = (masks[i] & (1ULL << (j)));
} }
} }
for (size_t i =0; i<height;i++) { for (size_t i = 0; i < height; i++) {
for (size_t j=0; j<width; j++) { for (size_t j = 0; j < width; j++) {
mtx_t[j][i] = mtx[i][j]; mtx_t[j][i] = mtx[i][j];
} }
} }
@ -150,17 +147,16 @@ std::vector<uint64_t> reduce_masks(std::vector<uint64_t> masks) {
for (uint64_t row = 0; row < height_t; row++) { for (uint64_t row = 0; row < height_t; row++) {
if (mtx_t[row][pvt_col]) { if (mtx_t[row][pvt_col]) {
filtered_masks.push_back(masks[pvt_col]); filtered_masks.push_back(masks[pvt_col]);
for (size_t c=0; c<width_t; c++) { for (size_t c = 0; c < width_t; c++) {
if (c == pvt_col) if (c == pvt_col)
continue; continue;
if (!(mtx_t[row][c])) if (!(mtx_t[row][c]))
continue; continue;
// column sum // column sum
for (size_t r=0; r<height_t; r++) { for (size_t r = 0; r < height_t; r++) {
mtx_t[r][c] = BOOL_XOR(mtx_t[r][c], mtx_t[r][pvt_col]); mtx_t[r][c] = BOOL_XOR(mtx_t[r][c], mtx_t[r][pvt_col]);
} }
} }
break; break;
} }
@ -169,11 +165,8 @@ std::vector<uint64_t> reduce_masks(std::vector<uint64_t> masks) {
} }
return filtered_masks; return filtered_masks;
} }
//---------------------------------------------------------- //----------------------------------------------------------
// from https://graphics.stanford.edu/~seander/bithacks.html#NextBitPermutation // from https://graphics.stanford.edu/~seander/bithacks.html#NextBitPermutation
uint64_t next_bit_permutation(uint64_t v) { uint64_t next_bit_permutation(uint64_t v) {
@ -181,25 +174,27 @@ uint64_t next_bit_permutation(uint64_t v) {
return (t + 1) | (((~t & -~t) - 1) >> (__builtin_ctzl(v) + 1)); return (t + 1) | (((~t & -~t) - 1) >> (__builtin_ctzl(v) + 1));
} }
//---------------------------------------------------------- //----------------------------------------------------------
std::vector<uint64_t> find_functions(std::vector<set_t> sets, size_t max_fn_bits, size_t msb, uint64_t flags) { std::vector<uint64_t> find_functions(std::vector<set_t> sets,
size_t max_fn_bits, size_t msb,
uint64_t flags) {
std::vector<uint64_t> masks; std::vector<uint64_t> masks;
verbose_printerr("~~~~~~~~~~ Candidate functions ~~~~~~~~~~\n"); verbose_printerr("~~~~~~~~~~ Candidate functions ~~~~~~~~~~\n");
for (size_t bits = 1L; bits <= max_fn_bits; bits++) { for (size_t bits = 1L; bits <= max_fn_bits; bits++) {
uint64_t fn_mask = ((1L<<(bits))-1); // avoid the first 6 bits since they are the cacheline bits uint64_t fn_mask =
uint64_t last_mask = (fn_mask<<(msb-bits)); ((1L << (bits)) -
1); // avoid the first 6 bits since they are the cacheline bits
uint64_t last_mask = (fn_mask << (msb - bits));
fn_mask <<= CL_SHIFT; fn_mask <<= CL_SHIFT;
verbose_printerr("[ LOG ] - #Bits: %ld \n", bits); verbose_printerr("[ LOG ] - #Bits: %ld \n", bits);
while (fn_mask != last_mask) { while (fn_mask != last_mask) {
if (fn_mask & LS_BITMASK(6)){ if (fn_mask & LS_BITMASK(6)) {
fn_mask = next_bit_permutation(fn_mask); fn_mask = next_bit_permutation(fn_mask);
continue; continue;
} }
for (size_t idx = 0; idx<sets.size(); idx++) { for (size_t idx = 0; idx < sets.size(); idx++) {
set_t curr_set = sets[idx]; set_t curr_set = sets[idx];
size_t inner_cnt = 0; size_t inner_cnt = 0;
for (size_t i = 1; i < curr_set.size(); i++) { for (size_t i = 1; i < curr_set.size(); i++) {
@ -210,7 +205,8 @@ std::vector<uint64_t> find_functions(std::vector<set_t> sets, size_t max_fn_bits
} }
} }
} }
verbose_printerr("\t Candidate: 0x%0lx \t\t bits: %s\n", fn_mask, bit_string(fn_mask)); verbose_printerr("\t Candidate: 0x%0lx \t\t bits: %s\n", fn_mask,
bit_string(fn_mask));
masks.push_back(fn_mask); masks.push_back(fn_mask);
next_mask: next_mask:
@ -220,21 +216,20 @@ std::vector<uint64_t> find_functions(std::vector<set_t> sets, size_t max_fn_bits
verbose_printerr("~~~~~~~~~~ Found Functions ~~~~~~~~~~\n"); verbose_printerr("~~~~~~~~~~ Found Functions ~~~~~~~~~~\n");
masks = reduce_masks(masks); masks = reduce_masks(masks);
if (flags & F_VERBOSE) { if (flags & F_VERBOSE) {
for (auto m: masks) { for (auto m : masks) {
fprintf(stderr, "\t Valid Function: 0x%0lx \t\t bits: %s\n", m, bit_string(m)); fprintf(stderr, "\t Valid Function: 0x%0lx \t\t bits: %s\n", m,
bit_string(m));
} }
} }
for (auto m: masks) { for (auto m : masks) {
fprintf(stdout, "0x%lx\n", m); fprintf(stdout, "0x%lx\n", m);
} }
return masks; return masks;
} }
std::vector<int> find_set_bits(uint64_t val) { std::vector<int> find_set_bits(uint64_t val) {
std::vector<int> set_bits; std::vector<int> set_bits;
for (int i = 0; i<64; i++) { for (int i = 0; i < 64; i++) {
if (!(val & (1ULL << i))) if (!(val & (1ULL << i)))
continue; continue;
@ -244,10 +239,11 @@ std::vector<int> find_set_bits(uint64_t val) {
} }
//---------------------------------------------------------- //----------------------------------------------------------
std::vector<uint8_t> get_dram_fn(uint64_t addr, std::vector<uint64_t> fn_masks) { std::vector<uint8_t> get_dram_fn(uint64_t addr,
std::vector<uint64_t> fn_masks) {
std::vector<uint8_t> addr_dram; std::vector<uint8_t> addr_dram;
for (auto fn:fn_masks) { for (auto fn : fn_masks) {
addr_dram.push_back(__builtin_parityl( addr & fn)); addr_dram.push_back(__builtin_parityl(addr & fn));
} }
return addr_dram; return addr_dram;
} }
@ -255,58 +251,56 @@ std::vector<uint8_t> get_dram_fn(uint64_t addr, std::vector<uint64_t> fn_masks)
//---------------------------------------------------------- //----------------------------------------------------------
/* /*
It currently finds some of the interesting bits for the row addressing. It currently finds some of the interesting bits for the row addressing.
@TODO still need to figure out which bits are used for the row addressing and which @TODO still need to figure out which bits are used for the row addressing and
are from the bank selection. This is currently done manually which are from the bank selection. This is currently done manually
*/ */
uint64_t find_row_mask(std::vector<set_t>& sets, std::vector<uint64_t> fn_masks, mem_buff_t mem, uint64_t threshold, uint64_t flags) { uint64_t find_row_mask(std::vector<set_t> &sets, std::vector<uint64_t> fn_masks,
mem_buff_t mem, uint64_t threshold, uint64_t flags) {
addr_tuple base_addr = gen_addr_tuple(get_rnd_addr(mem.buffer, mem.size, 0)); addr_tuple base_addr = gen_addr_tuple(get_rnd_addr(mem.buffer, mem.size, 0));
std::vector<set_t> same_row_sets; std::vector<set_t> same_row_sets;
verbose_printerr("~~~~~~~~~~ Looking for row bits ~~~~~~~~~~\n"); verbose_printerr("~~~~~~~~~~ Looking for row bits ~~~~~~~~~~\n");
for (int i = 0; i < 2; i++) { for (int i = 0; i < 2; i++) {
verbose_printerr("[LOG] - Set #%d\n", i); verbose_printerr("[LOG] - Set #%d\n", i);
addr_tuple base_addr = sets[i][0]; addr_tuple base_addr = sets[i][0];
std::vector<uint8_t> base_dram = get_dram_fn((uint64_t)base_addr.p_addr, fn_masks); std::vector<uint8_t> base_dram =
get_dram_fn((uint64_t)base_addr.p_addr, fn_masks);
same_row_sets.push_back({base_addr}); same_row_sets.push_back({base_addr});
uint64_t cnt = 0; uint64_t cnt = 0;
while (cnt < ROW_SET_CNT) { while (cnt < ROW_SET_CNT) {
addr_tuple tmp = gen_addr_tuple(get_rnd_addr(mem.buffer, mem.size, 0)); addr_tuple tmp = gen_addr_tuple(get_rnd_addr(mem.buffer, mem.size, 0));
if (get_dram_fn((uint64_t) tmp.p_addr, fn_masks) != base_dram) if (get_dram_fn((uint64_t)tmp.p_addr, fn_masks) != base_dram)
continue; continue;
uint64_t time = time_tuple((volatile char*)base_addr.v_addr, (volatile char*)tmp.v_addr, 1000); uint64_t time = time_tuple((volatile char *)base_addr.v_addr,
(volatile char *)tmp.v_addr, 1000);
if (time > threshold) if (time > threshold)
continue; continue;
verbose_printerr("[LOG] - %lx - %lx\t Time: %ld <== GOTCHA\n",
verbose_printerr("[LOG] - %lx - %lx\t Time: %ld <== GOTCHA\n", base_addr.p_addr, tmp.p_addr, time); base_addr.p_addr, tmp.p_addr, time);
same_row_sets[i].push_back(tmp); same_row_sets[i].push_back(tmp);
cnt++; cnt++;
} }
} }
uint64_t row_mask = LS_BITMASK(16); // use 16 bits for the row uint64_t row_mask = LS_BITMASK(16); // use 16 bits for the row
uint64_t last_mask = (row_mask<<(40-16)); uint64_t last_mask = (row_mask << (40 - 16));
row_mask <<= CL_SHIFT; // skip the lowest 6 bits since they're used for CL addressing row_mask <<=
CL_SHIFT; // skip the lowest 6 bits since they're used for CL addressing
while (row_mask < last_mask) { while (row_mask < last_mask) {
if (row_mask & LS_BITMASK(CL_SHIFT)){ if (row_mask & LS_BITMASK(CL_SHIFT)) {
row_mask = next_bit_permutation(row_mask); row_mask = next_bit_permutation(row_mask);
continue; continue;
} }
for (auto addr_pool:same_row_sets) { for (auto addr_pool : same_row_sets) {
addr_tuple base_addr = addr_pool[0]; addr_tuple base_addr = addr_pool[0];
for (int i = 1; i < addr_pool.size(); i++) { for (int i = 1; i < addr_pool.size(); i++) {
addr_tuple tmp = addr_pool[i]; addr_tuple tmp = addr_pool[i];
@ -314,7 +308,6 @@ uint64_t find_row_mask(std::vector<set_t>& sets, std::vector<uint64_t> fn_masks,
goto next_mask; goto next_mask;
} }
} }
} }
break; break;
@ -325,20 +318,20 @@ uint64_t find_row_mask(std::vector<set_t>& sets, std::vector<uint64_t> fn_masks,
return row_mask; return row_mask;
// super hackish way to recover the real row mask // super hackish way to recover the real row mask
for (auto m:fn_masks) { for (auto m : fn_masks) {
uint64_t lsb = (1<<(__builtin_ctzl(m)+1)); uint64_t lsb = (1 << (__builtin_ctzl(m) + 1));
if (lsb & row_mask) { if (lsb & row_mask) {
row_mask ^= (1<<__builtin_ctzl(m)); row_mask ^= (1 << __builtin_ctzl(m));
} }
} }
verbose_printerr("[LOG] - Row mask: 0x%0lx \t\t bits: %s\n", row_mask, bit_string(row_mask)); verbose_printerr("[LOG] - Row mask: 0x%0lx \t\t bits: %s\n", row_mask,
bit_string(row_mask));
printf("0x%lx\n", row_mask); printf("0x%lx\n", row_mask);
} }
//---------------------------------------------------------- //----------------------------------------------------------
void rev_mc(size_t sets_cnt, size_t threshold, size_t rounds, size_t m_size, char* o_file, uint64_t flags) { void rev_mc(size_t sets_cnt, size_t threshold, size_t rounds, size_t m_size,
char *o_file, uint64_t flags) {
time_t t; time_t t;
@ -346,17 +339,17 @@ void rev_mc(size_t sets_cnt, size_t threshold, size_t rounds, size_t m_size, cha
int huge_fd = 0; int huge_fd = 0;
std::vector<set_t> sets; std::vector<set_t> sets;
// std::vector<char*> used_addr; // std::vector<char*> used_addr;
std::set<char*> used_addr; std::set<char *> used_addr;
std::vector<uint64_t> fn_masks; std::vector<uint64_t> fn_masks;
srand((unsigned) time(&t)); srand((unsigned)time(&t));
if (flags & F_EXPORT) { if (flags & F_EXPORT) {
if (o_file == NULL) { if (o_file == NULL) {
fprintf(stderr, "[ERROR] - Missing export file name\n"); fprintf(stderr, "[ERROR] - Missing export file name\n");
exit(1); exit(1);
} }
if((o_fd = open(o_file, O_CREAT|O_RDWR, 0644)) == -1) { if ((o_fd = open(o_file, O_CREAT | O_RDWR, 0644)) == -1) {
perror("[ERROR] - Unable to create export file"); perror("[ERROR] - Unable to create export file");
exit(1); exit(1);
} }
@ -366,14 +359,13 @@ void rev_mc(size_t sets_cnt, size_t threshold, size_t rounds, size_t m_size, cha
mem_buff_t mem = { mem_buff_t mem = {
.buffer = NULL, .buffer = NULL,
.size = m_size, .size = m_size,
.flags = flags , .flags = flags,
}; };
alloc_buffer(&mem); alloc_buffer(&mem);
while (!found_enough(sets, sets_cnt, SET_SIZE)) { while (!found_enough(sets, sets_cnt, SET_SIZE)) {
char* rnd_addr = get_rnd_addr(mem.buffer, mem.size, CL_SHIFT); char *rnd_addr = get_rnd_addr(mem.buffer, mem.size, CL_SHIFT);
if (is_in(rnd_addr, used_addr)) if (is_in(rnd_addr, used_addr))
continue; continue;
@ -385,12 +377,15 @@ void rev_mc(size_t sets_cnt, size_t threshold, size_t rounds, size_t m_size, cha
for (size_t idx = 0; idx < sets.size(); idx++) { for (size_t idx = 0; idx < sets.size(); idx++) {
uint64_t time = 0; uint64_t time = 0;
addr_tuple tmp = sets[idx][0]; addr_tuple tmp = sets[idx][0];
time = time_tuple((volatile char*) tmp.v_addr, (volatile char*)tp.v_addr, rounds); time = time_tuple((volatile char *)tmp.v_addr, (volatile char *)tp.v_addr,
rounds);
if (flags & F_EXPORT) { if (flags & F_EXPORT) {
dprintf(o_fd, "%lx,%lx,%ld\n",(uint64_t) tp.v_addr, (uint64_t) tmp.v_addr,time); dprintf(o_fd, "%lx,%lx,%ld\n", (uint64_t)tp.v_addr,
(uint64_t)tmp.v_addr, time);
} }
if (time > threshold) { if (time > threshold) {
verbose_printerr("[LOG] - [%ld] Set: %03ld -\t %lx - %lx\t Time: %ld\n", used_addr.size(), idx, tp.p_addr, tmp.p_addr, time); verbose_printerr("[LOG] - [%ld] Set: %03ld -\t %lx - %lx\t Time: %ld\n",
used_addr.size(), idx, tp.p_addr, tmp.p_addr, time);
sets[idx].push_back(tp); sets[idx].push_back(tp);
found_set = true; found_set = true;
break; break;
@ -398,15 +393,17 @@ void rev_mc(size_t sets_cnt, size_t threshold, size_t rounds, size_t m_size, cha
} }
if (!found_set) { if (!found_set) {
sets.push_back({tp}); sets.push_back({tp});
verbose_printerr( "[LOG] - Set: %03ld -\t %p <== NEW!!\n", sets.size(), tp.v_addr); verbose_printerr("[LOG] - Set: %03ld -\t %p "
" <== NEW!!\n",
sets.size(), tp.v_addr);
} }
} }
filter_sets(sets, SET_SIZE); filter_sets(sets, SET_SIZE);
#ifdef DEBUG_SETS #ifdef DEBUG_SETS
fprintf(stderr, "[ LOG ] - Cleansing sets. This may take a while... stay put\n"); fprintf(stderr,
"[ LOG ] - Cleansing sets. This may take a while... stay put\n");
verify_sets(sets, threshold, rounds); verify_sets(sets, threshold, rounds);
fprintf(stderr, "[ LOG ] - Done\n"); fprintf(stderr, "[ LOG ] - Done\n");
#endif #endif
@ -421,19 +418,17 @@ void rev_mc(size_t sets_cnt, size_t threshold, size_t rounds, size_t m_size, cha
free_buffer(&mem); free_buffer(&mem);
} }
// Fin. // Fin.
//---------------------------------------------------------- //----------------------------------------------------------
// Helpers // Helpers
bool is_in(char* val, std::set<char*> arr) { bool is_in(char *val, std::set<char *> arr) {
return arr.find(val) != arr.end(); return arr.find(val) != arr.end();
} }
bool is_in(char* val, std::vector<char*> arr) { bool is_in(char *val, std::vector<char *> arr) {
for (auto v: arr) { for (auto v : arr) {
if (val == v) { if (val == v) {
return true; return true;
} }
@ -446,7 +441,7 @@ bool found_enough(std::vector<set_t> sets, uint64_t set_cnt, size_t set_size) {
size_t found_sets = 0; size_t found_sets = 0;
for (int i =0; i < sets.size(); i++) { for (int i = 0; i < sets.size(); i++) {
set_t curr_set = sets[i]; set_t curr_set = sets[i];
if (curr_set.size() > set_size) { if (curr_set.size() > set_size) {
found_sets += 1; found_sets += 1;
@ -454,15 +449,17 @@ bool found_enough(std::vector<set_t> sets, uint64_t set_cnt, size_t set_size) {
} }
if (found_sets > set_cnt) { if (found_sets > set_cnt) {
fprintf(stderr, "[ERROR] - Found too many sets. Is %ld the correct number of sets?\n", set_cnt); fprintf(
stderr,
"[ERROR] - Found too many sets. Is %ld the correct number of sets?\n",
set_cnt);
exit(1); exit(1);
} }
return (found_sets >= (set_cnt * SET_THRESH)) ? true : false; return (found_sets >= (set_cnt * SET_THRESH)) ? true : false;
} }
void filter_sets(std::vector<set_t> &sets, size_t set_size) {
void filter_sets(std::vector<set_t>& sets, size_t set_size) {
for (auto s = sets.begin(); s < sets.end(); s++) { for (auto s = sets.begin(); s < sets.end(); s++) {
if (s->size() < set_size) { if (s->size() < set_size) {
@ -472,22 +469,22 @@ void filter_sets(std::vector<set_t>& sets, size_t set_size) {
} }
} }
void print_sets(std::vector<set_t> sets) { void print_sets(std::vector<set_t> sets) {
for (int idx = 0; idx < sets.size(); idx++) { for (int idx = 0; idx < sets.size(); idx++) {
fprintf(stderr, "[LOG] - Set: %d\tSize: %ld\n", idx, sets[idx].size()); fprintf(stderr, "[LOG] - Set: %d\tSize: %ld\n", idx, sets[idx].size());
for (auto tmp: sets[idx]) { for (auto tmp : sets[idx]) {
fprintf(stderr, "\tv_addr:%p - p_addr:%p\n", tmp.v_addr, (void*) tmp.p_addr); fprintf(stderr, "\tv_addr:%p - p_addr:%p\n", tmp.v_addr,
(void *)tmp.p_addr);
} }
} }
} }
#ifdef DEBUG_SETS #ifdef DEBUG_SETS
void verify_sets(std::vector<set_t>& sets, uint64_t threshold, size_t rounds) { void verify_sets(std::vector<set_t> &sets, uint64_t threshold, size_t rounds) {
for (auto s: sets) { for (auto s : sets) {
// test every address against all the addresses in the set // test every address against all the addresses in the set
for (auto tp_base = s.begin(); tp_base < s.end(); tp_base++) { for (auto tp_base = s.begin(); tp_base < s.end(); tp_base++) {
uint64_t conflicts = 0; uint64_t conflicts = 0;
@ -495,12 +492,13 @@ void verify_sets(std::vector<set_t>& sets, uint64_t threshold, size_t rounds) {
if (tp_base == tp_probe) if (tp_base == tp_probe)
continue; continue;
uint64_t time = time_tuple((volatile char*) tp_base->v_addr,(volatile char*) tp_probe->v_addr, rounds); uint64_t time = time_tuple((volatile char *)tp_base->v_addr,
if (time>threshold){ (volatile char *)tp_probe->v_addr, rounds);
if (time > threshold) {
conflicts += 1; conflicts += 1;
} }
} }
if (!(conflicts > VALID_THRESH*s.size())) { if (!(conflicts > VALID_THRESH * s.size())) {
fprintf(stderr, "[ LOG ] - Removing: %p\n", tp_base->v_addr); fprintf(stderr, "[ LOG ] - Removing: %p\n", tp_base->v_addr);
s.erase(tp_base--); // reset the iterator s.erase(tp_base--); // reset the iterator
} }
@ -509,4 +507,3 @@ void verify_sets(std::vector<set_t>& sets, uint64_t threshold, size_t rounds) {
} }
#endif #endif