2 * $Id: server_ipc.c,v 1.1 2003-05-16 15:29:28 didg Exp $
4 * All rights reserved. See COPYRIGHT.
7 * ipc between parent and children.
14 #include <sys/types.h>
22 #include <atalk/server_child.h>
23 #include <atalk/server_ipc.h>
24 #include <atalk/logger.h>
26 typedef struct ipc_header {
33 static int pipe_fd[2];
35 void *server_ipc_create(void)
43 /* ----------------- */
44 int server_ipc_child(void *obj)
51 /* ----------------- */
52 int server_ipc_parent(void *obj)
57 /* ----------------- */
58 int ipc_kill_token (struct ipc_header *ipc, server_child *children)
62 if (ipc->len != sizeof(pid_t)) {
65 /* assume signals SA_RESTART set */
66 memcpy (&pid, ipc->msg, sizeof(pid_t));
68 LOG(log_info, logtype_default, "child %d disconnected", pid);
69 server_child_kill_one(children, CHILD_DSIFORK, pid);
73 /* ----------------- */
74 int ipc_get_session (struct ipc_header *ipc, server_child *children)
81 if (ipc->len < (sizeof(idlen) + sizeof(boottime)) ) {
85 memcpy (&idlen, p, sizeof(idlen));
86 idlen = ntohl (idlen);
89 memcpy (&boottime, p, sizeof(boottime));
90 p += sizeof(boottime);
92 if (ipc->len < idlen + sizeof(idlen) + sizeof(boottime)) {
95 if (NULL == (clientid = (char*) malloc(idlen)) ) {
98 memcpy (clientid, p, idlen);
100 server_child_kill_one_by_id (children, CHILD_DSIFORK, ipc->child_pid, idlen, clientid, boottime);
101 /* FIXME byte to ascii if we want to log clientid */
102 LOG (log_info, logtype_afpd, "ipc_get_session: len: %u, idlen %d, time %x", ipc->len, idlen, boottime);
106 #define IPC_HEADERLEN 10
107 #define IPC_MAXMSGSIZE 90
109 /* ----------------- */
110 int server_ipc_read(server_child *children)
113 struct ipc_header ipc;
114 char buf[IPC_MAXMSGSIZE], *p;
116 if ((ret = read(pipe_fd[0], buf, IPC_HEADERLEN)) != IPC_HEADERLEN) {
117 LOG (log_info, logtype_afpd, "Reading IPC header failed (%u of %u bytes read)", ret, IPC_HEADERLEN);
122 memcpy(&ipc.command, p, sizeof(ipc.command));
123 p += sizeof(ipc.command);
124 memcpy(&ipc.child_pid, p, sizeof(ipc.child_pid));
125 p += sizeof(ipc.child_pid);
126 memcpy(&ipc.len, p, sizeof(ipc.len));
128 /* This should never happen */
129 if (ipc.len > (IPC_MAXMSGSIZE - IPC_HEADERLEN))
131 LOG (log_info, logtype_afpd, "IPC message exceeds allowed size (%u)", ipc.len);
135 memset (buf, 0, IPC_MAXMSGSIZE);
137 if ((ret = read(pipe_fd[0], buf, ipc.len)) != ipc.len) {
138 LOG (log_info, logtype_afpd, "Reading IPC message failed (%u of %u bytes read)", ret, ipc.len);
144 LOG (log_info, logtype_afpd, "ipc_read: command: %u, pid: %u, len: %u", ipc.command, ipc.child_pid, ipc.len);
149 return (ipc_kill_token(&ipc, children));
152 return (ipc_get_session(&ipc, children));
155 LOG (log_info, logtype_afpd, "ipc_read: unknown command: %d", ipc.command);
161 /* ----------------- */
162 int server_ipc_write( u_int16_t command, int len, void *msg)
164 char block[IPC_MAXMSGSIZE], *p;
168 memset ( p, 0 , IPC_MAXMSGSIZE);
169 if (len + IPC_HEADERLEN > IPC_MAXMSGSIZE)
172 memcpy(p, &command, sizeof(command));
173 p += sizeof(command);
176 memcpy(p, &pid, sizeof(pid_t));
184 LOG (log_info, logtype_afpd, "ipc_write: command: %u, pid: %u, msglen: %u", command, pid, len);
185 return write(pipe_fd[1], block, len+IPC_HEADERLEN );