Makar
Makar

Reputation: 21

Server receiving and showing string from client using signals SIGUSR1 and SIGUSR2 can't handle with big amount of symbols

I had a task from school in which I need to write a client that will send string using signals (only SIGUSR1 as 1 or SIGUSR2 as 0) to server, which then should display this string. The problem is that server can normally handle only a little amount of symbols. In other cases it pauses with client or just shows weird symbols. I've tried to write in different ways using global variable in client for confirmation from server (with and without pausing the client), using usleep()(100/600/1000/10000), using pause(), result is always the same as when I fast call client again and again.

I'm writing it using VirtualBox Ubuntu.

UPD: Problem solved using sleep (5) instead of pause() in client and increasing usleep() up to 1000

Client:

#include "minitalk.h"

int g_recieve;

void    sending_bits(char c, int pid)
{
    int i;

    i = 128;
    while(i >= 1)
    {
        if (g_recieve == 1)
        {
            if (i & c)
            {
                if (kill(pid, SIGUSR1) == -1)
                    errors("Error in sending signal!\n");
            }
            else
            {
                if (kill(pid, SIGUSR2) == -1)
                    errors("Error in sending signal!\n");
            }
            i /= 2;
            g_recieve = 0;
        }
        //usleep(600);
    }
}


int send_str(int pid, char *s)
{
    int i;

    i = 0;
    while (s[i])
    {
        sending_bits(s[i], pid);
        i++;
    }
    return (0);
}

void    cl_handler(int signum, siginfo_t *siginfo, void *context)
{
    (void)context;
    (void)siginfo;
    (void)signum;
    g_recieve = 1;
    write(1, "Recieved signal from server\n", 28);
    return ;
}

int main(int argc, char **argv)
{
    struct sigaction    sigac;

    g_recieve = 1;
    sigemptyset(&sigac.sa_mask);
    sigaddset(&sigac.sa_mask, SIGINT);
    sigaddset(&sigac.sa_mask, SIGQUIT);
    sigaddset(&sigac.sa_mask, SIGUSR1);
    sigac.sa_flags = SA_SIGINFO;
    sigac.sa_sigaction = cl_handler;
    if (sigaction(SIGUSR2, &sigac, NULL) == -1)
        errors("Error in client sigaction\n");
    if (ft_atoi(argv[1]) < 0)
        errors("Wrong PID!\n");
    if (argc == 3)
        send_str(ft_atoi(argv[1]), argv[2]);
    else
        errors("Wrong arguments!\n");
    while (1)
        pause ();
    return (0);
}

Server:

#include "minitalk.h"

void    sv_handler(int signum, siginfo_t *siginfo, void *unused)
{
    static int  ascii = 0;
    static int  power = 0;

    (void)unused;
    if (signum == SIGUSR1)
        ascii += (128 >> power);
    power += 1;
    if (power == 8)
    {
        ft_putchar(ascii);
        power = 0;
        ascii = 0;
    }
    if (siginfo->si_pid == 0)
        errors("Server didn't get client's PID\n");
    if (kill(siginfo->si_pid, SIGUSR2) == -1)
        errors("Error in returning signal!\n");
}

int main(int argc, char **argv)
{
    struct sigaction    sigac;

    (void)argv;
    if (argc != 1)
        errors("Error arguments\n");
    write(1, "Server started!\nPID: ", 21);
    ft_putnbr(getpid());
    write(1, "\n", 1);
    sigemptyset(&sigac.sa_mask);
    //sigaddset(&sigac.sa_mask, SIGINT);
    //sigaddset(&sigac.sa_mask, SIGQUIT);
    sigac.sa_flags = SA_SIGINFO;
    sigac.sa_sigaction = sv_handler;
    if ((sigaction(SIGUSR1, &sigac, 0)) == -1)
        errors("Error sigaction\n");
    if ((sigaction(SIGUSR2, &sigac, 0)) == -1)
        errors("Error sigaction\n");
    while (1)
        pause();
    return (0);
}

Upvotes: 2

Views: 1098

Answers (1)

Makar
Makar

Reputation: 21

Problem solved using sleep(5) instead of pause() in client and increasing usleep() in client up to 1000.

Upvotes: 0

Related Questions