Go 编码建议——安全篇

2024-06-26 08:55:33 浏览数 (1)

文章目录

  • 1.内存管理
    • 1.切片长度校验
    • 2.指针判空
    • 3.整数安全

1.内存管理

1.切片长度校验

在对 slice 进行操作时,必须判断长度是否合法,防止程序 panic。

代码语言:javascript复制
// bad: slice bounds out of range
func foo(slice []int){
	fmt.Println(slice[:10])
}

// good: check the slice length
func foo(slice []int){
	if len(slice) >= 10 {
		fmt.Println(slice[:10])
		return
	}
	fmt.Println("no enough elems in slice")
}

2.指针判空

进行指针操作时,必须判断该指针是否为 nil,防止程序 panic,尤其在进行结构体Unmarshal 时。

代码语言:javascript复制
type Packet struct {
	Type    uint8
	Version uint8
	Data    *Data
}
type Data struct {
	Stat uint8
	Len  uint8
	Buf  [8]byte
}

// bad
func foo(p Packet) {
	fmt.Println(p.Data.Stat)
}

// good
func foo(p Packet) {
	if p.Data != nil {
		fmt.Println(p.Data.Stat)
		return
	}
	fmt.Println("packet is nil")
}

3.整数安全

在进行数字运算操作时,需要做好长度限制,防止外部输入运算导致异常:

  • 确保无符号整数运算时不会出现符号反转
  • 确保有符号整数运算时不会出现溢出
代码语言:javascript复制
// bad:未限制长度,导致整数溢出
func overflow(n int32) {
	var num int32 = 0
	num = n   1
	// 对长度限制不当,导致整数溢出
	fmt.Printf("%dn", num)
	// 使用 numInt,可能导致其他错误
}

func main() {
	overflow(2147483647)
}

// good
func overflow(n int32) {
	var num int32 = 0
	num = n   1
	if num < 0 {
		fmt.Println("integer overflow")
		return
	}
	fmt.Println("integer ok")
}

func main(){
	overflow(2147483647)
}
  • 确保整型转换时不会出现截断错误
  • 确保整型转换时不会出现符号错误

以下场景必须严格进行长度限制:

  • 作为数组索引
  • 作为对象的长度或者大小
  • 作为数组的边界(如作为循环计数器)

0 人点赞