Errno and the Three Syscall Layers

Trigger a real error, pull the raw errno out of the chain, and match it with a portable sentinel. Runs on Linux and macOS with only the standard library.

package main

import (
	"errors"
	"fmt"
	"os"
	"syscall"
)

func main() {
	// Top layer: os. Portable and ergonomic.
	_, err := os.Open("/no/such/file")
	fmt.Println("os.Open error:", err)
	// os.Open error: open /no/such/file: no such file or directory

	// Dig the raw errno out of the wrapped error chain.
	var errno syscall.Errno
	if errors.As(err, &errno) {
		fmt.Printf("errno: %d (%s)\n", uintptr(errno), errno)
		// errno: 2 (no such file or directory)
		fmt.Println("is ENOENT:", errno == syscall.ENOENT) // is ENOENT: true
	}

	// Prefer portable sentinels over comparing raw errno numbers.
	fmt.Println("matches os.ErrNotExist:", errors.Is(err, os.ErrNotExist))
	// matches os.ErrNotExist: true

	// Raw layer: syscall.Open hands back a file descriptor (an int), not an *os.File.
	fd, err := syscall.Open("/dev/null", syscall.O_RDONLY, 0)
	if err != nil {
		fmt.Println("syscall.Open:", err)
		return
	}
	defer syscall.Close(fd)
	fmt.Println("raw fd for /dev/null:", fd) // raw fd for /dev/null: 3
}

Save the code as main.go and run it:

go run main.go

Expected output:

os.Open error: open /no/such/file: no such file or directory
errno: 2 (no such file or directory)
is ENOENT: true
matches os.ErrNotExist: true
raw fd for /dev/null: 3

The raw file descriptor number may differ depending on what's already open.

💻 Run locally

Copy the code above and run it on your machine

© 2026 ByteLearn.dev. Free courses for developers. · Privacy