chiark / gitweb /
first attempt in implementinging execution logic
[elogind.git] / socket.c
1 /*-*- Mode: C; c-basic-offset: 8 -*-*/
2
3 #include "name.h"
4 #include "socket.h"
5
6 static int socket_load(Name *n) {
7         Socket *s = SOCKET(n);
8
9         exec_context_defaults(&s->exec_context);
10
11         return name_load_fragment_and_dropin(n);
12 }
13
14 static void socket_dump(Name *n, FILE *f, const char *prefix) {
15
16         static const char* const state_table[_SOCKET_STATE_MAX] = {
17                 [SOCKET_DEAD] = "dead",
18                 [SOCKET_START_PRE] = "start-pre",
19                 [SOCKET_START_POST] = "start-post",
20                 [SOCKET_LISTENING] = "listening",
21                 [SOCKET_RUNNING] = "running",
22                 [SOCKET_STOP_PRE] = "stop-pre",
23                 [SOCKET_STOP_POST] = "stop-post",
24                 [SOCKET_MAINTAINANCE] = "maintainance"
25         };
26
27         static const char* const command_table[_SOCKET_EXEC_MAX] = {
28                 [SOCKET_EXEC_START_PRE] = "StartPre",
29                 [SOCKET_EXEC_START_POST] = "StartPost",
30                 [SOCKET_EXEC_STOP_PRE] = "StopPre",
31                 [SOCKET_EXEC_STOP_POST] = "StopPost"
32         };
33
34         SocketExecCommand c;
35         Socket *s = SOCKET(n);
36         const char *t;
37         int r;
38         char *k;
39
40         assert(s);
41
42         if ((r = address_print(&n->socket.address, &k)) < 0)
43                 t = strerror(-r);
44         else
45                 t = k;
46
47         fprintf(f,
48                 "%sSocket State: %s\n"
49                 "%sAddress: %s\n",
50                 prefix, state_table[s->state],
51                 prefix, t);
52
53         free(k);
54
55         exec_context_dump(&s->exec_context, f, prefix);
56
57         for (c = 0; c < _SOCKET_EXEC_MAX; c++) {
58                 ExecCommand *i;
59
60                 LIST_FOREACH(i, s->exec_command[c])
61                         fprintf(f, "%s%s: %s\n", prefix, command_table[c], i->path);
62         }
63 }
64
65 static NameActiveState socket_active_state(Name *n) {
66
67         static const NameActiveState table[_SOCKET_STATE_MAX] = {
68                 [SOCKET_DEAD] = NAME_INACTIVE,
69                 [SOCKET_START_PRE] = NAME_ACTIVATING,
70                 [SOCKET_START_POST] = NAME_ACTIVATING,
71                 [SOCKET_LISTENING] = NAME_ACTIVE,
72                 [SOCKET_RUNNING] = NAME_ACTIVE,
73                 [SOCKET_STOP_PRE] = NAME_DEACTIVATING,
74                 [SOCKET_STOP_POST] = NAME_DEACTIVATING,
75                 [SOCKET_MAINTAINANCE] = NAME_INACTIVE,
76         };
77
78         return table[SOCKET(n)->state];
79 }
80
81 static void socket_free_hook(Name *n) {
82         unsigned i;
83         SocketExecCommand c;
84         Socket *s = SOCKET(n);
85
86         assert(s);
87
88         for (i = 0; i < s->n_fds; i++)
89                 close_nointr(s->fds[i]);
90
91         exec_context_free(&s->exec_context);
92
93         for (c = 0; c < _SOCKET_EXEC_MAX; c++)
94                 exec_command_free_list(s->exec_command[c]);
95
96         if (s->service)
97                 s->service->socket = NULL;
98 }
99
100 const NameVTable socket_vtable = {
101         .suffix = ".socket",
102
103         .load = socket_load,
104         .dump = socket_dump,
105
106         .start = NULL,
107         .stop = NULL,
108         .reload = NULL,
109
110         .active_state = socket_active_state,
111
112         .free_hook = socket_free_hook
113 };