mirror of
https://github.com/protocolbuffers/protobuf-go.git
synced 2025-01-30 12:32:36 +00:00
94bb78c93b
There currently is no risk of producing invalid wire format, but that will change with subsequent changes regarding lazy decoding. We have been running this change in production for about a month, without ever triggering the check (until lazy decoding is involved). related to golang/protobuf#1609 Change-Id: I3c5c956aee2fa81f99dea03ed2a977a1547081fc Reviewed-on: https://go-review.googlesource.com/c/protobuf/+/579595 Auto-Submit: Michael Stapelberg <stapelberg@google.com> Reviewed-by: Lasse Folger <lassefolger@google.com> LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
105 lines
2.5 KiB
Go
105 lines
2.5 KiB
Go
// Copyright 2018 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.
|
||
|
||
// Package errors implements functions to manipulate errors.
|
||
package errors
|
||
|
||
import (
|
||
"errors"
|
||
"fmt"
|
||
|
||
"google.golang.org/protobuf/internal/detrand"
|
||
)
|
||
|
||
// Error is a sentinel matching all errors produced by this package.
|
||
var Error = errors.New("protobuf error")
|
||
|
||
// New formats a string according to the format specifier and arguments and
|
||
// returns an error that has a "proto" prefix.
|
||
func New(f string, x ...interface{}) error {
|
||
return &prefixError{s: format(f, x...)}
|
||
}
|
||
|
||
type prefixError struct{ s string }
|
||
|
||
var prefix = func() string {
|
||
// Deliberately introduce instability into the error message string to
|
||
// discourage users from performing error string comparisons.
|
||
if detrand.Bool() {
|
||
return "proto: " // use non-breaking spaces (U+00a0)
|
||
} else {
|
||
return "proto: " // use regular spaces (U+0020)
|
||
}
|
||
}()
|
||
|
||
func (e *prefixError) Error() string {
|
||
return prefix + e.s
|
||
}
|
||
|
||
func (e *prefixError) Unwrap() error {
|
||
return Error
|
||
}
|
||
|
||
// Wrap returns an error that has a "proto" prefix, the formatted string described
|
||
// by the format specifier and arguments, and a suffix of err. The error wraps err.
|
||
func Wrap(err error, f string, x ...interface{}) error {
|
||
return &wrapError{
|
||
s: format(f, x...),
|
||
err: err,
|
||
}
|
||
}
|
||
|
||
type wrapError struct {
|
||
s string
|
||
err error
|
||
}
|
||
|
||
func (e *wrapError) Error() string {
|
||
return format("%v%v: %v", prefix, e.s, e.err)
|
||
}
|
||
|
||
func (e *wrapError) Unwrap() error {
|
||
return e.err
|
||
}
|
||
|
||
func (e *wrapError) Is(target error) bool {
|
||
return target == Error
|
||
}
|
||
|
||
func format(f string, x ...interface{}) string {
|
||
// avoid "proto: " prefix when chaining
|
||
for i := 0; i < len(x); i++ {
|
||
switch e := x[i].(type) {
|
||
case *prefixError:
|
||
x[i] = e.s
|
||
case *wrapError:
|
||
x[i] = format("%v: %v", e.s, e.err)
|
||
}
|
||
}
|
||
return fmt.Sprintf(f, x...)
|
||
}
|
||
|
||
func InvalidUTF8(name string) error {
|
||
return New("field %v contains invalid UTF-8", name)
|
||
}
|
||
|
||
func RequiredNotSet(name string) error {
|
||
return New("required field %v not set", name)
|
||
}
|
||
|
||
type SizeMismatchError struct {
|
||
Calculated, Measured int
|
||
}
|
||
|
||
func (e *SizeMismatchError) Error() string {
|
||
return fmt.Sprintf("size mismatch (see https://github.com/golang/protobuf/issues/1609): calculated=%d, measured=%d", e.Calculated, e.Measured)
|
||
}
|
||
|
||
func MismatchedSizeCalculation(calculated, measured int) error {
|
||
return &SizeMismatchError{
|
||
Calculated: calculated,
|
||
Measured: measured,
|
||
}
|
||
}
|