aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorEric S. Raymond <esr@thyrsus.com>2001-10-03 11:49:04 +0000
committerEric S. Raymond <esr@thyrsus.com>2001-10-03 11:49:04 +0000
commit1405a0444d316791af6a473324be754789fb98a1 (patch)
treec617c845fd630dcdef6d7a5c607b6ce13f20ed3c
parentb5abbf75ceef070108e4e82218953e74899d7e2b (diff)
downloadfetchmail-1405a0444d316791af6a473324be754789fb98a1.tar.gz
fetchmail-1405a0444d316791af6a473324be754789fb98a1.tar.bz2
fetchmail-1405a0444d316791af6a473324be754789fb98a1.zip
Security audit fix.
svn path=/trunk/; revision=3534
-rw-r--r--base64.c6
-rw-r--r--cram.c2
-rw-r--r--fetchmail.h2
-rw-r--r--gssapi.c4
-rw-r--r--kerberos.c4
-rw-r--r--unmime.c4
6 files changed, 12 insertions, 10 deletions
diff --git a/base64.c b/base64.c
index 1dc533dd..3658e956 100644
--- a/base64.c
+++ b/base64.c
@@ -52,7 +52,7 @@ void to64frombits(unsigned char *out, const unsigned char *in, int inlen)
*out = '\0';
}
-int from64tobits(char *out, const char *in)
+int from64tobits(char *out, const char *in, int maxlen)
/* base 64 to raw bytes in quasi-big-endian order, returning count of bytes */
{
int len = 0;
@@ -77,8 +77,10 @@ int from64tobits(char *out, const char *in)
if (digit4 != '=' && DECODE64(digit4) == BAD)
return(-1);
in += 4;
- *out++ = (DECODE64(digit1) << 2) | (DECODE64(digit2) >> 4);
++len;
+ if (len && len >= maxlen) /* prevent buffer overflow */
+ return(-1);
+ *out++ = (DECODE64(digit1) << 2) | (DECODE64(digit2) >> 4);
if (digit3 != '=')
{
*out++ = ((DECODE64(digit2) << 4) & 0xf0) | (DECODE64(digit3) >> 2);
diff --git a/cram.c b/cram.c
index c58533cc..d06df7f5 100644
--- a/cram.c
+++ b/cram.c
@@ -89,7 +89,7 @@ int do_cram_md5 (int sock, char *command, struct query *ctl, char *strip)
respdata = buf1;
if (strip && strncmp(buf1, strip, strlen(strip)) == 0)
respdata += strlen(strip);
- len = from64tobits (msg_id, respdata);
+ len = from64tobits (msg_id, respdata, sizeof(msg_id));
if (len < 0) {
report (stderr, GT_("could not decode BASE64 challenge\n"));
diff --git a/fetchmail.h b/fetchmail.h
index b8963ce8..1380ee95 100644
--- a/fetchmail.h
+++ b/fetchmail.h
@@ -505,7 +505,7 @@ int prc_filecheck(const char *, const flag);
/* base64.c */
void to64frombits(unsigned char *, const unsigned char *, int);
-int from64tobits(char *, const char *);
+int from64tobits(char *, const char *, int len);
/* unmime.c */
/* Bit-mask returned by MimeBodyType */
diff --git a/gssapi.c b/gssapi.c
index b33e2f45..cfc16d27 100644
--- a/gssapi.c
+++ b/gssapi.c
@@ -119,7 +119,7 @@ int do_gssauth(int sock, char *command, char *hostname, char *username)
gss_release_name(&min_stat, &target_name);
return result;
}
- request_buf.length = from64tobits(buf2, buf1 + 2);
+ request_buf.length = from64tobits(buf2, buf1 + 2, sizeof(buf2));
request_buf.value = buf2;
sec_token = &request_buf;
}
@@ -131,7 +131,7 @@ int do_gssauth(int sock, char *command, char *hostname, char *username)
if (result = gen_recv(sock, buf1, sizeof buf1))
return result;
- request_buf.length = from64tobits(buf2, buf1 + 2);
+ request_buf.length = from64tobits(buf2, buf1 + 2, sizeof(buf2));
request_buf.value = buf2;
maj_stat = gss_unwrap(&min_stat, context,
diff --git a/kerberos.c b/kerberos.c
index f0da5a1a..a6d97758 100644
--- a/kerberos.c
+++ b/kerberos.c
@@ -69,7 +69,7 @@ int do_rfc1731(int sock, char *command, char *truename)
return result;
}
- len = from64tobits(challenge1.cstr, buf1);
+ len = from64tobits(challenge1.cstr, buf1, sizeof(challenge1.cstr));
if (len < 0) {
report(stderr, GT_("could not decode initial BASE64 challenge\n"));
return PS_AUTHFAIL;
@@ -208,7 +208,7 @@ int do_rfc1731(int sock, char *command, char *truename)
* process is complete.
*/
- len = from64tobits(buf2, buf1);
+ len = from64tobits(buf2, buf1, sizeof(buf2x));
if (len < 0) {
report(stderr, GT_("could not decode BASE64 ready response\n"));
return PS_AUTHFAIL;
diff --git a/unmime.c b/unmime.c
index 35e5a96b..3e2ec521 100644
--- a/unmime.c
+++ b/unmime.c
@@ -71,7 +71,7 @@ void UnMimeHeader(unsigned char *hdr)
/* Note: Decoding is done "in-situ", i.e. without using an
* additional buffer for temp. storage. This is possible, since the
* decoded string will always be shorter than the encoded string,
- * due to the en- coding scheme.
+ * due to the encoding scheme.
*/
int state = S_COPY_PLAIN;
@@ -171,7 +171,7 @@ void UnMimeHeader(unsigned char *hdr)
int decoded_count;
delimsave = *p; *p = '\r';
- decoded_count = from64tobits(p_out, p_in);
+ decoded_count = from64tobits(p_out, p_in, 0);
*p = delimsave;
if (decoded_count > 0)
p_out += decoded_count;