Improve Go TLS address availability (#1207)

Fetch source and destination addresses with bpf from tcp kprobes, similar to how it is done for openssl lib.
Chunk contains both source address and destination address.
FD is no longer used to obtain addresses.
This commit is contained in:
Nimrod Gilboa Markevich 2022-07-19 14:31:27 +03:00 committed by GitHub
parent 5525214d0a
commit 692c500b0f
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
17 changed files with 389 additions and 460 deletions

View File

@ -16,34 +16,16 @@ static __always_inline int add_address_to_chunk(struct pt_regs *ctx, struct tls_
__u32 pid = id >> 32;
__u64 key = (__u64) pid << 32 | fd;
struct fd_info *fdinfo = bpf_map_lookup_elem(&file_descriptor_to_ipv4, &key);
conn_flags *flags = bpf_map_lookup_elem(&connection_context, &key);
if (fdinfo == NULL) {
// Happens when we don't catch the connect / accept (if the connection is created before tapping is started)
if (flags == NULL) {
return 0;
}
int err;
chunk->flags |= (*flags & FLAGS_IS_CLIENT_BIT);
switch (info->address_info.mode) {
case ADDRESS_INFO_MODE_UNDEFINED:
chunk->address_info.mode = ADDRESS_INFO_MODE_SINGLE;
err = bpf_probe_read(&chunk->address_info.sport, sizeof(chunk->address_info.sport), &fdinfo->ipv4_addr[2]);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_FD_ADDRESS, id, err, 0l);
return 0;
}
err = bpf_probe_read(&chunk->address_info.saddr, sizeof(chunk->address_info.saddr), &fdinfo->ipv4_addr[4]);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_FD_ADDRESS, id, err, 0l);
return 0;
}
break;
default:
bpf_probe_read(&chunk->address_info, sizeof(chunk->address_info), &info->address_info);
}
chunk->flags |= (fdinfo->flags & FLAGS_IS_CLIENT_BIT);
bpf_probe_read(&chunk->address_info, sizeof(chunk->address_info), &info->address_info);
return 1;
}

View File

@ -14,7 +14,6 @@ Copyright (C) UP9 Inc.
#define IPV4_ADDR_LEN (16)
struct accept_info {
__u64* sockaddr;
__u32* addrlen;
};
@ -39,7 +38,6 @@ void sys_enter_accept4(struct sys_enter_accept4_ctx *ctx) {
struct accept_info info = {};
info.sockaddr = ctx->sockaddr;
info.addrlen = ctx->addrlen;
long err = bpf_map_update_elem(&accept_syscall_context, &id, &info, BPF_ANY);
@ -94,26 +92,21 @@ void sys_exit_accept4(struct sys_exit_accept4_ctx *ctx) {
return;
}
struct fd_info fdinfo = {
.flags = 0
};
bpf_probe_read(fdinfo.ipv4_addr, sizeof(fdinfo.ipv4_addr), info.sockaddr);
conn_flags flags = 0;
__u32 pid = id >> 32;
__u32 fd = (__u32) ctx->ret;
__u64 key = (__u64) pid << 32 | fd;
err = bpf_map_update_elem(&file_descriptor_to_ipv4, &key, &fdinfo, BPF_ANY);
err = bpf_map_update_elem(&connection_context, &key, &flags, BPF_ANY);
if (err != 0) {
log_error(ctx, LOG_ERROR_PUTTING_FD_MAPPING, id, err, ORIGIN_SYS_EXIT_ACCEPT4_CODE);
log_error(ctx, LOG_ERROR_PUTTING_CONNECTION_CONTEXT, id, err, ORIGIN_SYS_EXIT_ACCEPT4_CODE);
}
}
struct connect_info {
__u64 fd;
__u64* sockaddr;
__u32 addrlen;
};
@ -138,7 +131,6 @@ void sys_enter_connect(struct sys_enter_connect_ctx *ctx) {
struct connect_info info = {};
info.sockaddr = ctx->sockaddr;
info.addrlen = ctx->addrlen;
info.fd = ctx->fd;
@ -193,19 +185,15 @@ void sys_exit_connect(struct sys_exit_connect_ctx *ctx) {
return;
}
struct fd_info fdinfo = {
.flags = FLAGS_IS_CLIENT_BIT
};
bpf_probe_read(fdinfo.ipv4_addr, sizeof(fdinfo.ipv4_addr), info.sockaddr);
conn_flags flags = FLAGS_IS_CLIENT_BIT;
__u32 pid = id >> 32;
__u32 fd = (__u32) info.fd;
__u64 key = (__u64) pid << 32 | fd;
err = bpf_map_update_elem(&file_descriptor_to_ipv4, &key, &fdinfo, BPF_ANY);
err = bpf_map_update_elem(&connection_context, &key, &flags, BPF_ANY);
if (err != 0) {
log_error(ctx, LOG_ERROR_PUTTING_FD_MAPPING, id, err, ORIGIN_SYS_EXIT_CONNECT_CODE);
log_error(ctx, LOG_ERROR_PUTTING_CONNECTION_CONTEXT, id, err, ORIGIN_SYS_EXIT_CONNECT_CODE);
}
}

View File

@ -10,8 +10,9 @@ Copyright (C) UP9 Inc.
#include "include/log.h"
#include "include/logger_messages.h"
#include "include/pids.h"
#include "include/common.h"
struct sys_enter_read_ctx {
struct sys_enter_read_write_ctx {
__u64 __unused_syscall_header;
__u32 __unused_syscall_nr;
@ -20,8 +21,46 @@ struct sys_enter_read_ctx {
__u64 count;
};
struct sys_exit_read_write_ctx {
__u64 __unused_syscall_header;
__u32 __unused_syscall_nr;
__u64 ret;
};
static __always_inline void fd_tracepoints_handle_openssl(struct sys_enter_read_write_ctx *ctx, __u64 id, struct ssl_info *infoPtr, struct bpf_map_def *map_fd, __u64 origin_code) {
struct ssl_info info;
long err = bpf_probe_read(&info, sizeof(struct ssl_info), infoPtr);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_SSL_CONTEXT, id, err, origin_code);
return;
}
info.fd = ctx->fd;
err = bpf_map_update_elem(map_fd, &id, &info, BPF_ANY);
if (err != 0) {
log_error(ctx, LOG_ERROR_PUTTING_FILE_DESCRIPTOR, id, err, origin_code);
return;
}
}
static __always_inline void fd_tracepoints_handle_go(struct sys_enter_read_write_ctx *ctx, __u64 id, struct bpf_map_def *map_fd, __u64 origin_code) {
__u32 fd = ctx->fd;
long err = bpf_map_update_elem(map_fd, &id, &fd, BPF_ANY);
if (err != 0) {
log_error(ctx, LOG_ERROR_PUTTING_FILE_DESCRIPTOR, id, err, origin_code);
return;
}
}
SEC("tracepoint/syscalls/sys_enter_read")
void sys_enter_read(struct sys_enter_read_ctx *ctx) {
void sys_enter_read(struct sys_enter_read_write_ctx *ctx) {
__u64 id = bpf_get_current_pid_tgid();
if (!should_tap(id >> 32)) {
@ -30,38 +69,15 @@ void sys_enter_read(struct sys_enter_read_ctx *ctx) {
struct ssl_info *infoPtr = bpf_map_lookup_elem(&openssl_read_context, &id);
if (infoPtr == NULL) {
return;
}
struct ssl_info info;
long err = bpf_probe_read(&info, sizeof(struct ssl_info), infoPtr);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_SSL_CONTEXT, id, err, ORIGIN_SYS_ENTER_READ_CODE);
return;
}
info.fd = ctx->fd;
err = bpf_map_update_elem(&openssl_read_context, &id, &info, BPF_ANY);
if (err != 0) {
log_error(ctx, LOG_ERROR_PUTTING_FILE_DESCRIPTOR, id, err, ORIGIN_SYS_ENTER_READ_CODE);
if (infoPtr != NULL) {
fd_tracepoints_handle_openssl(ctx, id, infoPtr, &openssl_read_context, ORIGIN_SYS_ENTER_READ_CODE);
}
fd_tracepoints_handle_go(ctx, id, &go_kernel_read_context, ORIGIN_SYS_ENTER_READ_CODE);
}
struct sys_enter_write_ctx {
__u64 __unused_syscall_header;
__u32 __unused_syscall_nr;
__u64 fd;
__u64* buf;
__u64 count;
};
SEC("tracepoint/syscalls/sys_enter_write")
void sys_enter_write(struct sys_enter_write_ctx *ctx) {
void sys_enter_write(struct sys_enter_read_write_ctx *ctx) {
__u64 id = bpf_get_current_pid_tgid();
if (!should_tap(id >> 32)) {
@ -70,23 +86,25 @@ void sys_enter_write(struct sys_enter_write_ctx *ctx) {
struct ssl_info *infoPtr = bpf_map_lookup_elem(&openssl_write_context, &id);
if (infoPtr == NULL) {
return;
}
struct ssl_info info;
long err = bpf_probe_read(&info, sizeof(struct ssl_info), infoPtr);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_SSL_CONTEXT, id, err, ORIGIN_SYS_ENTER_WRITE_CODE);
return;
}
info.fd = ctx->fd;
err = bpf_map_update_elem(&openssl_write_context, &id, &info, BPF_ANY);
if (err != 0) {
log_error(ctx, LOG_ERROR_PUTTING_FILE_DESCRIPTOR, id, err, ORIGIN_SYS_ENTER_WRITE_CODE);
if (infoPtr != NULL) {
fd_tracepoints_handle_openssl(ctx, id, infoPtr, &openssl_write_context, ORIGIN_SYS_ENTER_WRITE_CODE);
}
fd_tracepoints_handle_go(ctx, id, &go_kernel_write_context, ORIGIN_SYS_ENTER_WRITE_CODE);
}
SEC("tracepoint/syscalls/sys_exit_read")
void sys_exit_read(struct sys_exit_read_write_ctx *ctx) {
__u64 id = bpf_get_current_pid_tgid();
// Delete from go map. The value is not used after exiting this syscall.
// Keep value in openssl map.
bpf_map_delete_elem(&go_kernel_read_context, &id);
}
SEC("tracepoint/syscalls/sys_exit_write")
void sys_exit_write(struct sys_exit_read_write_ctx *ctx) {
__u64 id = bpf_get_current_pid_tgid();
// Delete from go map. The value is not used after exiting this syscall.
// Keep value in openssl map.
bpf_map_delete_elem(&go_kernel_write_context, &id);
}

View File

@ -220,7 +220,7 @@ static __always_inline void go_crypto_tls_uprobe(struct pt_regs *ctx, struct bpf
return;
}
static __always_inline void go_crypto_tls_ex_uprobe(struct pt_regs *ctx, struct bpf_map_def* go_context, __u32 flags, enum ABI abi) {
static __always_inline void go_crypto_tls_ex_uprobe(struct pt_regs *ctx, struct bpf_map_def* go_context, struct bpf_map_def* go_user_kernel_context, __u32 flags, enum ABI abi) {
__u64 pid_tgid = bpf_get_current_pid_tgid();
__u64 pid = pid_tgid >> 32;
if (!should_tap(pid)) {
@ -285,6 +285,21 @@ static __always_inline void go_crypto_tls_ex_uprobe(struct pt_regs *ctx, struct
}
}
__u64 key = (__u64) pid << 32 | info_ptr->fd;
struct address_info *address_info = bpf_map_lookup_elem(go_user_kernel_context, &key);
// Ideally we would delete the entry from the map after reading it,
// but sometimes the uprobe is called twice in a row without the tcp kprobes in between to fill in
// the entry again. Keeping it in the map and rely on LRU logic.
if (address_info == NULL) {
log_error(ctx, LOG_ERROR_GETTING_GO_USER_KERNEL_CONTEXT, pid_tgid, info_ptr->fd, err);
return;
}
info.address_info.daddr = address_info->daddr;
info.address_info.dport = address_info->dport;
info.address_info.saddr = address_info->saddr;
info.address_info.sport = address_info->sport;
output_ssl_chunk(ctx, &info, info.buffer_len, pid_tgid, flags);
return;
@ -298,7 +313,7 @@ int BPF_KPROBE(go_crypto_tls_abi0_write) {
SEC("uprobe/go_crypto_tls_abi0_write_ex")
int BPF_KPROBE(go_crypto_tls_abi0_write_ex) {
go_crypto_tls_ex_uprobe(ctx, &go_write_context, 0, ABI0);
go_crypto_tls_ex_uprobe(ctx, &go_write_context, &go_user_kernel_write_context, 0, ABI0);
return 1;
}
@ -310,7 +325,7 @@ int BPF_KPROBE(go_crypto_tls_abi0_read) {
SEC("uprobe/go_crypto_tls_abi0_read_ex")
int BPF_KPROBE(go_crypto_tls_abi0_read_ex) {
go_crypto_tls_ex_uprobe(ctx, &go_read_context, FLAGS_IS_READ_BIT, ABI0);
go_crypto_tls_ex_uprobe(ctx, &go_read_context, &go_user_kernel_read_context, FLAGS_IS_READ_BIT, ABI0);
return 1;
}
@ -322,7 +337,7 @@ int BPF_KPROBE(go_crypto_tls_abi_internal_write) {
SEC("uprobe/go_crypto_tls_abi_internal_write_ex")
int BPF_KPROBE(go_crypto_tls_abi_internal_write_ex) {
go_crypto_tls_ex_uprobe(ctx, &go_write_context, 0, ABIInternal);
go_crypto_tls_ex_uprobe(ctx, &go_write_context, &go_user_kernel_write_context, 0, ABIInternal);
return 1;
}
@ -334,6 +349,6 @@ int BPF_KPROBE(go_crypto_tls_abi_internal_read) {
SEC("uprobe/go_crypto_tls_abi_internal_read_ex")
int BPF_KPROBE(go_crypto_tls_abi_internal_read_ex) {
go_crypto_tls_ex_uprobe(ctx, &go_read_context, FLAGS_IS_READ_BIT, ABIInternal);
go_crypto_tls_ex_uprobe(ctx, &go_read_context, &go_user_kernel_read_context, FLAGS_IS_READ_BIT, ABIInternal);
return 1;
}

View File

@ -10,27 +10,28 @@ Copyright (C) UP9 Inc.
// Must be synced with bpf_logger_messages.go
//
#define LOG_ERROR_READING_BYTES_COUNT (0)
#define LOG_ERROR_READING_FD_ADDRESS (1)
#define LOG_ERROR_READING_FROM_SSL_BUFFER (2)
#define LOG_ERROR_BUFFER_TOO_BIG (3)
#define LOG_ERROR_ALLOCATING_CHUNK (4)
#define LOG_ERROR_READING_SSL_CONTEXT (5)
#define LOG_ERROR_PUTTING_SSL_CONTEXT (6)
#define LOG_ERROR_GETTING_SSL_CONTEXT (7)
#define LOG_ERROR_MISSING_FILE_DESCRIPTOR (8)
#define LOG_ERROR_PUTTING_FILE_DESCRIPTOR (9)
#define LOG_ERROR_PUTTING_ACCEPT_INFO (10)
#define LOG_ERROR_GETTING_ACCEPT_INFO (11)
#define LOG_ERROR_READING_ACCEPT_INFO (12)
#define LOG_ERROR_PUTTING_FD_MAPPING (13)
#define LOG_ERROR_PUTTING_CONNECT_INFO (14)
#define LOG_ERROR_GETTING_CONNECT_INFO (15)
#define LOG_ERROR_READING_CONNECT_INFO (16)
#define LOG_ERROR_READING_SOCKET_FAMILY (17)
#define LOG_ERROR_READING_SOCKET_DADDR (18)
#define LOG_ERROR_READING_SOCKET_SADDR (19)
#define LOG_ERROR_READING_SOCKET_DPORT (20)
#define LOG_ERROR_READING_SOCKET_SPORT (21)
#define LOG_ERROR_READING_FROM_SSL_BUFFER (1)
#define LOG_ERROR_BUFFER_TOO_BIG (2)
#define LOG_ERROR_ALLOCATING_CHUNK (3)
#define LOG_ERROR_READING_SSL_CONTEXT (4)
#define LOG_ERROR_PUTTING_SSL_CONTEXT (5)
#define LOG_ERROR_GETTING_SSL_CONTEXT (6)
#define LOG_ERROR_MISSING_FILE_DESCRIPTOR (7)
#define LOG_ERROR_PUTTING_FILE_DESCRIPTOR (8)
#define LOG_ERROR_PUTTING_ACCEPT_INFO (9)
#define LOG_ERROR_GETTING_ACCEPT_INFO (10)
#define LOG_ERROR_READING_ACCEPT_INFO (11)
#define LOG_ERROR_PUTTING_CONNECTION_CONTEXT (12)
#define LOG_ERROR_PUTTING_CONNECT_INFO (13)
#define LOG_ERROR_GETTING_CONNECT_INFO (14)
#define LOG_ERROR_READING_CONNECT_INFO (15)
#define LOG_ERROR_READING_SOCKET_FAMILY (16)
#define LOG_ERROR_READING_SOCKET_DADDR (17)
#define LOG_ERROR_READING_SOCKET_SADDR (18)
#define LOG_ERROR_READING_SOCKET_DPORT (19)
#define LOG_ERROR_READING_SOCKET_SPORT (20)
#define LOG_ERROR_PUTTING_GO_USER_KERNEL_CONTEXT (21)
#define LOG_ERROR_GETTING_GO_USER_KERNEL_CONTEXT (22)
// Sometimes we have the same error, happening from different locations.
// in order to be able to distinct between them in the log, we add an

View File

@ -25,14 +25,7 @@ Copyright (C) UP9 Inc.
// Be careful when editing, alignment and padding should be exactly the same in go/c.
//
typedef enum {
ADDRESS_INFO_MODE_UNDEFINED,
ADDRESS_INFO_MODE_SINGLE,
ADDRESS_INFO_MODE_PAIR,
} address_info_mode;
struct address_info {
address_info_mode mode;
__be32 saddr;
__be32 daddr;
__be16 sport;
@ -64,10 +57,7 @@ struct ssl_info {
size_t *count_ptr;
};
struct fd_info {
__u8 ipv4_addr[16]; // struct sockaddr (linux-src/include/linux/socket.h)
__u8 flags;
};
typedef __u8 conn_flags;
struct goid_offsets {
__u64 g_addr_offset;
@ -105,7 +95,7 @@ struct {
// Generic
BPF_HASH(pids_map, __u32, __u32);
BPF_LRU_HASH(file_descriptor_to_ipv4, __u64, struct fd_info);
BPF_LRU_HASH(connection_context, __u64, conn_flags);
BPF_PERF_OUTPUT(chunks_buffer);
BPF_PERF_OUTPUT(log_buffer);
@ -117,5 +107,9 @@ BPF_LRU_HASH(openssl_read_context, __u64, struct ssl_info);
BPF_HASH(goid_offsets_map, __u32, struct goid_offsets);
BPF_LRU_HASH(go_write_context, __u64, struct ssl_info);
BPF_LRU_HASH(go_read_context, __u64, struct ssl_info);
BPF_LRU_HASH(go_kernel_write_context, __u64, __u32);
BPF_LRU_HASH(go_kernel_read_context, __u64, __u32);
BPF_LRU_HASH(go_user_kernel_write_context, __u64, struct address_info);
BPF_LRU_HASH(go_user_kernel_read_context, __u64, struct address_info);
#endif /* __MAPS__ */

View File

@ -5,32 +5,19 @@
#include "include/pids.h"
#include "include/common.h"
static __always_inline void tcp_kprobe(struct pt_regs *ctx, struct bpf_map_def *map_fd, _Bool is_send) {
static __always_inline int tcp_kprobes_get_address_pair_from_ctx(struct pt_regs *ctx, __u64 id, struct address_info *address_info_ptr) {
long err;
__u64 id = bpf_get_current_pid_tgid();
__u32 pid = id >> 32;
if (!should_tap(id >> 32)) {
return;
}
struct ssl_info *info_ptr = bpf_map_lookup_elem(map_fd, &id);
// Happens when the connection is not tls
if (info_ptr == NULL) {
return;
}
struct sock *sk = (struct sock *) PT_REGS_PARM1(ctx);
short unsigned int family;
err = bpf_probe_read(&family, sizeof(family), (void *)&sk->__sk_common.skc_family);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_SOCKET_FAMILY, id, err, 0l);
return;
return -1;
}
if (family != AF_INET) {
return;
return -1;
}
// daddr, saddr and dport are in network byte order (big endian)
@ -43,37 +30,89 @@ static __always_inline void tcp_kprobe(struct pt_regs *ctx, struct bpf_map_def *
err = bpf_probe_read(&saddr, sizeof(saddr), (void *)&sk->__sk_common.skc_rcv_saddr);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_SOCKET_SADDR, id, err, 0l);
return;
return -1;
}
err = bpf_probe_read(&daddr, sizeof(daddr), (void *)&sk->__sk_common.skc_daddr);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_SOCKET_DADDR, id, err, 0l);
return;
return -1;
}
err = bpf_probe_read(&dport, sizeof(dport), (void *)&sk->__sk_common.skc_dport);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_SOCKET_DPORT, id, err, 0l);
return;
return -1;
}
err = bpf_probe_read(&sport, sizeof(sport), (void *)&sk->__sk_common.skc_num);
if (err != 0) {
log_error(ctx, LOG_ERROR_READING_SOCKET_SPORT, id, err, 0l);
return -1;
}
address_info_ptr->daddr = daddr;
address_info_ptr->saddr = saddr;
address_info_ptr->dport = dport;
address_info_ptr->sport = bpf_htons(sport);
return 0;
}
static __always_inline void tcp_kprobes_forward_go(struct pt_regs *ctx, __u64 id, __u32 fd, struct address_info address_info, struct bpf_map_def *map_fd_go_user_kernel) {
__u32 pid = id >> 32;
__u64 key = (__u64) pid << 32 | fd;
long err = bpf_map_update_elem(map_fd_go_user_kernel, &key, &address_info, BPF_ANY);
if (err != 0) {
log_error(ctx, LOG_ERROR_PUTTING_GO_USER_KERNEL_CONTEXT, id, fd, err);
return;
}
}
static void __always_inline tcp_kprobes_forward_openssl(struct ssl_info *info_ptr, struct address_info address_info) {
info_ptr->address_info.daddr = address_info.daddr;
info_ptr->address_info.saddr = address_info.saddr;
info_ptr->address_info.dport = address_info.dport;
info_ptr->address_info.sport = address_info.sport;
}
static __always_inline void tcp_kprobe(struct pt_regs *ctx, struct bpf_map_def *map_fd_openssl, struct bpf_map_def *map_fd_go_kernel, struct bpf_map_def *map_fd_go_user_kernel) {
long err;
__u64 id = bpf_get_current_pid_tgid();
if (!should_tap(id >> 32)) {
return;
}
info_ptr->address_info.mode = ADDRESS_INFO_MODE_PAIR;
info_ptr->address_info.daddr = daddr;
info_ptr->address_info.saddr = saddr;
info_ptr->address_info.dport = dport;
info_ptr->address_info.sport = bpf_htons(sport);
struct address_info address_info;
if (0 != tcp_kprobes_get_address_pair_from_ctx(ctx, id, &address_info)) {
return;
}
struct ssl_info *info_ptr = bpf_map_lookup_elem(map_fd_openssl, &id);
__u32 *fd_ptr;
if (info_ptr == NULL) {
fd_ptr = bpf_map_lookup_elem(map_fd_go_kernel, &id);
// Connection is used by a Go program
if (fd_ptr == NULL) {
// Connection was not created by a Go program or by openssl lib
return;
}
tcp_kprobes_forward_go(ctx, id, *fd_ptr, address_info, map_fd_go_user_kernel);
} else {
// Connection is used by openssl lib
tcp_kprobes_forward_openssl(info_ptr, address_info);
}
}
SEC("kprobe/tcp_sendmsg")
void BPF_KPROBE(tcp_sendmsg) {
tcp_kprobe(ctx, &openssl_write_context, true);
__u64 id = bpf_get_current_pid_tgid();
tcp_kprobe(ctx, &openssl_write_context, &go_kernel_write_context, &go_user_kernel_write_context);
}
SEC("kprobe/tcp_recvmsg")
void BPF_KPROBE(tcp_recvmsg) {
tcp_kprobe(ctx, &openssl_read_context, false);
__u64 id = bpf_get_current_pid_tgid();
tcp_kprobe(ctx, &openssl_read_context, &go_kernel_read_context, &go_user_kernel_read_context);
}

View File

@ -4,25 +4,26 @@ package tlstapper
//
var bpfLogMessages = []string{
/*0000*/ "[%d] Unable to read bytes count from _ex methods [err: %d]",
/*0001*/ "[%d] Unable to read ipv4 address [err: %d]",
/*0002*/ "[%d] Unable to read ssl buffer [err: %d]",
/*0003*/ "[%d] Buffer is too big [size: %d]",
/*0004*/ "[%d] Unable to allocate chunk in bpf heap",
/*0005*/ "[%d] Unable to read ssl context [err: %d] [origin: %d]",
/*0006*/ "[%d] Unable to put ssl context [err: %d]",
/*0007*/ "[%d] Unable to get ssl context",
/*0008*/ "[%d] File descriptor is missing for tls chunk",
/*0009*/ "[%d] Unable to put file descriptor [err: %d] [origin: %d]",
/*0010*/ "[%d] Unable to put accept info [err: %d]",
/*0011*/ "[%d] Unable to get accept info",
/*0012*/ "[%d] Unable to read accept info [err: %d]",
/*0013*/ "[%d] Unable to put file descriptor to address mapping [err: %d] [origin: %d]",
/*0014*/ "[%d] Unable to put connect info [err: %d]",
/*0015*/ "[%d] Unable to get connect info",
/*0016*/ "[%d] Unable to read connect info [err: %d]",
/*0017*/ "[%d] Unable to read socket family [err: %d]",
/*0018*/ "[%d] Unable to read socket daddr [err: %d]",
/*0019*/ "[%d] Unable to read socket saddr [err: %d]",
/*0001*/ "[%d] Unable to read ssl buffer [err: %d] [origin: %d]",
/*0002*/ "[%d] Buffer is too big [size: %d]",
/*0003*/ "[%d] Unable to allocate chunk in bpf heap",
/*0004*/ "[%d] Unable to read ssl context [err: %d] [origin: %d]",
/*0005*/ "[%d] Unable to put ssl context [err: %d]",
/*0006*/ "[%d] Unable to get ssl context",
/*0007*/ "[%d] File descriptor is missing for tls chunk",
/*0008*/ "[%d] Unable to put file descriptor [err: %d] [origin: %d]",
/*0009*/ "[%d] Unable to put accept info [err: %d]",
/*0010*/ "[%d] Unable to get accept info",
/*0011*/ "[%d] Unable to read accept info [err: %d]",
/*0012*/ "[%d] Unable to put connection info to connection context [err: %d] [origin: %d]",
/*0013*/ "[%d] Unable to put connect info [err: %d]",
/*0014*/ "[%d] Unable to get connect info",
/*0015*/ "[%d] Unable to read connect info [err: %d]",
/*0016*/ "[%d] Unable to read socket family [err: %d]",
/*0017*/ "[%d] Unable to read socket daddr [err: %d]",
/*0018*/ "[%d] Unable to read socket saddr [err: %d]",
/*0019*/ "[%d] Unable to read socket dport [err: %d]",
/*0021*/ "[%d] Unable to read socket sport [err: %d]",
/*0020*/ "[%d] Unable to read socket sport [err: %d]",
/*0021*/ "[%d] Unable to put go user-kernel context [fd: %d] [err: %d]",
/*0022*/ "[%d] Unable to get go user-kernel context [fd: %d]]",
}

View File

@ -4,17 +4,17 @@ import (
"encoding/binary"
"net"
"unsafe"
"github.com/up9inc/mizu/tap/api"
)
const FlagsIsClientBit uint32 = 1 << 0
const FlagsIsReadBit uint32 = 1 << 1
const (
addressInfoModeUndefined = iota
addressInfoModeSingle
addressInfoModePair
)
type addressPair struct {
srcIp net.IP
srcPort uint16
dstIp net.IP
dstPort uint16
}
func (c *tlsTapperTlsChunk) getSrcAddress() (net.IP, uint16) {
ip := intToIP(c.AddressInfo.Saddr)
@ -54,36 +54,18 @@ func (c *tlsTapperTlsChunk) isRequest() bool {
return (c.isClient() && c.isWrite()) || (c.isServer() && c.isRead())
}
func (c *tlsTapperTlsChunk) getAddressPair() (addressPair, bool) {
func (c *tlsTapperTlsChunk) getAddressPair() addressPair {
var (
srcIp, dstIp net.IP
srcPort, dstPort uint16
full bool
)
switch c.AddressInfo.Mode {
case addressInfoModeSingle:
if c.isRequest() {
srcIp, srcPort = api.UnknownIp, api.UnknownPort
dstIp, dstPort = c.getSrcAddress()
} else {
srcIp, srcPort = c.getSrcAddress()
dstIp, dstPort = api.UnknownIp, api.UnknownPort
}
full = false
case addressInfoModePair:
if c.isRequest() {
srcIp, srcPort = c.getSrcAddress()
dstIp, dstPort = c.getDstAddress()
} else {
srcIp, srcPort = c.getDstAddress()
dstIp, dstPort = c.getSrcAddress()
}
full = true
case addressInfoModeUndefined:
srcIp, srcPort = api.UnknownIp, api.UnknownPort
dstIp, dstPort = api.UnknownIp, api.UnknownPort
full = false
if c.isRequest() {
srcIp, srcPort = c.getSrcAddress()
dstIp, dstPort = c.getDstAddress()
} else {
srcIp, srcPort = c.getDstAddress()
dstIp, dstPort = c.getSrcAddress()
}
return addressPair{
@ -91,7 +73,7 @@ func (c *tlsTapperTlsChunk) getAddressPair() (addressPair, bool) {
srcPort: srcPort,
dstIp: dstIp,
dstPort: dstPort,
}, full
}
}
// intToIP converts IPv4 number to net.IP

View File

@ -1,122 +0,0 @@
package tlstapper
import (
"fmt"
"io/ioutil"
"net"
"os"
"regexp"
"strconv"
"strings"
"github.com/go-errors/errors"
)
var socketInodeRegex = regexp.MustCompile(`socket:\[(\d+)\]`)
const (
SRC_ADDRESS_FILED_INDEX = 1
DST_ADDRESS_FILED_INDEX = 2
INODE_FILED_INDEX = 9
)
type addressPair struct {
srcIp net.IP
srcPort uint16
dstIp net.IP
dstPort uint16
}
// This file helps to extract Ip and Port out of a Socket file descriptor.
//
// The equivalent bash commands are:
//
// > ls -l /proc/<pid>/fd/<fd>
// Output something like "socket:[1234]" for sockets - 1234 is the inode of the socket
// > cat /proc/<pid>/net/tcp | grep <inode>
// Output a line per ipv4 socket, the 9th field is the inode of the socket
// The 1st and 2nd fields are the source and dest ip and ports in a Hex format
// 0100007F:50 is 127.0.0.1:80
func getAddressBySockfd(procfs string, pid uint32, fd uint32) (addressPair, error) {
inode, err := getSocketInode(procfs, pid, fd)
if err != nil {
return addressPair{}, err
}
tcppath := fmt.Sprintf("%s/%d/net/tcp", procfs, pid)
tcp, err := ioutil.ReadFile(tcppath)
if err != nil {
return addressPair{}, errors.Wrap(err, 0)
}
for _, line := range strings.Split(string(tcp), "\n") {
parts := strings.Fields(line)
if len(parts) < 10 {
continue
}
if inode == parts[INODE_FILED_INDEX] {
srcIp, srcPort, srcErr := parseHexAddress(parts[SRC_ADDRESS_FILED_INDEX])
if srcErr != nil {
return addressPair{}, srcErr
}
dstIp, dstPort, dstErr := parseHexAddress(parts[DST_ADDRESS_FILED_INDEX])
if dstErr != nil {
return addressPair{}, dstErr
}
return addressPair{
srcIp: srcIp,
srcPort: srcPort,
dstIp: dstIp,
dstPort: dstPort,
}, nil
}
}
return addressPair{}, errors.Errorf("address not found [pid: %d] [sockfd: %d] [inode: %s]", pid, fd, inode)
}
func getSocketInode(procfs string, pid uint32, fd uint32) (string, error) {
fdlinkPath := fmt.Sprintf("%s/%d/fd/%d", procfs, pid, fd)
fdlink, err := os.Readlink(fdlinkPath)
if err != nil {
return "", errors.Wrap(err, 0)
}
tokens := socketInodeRegex.FindStringSubmatch(fdlink)
if tokens == nil || len(tokens) < 1 {
return "", errors.Errorf("socket inode not found [pid: %d] [sockfd: %d] [link: %s]", pid, fd, fdlink)
}
return tokens[1], nil
}
// Format looks like 0100007F:50 for 127.0.0.1:80
//
func parseHexAddress(addr string) (net.IP, uint16, error) {
addrParts := strings.Split(addr, ":")
port, err := strconv.ParseUint(addrParts[1], 16, 16)
if err != nil {
return nil, 0, errors.Wrap(err, 0)
}
ip, err := strconv.ParseUint(addrParts[0], 16, 32)
if err != nil {
return nil, 0, errors.Wrap(err, 0)
}
return net.IP{uint8(ip), uint8(ip >> 8), uint8(ip >> 16), uint8(ip >> 24)}, uint16(port), nil
}

View File

@ -14,8 +14,6 @@ type sslHooks struct {
sslWriteExRetProbe link.Link
sslReadExProbe link.Link
sslReadExRetProbe link.Link
tcpSendmsg link.Link
tcpRecvmsg link.Link
}
func (s *sslHooks) installUprobes(bpfObjects *tlsTapperObjects, sslLibraryPath string) error {
@ -105,16 +103,6 @@ func (s *sslHooks) installSslHooks(bpfObjects *tlsTapperObjects, sslLibrary *lin
}
}
s.tcpSendmsg, err = link.Kprobe("tcp_sendmsg", bpfObjects.TcpSendmsg, nil)
if err != nil {
return errors.Wrap(err, 0)
}
s.tcpRecvmsg, err = link.Kprobe("tcp_recvmsg", bpfObjects.TcpRecvmsg, nil)
if err != nil {
return errors.Wrap(err, 0)
}
return nil
}
@ -161,17 +149,5 @@ func (s *sslHooks) close() []error {
}
}
if s.tcpSendmsg != nil {
if err := s.tcpSendmsg.Close(); err != nil {
returnValue = append(returnValue, err)
}
}
if s.tcpRecvmsg != nil {
if err := s.tcpRecvmsg.Close(); err != nil {
returnValue = append(returnValue, err)
}
}
return returnValue
}

View File

@ -8,6 +8,8 @@ import (
type syscallHooks struct {
sysEnterRead link.Link
sysEnterWrite link.Link
sysExitRead link.Link
sysExitWrite link.Link
sysEnterAccept4 link.Link
sysExitAccept4 link.Link
sysEnterConnect link.Link
@ -29,6 +31,18 @@ func (s *syscallHooks) installSyscallHooks(bpfObjects *tlsTapperObjects) error {
return errors.Wrap(err, 0)
}
s.sysExitRead, err = link.Tracepoint("syscalls", "sys_exit_read", bpfObjects.SysExitRead, nil)
if err != nil {
return errors.Wrap(err, 0)
}
s.sysExitWrite, err = link.Tracepoint("syscalls", "sys_exit_write", bpfObjects.SysExitWrite, nil)
if err != nil {
return errors.Wrap(err, 0)
}
s.sysEnterAccept4, err = link.Tracepoint("syscalls", "sys_enter_accept4", bpfObjects.SysEnterAccept4, nil)
if err != nil {
@ -67,6 +81,14 @@ func (s *syscallHooks) close() []error {
returnValue = append(returnValue, err)
}
if err := s.sysExitRead.Close(); err != nil {
returnValue = append(returnValue, err)
}
if err := s.sysExitWrite.Close(); err != nil {
returnValue = append(returnValue, err)
}
if err := s.sysEnterAccept4.Close(); err != nil {
returnValue = append(returnValue, err)
}

View File

@ -0,0 +1,45 @@
package tlstapper
import (
"github.com/cilium/ebpf/link"
"github.com/go-errors/errors"
)
type tcpKprobeHooks struct {
tcpSendmsg link.Link
tcpRecvmsg link.Link
}
func (s *tcpKprobeHooks) installTcpKprobeHooks(bpfObjects *tlsTapperObjects) error {
var err error
s.tcpSendmsg, err = link.Kprobe("tcp_sendmsg", bpfObjects.TcpSendmsg, nil)
if err != nil {
return errors.Wrap(err, 0)
}
s.tcpRecvmsg, err = link.Kprobe("tcp_recvmsg", bpfObjects.TcpRecvmsg, nil)
if err != nil {
return errors.Wrap(err, 0)
}
return nil
}
func (s *tcpKprobeHooks) close() []error {
returnValue := make([]error, 0)
if s.tcpSendmsg != nil {
if err := s.tcpSendmsg.Close(); err != nil {
returnValue = append(returnValue, err)
}
}
if s.tcpRecvmsg != nil {
if err := s.tcpRecvmsg.Close(); err != nil {
returnValue = append(returnValue, err)
}
}
return returnValue
}

View File

@ -134,10 +134,7 @@ func (p *tlsPoller) pollChunksPerfBuffer(chunks chan<- *tlsTapperTlsChunk) {
func (p *tlsPoller) handleTlsChunk(chunk *tlsTapperTlsChunk, extension *api.Extension, emitter api.Emitter,
options *api.TrafficFilteringOptions, streamsMap api.TcpStreamMap) error {
address, err := p.getAddressPair(chunk)
if err != nil {
return err
}
address := chunk.getAddressPair()
key := buildTlsKey(address)
reader, exists := p.readers[key]
@ -156,22 +153,6 @@ func (p *tlsPoller) handleTlsChunk(chunk *tlsTapperTlsChunk, extension *api.Exte
return nil
}
func (p *tlsPoller) getAddressPair(chunk *tlsTapperTlsChunk) (addressPair, error) {
addrPairFromChunk, full := chunk.getAddressPair()
if full {
return addrPairFromChunk, nil
}
addrPairFromSockfd, err := p.getSockfdAddressPair(chunk)
if err == nil {
return addrPairFromSockfd, nil
} else {
logger.Log.Error("failed to get address from sock fd:", err)
}
return addrPairFromChunk, err
}
func (p *tlsPoller) startNewTlsReader(chunk *tlsTapperTlsChunk, address *addressPair, key string,
emitter api.Emitter, extension *api.Extension, options *api.TrafficFilteringOptions,
streamsMap api.TcpStreamMap) *tlsReader {
@ -227,41 +208,6 @@ func (p *tlsPoller) closeReader(key string, r *tlsReader) {
p.closedReaders <- key
}
func (p *tlsPoller) getSockfdAddressPair(chunk *tlsTapperTlsChunk) (addressPair, error) {
address, err := getAddressBySockfd(p.procfs, chunk.Pid, chunk.Fd)
fdCacheKey := fmt.Sprintf("%d:%d", chunk.Pid, chunk.Fd)
if err == nil {
if !chunk.isRequest() {
switchedAddress := addressPair{
srcIp: address.dstIp,
srcPort: address.dstPort,
dstIp: address.srcIp,
dstPort: address.srcPort,
}
p.fdCache.Add(fdCacheKey, switchedAddress)
return switchedAddress, nil
} else {
p.fdCache.Add(fdCacheKey, address)
return address, nil
}
}
fromCacheIfc, ok := p.fdCache.Get(fdCacheKey)
if !ok {
return addressPair{}, err
}
fromCache, ok := fromCacheIfc.(addressPair)
if !ok {
return address, errors.Errorf("Unable to cast %T to addressPair", fromCacheIfc)
}
return fromCache, nil
}
func buildTlsKey(address addressPair) string {
return fmt.Sprintf("%s:%d>%s:%d", address.srcIp, address.srcPort, address.dstIp, address.dstPort)
}

View File

@ -22,6 +22,7 @@ const GlobalTapPid = 0
type TlsTapper struct {
bpfObjects tlsTapperObjects
syscallHooks syscallHooks
tcpKprobeHooks tcpKprobeHooks
sslHooksStructs []sslHooks
goHooksStructs []goHooks
poller *tlsPoller
@ -63,6 +64,11 @@ func (t *TlsTapper) Init(chunksBufferSize int, logBufferSize int, procfs string,
return err
}
t.tcpKprobeHooks = tcpKprobeHooks{}
if err := t.tcpKprobeHooks.installTcpKprobeHooks(&t.bpfObjects); err != nil {
return err
}
t.sslHooksStructs = make([]sslHooks, 0)
t.bpfLogger = newBpfLogger()
@ -152,6 +158,8 @@ func (t *TlsTapper) Close() []error {
returnValue = append(returnValue, t.syscallHooks.close()...)
returnValue = append(returnValue, t.tcpKprobeHooks.close()...)
for _, sslHooks := range t.sslHooksStructs {
returnValue = append(returnValue, sslHooks.close()...)
}

View File

@ -27,7 +27,6 @@ type tlsTapper46TlsChunk struct {
Fd uint32
Flags uint32
AddressInfo struct {
Mode int32
Saddr uint32
Daddr uint32
Sport uint16
@ -99,6 +98,8 @@ type tlsTapper46ProgramSpecs struct {
SysEnterWrite *ebpf.ProgramSpec `ebpf:"sys_enter_write"`
SysExitAccept4 *ebpf.ProgramSpec `ebpf:"sys_exit_accept4"`
SysExitConnect *ebpf.ProgramSpec `ebpf:"sys_exit_connect"`
SysExitRead *ebpf.ProgramSpec `ebpf:"sys_exit_read"`
SysExitWrite *ebpf.ProgramSpec `ebpf:"sys_exit_write"`
TcpRecvmsg *ebpf.ProgramSpec `ebpf:"tcp_recvmsg"`
TcpSendmsg *ebpf.ProgramSpec `ebpf:"tcp_sendmsg"`
}
@ -107,18 +108,22 @@ type tlsTapper46ProgramSpecs struct {
//
// It can be passed ebpf.CollectionSpec.Assign.
type tlsTapper46MapSpecs struct {
AcceptSyscallContext *ebpf.MapSpec `ebpf:"accept_syscall_context"`
ChunksBuffer *ebpf.MapSpec `ebpf:"chunks_buffer"`
ConnectSyscallInfo *ebpf.MapSpec `ebpf:"connect_syscall_info"`
FileDescriptorToIpv4 *ebpf.MapSpec `ebpf:"file_descriptor_to_ipv4"`
GoReadContext *ebpf.MapSpec `ebpf:"go_read_context"`
GoWriteContext *ebpf.MapSpec `ebpf:"go_write_context"`
GoidOffsetsMap *ebpf.MapSpec `ebpf:"goid_offsets_map"`
Heap *ebpf.MapSpec `ebpf:"heap"`
LogBuffer *ebpf.MapSpec `ebpf:"log_buffer"`
OpensslReadContext *ebpf.MapSpec `ebpf:"openssl_read_context"`
OpensslWriteContext *ebpf.MapSpec `ebpf:"openssl_write_context"`
PidsMap *ebpf.MapSpec `ebpf:"pids_map"`
AcceptSyscallContext *ebpf.MapSpec `ebpf:"accept_syscall_context"`
ChunksBuffer *ebpf.MapSpec `ebpf:"chunks_buffer"`
ConnectSyscallInfo *ebpf.MapSpec `ebpf:"connect_syscall_info"`
ConnectionContext *ebpf.MapSpec `ebpf:"connection_context"`
GoKernelReadContext *ebpf.MapSpec `ebpf:"go_kernel_read_context"`
GoKernelWriteContext *ebpf.MapSpec `ebpf:"go_kernel_write_context"`
GoReadContext *ebpf.MapSpec `ebpf:"go_read_context"`
GoUserKernelReadContext *ebpf.MapSpec `ebpf:"go_user_kernel_read_context"`
GoUserKernelWriteContext *ebpf.MapSpec `ebpf:"go_user_kernel_write_context"`
GoWriteContext *ebpf.MapSpec `ebpf:"go_write_context"`
GoidOffsetsMap *ebpf.MapSpec `ebpf:"goid_offsets_map"`
Heap *ebpf.MapSpec `ebpf:"heap"`
LogBuffer *ebpf.MapSpec `ebpf:"log_buffer"`
OpensslReadContext *ebpf.MapSpec `ebpf:"openssl_read_context"`
OpensslWriteContext *ebpf.MapSpec `ebpf:"openssl_write_context"`
PidsMap *ebpf.MapSpec `ebpf:"pids_map"`
}
// tlsTapper46Objects contains all objects after they have been loaded into the kernel.
@ -140,18 +145,22 @@ func (o *tlsTapper46Objects) Close() error {
//
// It can be passed to loadTlsTapper46Objects or ebpf.CollectionSpec.LoadAndAssign.
type tlsTapper46Maps struct {
AcceptSyscallContext *ebpf.Map `ebpf:"accept_syscall_context"`
ChunksBuffer *ebpf.Map `ebpf:"chunks_buffer"`
ConnectSyscallInfo *ebpf.Map `ebpf:"connect_syscall_info"`
FileDescriptorToIpv4 *ebpf.Map `ebpf:"file_descriptor_to_ipv4"`
GoReadContext *ebpf.Map `ebpf:"go_read_context"`
GoWriteContext *ebpf.Map `ebpf:"go_write_context"`
GoidOffsetsMap *ebpf.Map `ebpf:"goid_offsets_map"`
Heap *ebpf.Map `ebpf:"heap"`
LogBuffer *ebpf.Map `ebpf:"log_buffer"`
OpensslReadContext *ebpf.Map `ebpf:"openssl_read_context"`
OpensslWriteContext *ebpf.Map `ebpf:"openssl_write_context"`
PidsMap *ebpf.Map `ebpf:"pids_map"`
AcceptSyscallContext *ebpf.Map `ebpf:"accept_syscall_context"`
ChunksBuffer *ebpf.Map `ebpf:"chunks_buffer"`
ConnectSyscallInfo *ebpf.Map `ebpf:"connect_syscall_info"`
ConnectionContext *ebpf.Map `ebpf:"connection_context"`
GoKernelReadContext *ebpf.Map `ebpf:"go_kernel_read_context"`
GoKernelWriteContext *ebpf.Map `ebpf:"go_kernel_write_context"`
GoReadContext *ebpf.Map `ebpf:"go_read_context"`
GoUserKernelReadContext *ebpf.Map `ebpf:"go_user_kernel_read_context"`
GoUserKernelWriteContext *ebpf.Map `ebpf:"go_user_kernel_write_context"`
GoWriteContext *ebpf.Map `ebpf:"go_write_context"`
GoidOffsetsMap *ebpf.Map `ebpf:"goid_offsets_map"`
Heap *ebpf.Map `ebpf:"heap"`
LogBuffer *ebpf.Map `ebpf:"log_buffer"`
OpensslReadContext *ebpf.Map `ebpf:"openssl_read_context"`
OpensslWriteContext *ebpf.Map `ebpf:"openssl_write_context"`
PidsMap *ebpf.Map `ebpf:"pids_map"`
}
func (m *tlsTapper46Maps) Close() error {
@ -159,8 +168,12 @@ func (m *tlsTapper46Maps) Close() error {
m.AcceptSyscallContext,
m.ChunksBuffer,
m.ConnectSyscallInfo,
m.FileDescriptorToIpv4,
m.ConnectionContext,
m.GoKernelReadContext,
m.GoKernelWriteContext,
m.GoReadContext,
m.GoUserKernelReadContext,
m.GoUserKernelWriteContext,
m.GoWriteContext,
m.GoidOffsetsMap,
m.Heap,
@ -197,6 +210,8 @@ type tlsTapper46Programs struct {
SysEnterWrite *ebpf.Program `ebpf:"sys_enter_write"`
SysExitAccept4 *ebpf.Program `ebpf:"sys_exit_accept4"`
SysExitConnect *ebpf.Program `ebpf:"sys_exit_connect"`
SysExitRead *ebpf.Program `ebpf:"sys_exit_read"`
SysExitWrite *ebpf.Program `ebpf:"sys_exit_write"`
TcpRecvmsg *ebpf.Program `ebpf:"tcp_recvmsg"`
TcpSendmsg *ebpf.Program `ebpf:"tcp_sendmsg"`
}
@ -225,6 +240,8 @@ func (p *tlsTapper46Programs) Close() error {
p.SysEnterWrite,
p.SysExitAccept4,
p.SysExitConnect,
p.SysExitRead,
p.SysExitWrite,
p.TcpRecvmsg,
p.TcpSendmsg,
)

View File

@ -27,7 +27,6 @@ type tlsTapperTlsChunk struct {
Fd uint32
Flags uint32
AddressInfo struct {
Mode int32
Saddr uint32
Daddr uint32
Sport uint16
@ -99,6 +98,8 @@ type tlsTapperProgramSpecs struct {
SysEnterWrite *ebpf.ProgramSpec `ebpf:"sys_enter_write"`
SysExitAccept4 *ebpf.ProgramSpec `ebpf:"sys_exit_accept4"`
SysExitConnect *ebpf.ProgramSpec `ebpf:"sys_exit_connect"`
SysExitRead *ebpf.ProgramSpec `ebpf:"sys_exit_read"`
SysExitWrite *ebpf.ProgramSpec `ebpf:"sys_exit_write"`
TcpRecvmsg *ebpf.ProgramSpec `ebpf:"tcp_recvmsg"`
TcpSendmsg *ebpf.ProgramSpec `ebpf:"tcp_sendmsg"`
}
@ -107,18 +108,22 @@ type tlsTapperProgramSpecs struct {
//
// It can be passed ebpf.CollectionSpec.Assign.
type tlsTapperMapSpecs struct {
AcceptSyscallContext *ebpf.MapSpec `ebpf:"accept_syscall_context"`
ChunksBuffer *ebpf.MapSpec `ebpf:"chunks_buffer"`
ConnectSyscallInfo *ebpf.MapSpec `ebpf:"connect_syscall_info"`
FileDescriptorToIpv4 *ebpf.MapSpec `ebpf:"file_descriptor_to_ipv4"`
GoReadContext *ebpf.MapSpec `ebpf:"go_read_context"`
GoWriteContext *ebpf.MapSpec `ebpf:"go_write_context"`
GoidOffsetsMap *ebpf.MapSpec `ebpf:"goid_offsets_map"`
Heap *ebpf.MapSpec `ebpf:"heap"`
LogBuffer *ebpf.MapSpec `ebpf:"log_buffer"`
OpensslReadContext *ebpf.MapSpec `ebpf:"openssl_read_context"`
OpensslWriteContext *ebpf.MapSpec `ebpf:"openssl_write_context"`
PidsMap *ebpf.MapSpec `ebpf:"pids_map"`
AcceptSyscallContext *ebpf.MapSpec `ebpf:"accept_syscall_context"`
ChunksBuffer *ebpf.MapSpec `ebpf:"chunks_buffer"`
ConnectSyscallInfo *ebpf.MapSpec `ebpf:"connect_syscall_info"`
ConnectionContext *ebpf.MapSpec `ebpf:"connection_context"`
GoKernelReadContext *ebpf.MapSpec `ebpf:"go_kernel_read_context"`
GoKernelWriteContext *ebpf.MapSpec `ebpf:"go_kernel_write_context"`
GoReadContext *ebpf.MapSpec `ebpf:"go_read_context"`
GoUserKernelReadContext *ebpf.MapSpec `ebpf:"go_user_kernel_read_context"`
GoUserKernelWriteContext *ebpf.MapSpec `ebpf:"go_user_kernel_write_context"`
GoWriteContext *ebpf.MapSpec `ebpf:"go_write_context"`
GoidOffsetsMap *ebpf.MapSpec `ebpf:"goid_offsets_map"`
Heap *ebpf.MapSpec `ebpf:"heap"`
LogBuffer *ebpf.MapSpec `ebpf:"log_buffer"`
OpensslReadContext *ebpf.MapSpec `ebpf:"openssl_read_context"`
OpensslWriteContext *ebpf.MapSpec `ebpf:"openssl_write_context"`
PidsMap *ebpf.MapSpec `ebpf:"pids_map"`
}
// tlsTapperObjects contains all objects after they have been loaded into the kernel.
@ -140,18 +145,22 @@ func (o *tlsTapperObjects) Close() error {
//
// It can be passed to loadTlsTapperObjects or ebpf.CollectionSpec.LoadAndAssign.
type tlsTapperMaps struct {
AcceptSyscallContext *ebpf.Map `ebpf:"accept_syscall_context"`
ChunksBuffer *ebpf.Map `ebpf:"chunks_buffer"`
ConnectSyscallInfo *ebpf.Map `ebpf:"connect_syscall_info"`
FileDescriptorToIpv4 *ebpf.Map `ebpf:"file_descriptor_to_ipv4"`
GoReadContext *ebpf.Map `ebpf:"go_read_context"`
GoWriteContext *ebpf.Map `ebpf:"go_write_context"`
GoidOffsetsMap *ebpf.Map `ebpf:"goid_offsets_map"`
Heap *ebpf.Map `ebpf:"heap"`
LogBuffer *ebpf.Map `ebpf:"log_buffer"`
OpensslReadContext *ebpf.Map `ebpf:"openssl_read_context"`
OpensslWriteContext *ebpf.Map `ebpf:"openssl_write_context"`
PidsMap *ebpf.Map `ebpf:"pids_map"`
AcceptSyscallContext *ebpf.Map `ebpf:"accept_syscall_context"`
ChunksBuffer *ebpf.Map `ebpf:"chunks_buffer"`
ConnectSyscallInfo *ebpf.Map `ebpf:"connect_syscall_info"`
ConnectionContext *ebpf.Map `ebpf:"connection_context"`
GoKernelReadContext *ebpf.Map `ebpf:"go_kernel_read_context"`
GoKernelWriteContext *ebpf.Map `ebpf:"go_kernel_write_context"`
GoReadContext *ebpf.Map `ebpf:"go_read_context"`
GoUserKernelReadContext *ebpf.Map `ebpf:"go_user_kernel_read_context"`
GoUserKernelWriteContext *ebpf.Map `ebpf:"go_user_kernel_write_context"`
GoWriteContext *ebpf.Map `ebpf:"go_write_context"`
GoidOffsetsMap *ebpf.Map `ebpf:"goid_offsets_map"`
Heap *ebpf.Map `ebpf:"heap"`
LogBuffer *ebpf.Map `ebpf:"log_buffer"`
OpensslReadContext *ebpf.Map `ebpf:"openssl_read_context"`
OpensslWriteContext *ebpf.Map `ebpf:"openssl_write_context"`
PidsMap *ebpf.Map `ebpf:"pids_map"`
}
func (m *tlsTapperMaps) Close() error {
@ -159,8 +168,12 @@ func (m *tlsTapperMaps) Close() error {
m.AcceptSyscallContext,
m.ChunksBuffer,
m.ConnectSyscallInfo,
m.FileDescriptorToIpv4,
m.ConnectionContext,
m.GoKernelReadContext,
m.GoKernelWriteContext,
m.GoReadContext,
m.GoUserKernelReadContext,
m.GoUserKernelWriteContext,
m.GoWriteContext,
m.GoidOffsetsMap,
m.Heap,
@ -197,6 +210,8 @@ type tlsTapperPrograms struct {
SysEnterWrite *ebpf.Program `ebpf:"sys_enter_write"`
SysExitAccept4 *ebpf.Program `ebpf:"sys_exit_accept4"`
SysExitConnect *ebpf.Program `ebpf:"sys_exit_connect"`
SysExitRead *ebpf.Program `ebpf:"sys_exit_read"`
SysExitWrite *ebpf.Program `ebpf:"sys_exit_write"`
TcpRecvmsg *ebpf.Program `ebpf:"tcp_recvmsg"`
TcpSendmsg *ebpf.Program `ebpf:"tcp_sendmsg"`
}
@ -225,6 +240,8 @@ func (p *tlsTapperPrograms) Close() error {
p.SysEnterWrite,
p.SysExitAccept4,
p.SysExitConnect,
p.SysExitRead,
p.SysExitWrite,
p.TcpRecvmsg,
p.TcpSendmsg,
)