1/*
2 * Copyright (c) 2007-2012, ETH Zurich.
3 * All rights reserved.
4 *
5 * This file is distributed under the terms in the attached LICENSE file.
6 * If you do not find this file, copies can be found by writing to:
7 * ETH Zurich D-INFK, Universitaetstrasse 6, CH-8092 Zurich. Attn: Systems Group.
8 */
9
10#include <stdio.h>
11#include <stdlib.h>
12#include <string.h>
13
14#include <barrelfish/barrelfish.h>
15#include <barrelfish/spawn_client.h>
16
17#include "sleep.h"
18
19#include <skb/skb.h>
20
21// From lib/dist/skb.c
22errval_t get_cores_skb(coreid_t **cores, int *n_cores);
23
24
25static void memory_affinity(int core, uint64_t* min, uint64_t* max)
26{
27    errval_t r;
28    r = skb_execute_query("local_memory_affinity(%d, B, L),"
29                          "write(base(B)),write(limit(L)).", core);
30    assert(err_is_ok(r));
31
32    r = skb_read_output("base(%lu)limit(%lu).", min, max);
33    assert(err_is_ok(r));
34}
35
36
37static void start_run(uint8_t core, uint8_t memory, int payload, int nocache,
38                      int read_incoming, int head_idx_wb)
39{
40    errval_t r;
41    struct capref new_domain;
42    uint8_t code;
43    char plsz[strlen("payload_size=0000") + 1];
44    char noca[strlen("elb_nocache=0") + 1];
45    char rdic[strlen("read_incoming=0") + 1];
46    char hiwb[strlen("head_idx_wb=0") + 1];
47    char affmin[64];
48    char affmax[64];
49    char prefix[128];
50    uint64_t aff_min, aff_max;
51
52    memory_affinity(memory, &aff_min, &aff_max);
53
54    char* const argv[] = { "e10k_queue_elb", "queue=0", "runs=1000",
55                           "dump_each=1", plsz, noca, rdic, hiwb, affmin,
56                           affmax, prefix, NULL };
57
58    sprintf(plsz, "payload_size=%d", payload);
59    sprintf(plsz, "elb_nocache=%d", nocache);
60    sprintf(rdic, "read_incoming=%d", read_incoming);
61    sprintf(hiwb, "head_idx_wb=%d", head_idx_wb);
62    sprintf(affmin, "affinitymin=%"PRIu64, aff_min);
63    sprintf(affmax, "affinitymax=%"PRIu64, aff_max);
64    sprintf(prefix, "elp_outprefix=%%%d,%d,%d,%d,%d,%d,", core, memory, payload,
65            nocache, read_incoming, head_idx_wb);
66
67    printf("##### spawning programm %s\n", argv[0]);
68    r = spawn_program(core, argv[0], argv, NULL, SPAWN_FLAGS_NEW_DOMAIN, &new_domain);
69    assert(err_is_ok(r));
70
71    r = spawn_wait_core(core, new_domain, &code, false);
72    assert(err_is_ok(r));
73}
74
75
76int main(int argc, char **argv)
77{
78    coreid_t *cores;
79    int core_count;
80
81    int c_idx;
82    uint8_t memory;
83    int payloadsz = 64;
84    int nocache = 0;
85    int read_incoming = 0;
86    int head_idx_wb = 1;
87    errval_t err;
88
89    sleep_init();
90
91    // Connect to SKB to get info
92    err = skb_client_connect();
93    assert(err_is_ok(err));
94
95    // Get information about available cores
96    get_cores_skb(&cores, &core_count);
97
98    printf("Net latency benchmark start\n");
99    printf("%%\"core\",\"memory\",\"payload\",\"nocache\",\"touch\",\"hiwb\","
100           "\"rtt\",\"time\"\n");
101    for (c_idx = 0; c_idx < core_count; c_idx++) {
102        for (memory = 0; memory < 16; memory += 4) {
103        for (payloadsz = 64; payloadsz < 1500; payloadsz *= 4) {
104            for (nocache = 0; nocache <= 1; nocache++) {
105                for (read_incoming = 0; read_incoming <= 1; read_incoming++) {
106                for (head_idx_wb = 0; head_idx_wb <= 1; head_idx_wb++) {
107                    start_run(cores[c_idx], memory, payloadsz, nocache,
108                             read_incoming, head_idx_wb);
109                }
110                }
111            }
112        }
113        }
114    }
115    printf("Net latency benchmark done\n");
116    return 0;
117}
118
119