Чтение онлайн

ЖАНРЫ

QNX/UNIX: Анатомия параллелизма
Шрифт:

unsigned int blk = 100;

char PATH[_POSIX_PATH_MAX] = "";

bool lowlvl = true;

while ((opt = getopt(argc, argv, "n:b:d")) != -1) {

switch(opt) {

case 'n': // имя сетевого узла

strcpy(PATH, "/net/");

strcat(PATH, optarg);

break;

case 'b': // размер блока данных

if (sscanf(optarg, "%i", &blk) ! = 1)

exit("parse command line failed");

break;

case 'd': //
обмен сообщениями

lowlvl = false;

break;

default:

exit(EXIT_FAILURE);

}

}

strcat(PATH, DEVNAME);

cout << "server path: " << PATH

<< ", block size = " << blk << " bytes" << endl;

// при инициализации мы сразу получаем скорость процессора клиента

result data;

cout << "CPU speed [c.p.s.]: client = " << data.cps;

uint64_t cps = data.cps;

// пытаемся подключиться к серверу-менеджеру

int fd = open(PATH, O_RDONLY);

if (fd < 0) exit("server not found");

// читаем его параметры

if (read(fd, &data, sizeof(result)) == -1)

exit("parameter block read");

cout << ", server = " << data.cps << endl;

// определяем дескриптор сетевого узла

int32_t node = netmgr_strtond(PATH, NULL);

if (node == -1 && fd > 0 && errno == ENOENT)

node = ND_LOCAL_NODE;

// по адресным данным, полученным ранее по read, создаем

// канал для прямого обмена сообщениями с тем же процессом

int coid = ConnectAttach(node, data.pid, data.chid, _NTO_SIDE_CHANNEL, 0);

if (coid < 0) exit("connect to message channel");

// динамически готовим код команды devctl:

unsigned int DCTL = (blk << 16) + DCMD_SRR;

cout << " . . . . . waiting ^C . . . . . " << flush;

// устанавливается реакция на пользовательский ^C

signal(SIGINT, trap);

uint64_t num = 0;

uint8_t *bufin = new uint8_t[blk], *bufou = new uint8_t[blk];

uint64_t tim = ClockCycles;

//
в зависимости от выбранного механизма передаем с его помощью данные

if (lowlvl)

while (true) {

if (MsgSend(coid, bufou, blk, bufin, blk) == -1)

exit("exchange data with channel");

num++;

if (!conti) break;

}

else {

while (true) {

if (devctl(fd, DCTL, bufou, blk, NULL) != EOK)

exit("DEVCTL error");

num++;

if (!conti) break;

}

}

tim = ClockCycles - tim;

cout << '\r' << (lowlvl ? "message exchange:" : "manager exchange:") <<

" number = " << num << "; stream = "

<< (double)num * blk / ((double)tim / (double)cps) / 1E6 * 8 <<

" Mbit/sec" << endl;

ConnectDetach(coid);

close(fd);

delete [] bufin;

delete [] bufou;

return EXIT_SUCCESS;

}

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

# clr -b1

SRR repeater: vers. 1.03

server path: /dev/srr, block size = 1 bytes

CPU speed [c.p.s.]: client = 534639500, server = 534639500

message exchange: number = 906400; stream = 1.54088 Mbit/sec

# clr -b1 -d

SRR repeater: vers. 1.03

server path: /dev/srr, block size = 1

bytes CPU speed [c.p.s.]: client = 534639500, server = 534639500

manager exchange, number = 335725; stream = 0.617311 Mbit/sec

# clr -b10

SRR repeater: vers. 1.03

server path: /dev/srr, block size = 10 bytes

CPU speed [c.p.s.]: client = 534639500, server = 534639500

message exchange: number = 1119211; stream = 15.0758 Mbit/sec

# clr -bl0 -d

SRR repeater: vers. 1.03

server path: /dev/srr, block size = 10 bytes

Поделиться с друзьями: