<html><head></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space; "><meta charset="utf-8"><span class="Apple-style-span" style="font-family: verdana; color: rgb(255, 255, 255); font-size: 12px; "><font class="Apple-style-span" color="#010101">Estoy haciendo una prueba para sincronizar 2 hilos (pthreads). Lo que ando buscando es crear una barrera en ambos hilos para que a partir de allí ambos hilos se ejecuten al mismo tiempo.<br><br>EL problema es que no entiendo que falla.<br></font><span style="text-decoration: underline; "><font class="Apple-style-span" color="#010101">Programa Principal.</font></span><font class="Apple-style-span" color="#010101"><br></font><div class="codeheader" style="text-decoration: none; font-style: normal; font-weight: bold; font-size: x-small; "><font class="Apple-style-span" color="#010101">Código</font></div><pre class="geshi" style="color: rgb(255, 255, 255); background-color: rgb(51, 51, 51); border-top-width: 1px; border-right-width: 1px; border-bottom-width: 1px; border-left-width: 1px; border-top-style: solid; border-right-style: solid; border-bottom-style: solid; border-left-style: solid; border-top-color: black; border-right-color: black; border-bottom-color: black; border-left-color: black; margin-top: 1px; margin-right: 1px; margin-bottom: 1px; margin-left: 1px; padding-top: 1px; padding-right: 1px; padding-bottom: 1px; padding-left: 1px; font-size: small; position: static; z-index: auto; "><span style="color: rgb(51, 153, 0); ">#include <pthread.h></span><br><span style="color: rgb(51, 153, 0); ">#include <stdio.h></span><br><span style="color: rgb(51, 153, 0); ">#include "procedimientos.h"</span><br><span style="color: rgb(51, 153, 0); ">#include "barrier.h"</span><br> <br><span style="color: rgb(0, 0, 255); ">int</span> contador = <span style="color: rgb(0, 0, 221); ">0</span>;<br><span style="color: rgb(0, 0, 255); ">struct</span> thdata<br><span style="color: rgb(0, 0, 0); ">{</span><br>            <span style="color: rgb(0, 0, 255); ">int</span> thread_no<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">2</span><span style="color: rgb(0, 0, 0); ">]</span>; <br>            <span style="color: rgb(0, 0, 255); ">char</span> message<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">100</span><span style="color: rgb(0, 0, 0); ">]</span>;<br>            barrier_t *barrier;<br><span style="color: rgb(0, 0, 0); ">}</span>;<br> <br><span style="color: rgb(0, 0, 255); ">int</span> main<span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 0); ">)</span><br><span style="color: rgb(0, 0, 0); ">{</span><br> <span style="color: rgb(255, 0, 0); font-style: italic; ">/* Identificador del thread hijo */</span><br>    pthread_t idHilo<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">2</span><span style="color: rgb(0, 0, 0); ">]</span>;<br>     thdata shared_data;         <br>      pthread_attr_t attr;<br>  barrier_t barrier;<br> <br>    <span style="color: rgb(255, 0, 0); font-style: italic; ">/* error devuelto por la función de creación del thread */</span><br>     <span style="color: rgb(0, 0, 255); ">int</span> error<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">2</span><span style="color: rgb(0, 0, 0); ">]</span>;<br> <br> shared_data.<span style="color: rgb(0, 238, 255); ">thread_no</span><span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">0</span><span style="color: rgb(0, 0, 0); ">]</span> = <span style="color: rgb(0, 0, 221); ">1</span>;<br>    shared_data.<span style="color: rgb(0, 238, 255); ">thread_no</span><span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">1</span><span style="color: rgb(0, 0, 0); ">]</span> = <span style="color: rgb(0, 0, 221); ">2</span>;<br>    shared_data.<span style="color: rgb(0, 238, 255); ">barrier</span>= &barrier;<br> <br>       barrier_init<span style="color: rgb(0, 0, 0); ">(</span>&barrier, <span style="color: rgb(0, 0, 221); ">3</span><span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>   pthread_attr_init<span style="color: rgb(0, 0, 0); ">(</span>&attr<span style="color: rgb(0, 0, 0); ">)</span>;<br>       pthread_attr_setdetachstate<span style="color: rgb(0, 0, 0); ">(</span>&attr, PTHREAD_CREATE_JOINABLE<span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>    error<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">0</span><span style="color: rgb(0, 0, 0); ">]</span> = pthread_create <span style="color: rgb(0, 0, 0); ">(</span>&idHilo<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">0</span><span style="color: rgb(0, 0, 0); ">]</span>, <span style="color: rgb(0, 0, 255); ">NULL</span>, funcionThread1, <span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 255); ">void</span> *<span style="color: rgb(0, 0, 0); ">)</span> &shared_data<span style="color: rgb(0, 0, 0); ">)</span>;<br>      error<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">1</span><span style="color: rgb(0, 0, 0); ">]</span> = pthread_create <span style="color: rgb(0, 0, 0); ">(</span>&idHilo<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">1</span><span style="color: rgb(0, 0, 0); ">]</span>, <span style="color: rgb(0, 0, 255); ">NULL</span>, funcionThread2, <span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 255); ">void</span> *<span style="color: rgb(0, 0, 0); ">)</span> &shared_data<span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>      <span style="color: rgb(255, 0, 0); font-style: italic; ">/* Comprobamos el error al arrancar el thread */</span><br>       <span style="color: rgb(0, 0, 255); ">if</span> <span style="color: rgb(0, 0, 0); ">(</span>error<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">0</span><span style="color: rgb(0, 0, 0); ">]</span> != <span style="color: rgb(0, 0, 221); ">0</span><span style="color: rgb(0, 0, 0); ">)</span><br>       <span style="color: rgb(0, 0, 0); ">{</span><br>            <span style="color: rgb(0, 0, 221); ">printf</span><span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(102, 102, 102); ">"No puedo crear thread"</span><span style="color: rgb(0, 0, 0); ">)</span>;<br>                <span style="color: rgb(0, 0, 255); ">return</span> <span style="color: rgb(0, 0, 221); ">-1</span>;<br>      <span style="color: rgb(0, 0, 0); ">}</span><br> <br>    <span style="color: rgb(255, 0, 0); font-style: italic; ">/* Bucle infinito para incrementar el contador y mostrarlo en pantalla */</span><br>      pthread_attr_destroy<span style="color: rgb(0, 0, 0); ">(</span>&attr<span style="color: rgb(0, 0, 0); ">)</span>; <br>   barrier_cross<span style="color: rgb(0, 0, 0); ">(</span>&barrier<span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>        pthread_join<span style="color: rgb(0, 0, 0); ">(</span>idHilo<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">0</span><span style="color: rgb(0, 0, 0); ">]</span>, <span style="color: rgb(0, 0, 255); ">NULL</span><span style="color: rgb(0, 0, 0); ">)</span>;<br>      pthread_join<span style="color: rgb(0, 0, 0); ">(</span>idHilo<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">1</span><span style="color: rgb(0, 0, 0); ">]</span>, <span style="color: rgb(0, 0, 255); ">NULL</span><span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>      <span style="color: rgb(0, 0, 255); ">return</span> <span style="color: rgb(0, 0, 221); ">0</span>;<br><span style="color: rgb(0, 0, 0); ">}</span></pre><font class="Apple-style-span" color="#010101"><br>- Diseño para la barrera<br></font><span style="text-decoration: underline; "><font class="Apple-style-span" color="#010101">Estructura barrera</font></span><font class="Apple-style-span" color="#010101"><br></font><div class="codeheader" style="text-decoration: none; font-style: normal; font-weight: bold; font-size: x-small; "><font class="Apple-style-span" color="#010101">Código</font></div><pre class="geshi" style="color: rgb(255, 255, 255); background-color: rgb(51, 51, 51); border-top-width: 1px; border-right-width: 1px; border-bottom-width: 1px; border-left-width: 1px; border-top-style: solid; border-right-style: solid; border-bottom-style: solid; border-left-style: solid; border-top-color: black; border-right-color: black; border-bottom-color: black; border-left-color: black; margin-top: 1px; margin-right: 1px; margin-bottom: 1px; margin-left: 1px; padding-top: 1px; padding-right: 1px; padding-bottom: 1px; padding-left: 1px; font-size: small; "><span style="color: rgb(0, 0, 255); ">typedef</span> <span style="color: rgb(0, 0, 255); ">struct</span> barrier <br><span style="color: rgb(0, 0, 0); ">{</span><br>  pthread_cond_t complete;<br>  pthread_mutex_t mutex;<br>  <span style="color: rgb(0, 0, 255); ">int</span> count;<br>  <span style="color: rgb(0, 0, 255); ">int</span> crossing;<br><span style="color: rgb(0, 0, 0); ">}</span> barrier_t;</pre><span style="text-decoration: underline; "><font class="Apple-style-span" color="#000000">Funciones</font></span><font class="Apple-style-span" color="#000000"><br></font><div class="codeheader" style="text-decoration: none; font-style: normal; font-weight: bold; font-size: x-small; "><font class="Apple-style-span" color="#000000">Código</font></div><pre class="geshi" style="color: rgb(255, 255, 255); background-color: rgb(51, 51, 51); border-top-width: 1px; border-right-width: 1px; border-bottom-width: 1px; border-left-width: 1px; border-top-style: solid; border-right-style: solid; border-bottom-style: solid; border-left-style: solid; border-top-color: black; border-right-color: black; border-bottom-color: black; border-left-color: black; margin-top: 1px; margin-right: 1px; margin-bottom: 1px; margin-left: 1px; padding-top: 1px; padding-right: 1px; padding-bottom: 1px; padding-left: 1px; font-size: small; position: static; z-index: auto; "> <span style="color: rgb(255, 0, 0); font-style: italic; ">/* ################################################################### *<br> * BARRIER<br> * ################################################################### */</span><br><span style="color: rgb(51, 153, 0); ">#include <pthread.h></span><br><span style="color: rgb(51, 153, 0); ">#include "barrier.h"</span><br> <br><span style="color: rgb(0, 0, 255); ">void</span> barrier_init<span style="color: rgb(0, 0, 0); ">(</span>barrier_t *b, <span style="color: rgb(0, 0, 255); ">int</span> n<span style="color: rgb(0, 0, 0); ">)</span><br><span style="color: rgb(0, 0, 0); ">{</span><br>  pthread_cond_init<span style="color: rgb(0, 0, 0); ">(</span>&b->complete, <span style="color: rgb(0, 0, 255); ">NULL</span><span style="color: rgb(0, 0, 0); ">)</span>;<br>  pthread_mutex_init<span style="color: rgb(0, 0, 0); ">(</span>&b->mutex, <span style="color: rgb(0, 0, 255); ">NULL</span><span style="color: rgb(0, 0, 0); ">)</span>;<br>  b->count = n;<br>  b->crossing = <span style="color: rgb(0, 0, 221); ">0</span>;<br><span style="color: rgb(0, 0, 0); ">}</span><br> <br><span style="color: rgb(0, 0, 255); ">void</span> barrier_cross<span style="color: rgb(0, 0, 0); ">(</span>barrier_t *b<span style="color: rgb(0, 0, 0); ">)</span><br><span style="color: rgb(0, 0, 0); ">{</span><br>  pthread_mutex_lock<span style="color: rgb(0, 0, 0); ">(</span>&b->mutex<span style="color: rgb(0, 0, 0); ">)</span>;<br>    b->crossing++;<br>  <br>  <span style="color: rgb(0, 0, 255); ">if</span> <span style="color: rgb(0, 0, 0); ">(</span>b->crossing < b->count<span style="color: rgb(0, 0, 0); ">)</span> <span style="color: rgb(0, 0, 0); ">{</span><br>    pthread_cond_wait<span style="color: rgb(0, 0, 0); ">(</span>&b->complete, &b->mutex<span style="color: rgb(0, 0, 0); ">)</span>;<br>  <span style="color: rgb(0, 0, 0); ">}</span> <span style="color: rgb(0, 0, 255); ">else</span> <span style="color: rgb(0, 0, 0); ">{</span><br>    pthread_cond_broadcast<span style="color: rgb(0, 0, 0); ">(</span>&b->complete<span style="color: rgb(0, 0, 0); ">)</span>;<br>    b->crossing = <span style="color: rgb(0, 0, 221); ">0</span>;<br>  <span style="color: rgb(0, 0, 0); ">}</span><br>  pthread_mutex_unlock<span style="color: rgb(0, 0, 0); ">(</span>&b->mutex<span style="color: rgb(0, 0, 0); ">)</span>;<br><span style="color: rgb(0, 0, 0); ">}</span></pre><font class="Apple-style-span" color="#000000"><br>Y finalmente funciones que ejecutan los hilos.<br><br></font><span style="text-decoration: underline; "><font class="Apple-style-span" color="#000000">Funciones</font></span><font class="Apple-style-span" color="#000000"><br><br></font><div class="codeheader" style="text-decoration: none; font-style: normal; font-weight: bold; font-size: x-small; "><font class="Apple-style-span" color="#000000">Código</font></div><pre class="geshi" style="color: rgb(255, 255, 255); background-color: rgb(51, 51, 51); border-top-width: 1px; border-right-width: 1px; border-bottom-width: 1px; border-left-width: 1px; border-top-style: solid; border-right-style: solid; border-bottom-style: solid; border-left-style: solid; border-top-color: black; border-right-color: black; border-bottom-color: black; border-left-color: black; margin-top: 1px; margin-right: 1px; margin-bottom: 1px; margin-left: 1px; padding-top: 1px; padding-right: 1px; padding-bottom: 1px; padding-left: 1px; font-size: small; position: static; z-index: auto; "><span style="color: rgb(51, 153, 0); ">#include <pthread.h> </span><br><span style="color: rgb(51, 153, 0); ">#include "procedimientos.h"</span><br><span style="color: rgb(51, 153, 0); ">#include "barrier.h"</span><br><span style="color: rgb(51, 153, 0); ">#include <unistd.h>     </span><br><span style="color: rgb(51, 153, 0); ">#include <sys/types.h>   </span><br><span style="color: rgb(51, 153, 0); ">#include <errno.h>      </span><br><span style="color: rgb(51, 153, 0); ">#include <stdio.h>      </span><br><span style="color: rgb(51, 153, 0); ">#include <stdlib.h>     </span><br><span style="color: rgb(51, 153, 0); ">#include <string.h>    </span><br><span style="color: rgb(51, 153, 0); ">#include <assert.h></span><br><span style="color: rgb(51, 153, 0); ">#include <getopt.h></span><br><span style="color: rgb(51, 153, 0); ">#include <limits.h></span><br> <br><span style="color: rgb(0, 0, 255); ">struct</span> thdata<br><span style="color: rgb(0, 0, 0); ">{</span><br>              <span style="color: rgb(0, 0, 255); ">int</span> thread_no<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">2</span><span style="color: rgb(0, 0, 0); ">]</span>; <br>            <span style="color: rgb(0, 0, 255); ">char</span> mensaje<span style="color: rgb(0, 0, 0); ">[</span><span style="color: rgb(0, 0, 221); ">100</span><span style="color: rgb(0, 0, 0); ">]</span>;<br>            barrier_t *barrier;<br><span style="color: rgb(0, 0, 0); ">}</span>;<br> <br><span style="color: rgb(0, 0, 255); ">void</span> *funcionThread1 <span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 255); ">void</span> *ptr<span style="color: rgb(0, 0, 0); ">)</span><br><span style="color: rgb(0, 0, 0); ">{</span><br>        thdata *data;            <br>    data = <span style="color: rgb(0, 0, 0); ">(</span>thdata *<span style="color: rgb(0, 0, 0); ">)</span>ptr; <span style="color: rgb(255, 0, 0); ">// Datos que mandamos al hilo</span><br> <br>    <span style="color: rgb(0, 0, 221); ">printf</span><span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(102, 102, 102); ">"hilo 1"</span><span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>    sleep<span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 221); ">3</span><span style="color: rgb(0, 0, 0); ">)</span>;<br>  barrier_cross<span style="color: rgb(0, 0, 0); ">(</span>data->barrier<span style="color: rgb(0, 0, 0); ">)</span>; <span style="color: rgb(255, 0, 0); ">// Barrera usada para sincronizacion</span><br>    <span style="color: rgb(0, 0, 221); ">printf</span><span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(102, 102, 102); ">"Arriba hilo 1"</span><span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>        pthread_exit<span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 221); ">0</span><span style="color: rgb(0, 0, 0); ">)</span>; <br><span style="color: rgb(0, 0, 0); ">}</span><br><span style="color: rgb(0, 0, 255); ">void</span> *funcionThread2 <span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 255); ">void</span> *ptr<span style="color: rgb(0, 0, 0); ">)</span><br><span style="color: rgb(0, 0, 0); ">{</span><br>      thdata *data;            <br>    data = <span style="color: rgb(0, 0, 0); ">(</span>thdata *<span style="color: rgb(0, 0, 0); ">)</span>ptr; <br> <br>    <span style="color: rgb(0, 0, 221); ">printf</span><span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(102, 102, 102); ">"hilo 2"</span><span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>        barrier_cross<span style="color: rgb(0, 0, 0); ">(</span>data->barrier<span style="color: rgb(0, 0, 0); ">)</span>;<br>        sleep<span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 221); ">1</span><span style="color: rgb(0, 0, 0); ">)</span>;<br>        <span style="color: rgb(0, 0, 221); ">printf</span><span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(102, 102, 102); ">"Despierta hilo 2"</span><span style="color: rgb(0, 0, 0); ">)</span>;<br> <br>     pthread_exit<span style="color: rgb(0, 0, 0); ">(</span><span style="color: rgb(0, 0, 221); ">0</span><span style="color: rgb(0, 0, 0); ">)</span>; <br><span style="color: rgb(0, 0, 0); ">}</span></pre><font class="Apple-style-span" color="#000000"><br>En este último fichero sobran librerías incluidas pero no recordaba que librería contiene la función sleep y meti unas cuantas que tenía en otro programa.<br><br>No incluye los ficheros de cabecera porque son "triviales".<br><br></font><span style="text-decoration: underline; "><b><font class="Apple-style-span" color="#000000">Solución obtenida con ese código.</font></b></span><font class="Apple-style-span" color="#000000"><br><br>Se produce el sleep durante 3 segundos  y psoteriormente se muestra todo seguido por pantalla.<br><br></font><b><span style="text-decoration: underline; "><font class="Apple-style-span" color="#000000">Solucion deseada:</font></span></b><font class="Apple-style-span" color="#000000"><br><br>Salidas en pantalla:<br>hilo 1<br>hilo2<br>-- nada durante 3 segundos<br>arriba hilo 1<br>--espera un segundo - diferencial<br>Depierta hilo 2<br><br><br>El problema creo que está en las funciones del barrier pero  no consigo hacerlo funcionar bien.<br><br>Gracias de antemano, cualquier ayuda será bienvenida.</font></span></body></html>