elhacker.net cabecera Bienvenido(a), Visitante. Por favor Ingresar o Registrarse
¿Perdiste tu email de activación?.

 

 


Tema destacado: Sigue las noticias más importantes de seguridad informática en el Twitter! de elhacker.NET


+  Foro de elhacker.net
|-+  Programación
| |-+  Programación C/C++ (Moderadores: Eternal Idol, Littlehorse, K-YreX)
| | |-+  Sincronización de procesos
0 Usuarios y 1 Visitante están viendo este tema.
Páginas: [1] Ir Abajo Respuesta Imprimir
Autor Tema: Sincronización de procesos  (Leído 5,141 veces)
prosebas

Desconectado Desconectado

Mensajes: 17


Ver Perfil
Sincronización de procesos
« en: 24 Mayo 2021, 04:11 am »

Código
  1. static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
  2. static pthread_mutex_t mutex1 = PTHREAD_MUTEX_INITIALIZER;
  3.  

Routinas
Código
  1. void *routineRead(void *val)
  2. {
  3.    pthread_mutex_lock(&mutex);
  4.    int fg = 0, fd;
  5.    void *buf = malloc(MAX_SIZE * 2);
  6.    do
  7.    {
  8.        fd = open(val, O_RDONLY);
  9.        if (fd == -1)
  10.        {
  11.            perror("pipe");
  12.            printf(" Se volvera a intentar despues\n");
  13.            sleep(5);
  14.        }
  15.        else
  16.            fg = 1;
  17.    } while (fg == 0);
  18.    read(fd, buf, MAX_SIZE * 2);
  19.    close(fd);
  20.    pthread_mutex_unlock(&mutex);
  21.    return buf;
  22. }
  23. void *routineWrite(void *val)
  24. {
  25.    pthread_mutex_lock(&mutex1);
  26.    int fg = 0, fd;
  27.    int *time = malloc(sizeof(int));
  28.    *time = bh.current_time;
  29.    do
  30.    {
  31.        fd = open(val, O_WRONLY);
  32.        if (fd == -1)
  33.        {
  34.            perror("pipe");
  35.            printf(" Se volvera a intentar despues\n");
  36.            sleep(5);
  37.        }
  38.        else
  39.            fg = 1;
  40.    } while (fg == 0);
  41.    write(fd, time, MAX_SIZE);
  42.    close(fd);
  43.    pthread_mutex_unlock(&mutex1);
  44. }
  45.  

Mi proyecto consiste en conectar  dos procesos mediante pipes, un proceso es el controlador y el otro es agente. El controlador basicamente  se encarga de leer del pipe y enviar una respuesta, el punto es que estoy leyendo del pipe a través de un hilo, sin embargo,cada vez que se conecta un agente, el controlador lee el nombre del agente enviado por el agente y luego se crea un fifo que es el fd por donde se comunicaran ellos dos. Vale, el punto es que si llegan el agente1 y el agente2 al mismo tiempo no estoy seguro de lo que pasa pero creo que ambos entra a la sección critica y no me crea el fifo para cada agente sino  que la variable se concatena.

No supe montar la imagen aqui pero en el link pueden ver que es lo que pasa
https://ibb.co/JsgfTp5


Entonces no se  si me puedan ayudar a garantizar que si dos agente o mas se conectan a la vez atienda primero a uno y luego si siga con el otro.

Código
  1.    pthread_t p_read, p_write, p_time;
  2.    sem_init(&sem, 0, 1);
  3.    sem_init(&sem1, 0, 1);
  4.    clean_fifo(pipe);
  5.    int seconds = atoi(argv[6]);
  6.    pthread_create(&p_time, NULL, routineTime, &seconds);
  7.    do
  8.    {
  9.        int cont = 0;
  10.        //p_read get the agent name from the pipe
  11.        pthread_create(&p_read, NULL, routineRead, pipe);
  12.        pthread_join(p_read, (void **)&agent_name);
  13.        printf("Agente:%s\t", agent_name);
  14.        clean_fifo(agent_name);
  15.        //send current time
  16.        pthread_create(&p_write, NULL, routineWrite, pipe);
  17.        pthread_join(p_write, NULL);
  18.        printf("pipe: %s\n", agent_name);
  19.        //Read all the requests by an agent
  20.        do
  21.        {
  22.            pthread_create(&p_read, NULL, routineRead, agent_name);
  23.            pthread_join(p_read, (void **)&data[cont].re);
  24.            if (data[cont].re->amount_people != 0)
  25.                answer_request(&tree, data[cont].re, &bh);
  26.            else
  27.                break;
  28.            write_pipe(fd, (struct Reserva *)data[cont].re, sizeof(Reserva), agent_name, O_WRONLY);
  29.            cont++;
  30.        } while (1);
  31.  
  32.    } while (1);
  33.  



« Última modificación: 24 Mayo 2021, 04:21 am por prosebas » En línea

RayR

Desconectado Desconectado

Mensajes: 243


Ver Perfil
Re: Sincronización de procesos
« Respuesta #1 en: 25 Mayo 2021, 01:10 am »

Ese código tiene toda la apariencia de haber sido copiado de algún lado. No lo hagas, o vas a tener muchos problemas para entender estos temas.

Tu programa no funciona como multihilo, ya que, si a cada create le sigue inmediatamente un join, estás forzando a que se ejecute de forma secuencial. De todas formas, si, como planteas en tu pregunta, quieres que el controlador atienda un agente a la vez, no tiene sentido querer usar hilos. Mejor llama directamente a routineRead y routineWrite.

Omitiste demasiado código, pero parece que dentro del segundo do while usas un pipe distinto por cada proceso, como debe ser. Sin embargo, parece que al principio (línea 11 del último código) el controlador abre un pipe predefinido mediante el cual todos los agentes le envían su nombre, que luego usará para crear fifos para comunicarse con cada proceso. El problema sería que más de un proceso puede escribir en el pipe predefinido antes de que el controlador lo lea, así que cuando finalmente éste lo lee, recibe varios  juntos. Primero, el hecho de que se muestren pegados por pantalla indica que no estás enviando cadenas completas (cerradas), lo cual puede causar problemas de memoria. Si en el agente tienes algo así:

Código
  1. write(fd, nombre_agente, strlen(nombre_agente));

cambia el último parámetro a strlen(nombre_agente) + 1, para que también se envíe el caracter nulo. Con esto estarás mandando cadenas correctas, pero todavía queda el problema original. La cuestión es que lo que hagan los procesos externos está, en general, fuera de tu control.

Quizás lo mejor sería usar otro mecanismo (no pipes) para ese intercambio original de información, los nombres de agentes y pipes. Pero si lo quieres/tienes que hacer con pipes, lo que necesitas es delimitar de alguna forma cada mensaje. Lo más sencillo es que cada mensaje enviado al pipe predefinido (el que usas al principio para enviar el nombre del agente) sea de un tamaño fijo. Por ejemplo:

Código
  1. #define TAM_BUFFER 64
  2.  
  3. char nombre_agente[TAM_BUFFER];
  4. ( ...)
  5. write(fd, nombre_agente, TAM_BUFFER);

y haces lo mismo con read. Con eso, siempre estarás leyendo exactamente un único nombre.


« Última modificación: 25 Mayo 2021, 01:15 am por RayR » En línea

Páginas: [1] Ir Arriba Respuesta Imprimir 

Ir a:  

Mensajes similares
Asunto Iniciado por Respuestas Vistas Último mensaje
Listar procesos y realizar cosas con los procesos
Programación Visual Basic
sebas369 2 3,399 Último mensaje 14 Julio 2006, 16:08 pm
por sebas369
ERROR! EN SINCRONIZACION DE PROCESOS
Programación C/C++
Odai 2 2,400 Último mensaje 2 Mayo 2013, 14:35 pm
por Odai
Ayuda con sincronización de procesos para MITM en C++
Programación C/C++
Kaxperday 3 3,678 Último mensaje 15 Julio 2015, 19:41 pm
por x64core
entender sincronizacion de procesos(semaforos,monitores) en c#
.NET (C#, VB.NET, ASP)
jhulyo 0 2,081 Último mensaje 15 Abril 2017, 00:10 am
por jhulyo
sincronización
Dudas Generales
inma55 3 3,248 Último mensaje 16 Diciembre 2019, 02:06 am
por Machacador
WAP2 - Aviso Legal - Powered by SMF 1.1.21 | SMF © 2006-2008, Simple Machines