c/os: Setrlimit/Getrlimit
This commit is contained in:
52
internal/lib/syscall/rlimit.go
Normal file
52
internal/lib/syscall/rlimit.go
Normal file
@@ -0,0 +1,52 @@
|
||||
// Copyright 2022 The Go Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
//go:build unix
|
||||
|
||||
package syscall
|
||||
|
||||
import (
|
||||
"sync/atomic"
|
||||
|
||||
"github.com/goplus/llgo/c/syscall"
|
||||
)
|
||||
|
||||
// origRlimitNofile, if not {0, 0}, is the original soft RLIMIT_NOFILE.
|
||||
// When we can assume that we are bootstrapping with Go 1.19,
|
||||
// this can be atomic.Pointer[Rlimit].
|
||||
var origRlimitNofile atomic.Value // of Rlimit
|
||||
|
||||
// Some systems set an artificially low soft limit on open file count, for compatibility
|
||||
// with code that uses select and its hard-coded maximum file descriptor
|
||||
// (limited by the size of fd_set).
|
||||
//
|
||||
// Go does not use select, so it should not be subject to these limits.
|
||||
// On some systems the limit is 256, which is very easy to run into,
|
||||
// even in simple programs like gofmt when they parallelize walking
|
||||
// a file tree.
|
||||
//
|
||||
// After a long discussion on go.dev/issue/46279, we decided the
|
||||
// best approach was for Go to raise the limit unconditionally for itself,
|
||||
// and then leave old software to set the limit back as needed.
|
||||
// Code that really wants Go to leave the limit alone can set the hard limit,
|
||||
// which Go of course has no choice but to respect.
|
||||
func init() {
|
||||
var lim Rlimit
|
||||
if err := Getrlimit(syscall.RLIMIT_NOFILE, &lim); err == nil && lim.Cur != lim.Max {
|
||||
origRlimitNofile.Store(lim)
|
||||
lim.Cur = lim.Max
|
||||
adjustFileLimit(&lim)
|
||||
setrlimit(syscall.RLIMIT_NOFILE, &lim)
|
||||
}
|
||||
}
|
||||
|
||||
func Setrlimit(resource int, rlim *Rlimit) error {
|
||||
err := setrlimit(resource, rlim)
|
||||
if err == nil && resource == syscall.RLIMIT_NOFILE {
|
||||
// Store zeroes in origRlimitNofile to tell StartProcess
|
||||
// to not adjust the rlimit in the child process.
|
||||
origRlimitNofile.Store(Rlimit{0, 0})
|
||||
}
|
||||
return err
|
||||
}
|
||||
Reference in New Issue
Block a user