About
About Zhenzhong Wu: systems programming, Linux networking, debugging tools, runtime observability, and engineering retrospectives.
About Me
I am Zhenzhong Wu, also known online as swananan. I am a systems engineer with a long-standing interest in QUIC, Rust, Linux network programming, eBPF, GDB/DWARF, production troubleshooting, and engineering practices.
My Approach to AI
Around June 2025, I shifted to an AI-native development workflow, handing much of my research and code generation work over to AI. That does not mean compromising on engineering quality. For every contribution I submit upstream, I carefully review the LLM-generated work and verify it repeatedly until the PR meets my standards. Sometimes I honestly think writing it myself would have been faster = =||. I also never use AI to write my replies when communicating with people in open-source communities. I value every interaction; each one is an important part of my own growth.
As for this blog, I write because I enjoy it and because explaining something clearly—teaching—is a core skill for programmers. That is why I do not use LLMs to generate posts directly. I once tried letting an LLM write a post, but it never felt quite right, which is why I stopped. That post is clearly labeled at the beginning so no one unknowingly consumes AI-generated prose 😁. At present, however, all of my English posts are translated by LLMs from Chinese posts I wrote by hand. I apologize for that; perhaps someday I should try writing a post directly in English.
Open-Source Contributions
I try to turn real problems I encounter into upstream PRs or patches. My public contributions mostly come from issues I hit in daily work or personal projects, covering OpenResty / Nginx, Linux networking, and the eBPF / Rust ecosystem.
Linux Kernel
Found and fixed a TCP listener migration issue: tcp: call sk_data_ready() after listener migration.
Investigated the eBPF verifier issue exposed by Aya's FExitContext::ret() test on Linux 6.6 LTS, built a minimized C reproducer, ran kernel git bisect, analyzed the verifier root cause, and submitted the 6.6 backport patch series: Linux 6.6 backport patch series. The issue background and investigation notes are in the Aya PR: aya-ebpf: document FExit ret kernel range.
Aya / Rust eBPF Ecosystem
Recently, I have devoted a substantial share of my open-source time to Aya. As of August 2026, 31 of my PRs have been merged upstream in the past six months. Most of this work grew out of real needs I encountered while building GhostScope and debugging Linux networking, though some of it came from community feedback or issues I noticed while reading Aya's code.
I want to keep investing time in the Aya community largely because it sets an exceptionally high bar for code quality and consistently chooses quality over quantity. Each interaction with the community teaches me something and deepens my appreciation for Rust and eBPF.
OpenResty / Nginx Community
I participated in OpenResty HTTP/3 and PCRE2 work. During the PCRE2 work, I found a memory leak in upstream Nginx PCRE support, reported it to the community, and submitted a patch: Memory Leak Issue in Nginx PCRE2.
I also fixed a key issue in lua-nginx-module where Lua coroutine yield APIs were unavailable in HTTP/3 scenarios: PR. I have also reported and discussed defects in Nginx HTTP/3 hot upgrade behavior.
Personal Open-Source Projects
GhostScope
GhostScope is the personal open-source project I am spending the most time on right now. It tries to solve a simple but difficult problem: a production process is still running, GDB is too risky to attach, but during debugging we keep thinking, "if only I could add one more printf here."
GhostScope tries to make that possible with low-intrusion runtime debugging. Without stopping the target process, it can set probes at the function, source-line, or instruction level, then print the variables we care about using source-level names.
The hard part is that GhostScope is not just a wrapper around eBPF and uprobes. It has to read ELF and DWARF, understand source locations, variable visibility, type layout, inline scopes, ASLR/PIE address mapping, and where a variable lives at a given instruction. A variable may be in a register, on the stack, or already optimized away.
It also needs a small trace language. User expressions written with source-level names have to be combined with DWARF's plan for the current PC, then compiled into verifier-friendly eBPF bytecode through LLVM at runtime. In short, it has to solve part of the same DWARF problem debuggers like GDB have solved for years, and then turn the result into eBPF that the verifier will accept.
Next, I want to add eBPF-based DWARF stack unwinding, so trace output is not just an isolated variable snapshot but also carries call-chain context. I also want to gradually support more complex language behavior, such as Rust async, trait objects, and maybe even variables and stack information inside some interpreted language runtimes.
My expectations for GhostScope are high. I do not want it to remain a niche command-line tool or another generic observability dashboard. I want compiled binaries to feel less like black boxes. Users should be able to ask questions using the names they see in source code, write flexible trace scripts in a TUI, and let LLMs generate executable trace scripts from source paths, DWARF, and runtime context. Ideally, some production problems that used to require a new release with extra logs and a lot of guessing can become problems where we ask a precise question, sample the right place, and verify quickly.
feather-quic
feather-quic is an experimental QUIC protocol stack I wrote in Rust. It is not meant to replace production implementations. It is a way for me to take a protocol stack apart and check the details by building them myself. Through the project, I reimplemented QUIC piece by piece: handshake, TLS 1.3, reliability, streams, connection close, MTU discovery, connection migration, and more. For me, the most important output was not the code itself, but the article series built around protocol implementation and my past engineering experience:
- Implementing QUIC from Scratch with Rust: A Fresh Start
- Implementing QUIC from Scratch with Rust: Runtime
- Implementing QUIC from Scratch with Rust: A Deep Dive into the QUIC Handshake
- Implementing QUIC from Scratch with Rust: TLS 1.3 Handshake and QUIC-TLS Key Update
- Implementing QUIC from Scratch with Rust: Reliability
- Implementing QUIC from Scratch with Rust: Streams and Flow Control
- Implementing QUIC from Scratch with Rust: Connection Close and Error Handling
- Implementing QUIC from Scratch with Rust: MTU Discovery
- Implementing QUIC from Scratch with Rust: Connection Migration
This series is currently paused. LLMs are now very good at writing code and doing technical research, so my motivation has changed a bit. Still, I believe this series has its own value, and you are welcome to read it. In the future, feather-quic will probably only get one or two more posts, perhaps about congestion control and real Tokio async support. The style will stay the same: the focus is still on projects I have actually worked on and the engineering experience behind them.