Commit 5e1b0bfb 5e1b0bfbc373116076cd70b7b2a52ea842d32122 by Sergey Poznyakoff

(sql_escape_string): Escape ocurrences of ' and " in string.

(mu_sql_expand_query): prevent possible sql injection
1 parent a746a09b
...@@ -63,15 +63,45 @@ char *mu_sql_db = "accounts"; /* Database Name */ ...@@ -63,15 +63,45 @@ char *mu_sql_db = "accounts"; /* Database Name */
63 int mu_sql_port = 0; /* Port number to connect to. 63 int mu_sql_port = 0; /* Port number to connect to.
64 0 means default port */ 64 0 means default port */
65 65
66 static char *
67 sql_escape_string (const char *ustr)
68 {
69 char *str, *q;
70 const unsigned char *p;
71 size_t len = strlen (ustr);
72
73 for (p = (const unsigned char *) ustr; *p; p++)
74 {
75 if (strchr ("'\"", *p))
76 len++;
77 }
78
79 str = malloc (len + 1);
80 if (!str)
81 return NULL;
82
83 for (p = (const unsigned char *) ustr, q = str; *p; p++)
84 {
85 if (strchr ("'\"", *p))
86 *q++ = '\\';
87 *q++ = *p;
88 }
89 *q = 0;
90 return str;
91 }
92
66 char * 93 char *
67 mu_sql_expand_query (const char *query, const char *ustr) 94 mu_sql_expand_query (const char *query, const char *ustr)
68 { 95 {
69 char *p, *q, *res; 96 char *p, *q, *res;
70 int len; 97 int len;
98 char *esc_ustr;
71 99
72 if (!query) 100 if (!query)
73 return NULL; 101 return NULL;
74 102
103 esc_ustr = sql_escape_string (ustr);
104
75 /* Compute resulting query length */ 105 /* Compute resulting query length */
76 for (len = 0, p = (char *) query; *p; ) 106 for (len = 0, p = (char *) query; *p; )
77 { 107 {
...@@ -79,7 +109,7 @@ mu_sql_expand_query (const char *query, const char *ustr) ...@@ -79,7 +109,7 @@ mu_sql_expand_query (const char *query, const char *ustr)
79 { 109 {
80 if (p[1] == 'u') 110 if (p[1] == 'u')
81 { 111 {
82 len += strlen (ustr); 112 len += strlen (esc_ustr);
83 p += 2; 113 p += 2;
84 } 114 }
85 else if (p[1] == '%') 115 else if (p[1] == '%')
...@@ -102,7 +132,10 @@ mu_sql_expand_query (const char *query, const char *ustr) ...@@ -102,7 +132,10 @@ mu_sql_expand_query (const char *query, const char *ustr)
102 132
103 res = malloc (len + 1); 133 res = malloc (len + 1);
104 if (!res) 134 if (!res)
135 {
136 free (esc_ustr);
105 return res; 137 return res;
138 }
106 139
107 for (p = (char *) query, q = res; *p; ) 140 for (p = (char *) query, q = res; *p; )
108 { 141 {
...@@ -111,7 +144,7 @@ mu_sql_expand_query (const char *query, const char *ustr) ...@@ -111,7 +144,7 @@ mu_sql_expand_query (const char *query, const char *ustr)
111 switch (*++p) 144 switch (*++p)
112 { 145 {
113 case 'u': 146 case 'u':
114 strcpy (q, ustr); 147 strcpy (q, esc_ustr);
115 q += strlen (q); 148 q += strlen (q);
116 p++; 149 p++;
117 break; 150 break;
...@@ -128,6 +161,8 @@ mu_sql_expand_query (const char *query, const char *ustr) ...@@ -128,6 +161,8 @@ mu_sql_expand_query (const char *query, const char *ustr)
128 *q++ = *p++; 161 *q++ = *p++;
129 } 162 }
130 *q = 0; 163 *q = 0;
164
165 free (esc_ustr);
131 return res; 166 return res;
132 } 167 }
133 168
......