mirror of
				https://github.com/tailscale/tailscale.git
				synced 2025-10-31 08:11:32 +01:00 
			
		
		
		
	Removes 434 KB from the minimal Linux binary, or ~3%. Primarily this comes from not linking in the zstd encoding code. Fixes #17323 Change-Id: I0a90de307dfa1ad7422db7aa8b1b46c782bfaaf7 Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
		
			
				
	
	
		
			86 lines
		
	
	
		
			1.6 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
			
		
		
	
	
			86 lines
		
	
	
		
			1.6 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
| // Copyright (c) Tailscale Inc & AUTHORS
 | |
| // SPDX-License-Identifier: BSD-3-Clause
 | |
| 
 | |
| //go:build !ts_omit_logtail
 | |
| 
 | |
| package logtail
 | |
| 
 | |
| import (
 | |
| 	"bytes"
 | |
| 	"errors"
 | |
| 	"fmt"
 | |
| 	"sync"
 | |
| )
 | |
| 
 | |
| type Buffer interface {
 | |
| 	// TryReadLine tries to read a log line from the ring buffer.
 | |
| 	// If no line is available it returns a nil slice.
 | |
| 	// If the ring buffer is closed it returns io.EOF.
 | |
| 	//
 | |
| 	// The returned slice may point to data that will be overwritten
 | |
| 	// by a subsequent call to TryReadLine.
 | |
| 	TryReadLine() ([]byte, error)
 | |
| 
 | |
| 	// Write writes a log line into the ring buffer.
 | |
| 	// Implementations must not retain the provided buffer.
 | |
| 	Write([]byte) (int, error)
 | |
| }
 | |
| 
 | |
| func NewMemoryBuffer(numEntries int) Buffer {
 | |
| 	return &memBuffer{
 | |
| 		pending: make(chan qentry, numEntries),
 | |
| 	}
 | |
| }
 | |
| 
 | |
| type memBuffer struct {
 | |
| 	next    []byte
 | |
| 	pending chan qentry
 | |
| 
 | |
| 	dropMu    sync.Mutex
 | |
| 	dropCount int
 | |
| }
 | |
| 
 | |
| func (m *memBuffer) TryReadLine() ([]byte, error) {
 | |
| 	if m.next != nil {
 | |
| 		msg := m.next
 | |
| 		m.next = nil
 | |
| 		return msg, nil
 | |
| 	}
 | |
| 
 | |
| 	select {
 | |
| 	case ent := <-m.pending:
 | |
| 		if ent.dropCount > 0 {
 | |
| 			m.next = ent.msg
 | |
| 			return fmt.Appendf(nil, "----------- %d logs dropped ----------", ent.dropCount), nil
 | |
| 		}
 | |
| 		return ent.msg, nil
 | |
| 	default:
 | |
| 		return nil, nil
 | |
| 	}
 | |
| }
 | |
| 
 | |
| func (m *memBuffer) Write(b []byte) (int, error) {
 | |
| 	m.dropMu.Lock()
 | |
| 	defer m.dropMu.Unlock()
 | |
| 
 | |
| 	ent := qentry{
 | |
| 		msg:       bytes.Clone(b),
 | |
| 		dropCount: m.dropCount,
 | |
| 	}
 | |
| 	select {
 | |
| 	case m.pending <- ent:
 | |
| 		m.dropCount = 0
 | |
| 		return len(b), nil
 | |
| 	default:
 | |
| 		m.dropCount++
 | |
| 		return 0, errBufferFull
 | |
| 	}
 | |
| }
 | |
| 
 | |
| type qentry struct {
 | |
| 	msg       []byte
 | |
| 	dropCount int
 | |
| }
 | |
| 
 | |
| var errBufferFull = errors.New("logtail: buffer full")
 |