SlideShare uma empresa Scribd logo
1 de 90
Baixar para ler offline
Что-то с памятью
моей стало
Сколько стоит доступ в память,
и что с этим делать
Антон Орлов
Qrator Labs
ao@qrator.net
100 Mpps
100 Mpps
10 нс / пакет
100 Mpps
10 нс / пакет
Image source:
http://www.esaitech.com/supermicro-x9drw-7tpf-b-intel-c602-lga-2
011-ddr3-1600mhz-proprietary-wio-server-motherboard.html
100 Mpps
10 нс / пакет
1 такт: 3.5 см
Image source:
http://www.esaitech.com/supermicro-x9drw-7tpf-b-intel-c602-lga-2
011-ddr3-1600mhz-proprietary-wio-server-motherboard.html
100 Mpps
10 нс / пакет
1 такт: 3.5 см
1 нс: 11 см
Image source:
http://www.esaitech.com/supermicro-x9drw-7tpf-b-intel-c602-lga-2
011-ddr3-1600mhz-proprietary-wio-server-motherboard.html
Время, нс
Размер данных
L1 L2 L3 RAM
The Myth of RAM
Emil Ernerfeldt
https://github.com/emilk/ram_bench
Время, нс
Размер данных
L1 L2 L3 RAM
The Myth of RAM
Emil Ernerfeldt
https://github.com/emilk/ram_bench
Время, нс
Размер данных
L1 L2 L3 RAM
The Myth of RAM
Emil Ernerfeldt
https://github.com/emilk/ram_bench
Время, нс
Размер данных
L1 L2 L3 RAM
The Myth of RAM
Emil Ernerfeldt
https://github.com/emilk/ram_bench
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
12.32s
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
12.32s
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
12.32s
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
12.32s
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
12.32s
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS/2; i++)
mat[i][j] = (char)j;
}
for (int j = 0; j < ROWS; j++) {
for (int i = COLUMNS/2; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
1.96s
Время, сек
Количество колонок
Как понять, что происходит?
# likwid-perfctr -E L1
Found 13 event(s) with search key L1:
PAGE_WALKER_LOADS_ITLB_L1
MEM_LOAD_UOPS_RETIRED_L1_HIT
MEM_LOAD_UOPS_RETIRED_L1_MISS
MEM_LOAD_UOPS_RETIRED_L1_ALL
L2_TRANS_L1D_WB
L1_POWER_CYCLES
L1D_PEND_MISS_PENDING
L1D_PEND_MISS_PENDING_CYCLES
L1D_PEND_MISS_OCCURRENCES
L1D_REPLACEMENT
CYCLE_ACTIVITY_CYCLES_L1D_MISS
CYCLE_ACTIVITY_STALLS_L1D_MISS
PAGE_WALKER_LOADS_DTLB_L1
https://github.com/RRZE-HPC/likwid
Как понять, что происходит?
Events:
• L1D_REPLACEMENT 911,569,595 51,124,840
• L2_TRANS_L1D_WB 957,062,801 54,446,831
Metric:
• L2 data volume [GBytes] 119.5931 6.7568
Адресация в 8-канальном
32КБ кэше
063
Адресация в 8-канальном
32КБ кэше
04863
• Кэш-линия: 64 = 26
байт
Адресация в 8-канальном
32КБ кэше
064863
• Кэш-линия: 64 = 26
байт
• Всего кэш-линий: 32 КБ / 64 Б = 512
Адресация в 8-канальном
32КБ кэше
064863
• Кэш-линия: 64 = 26
байт
• Всего кэш-линий: 32 КБ / 64 Б = 512
Адресация в 8-канальном
32КБ кэше
064863
8
Адресация в 8-канальном
32КБ кэше
064863
64
8
• Кэш-линия: 64 = 26
байт
• Всего кэш-линий: 32 КБ / 64 Б = 512
• Бакетов: 512 / 8 = 64 = 26
Адресация в 8-канальном
32КБ кэше
06124863
64
8
• Кэш-линия: 64 = 26
байт
• Всего кэш-линий: 32 КБ / 64 Б = 512
• Бакетов: 512 / 8 = 64 = 26
idx
Адресация в 8-канальном
32КБ кэше
06124863
64
8
• Кэш-линия: 64 = 26
байт
• Всего кэш-линий: 32 КБ / 64 Б = 512
• Бакетов: 512 / 8 = 64 = 26
tag idx
Адресация в 8-канальном
32КБ кэше
06124863
64
8
• Кэш-линия: 64 = 26
байт
• Всего кэш-линий: 32 КБ / 64 Б = 512
• Бакетов: 512 / 8 = 64 = 26
• В каждом бакете:
у адресов совпадают 6 бит idx
tag idx
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS);
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
12.32s
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS + 64*i) + 64*i;
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS + 64*i) + 64*i;
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS + 64*i) + 64*i;
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS + 64*i) + 64*i;
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
#define COLUMNS 10
#define ROWS (1<<28) // 256MB
int main () {
char* mat[COLUMNS];
for (int i = 0; i < COLUMNS; i++)
mat[i] = (char*)malloc(ROWS + 64*i) + 64*i;
for (int j = 0; j < ROWS; j++) {
for (int i = 0; i < COLUMNS; i++)
mat[i][j] = (char)j;
}
int res = 0;
for (int i = 0; i < COLUMNS; i++)
res += mat[i][i];
return res;
}
2.12s
Кэш L1 и виртуальная память
06124863
64
8
Виртуальный адрес:
tag idx
Кэш L1 и виртуальная память
06124863
64
8
Виртуальный адрес:
tag idx
Страница: 4096 байт (12 бит адреса)
Кэш L1 и виртуальная память
06124863
64
8
Виртуальный адрес:
tag idx
061245
Физический адрес:
tag idx
Страница: 4096 байт (12 бит адреса)
Кэш L1 и виртуальная память
06124863
64
8
Виртуальный адрес:
tag idx
061245
Физический адрес:
tag idx
Страница: 4096 байт (12 бит адреса)
TLB: кэш для трансляции адресов
Проблема мелких страниц
64
8
1. Страница: 4 КБ
64
8Проблема мелких страниц
1. Страница: 4 КБ
2. L1 = 8 × 4 КБ = 32 КБ
64
8Проблема мелких страниц
1. Страница: 4 КБ
2. L1 = 8 × 4 КБ = 32 КБ
Что делать?
• Повышать ассоциативность (канальность)
• Виртуальные адреса в кэше
64
8Проблема мелких страниц
1. Страница: 4 КБ
2. L1 = 8 × 4 КБ = 32 КБ
Что делать?
• Повышать ассоциативность (канальность)
• Виртуальные адреса в кэше
3. TLB маленький!
64 × 4 КБ = 512 КБ
1. Страница: 4 КБ
2. L1 = 8 × 4 КБ = 32 КБ
Что делать?
• Повышать ассоциативность (канальность)
• Виртуальные адреса в кэше
3. TLB маленький!
64 × 4 КБ = 512 КБ
4. Количество страниц
256 ГБ / 4 КБ = 64 М!
Проблема мелких страниц
64
8
Source: http://mechanical-sympathy.blogspot.ru/2013/02/cpu-cache-flushing-fallacy.html
Source: http://mechanical-sympathy.blogspot.ru/2013/02/cpu-cache-flushing-fallacy.html
Source: http://mechanical-sympathy.blogspot.ru/2013/02/cpu-cache-flushing-fallacy.html
Source: http://mechanical-sympathy.blogspot.ru/2013/02/cpu-cache-flushing-fallacy.html
Source: http://mechanical-sympathy.blogspot.ru/2013/02/cpu-cache-flushing-fallacy.html
Source: http://mechanical-sympathy.blogspot.ru/2013/02/cpu-cache-flushing-fallacy.html
Source: http://mechanical-sympathy.blogspot.ru/2013/02/cpu-cache-flushing-fallacy.html
Row hammer
Source: https://en.wikipedia.org/wiki/Row_hammerSource: https://www.akkadia.org/drepper/cpumemory.pdf
Row hammer
Source: https://en.wikipedia.org/wiki/Row_hammerSource: https://www.akkadia.org/drepper/cpumemory.pdf
Row hammer
Source: https://en.wikipedia.org/wiki/Row_hammerSource: https://www.akkadia.org/drepper/cpumemory.pdf
Summary
• Меньше памяти — лучше!
• Доступ в память — не O(1)
• Меньше промахов в кэши и TLB
• Меньше задержки на линках (RDIMM, LRDIMM, ECC)
Summary
• Меньше памяти — лучше!
• Доступ в память — не O(1)
• Меньше промахов в кэши и TLB
• Меньше задержки на линках (RDIMM, LRDIMM, ECC)
• Важно помнить про иерархию
• Cчетчики
• Через уровни можно прыгать
Future
1. Parallel → Serial
• HMC
2. 3D stacking
• 3D TSV RLDIMM
• HBM
3. NVRAM
Source: http://www.intelsalestraining.com/infographics/memory/3DXPointc.pdf
NVRAM в качестве основной памяти?
1: node = nvm_alloc(sizeof(node_t));
2: node->value = val;
3: node->next = head;
4: head = node;
Source: http://www.hpl.hp.com/techreports/2012/HPL-2012-236.pdf
NVRAM в качестве основной памяти?
1: node = nvm_alloc(sizeof(node_t));
2: node->value = val;
3: node->next = head;
4: head = node;
Intel:
● CLWB (Cache Line Write Back)
● PCOMMIT (to Persistent storage COMMIT)
Source: http://www.hpl.hp.com/techreports/2012/HPL-2012-236.pdf
NVRAM в качестве основной памяти?
1: node = nvm_alloc(sizeof(node_t));
2: node->value = val;
3: node->next = head;
4: head = node;
Intel:
● CLWB (Cache Line Write Back)
● PCOMMIT (to Persistent storage COMMIT)
Source: http://www.hpl.hp.com/techreports/2012/HPL-2012-236.pdf
Спасибо за внимание!
Вопросы?
“What Every Programmer Should Know About Memory”
Ulrich Drepper, 2007
https://www.akkadia.org/drepper/cpumemory.pdf
Другие полезные ссылки
• Dick Sites, Datacenter Computers: modern challenges in CPU design
Видео: https://www.youtube.com/watch?v=QBu2Ae8-8LM
Слайды: http://www.pdl.cmu.edu/SDI/2015/slides/DatacenterComputers.pdf
• What's new in CPUs since the 80s and how does it affect programmers?
http://danluu.com/new-cpu-features/
• Row hammer Android exploit https://www.vusec.net/projects/drammer/
• Kumud Bhandari, Dhruva R. Chakrabarti, Hans-J. Boehm, Implications of CPU
Caching on Byte-addressable Non-Volatile Memory Programming
http://www.hpl.hp.com/techreports/2012/HPL-2012-236.pdf
RDIMM LRDIMM
Source: https://habrahabr.ru/company/hostkey/blog/272063/
2.5 ГБ
2.5 ГБ
2.5 ГБ
L1 TLB
2.5 ГБ
L2 TLB
256 ГБ
L2 TLB

Mais conteúdo relacionado

Mais procurados

Лекция 8. Графы. Обходы графов
Лекция 8. Графы. Обходы графовЛекция 8. Графы. Обходы графов
Лекция 8. Графы. Обходы графовMikhail Kurnosov
 
8 встреча — Язык программирования Python (В. Ананьев)
8 встреча — Язык программирования Python (В. Ананьев)8 встреча — Язык программирования Python (В. Ананьев)
8 встреча — Язык программирования Python (В. Ананьев)Smolensk Computer Science Club
 
Об особенностях использования значимых типов в .NET
Об особенностях использования значимых типов в .NETОб особенностях использования значимых типов в .NET
Об особенностях использования значимых типов в .NETAndrey Akinshin
 
Pyton – пробуем функциональный стиль
Pyton – пробуем функциональный стильPyton – пробуем функциональный стиль
Pyton – пробуем функциональный стильPython Meetup
 
Григорий Демченко, “Асинхронность и сопрограммы: обработка данных“
Григорий Демченко, “Асинхронность и сопрограммы: обработка данных“Григорий Демченко, “Асинхронность и сопрограммы: обработка данных“
Григорий Демченко, “Асинхронность и сопрограммы: обработка данных“Platonov Sergey
 
Лекция 7. Стандарт OpenMP (подолжение)
Лекция 7. Стандарт OpenMP (подолжение)Лекция 7. Стандарт OpenMP (подолжение)
Лекция 7. Стандарт OpenMP (подолжение)Mikhail Kurnosov
 
DevConf. Дмитрий Сошников - ECMAScript 6
DevConf. Дмитрий Сошников - ECMAScript 6DevConf. Дмитрий Сошников - ECMAScript 6
DevConf. Дмитрий Сошников - ECMAScript 6Dmitry Soshnikov
 
Cocoheads Moscow September
Cocoheads Moscow SeptemberCocoheads Moscow September
Cocoheads Moscow SeptemberAlexander Zimin
 
Магия метаклассов
Магия метаклассовМагия метаклассов
Магия метаклассовAndrey Zakharevich
 
Python dict: прошлое, настоящее, будущее
Python dict: прошлое, настоящее, будущееPython dict: прошлое, настоящее, будущее
Python dict: прошлое, настоящее, будущееdelimitry
 
JS Fest 2019. Владимир Агафонкин. Быстро по умолчанию: алгоритмическое мышлен...
JS Fest 2019. Владимир Агафонкин. Быстро по умолчанию: алгоритмическое мышлен...JS Fest 2019. Владимир Агафонкин. Быстро по умолчанию: алгоритмическое мышлен...
JS Fest 2019. Владимир Агафонкин. Быстро по умолчанию: алгоритмическое мышлен...JSFestUA
 
DSLs in Lisp and Clojure
DSLs in Lisp and ClojureDSLs in Lisp and Clojure
DSLs in Lisp and ClojureVasil Remeniuk
 
Красота и изящность стандартной библиотеки Python
Красота и изящность стандартной библиотеки PythonКрасота и изящность стандартной библиотеки Python
Красота и изящность стандартной библиотеки PythonPython Meetup
 
Лекция 9. Поиск кратчайшего пути в графе
Лекция 9. Поиск кратчайшего пути в графеЛекция 9. Поиск кратчайшего пути в графе
Лекция 9. Поиск кратчайшего пути в графеMikhail Kurnosov
 
Лекция 4: Стек. Очередь
Лекция 4: Стек. ОчередьЛекция 4: Стек. Очередь
Лекция 4: Стек. ОчередьMikhail Kurnosov
 
Лекция 2: Абстрактные типы данных. Алгоритмы сортировки
Лекция 2: Абстрактные типы данных. Алгоритмы сортировкиЛекция 2: Абстрактные типы данных. Алгоритмы сортировки
Лекция 2: Абстрактные типы данных. Алгоритмы сортировкиMikhail Kurnosov
 
Лекция 10. Графы. Остовные деревья минимальной стоимости
Лекция 10. Графы. Остовные деревья минимальной стоимостиЛекция 10. Графы. Остовные деревья минимальной стоимости
Лекция 10. Графы. Остовные деревья минимальной стоимостиMikhail Kurnosov
 

Mais procurados (19)

Лекция 8. Графы. Обходы графов
Лекция 8. Графы. Обходы графовЛекция 8. Графы. Обходы графов
Лекция 8. Графы. Обходы графов
 
8 встреча — Язык программирования Python (В. Ананьев)
8 встреча — Язык программирования Python (В. Ананьев)8 встреча — Язык программирования Python (В. Ананьев)
8 встреча — Язык программирования Python (В. Ананьев)
 
Charming python sc2-8
Charming python sc2-8Charming python sc2-8
Charming python sc2-8
 
Об особенностях использования значимых типов в .NET
Об особенностях использования значимых типов в .NETОб особенностях использования значимых типов в .NET
Об особенностях использования значимых типов в .NET
 
Pyton – пробуем функциональный стиль
Pyton – пробуем функциональный стильPyton – пробуем функциональный стиль
Pyton – пробуем функциональный стиль
 
Григорий Демченко, “Асинхронность и сопрограммы: обработка данных“
Григорий Демченко, “Асинхронность и сопрограммы: обработка данных“Григорий Демченко, “Асинхронность и сопрограммы: обработка данных“
Григорий Демченко, “Асинхронность и сопрограммы: обработка данных“
 
Лекция 7. Стандарт OpenMP (подолжение)
Лекция 7. Стандарт OpenMP (подолжение)Лекция 7. Стандарт OpenMP (подолжение)
Лекция 7. Стандарт OpenMP (подолжение)
 
DevConf. Дмитрий Сошников - ECMAScript 6
DevConf. Дмитрий Сошников - ECMAScript 6DevConf. Дмитрий Сошников - ECMAScript 6
DevConf. Дмитрий Сошников - ECMAScript 6
 
Cocoheads Moscow September
Cocoheads Moscow SeptemberCocoheads Moscow September
Cocoheads Moscow September
 
Магия метаклассов
Магия метаклассовМагия метаклассов
Магия метаклассов
 
урок2
урок2урок2
урок2
 
Python dict: прошлое, настоящее, будущее
Python dict: прошлое, настоящее, будущееPython dict: прошлое, настоящее, будущее
Python dict: прошлое, настоящее, будущее
 
JS Fest 2019. Владимир Агафонкин. Быстро по умолчанию: алгоритмическое мышлен...
JS Fest 2019. Владимир Агафонкин. Быстро по умолчанию: алгоритмическое мышлен...JS Fest 2019. Владимир Агафонкин. Быстро по умолчанию: алгоритмическое мышлен...
JS Fest 2019. Владимир Агафонкин. Быстро по умолчанию: алгоритмическое мышлен...
 
DSLs in Lisp and Clojure
DSLs in Lisp and ClojureDSLs in Lisp and Clojure
DSLs in Lisp and Clojure
 
Красота и изящность стандартной библиотеки Python
Красота и изящность стандартной библиотеки PythonКрасота и изящность стандартной библиотеки Python
Красота и изящность стандартной библиотеки Python
 
Лекция 9. Поиск кратчайшего пути в графе
Лекция 9. Поиск кратчайшего пути в графеЛекция 9. Поиск кратчайшего пути в графе
Лекция 9. Поиск кратчайшего пути в графе
 
Лекция 4: Стек. Очередь
Лекция 4: Стек. ОчередьЛекция 4: Стек. Очередь
Лекция 4: Стек. Очередь
 
Лекция 2: Абстрактные типы данных. Алгоритмы сортировки
Лекция 2: Абстрактные типы данных. Алгоритмы сортировкиЛекция 2: Абстрактные типы данных. Алгоритмы сортировки
Лекция 2: Абстрактные типы данных. Алгоритмы сортировки
 
Лекция 10. Графы. Остовные деревья минимальной стоимости
Лекция 10. Графы. Остовные деревья минимальной стоимостиЛекция 10. Графы. Остовные деревья минимальной стоимости
Лекция 10. Графы. Остовные деревья минимальной стоимости
 

Destaque

Сетевая диагностика: новый взгляд сквозь старые щели
Сетевая диагностика: новый взгляд сквозь старые щелиСетевая диагностика: новый взгляд сквозь старые щели
Сетевая диагностика: новый взгляд сквозь старые щелиQrator Labs
 
História em quadrinhos
História em quadrinhosHistória em quadrinhos
História em quadrinhosSérgio Lima
 
Difference between Prefix & Postfix
 Difference between Prefix & Postfix Difference between Prefix & Postfix
Difference between Prefix & PostfixKms Nira
 
PROYECTO ESTADISTICA "FACTORES QUE INFLUYEN QUE LOS ESTUDIANTES DEL PL18 TEHU...
PROYECTO ESTADISTICA "FACTORES QUE INFLUYEN QUE LOS ESTUDIANTES DEL PL18 TEHU...PROYECTO ESTADISTICA "FACTORES QUE INFLUYEN QUE LOS ESTUDIANTES DEL PL18 TEHU...
PROYECTO ESTADISTICA "FACTORES QUE INFLUYEN QUE LOS ESTUDIANTES DEL PL18 TEHU...Dalia Violeta Gutierrez Ruíz
 
Songwriting Unleashed
Songwriting UnleashedSongwriting Unleashed
Songwriting UnleashedDaniel Mayo
 
А.Кумаков Apiship eRetailForum2015
А.Кумаков Apiship eRetailForum2015А.Кумаков Apiship eRetailForum2015
А.Кумаков Apiship eRetailForum2015InSales
 
DDoS Attacks - Scenery, Evolution and Mitigation
DDoS Attacks - Scenery, Evolution and MitigationDDoS Attacks - Scenery, Evolution and Mitigation
DDoS Attacks - Scenery, Evolution and MitigationWilson Rogerio Lopes
 
DDoS Prevention: Market Growth, Deployments, and NSS Test Results
DDoS Prevention: Market Growth, Deployments, and NSS Test ResultsDDoS Prevention: Market Growth, Deployments, and NSS Test Results
DDoS Prevention: Market Growth, Deployments, and NSS Test ResultsNSS Labs
 
Utilizando a Lousa Digital e o Projetor PROINFO
Utilizando a Lousa Digital e o Projetor PROINFOUtilizando a Lousa Digital e o Projetor PROINFO
Utilizando a Lousa Digital e o Projetor PROINFOSérgio Lima
 
Introduction to programming
Introduction to programmingIntroduction to programming
Introduction to programmingPTtp WgWt
 
Latest resume ETA Aug 2016
Latest resume ETA Aug 2016Latest resume ETA Aug 2016
Latest resume ETA Aug 2016senthil kumar
 

Destaque (14)

Сетевая диагностика: новый взгляд сквозь старые щели
Сетевая диагностика: новый взгляд сквозь старые щелиСетевая диагностика: новый взгляд сквозь старые щели
Сетевая диагностика: новый взгляд сквозь старые щели
 
História em quadrinhos
História em quadrinhosHistória em quadrinhos
História em quadrinhos
 
Difference between Prefix & Postfix
 Difference between Prefix & Postfix Difference between Prefix & Postfix
Difference between Prefix & Postfix
 
PROYECTO ESTADISTICA "FACTORES QUE INFLUYEN QUE LOS ESTUDIANTES DEL PL18 TEHU...
PROYECTO ESTADISTICA "FACTORES QUE INFLUYEN QUE LOS ESTUDIANTES DEL PL18 TEHU...PROYECTO ESTADISTICA "FACTORES QUE INFLUYEN QUE LOS ESTUDIANTES DEL PL18 TEHU...
PROYECTO ESTADISTICA "FACTORES QUE INFLUYEN QUE LOS ESTUDIANTES DEL PL18 TEHU...
 
Songwriting Unleashed
Songwriting UnleashedSongwriting Unleashed
Songwriting Unleashed
 
А.Кумаков Apiship eRetailForum2015
А.Кумаков Apiship eRetailForum2015А.Кумаков Apiship eRetailForum2015
А.Кумаков Apiship eRetailForum2015
 
Виртуальный номер связывает филиалы в единую сеть
Виртуальный номер связывает филиалы в единую сетьВиртуальный номер связывает филиалы в единую сеть
Виртуальный номер связывает филиалы в единую сеть
 
Capital budgeting
Capital budgetingCapital budgeting
Capital budgeting
 
DDoS Attacks - Scenery, Evolution and Mitigation
DDoS Attacks - Scenery, Evolution and MitigationDDoS Attacks - Scenery, Evolution and Mitigation
DDoS Attacks - Scenery, Evolution and Mitigation
 
DDoS Prevention: Market Growth, Deployments, and NSS Test Results
DDoS Prevention: Market Growth, Deployments, and NSS Test ResultsDDoS Prevention: Market Growth, Deployments, and NSS Test Results
DDoS Prevention: Market Growth, Deployments, and NSS Test Results
 
WSO2-WSF-install-manual-linux-th
WSO2-WSF-install-manual-linux-thWSO2-WSF-install-manual-linux-th
WSO2-WSF-install-manual-linux-th
 
Utilizando a Lousa Digital e o Projetor PROINFO
Utilizando a Lousa Digital e o Projetor PROINFOUtilizando a Lousa Digital e o Projetor PROINFO
Utilizando a Lousa Digital e o Projetor PROINFO
 
Introduction to programming
Introduction to programmingIntroduction to programming
Introduction to programming
 
Latest resume ETA Aug 2016
Latest resume ETA Aug 2016Latest resume ETA Aug 2016
Latest resume ETA Aug 2016
 

Semelhante a Сколько стоит доступ в память, и что с этим делать

CSSO – история ускорения
CSSO – история ускоренияCSSO – история ускорения
CSSO – история ускоренияRoman Dvornov
 
Лекция 8: Многопоточное программирование: Intel Threading Building Blocks
Лекция 8: Многопоточное программирование: Intel Threading Building BlocksЛекция 8: Многопоточное программирование: Intel Threading Building Blocks
Лекция 8: Многопоточное программирование: Intel Threading Building BlocksMikhail Kurnosov
 
Аскетичная разработка браузера
Аскетичная разработка браузераАскетичная разработка браузера
Аскетичная разработка браузераPlatonov Sergey
 
ПВТ - осень 2014 - Лекция 5 - Многопоточное программирование в языке С++. Р...
ПВТ - осень 2014 - Лекция 5 - Многопоточное программирование в языке С++.   Р...ПВТ - осень 2014 - Лекция 5 - Многопоточное программирование в языке С++.   Р...
ПВТ - осень 2014 - Лекция 5 - Многопоточное программирование в языке С++. Р...Alexey Paznikov
 
Extended High-Level C-Compatible Memory Model with Limited Low-Level Pointer ...
Extended High-Level C-Compatible Memory Model with Limited Low-Level Pointer ...Extended High-Level C-Compatible Memory Model with Limited Low-Level Pointer ...
Extended High-Level C-Compatible Memory Model with Limited Low-Level Pointer ...Iosif Itkin
 
Лекция 8. Intel Threading Building Blocks
Лекция 8. Intel Threading Building BlocksЛекция 8. Intel Threading Building Blocks
Лекция 8. Intel Threading Building BlocksMikhail Kurnosov
 
Aleksei Milovidov "Let's optimize one aggregate function in ClickHouse"
Aleksei Milovidov "Let's optimize one aggregate function in ClickHouse"Aleksei Milovidov "Let's optimize one aggregate function in ClickHouse"
Aleksei Milovidov "Let's optimize one aggregate function in ClickHouse"Fwdays
 
Встреча №9. Алгоритмы и коллекции стандартных библиотек C++, C#, Java, Object...
Встреча №9. Алгоритмы и коллекции стандартных библиотек C++, C#, Java, Object...Встреча №9. Алгоритмы и коллекции стандартных библиотек C++, C#, Java, Object...
Встреча №9. Алгоритмы и коллекции стандартных библиотек C++, C#, Java, Object...CocoaHeads
 
Догнать и перегнать boost::lexical_cast
Догнать и перегнать boost::lexical_castДогнать и перегнать boost::lexical_cast
Догнать и перегнать boost::lexical_castRoman Orlov
 
Статический анализ кода
Статический анализ кода Статический анализ кода
Статический анализ кода Pavel Tsukanov
 
статический анализ кода
статический анализ кодастатический анализ кода
статический анализ кодаAndrey Karpov
 
Архитектура корпоративных систем
Архитектура корпоративных системАрхитектура корпоративных систем
Архитектура корпоративных системConstantin Kichinsky
 

Semelhante a Сколько стоит доступ в память, и что с этим делать (14)

CSSO – история ускорения
CSSO – история ускоренияCSSO – история ускорения
CSSO – история ускорения
 
Лекция 8: Многопоточное программирование: Intel Threading Building Blocks
Лекция 8: Многопоточное программирование: Intel Threading Building BlocksЛекция 8: Многопоточное программирование: Intel Threading Building Blocks
Лекция 8: Многопоточное программирование: Intel Threading Building Blocks
 
Аскетичная разработка браузера
Аскетичная разработка браузераАскетичная разработка браузера
Аскетичная разработка браузера
 
Array Work C
Array Work CArray Work C
Array Work C
 
ПВТ - осень 2014 - Лекция 5 - Многопоточное программирование в языке С++. Р...
ПВТ - осень 2014 - Лекция 5 - Многопоточное программирование в языке С++.   Р...ПВТ - осень 2014 - Лекция 5 - Многопоточное программирование в языке С++.   Р...
ПВТ - осень 2014 - Лекция 5 - Многопоточное программирование в языке С++. Р...
 
Extended High-Level C-Compatible Memory Model with Limited Low-Level Pointer ...
Extended High-Level C-Compatible Memory Model with Limited Low-Level Pointer ...Extended High-Level C-Compatible Memory Model with Limited Low-Level Pointer ...
Extended High-Level C-Compatible Memory Model with Limited Low-Level Pointer ...
 
Algo 00
Algo 00Algo 00
Algo 00
 
Лекция 8. Intel Threading Building Blocks
Лекция 8. Intel Threading Building BlocksЛекция 8. Intel Threading Building Blocks
Лекция 8. Intel Threading Building Blocks
 
Aleksei Milovidov "Let's optimize one aggregate function in ClickHouse"
Aleksei Milovidov "Let's optimize one aggregate function in ClickHouse"Aleksei Milovidov "Let's optimize one aggregate function in ClickHouse"
Aleksei Milovidov "Let's optimize one aggregate function in ClickHouse"
 
Встреча №9. Алгоритмы и коллекции стандартных библиотек C++, C#, Java, Object...
Встреча №9. Алгоритмы и коллекции стандартных библиотек C++, C#, Java, Object...Встреча №9. Алгоритмы и коллекции стандартных библиотек C++, C#, Java, Object...
Встреча №9. Алгоритмы и коллекции стандартных библиотек C++, C#, Java, Object...
 
Догнать и перегнать boost::lexical_cast
Догнать и перегнать boost::lexical_castДогнать и перегнать boost::lexical_cast
Догнать и перегнать boost::lexical_cast
 
Статический анализ кода
Статический анализ кода Статический анализ кода
Статический анализ кода
 
статический анализ кода
статический анализ кодастатический анализ кода
статический анализ кода
 
Архитектура корпоративных систем
Архитектура корпоративных системАрхитектура корпоративных систем
Архитектура корпоративных систем
 

Mais de Qrator Labs

Годовой отчет Qrator Labs об угрозах интернета 2017
Годовой отчет Qrator Labs об угрозах интернета 2017Годовой отчет Qrator Labs об угрозах интернета 2017
Годовой отчет Qrator Labs об угрозах интернета 2017Qrator Labs
 
Qrator Labs annual report 2017
Qrator Labs annual report 2017Qrator Labs annual report 2017
Qrator Labs annual report 2017Qrator Labs
 
Memcached amplification DDoS: a 2018 threat.
Memcached amplification DDoS: a 2018 threat. Memcached amplification DDoS: a 2018 threat.
Memcached amplification DDoS: a 2018 threat. Qrator Labs
 
DNS Survival Guide.
DNS Survival Guide.DNS Survival Guide.
DNS Survival Guide.Qrator Labs
 
BGP Flexibility and its Consequences.
BGP Flexibility and its Consequences. BGP Flexibility and its Consequences.
BGP Flexibility and its Consequences. Qrator Labs
 
BGP Route Leaks at Ripe74
BGP Route Leaks at Ripe74BGP Route Leaks at Ripe74
BGP Route Leaks at Ripe74Qrator Labs
 
IoT: реальная угроза или маркетинг?
IoT: реальная угроза или маркетинг?IoT: реальная угроза или маркетинг?
IoT: реальная угроза или маркетинг?Qrator Labs
 
Network Security in 2016
Network Security in 2016Network Security in 2016
Network Security in 2016Qrator Labs
 
Состояние сетевой безопасности в 2016 году
Состояние сетевой безопасности в 2016 году Состояние сетевой безопасности в 2016 году
Состояние сетевой безопасности в 2016 году Qrator Labs
 
Анализ количества посетителей на сайте [Считаем уникальные элементы]
Анализ количества посетителей на сайте [Считаем уникальные элементы]Анализ количества посетителей на сайте [Считаем уникальные элементы]
Анализ количества посетителей на сайте [Считаем уникальные элементы]Qrator Labs
 
Caution i pv6 is here
Caution i pv6 is hereCaution i pv6 is here
Caution i pv6 is hereQrator Labs
 
Масштабируя TLS
Масштабируя TLSМасштабируя TLS
Масштабируя TLSQrator Labs
 
ISP Border Definition
ISP Border DefinitionISP Border Definition
ISP Border DefinitionQrator Labs
 
DDoS Attacks in 2017: Beyond Packet Filtering
DDoS Attacks in 2017: Beyond Packet FilteringDDoS Attacks in 2017: Beyond Packet Filtering
DDoS Attacks in 2017: Beyond Packet FilteringQrator Labs
 
Internet Roads of Caucasus
Internet Roads of CaucasusInternet Roads of Caucasus
Internet Roads of CaucasusQrator Labs
 
Latency i pv4 vs ipv6
Latency i pv4 vs ipv6Latency i pv4 vs ipv6
Latency i pv4 vs ipv6Qrator Labs
 
Особенности использования машинного обучения при защите от DDoS-атак
Особенности использования машинного обучения при защите от DDoS-атакОсобенности использования машинного обучения при защите от DDoS-атак
Особенности использования машинного обучения при защите от DDoS-атакQrator Labs
 
Финансовый сектор. Аспекты информационной безопасности 2016
Финансовый сектор. Аспекты информационной безопасности 2016Финансовый сектор. Аспекты информационной безопасности 2016
Финансовый сектор. Аспекты информационной безопасности 2016Qrator Labs
 
White Paper. Эволюция DDoS-атак и средств противодействия данной угрозе
White Paper. Эволюция DDoS-атак и средств противодействия данной угрозеWhite Paper. Эволюция DDoS-атак и средств противодействия данной угрозе
White Paper. Эволюция DDoS-атак и средств противодействия данной угрозеQrator Labs
 
Тренды 2015 года в области интернет-безопасности в россии и в мире
Тренды 2015 года в области интернет-безопасности в россии и в миреТренды 2015 года в области интернет-безопасности в россии и в мире
Тренды 2015 года в области интернет-безопасности в россии и в миреQrator Labs
 

Mais de Qrator Labs (20)

Годовой отчет Qrator Labs об угрозах интернета 2017
Годовой отчет Qrator Labs об угрозах интернета 2017Годовой отчет Qrator Labs об угрозах интернета 2017
Годовой отчет Qrator Labs об угрозах интернета 2017
 
Qrator Labs annual report 2017
Qrator Labs annual report 2017Qrator Labs annual report 2017
Qrator Labs annual report 2017
 
Memcached amplification DDoS: a 2018 threat.
Memcached amplification DDoS: a 2018 threat. Memcached amplification DDoS: a 2018 threat.
Memcached amplification DDoS: a 2018 threat.
 
DNS Survival Guide.
DNS Survival Guide.DNS Survival Guide.
DNS Survival Guide.
 
BGP Flexibility and its Consequences.
BGP Flexibility and its Consequences. BGP Flexibility and its Consequences.
BGP Flexibility and its Consequences.
 
BGP Route Leaks at Ripe74
BGP Route Leaks at Ripe74BGP Route Leaks at Ripe74
BGP Route Leaks at Ripe74
 
IoT: реальная угроза или маркетинг?
IoT: реальная угроза или маркетинг?IoT: реальная угроза или маркетинг?
IoT: реальная угроза или маркетинг?
 
Network Security in 2016
Network Security in 2016Network Security in 2016
Network Security in 2016
 
Состояние сетевой безопасности в 2016 году
Состояние сетевой безопасности в 2016 году Состояние сетевой безопасности в 2016 году
Состояние сетевой безопасности в 2016 году
 
Анализ количества посетителей на сайте [Считаем уникальные элементы]
Анализ количества посетителей на сайте [Считаем уникальные элементы]Анализ количества посетителей на сайте [Считаем уникальные элементы]
Анализ количества посетителей на сайте [Считаем уникальные элементы]
 
Caution i pv6 is here
Caution i pv6 is hereCaution i pv6 is here
Caution i pv6 is here
 
Масштабируя TLS
Масштабируя TLSМасштабируя TLS
Масштабируя TLS
 
ISP Border Definition
ISP Border DefinitionISP Border Definition
ISP Border Definition
 
DDoS Attacks in 2017: Beyond Packet Filtering
DDoS Attacks in 2017: Beyond Packet FilteringDDoS Attacks in 2017: Beyond Packet Filtering
DDoS Attacks in 2017: Beyond Packet Filtering
 
Internet Roads of Caucasus
Internet Roads of CaucasusInternet Roads of Caucasus
Internet Roads of Caucasus
 
Latency i pv4 vs ipv6
Latency i pv4 vs ipv6Latency i pv4 vs ipv6
Latency i pv4 vs ipv6
 
Особенности использования машинного обучения при защите от DDoS-атак
Особенности использования машинного обучения при защите от DDoS-атакОсобенности использования машинного обучения при защите от DDoS-атак
Особенности использования машинного обучения при защите от DDoS-атак
 
Финансовый сектор. Аспекты информационной безопасности 2016
Финансовый сектор. Аспекты информационной безопасности 2016Финансовый сектор. Аспекты информационной безопасности 2016
Финансовый сектор. Аспекты информационной безопасности 2016
 
White Paper. Эволюция DDoS-атак и средств противодействия данной угрозе
White Paper. Эволюция DDoS-атак и средств противодействия данной угрозеWhite Paper. Эволюция DDoS-атак и средств противодействия данной угрозе
White Paper. Эволюция DDoS-атак и средств противодействия данной угрозе
 
Тренды 2015 года в области интернет-безопасности в россии и в мире
Тренды 2015 года в области интернет-безопасности в россии и в миреТренды 2015 года в области интернет-безопасности в россии и в мире
Тренды 2015 года в области интернет-безопасности в россии и в мире
 

Сколько стоит доступ в память, и что с этим делать

  • 1. Что-то с памятью моей стало Сколько стоит доступ в память, и что с этим делать Антон Орлов Qrator Labs ao@qrator.net
  • 3. 100 Mpps 10 нс / пакет
  • 4. 100 Mpps 10 нс / пакет Image source: http://www.esaitech.com/supermicro-x9drw-7tpf-b-intel-c602-lga-2 011-ddr3-1600mhz-proprietary-wio-server-motherboard.html
  • 5. 100 Mpps 10 нс / пакет 1 такт: 3.5 см Image source: http://www.esaitech.com/supermicro-x9drw-7tpf-b-intel-c602-lga-2 011-ddr3-1600mhz-proprietary-wio-server-motherboard.html
  • 6. 100 Mpps 10 нс / пакет 1 такт: 3.5 см 1 нс: 11 см Image source: http://www.esaitech.com/supermicro-x9drw-7tpf-b-intel-c602-lga-2 011-ddr3-1600mhz-proprietary-wio-server-motherboard.html
  • 7. Время, нс Размер данных L1 L2 L3 RAM The Myth of RAM Emil Ernerfeldt https://github.com/emilk/ram_bench
  • 8. Время, нс Размер данных L1 L2 L3 RAM The Myth of RAM Emil Ernerfeldt https://github.com/emilk/ram_bench
  • 9. Время, нс Размер данных L1 L2 L3 RAM The Myth of RAM Emil Ernerfeldt https://github.com/emilk/ram_bench
  • 10. Время, нс Размер данных L1 L2 L3 RAM The Myth of RAM Emil Ernerfeldt https://github.com/emilk/ram_bench
  • 11. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 12. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 13. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 14. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 15. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 16. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 17. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 18. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 19. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 20. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 21. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; } 12.32s
  • 22. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; } 12.32s #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 23. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; } 12.32s #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 24. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; } 12.32s #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 25. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 26. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 27. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 28. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 29. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 30. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 31. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 32. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 33. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 34. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 35. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 36. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 37. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 38. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; } 12.32s #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS/2; i++) mat[i][j] = (char)j; } for (int j = 0; j < ROWS; j++) { for (int i = COLUMNS/2; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; } 1.96s
  • 40. Как понять, что происходит? # likwid-perfctr -E L1 Found 13 event(s) with search key L1: PAGE_WALKER_LOADS_ITLB_L1 MEM_LOAD_UOPS_RETIRED_L1_HIT MEM_LOAD_UOPS_RETIRED_L1_MISS MEM_LOAD_UOPS_RETIRED_L1_ALL L2_TRANS_L1D_WB L1_POWER_CYCLES L1D_PEND_MISS_PENDING L1D_PEND_MISS_PENDING_CYCLES L1D_PEND_MISS_OCCURRENCES L1D_REPLACEMENT CYCLE_ACTIVITY_CYCLES_L1D_MISS CYCLE_ACTIVITY_STALLS_L1D_MISS PAGE_WALKER_LOADS_DTLB_L1 https://github.com/RRZE-HPC/likwid
  • 41. Как понять, что происходит? Events: • L1D_REPLACEMENT 911,569,595 51,124,840 • L2_TRANS_L1D_WB 957,062,801 54,446,831 Metric: • L2 data volume [GBytes] 119.5931 6.7568
  • 44. • Кэш-линия: 64 = 26 байт Адресация в 8-канальном 32КБ кэше 064863
  • 45. • Кэш-линия: 64 = 26 байт • Всего кэш-линий: 32 КБ / 64 Б = 512 Адресация в 8-канальном 32КБ кэше 064863
  • 46. • Кэш-линия: 64 = 26 байт • Всего кэш-линий: 32 КБ / 64 Б = 512 Адресация в 8-канальном 32КБ кэше 064863 8
  • 47. Адресация в 8-канальном 32КБ кэше 064863 64 8 • Кэш-линия: 64 = 26 байт • Всего кэш-линий: 32 КБ / 64 Б = 512 • Бакетов: 512 / 8 = 64 = 26
  • 48. Адресация в 8-канальном 32КБ кэше 06124863 64 8 • Кэш-линия: 64 = 26 байт • Всего кэш-линий: 32 КБ / 64 Б = 512 • Бакетов: 512 / 8 = 64 = 26 idx
  • 49. Адресация в 8-канальном 32КБ кэше 06124863 64 8 • Кэш-линия: 64 = 26 байт • Всего кэш-линий: 32 КБ / 64 Б = 512 • Бакетов: 512 / 8 = 64 = 26 tag idx
  • 50. Адресация в 8-канальном 32КБ кэше 06124863 64 8 • Кэш-линия: 64 = 26 байт • Всего кэш-линий: 32 КБ / 64 Б = 512 • Бакетов: 512 / 8 = 64 = 26 • В каждом бакете: у адресов совпадают 6 бит idx tag idx
  • 51. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS); for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; } 12.32s
  • 52. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS + 64*i) + 64*i; for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 53. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS + 64*i) + 64*i; for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 54. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS + 64*i) + 64*i; for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 55. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS + 64*i) + 64*i; for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; }
  • 56. #define COLUMNS 10 #define ROWS (1<<28) // 256MB int main () { char* mat[COLUMNS]; for (int i = 0; i < COLUMNS; i++) mat[i] = (char*)malloc(ROWS + 64*i) + 64*i; for (int j = 0; j < ROWS; j++) { for (int i = 0; i < COLUMNS; i++) mat[i][j] = (char)j; } int res = 0; for (int i = 0; i < COLUMNS; i++) res += mat[i][i]; return res; } 2.12s
  • 57. Кэш L1 и виртуальная память 06124863 64 8 Виртуальный адрес: tag idx
  • 58. Кэш L1 и виртуальная память 06124863 64 8 Виртуальный адрес: tag idx Страница: 4096 байт (12 бит адреса)
  • 59. Кэш L1 и виртуальная память 06124863 64 8 Виртуальный адрес: tag idx 061245 Физический адрес: tag idx Страница: 4096 байт (12 бит адреса)
  • 60. Кэш L1 и виртуальная память 06124863 64 8 Виртуальный адрес: tag idx 061245 Физический адрес: tag idx Страница: 4096 байт (12 бит адреса) TLB: кэш для трансляции адресов
  • 62. 64 8Проблема мелких страниц 1. Страница: 4 КБ 2. L1 = 8 × 4 КБ = 32 КБ
  • 63. 64 8Проблема мелких страниц 1. Страница: 4 КБ 2. L1 = 8 × 4 КБ = 32 КБ Что делать? • Повышать ассоциативность (канальность) • Виртуальные адреса в кэше
  • 64. 64 8Проблема мелких страниц 1. Страница: 4 КБ 2. L1 = 8 × 4 КБ = 32 КБ Что делать? • Повышать ассоциативность (канальность) • Виртуальные адреса в кэше 3. TLB маленький! 64 × 4 КБ = 512 КБ
  • 65. 1. Страница: 4 КБ 2. L1 = 8 × 4 КБ = 32 КБ Что делать? • Повышать ассоциативность (канальность) • Виртуальные адреса в кэше 3. TLB маленький! 64 × 4 КБ = 512 КБ 4. Количество страниц 256 ГБ / 4 КБ = 64 М! Проблема мелких страниц 64 8
  • 73. Row hammer Source: https://en.wikipedia.org/wiki/Row_hammerSource: https://www.akkadia.org/drepper/cpumemory.pdf
  • 74. Row hammer Source: https://en.wikipedia.org/wiki/Row_hammerSource: https://www.akkadia.org/drepper/cpumemory.pdf
  • 75. Row hammer Source: https://en.wikipedia.org/wiki/Row_hammerSource: https://www.akkadia.org/drepper/cpumemory.pdf
  • 76. Summary • Меньше памяти — лучше! • Доступ в память — не O(1) • Меньше промахов в кэши и TLB • Меньше задержки на линках (RDIMM, LRDIMM, ECC)
  • 77. Summary • Меньше памяти — лучше! • Доступ в память — не O(1) • Меньше промахов в кэши и TLB • Меньше задержки на линках (RDIMM, LRDIMM, ECC) • Важно помнить про иерархию • Cчетчики • Через уровни можно прыгать
  • 78. Future 1. Parallel → Serial • HMC 2. 3D stacking • 3D TSV RLDIMM • HBM 3. NVRAM
  • 80. NVRAM в качестве основной памяти? 1: node = nvm_alloc(sizeof(node_t)); 2: node->value = val; 3: node->next = head; 4: head = node; Source: http://www.hpl.hp.com/techreports/2012/HPL-2012-236.pdf
  • 81. NVRAM в качестве основной памяти? 1: node = nvm_alloc(sizeof(node_t)); 2: node->value = val; 3: node->next = head; 4: head = node; Intel: ● CLWB (Cache Line Write Back) ● PCOMMIT (to Persistent storage COMMIT) Source: http://www.hpl.hp.com/techreports/2012/HPL-2012-236.pdf
  • 82. NVRAM в качестве основной памяти? 1: node = nvm_alloc(sizeof(node_t)); 2: node->value = val; 3: node->next = head; 4: head = node; Intel: ● CLWB (Cache Line Write Back) ● PCOMMIT (to Persistent storage COMMIT) Source: http://www.hpl.hp.com/techreports/2012/HPL-2012-236.pdf
  • 83. Спасибо за внимание! Вопросы? “What Every Programmer Should Know About Memory” Ulrich Drepper, 2007 https://www.akkadia.org/drepper/cpumemory.pdf
  • 84. Другие полезные ссылки • Dick Sites, Datacenter Computers: modern challenges in CPU design Видео: https://www.youtube.com/watch?v=QBu2Ae8-8LM Слайды: http://www.pdl.cmu.edu/SDI/2015/slides/DatacenterComputers.pdf • What's new in CPUs since the 80s and how does it affect programmers? http://danluu.com/new-cpu-features/ • Row hammer Android exploit https://www.vusec.net/projects/drammer/ • Kumud Bhandari, Dhruva R. Chakrabarti, Hans-J. Boehm, Implications of CPU Caching on Byte-addressable Non-Volatile Memory Programming http://www.hpl.hp.com/techreports/2012/HPL-2012-236.pdf