Skip to content

Notes - Trying to run go binaries on Airport #7

@krackers

Description

@krackers

Unfortunately I wasn't really able to get it to work. But here's some notes in case someone else wants to pick up where I left off.

First thank you to @gchehab for providing the precompiled BSD base sets (#4) which makes spelunking a lot easier. It includes gcc so while it's possible to compile newer versions of curl, perl, rsync, etc. directly on device, this is a bit of a pain and it's probably quite slow to do so as well. Go has legendary cross-compile abilities (since it basically avoids libc entirely and makes direct syscalls), and it natively supports arm v6 + netbsd. Plus binaries are statically linked by default. So I thought this would just work out of the box.

Issue 1: Newer versions of Go use a version of lwp_park syscall not supported on netbsd 6. This is described in https://mail-index.netbsd.org/tech-pkg/2018/07/05/msg019971.html – You can either use go1.9, or just revert the aforementioned commit.

Issue 2: While that's sufficient to have the resulting binary begin the go runtime initialization, it gets stuck after the call to lwp_park (semasleep). It seems that there's a deadlock somewhere, nothing is waking it up (semawakeup). Tracing with gdb shows that there's only one thread active, so something about the thread creation seems wonky.

I also tried using the most modern go version with the above commit reverted. This crashes even before the call to lwp_park, on the thread creation itself which returns EINVAL. After some debugging, seems something is weird with the lwp_mcontext_init call, it sets R15 (PC) to the address to resume from (lwp_tramp), but for some reason the alignment of the function seems to be off and bsd doesn't like it. I didn't really debug further, I just brute-forced by inserting nop until the alignment worked out and it got past this. Unfortunately it still hung on the lwp_park.

The hang there might be a kernel issue, I see netbsd had some kernel changes to support Go (Go is also unique in that it makes syscalls directly which I recall is not really supported on BSDs, so I can imagine that it's doing something which bsd doesn't like).

If anyone wants to give this a shot, then trying to see why the lwp_create doesn't actually create a new thread is probably the way to go. I suspect that this created thread is what would send the wakeup call and get things moving.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions