Skip to content

Commit

Permalink
Php Object Injection Emulator (#320)
Browse files Browse the repository at this point in the history
* POI emulator

* changed vuln class

* phpox helper added

* improved naming
  • Loading branch information
rjt-gupta authored and rnehra01 committed Jun 4, 2019
1 parent 7f76159 commit 4f39e4e
Show file tree
Hide file tree
Showing 5 changed files with 80 additions and 5 deletions.
2 changes: 1 addition & 1 deletion tanner/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
'REDIS': {'host': 'localhost', 'port': 6379, 'poolsize': 80, 'timeout': 1},
'EMULATORS': {'root_dir': '/opt/tanner'},
'EMULATOR_ENABLED': {'sqli': True, 'rfi': True, 'lfi': True, 'xss': True, 'cmd_exec': True,
'php_code_injection': True, "crlf": True},
'php_code_injection': True, 'php_object_injection': True, "crlf": True},
'SQLI': {'type': 'SQLITE', 'db_name': 'tanner_db', 'host': 'localhost', 'user': 'root',
'password': 'user_pass'},
'DOCKER': {'host_image': 'busybox:latest'},
Expand Down
12 changes: 8 additions & 4 deletions tanner/emulators/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

from tanner import __version__ as tanner_version
from tanner.config import TannerConfig
from tanner.emulators import lfi, rfi, sqli, xss, cmd_exec, php_code_injection, crlf
from tanner.emulators import lfi, rfi, sqli, xss, cmd_exec, php_code_injection, php_object_injection, crlf
from tanner.utils import patterns


Expand All @@ -21,12 +21,16 @@ def __init__(self, base_dir, db_name, loop=None):
'cmd_exec': cmd_exec.CmdExecEmulator() if self.emulator_enabled['cmd_exec'] else None,
'php_code_injection': php_code_injection.PHPCodeInjection(loop) if self.emulator_enabled[
'php_code_injection'] else None,
'php_object_injection': php_object_injection.PHPObjectInjection(loop) if self.emulator_enabled[
'php_object_injection'] else None,
'crlf': crlf.CRLFEmulator() if self.emulator_enabled['crlf'] else None
}

self.get_emulators = ['sqli', 'rfi', 'lfi', 'xss', 'php_code_injection', 'cmd_exec', 'crlf']
self.post_emulators = ['sqli', 'rfi', 'lfi', 'xss', 'php_code_injection', 'cmd_exec', 'crlf']
self.cookie_emulators = ['sqli']
self.get_emulators = ['sqli', 'rfi', 'lfi', 'xss', 'php_code_injection', 'php_object_injection',
'cmd_exec', 'crlf']
self.post_emulators = ['sqli', 'rfi', 'lfi', 'xss', 'php_code_injection', 'php_object_injection',
'cmd_exec', 'crlf']
self.cookie_emulators = ['sqli', 'php_object_injection']

def extract_get_data(self, path):
"""
Expand Down
43 changes: 43 additions & 0 deletions tanner/emulators/php_object_injection.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
import asyncio
import logging

from tanner.utils.php_sandbox_helper import PHPSandboxHelper
from tanner.utils import patterns


class PHPObjectInjection:
def __init__(self, loop=None):
self._loop = loop if loop is not None else asyncio.get_event_loop()
self.logger = logging.getLogger('tanner.php_object_injection')
self.helper = PHPSandboxHelper(self._loop)

async def get_injection_result(self, code):

vul_code = "<?php " \
"class ObjectInjection { " \
"public $insert; " \
"public function __destruct() { " \
"$var = system($this->insert, $ret);" \
"print $var[0];" \
"$this->date = date('d-m-y');" \
"$this->filename = '/tmp/logs/' . $this->date;" \
"file_put_contents($this->filename, $var[0], FILE_APPEND);" \
"}} " \
"$cmd = unserialize(\'%s\');" \
"?>" % code

object_injection_result = await self.helper.get_result(vul_code)

return object_injection_result

def scan(self, value):
detection = None
if patterns.PHP_OBJECT_INJECTION.match(value):
detection = dict(name='php_object_injection', order=3)
return detection

async def handle(self, attack_params):
result = await self.get_injection_result(attack_params[0]['value'])
if not result or 'stdout' not in result:
return dict(status_code=504)
return dict(value=result['stdout'], page=False)
1 change: 1 addition & 0 deletions tanner/utils/patterns.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
r'(alias|cat|cd|cp|echo|exec|find|for|grep|ifconfig|ls|man|mkdir|netstat|ping|ps|pwd|uname|wget|touch|while)'
r'([^A-z:./]|\b)')
PHP_CODE_INJECTION = re.compile(r'.*(;)*(echo|system|print|phpinfo)(\(.*\)).*')
PHP_OBJECT_INJECTION = re.compile(r'(^|;|{|})O:[0-9]+:')
CRLF_ATTACK = re.compile(r'.*(\r\n).*')
REMOTE_FILE_URL = re.compile(r'(.*(http(s){0,1}|ftp(s){0,1}):.*)')
WORD_PRESS_CONTENT = re.compile(r'/wp-content/.*')
Expand Down
27 changes: 27 additions & 0 deletions tanner/utils/php_sandbox_helper.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import logging
import asyncio
import aiohttp
from tanner import config


class PHPSandboxHelper:
def __init__(self, loop):
self.logger = logging.getLogger('tanner.php_sandbox_helper.PHPSandboxHelper')
self._loop = loop if loop is not None else asyncio.get_event_loop()

async def get_result(self, code):
result = None

phpox_address = 'http://{host}:{port}'.format(host=config.TannerConfig.get('PHPOX', 'host'),
port=config.TannerConfig.get('PHPOX', 'port')
)

try:
async with aiohttp.ClientSession(loop=self._loop) as session:
async with session.post(phpox_address, data=code) as resp:
result = await resp.json()
except aiohttp.ClientError as client_error:
self.logger.error('Error during connection to php sandbox %s', client_error)
finally:
await session.close()
return result

0 comments on commit 4f39e4e

Please # to comment.