Skip to content

Support for the boringssl library on Android 12\13\14. #410

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Nov 10, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -195,7 +195,8 @@ TARGETS += kern/openssl_1_1_1j
TARGETS += kern/openssl_1_1_0a
TARGETS += kern/openssl_1_0_2a
TARGETS += kern/openssl_3_0_0
TARGETS += kern/boringssl_1_1_1
TARGETS += kern/boringssl_a_13
TARGETS += kern/boringssl_a_14
TARGETS += kern/bash
TARGETS += kern/gnutls
TARGETS += kern/nspr
Expand Down
10 changes: 5 additions & 5 deletions kern/boringssl_1_1_1_kern.c → kern/boringssl_a_13_kern.c
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
#ifndef ECAPTURE_BORINGSSL_1_1_1_KERN_H
#define ECAPTURE_BORINGSSL_1_1_1_KERN_H
#ifndef ECAPTURE_BORINGSSL_A_13_KERN_H
#define ECAPTURE_BORINGSSL_A_13_KERN_H

/* OPENSSL_VERSION_TEXT: OpenSSL 1.1.1 (compatible; BoringSSL) */
/* OPENSSL_VERSION_NUMBER: 269488255 */
Expand Down Expand Up @@ -28,12 +28,12 @@
// ssl_session_st->cipher
#define SSL_SESSION_ST_CIPHER 0xd0

// ssl_cipher_st->id
#define SSL_CIPHER_ST_ID 0x10

// bio_st->num
#define BIO_ST_NUM 0x18

// ssl_cipher_st->id
#define SSL_CIPHER_ST_ID 0x10

// bssl::SSL3_STATE->hs
#define BSSL__SSL3_STATE_HS 0x110

Expand Down
74 changes: 74 additions & 0 deletions kern/boringssl_a_14_kern.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
#ifndef ECAPTURE_BORINGSSL_A_14_KERN_H
#define ECAPTURE_BORINGSSL_A_14_KERN_H

/* OPENSSL_VERSION_TEXT: OpenSSL 1.1.1 (compatible; BoringSSL) */
/* OPENSSL_VERSION_NUMBER: 269488255 */

// ssl_st->version
#define SSL_ST_VERSION 0x10

// ssl_st->session
#define SSL_ST_SESSION 0x58

// ssl_st->rbio
#define SSL_ST_RBIO 0x18

// ssl_st->wbio
#define SSL_ST_WBIO 0x20

// ssl_st->s3
#define SSL_ST_S3 0x30

// ssl_session_st->secret_length
#define SSL_SESSION_ST_SECRET_LENGTH 0xa

// ssl_session_st->secret
#define SSL_SESSION_ST_SECRET 0xb

// ssl_session_st->cipher
#define SSL_SESSION_ST_CIPHER 0xc8

// bio_st->num
#define BIO_ST_NUM 0x18

// ssl_cipher_st->id
#define SSL_CIPHER_ST_ID 0x10

// bssl::SSL3_STATE->hs
#define BSSL__SSL3_STATE_HS 0x118

// bssl::SSL3_STATE->client_random
#define BSSL__SSL3_STATE_CLIENT_RANDOM 0x30

// bssl::SSL3_STATE->exporter_secret
#define BSSL__SSL3_STATE_EXPORTER_SECRET 0x180

// bssl::SSL3_STATE->established_session
#define BSSL__SSL3_STATE_ESTABLISHED_SESSION 0x1d0

// bssl::SSL_HANDSHAKE->new_session
#define BSSL__SSL_HANDSHAKE_NEW_SESSION 0x5f0

// bssl::SSL_HANDSHAKE->early_session
#define BSSL__SSL_HANDSHAKE_EARLY_SESSION 0x5f8

// bssl::SSL_HANDSHAKE->hints
#define BSSL__SSL_HANDSHAKE_HINTS 0x628

// bssl::SSL_HANDSHAKE->client_version
#define BSSL__SSL_HANDSHAKE_CLIENT_VERSION 0x634

// bssl::SSL_HANDSHAKE->state
#define BSSL__SSL_HANDSHAKE_STATE 0x14

// bssl::SSL_HANDSHAKE->tls13_state
#define BSSL__SSL_HANDSHAKE_TLS13_STATE 0x18

// bssl::SSL_HANDSHAKE->max_version
#define BSSL__SSL_HANDSHAKE_MAX_VERSION 0x1e

#include "boringssl_const.h"
#include "boringssl_masterkey.h"
#include "openssl.h"

#endif
1 change: 1 addition & 0 deletions user/config/config_openssl.go
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ type OpensslConfig struct {
CGroupPath string `json:"CGroupPath"` // cgroup path, used for filter process
ElfType uint8 //
IsAndroid bool // is Android OS ?
AndroidVer string // Android OS version
}

func NewOpensslConfig() *OpensslConfig {
Expand Down
27 changes: 23 additions & 4 deletions user/config/config_openssl_androidgki.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,18 +18,21 @@
package config

import (
"bufio"
"os"
"strings"
)

const (
DefaultOpensslPath = "/apex/com.android.conscrypt/lib64/libssl.so"
DEFAULT_LIBC_PATH = "/apex/com.android.runtime/lib64/bionic/libc.so"

DefaultIfname = "wlan0"
DefaultLibcPath = "/apex/com.android.runtime/lib64/bionic/libc.so"
BuildPropPath = "/system/build.prop"
ReleasePrefix = "ro.build.version.release="
DefaultIfname = "wlan0"
)

func (oc *OpensslConfig) Check() error {
oc.AndroidVer = "12"
oc.IsAndroid = true
// 如果readline 配置,且存在,则直接返回。
if oc.Openssl != "" || len(strings.TrimSpace(oc.Openssl)) > 0 {
Expand All @@ -49,11 +52,27 @@ func (oc *OpensslConfig) Check() error {
return e
}
} else {
oc.Pthread = DEFAULT_LIBC_PATH
oc.Pthread = DefaultLibcPath
}

if oc.Ifname == "" || len(strings.TrimSpace(oc.Ifname)) == 0 {
oc.Ifname = DefaultIfname
}

f, err := os.Open(BuildPropPath)
if err != nil {
return nil
}
defer f.Close()

// detect android version (use Android version?), and set AndroidVer
sc := bufio.NewScanner(f)
for sc.Scan() {
line := sc.Text()
if strings.HasPrefix(line, ReleasePrefix) {
oc.AndroidVer = strings.TrimSpace(strings.TrimPrefix(line, ReleasePrefix))
break
}
}
return nil
}
19 changes: 0 additions & 19 deletions user/config/config_openssl_linux.go
Original file line number Diff line number Diff line change
Expand Up @@ -156,26 +156,7 @@ func (oc *OpensslConfig) Check() error {
oc.ElfType = ElfTypeSo
checkedOpenssl = true
}
/*
//如果配置 Curlpath的地址,判断文件是否存在,不存在则直接返回
if oc.Curlpath != "" || len(strings.TrimSpace(oc.Curlpath)) > 0 {
_, e := os.Stat(oc.Curlpath)
if e != nil {
return e
}
} else {
//如果没配置,则直接指定。
oc.Curlpath = "/usr/bin/curl"
}

if oc.Pthread != "" || len(strings.TrimSpace(oc.Pthread)) > 0 {
_, e := os.Stat(oc.Pthread)
if e != nil {
return e
}
checkedConnect = true
}
*/
if oc.Ifname == "" || len(strings.TrimSpace(oc.Ifname)) == 0 {
oc.Ifname = DefaultIfname
}
Expand Down
22 changes: 18 additions & 4 deletions user/module/probe_openssl_lib.go
Original file line number Diff line number Diff line change
Expand Up @@ -55,8 +55,10 @@ func (m *MOpenSSLProbe) initOpensslOffset() {
LinuxDefauleFilename_3_0: "openssl_3_0_0_kern.o",

// boringssl
"boringssl 1.1.1": "boringssl_1_1_1_kern.o",
AndroidDefauleFilename: "boringssl_1_1_1_kern.o",
"boringssl 1.1.1": "boringssl_a_13_kern.o",
"boringssl_a_13": "boringssl_a_13_kern.o",
"boringssl_a_14": "boringssl_a_14_kern.o",
AndroidDefauleFilename: "boringssl_a_13_kern.o",
}

// in openssl source files, there are 4 offset groups for all 1.1.1* version.
Expand Down Expand Up @@ -192,10 +194,22 @@ func (m *MOpenSSLProbe) detectOpenssl(soPath string) error {
}

isAndroid := m.conf.(*config.OpensslConfig).IsAndroid
androidVer := m.conf.(*config.OpensslConfig).AndroidVer
// if not found, use default
if isAndroid {
bpfFile, _ = m.sslVersionBpfMap[AndroidDefauleFilename]
m.logger.Printf("%s\tOpenSSL/BoringSSL version not found, used default version :%s\n", m.Name(), AndroidDefauleFilename)
// sometimes,boringssl version always was "boringssl 1.1.1" on android. but offsets are different.
// see kern/boringssl_a_13_kern.c and kern/boringssl_a_14_kern.c
// Perhaps we can utilize the Android Version to choose a specific version of boringssl.
// use the corresponding bpfFile
bpfFildAndroid := fmt.Sprintf("boringssl_a_%s", androidVer)
bpfFile, found = m.sslVersionBpfMap[bpfFildAndroid]
if found {
m.sslBpfFile = bpfFile
m.logger.Printf("%s\tOpenSSL/BoringSSL version found, ro.build.version.release=%s\n", m.Name(), androidVer)
} else {
bpfFile, _ = m.sslVersionBpfMap[AndroidDefauleFilename]
m.logger.Printf("%s\tOpenSSL/BoringSSL version not found, used default version :%s\n", m.Name(), AndroidDefauleFilename)
}
} else {
if strings.Contains(soPath, "libssl.so.3") {
bpfFile, _ = m.sslVersionBpfMap[LinuxDefauleFilename_3_0]
Expand Down
Original file line number Diff line number Diff line change
@@ -1,20 +1,9 @@
#!/usr/bin/env bash
set -e


echo $NON_ANDROID

PROJECT_ROOT_DIR=$(pwd)
BORINGSSL_REPO=https://android.googlesource.com/platform/external/boringssl
BORINGSSL_DIR="${PROJECT_ROOT_DIR}/deps/boringssl"

NON_ANDROID=0
if [[ $1 == 1 ]] ; then
BORINGSSL_REPO=https://github.com/google/boringssl.git
BORINGSSL_DIR="${PROJECT_ROOT_DIR}/deps/boringssl_non_android"
NON_ANDROID=1
fi

OUTPUT_DIR="${PROJECT_ROOT_DIR}/kern"

if [[ ! -f "go.mod" ]]; then
Expand All @@ -26,7 +15,6 @@ fi
if [[ ! -d "${BORINGSSL_DIR}/.git" ]]; then
# skip cloning if the openssl directory already exists
if [[ ! -d "${BORINGSSL_DIR}" ]]; then
# git clone https://github.com/google/boringssl.git ${BORINGSSL_DIR}
git clone ${BORINGSSL_REPO} ${BORINGSSL_DIR}
fi
fi
Expand All @@ -39,22 +27,23 @@ function run() {
# see https://android.googlesource.com/platform/external/boringssl/+/refs/heads/android12-release .
# range commit id from 160e1757ccacbde7488b145070eca94f2c370de2
# this repo is different from https://boringssl.googlesource.com/boringssl
sslVerMap["0"]="0"
sslVerMap["1"]="13" # android13-release
sslVerMap["2"]="14" # android14-release

# shellcheck disable=SC2068
# shellcheck disable=SC2034
for ver in ${!sslVerMap[@]}; do
# tag="openssl-3.0.${ver}"
# val=${sslVerMap[$ver]}
header_file="${OUTPUT_DIR}/boringssl_1_1_1_kern.c"
header_define="BORINGSSL_1_1_1_KERN_H"
val=${sslVerMap[$ver]}
tag="android${val}-release"

header_file="${OUTPUT_DIR}/boringssl_a_${val}_kern.c"
header_define="BORINGSSL_A_${val}_KERN_H"

if [[ -f ${header_file} ]]; then
echo "Skip ${header_file}"
continue
fi

# git checkout ${tag}
git checkout ${tag}
echo "Generating ${header_file}"

g++ -Wno-write-strings -Wno-invalid-offsetof -I include/ -I . -I ./src/ offset.c -o offset
Expand Down
64 changes: 64 additions & 0 deletions utils/boringssl_non_android_offset.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
#!/usr/bin/env bash
set -e

# for non android boringssl , git repo : https://github.com/google/boringssl
BORINGSSL_REPO=https://github.com/google/boringssl.git
BORINGSSL_DIR="${PROJECT_ROOT_DIR}/deps/boringssl_non_android"
OUTPUT_DIR="${PROJECT_ROOT_DIR}/kern"

if [[ ! -f "go.mod" ]]; then
echo "non-Android lib, Run the script from the project root directory"
exit 1
fi

# skip cloning if the header file of the max supported version is already generated
if [[ ! -d "${BORINGSSL_DIR}/.git" ]]; then
# skip cloning if the openssl directory already exists
if [[ ! -d "${BORINGSSL_DIR}" ]]; then
git clone ${BORINGSSL_REPO} ${BORINGSSL_DIR}
fi
fi

function run() {
git fetch --tags
cp -f ${PROJECT_ROOT_DIR}/utils/boringssl-offset.c ${BORINGSSL_DIR}/offset.c
declare -A sslVerMap=()
sslVerMap["0"]="12" # android12-release
sslVerMap["1"]="13" # android13-release
sslVerMap["2"]="14" # android14-release

# shellcheck disable=SC2068
# shellcheck disable=SC2034
for ver in ${!sslVerMap[@]}; do
tag="android${ver}-release"
val=${sslVerMap[$ver]}

header_file="${OUTPUT_DIR}/boringssl_na_kern.c"
header_define="BORINGSSL_NA_KERN_H"

if [[ -f ${header_file} ]]; then
echo "Skip ${header_file}"
continue
fi
git checkout ${tag}
echo "Generating ${header_file}"

g++ -Wno-write-strings -Wno-invalid-offsetof -I include/ -I . -I ./src/ offset.c -o offset

echo -e "#ifndef ECAPTURE_${header_define}" >${header_file}
echo -e "#define ECAPTURE_${header_define}\n" >>${header_file}
./offset >>${header_file}
echo -e "#include \"boringssl_const.h\"" >>${header_file}
echo -e "#include \"boringssl_masterkey.h\"" >>${header_file}
echo -e "#include \"openssl.h\"" >>${header_file}
echo -e "\n#endif" >>${header_file}

done

rm offset.c
}

pushd ${BORINGSSL_DIR}
(run)
[[ "$?" != 0 ]] && popd
popd