Fundamentals 7 min read

Mastering Go’s GC: Adjusted Stack, Old Stack, and New Stack Explained

This article explains how Go's garbage collector manages adjusted, old, and new stacks, detailing the stack adjustment process, expansion and contraction steps, and practical techniques—including debugging tools, stack printing, memory profiling, and stress testing—to verify correct behavior.

Ops Development & AI Practice
Ops Development & AI Practice
Ops Development & AI Practice
Mastering Go’s GC: Adjusted Stack, Old Stack, and New Stack Explained

Adjusted Stack

The adjusted stack is a runtime technique where the GC modifies stack memory during collection to ensure all pointers reference valid objects, especially after stack growth or shrinkage.

Adjustment Process

Mark Phase: GC scans all stack pointers and marks them as visited to prevent accidental reclamation.

Pointer Adjustment: After stack expansion or contraction, GC updates pointers to point to the new stack locations.

Verification: GC validates the adjusted pointers to guarantee they still reference valid objects, avoiding memory errors.

Old Stack and New Stack

When the Go runtime expands or shrinks a stack, the original stack becomes the old stack and the resized one becomes the new stack .

Stack Expansion

When a function needs more stack space, the runtime allocates a larger stack and copies the old stack's contents.

Allocate New Stack: Reserve a larger stack region.

Copy Contents: Transfer all variables and pointers from the old stack.

Update Pointers: Adjust every pointer to reference the corresponding location in the new stack.

Stack Contraction

After a function returns and excess stack space is no longer needed, the runtime may shrink the stack.

Allocate New Stack: Reserve a smaller stack region.

Copy Contents: Move data from the old stack to the new, smaller stack.

Update Pointers: Repoint all pointers to their new locations.

Verification Techniques

To confirm that the GC correctly adjusts stacks, you can use the following methods:

1. Debugging Tools

Use Go debugging tools such as GDB or Delve to set breakpoints and inspect stack pointer changes.

2. Print Stack Information

Add print statements to output the stack’s start address, end address, and pointer locations.

package main

import (
    "fmt"
    "runtime"
)

func printStack() {
    var buf [4096]byte
    n := runtime.Stack(buf[:], false)
    fmt.Printf("Stack:
%s
", buf[:n])
}

func main() {
    printStack()
}
go run .\main.go
Stack:
... (stack trace output) ...

3. Memory Profiling Tools

Use profiling tools like pprof to generate memory usage reports for the stack.

import (
    "net/http"
    _ "net/http/pprof"
)

func main() {
    go func() {
        log.Println(http.ListenAndServe("localhost:6060", nil))
    }()
    // Your program logic here
}

4. Stress Testing

Run high‑concurrency stress tests to verify the GC’s stability under load.

package main

import (
    "fmt"
    "sync"
)

func main() {
    var wg sync.WaitGroup
    for i := 0; i < 1000; i++ {
        wg.Add(1)
        go func(i int) {
            defer wg.Done()
            fmt.Printf("Goroutine %d
", i)
            printStack()
        }(i)
    }
    wg.Wait()
}

Conclusion

Adjusted, old, and new stacks are crucial for Go’s GC to manage stack memory safely. By employing debugging tools, stack printing, profiling, and stress testing, developers can verify the correctness and stability of these mechanisms, leading to more performant and reliable Go applications.

Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

performanceGoGarbage CollectionStack Management
Ops Development & AI Practice
Written by

Ops Development & AI Practice

DevSecOps engineer sharing experiences and insights on AI, Web3, and Claude code development. Aims to help solve technical challenges, improve development efficiency, and grow through community interaction. Feel free to comment and discuss.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.