# Debug Skills, Part 1

## How I Debugged an Async Memory Leak with a Custom WithName() Extension

In 2022 I traced a memory leak in a TCP handler system using a custom WithName() extension (I got the concept from Jon Skeet's Stack Overflow answer about task naming, then built my own implementation at the time).

The problem: Handlers weren't canceled and kept running in memory, causing a leak. I suspected the leak was in async handling, I used WithName() to trace async commands:

```csharp
await ReceiveMessagesAsync().WithName("ReceiveMessagesAsync");
```

Actual example from application logs (Worker class):

```
+++++++ GetAwaiter called for task "ReceiveMessagesAsync"
+++++++ OnCompleted called for task "ReceiveMessagesAsync"
....
+++++++ GetResult called for task "ReceiveMessagesAsync"
```

What WithName() does:

- Wraps tasks with a name (NamedTask<T> struct).
- Logs when GetAwaiter(), OnCompleted(), and GetResult() are called using Console.WriteLine().
- Makes it easy to see which async operations are still running.
- Based on Jon Skeet's Stack Overflow concept about naming async operations for debugging (C# master with 1.5M+ reputation).

Why I used Console.WriteLine() instead of ILogger:

- Simple for temporary/local debugging in April 2022.
- No dependencies needed.
- Quick to test (just run and see output).
- Perfect for showing the concept without extra complexity.
- I don't use this code anymore, no need to spend time on legacy code.

The fix: Once I found the leak, I added an abort method with cancellation token linking:

```csharp
abortReceivedMessagesTokenSource = new CancellationTokenSource();
combinedTokenSource = CancellationTokenSource.CreateLinkedTokenSource(stoppingToken, abortReceivedMessagesTokenSource.Token);
```

Why this helps for memory leak debugging:

- Names async commands (easier to trace).
- Shows which operations are still running.
- Makes memory leak debugging much easier.

Thanks to Jon Skeet for the concept that inspired this!

Try it yourself: if you're dealing with async memory leaks in C#, add `.WithName()` to your async operations to trace them.

Link to the class: [DiagnosticTaskExtensions.cs](https://github.com/P47K0/csharp-withname-extension/blob/main/DiagnosticTaskExtensions.cs)

---

*Co-authored with Claude.*

If this was useful, [you can buy me a coffee](https://ko-fi.com/p47k0).

New articles: [follow via RSS](https://blog.koorevaar.com/feed.xml).
