diff options
author | Anton Luka Šijanec <anton@sijanec.eu> | 2023-01-31 21:55:33 +0100 |
---|---|---|
committer | Anton Luka Šijanec <anton@sijanec.eu> | 2023-01-31 21:55:33 +0100 |
commit | 258c9ef71e45c8e6dff9ee708ce51681dc90ecf9 (patch) | |
tree | 78a99cc9919ee1a9c8d586c2ebbe168dfb5193d2 /main.c | |
download | ebs-258c9ef71e45c8e6dff9ee708ce51681dc90ecf9.tar ebs-258c9ef71e45c8e6dff9ee708ce51681dc90ecf9.tar.gz ebs-258c9ef71e45c8e6dff9ee708ce51681dc90ecf9.tar.bz2 ebs-258c9ef71e45c8e6dff9ee708ce51681dc90ecf9.tar.lz ebs-258c9ef71e45c8e6dff9ee708ce51681dc90ecf9.tar.xz ebs-258c9ef71e45c8e6dff9ee708ce51681dc90ecf9.tar.zst ebs-258c9ef71e45c8e6dff9ee708ce51681dc90ecf9.zip |
Diffstat (limited to 'main.c')
-rw-r--r-- | main.c | 137 |
1 files changed, 137 insertions, 0 deletions
@@ -0,0 +1,137 @@ +#include <ebs.c> +#include <sys/mman.h> +#include <error.h> +#include <errno.h> +#include <poll.h> +#include <sys/stat.h> +#include <fcntl.h> +#include <unistd.h> +#include <pthread.h> +#include <stdatomic.h> +#include <time.h> +#define S0(x) ((x) ? (x) : "") +static unsigned long long micros (void) { + struct timespec tp; + clock_gettime(CLOCK_MONOTONIC, &tp); + return tp.tv_sec*1000000+tp.tv_nsec/1000; +} +struct nit { + atomic_int možen; + int pipe; +}; +static void * pričakuj (void * ptr) { + struct nit * nit = (struct nit *) ptr; + struct pollfd pollfd[] = { + { + .fd = STDIN_FILENO, + .events = POLLIN + }, + { + .fd = nit->pipe, + .events = POLLIN + } + }; + while (1) { + int ret = poll(pollfd, 2, -1); + if (ret == -1) { + error_at_line(0, errno, __FILE__, __LINE__, "poll"); + nit->možen = 2; + return NULL; + } + if (pollfd[1].revents & POLLIN) + return NULL; + if (pollfd[0].revents & POLLIN) + nit->možen = 1; + } +} +int main (int argc, char ** argv) { + if (argc != 1+1) + error_at_line(1, 0, __FILE__, __LINE__, "%s program.ebs", S0(argv[0])); + int r = 0; + struct ebs ebs; + ebs_init(&ebs); + pthread_t vhod; + int pipefd[2]; + int threadret = -1; + int pfd = -1; + if (pipe(pipefd) == -1) + error_at_line(2, errno, __FILE__, __LINE__, "pipe"); + struct nit nit = { + .možen = 0, + .pipe = pipefd[0] + }; + if ((threadret = pthread_create(&vhod, NULL, pričakuj, &nit))) { + error_at_line(0, threadret, __FILE__, __LINE__, "pthread_create"); + r = 3; + goto r; + } + if ((pfd = open(argv[1], O_RDONLY | O_CLOEXEC)) == -1) { + error_at_line(0, errno, __FILE__, __LINE__, "open(%s)", argv[1]); + r = 4; + goto r; + } + struct stat statbuf; + if (fstat(pfd, &statbuf) == -1) { + error_at_line(0, errno, __FILE__, __LINE__, "fstat(pfd, &statbuf)"); + r = 5; + goto r; + } + if (!(ebs.pm_velikost = statbuf.st_size)) { + error_at_line(0, errno, __FILE__, __LINE__, "!(ebs.pm_velikost = statbuf.st_size)"); + r = 6; + goto r; + } + if (!(ebs.pm = mmap(NULL, ebs.pm_velikost, PROT_READ, MAP_SHARED, pfd, 0))) { + error_at_line(0, errno, __FILE__, __LINE__, "!mmap(NULL, ebs.pm_velikost, PROT_READ, MAP_SHARED, pfd, 0)"); + r = 7; + goto r; + } + unsigned long long int začetek = micros(); + unsigned long long inštrukcij = 0; + while (ebs_delo(&ebs) == nadaljuj) { + inštrukcij++; + if (!(inštrukcij % 100000000)) + fprintf(stderr, "hitrost izvajanja: %llu op/us (MHz)\r", inštrukcij/(micros()-začetek)); + switch (nit.možen) { + case 0: // ni vhoda, ni napake + break; + case 1: // imamo vsaj en bajt + if (ebs.vhod_medp_indeks > 7) { + char buf; + int got = read(STDIN_FILENO, &buf, 1); + if (got == -1) { + error_at_line(0, errno, __FILE__, __LINE__, "read"); + r = 8; + goto r; + } + ebs.vhod_medp_indeks = 0; + ebs.vhod_medp = buf; + nit.možen = 0; + } + break; + case 2: // napaka + error_at_line(0, 0, __FILE__, __LINE__, "napaka v vhodni niti"); + r = 8; + goto r; + break; + } + } + fprintf(stderr, "konec izvajanja"); + r: + if (!threadret) { + if (write(pipefd[1], "", 1) == -1) + error_at_line(0, errno, __FILE__, __LINE__, "write"); + threadret = pthread_join(vhod, NULL); + if (threadret) + error_at_line(0, threadret, __FILE__, __LINE__, "pthread_join"); + } + if (close(pipefd[0]) == -1) + error_at_line(0, errno, __FILE__, __LINE__, "close(pipefd[0])"); + if (close(pipefd[1]) == -1) + error_at_line(0, errno, __FILE__, __LINE__, "close(pipefd[1])"); + if (ebs.pm && munmap(ebs.pm, ebs.pm_velikost) == -1) + error_at_line(0, errno, __FILE__, __LINE__, "munmap(ebs.pm, ebs.pm_velikost)"); + close(pfd); + pfd = -1; + return r; +} |