Source File
pool.go
Belonging Package
github.com/libp2p/go-buffer-pool
// Package pool provides a sync.Pool equivalent that buckets incoming// requests to one of 32 sub-pools, one for each power of 2, 0-32.//// import (pool "github.com/libp2p/go-buffer-pool")// var p pool.BufferPool//// small := make([]byte, 1024)// large := make([]byte, 4194304)// p.Put(small)// p.Put(large)//// small2 := p.Get(1024)// large2 := p.Get(4194304)// fmt.Println("small2 len:", len(small2))// fmt.Println("large2 len:", len(large2))//// // Output:// // small2 len: 1024// // large2 len: 4194304//package poolimport ()// GlobalPool is a static Pool for reusing byteslices of various sizes.var GlobalPool = new(BufferPool)// MaxLength is the maximum length of an element that can be added to the Pool.const MaxLength = math.MaxInt32// BufferPool is a pool to handle cases of reusing elements of varying sizes. It// maintains 32 internal pools, for each power of 2 in 0-32.//// You should generally just call the package level Get and Put methods or use// the GlobalPool BufferPool instead of constructing your own.//// You MUST NOT copy Pool after using.type BufferPool struct {pools [32]sync.Pool // a list of singlePoolsptrs sync.Pool}type bufp struct {buf []byte}// Get retrieves a buffer of the appropriate length from the buffer pool or// allocates a new one. Get may choose to ignore the pool and treat it as empty.// Callers should not assume any relation between values passed to Put and the// values returned by Get.//// If no suitable buffer exists in the pool, Get creates one.func ( *BufferPool) ( int) []byte {if == 0 {return nil}// Calling this function with a negative length is invalid.// make will panic if length is negative, so we don't have to.if > MaxLength || < 0 {return make([]byte, )}:= nextLogBase2(uint32())if := .pools[].Get(); != nil {:= .(*bufp):= .buf[:uint32()].buf = nil.ptrs.Put()return}return make([]byte, 1<<)[:uint32()]}// Put adds x to the pool.func ( *BufferPool) ( []byte) {:= cap()if == 0 || > MaxLength {return // drop it}:= prevLogBase2(uint32())var *bufpif := .ptrs.Get(); != nil {= .(*bufp)} else {= new(bufp)}.buf =.pools[].Put()}// Get retrieves a buffer of the appropriate length from the global buffer pool// (or allocates a new one).func ( int) []byte {return GlobalPool.Get()}// Put returns a buffer to the global buffer pool.func ( []byte) {GlobalPool.Put()}// Log of base two, round up (for v > 0).func nextLogBase2( uint32) uint32 {return uint32(bits.Len32( - 1))}// Log of base two, round down (for v > 0)func prevLogBase2( uint32) uint32 {:= nextLogBase2()if == (1 << uint32()) {return}return - 1}
![]() |
The pages are generated with Golds v0.8.2. (GOOS=linux GOARCH=amd64) Golds is a Go 101 project developed by Tapir Liu. PR and bug reports are welcome and can be submitted to the issue list. Please follow @zigo_101 (reachable from the left QR code) to get the latest news of Golds. |