#include "proc.h" #include #include #define SQR(n) (n) * (n) #define FILDES_MATRIX_SIZE(n) SQR(n) #define READ_FILDES_I read_fildes[from * n + to] #define WRITE_FILDES_I write_fildes[to * n + from] static int pipes_matrix_init(FILE *log, size_t n, int *read_fildes, int *write_fildes) { int fildes[2]; for (size_t from = 0; from < n; ++from) { for (size_t to = 0; to < n; ++to) { if (from == to) continue; if (pipe(fildes)) { perror("opening pipes"); return 1; } fprintf(log, "PIPES %d and %d are paired\n", fildes[0], fildes[1]); fcntl(fildes[0], F_SETFL, O_NONBLOCK); fcntl(fildes[1], F_SETFL, O_NONBLOCK); READ_FILDES_I = fildes[0]; WRITE_FILDES_I = fildes[1]; } } return 0; } static int pipes_matrix_extract_fildes(FILE *log, size_t n, int *read_fildes, int *write_fildes, size_t i, int *read_fildes_row, int *write_fildes_row) { for (size_t from = 0; from < n; ++from) { for (size_t to = 0; to < n; ++to) { if (from == to) { continue; } if (to == i) { read_fildes_row[from] = READ_FILDES_I; } else { if (close(READ_FILDES_I)) { perror("closing read fildes"); return 1; } else { fprintf(log, "CLOSING: %zu:" "read form %zu to %zu: %d\n", i, from, to, READ_FILDES_I); } } if (from == i) { write_fildes_row[to] = WRITE_FILDES_I; } else { if (close(WRITE_FILDES_I)) { perror("closing write fildes"); return 1; } else { fprintf(log, "CLOSING: %zu:" "write from %zu to %zu: %d\n", i, from, to, WRITE_FILDES_I); } } } } write_fildes_row[i] = 1337; read_fildes_row[i] = 1488; return 0; } int await_all(Process *me, int16_t type) { for (uint8_t i = 1; i < me->fildes_num; ++i) { if (i == me->id) continue; Message msg; if (receive(me, i, &msg)) { fprintf(stderr, "Failed to receive: p = %d, i = %d\n", me->id, i); return 1; } if (msg.s_header.s_type != type) { fprintf(stderr, "HHH:((( \n"); } } return 0; } int proc_init(uint8_t n, Process *proc, FILE *log) { int read_fildes[FILDES_MATRIX_SIZE(n)]; int write_fildes[FILDES_MATRIX_SIZE(n)]; pipes_matrix_init(log, n, read_fildes, write_fildes); proc->id = PARENT_ID; proc->fildes_num = n; for (uint8_t i = 1; i < n; ++i) { pid_t pid = fork(); if (pid == 0) { proc->id = i; break; } } pipes_matrix_extract_fildes(log, n, read_fildes, write_fildes, proc->id, proc->read_fildes, proc->write_fildes); return 0; } void proc_destruct(Process *proc) { for (uint8_t i = 0; i < proc->fildes_num; ++i) { if (i != proc->id) { close(proc->read_fildes[i]); close(proc->write_fildes[i]); } } }