server_start.c
author viric@mandarina
Fri, 02 Oct 2009 19:20:41 +0200
changeset 274 62048132f95f
parent 267 11631dd11ff8
child 302 c60e0db23bd7
permissions -rw-r--r--
Making changes so it looks like the code in ts-0.6.4, which I can't find
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
49
09bb8a5583e9 Added the license.
lbatlle@npdl268.bpo.hp.com
parents: 44
diff changeset
     1
/*
09bb8a5583e9 Added the license.
lbatlle@npdl268.bpo.hp.com
parents: 44
diff changeset
     2
    Task Spooler - a task queue system for the unix user
267
11631dd11ff8 Updating copyright years in the source.
viric@mandarina
parents: 251
diff changeset
     3
    Copyright (C) 2007-2009  LluĂ­s Batlle i Rossell
49
09bb8a5583e9 Added the license.
lbatlle@npdl268.bpo.hp.com
parents: 44
diff changeset
     4
09bb8a5583e9 Added the license.
lbatlle@npdl268.bpo.hp.com
parents: 44
diff changeset
     5
    Please find the license in the provided COPYING file.
09bb8a5583e9 Added the license.
lbatlle@npdl268.bpo.hp.com
parents: 44
diff changeset
     6
*/
44
4dcf05746ece Better include files.
viric@llimona
parents: 28
diff changeset
     7
#include <unistd.h>
4dcf05746ece Better include files.
viric@llimona
parents: 28
diff changeset
     8
#include <string.h>
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
     9
#include <sys/types.h>
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    10
#include <sys/socket.h>
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    11
#include <sys/un.h>
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    12
#include <errno.h>
3
2fb8a6bdd024 More code.
viric@llimona
parents: 2
diff changeset
    13
#include <stdlib.h>
9
9acd8ae3190c First usable version!
lbatlle@npdl268.bpo.hp.com
parents: 3
diff changeset
    14
#include <stdio.h>
146
5e689cb593aa Bones of the "-i" parameter, job info.
viric@llimona
parents: 133
diff changeset
    15
#include <sys/time.h>
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    16
#include <signal.h>
3
2fb8a6bdd024 More code.
viric@llimona
parents: 2
diff changeset
    17
2fb8a6bdd024 More code.
viric@llimona
parents: 2
diff changeset
    18
#include "main.h"
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    19
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    20
extern int server_socket;
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    21
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    22
static char *socket_path;
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    23
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    24
static int fork_server();
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    25
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    26
void create_socket_path(char **path)
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    27
{
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    28
    char *tmpdir;
119
361b08d33762 $USER is no more used for crating the socket path. Now the UID is used.
viric@llimona
parents: 92
diff changeset
    29
    char userid[20];
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    30
    int size;
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    31
64
2a17c9c7b1d5 Added a limit to the number of finished jobs.
viric@llimona
parents: 49
diff changeset
    32
    /* As a priority, TS_SOCKET mandates over the path creation */
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    33
    *path = getenv("TS_SOCKET");
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    34
    if (*path != 0)
64
2a17c9c7b1d5 Added a limit to the number of finished jobs.
viric@llimona
parents: 49
diff changeset
    35
    {
2a17c9c7b1d5 Added a limit to the number of finished jobs.
viric@llimona
parents: 49
diff changeset
    36
        /* We need this in our memory, for forks and future 'free'. */
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    37
        size = strlen(*path) + 1;
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    38
        *path = (char *) malloc(size);
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    39
        strcpy(*path, getenv("TS_SOCKET"));
64
2a17c9c7b1d5 Added a limit to the number of finished jobs.
viric@llimona
parents: 49
diff changeset
    40
        return;
2a17c9c7b1d5 Added a limit to the number of finished jobs.
viric@llimona
parents: 49
diff changeset
    41
    }
2a17c9c7b1d5 Added a limit to the number of finished jobs.
viric@llimona
parents: 49
diff changeset
    42
2a17c9c7b1d5 Added a limit to the number of finished jobs.
viric@llimona
parents: 49
diff changeset
    43
    /* ... if the $TS_SOCKET doesn't exist ... */
2a17c9c7b1d5 Added a limit to the number of finished jobs.
viric@llimona
parents: 49
diff changeset
    44
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    45
    /* Create the path */
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    46
    tmpdir = getenv("TMPDIR");
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    47
    if (tmpdir == NULL)
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    48
        tmpdir = "/tmp";
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    49
119
361b08d33762 $USER is no more used for crating the socket path. Now the UID is used.
viric@llimona
parents: 92
diff changeset
    50
    sprintf(userid, "%u", (unsigned int) getuid());
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    51
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    52
    /* Calculate the size */
119
361b08d33762 $USER is no more used for crating the socket path. Now the UID is used.
viric@llimona
parents: 92
diff changeset
    53
    size = strlen(tmpdir) + strlen("/socket-ts.") + strlen(userid) + 1;
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    54
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    55
    /* Freed after preparing the socket address */
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    56
    *path = (char *) malloc(size);
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    57
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    58
    sprintf(*path, "%s/socket-ts.%s", tmpdir, userid);
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    59
}
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
    60
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    61
int try_connect(int s)
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    62
{
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    63
    struct sockaddr_un addr;
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    64
    int res;
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    65
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    66
    addr.sun_family = AF_UNIX;
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
    67
    strcpy(addr.sun_path, socket_path);
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    68
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    69
    res = connect(s, (struct sockaddr *) &addr, sizeof(addr));
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    70
    return res;
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    71
}
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    72
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    73
void wait_server_up(int fd)
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    74
{
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    75
    char a;
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    76
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    77
    read(fd, &a, 1);
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    78
    close(fd);
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    79
}
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    80
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    81
/* Returns the fd where to wait for the parent notification */
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    82
static int fork_server()
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    83
{
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    84
    int pid;
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    85
    int p[2];
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    86
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    87
    /* !!! stdin/stdout */
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    88
    pipe(p);
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
    89
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    90
    pid = fork();
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    91
    switch (pid)
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    92
    {
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
    93
        case 0: /* Child */
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
    94
            close(p[0]);
3
2fb8a6bdd024 More code.
viric@llimona
parents: 2
diff changeset
    95
            close(server_socket);
66
f70a27afd92e Adding "swap jobs" with -U. Fixed a big problem with fds 0, 1, 2.
viric@mandarina
parents: 64
diff changeset
    96
            /* Close all std handles for the server */
f70a27afd92e Adding "swap jobs" with -U. Fixed a big problem with fds 0, 1, 2.
viric@mandarina
parents: 64
diff changeset
    97
            close(0);
f70a27afd92e Adding "swap jobs" with -U. Fixed a big problem with fds 0, 1, 2.
viric@mandarina
parents: 64
diff changeset
    98
            close(1);
f70a27afd92e Adding "swap jobs" with -U. Fixed a big problem with fds 0, 1, 2.
viric@mandarina
parents: 64
diff changeset
    99
            close(2);
133
4306e96f5906 Added setsid when going background.
viric@llimona
parents: 129
diff changeset
   100
            setsid();
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
   101
            server_main(p[1], socket_path);
3
2fb8a6bdd024 More code.
viric@llimona
parents: 2
diff changeset
   102
            exit(0);
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   103
            break;
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   104
        case -1: /* Error */
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   105
            return -1;
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   106
        default: /* Parent */
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   107
            close(p[1]);
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   108
    }
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   109
    /* Return the read fd */
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   110
    return p[0];
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   111
}
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   112
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   113
void notify_parent(int fd)
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   114
{
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   115
    char a = 'a';
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   116
    write(fd, &a, 1);
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   117
    close(fd);
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   118
}
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   119
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   120
int ensure_server_up()
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   121
{
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   122
    int res;
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   123
    int notify_fd;
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   124
129
312083fb8899 Change PF_UNIX to AF_UNIX. According to socket(2), this is better.
viric@llimona
parents: 119
diff changeset
   125
    server_socket = socket(AF_UNIX, SOCK_STREAM, 0);
92
05004c52ecff Better error reports on internal handled errors.
viric@llimona
parents: 66
diff changeset
   126
    if (server_socket == -1)
05004c52ecff Better error reports on internal handled errors.
viric@llimona
parents: 66
diff changeset
   127
        error("getting the server socket");
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   128
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
   129
    create_socket_path(&socket_path);
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
   130
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   131
    res = try_connect(server_socket);
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   132
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   133
    /* Good connection */
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   134
    if (res == 0)
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   135
        return 1;
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   136
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   137
    /* If error other than "No one listens on the other end"... */
3
2fb8a6bdd024 More code.
viric@llimona
parents: 2
diff changeset
   138
    if (!(errno == ENOENT || errno == ECONNREFUSED))
92
05004c52ecff Better error reports on internal handled errors.
viric@llimona
parents: 66
diff changeset
   139
        error("c: cannot connect to the server");
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   140
3
2fb8a6bdd024 More code.
viric@llimona
parents: 2
diff changeset
   141
    if (errno == ECONNREFUSED)
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
   142
        unlink(socket_path);
3
2fb8a6bdd024 More code.
viric@llimona
parents: 2
diff changeset
   143
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   144
    /* Try starting the server */
25
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   145
    notify_fd = fork_server();
e9e4babe6262 Now the server is quicly started.
viric@llimona
parents: 9
diff changeset
   146
    wait_server_up(notify_fd);
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   147
    res = try_connect(server_socket);
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   148
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   149
    /* The second time didn't work. Abort. */
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   150
    if (res == -1)
9
9acd8ae3190c First usable version!
lbatlle@npdl268.bpo.hp.com
parents: 3
diff changeset
   151
    {
9acd8ae3190c First usable version!
lbatlle@npdl268.bpo.hp.com
parents: 3
diff changeset
   152
        fprintf(stderr, "The server didn't come up.\n");
9acd8ae3190c First usable version!
lbatlle@npdl268.bpo.hp.com
parents: 3
diff changeset
   153
        exit(-1);
9acd8ae3190c First usable version!
lbatlle@npdl268.bpo.hp.com
parents: 3
diff changeset
   154
    }
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   155
251
5e0802df5788 Making a ts.error file for each socket ($TS_SOCKET.error)
viric@mandarina
parents: 231
diff changeset
   156
    free(socket_path);
28
107abb4ec98a Unified socket path, depending on the username and $TMPDIR.
viric@llimona
parents: 25
diff changeset
   157
2
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   158
    /* Good connection on the second time */
602bd67df3aa Changed tabs to 4 spaces. Rule.
viric@llimona
parents: 1
diff changeset
   159
    return 1;
1
74928e2b27f4 Honta versio de ia strukturo.
viric@llimona
parents:
diff changeset
   160
}