summaryrefslogtreecommitdiffstats
path: root/src/lib/krb5
diff options
context:
space:
mode:
authorTom Yu <tlyu@mit.edu>2004-06-01 20:16:38 +0000
committerTom Yu <tlyu@mit.edu>2004-06-01 20:16:38 +0000
commitd60e990037df6682e6459c7ae29ac1a7bae21a41 (patch)
tree3109c58bf5af3a6e880488ab71a7ce8edda2081f /src/lib/krb5
parent57f38a772375eb3d8ccfbe8f08a7cf0d5395cc3c (diff)
downloadkrb5-d60e990037df6682e6459c7ae29ac1a7bae21a41.tar.gz
krb5-d60e990037df6682e6459c7ae29ac1a7bae21a41.tar.xz
krb5-d60e990037df6682e6459c7ae29ac1a7bae21a41.zip
fix buffer overflow in an_to_ln.c
* an_to_ln.c (rule_an_to_ln): Fix buffer overflow when parsing principal names into components. (do_replacement): likewise (aname_replacer): Support error return from do_replacement ticket: new version_reported: 1.3.3 target_version: 1.3.4 tags: pullup component: krb5-libs git-svn-id: svn://anonsvn.mit.edu/krb5/trunk@16381 dc483132-0cff-0310-8789-dd5450dbe970
Diffstat (limited to 'src/lib/krb5')
-rw-r--r--src/lib/krb5/os/ChangeLog7
-rw-r--r--src/lib/krb5/os/an_to_ln.c45
2 files changed, 48 insertions, 4 deletions
diff --git a/src/lib/krb5/os/ChangeLog b/src/lib/krb5/os/ChangeLog
index 59c24dc0d5..790bc2f2b4 100644
--- a/src/lib/krb5/os/ChangeLog
+++ b/src/lib/krb5/os/ChangeLog
@@ -1,3 +1,10 @@
+2004-06-01 Sam Hartman <hartmans@mit.edu>
+
+ * an_to_ln.c (rule_an_to_ln): Fix buffer overflow when parsing
+ principal names into components.
+ (do_replacement): likewise
+ (aname_replacer): Support error return from do_replacement
+
2004-05-07 Sam Hartman <hartmans@mit.edu>
* an_to_ln.c: Patch from Matt Crawford to allow matching on
diff --git a/src/lib/krb5/os/an_to_ln.c b/src/lib/krb5/os/an_to_ln.c
index 41a5bde313..c134cafcfc 100644
--- a/src/lib/krb5/os/an_to_ln.c
+++ b/src/lib/krb5/os/an_to_ln.c
@@ -270,9 +270,14 @@ aname_do_match(char *string, char **contextp)
* If no regcomp() then just return the input string verbatim in the output
* string.
*/
-static void
+#define use_bytes(x) \
+ out_used += (x); \
+ if (out_used > MAX_FORMAT_BUFFER) goto mem_err
+
+static int
do_replacement(char *regexp, char *repl, int doall, char *in, char *out)
{
+ size_t out_used = 0;
#if HAVE_REGCOMP
regex_t match_exp;
regmatch_t match_match;
@@ -287,17 +292,22 @@ do_replacement(char *regexp, char *repl, int doall, char *in, char *out)
do {
if (!regexec(&match_exp, cp, 1, &match_match, 0)) {
if (match_match.rm_so) {
+ use_bytes(match_match.rm_so);
strncpy(op, cp, match_match.rm_so);
op += match_match.rm_so;
}
+ use_bytes(strlen(repl));
strncpy(op, repl, MAX_FORMAT_BUFFER - 1 - (op - out));
op += strlen(op);
cp += match_match.rm_eo;
- if (!doall)
+ if (!doall) {
+ use_bytes(strlen(cp));
strncpy(op, cp, MAX_FORMAT_BUFFER - 1 - (op - out));
+ }
matched = 1;
}
else {
+ use_bytes(strlen(cp));
strncpy(op, cp, MAX_FORMAT_BUFFER - 1 - (op - out));
matched = 0;
}
@@ -322,17 +332,21 @@ do_replacement(char *regexp, char *repl, int doall, char *in, char *out)
sdispl = (size_t) (loc1 - cp);
edispl = (size_t) (loc2 - cp);
if (sdispl) {
+ use_bytes(sdispl);
strncpy(op, cp, sdispl);
op += sdispl;
}
+ use_bytes(strlen(repl));
strncpy(op, repl, MAX_FORMAT_BUFFER - 1 - (op - out));
op += strlen(repl);
cp += edispl;
if (!doall)
+ use_bytes(strlen(cp));
strncpy(op, cp, MAX_FORMAT_BUFFER - 1 - (op - out));
matched = 1;
}
else {
+ use_bytes(strlen(cp));
strncpy(op, cp, MAX_FORMAT_BUFFER - 1 - (op - out));
matched = 0;
}
@@ -340,7 +354,15 @@ do_replacement(char *regexp, char *repl, int doall, char *in, char *out)
#else /* HAVE_REGEXP_H */
memcpy(out, in, MAX_FORMAT_BUFFER);
#endif /* HAVE_REGCOMP */
+ return 1;
+ mem_err:
+#ifdef HAVE_REGCMP
+ regfree(&match_exp);
+#endif
+ return 0;
+
}
+#undef use_bytes
/*
* aname_replacer() - Perform the specified substitutions on the input
@@ -412,7 +434,12 @@ aname_replacer(char *string, char **contextp, char **result)
/* Do the replacemenbt */
memset(out, '\0', MAX_FORMAT_BUFFER);
- do_replacement(rule, repl, doglobal, in, out);
+ if (!do_replacement(rule, repl, doglobal, in, out)) {
+ free(rule);
+ free(repl);
+ kret = KRB5_LNAME_NOTRANS;
+ break;
+ }
free(rule);
free(repl);
@@ -459,6 +486,7 @@ rule_an_to_ln(krb5_context context, char *rule, krb5_const_principal aname, cons
char *fprincname;
char *selstring = 0;
int num_comps, compind;
+ size_t selstring_used;
char *cout;
krb5_const krb5_data *datap;
char *outstring;
@@ -479,6 +507,7 @@ rule_an_to_ln(krb5_context context, char *rule, krb5_const_principal aname, cons
*/
current = strchr(current, ':');
selstring = (char *) malloc(MAX_FORMAT_BUFFER);
+ selstring_used = 0;
if (current && selstring) {
current++;
cout = selstring;
@@ -499,6 +528,14 @@ rule_an_to_ln(krb5_context context, char *rule, krb5_const_principal aname, cons
compind-1)
: krb5_princ_realm(context, aname))
) {
+ if ((datap->length < MAX_FORMAT_BUFFER)
+ && (selstring_used+datap->length
+ < MAX_FORMAT_BUFFER)) {
+ selstring_used += datap->length;
+ } else {
+ kret = ENOMEM;
+ goto errout;
+ }
strncpy(cout,
datap->data,
(unsigned) datap->length);
@@ -529,7 +566,7 @@ rule_an_to_ln(krb5_context context, char *rule, krb5_const_principal aname, cons
else
kret = KRB5_CONFIG_BADFORMAT;
- if (kret)
+ errout: if (kret)
free(selstring);
}
}