void qmgr_active_done(QMGR_MESSAGE *message) { char *myname = "qmgr_active_done"; struct stat st; if (msg_verbose) msg_info("%s: %s", myname, message->queue_id); /* * During a previous iteration, an attempt to bounce this message may * have failed, so there may still be a bounce log lying around. XXX By * groping around in the bounce queue, we're trespassing on the bounce * service's territory. But doing so is more robust than depending on the * bounce daemon to do the lookup for us, and for us to do the deleting * after we have received a successful status from the bounce service. * The bounce queue directory blocks are most likely in memory anyway. If * these lookups become a performance problem we will have to build an * in-core cache into the bounce daemon. * * Don't bounce when the bounce log is empty. The bounce process obviously * failed, and the delivery agent will have requested that the message be * deferred. * * Bounces are sent asynchronously to avoid stalling while the cleanup * daemon waits for the qmgr to accept the "new mail" trigger. */ if (stat(mail_queue_path((VSTRING *) 0, MAIL_QUEUE_BOUNCE, message->queue_id), &st) == 0) { if (st.st_size == 0) { if (mail_queue_remove(MAIL_QUEUE_BOUNCE, message->queue_id)) msg_fatal("remove %s %s: %m", MAIL_QUEUE_BOUNCE, message->queue_id); } else { if (msg_verbose) msg_info("%s: bounce %s", myname, message->queue_id); if (message->verp_delims == 0 || var_verp_bounce_off) abounce_flush(BOUNCE_FLAG_KEEP, message->queue_name, message->queue_id, message->encoding, message->errors_to, qmgr_active_done_2_bounce_flush, (char *) message); else abounce_flush_verp(BOUNCE_FLAG_KEEP, message->queue_name, message->queue_id, message->encoding, message->errors_to, message->verp_delims, qmgr_active_done_2_bounce_flush, (char *) message); return; } } /* * Asynchronous processing does not reach this point. */ qmgr_active_done_2_generic(message); }
static void qmgr_active_done_2_bounce_flush(int status, char *context) { QMGR_MESSAGE *message = (QMGR_MESSAGE *) context; /* * Process abounce_flush() status and continue processing. */ message->flags |= status; qmgr_active_done_2_generic(message); }