From: Leandro Lucarella Date: Tue, 25 Apr 2006 06:58:29 +0000 (+0000) Subject: Finalizado 2.3.2. X-Git-Tag: svn_import~88 X-Git-Url: https://git.llucax.com/z.facultad/75.74/practicos.git/commitdiff_plain/dfb352c0c066ff99c29291cf5d6d4a41bf005fbf Finalizado 2.3.2. --- diff --git a/practicas/practica2/P02e2321.cpp b/practicas/practica2/P02e2321.cpp new file mode 100644 index 0000000..aa1e773 --- /dev/null +++ b/practicas/practica2/P02e2321.cpp @@ -0,0 +1,106 @@ +/** + * Leandro Lucarella (77891) + * + * Ejercicio 2.3.2. Implementa productor-consumidor con pipes, con 3 + * productores que producen 1/3 cada uno y 2 consumidores que consumen todo. + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +using std::cerr; +using std::cout; +using std::endl; +using std::ostringstream; + +// Nombre base del pipe +#define PIPE_BASE "/tmp/77891_P02e2321_" + +/// Nombres de los procesos +enum proc_t { PRODUCTOR1, PRODUCTOR2, PRODUCTOR3, CONSUMIDOR1, CONSUMIDOR2 }; + +#define TEST(v) do { if ((v) == -1) { perror("P02e2221"); exit(200); } } while (0) + +void producir(int pipes[], int parte) +{ + int val = rand(); + TEST(write(pipes[0], &val, sizeof(int))); + TEST(write(pipes[1], &val, sizeof(int))); + cout << "Producida parte " << parte << ": " << (int)val << endl; +} + +void consumir(int pipes[], int consumidor) +{ + int completo[3]; + TEST(read(pipes[0], &completo[0], sizeof(int))); + TEST(read(pipes[1], &completo[1], sizeof(int))); + TEST(read(pipes[2], &completo[2], sizeof(int))); + cout << "Consumidor " << consumidor << " consumió: " << completo[0] << "," + << completo[1] << "," << completo[2] << endl; +} + +int main(int argc, char *argv[]) +{ + srand(getpid()); + + if (argc < 2) + { + cerr << "Faltan parametros: " << argv[0] << " N [max_iter]\n"; + return 1; + } + proc_t proc = (proc_t) atoi(argv[1]); + + // Maxima cantidad de iteraciones (puede venir por parametro) + int max_iter = 10; + if (argc > 2) + max_iter = atoi(argv[2]); + + // Abro pipes según corresponda + int pipes[3]; + if (proc <= PRODUCTOR3) // Productores + { + ostringstream oss; + oss << PIPE_BASE << proc << "_0"; + pipes[0] = open(oss.str().c_str(), O_WRONLY); + TEST(pipes[0]); + oss.str(""); + oss << PIPE_BASE << proc << "_1"; + pipes[1] = open(oss.str().c_str(), O_WRONLY); + TEST(pipes[1]); + } + else // Consumidores + { + int consumidor = proc-3; + ostringstream oss; + oss << PIPE_BASE << "0_" << consumidor; + pipes[0] = open(oss.str().c_str(), O_RDONLY); + TEST(pipes[0]); + oss.str(""); + oss << PIPE_BASE << "1_" << consumidor; + pipes[1] = open(oss.str().c_str(), O_RDONLY); + TEST(pipes[1]); + oss.str(""); + oss << PIPE_BASE << "2_" << consumidor; + pipes[2] = open(oss.str().c_str(), O_RDONLY); + TEST(pipes[2]); + } + + for (int i = 0; i < max_iter; ++i) + { + if (proc <= PRODUCTOR3) + producir(pipes, proc); + else + consumir(pipes, proc-3); + sched_yield(); + } + + return 0; +} + +// vim: set et sw=4 sts=4 : diff --git a/practicas/practica2/P02e2321.sh b/practicas/practica2/P02e2321.sh new file mode 100755 index 0000000..4cd4477 --- /dev/null +++ b/practicas/practica2/P02e2321.sh @@ -0,0 +1,42 @@ +#!/bin/sh + +FIFO_BASE=/tmp/77891_P02e2321_ + +# Creo named pipes +for i in 0 1 2; +do + for j in _0 _1; + do + mkfifo $FIFO_BASE$i$j + done +done + +# Lanzo procesos +# Productores +./P02e2321 0 $1 & +p0=$! +./P02e2321 1 $1 & +p1=$! +./P02e2321 2 $1 & +p2=$! +# Consumidores +./P02e2321 3 $1 & +p3=$! +./P02e2321 4 $1 & +p4=$! + +# Espero que terminen +wait $p0 +wait $p01 +wait $p02 +wait $p03 +wait $p04 + +# Limpio pipes +for i in 0 1 2; +do + for j in _0 _1; + do + rm $FIFO_BASE$i$j + done +done diff --git a/practicas/practica2/README b/practicas/practica2/README index cf3cc35..36fa2e8 100644 --- a/practicas/practica2/README +++ b/practicas/practica2/README @@ -88,3 +88,15 @@ productor, 1 es consumidor) Se provee un script lanzador: ./P02e2311.sh (recibe un parámetro opcional con la cantidad de iteraciones) +P02e2321 +======== +Ejercicio 2.3.2. Productor-consumidor usando pipes pero con 3 productores +que producen parcialmente y 2 consumidores que consumen todo. Debe correr +primero el primer productor porque inicializa las estructuras compartidas. +Por ejemplo: +$ ./P02e2321 0 & ./P02e2321 1 & ./P02e2321 2 & ./P02e2321 3 & ./P02e2321 4 & +(el proceso 0 a 2 son productores, el 3 y 4 consumidores). + +Se provee un script lanzador: ./P02e2321.sh +(recibe un parámetro opcional con la cantidad de iteraciones) +