/* Public domain */ #ifndef QMGR_UIDMIN #define QMGR_UIDMIN 1 #endif #ifndef QMGR_GIDMIN #define QMGR_GIDMIN 1 #endif #define QMGR_ID_MAX 12 typedef struct qmgr_worker { uid_t uid; gid_t gid; pid_t pid; int pipe; TAILQ_ENTRY(qmgr_worker) workers; } QMGR_Worker; typedef TAILQ_HEAD(qmgr_workerq, qmgr_worker) QMGR_WorkerQ; typedef struct qmgr_metadata { uid_t uid; /* UID of recipient */ gid_t gid; /* GID of recipient */ char qid[QMGR_ID_MAX]; /* Message ID in active queue */ char from[ADDRESS_MAX]; /* Envelope sender address */ char rcpt[ADDRESS_MAX]; /* Envelope recipient address */ char ip[IP_ADDRESS_MAX]; /* IP address in Received: */ } QMGR_MetaData; extern QMGR_WorkerQ qmgrWorkers; /* MAIN: Active workers */ extern Uint qmgrWorkerCount; extern char *pathQueue; extern char pathQueueTmpDir[FILENAME_MAX]; int QMGR_Init(CFG_File *); int QMGR_Todo(void); void QMGR_ForkInstance(void); int QMGR_Read(int, void *, size_t); int QMGR_Write(int, const void *, size_t); int QMGR_CheckSignals(void); MPD_Message *QMGR_LoadMessage(const char *, const QMGR_MetaData *); int QMGR_Queue(MPD_Message *, MPD_Recipient *, int); int QMGR_WakeWorker(const QMGR_MetaData *); int QMGR_WorkerMain(uid_t); static __inline__ int QMGR_Readv(int fd, const struct iovec *iov, int iovcnt) { ssize_t rv; for (;;) { rv = readv(fd, iov, iovcnt); if (rv == -1) { if (errno == EINTR || errno == EAGAIN) { if (QMGR_CheckSignals()) { return (-1); } continue; } else { MPD_SetError("QMGR_Readv: %s", strerror(errno)); return (-1); } } else { return (0); } } } static __inline__ int QMGR_Writev(int fd, const struct iovec *iov, int iovcnt) { ssize_t rv; for (;;) { rv = writev(fd, iov, iovcnt); if (rv == -1) { if (errno == EINTR || errno == EAGAIN) { if (QMGR_CheckSignals()) { return (-1); } continue; } else { MPD_SetError("QMGR_Writev: %s", strerror(errno)); return (-1); } } else { return (0); } } }