Commit 0dbd5a87 authored by Harin Vadodaria's avatar Harin Vadodaria

Bug#21973610: BUFFER OVERFLOW ISSUES

Description : Incorrect usage of sprintf/strcpy caused
              possible buffer overflow issues at various
              places.

Solution : - Fixed mysql_plugin and mysqlshow
           - Fixed regex library issues

Reviewed-By : Georgi Kodinov <georgi.kodinov@oracle.com>
Reviewed-By : Venkata S Murthy Sidagam <venkata.sidagam@oracle.com>
parent fd983141
/* /*
Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved. Copyright (c) 2011, 2015, Oracle and/or its affiliates. All rights reserved.
This program is free software; you can redistribute it and/or modify This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by it under the terms of the GNU General Public License as published by
...@@ -406,7 +406,7 @@ exit: ...@@ -406,7 +406,7 @@ exit:
static void usage(void) static void usage(void)
{ {
PRINT_VERSION; PRINT_VERSION;
puts("Copyright (c) 2011, Oracle and/or its affiliates. " puts("Copyright (c) 2011, 2015, Oracle and/or its affiliates. "
"All rights reserved.\n"); "All rights reserved.\n");
puts("Enable or disable plugins."); puts("Enable or disable plugins.");
printf("\nUsage: %s [options] <plugin> ENABLE|DISABLE\n\nOptions:\n", printf("\nUsage: %s [options] <plugin> ENABLE|DISABLE\n\nOptions:\n",
...@@ -757,6 +757,11 @@ static int check_options(int argc, char **argv, char *operation) ...@@ -757,6 +757,11 @@ static int check_options(int argc, char **argv, char *operation)
/* read the plugin config file and check for match against argument */ /* read the plugin config file and check for match against argument */
else else
{ {
if (strlen(argv[i]) + 4 + 1 > FN_REFLEN)
{
fprintf(stderr, "ERROR: argument is too long.\n");
return 1;
}
strcpy(plugin_name, argv[i]); strcpy(plugin_name, argv[i]);
strcpy(config_file, argv[i]); strcpy(config_file, argv[i]);
strcat(config_file, ".ini"); strcat(config_file, ".ini");
...@@ -848,6 +853,7 @@ static int process_options(int argc, char *argv[], char *operation) ...@@ -848,6 +853,7 @@ static int process_options(int argc, char *argv[], char *operation)
if (opt_basedir[i-1] != FN_LIBCHAR || opt_basedir[i-1] != FN_LIBCHAR2) if (opt_basedir[i-1] != FN_LIBCHAR || opt_basedir[i-1] != FN_LIBCHAR2)
{ {
char buff[FN_REFLEN]; char buff[FN_REFLEN];
memset(buff, 0, sizeof(buff));
strncpy(buff, opt_basedir, sizeof(buff) - 1); strncpy(buff, opt_basedir, sizeof(buff) - 1);
#ifdef __WIN__ #ifdef __WIN__
......
...@@ -377,7 +377,7 @@ list_dbs(MYSQL *mysql,const char *wild) ...@@ -377,7 +377,7 @@ list_dbs(MYSQL *mysql,const char *wild)
uint length, counter = 0; uint length, counter = 0;
ulong rowcount = 0L; ulong rowcount = 0L;
char tables[NAME_LEN+1], rows[NAME_LEN+1]; char tables[NAME_LEN+1], rows[NAME_LEN+1];
char query[255]; char query[NAME_LEN + 100];
MYSQL_FIELD *field; MYSQL_FIELD *field;
MYSQL_RES *result; MYSQL_RES *result;
MYSQL_ROW row= NULL, rrow; MYSQL_ROW row= NULL, rrow;
...@@ -444,7 +444,8 @@ list_dbs(MYSQL *mysql,const char *wild) ...@@ -444,7 +444,8 @@ list_dbs(MYSQL *mysql,const char *wild)
MYSQL_ROW trow; MYSQL_ROW trow;
while ((trow = mysql_fetch_row(tresult))) while ((trow = mysql_fetch_row(tresult)))
{ {
sprintf(query,"SELECT COUNT(*) FROM `%s`",trow[0]); my_snprintf(query, sizeof(query),
"SELECT COUNT(*) FROM `%s`", trow[0]);
if (!(mysql_query(mysql,query))) if (!(mysql_query(mysql,query)))
{ {
MYSQL_RES *rresult; MYSQL_RES *rresult;
...@@ -500,7 +501,7 @@ list_tables(MYSQL *mysql,const char *db,const char *table) ...@@ -500,7 +501,7 @@ list_tables(MYSQL *mysql,const char *db,const char *table)
{ {
const char *header; const char *header;
uint head_length, counter = 0; uint head_length, counter = 0;
char query[255], rows[NAME_LEN], fields[16]; char query[NAME_LEN + 100], rows[NAME_LEN], fields[16];
MYSQL_FIELD *field; MYSQL_FIELD *field;
MYSQL_RES *result; MYSQL_RES *result;
MYSQL_ROW row, rrow; MYSQL_ROW row, rrow;
...@@ -585,7 +586,8 @@ list_tables(MYSQL *mysql,const char *db,const char *table) ...@@ -585,7 +586,8 @@ list_tables(MYSQL *mysql,const char *db,const char *table)
if (opt_verbose > 1) if (opt_verbose > 1)
{ {
/* Print the count of rows for each table */ /* Print the count of rows for each table */
sprintf(query,"SELECT COUNT(*) FROM `%s`",row[0]); my_snprintf(query, sizeof(query), "SELECT COUNT(*) FROM `%s`",
row[0]);
if (!(mysql_query(mysql,query))) if (!(mysql_query(mysql,query)))
{ {
if ((rresult = mysql_store_result(mysql))) if ((rresult = mysql_store_result(mysql)))
...@@ -645,13 +647,15 @@ list_tables(MYSQL *mysql,const char *db,const char *table) ...@@ -645,13 +647,15 @@ list_tables(MYSQL *mysql,const char *db,const char *table)
static int static int
list_table_status(MYSQL *mysql,const char *db,const char *wild) list_table_status(MYSQL *mysql,const char *db,const char *wild)
{ {
char query[1024],*end; char query[NAME_LEN + 100];
int len;
MYSQL_RES *result; MYSQL_RES *result;
MYSQL_ROW row; MYSQL_ROW row;
end=strxmov(query,"show table status from `",db,"`",NullS); len= sizeof(query);
if (wild && wild[0]) len-= my_snprintf(query, len, "show table status from `%s`", db);
strxmov(end," like '",wild,"'",NullS); if (wild && wild[0] && len)
strxnmov(query + strlen(query), len, " like '", wild, "'", NullS);
if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql))) if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql)))
{ {
fprintf(stderr,"%s: Cannot get status for db: %s, table: %s: %s\n", fprintf(stderr,"%s: Cannot get status for db: %s, table: %s: %s\n",
...@@ -683,7 +687,8 @@ static int ...@@ -683,7 +687,8 @@ static int
list_fields(MYSQL *mysql,const char *db,const char *table, list_fields(MYSQL *mysql,const char *db,const char *table,
const char *wild) const char *wild)
{ {
char query[1024],*end; char query[NAME_LEN + 100];
int len;
MYSQL_RES *result; MYSQL_RES *result;
MYSQL_ROW row; MYSQL_ROW row;
ulong UNINIT_VAR(rows); ulong UNINIT_VAR(rows);
...@@ -697,7 +702,7 @@ list_fields(MYSQL *mysql,const char *db,const char *table, ...@@ -697,7 +702,7 @@ list_fields(MYSQL *mysql,const char *db,const char *table,
if (opt_count) if (opt_count)
{ {
sprintf(query,"select count(*) from `%s`", table); my_snprintf(query, sizeof(query), "select count(*) from `%s`", table);
if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql))) if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql)))
{ {
fprintf(stderr,"%s: Cannot get record count for db: %s, table: %s: %s\n", fprintf(stderr,"%s: Cannot get record count for db: %s, table: %s: %s\n",
...@@ -709,9 +714,11 @@ list_fields(MYSQL *mysql,const char *db,const char *table, ...@@ -709,9 +714,11 @@ list_fields(MYSQL *mysql,const char *db,const char *table,
mysql_free_result(result); mysql_free_result(result);
} }
end=strmov(strmov(strmov(query,"show /*!32332 FULL */ columns from `"),table),"`"); len= sizeof(query);
if (wild && wild[0]) len-= my_snprintf(query, len, "show /*!32332 FULL */ columns from `%s`",
strxmov(end," like '",wild,"'",NullS); table);
if (wild && wild[0] && len)
strxnmov(query + strlen(query), len, " like '", wild, "'", NullS);
if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql))) if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql)))
{ {
fprintf(stderr,"%s: Cannot list columns in db: %s, table: %s: %s\n", fprintf(stderr,"%s: Cannot list columns in db: %s, table: %s: %s\n",
...@@ -732,7 +739,7 @@ list_fields(MYSQL *mysql,const char *db,const char *table, ...@@ -732,7 +739,7 @@ list_fields(MYSQL *mysql,const char *db,const char *table,
print_res_top(result); print_res_top(result);
if (opt_show_keys) if (opt_show_keys)
{ {
end=strmov(strmov(strmov(query,"show keys from `"),table),"`"); my_snprintf(query, sizeof(query), "show keys from `%s`", table);
if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql))) if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql)))
{ {
fprintf(stderr,"%s: Cannot list keys in db: %s, table: %s: %s\n", fprintf(stderr,"%s: Cannot list keys in db: %s, table: %s: %s\n",
......
/* Copyright (c) 2000, 2011, Oracle and/or its affiliates. All rights reserved. /* Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
This program is free software; you can redistribute it and/or modify This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by it under the terms of the GNU General Public License as published by
...@@ -118,7 +118,7 @@ print_arrays_for(char *set) ...@@ -118,7 +118,7 @@ print_arrays_for(char *set)
{ {
FILE *f; FILE *f;
sprintf(buf, "%s.conf", set); snprintf(buf, sizeof(buf), "%s.conf", set);
if ((f = fopen(buf, "r")) == NULL) { if ((f = fopen(buf, "r")) == NULL) {
fprintf(stderr, "%s: can't read conf file for charset %s\n", prog, set); fprintf(stderr, "%s: can't read conf file for charset %s\n", prog, set);
......
...@@ -425,7 +425,8 @@ char *should; ...@@ -425,7 +425,8 @@ char *should;
(sub.rm_so != -1 && sub.rm_eo == -1) || (sub.rm_so != -1 && sub.rm_eo == -1) ||
(sub.rm_so != -1 && sub.rm_so < 0) || (sub.rm_so != -1 && sub.rm_so < 0) ||
(sub.rm_eo != -1 && sub.rm_eo < 0) ) { (sub.rm_eo != -1 && sub.rm_eo < 0) ) {
sprintf(grump, "start %ld end %ld", (long)sub.rm_so, snprintf(grump, sizeof(grump),
"start %ld end %ld", (long)sub.rm_so,
(long)sub.rm_eo); (long)sub.rm_eo);
return(grump); return(grump);
} }
...@@ -438,7 +439,8 @@ char *should; ...@@ -438,7 +439,8 @@ char *should;
/* check for in range */ /* check for in range */
if ((int) sub.rm_eo > (int) strlen(str)) { if ((int) sub.rm_eo > (int) strlen(str)) {
sprintf(grump, "start %ld end %ld, past end of string", snprintf(grump, sizeof(grump),
"start %ld end %ld, past end of string",
(long)sub.rm_so, (long)sub.rm_eo); (long)sub.rm_so, (long)sub.rm_eo);
return(grump); return(grump);
} }
...@@ -449,13 +451,15 @@ char *should; ...@@ -449,13 +451,15 @@ char *should;
/* check for not supposed to match */ /* check for not supposed to match */
if (should == NULL) { if (should == NULL) {
sprintf(grump, "matched `%.*s'", len, p); snprintf(grump, sizeof(grump),
"matched `%.*s'", len, p);
return(grump); return(grump);
} }
/* check for wrong match */ /* check for wrong match */
if (len != shlen || strncmp(p, should, (size_t)shlen) != 0) { if (len != shlen || strncmp(p, should, (size_t)shlen) != 0) {
sprintf(grump, "matched `%.*s' instead", len, p); snprintf(grump, sizeof(grump),
"matched `%.*s' instead", len, p);
return(grump); return(grump);
} }
if (shlen > 0) if (shlen > 0)
...@@ -468,7 +472,8 @@ char *should; ...@@ -468,7 +472,8 @@ char *should;
if (shlen == 0) if (shlen == 0)
shlen = 1; /* force check for end-of-string */ shlen = 1; /* force check for end-of-string */
if (strncmp(p, at, shlen) != 0) { if (strncmp(p, at, shlen) != 0) {
sprintf(grump, "matched null at `%.20s'", p); snprintf(grump, sizeof(grump),
"matched null at `%.20s'", p);
return(grump); return(grump);
} }
return(NULL); return(NULL);
...@@ -501,7 +506,7 @@ char *name; ...@@ -501,7 +506,7 @@ char *name;
static char efbuf[100]; static char efbuf[100];
my_regex_t re; my_regex_t re;
sprintf(efbuf, "REG_%s", name); snprintf(efbuf, sizeof(efbuf), "REG_%s", name);
assert(strlen(efbuf) < sizeof(efbuf)); assert(strlen(efbuf) < sizeof(efbuf));
re.re_endp = efbuf; re.re_endp = efbuf;
(void) my_regerror(REG_ATOI, &re, efbuf, sizeof(efbuf)); (void) my_regerror(REG_ATOI, &re, efbuf, sizeof(efbuf));
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment