Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

syscall 包详解

概述

syscall 包提供了对底层操作系统原语的接口。具体实现因底层系统而异,默认情况下 godoc 会显示当前系统的 syscall 文档。

核心功能

  • 系统调用接口(文件、进程、网络、信号等)
  • 低级操作系统原语访问
  • 平台相关的系统调用号
  • 错误处理和类型转换

重要说明

  • ⚠️ 平台相关:细节因操作系统而异
  • ⚠️ 使用建议:优先使用 os、time、net 等更便携的包
  • ⚠️ 现代替代:新代码应优先使用 golang.org/x/sys 包
  • 错误处理:返回 err == nil 表示成功,否则为 Errno 类型错误

包导入

import "syscall"

常量和变量

错误常量(Errno)

// 常见错误号
var (
    EPERM     Errno = 0x1  // 操作不允许
    ENOENT    Errno = 0x2  // 文件或目录不存在
    ESRCH     Errno = 0x3  // 进程不存在
    EINTR     Errno = 0x4  // 系统调用被中断
    EIO       Errno = 0x5  // I/O 错误
    ENXIO     Errno = 0x6  // 设备或地址不存在
    E2BIG     Errno = 0x7  // 参数列表过长
    ENOEXEC   Errno = 0x8  // 可执行文件格式错误
    EBADF     Errno = 0x9  // 文件描述符错误
    ECHILD    Errno = 0xa  // 子进程不存在
    EAGAIN    Errno = 0xb  // 资源暂时不可用
    ENOMEM    Errno = 0xc  // 内存不足
    EACCES    Errno = 0xd  // 权限不足
    EFAULT    Errno = 0xe  // 地址错误
    // ... 更多错误号
)

系统调用号常量

// Linux AMD64 常见系统调用号
const (
    SYS_READ           = 0
    SYS_WRITE          = 1
    SYS_OPEN           = 2
    SYS_CLOSE          = 3
    SYS_STAT           = 4
    SYS_FSTAT          = 5
    SYS_LSTAT          = 6
    SYS_POLL           = 7
    SYS_LSEEK          = 8
    SYS_MMAP           = 9
    SYS_MPROTECT       = 10
    SYS_MUNMAP         = 11
    SYS_BRK            = 12
    SYS_EXIT           = 60
    SYS_FORK           = 57
    SYS_EXECVE         = 59
    SYS_GETPID         = 39
    SYS_GETUID         = 102
    SYS_GETGID         = 104
    // ... 300+ 系统调用号
)

信号常量

const (
    SIGHUP    Signal = 1  // 挂起
    SIGINT    Signal = 2  // 中断(Ctrl+C)
    SIGQUIT   Signal = 3  // 退出
    SIGILL    Signal = 4  // 非法指令
    SIGTRAP   Signal = 5  // 跟踪陷阱
    SIGABRT   Signal = 6  // 中止
    SIGBUS    Signal = 7  // 总线错误
    SIGFPE    Signal = 8  // 浮点异常
    SIGKILL   Signal = 9  // 杀死(不可捕获)
    SIGUSR1   Signal = 10 // 用户定义信号 1
    SIGSEGV   Signal = 11 // 段错误
    SIGUSR2   Signal = 12 // 用户定义信号 2
    SIGPIPE   Signal = 13 // 管道破裂
    SIGALRM   Signal = 14 // 定时器
    SIGTERM   Signal = 15 // 终止
    SIGCHLD   Signal = 17 // 子进程状态改变
    SIGCONT   Signal = 18 // 继续
    SIGSTOP   Signal = 19 // 停止(不可捕获)
    SIGTSTP   Signal = 20 // 终端停止
    // ... 更多信号
)

类型详解(按 A-Z 分类)

Dirent

type Dirent struct {
    Ino    uint64 // inode 号
    Off    int64  // 偏移
    Reclen uint16 // 记录长度
    Type   uint8  // 文件类型
    Name   [256]int8 // 文件名
}

功能: 表示目录条目。

EpollEvent

type EpollEvent struct {
    Events uint32
    Fd     int32
    Pad    int32
}

功能: epoll 事件结构。

事件类型

  • EPOLLIN - 可读
  • EPOLLOUT - 可写
  • EPOLLERR - 错误
  • EPOLLHUP - 挂起

Flock_t

type Flock_t struct {
    Type   int16
    Whence int16
    Start  int64
    Len    int64
    Pid    int32
}

功能: 文件锁结构。

ProcAttr

type ProcAttr struct {
    Dir   string
    Env   []string
    Files []uintptr
    Sys   *SysProcAttr
}

功能: 进程属性,用于 ForkExec。

Rlimit

type Rlimit struct {
    Cur uint64 // 当前限制
    Max uint64 // 最大限制
}

功能: 资源限制。

Rusage

type Rusage struct {
    Utime    Timeval // 用户 CPU 时间
    Stime    Timeval // 系统 CPU 时间
    Maxrss   int64   // 最大驻留集大小
    Ixrss    int64
    Idrss    int64
    Isrss    int64
    Minflt   int64 // 次要页面错误
    Majflt   int64 // 主要页面错误
    Nswap    int64
    Inblock  int64 // 输入块操作
    Oublock  int64 // 输出块操作
    Msgsnd   int64
    Msgrcv   int64
    Nsignals int64
    Nvcsw    int64 // 自愿上下文切换
    Nivcsw   int64 // 非自愿上下文切换
}

功能: 资源使用情况。

Stat_t

type Stat_t struct {
    Dev     uint64 // 设备 ID
    Ino     uint64 // inode 号
    Nlink   uint64 // 硬链接数
    Mode    uint32 // 文件模式
    Uid     uint32 // 用户 ID
    Gid     uint32 // 组 ID
    Rdev    uint64 // 设备类型
    Size    int64  // 文件大小
    Blksize int64  // 块大小
    Blocks  int64  // 块数
    Atim    Timespec // 最后访问时间
    Mtim    Timespec // 最后修改时间
    Ctim    Timespec // 最后更改时间
}

功能: 文件状态信息。

Statfs_t

type Statfs_t struct {
    Type    int64
    Bsize   int64
    Blocks  uint64
    Bfree   uint64
    Bavail  uint64
    Files   uint64
    Ffree   uint64
    Fsid    Fsid
    Namelen int64
    Frsize  int64
    Flags   int64
}

功能: 文件系统状态信息。

SysProcAttr

type SysProcAttr struct {
    Chroot     string
    Credential *Credential
    Pdeathsig  Signal
    Setpgid    bool
    Setctty    bool
    Setsid     bool
    Ctty       int
    Noctty     bool
    // ... 更多字段
}

功能: 系统特定的进程属性。

Timeval

type Timeval struct {
    Sec  int64 // 秒
    Usec int64 // 微秒
}

功能: 时间值(微秒精度)。

Timespec

type Timespec struct {
    Sec  int64 // 秒
    Nsec int64 // 纳秒
}

功能: 时间值(纳秒精度)。

函数详解(按 A-Z 分类)

A

Access

func Access(path string, mode uint32) (err error)

功能: 检查调用者是否可以访问指定路径。

参数

  • path string - 文件路径
  • mode uint32 - 访问模式(F_OK、R_OK、W_OK、X_OK)

返回值

  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 检查文件是否存在
    if err := syscall.Access("/etc/passwd", syscall.F_OK); err != nil {
        fmt.Println("文件不存在")
    } else {
        fmt.Println("文件存在")
    }
    
    // 检查是否可读
    if err := syscall.Access("/etc/passwd", syscall.R_OK); err != nil {
        fmt.Println("文件不可读")
    } else {
        fmt.Println("文件可读")
    }
}

B

BytePtrFromString

func BytePtrFromString(s string) (*byte, error)

功能: 从 Go 字符串创建 C 风格的字符串指针(以 null 结尾)。

参数

  • s string - 输入字符串

返回值

  • *byte - 指向字节数组的指针
  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
    "unsafe"
)

func main() {
    ptr, err := syscall.BytePtrFromString("hello")
    if err != nil {
        fmt.Println("错误:", err)
        return
    }
    
    // 使用 unsafe 转换为 C 字符串
    fmt.Println("指针地址:", uintptr(unsafe.Pointer(ptr)))
}

C

Chdir

func Chdir(path string) (err error)

功能: 改变当前工作目录。

参数

  • path string - 目标目录路径

返回值

  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    if err := syscall.Chdir("/tmp"); err != nil {
        fmt.Println("改变目录失败:", err)
    } else {
        fmt.Println("目录已改变到 /tmp")
    }
}

Chmod

func Chmod(path string, mode uint32) (err error)

功能: 改变文件权限。

参数

  • path string - 文件路径
  • mode uint32 - 权限模式

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 设置文件为 0755
    if err := syscall.Chmod("/tmp/test.txt", 0755); err != nil {
        fmt.Println("错误:", err)
    }
}

Chown

func Chown(path string, uid int, gid int) (err error)

功能: 改变文件所有者和组。

参数

  • path string - 文件路径
  • uid int - 用户 ID
  • gid int - 组 ID

Close

func Close(fd int) (err error)

功能: 关闭文件描述符。

参数

  • fd int - 文件描述符

返回值

  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    fd, err := syscall.Open("/tmp/test.txt", syscall.O_RDONLY, 0)
    if err != nil {
        fmt.Println("打开失败:", err)
        return
    }
    
    if err := syscall.Close(fd); err != nil {
        fmt.Println("关闭失败:", err)
    }
}

D

Dup

func Dup(oldfd int) (fd int, err error)

功能: 复制文件描述符。

参数

  • oldfd int - 原文件描述符

返回值

  • fd int - 新文件描述符
  • error - 错误

Dup2

func Dup2(oldfd int, newfd int) (err error)

功能: 将文件描述符 oldfd 复制到 newfd。

参数

  • oldfd int - 原文件描述符
  • newfd int - 新文件描述符

返回值

  • error - 错误

E

Environ

func Environ() []string

功能: 返回环境变量。

返回值

  • []string - 环境变量数组

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    env := syscall.Environ()
    for _, e := range env {
        fmt.Println(e)
    }
}

Exec

func Exec(argv0 string, argv []string, envv []string) (err error)

功能: 执行新程序替换当前进程。

参数

  • argv0 string - 可执行文件路径
  • argv []string - 参数列表
  • envv []string - 环境变量

返回值

  • error - 错误(如果成功则不返回)

注意

  • 成功时不会返回
  • 当前进程被新程序替换

Exit

func Exit(code int)

功能: 以指定退出码终止进程。

参数

  • code int - 退出码

注意

  • 不会返回
  • 不调用 defer

F

Fchdir

func Fchdir(fd int) (err error)

功能: 通过文件描述符改变目录。

参数

  • fd int - 目录的文件描述符

Fchmod

func Fchmod(fd int, mode uint32) (err error)

功能: 通过文件描述符改变文件权限。

Fchown

func Fchown(fd int, uid int, gid int) (err error)

功能: 通过文件描述符改变文件所有者。

ForkExec

func ForkExec(argv0 string, argv []string, attr *ProcAttr) (pid int, err error)

功能: fork 并 exec 新进程。

参数

  • argv0 string - 可执行文件
  • argv []string - 参数
  • attr *ProcAttr - 进程属性

返回值

  • pid int - 子进程 ID
  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    attr := &syscall.ProcAttr{
        Files: []uintptr{0, 1, 2},
    }
    
    pid, err := syscall.ForkExec("/bin/ls", []string{"ls", "-l"}, attr)
    if err != nil {
        fmt.Println("错误:", err)
        return
    }
    
    fmt.Println("子进程 PID:", pid)
}

Fstat

func Fstat(fd int, stat *Stat_t) (err error)

功能: 通过文件描述符获取文件状态。

参数

  • fd int - 文件描述符
  • stat *Stat_t - 状态结构

返回值

  • error - 错误

Fsync

func Fsync(fd int) (err error)

功能: 同步文件到磁盘。

Ftruncate

func Ftruncate(fd int, length int64) (err error)

功能: 截断文件到指定长度。

G

Getcwd

func Getcwd(buf []byte) (n int, err error)

功能: 获取当前工作目录。

参数

  • buf []byte - 缓冲区

返回值

  • n int - 读取的字节数
  • error - 错误

Getegid

func Getegid() (egid int)

功能: 获取有效组 ID。

Getenv

func Getenv(key string) (value string, found bool)

功能: 获取环境变量。

参数

  • key string - 变量名

返回值

  • value string - 变量值
  • found bool - 是否存在

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    if val, found := syscall.Getenv("HOME"); found {
        fmt.Println("HOME:", val)
    } else {
        fmt.Println("HOME 未设置")
    }
}

Geteuid

func Geteuid() (euid int)

功能: 获取有效用户 ID。

Getgid

func Getgid() (gid int)

功能: 获取组 ID。

Getgroups

func Getgroups() (gids []int, err error)

功能: 获取附属组 ID 列表。

Getpagesize

func Getpagesize() int

功能: 获取系统页面大小。

Getpgid

func Getpgid(pid int) (pgid int, err error)

功能: 获取进程组 ID。

Getpid

func Getpid() (pid int)

功能: 获取当前进程 ID。

Getppid

func Getppid() (ppid int)

功能: 获取父进程 ID。

Getpriority

func Getpriority(which int, who int) (prio int, err error)

功能: 获取进程优先级。

Getrlimit

func Getrlimit(resource int, rlim *Rlimit) (err error)

功能: 获取资源限制。

参数

  • resource int - 资源类型(RLIMIT_CPU、RLIMIT_FSIZE 等)
  • rlim *Rlimit - 限制结构

Getrusage

func Getrusage(who int, rusage *Rusage) (err error)

功能: 获取资源使用情况。

参数

  • who int - 目标(RUSAGE_SELF、RUSAGE_CHILDREN)
  • rusage *Rusage - 使用情况结构

Getsid

func Getsid(pid int) (sid int, err error)

功能: 获取进程会话 ID。

Gettid

func Gettid() (tid int)

功能: 获取线程 ID。

Gettimeofday

func Gettimeofday(tv *Timeval) (err error)

功能: 获取当前时间。

Getuid

func Getuid() (uid int)

功能: 获取用户 ID。

Getwd

func Getwd() (wd string, err error)

功能: 获取当前工作目录。

返回值

  • wd string - 工作目录路径
  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    wd, err := syscall.Getwd()
    if err != nil {
        fmt.Println("错误:", err)
        return
    }
    fmt.Println("当前目录:", wd)
}

K

Kill

func Kill(pid int, signum Signal) (err error)

功能: 发送信号到进程。

参数

  • pid int - 进程 ID
  • signum Signal - 信号

返回值

  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 发送 SIGTERM
    if err := syscall.Kill(1234, syscall.SIGTERM); err != nil {
        fmt.Println("错误:", err)
    }
}

L

func Link(path string, link string) (err error)

功能: 创建硬链接。

Listen

func Listen(fd int, backlog int) (err error)

功能: 监听 socket 连接。

M

Mkdir

func Mkdir(path string, mode uint32) (err error)

功能: 创建目录。

Mmap

func Mmap(fd int, offset int64, length int, prot int, flags int) (data []byte, err error)

功能: 内存映射文件。

Munmap

func Munmap(b []byte) (err error)

功能: 取消内存映射。

N

Nanosleep

func Nanosleep(time *Timespec, leftover *Timespec) (err error)

功能: 高精度睡眠。

O

Open

func Open(path string, mode int, perm uint32) (fd int, err error)

功能: 打开文件。

参数

  • path string - 文件路径
  • mode int - 打开模式(O_RDONLY、O_WRONLY、O_RDWR 等)
  • perm uint32 - 权限

返回值

  • fd int - 文件描述符
  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    fd, err := syscall.Open("/tmp/test.txt", syscall.O_RDONLY, 0)
    if err != nil {
        fmt.Println("错误:", err)
        return
    }
    defer syscall.Close(fd)
    
    fmt.Println("文件描述符:", fd)
}

P

Pipe

func Pipe(p []int) (err error)

功能: 创建管道。

参数

  • p []int - 长度为 2 的数组(p[0] 读端,p[1] 写端)

返回值

  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    var p [2]int
    if err := syscall.Pipe(p[:]); err != nil {
        fmt.Println("错误:", err)
        return
    }
    
    fmt.Printf("读端:%d, 写端:%d\n", p[0], p[1])
}

Poll

func Poll(fds []PollFd, timeout int) (n int, err error)

功能: 等待文件描述符上的事件。

R

Read

func Read(fd int, p []byte) (n int, err error)

功能: 从文件描述符读取数据。

参数

  • fd int - 文件描述符
  • p []byte - 缓冲区

返回值

  • n int - 读取的字节数
  • error - 错误

Readdir

func Readdir(fd int, buf []byte) (n int, err error)

功能: 读取目录条目。

Rename

func Rename(oldpath string, newpath string) (err error)

功能: 重命名文件或目录。

Rmdir

func Rmdir(path string) (err error)

功能: 删除目录。

S

Select

func Select(nfd int, r *FdSet, w *FdSet, e *FdSet, timeout *Timeval) (n int, err error)

功能: 同步多路复用 I/O。

Setenv

func Setenv(key, value string) error

功能: 设置环境变量。

Setgid

func Setgid(gid int) (err error)

功能: 设置组 ID。

Setpgid

func Setpgid(pid int, pgid int) (err error)

功能: 设置进程组 ID。

Setpriority

func Setpriority(which int, who int, prio int) (err error)

功能: 设置进程优先级。

Setrlimit

func Setrlimit(resource int, rlim *Rlimit) (err error)

功能: 设置资源限制。

Setsid

func Setsid() (pid int, err error)

功能: 创建新会话。

Setuid

func Setuid(uid int) (err error)

功能: 设置用户 ID。

Shutdown

func Shutdown(fd int, how int) (err error)

功能: 关闭 socket 连接。

Socket

func Socket(domain, typ, proto int) (fd int, err error)

功能: 创建 socket。

Socketpair

func Socketpair(domain, typ, proto int) (fd [2]int, err error)

功能: 创建 socket 对。

Stat

func Stat(path string, stat *Stat_t) (err error)

功能: 获取文件状态。

参数

  • path string - 文件路径
  • stat *Stat_t - 状态结构

返回值

  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    var stat syscall.Stat_t
    if err := syscall.Stat("/etc/passwd", &stat); err != nil {
        fmt.Println("错误:", err)
        return
    }
    
    fmt.Printf("文件大小:%d 字节\n", stat.Size)
    fmt.Printf("inode: %d\n", stat.Ino)
    fmt.Printf("模式:%o\n", stat.Mode)
}

Statfs

func Statfs(path string, buf *Statfs_t) (err error)

功能: 获取文件系统状态。

func Symlink(oldpath string, newpath string) (err error)

功能: 创建符号链接。

T

Truncate

func Truncate(path string, length int64) (err error)

功能: 截断文件。

U

Umask

func Umask(mask int) (oldmask int)

功能: 设置文件创建掩码。

func Unlink(path string) (err error)

功能: 删除文件。

Unsetenv

func Unsetenv(key string) error

功能: 删除环境变量。

W

Wait4

func Wait4(pid int, wstatus *WaitStatus, options int, rusage *Rusage) (wpid int, err error)

功能: 等待子进程状态改变。

Write

func Write(fd int, p []byte) (n int, err error)

功能: 写入数据到文件描述符。

参数

  • fd int - 文件描述符
  • p []byte - 数据

返回值

  • n int - 写入的字节数
  • error - 错误

示例

package main

import (
    "fmt"
    "syscall"
)

func main() {
    fd, err := syscall.Open("/tmp/test.txt", syscall.O_WRONLY|syscall.O_CREAT, 0644)
    if err != nil {
        fmt.Println("错误:", err)
        return
    }
    defer syscall.Close(fd)
    
    n, err := syscall.Write(fd, []byte("Hello, World!"))
    if err != nil {
        fmt.Println("写入错误:", err)
        return
    }
    
    fmt.Println("写入了", n, "字节")
}

典型示例

示例 1:文件操作

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 打开文件
    fd, err := syscall.Open("/tmp/test.txt", syscall.O_RDWR|syscall.O_CREAT, 0644)
    if err != nil {
        fmt.Println("打开失败:", err)
        return
    }
    defer syscall.Close(fd)
    
    // 写入数据
    syscall.Write(fd, []byte("Hello"))
    
    // 获取文件状态
    var stat syscall.Stat_t
    syscall.Fstat(fd, &stat)
    fmt.Printf("文件大小:%d\n", stat.Size)
    
    // 截断文件
    syscall.Ftruncate(fd, 0)
}

示例 2:进程管理

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 获取进程信息
    fmt.Println("PID:", syscall.Getpid())
    fmt.Println("PPID:", syscall.Getppid())
    fmt.Println("UID:", syscall.Getuid())
    fmt.Println("GID:", syscall.Getgid())
    
    // 获取资源使用
    var rusage syscall.Rusage
    syscall.Getrusage(syscall.RUSAGE_SELF, &rusage)
    fmt.Printf("最大内存:%d KB\n", rusage.Maxrss)
}

示例 3:环境变量

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 获取
    if val, found := syscall.Getenv("PATH"); found {
        fmt.Println("PATH:", val)
    }
    
    // 设置
    syscall.Setenv("MY_VAR", "value")
    
    // 再次获取
    fmt.Println(syscall.Getenv("MY_VAR"))
    
    // 删除
    syscall.Unsetenv("MY_VAR")
    
    // 获取所有环境变量
    for _, env := range syscall.Environ() {
        fmt.Println(env)
    }
}

示例 4:管道通信

package main

import (
    "fmt"
    "syscall"
)

func main() {
    var p [2]int
    syscall.Pipe(p[:])
    
    // 写数据
    syscall.Write(p[1], []byte("Hello"))
    
    // 读数据
    buf := make([]byte, 100)
    n, _ := syscall.Read(p[0], buf)
    fmt.Println(string(buf[:n])) // Hello
    
    // 关闭
    syscall.Close(p[0])
    syscall.Close(p[1])
}

示例 5:信号处理

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 获取自身 PID
    pid := syscall.Getpid()
    fmt.Println("当前 PID:", pid)
    
    // 可以发送信号给自己
    // syscall.Kill(pid, syscall.SIGTERM)
}

示例 6:资源限制

package main

import (
    "fmt"
    "syscall"
)

func main() {
    var rlim syscall.Rlimit
    
    // 获取当前限制
    syscall.Getrlimit(syscall.RLIMIT_NOFILE, &rlim)
    fmt.Printf("文件描述符限制:Cur=%d, Max=%d\n", rlim.Cur, rlim.Max)
    
    // 设置新限制
    rlim.Cur = 1024
    rlim.Max = 4096
    syscall.Setrlimit(syscall.RLIMIT_NOFILE, &rlim)
}

示例 7:内存映射

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 打开文件
    fd, _ := syscall.Open("/tmp/test.bin", syscall.O_RDWR|syscall.O_CREAT, 0644)
    defer syscall.Close(fd)
    
    // 设置文件大小
    syscall.Ftruncate(fd, 4096)
    
    // 内存映射
    data, err := syscall.Mmap(fd, 0, 4096, syscall.PROT_READ|syscall.PROT_WRITE, syscall.MAP_SHARED)
    if err != nil {
        fmt.Println("错误:", err)
        return
    }
    
    // 使用映射的内存
    data[0] = 'H'
    data[1] = 'i'
    
    // 取消映射
    syscall.Munmap(data)
}

示例 8:目录操作

package main

import (
    "fmt"
    "syscall"
)

func main() {
    // 获取当前目录
    wd, _ := syscall.Getwd()
    fmt.Println("当前目录:", wd)
    
    // 改变目录
    syscall.Chdir("/tmp")
    
    // 创建目录
    syscall.Mkdir("/tmp/testdir", 0755)
    
    // 删除目录
    syscall.Rmdir("/tmp/testdir")
    
    // 恢复目录
    syscall.Chdir(wd)
}

最佳实践

1. 优先使用高级包

// ✅ 推荐:使用 os 包
file, _ := os.Open("/tmp/test.txt")
defer file.Close()

// ⚠️ 不推荐:直接使用 syscall
fd, _ := syscall.Open("/tmp/test.txt", syscall.O_RDONLY, 0)
defer syscall.Close(fd)

2. 正确关闭文件描述符

// ✅ 推荐
fd, err := syscall.Open(path, mode, perm)
if err != nil {
    return err
}
defer syscall.Close(fd)

// ⚠️ 不推荐:忘记关闭
fd, _ := syscall.Open(path, mode, perm)
// 使用 fd...
// 忘记关闭会导致资源泄漏

3. 检查所有错误

// ✅ 推荐
if err := syscall.Chmod(path, mode); err != nil {
    // 处理错误
}

// ⚠️ 不推荐:忽略错误
syscall.Chmod(path, mode) // 可能失败

4. 使用 golang.org/x/sys

// ✅ 推荐:使用 x/sys
import "golang.org/x/sys/unix"
unix.Open(...)

// ⚠️ 不推荐:syscall 已不推荐
import "syscall"
syscall.Open(...)

与其他包配合

与 os 包配合

package main

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

func main() {
    // os.File 获取 syscall 文件描述符
    file, _ := os.Open("/tmp/test.txt")
    defer file.Close()
    
    fd := int(file.Fd())
    
    // 使用 syscall 操作
    var stat syscall.Stat_t
    syscall.Fstat(fd, &stat)
    fmt.Println("文件大小:", stat.Size)
}

与 unsafe 包配合

package main

import (
    "syscall"
    "unsafe"
)

func main() {
    // C 风格字符串
    ptr, _ := syscall.BytePtrFromString("hello")
    
    // 使用 unsafe 转换
    _ = uintptr(unsafe.Pointer(ptr))
}

注意事项

限制

  1. 平台相关

    • 不同操作系统有不同的系统调用号
    • 某些函数只在特定平台可用
  2. 不推荐使用

    • 大多数 syscall 函数已被更高级的包替代
    • 新代码应使用 golang.org/x/sys
  3. 错误处理

    • 错误类型为 Errno
    • 需要手动检查所有错误
  4. 可移植性

    • 直接使用 syscall 会降低代码可移植性
    • 优先使用 os、net 等标准库

使用建议

  1. 何时使用 syscall

    • 需要访问底层系统功能
    • 标准库不提供相应功能
    • 性能关键代码
  2. 何时避免

    • 有标准库替代(os、net、time)
    • 需要跨平台支持
    • 一般应用代码

快速参考

文件操作

函数功能
Open打开文件
Close关闭文件
Read读取文件
Write写入文件
Stat获取文件状态
Chmod改变权限
Chown改变所有者
Link创建硬链接
Symlink创建符号链接
Unlink删除文件

进程管理

函数功能
Getpid获取进程 ID
Getppid获取父进程 ID
Getuid获取用户 ID
Getgid获取组 ID
ForkExecfork 并 exec
Exec执行新程序
Exit退出进程
Wait4等待子进程
Kill发送信号

环境变量

函数功能
Getenv获取环境变量
Setenv设置环境变量
Unsetenv删除环境变量
Environ获取所有环境变量
Clearenv清空环境变量

网络

函数功能
Socket创建 socket
Bind绑定地址
Listen监听
Accept接受连接
Connect连接
Sendto发送数据
Recvfrom接收数据
Shutdown关闭连接

常见错误

错误含义
ENOENT文件或目录不存在
EACCES权限不足
EEXIST文件已存在
EINVAL参数无效
ENOMEM内存不足
EBUSY资源忙
EINTR系统调用被中断

总结

syscall 包提供了对底层操作系统原语的接口。

核心优势

  • ✅ 直接访问系统调用
  • ✅ 完整的系统功能支持
  • ✅ 高性能(无额外抽象)

重要限制

  • ⚠️ 平台相关,可移植性差
  • ⚠️ 不推荐使用,优先使用 golang.org/x/sys
  • ⚠️ 需要手动管理资源
  • ⚠️ 错误处理复杂

主要用途

  • 文件操作(Open、Read、Write、Stat)
  • 进程管理(ForkExec、Exec、Wait4)
  • 网络编程(Socket、Bind、Listen)
  • 系统信息(Getpid、Getuid、Getrusage)
  • 资源管理(Getrlimit、Setrlimit)

使用建议

  1. 优先使用 os、net、time 等高级包
  2. 新代码使用 golang.org/x/sys
  3. 始终检查错误
  4. 正确关闭文件描述符
  5. 注意平台差异

现代替代方案

  • golang.org/x/sys/unix(Unix 系统)
  • golang.org/x/sys/windows(Windows 系统)
  • os、net、time 等标准库包