qreceipt.c
changeset 0 068428edee47
equal deleted inserted replaced
-1:000000000000 0:068428edee47
       
     1 #include "sig.h"
       
     2 #include "env.h"
       
     3 #include "substdio.h"
       
     4 #include "stralloc.h"
       
     5 #include "subfd.h"
       
     6 #include "getln.h"
       
     7 #include "alloc.h"
       
     8 #include "str.h"
       
     9 #include "hfield.h"
       
    10 #include "token822.h"
       
    11 #include "error.h"
       
    12 #include "gen_alloc.h"
       
    13 #include "gen_allocdefs.h"
       
    14 #include "headerbody.h"
       
    15 #include "exit.h"
       
    16 #include "open.h"
       
    17 #include "quote.h"
       
    18 #include "qmail.h"
       
    19 
       
    20 void die_noreceipt() { _exit(0); }
       
    21 void die() { _exit(100); }
       
    22 void die_temp() { _exit(111); }
       
    23 void die_nomem() {
       
    24  substdio_putsflush(subfderr,"qreceipt: fatal: out of memory\n"); die_temp(); }
       
    25 void die_fork() {
       
    26  substdio_putsflush(subfderr,"qreceipt: fatal: unable to fork\n"); die_temp(); }
       
    27 void die_qqperm() {
       
    28  substdio_putsflush(subfderr,"qreceipt: fatal: permanent qmail-queue error\n"); die(); }
       
    29 void die_qqtemp() {
       
    30  substdio_putsflush(subfderr,"qreceipt: fatal: temporary qmail-queue error\n"); die_temp(); }
       
    31 void die_usage() {
       
    32  substdio_putsflush(subfderr,
       
    33  "qreceipt: usage: qreceipt deliveryaddress\n"); die(); }
       
    34 void die_read() {
       
    35  if (errno == error_nomem) die_nomem();
       
    36  substdio_putsflush(subfderr,"qreceipt: fatal: read error\n"); die_temp(); }
       
    37 void doordie(sa,r) stralloc *sa; int r; {
       
    38  if (r == 1) return; if (r == -1) die_nomem();
       
    39  substdio_putsflush(subfderr,"qreceipt: fatal: unable to parse this: ");
       
    40  substdio_putflush(subfderr,sa->s,sa->len); die(); }
       
    41 
       
    42 char *target;
       
    43 
       
    44 int flagreceipt = 0;
       
    45 
       
    46 char *returnpath;
       
    47 stralloc messageid = {0};
       
    48 stralloc sanotice = {0};
       
    49 
       
    50 int rwnotice(addr) token822_alloc *addr; { token822_reverse(addr);
       
    51  if (token822_unquote(&sanotice,addr) != 1) die_nomem();
       
    52  if (sanotice.len == str_len(target))
       
    53    if (!str_diffn(sanotice.s,target,sanotice.len))
       
    54      flagreceipt = 1;
       
    55  token822_reverse(addr); return 1; }
       
    56 
       
    57 struct qmail qqt;
       
    58 
       
    59 stralloc quoted = {0};
       
    60 
       
    61 void finishheader()
       
    62 {
       
    63  char *qqx;
       
    64 
       
    65  if (!flagreceipt) die_noreceipt();
       
    66  if (str_equal(returnpath,"")) die_noreceipt();
       
    67  if (str_equal(returnpath,"#@[]")) die_noreceipt();
       
    68 
       
    69  if (!quote2(&quoted,returnpath)) die_nomem();
       
    70 
       
    71  if (qmail_open(&qqt) == -1) die_fork();
       
    72 
       
    73  qmail_puts(&qqt,"From: DELIVERY NOTICE SYSTEM <");
       
    74  qmail_put(&qqt,quoted.s,quoted.len);
       
    75  qmail_puts(&qqt,">\n");
       
    76  qmail_puts(&qqt,"To: <");
       
    77  qmail_put(&qqt,quoted.s,quoted.len);
       
    78  qmail_puts(&qqt,">\n");
       
    79  qmail_puts(&qqt,"Subject: success notice\n\
       
    80 \n\
       
    81 Hi! This is the qreceipt program. Your message was delivered to the\n\
       
    82 following address: ");
       
    83  qmail_puts(&qqt,target);
       
    84  qmail_puts(&qqt,". Thanks for asking.\n");
       
    85  if (messageid.s)
       
    86   {
       
    87    qmail_puts(&qqt,"Your ");
       
    88    qmail_put(&qqt,messageid.s,messageid.len);
       
    89   }
       
    90 
       
    91  qmail_from(&qqt,"");
       
    92  qmail_to(&qqt,returnpath);
       
    93  qqx = qmail_close(&qqt);
       
    94 
       
    95  if (*qqx)
       
    96    if (*qqx == 'D') die_qqperm();
       
    97    else die_qqtemp();
       
    98 }
       
    99 
       
   100 stralloc hfbuf = {0};
       
   101 token822_alloc hfin = {0};
       
   102 token822_alloc hfrewrite = {0};
       
   103 token822_alloc hfaddr = {0};
       
   104 
       
   105 void doheaderfield(h)
       
   106 stralloc *h;
       
   107 {
       
   108  switch(hfield_known(h->s,h->len))
       
   109   {
       
   110    case H_MESSAGEID:
       
   111      if (!stralloc_copy(&messageid,h)) die_nomem();
       
   112      break;
       
   113    case H_NOTICEREQUESTEDUPONDELIVERYTO:
       
   114      doordie(h,token822_parse(&hfin,h,&hfbuf));
       
   115      doordie(h,token822_addrlist(&hfrewrite,&hfaddr,&hfin,rwnotice));
       
   116      break;
       
   117   }
       
   118 }
       
   119 
       
   120 void dobody(h) stralloc *h; { ; }
       
   121 
       
   122 void main(argc,argv)
       
   123 int argc;
       
   124 char **argv;
       
   125 {
       
   126  sig_pipeignore();
       
   127  if (!(target = argv[1])) die_usage();
       
   128  if (!(returnpath = env_get("SENDER"))) die_usage();
       
   129  if (headerbody(subfdin,doheaderfield,finishheader,dobody) == -1) die_read();
       
   130  die_noreceipt();
       
   131 }