]> Pileus Git - ~andy/fetchmail/blobdiff - rpa.c
Minor bug fixes for socket.c
[~andy/fetchmail] / rpa.c
diff --git a/rpa.c b/rpa.c
index f05c40725d0205781cd54c3e9779204ad0321166..c365f0ded8b2338ed9a1b2792557c4d0da07b209 100644 (file)
--- a/rpa.c
+++ b/rpa.c
@@ -8,19 +8,24 @@
   description:  RPA authorisation code for POP3 client
 
   The sole entry point is POP3_auth_rpa()
+
+  For license terms, see the file COPYING in this directory.
+
  ***********************************************************************/
 
 #include  "config.h"
 
 #if defined(POP3_ENABLE) && defined(RPA_ENABLE)
 #include  <stdio.h>
+#include  <stdlib.h>
 #include  <unistd.h>
 #include  <ctype.h>
-#include  <string.h> 
+#include  <string.h>
+#include  <sys/types.h>
 
 #include  "socket.h"
 #include  "fetchmail.h"
-#include  "md5.h"
+#include  "fm_md5.h"
 #include  "i18n.h"
 
 #ifdef TESTMODE
@@ -33,20 +38,20 @@ extern int linecount;
 
 #ifndef NO_PROTO
   /* prototypes for internal functions */
-  static int  POP3_rpa_resp(unsigned char* argbuf, int socket );
-  static void LenAppend(unsigned char** pptr, int len);
-  static int  LenSkip(unsigned char** pptr, int rxlen);
-  static int  DecBase64(unsigned char* bufp);
-  static void EncBase64(unsigned char* bufp, int len);
-  static void ToUnicode(unsigned char** pptr, unsigned char delim,
-                       unsigned char* buf, int* plen, int conv);
-  static int  SetRealmService(unsigned char* bufp);
+  static int  POP3_rpa_resp(char* argbuf, int socket );
+  static void LenAppend(char** pptr, int len);
+  static int  LenSkip(char** pptr, int rxlen);
+  static int  DecBase64(char* bufp);
+  static void EncBase64(char* bufp, int len);
+  static void ToUnicode(char** pptr, char delim, unsigned char* buf, int* plen,
+                       int conv);
+  static int  SetRealmService(char* bufp);
   static void GenChallenge(unsigned char* buf, int len);
-  static int  DigestPassphrase(unsigned char* passphrase,
+  static int  DigestPassphrase(char* passphrase,
                               unsigned char* rbuf, int unicodeit);
-  static void CompUserResp();
-  static int  CheckUserAuth();
-  static void md5(unsigned char* in, int len, unsigned char* out);
+  static void CompUserResp(void);
+  static int  CheckUserAuth(void);
+  static void md5(const void* in, int len, unsigned char* out);
 #endif
 
 /* RPA protocol definitions */
@@ -104,13 +109,13 @@ unsigned char   Kus[Kusl];                  /* Session key           */
   globals:       read outlevel.
  *********************************************************************/
 
-int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
+int POP3_auth_rpa (char *userid, char *passphrase, int socket)
 {
     int      ok,rxlen,verh,verl,i,rll;
-    unsigned char buf [POPBUFSIZE];
-    unsigned char *bufp;
+    char buf [POPBUFSIZE];
+    char *bufp;
     int      status,aulin,kuslin;
-    char* stdec[4] = { N_("Success") ,
+    const char* stdec[4] = { N_("Success") ,
                       N_("Restricted user (something wrong with account)") ,
                       N_("Invalid userid or passphrase") ,
                       N_("Deity error") };
@@ -166,7 +171,7 @@ int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
     if ((rxlen = DecBase64(buf)) == 0)
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("RPA token 2: Base64 decode error\n"));
+           report(stderr, GT_("RPA token 2: Base64 decode error\n"));
        return(PS_RPA);
     }
     bufp = buf;
@@ -175,15 +180,15 @@ int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
 
     /* Interpret Token 2 */
 
-    verh = *(bufp++); verl = *(bufp++);
+    verh = (unsigned char)*(bufp++); verl = (unsigned char)*(bufp++);
     if (outlevel >= O_DEBUG)
-       report(stdout, _("Service chose RPA version %d.%d\n"),verh,verl);
-    Csl  = *(bufp++);
+       report(stdout, GT_("Service chose RPA version %d.%d\n"),verh,verl);
+    Csl  = (unsigned char)*(bufp++);
     memcpy(Cs, bufp, Csl);
     bufp += Csl;
     if (outlevel >= O_DEBUG)
     {
-       report(stdout, _("Service challenge (l=%d):\n"),Csl);
+       report(stdout, GT_("Service challenge (l=%d):\n"),Csl);
        for (i=0; i<Csl; i++)
            report_build(stdout, "%02X ",Cs[i]);
        report_complete(stdout, "\n");
@@ -192,20 +197,20 @@ int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
     Ts[Tsl] = 0;
     bufp += Tsl;
     if (outlevel >= O_DEBUG)
-       report(stdout, _("Service timestamp %s\n"),Ts);
-    rll = *(bufp++) << 8; rll = rll | *(bufp++);
+       report(stdout, GT_("Service timestamp %s\n"),Ts);
+    rll = (unsigned char)*(bufp++) << 8; rll = rll | (unsigned char)*(bufp++);
     if ((bufp-buf+rll) != rxlen)
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("RPA token 2 length error\n"));
+           report(stderr, GT_("RPA token 2 length error\n"));
        return(PS_RPA);
     }
     if (outlevel >= O_DEBUG)
-       report(stdout, _("Realm list: %s\n"),bufp);
+       report(stdout, GT_("Realm list: %s\n"),bufp);
     if (SetRealmService(bufp) != 0)
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("RPA error in service@realm string\n"));
+           report(stderr, GT_("RPA error in service@realm string\n"));
        return(PS_RPA);
     }
 
@@ -242,7 +247,7 @@ int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
     if ((rxlen = DecBase64(buf)) == 0)
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("RPA token 4: Base64 decode error\n"));
+           report(stderr, GT_("RPA token 4: Base64 decode error\n"));
        return(PS_RPA);
     }
     bufp = buf;
@@ -250,10 +255,10 @@ int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
 
     /* Interpret Token 4 */
 
-    aulin = *(bufp++);
+    aulin = (unsigned char)*(bufp++);
     if (outlevel >= O_DEBUG)
     {
-       report(stdout, _("User authentication (l=%d):\n"),aulin);
+       report(stdout, GT_("User authentication (l=%d):\n"),aulin);
        for (i=0; i<aulin; i++)
            report_build(stdout, "%02X ",bufp[i]);
        report_complete(stdout, "\n");
@@ -267,44 +272,46 @@ int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
     {
        status = *(bufp++);
        if (outlevel >= O_DEBUG)
-           report(stdout, _("RPA status: %02X\n"),status);
+           report(stdout, GT_("RPA status: %02X\n"),status);
     }
     else status = 0;
     if ((bufp - buf) != rxlen)
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("RPA token 4 length error\n"));
+           report(stderr, GT_("RPA token 4 length error\n"));
        return(PS_RPA);
     }
     if (status != 0)
     {
-       if (outlevel > O_SILENT)
-           if (status < 4)
-               report(stderr, _("RPA rejects you: %s\n"),_(stdec[status]));
-           else
-               report(stderr, _("RPA rejects you, reason unknown\n"));
+       if (outlevel > O_SILENT) {
+           if (status < 4) {
+               report(stderr, GT_("RPA rejects you: %s\n"),GT_(stdec[status]));
+           } else {
+               report(stderr, GT_("RPA rejects you, reason unknown\n"));
+           }
+       }
        return(PS_AUTHFAIL);
     }
     if (Aul != aulin)
     {
        report(stderr, 
-              _("RPA User Authentication length error: %d\n"),aulin);
+              GT_("RPA User Authentication length error: %d\n"),aulin);
        return(PS_RPA);
     }
     if (Kusl != kuslin)
     {
-       report(stderr, _("RPA Session key length error: %d\n"),kuslin);
+       report(stderr, GT_("RPA Session key length error: %d\n"),kuslin);
        return(PS_RPA);
     }
     if (CheckUserAuth() != 0)
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("RPA _service_ auth fail. Spoof server?\n"));
+           report(stderr, GT_("RPA _service_ auth fail. Spoof server?\n"));
        return(PS_AUTHFAIL);
     }
     if (outlevel >= O_DEBUG)
     {
-       report(stdout, _("Session key established:\n"));
+       report(stdout, GT_("Session key established:\n"));
        for (i=0; i<Kusl; i++)
            report_build(stdout, "%02X ",Kus[i]);
        report_complete(stdout, "\n");
@@ -335,7 +342,7 @@ int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
     }
 
     if (outlevel > O_SILENT)
-       report(stdout, _("RPA authorisation complete\n"));
+       report(stdout, GT_("RPA authorisation complete\n"));
 
     return(PS_SUCCESS);
 }
@@ -354,9 +361,7 @@ int POP3_auth_rpa (unsigned char *userid, unsigned char *passphrase, int socket)
   globals:       reads outlevel.
  *********************************************************************/
 
-static int POP3_rpa_resp (argbuf,socket)
-unsigned char *argbuf;
-int socket;
+static int POP3_rpa_resp (char *argbuf, int socket)
 {
     int ok;
     char buf [POPBUFSIZE];
@@ -364,7 +369,7 @@ int socket;
     int sockrc;
 
     if (outlevel >= O_DEBUG)
-       report(stdout,  _("Get response\n"));
+       report(stdout,  GT_("Get response\n"));
 #ifndef TESTMODE
     sockrc = gen_recv(socket, buf, sizeof(buf));
 #else
@@ -394,7 +399,7 @@ int socket;
     else
        ok = PS_SOCKET;
     if (outlevel >= O_DEBUG)
-       report(stdout,  _("Get response return %d [%s]\n"), ok, buf);
+       report(stdout,  GT_("Get response return %d [%s]\n"), ok, buf);
     buf[sockrc] = 0;
     return(ok);
 }
@@ -413,10 +418,10 @@ int socket;
   globals:       none
  *********************************************************************/
 
-static void LenAppend(pptr,len)
-unsigned char **pptr;
-int  len;
+static void LenAppend(char **pptr_, int len)
 {
+    unsigned char **pptr = (unsigned char **)pptr_;
+
     if (len < 0x80)
     {
        **pptr = len; (*pptr)++;
@@ -447,49 +452,47 @@ int  len;
   globals:       reads outlevel.
  *********************************************************************/
 
-int LenSkip(pptr,rxlen)
-unsigned char **pptr;
-int rxlen;
+int LenSkip(char **pptr, int rxlen)
 {
     int len;
-    unsigned char *save;
+    char *save;
     save = *pptr;
-    if (**pptr != HDR)
+    if ((unsigned char)**pptr != HDR)
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("Hdr not 60\n"));
+           report(stderr, GT_("Hdr not 60\n"));
        return(0);
     }
     (*pptr)++;
-    if (((**pptr) & 0x80) == 0 )
+    if (((unsigned char)(**pptr) & 0x80) == 0 )
     {
-       len = **pptr; (*pptr)++;
+       len = (unsigned char)**pptr; (*pptr)++;
     }
-    else if ((**pptr) == 0x81)
+    else if ((unsigned char)(**pptr) == 0x81)
     {
-       len = *(*pptr+1); (*pptr) += 2;
+       len = (unsigned char)*(*pptr+1); (*pptr) += 2;
     }
-    else if ((**pptr) == 0x82)
+    else if ((unsigned char)(**pptr) == 0x82)
     {
-       len = ((*(*pptr+1)) << 8) | *(*pptr+2);
+       len = ((unsigned char)(*(*pptr+1)) << 8) | (unsigned char)*(*pptr+2);
        (*pptr) += 3;
     }
     else len = 0;
     if (len==0)
     {
        if (outlevel>O_SILENT)
-           report(stderr, _("Token length error\n"));
+           report(stderr, GT_("Token length error\n"));
     }
     else if (((*pptr-save)+len) != rxlen)
     {
        if (outlevel>O_SILENT)
-           report(stderr, _("Token Length %d disagrees with rxlen %d\n"),len,rxlen);
+           report(stderr, GT_("Token Length %d disagrees with rxlen %d\n"),len,rxlen);
        len = 0;
     }
     else if (memcmp(*pptr,MECH,11))
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("Mechanism field incorrect\n"));
+           report(stderr, GT_("Mechanism field incorrect\n"));
        len = 0;
     }
     else (*pptr) += 11;  /* Skip mechanism field */
@@ -509,27 +512,26 @@ int rxlen;
   globals:       reads outlevel.
  *********************************************************************/
 
-static int DecBase64(bufp)
-unsigned char *bufp;
+static int DecBase64(char *bufp)
 {
-    unsigned int   new, bits=0, cnt=0, i, part=0;
+    unsigned int   newx, bits=0, cnt=0, i, part=0;
     unsigned char  ch;
-    unsigned char* outp=bufp;
-    unsigned char* inp=bufp;
-    while((ch=*(inp++)) != 0)
+    char* outp=bufp;
+    char* inp=bufp;
+    while((ch=(unsigned char)*(inp++)) != 0)
     {
        if ((ch != '=') && (ch != ' ') && (ch != '\n') && (ch != '\r'))
        {
-           if      ((ch>='A') && (ch <= 'Z'))   new = ch - 'A';
-           else if ((ch>='a') && (ch <= 'z'))   new = ch - 'a' + 26;
-           else if ((ch>='0') && (ch <= '9'))   new = ch - '0' + 52;
-           else if ( ch=='+'                )   new = 62;
-           else if ( ch=='/'                )   new = 63;
+           if      ((ch>='A') && (ch <= 'Z'))   newx = ch - 'A';
+           else if ((ch>='a') && (ch <= 'z'))   newx = ch - 'a' + 26;
+           else if ((ch>='0') && (ch <= '9'))   newx = ch - '0' + 52;
+           else if ( ch=='+'                )   newx = 62;
+           else if ( ch=='/'                )   newx = 63;
            else {
-               report(stderr,  _("dec64 error at char %d: %x\n"), inp - bufp, ch);
+               report(stderr,  GT_("dec64 error at char %d: %x\n"), (int)(inp - bufp), ch);
                return(0);
            }
-           part=((part & 0x3F)*64) + new;
+           part=((part & 0x3F)*64) + newx;
            bits += 6;
            if (bits >= 8)
            {
@@ -541,10 +543,10 @@ unsigned char *bufp;
     }
     if (outlevel >= O_MONITOR)
     {
-       report(stdout, _("Inbound binary data:\n"));
+       report(stdout, GT_("Inbound binary data:\n"));
        for (i=0; i<cnt; i++)
        {
-           report_build(stdout, "%02X ",bufp[i]);
+           report_build(stdout, "%02X ",(unsigned char)bufp[i]);
            if (((i % 16)==15) || (i==(cnt-1)))
                report_complete(stdout, "\n");
        }
@@ -568,21 +570,19 @@ unsigned char *bufp;
   globals:       reads outlevel;
  *********************************************************************/
 
-static void EncBase64(bufp,len)
-unsigned char *bufp;
-int  len;
+static void EncBase64(char *bufp, int len)
 {
-    unsigned char* outp;
+    char* outp;
     unsigned char  c1,c2,c3;
     char x[]="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
     int  i;
 
     if (outlevel >= O_MONITOR)
     {
-       report(stdout, _("Outbound data:\n"));
+       report(stdout, GT_("Outbound data:\n"));
        for (i=0; i<len; i++)
        {
-           report_build(stdout, "%02X ",bufp[i]);
+           report_build(stdout, "%02X ",(unsigned char)bufp[i]);
            if (((i % 16)==15) || (i==(len-1)))
                report_complete(stdout, "\n");
        }
@@ -592,9 +592,9 @@ int  len;
     /* So we can do the update in place, start at the far end! */
     for (i=((len-1)/3)*3; i>=0; i-=3)
     {
-       c1 = bufp[i];
-       if ((i+1) < len) c2 = bufp[i+1]; else c2=0;
-       if ((i+2) < len) c3 = bufp[i+2]; else c3=0;
+       c1 = (unsigned char)bufp[i];
+       if ((i+1) < len) c2 = (unsigned char)bufp[i+1]; else c2=0;
+       if ((i+2) < len) c3 = (unsigned char)bufp[i+2]; else c3=0;
        *(outp) = x[c1/4];
        *(outp+1) = x[((c1 & 3)*16) + (c2/16)];
        if ((i+1) < len) *(outp+2) = x[((c2 & 0x0F)*4) + (c3/64)];
@@ -622,12 +622,9 @@ int  len;
   globals:       reads outlevel;
  *********************************************************************/
 
-static void ToUnicode(pptr,delim,buf,plen,conv)
-unsigned char **pptr; /* input string  */
-unsigned char delim;
-unsigned char *buf;   /* output buffer */
-int  *plen;
-int conv;
+static void ToUnicode(char **pptr /* input string*/,
+       char delim, unsigned char *buf /* output buffer */,
+       int *plen, int conv)
 {
     unsigned char *p;
     int i;
@@ -636,7 +633,7 @@ int conv;
     {
        *(p++) = 0;
        if (conv)
-           *(p++) = tolower(**pptr);
+           *(p++) = tolower((unsigned char)**pptr);
        else
            *(p++) = (**pptr);
        (*plen) += 2;
@@ -645,12 +642,12 @@ int conv;
     if ( ((**pptr)!=delim) && ((**pptr)!=0) && ((*plen)==STRMAX) )
     {
        if (outlevel > O_SILENT)
-           report(stderr, _("RPA String too long\n"));
+           report(stderr, GT_("RPA String too long\n"));
        *plen = 0;
     }
     if (outlevel >= O_DEBUG)
     {
-       report(stdout, _("Unicode:\n"));
+       report(stdout, GT_("Unicode:\n"));
        for (i=0; i<(*plen); i++)
        {
            report_build(stdout, "%02X ",buf[i]);
@@ -673,8 +670,7 @@ int conv;
                  writes Ns Nsl Nr Nrl
  *********************************************************************/
 
-static int SetRealmService(bufp)
-unsigned char* bufp;
+static int SetRealmService(char *bufp)
 {
     /* For the moment we pick the first available realm. It would */
     /* make more sense to verify that the realm which the user    */
@@ -702,9 +698,7 @@ unsigned char* bufp;
                  reads /dev/random
  *********************************************************************/
 
-static void GenChallenge(buf,len)
-unsigned char *buf;
-int  len;
+static void GenChallenge(unsigned char *buf, int len)
 {
     int  i;
     FILE *devrandom;
@@ -712,11 +706,11 @@ int  len;
     devrandom = fopen("/dev/urandom","rb");
     if (devrandom == NULL && outlevel > O_SILENT)
     {
-       report(stdout, _("RPA Failed open of /dev/urandom. This shouldn't\n"));
-       report(stdout, _("    prevent you logging in, but means you\n"));
-       report(stdout, _("    cannot be sure you are talking to the\n"));
-       report(stdout, _("    service that you think you are (replay\n"));
-       report(stdout, _("    attacks by a dishonest service are possible.)\n"));
+       report(stdout, GT_("RPA Failed open of /dev/urandom. This shouldn't\n"));
+       report(stdout, GT_("    prevent you logging in, but means you\n"));
+       report(stdout, GT_("    cannot be sure you are talking to the\n"));
+       report(stdout, GT_("    service that you think you are (replay\n"));
+       report(stdout, GT_("    attacks by a dishonest service are possible.)\n"));
     }
 
     for(i=0; i<len; i++)
@@ -727,7 +721,7 @@ int  len;
 
     if (outlevel >= O_DEBUG)
     {
-       report(stdout, _("User challenge:\n"));
+       report(stdout, GT_("User challenge:\n"));
        for (i=0; i<len; i++)
          {
          report_build(stdout, "%02X ",buf[i]);
@@ -753,14 +747,12 @@ int  len;
                  writes Pu.
  *********************************************************************/
 
-static int DigestPassphrase(passphrase,rbuf,unicodeit)
-unsigned char *passphrase;
-unsigned char *rbuf;
-int unicodeit;
+static int DigestPassphrase(char *passphrase,unsigned char *rbuf,
+       int unicodeit)
 {
     int   len;
     unsigned char  workarea[STRMAX];
-    unsigned char* ptr;
+    char* ptr;
 
     if (unicodeit)  /* Option in spec. Yuck. */
     {
@@ -768,14 +760,10 @@ int unicodeit;
        ToUnicode(&ptr, '\0', workarea, &len, 0); /* No case conv here */
        if (len == 0)
            return(PS_SYNTAX);
-       ptr = workarea;
+       md5(workarea,len,rbuf);
     }
     else
-    {
-       ptr = rbuf;
-       len = strlen(passphrase);
-    }
-    md5(ptr,len,rbuf);
+       md5(rbuf,strlen(passphrase),rbuf);
     return(0);
 }
 
@@ -792,7 +780,7 @@ int unicodeit;
                  writes Ru.
  *********************************************************************/
 
-static void CompUserResp()
+static void CompUserResp(void)
 {
     unsigned char  workarea[Pul+48+STRMAX*5+Tsl+Pul];
     unsigned char* p;
@@ -824,7 +812,7 @@ static void CompUserResp()
                  writes Ru.
  *********************************************************************/
 
-static int CheckUserAuth()
+static int CheckUserAuth(void)
 {
     unsigned char  workarea[Pul+48+STRMAX*7+Tsl+Pul];
     unsigned char* p;
@@ -875,17 +863,15 @@ static int CheckUserAuth()
   globals:       reads outlevel
  *********************************************************************/
 
-static void md5(in,len,out)
-unsigned char*    in;
-int      len;
-unsigned char*    out;
+static void md5(const void *in_,int len,unsigned char *out)
 {
     int      i;
     MD5_CTX  md5context;
+    const unsigned char *in = (const unsigned char *)in_;
 
     if (outlevel >= O_DEBUG)
     {
-       report(stdout, _("MD5 being applied to data block:\n"));
+       report(stdout, GT_("MD5 being applied to data block:\n"));
        for (i=0; i<len; i++)
        {
            report_build(stdout, "%02X ",in[i]);
@@ -898,7 +884,7 @@ unsigned char*    out;
     MD5Final(  out, &md5context );
     if (outlevel >= O_DEBUG)
     {
-       report(stdout, _("MD5 result is: \n"));
+       report(stdout, GT_("MD5 result is:\n"));
        for (i=0; i<16; i++)
        {
            report_build(stdout, "%02X ",out[i]);