Skip to content
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

btf: use recursion in coreAreTypesCompatible #1383

Merged
merged 1 commit into from
Mar 22, 2024

Conversation

lmb
Copy link
Collaborator

@lmb lmb commented Mar 20, 2024

coreAreTypesCompatible currently uses two manually maintained stacks to traverse two types to compare. The original idea was that using stacks would somehow be more efficient or it'd be easier to understand than the recursive approach. Time has shown that this was probably not true. Using the stacks is both harder to understand and probably less performant than using recursion. This is because the runtime maintains a stack for us, which can be reused across many invocations. Allocating on the (goroutine) stack is also incredibly cheap.

Rewrite coreAreTypesCompatible to use recursion to traverse the two types. Instead of using walkType we simply open code the switch cases for Pointer, Array and FuncProto. This isn't much code and gets rid of a bunch of complexity and allocations, especially for FuncParam.

The depth check is removed completely. It's a hold over from libbpf, which probably uses it to avoid stack overflow. This isn't necessary in Go, since overflowing the stack is guaranteed to panic. Instead, we deal with cyclical types by maintaining a visited map.

coreAreTypesCompatible currently uses two manually maintained
stacks to traverse two types to compare. The original idea was
that using stacks would somehow be more efficient or it'd be
easier to understand than the recursive approach. Time has shown
that this was probably not true. Using the stacks is both harder
to understand and probably less performant than using recursion.
This is because the runtime maintains a stack for us, which can
be reused across many invocations. Allocating on the (goroutine)
stack is also incredibly cheap.

Rewrite coreAreTypesCompatible to use recursion to traverse the
two types. Instead of using walkType we simply open code the
switch cases for Pointer, Array and FuncProto. This isn't much
code and gets rid of a bunch of complexity and allocations,
especially for FuncParam.

The depth check is removed completely. It's a hold over from
libbpf, which probably uses it to avoid stack overflow. This
isn't necessary in Go, since overflowing the stack is guaranteed
to panic. Instead, we deal with cyclical types by maintaining
a visited map.

Signed-off-by: Lorenz Bauer <lmb@isovalent.com>
Copy link
Member

@dylandreimerink dylandreimerink left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

@lmb lmb merged commit ebf148f into cilium:main Mar 22, 2024
15 checks passed
@lmb lmb deleted the btf-core-compatible branch March 22, 2024 09:35
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants