Go

Go: JSON v2 Breaking Changes & ARM64 Performance Wins

The Go team made significant breaking changes to JSON v2, removing the complex `unknown` tag option and DiscardUnknownMembers in favor of simpler alternatives. Meanwhile, ARM64 got a performance boost with new CCMP instruction support, and the compiler saw memory optimizations that reduced binary sizes by 16K.

Duration: PT3M53S

https://podlog.io/listen/go-e282e2e6/episode/go-json-v2-breaking-changes-arm64-performance-wins-4f3724b0

Transcript

Hey there, Go developers! Welcome back to another episode. I'm your host, and wow, do we have some interesting changes to dive into today from the Go codebase. Grab your favorite beverage because we're talking about some pretty significant updates, including some breaking changes that show the team's commitment to getting things right.

So here's the big story today - Joe Tsai made a bold move with JSON v2 that I think really shows the thoughtfulness of the Go team. They removed the `unknown` tag option and the DiscardUnknownMembers marshal option from the experimental JSON v2 package. Now, I know what you're thinking - breaking changes can be scary, right? But here's the beautiful part of this decision.

Joe mentioned in the commit that the `unknown` tag option semantics were "a bit too subtle even for experienced Go programmers to understand." I love this kind of honest assessment. Sometimes as developers, we build something that works technically, but then we step back and realize it's just too complex for real-world use. The team already supports the `inline` tag option, which can handle most of the use cases people would want anyway. It's like Marie Kondo for APIs - if it doesn't spark joy and clarity, maybe it shouldn't be there.

Now, let's talk about some performance wins because these are always exciting! Ian Lance Taylor worked on compiler optimizations that are reducing binary sizes. The tailscaled binary got 16K smaller just by setting better alignment for content-addressable symbols. It might sound like a small technical detail, but these kinds of optimizations add up and make everyone's binaries leaner and meaner.

Speaking of performance, we've got some cool ARM64 improvements. Ch1n-ch1nless introduced a new SSA pass that converts conditionals with logical AND into CMP/CCMP instruction sequences. This is the kind of low-level optimization that ARM64 users are going to love - the compiler is getting smarter about using the specific features of the architecture.

There's also a really nice fix from Youlin Feng around slice bounds check elimination after function inlining. This is one of those compiler improvements that happens behind the scenes but makes your code faster without you having to change anything. The compiler is getting better at understanding when it can optimize away safety checks that aren't actually needed.

And I've got to give a shoutout to Michael Podtserkovskii for tackling an issue with large generated code. They removed a 2GB allocation limit that was preventing compilation of really large codebases. Sometimes you don't know these limits exist until you hit them, and it's great to see the team staying ahead of these scaling challenges.

On the tooling side, Oleksandr Redko fixed a panic in 'go run -C' - those kinds of fixes might seem small, but they prevent those frustrating moments where your development flow gets interrupted by an unexpected crash.

The documentation got some love too. Sean Liao clarified that LoadLocation creates new Location instances every time, which is one of those details that's really important to understand when you're working with time zones in production code.

Today's Focus: If you're experimenting with JSON v2, now's a great time to review your code and see if you were using the removed `unknown` tag option. Check if the `inline` option can handle your use case instead - it probably can, and your code will be cleaner for it. Also, if you're working with ARM64 targets, keep an eye on your performance metrics - you might see some nice improvements from these compiler optimizations.

That's a wrap for today's episode! The Go team continues to make thoughtful decisions about API design and performance. Sometimes the best choice is removing complexity rather than adding features, and today's changes really demonstrate that philosophy. Keep coding, keep learning, and I'll catch you next time!