Skip to content

Commit

Permalink
first release build
Browse files Browse the repository at this point in the history
  • Loading branch information
daniel baier committed Feb 11, 2022
1 parent f0c405e commit 6421345
Show file tree
Hide file tree
Showing 7 changed files with 537 additions and 47 deletions.
67 changes: 42 additions & 25 deletions _ssl_log.js

Large diffs are not rendered by default.

10 changes: 8 additions & 2 deletions agent/openssl_boringssl.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ export function execute(moduleName:string) {


// the socket methods are in all systems the same
library_method_mapping[`*${socket_library}*`] = ["getpeername", "getsockname", "ntohs", "ntohl"]
library_method_mapping[`*${socket_library}*`] = ["getpeername*", "getsockname*", "ntohs*", "ntohl*"]



Expand Down Expand Up @@ -94,31 +94,37 @@ export function execute(moduleName:string) {
Interceptor.attach(addresses["SSL_read"],
{
onEnter: function (args: any) {
if (!ObjC.available){
var message = getPortsAndAddresses(SSL_get_fd(args[0]) as number, true, addresses)
message["ssl_session_id"] = getSslSessionId(args[0])
/* var my_Bio = args[0] as NativePointer
my_Bio.readPointer*/
message["function"] = "SSL_read"
this.message = message
this.buf = args[1]
} // this is a temporary workaround for the fd problem on iOS
},
onLeave: function (retval: any) {
if (!ObjC.available){
retval |= 0 // Cast retval to 32-bit integer.
if (retval <= 0) {
return
}
this.message["contentType"] = "datalog"
send(this.message, this.buf.readByteArray(retval))
} // this is a temporary workaround for the fd problem on iOS
}
})
Interceptor.attach(addresses["SSL_write"],
{
onEnter: function (args: any) {
if (!ObjC.available){
var message = getPortsAndAddresses(SSL_get_fd(args[0]) as number, false, addresses)
message["ssl_session_id"] = getSslSessionId(args[0])
message["function"] = "SSL_write"
message["contentType"] = "datalog"
send(message, args[1].readByteArray(parseInt(args[2])))
} // this is a temporary workaround for the fd problem on iOS
},
onLeave: function (retval: any) {
}
Expand All @@ -135,7 +141,7 @@ export function execute(moduleName:string) {
}
Interceptor.attach(addresses["SSL_CTX_set_info_callback"], {
onEnter: function (args : any) {
console.log("found boringSSL");
log("found boringSSL TLS key");
ptr(args[0]).add(CALLBACK_OFFSET).writePointer(keylog_callback);
}
});
Expand Down
10 changes: 8 additions & 2 deletions agent/ssl_log.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ var moduleNames: Array<string> = getModuleNames()

var module_library_mapping: { [key: string]: Array<[any, (moduleName: string)=>void]> } = {}
module_library_mapping["windows"] = [[/libssl-[0-9]+(_[0-9]+)?\.dll/, boring_execute],[/.*wolfssl.*\.dll/, wolf_execute],[/.*libgnutls-[0-9]+\.dll/, gnutls_execute],[/nspr[0-9]*\.dll/,nss_execute], [/sspicli\.dll/i,sspi_execute], [/mbedTLS\.dll/, mbedtls_execute]]
module_library_mapping["linux"] = [[/.*libssl\.so/, boring_execute],[/.*libgnutls\.so/, gnutls_execute],[/.*libwolfssl\.so/, wolf_execute],[/.*libnspr[0-9]?\.so/,nss_execute], [/libmbedtls\.so.*/, mbedtls_execute]]
module_library_mapping["linux"] = [[/.*libssl_sb.so/, boring_execute],[/.*libssl\.so/, boring_execute],[/.*libgnutls\.so/, gnutls_execute],[/.*libwolfssl\.so/, wolf_execute],[/.*libnspr[0-9]?\.so/,nss_execute], [/libmbedtls\.so.*/, mbedtls_execute]]
module_library_mapping["darwin"] = [[/.*libboringssl\.dylib/, boring_execute]]


Expand All @@ -51,7 +51,13 @@ if(Process.platform === "linux"){
for(let module of moduleNames){
if (regex.test(module)){
log(`${module} found & will be hooked on Linux!`)
func(module)
try{
func(module) // on some Android Apps we encounterd the problem of multiple SSL libraries but only one was used for the SSL encryption/decryption
}catch (error) {
log(`error: skipping module ${module}`)
// {'description': 'Could not find *libssl*.so!SSL_ImportFD', 'type': 'error'}
}

}
}
}
Expand Down
38 changes: 20 additions & 18 deletions friTap.py
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import frida
import argparse
import signal
Expand Down Expand Up @@ -68,15 +71,14 @@ def temp_fifo():
print(f'Failed to create FIFO: {e}')


def ssl_log(app, pcap=None, verbose=False, spawn=False, keylog=False, enable_spawn_gating=False, android=False, live=False, environment_file=None, debug_output=False):
def ssl_log(app, pcap=None, verbose=False, spawn=False, keylog=False, enable_spawn_gating=False, mobile=False, live=False, environment_file=None, debug_output=False):

def log_pcap(pcap_file, ss_family, ssl_session_id, function, src_addr, src_port,
def log_pcap(pcap_file, ss_family, function, src_addr, src_port,
dst_addr, dst_port, data):
"""Writes the captured data to a pcap file.
Args:
pcap_file: The opened pcap file.
ss_family: The family of the connection, IPv4/IPv6
ssl_session_id: The SSL session ID for the communication.
function: The function that was intercepted ("SSL_read" or "SSL_write").
src_addr: The source address of the logged packet.
src_port: The source port of the logged packet.
Expand Down Expand Up @@ -219,6 +221,9 @@ def on_message(message, data):
if p["keylog"] not in keydump_Set:
print(p["keylog"])
keydump_Set.add(p["keylog"])
if keylog:
keylog_file.write(p["keylog"] + "\n")
keylog_file.flush()
elif not data or len(data) == 0:
return
else:
Expand All @@ -245,11 +250,11 @@ def on_message(message, data):
hexdump.hexdump(data)
print()
if pcap and p["contentType"] == "datalog":
log_pcap(pcap_file, p["ss_family"], p["ssl_session_id"], p["function"], p["src_addr"],
log_pcap(pcap_file, p["ss_family"], p["function"], p["src_addr"],
p["src_port"], p["dst_addr"], p["dst_port"], data)
if live and p["contentType"] == "datalog":
try:
log_pcap(named_pipe, p["ss_family"], p["ssl_session_id"], p["function"], p["src_addr"],
log_pcap(named_pipe, p["ss_family"], p["function"], p["src_addr"],
p["src_port"], p["dst_addr"], p["dst_port"], data)
except (BrokenPipeError, IOError):
process.detach()
Expand Down Expand Up @@ -279,7 +284,7 @@ def instrument(process):
script.load()

# Main code
if android:
if mobile:
device = frida.get_usb_device()
else:
device = frida.get_local_device()
Expand All @@ -290,12 +295,11 @@ def instrument(process):
device.on("spawn_added", on_spawn_added)
if spawn:
print("spawning "+ app)
if android:
if mobile:
pid = device.spawn(app)
else:
used_env = {}
if environment_file:
#used_env = json.loads(environment)
with open(environment_file) as json_env_file:
used_env = json.load(json_env_file)
pid = device.spawn(app.split(" "),env=used_env)
Expand All @@ -314,8 +318,6 @@ def instrument(process):
print(
f'[*] Now open this named pipe with Wireshark in another terminal: sudo wireshark -k -i {fifo_file}')
print(f'[*] friTap will continue after the named pipe is ready....\n')
# input()
#named_pipe = os.open(fifo_file, os.O_WRONLY | os.O_CREAT | os.O_NONBLOCK)
named_pipe = open(fifo_file, "wb", 0)
named_pipe = write_pcap_header(named_pipe)
elif pcap:
Expand Down Expand Up @@ -358,20 +360,20 @@ def error(self, message):

parser = ArgParser(
add_help=False,
description="Decrypts and logs an executables or android applications SSL/TLS traffic.",
description="Decrypts and logs an executables or mobile applications SSL/TLS traffic.",
formatter_class=argparse.RawDescriptionHelpFormatter,
epilog=r"""
Examples:
%(prog)s -a -p ssl.pcap com.example.app
%(prog)s -a --verbose com.example.app
%(prog)s -a --pcap log.pcap --verbose com.example.app
%(prog)s -a -k keys.log -v -s com.example.app
%(prog)s -m -p ssl.pcap com.example.app
%(prog)s -m --verbose com.example.app
%(prog)s -m --pcap log.pcap --verbose com.example.app
%(prog)s -m -k keys.log -v -s com.example.app
%(prog)s --pcap log.pcap "$(which curl) https://www.google.com"
""")

args = parser.add_argument_group("Arguments")
args.add_argument("-a", "--android", required=False, action="store_const",
const=True, help="Attach to a process on android")
args.add_argument("-m", "--mobile", required=False, action="store_const",
const=True, help="Attach to a process on android or iOS")
args.add_argument("-d", "--debug", required=False, action="store_const", const=True,
help="Set the debug output of friTap")
args.add_argument("-k", "--keylog", metavar="<path>", required=False,
Expand All @@ -395,7 +397,7 @@ def error(self, message):
try:
print("Start logging")
ssl_log(parsed.exec, parsed.pcap, parsed.verbose,
parsed.spawn, parsed.keylog, parsed.enable_spawn_gating, parsed.android, parsed.live, parsed.environment, parsed.debug)
parsed.spawn, parsed.keylog, parsed.enable_spawn_gating, parsed.mobile, parsed.live, parsed.environment, parsed.debug)
except Exception as ar:
print(ar)

Expand Down
15 changes: 15 additions & 0 deletions release/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# Create release build

In order to create a standalone friTap.py script we ensure at first that the used frida Javascript is on its latest version

```bash
cd <friTap repo>
frida-compile agent/ssl_log.ts -o _ssl_log.js
```

next we invoke the `createRelease.py` script in order to create a friTap.py standalone version:
```bash
cd <friTap repo>/release
./createRelease.py
```

28 changes: 28 additions & 0 deletions release/createRelease.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import os
import stat

template_index=30
release_string="./friTap.py"

def main():
with open('../_ssl_log.js') as js_File:
frida_js_code = js_File.readlines()

with open("./friTap_release_template.py", "r") as f:
contents = f.readlines()

contents.insert(template_index, frida_js_code)

with open(release_string, "w") as f:
for lines in contents:
f.write("".join(str(line) for line in lines))

st = os.stat(release_string)
os.chmod(release_string, st.st_mode | stat.S_IEXEC)


if __name__ == "__main__":
main()
Loading

0 comments on commit 6421345

Please sign in to comment.