XTLS/Xray-core · warning

failed to write addons protobuf value

Error message

failed to write addons protobuf value

What it means

After successfully writing the one-byte length, Xray writes the marshaled addons protobuf bytes into the header buffer. Buffer.Write fails only when the serialized addons exceed the remaining buffer capacity — i.e. a addons message larger than ~2KB, which the current schema cannot produce. Internal invariant; not expected at runtime.

Source

Thrown at proxy/vless/encoding/addons.go:28

	"github.com/xtls/xray-core/common/protocol"
	"github.com/xtls/xray-core/common/session"
	"github.com/xtls/xray-core/proxy"
	"github.com/xtls/xray-core/proxy/vless"
	"google.golang.org/protobuf/proto"
)

func EncodeHeaderAddons(buffer *buf.Buffer, addons *Addons) error {
	switch addons.Flow {
	case vless.XRV:
		bytes, err := proto.Marshal(addons)
		if err != nil {
			return errors.New("failed to marshal addons protobuf value").Base(err)
		}
		if err := buffer.WriteByte(byte(len(bytes))); err != nil {
			return errors.New("failed to write addons protobuf length").Base(err)
		}
		if _, err := buffer.Write(bytes); err != nil {
			return errors.New("failed to write addons protobuf value").Base(err)
		}
	default:
		if err := buffer.WriteByte(0); err != nil {
			return errors.New("failed to write addons protobuf length").Base(err)
		}
	}

	return nil
}

func DecodeHeaderAddons(buffer *buf.Buffer, reader io.Reader) (*Addons, error) {
	addons := new(Addons)
	buffer.Clear()
	if _, err := buffer.ReadFullFrom(reader, 1); err != nil {
		return nil, errors.New("failed to read addons protobuf length").Base(err)
	}

	if length := int32(buffer.Byte(0)); length != 0 {

View on GitHub (pinned to 7d214f8b09)

Solutions

  1. Use official builds; if extending addons in a fork, cap field sizes or enlarge the buffer
  2. Report upstream with the config that triggered it
Defensive patterns

Strategy: try-catch

Try / catch

if err := encoding.EncodeHeaderAddons(buffer, addons); err != nil {
	log.Warnf("addons encode: %v", err)
	return conn.Close()
}

Prevention

When it happens

Trigger: A fork adding very large fields to Addons (e.g. long seed/test values) exceeding buf.Buffer capacity; otherwise unreachable.

Common situations: Custom builds extending the addons proto with big payloads (Testpre/Testseed experiments) without resizing buffers.

Related errors


AI-assisted analysis of XTLS/Xray-core@7d214f8b09 (2026-08-15). Data as JSON: /api/errors/2a02949cf8632410. Report an issue: GitHub.