← Back to Projects
C# Metaprogramming Networking ILWeaving

Async Fishnet RPC

ILPostProcessor_PostProcess
Injecting hooks into RpcLogic___MethodName

The Goal

Fishnet's default RPCs are fire-and-forget, which is great for speed but tough for logic-heavy features like turn-based combat or item trades. I wanted to be able to await a server response directly in my code without getting stuck in "callback hell".

What I Built

I wrote an extension for Fishnet that uses IL weaving (Mono.Cecil) to add awaitable RPC support.

  • IL Weaving: My tool scans for methods with an [AsyncRpc] attribute and injects hooks into the Fishnet-generated bytecode at compile-time.
  • Task-Based Workflow: Wrapped the networking layer with UniTask so you can use standard async/await syntax for network calls.
  • ID Tracking: Implemented a thread-safe mapping of request IDs to completion sources. When the server finishes its work, it signals the client to resolve the task.
  • Non-Invasive: Since it uses IL post-processing, it works with any Fishnet project without needing to modify the framework's source code.

Takeaways

  • Metaprogramming Power: Learning how to use Mono.Cecil to modify assemblies opened up a whole new level of what's possible in C#.
  • Developer Experience: Turning complex asynchronous callbacks into a single line of await code made the networking logic much easier to write and debug.