Back to index

courier  0.68.2
comverp.c
Go to the documentation of this file.
00001 /*
00002 ** Copyright 1998 - 2000 Double Precision, Inc.
00003 ** See COPYING for distribution information.
00004 */
00005 
00006 #include      "comverp.h"
00007 #include      "courier.h"
00008 #include      "comctlfile.h"
00009 #include      <stdlib.h>
00010 #include      <string.h>
00011 
00012 static const char xdigit[]="0123456789ABCDEF";
00013 
00014 /*
00015 ** Encode the recipient address.  We have to handle UUCP addresses as well,
00016 ** that do not contain a @, so there's a slight deviation from the draft
00017 ** here...
00018 */
00019 
00020 size_t verp_encode(const char *receipient, char *buf)
00021 {
00022 size_t i=1;
00023 unsigned j;
00024 
00025        while (*receipient)
00026        {
00027               if (*receipient == '@' && strchr(receipient+1, '@') == 0)
00028               {
00029                      if (buf)      *buf++ = '=';
00030                      ++i;
00031                      ++receipient;
00032                      continue;
00033               }
00034 
00035               switch (*receipient) {
00036               case '=':
00037                      if (strchr(receipient, '@'))
00038                      {
00039                             if (buf)      *buf++ = *receipient;
00040 
00041                             ++receipient;
00042                             ++i;
00043                             break;
00044                      }
00045 
00046                      /* UUCP, no @, must encode it */
00047 
00048               case '@':
00049               case ':':
00050               case '%':
00051               case '!':
00052               case '+':
00053               case '-':
00054               case '[':
00055               case ']':
00056                      j=(unsigned)(unsigned char)*receipient++;
00057 
00058                      if (buf)
00059                      {
00060                             *buf++='+';
00061                             *buf++=xdigit[ j / 16 ];
00062                             *buf++=xdigit[ j % 16 ];
00063                      }
00064                      i += 3;
00065                      break;
00066               default:
00067                      if (buf)      *buf++ = *receipient;
00068 
00069                      ++receipient;
00070                      ++i;
00071               }
00072        }
00073        if (buf)      *buf=0;
00074        return (i);
00075 }
00076 
00077 /*
00078 ** Get the return address of a message.  If the message has the VERP flag
00079 ** set, construct the VERPed address appropriately.
00080 */
00081 
00082 char *verp_getsender(struct ctlfile *ctf, const char *receipient)
00083 {
00084 const char *p, *r;
00085 char   *q, *s;
00086 
00087        if (ctf->sender[0] == '\0')
00088               return (strcpy(courier_malloc(1), ""));
00089 
00090        p=ctf->sender;
00091 
00092        if (ctlfile_searchfirst(ctf, COMCTLFILE_VERP) < 0 ||
00093               (r=strrchr(p, '@')) == 0)
00094               return (strcpy(courier_malloc(strlen(p)+1), p));
00095               /* VERP not set */
00096 
00097        q=courier_malloc(strlen(p)+1+verp_encode(receipient, 0));
00098        memcpy(q, p, r-p);
00099        s=q + (r-p);
00100        *s++='-';
00101        s += verp_encode(receipient, s)-1;
00102        strcpy(s, r);
00103        return (q);
00104 }