diff --git a/go.sum b/go.sum
index ad4ba2a93b..cabfccd98f 100644
--- a/go.sum
+++ b/go.sum
@@ -130,6 +130,7 @@ github.com/alessio/shellescape v1.4.1/go.mod h1:PZAiSCk0LJaZkiCSkPv8qIobYglO3FPp
github.com/andreyvit/diff v0.0.0-20170406064948-c7f18ee00883/go.mod h1:rCTlJbsFo29Kk6CurOXKm700vrz8f0KW0JNfpkRJY/8=
github.com/anmitsu/go-shlex v0.0.0-20161002113705-648efa622239/go.mod h1:2FmKhYUyUczH0OGQWaF5ceTx0UBShxjsH6f8oGKYe2c=
github.com/antihax/optional v1.0.0/go.mod h1:uupD/76wgC+ih3iEmQUL+0Ugr19nfwCT1kdvxnR2qWY=
+github.com/antlr/antlr4/runtime/Go/antlr v0.0.0-20210826220005-b48c857c3a0e h1:GCzyKMDDjSGnlpl3clrdAK7I1AaVoaiKDOYkUzChZzg=
github.com/antlr/antlr4/runtime/Go/antlr v0.0.0-20210826220005-b48c857c3a0e/go.mod h1:F7bn7fEU90QkQ3tnmaTx3LTKLEDqnwWODIYppRQ5hnY=
github.com/apache/thrift v0.12.0/go.mod h1:cp2SuWMxlEZw2r+iP2GNCdIi4C1qmUzdZFSVb+bacwQ=
github.com/apache/thrift v0.13.0/go.mod h1:cp2SuWMxlEZw2r+iP2GNCdIi4C1qmUzdZFSVb+bacwQ=
@@ -553,6 +554,7 @@ github.com/google/btree v0.0.0-20180813153112-4030bb1f1f0c/go.mod h1:lNA+9X1NB3Z
github.com/google/btree v1.0.0/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ=
github.com/google/btree v1.0.1 h1:gK4Kx5IaGY9CD5sPJ36FHiBJ6ZXl0kilRiiCj+jdYp4=
github.com/google/btree v1.0.1/go.mod h1:xXMiIv4Fb/0kKde4SpL7qlzvu5cMJDRkFDxJfI9uaxA=
+github.com/google/cel-go v0.9.0 h1:u1hg7lcZ/XWw2d3aV1jFS30ijQQ6q0/h1C2ZBeBD1gY=
github.com/google/cel-go v0.9.0/go.mod h1:U7ayypeSkw23szu4GaQTPJGx66c20mx8JklMSxrmI1w=
github.com/google/cel-spec v0.6.0/go.mod h1:Nwjgxy5CbjlPrtCWjeDjUyKMl8w41YBYGjsyDdqk0xA=
github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
@@ -1075,6 +1077,7 @@ github.com/spf13/viper v1.3.2/go.mod h1:ZiWeW+zYFKm7srdB9IoDzzZXaJaI5eL9QjNiN/DM
github.com/spf13/viper v1.4.0/go.mod h1:PTJ7Z/lr49W6bUbkmS1V3by4uWynFiR9p7+dSq/yZzE=
github.com/spf13/viper v1.7.0/go.mod h1:8WkrPz2fc9jxqZNCJI/76HCieCp4Q8HaLFoCha5qpdg=
github.com/spf13/viper v1.8.1/go.mod h1:o0Pch8wJ9BVSWGQMbra6iw0oQ5oktSIBaujf1rJH9Ns=
+github.com/stoewer/go-strcase v1.2.0 h1:Z2iHWqGXH00XYgqDmNgQbIBxf3wrNq0F3feEy0ainaU=
github.com/stoewer/go-strcase v1.2.0/go.mod h1:IBiWB2sKIp3wVVQ3Y035++gc+knqhUQag1KpM8ahLw8=
github.com/streadway/amqp v0.0.0-20190404075320-75d898a42a94/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw=
github.com/streadway/amqp v0.0.0-20190827072141-edfb9018d271/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw=
diff --git a/pkg/controller/registry/resolver/cache/predicates.go b/pkg/controller/registry/resolver/cache/predicates.go
index 9bdf097dc9..25200917e9 100644
--- a/pkg/controller/registry/resolver/cache/predicates.go
+++ b/pkg/controller/registry/resolver/cache/predicates.go
@@ -6,7 +6,6 @@ import (
"fmt"
"github.com/blang/semver/v4"
-
opregistry "github.com/operator-framework/operator-registry/pkg/registry"
)
@@ -282,6 +281,32 @@ func (p orPredicate) String() string {
return b.String()
}
+func Not(p ...Predicate) Predicate {
+ return notPredicate{
+ predicates: p,
+ }
+}
+
+type notPredicate struct {
+ predicates []Predicate
+}
+
+func (p notPredicate) Test(o *Entry) bool {
+ // !pred && !pred is equivalent to !(pred || pred).
+ return !orPredicate{p.predicates}.Test(o)
+}
+
+func (p notPredicate) String() string {
+ var b bytes.Buffer
+ for i, predicate := range p.predicates {
+ b.WriteString(predicate.String())
+ if i != len(p.predicates)-1 {
+ b.WriteString(" and not ")
+ }
+ }
+ return b.String()
+}
+
type booleanPredicate struct {
result bool
}
diff --git a/pkg/controller/registry/resolver/resolver.go b/pkg/controller/registry/resolver/resolver.go
index 5f865a6db9..6b1d8a6d80 100644
--- a/pkg/controller/registry/resolver/resolver.go
+++ b/pkg/controller/registry/resolver/resolver.go
@@ -11,6 +11,7 @@ import (
"github.com/sirupsen/logrus"
utilerrors "k8s.io/apimachinery/pkg/util/errors"
+ "github.com/operator-framework/api/pkg/constraints"
"github.com/operator-framework/api/pkg/operators/v1alpha1"
v1alpha1listers "github.com/operator-framework/operator-lifecycle-manager/pkg/api/client/listers/operators/v1alpha1"
"github.com/operator-framework/operator-lifecycle-manager/pkg/controller/registry/resolver/cache"
@@ -27,12 +28,14 @@ type OperatorResolver interface {
type SatResolver struct {
cache cache.OperatorCacheProvider
log logrus.FieldLogger
+ pc *predicateConverter
}
func NewDefaultSatResolver(rcp cache.SourceProvider, catsrcLister v1alpha1listers.CatalogSourceLister, logger logrus.FieldLogger) *SatResolver {
return &SatResolver{
cache: cache.New(rcp, cache.WithLogger(logger), cache.WithCatalogSourceLister(catsrcLister)),
log: logger,
+ pc: &predicateConverter{},
}
}
@@ -337,7 +340,7 @@ func (r *SatResolver) getBundleInstallables(preferredNamespace string, bundleSta
visited[bundle] = &bundleInstallable
- dependencyPredicates, err := DependencyPredicates(bundle.Properties)
+ dependencyPredicates, err := r.pc.convertDependencyProperties(bundle.Properties)
if err != nil {
errs = append(errs, err)
continue
@@ -733,10 +736,14 @@ func sortChannel(bundles []*cache.Entry) ([]*cache.Entry, error) {
return chains[0], nil
}
-func DependencyPredicates(properties []*api.Property) ([]cache.Predicate, error) {
+// predicateConverter configures olm.constraint value -> predicate conversion for the resolver.
+type predicateConverter struct{}
+
+// convertDependencyProperties converts all known constraint properties to predicates.
+func (pc *predicateConverter) convertDependencyProperties(properties []*api.Property) ([]cache.Predicate, error) {
var predicates []cache.Predicate
for _, property := range properties {
- predicate, err := predicateForProperty(property)
+ predicate, err := pc.predicateForProperty(property)
if err != nil {
return nil, err
}
@@ -748,18 +755,80 @@ func DependencyPredicates(properties []*api.Property) ([]cache.Predicate, error)
return predicates, nil
}
-func predicateForProperty(property *api.Property) (cache.Predicate, error) {
+func (pc *predicateConverter) predicateForProperty(property *api.Property) (cache.Predicate, error) {
if property == nil {
return nil, nil
}
- p, ok := predicates[property.Type]
+
+ // olm.constraint holds all constraint types except legacy types,
+ // so defer error handling to its parser.
+ if property.Type == constraints.OLMConstraintType {
+ return pc.predicateForConstraintProperty(property.Value)
+ }
+
+ // Legacy behavior dictates that unknown properties are ignored. See enhancement for details:
+ // https://github.com/operator-framework/enhancements/blob/master/enhancements/compound-bundle-constraints.md
+ p, ok := legacyPredicateParsers[property.Type]
if !ok {
return nil, nil
}
return p(property.Value)
}
-var predicates = map[string]func(string) (cache.Predicate, error){
+func (pc *predicateConverter) predicateForConstraintProperty(value string) (cache.Predicate, error) {
+ constraint, err := constraints.Parse(json.RawMessage([]byte(value)))
+ if err != nil {
+ return nil, fmt.Errorf("parse olm.constraint: %v", err)
+ }
+
+ preds, err := pc.convertConstraints(constraint)
+ if err != nil {
+ return nil, fmt.Errorf("convert olm.constraint to resolver predicate: %v", err)
+ }
+ return preds[0], nil
+}
+
+// convertConstraints creates predicates from each element of constraints, recursing on compound constraints.
+// New constraint types added to the constraints package must be handled here.
+func (pc *predicateConverter) convertConstraints(constraints ...constraints.Constraint) ([]cache.Predicate, error) {
+
+ preds := make([]cache.Predicate, len(constraints))
+ for i, constraint := range constraints {
+
+ var err error
+ switch {
+ case constraint.GVK != nil:
+ preds[i] = cache.ProvidingAPIPredicate(opregistry.APIKey{
+ Group: constraint.GVK.Group,
+ Version: constraint.GVK.Version,
+ Kind: constraint.GVK.Kind,
+ })
+ case constraint.Package != nil:
+ preds[i], err = newPackageRequiredPredicate(constraint.Package.PackageName, constraint.Package.VersionRange)
+ case constraint.All != nil:
+ subs, perr := pc.convertConstraints(constraint.All.Constraints...)
+ preds[i], err = cache.And(subs...), perr
+ case constraint.Any != nil:
+ subs, perr := pc.convertConstraints(constraint.Any.Constraints...)
+ preds[i], err = cache.Or(subs...), perr
+ case constraint.None != nil:
+ subs, perr := pc.convertConstraints(constraint.None.Constraints...)
+ preds[i], err = cache.Not(subs...), perr
+ default:
+ // Unknown constraint types are handled by constraints.Parse(),
+ // but parsed constraints may be empty.
+ return nil, fmt.Errorf("constraint is empty")
+ }
+ if err != nil {
+ return nil, err
+ }
+
+ }
+
+ return preds, nil
+}
+
+var legacyPredicateParsers = map[string]func(string) (cache.Predicate, error){
"olm.gvk.required": predicateForRequiredGVKProperty,
"olm.package.required": predicateForRequiredPackageProperty,
"olm.label.required": predicateForRequiredLabelProperty,
@@ -789,11 +858,15 @@ func predicateForRequiredPackageProperty(value string) (cache.Predicate, error)
if err := json.Unmarshal([]byte(value), &pkg); err != nil {
return nil, err
}
- ver, err := semver.ParseRange(pkg.VersionRange)
+ return newPackageRequiredPredicate(pkg.PackageName, pkg.VersionRange)
+}
+
+func newPackageRequiredPredicate(name, verRange string) (cache.Predicate, error) {
+ ver, err := semver.ParseRange(verRange)
if err != nil {
return nil, err
}
- return cache.And(cache.PkgPredicate(pkg.PackageName), cache.VersionInRangePredicate(ver, pkg.VersionRange)), nil
+ return cache.And(cache.PkgPredicate(name), cache.VersionInRangePredicate(ver, verRange)), nil
}
func predicateForRequiredLabelProperty(value string) (cache.Predicate, error) {
diff --git a/pkg/controller/registry/resolver/resolver_test.go b/pkg/controller/registry/resolver/resolver_test.go
index 30f633f47b..90d538b99e 100644
--- a/pkg/controller/registry/resolver/resolver_test.go
+++ b/pkg/controller/registry/resolver/resolver_test.go
@@ -3,7 +3,9 @@ package resolver
import (
"errors"
"fmt"
+ "math/rand"
"testing"
+ "time"
"github.com/blang/semver/v4"
"github.com/sirupsen/logrus"
@@ -14,6 +16,7 @@ import (
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/labels"
+ "github.com/operator-framework/api/pkg/constraints"
opver "github.com/operator-framework/api/pkg/lib/version"
"github.com/operator-framework/api/pkg/operators/v1alpha1"
listersv1alpha1 "github.com/operator-framework/operator-lifecycle-manager/pkg/api/client/listers/operators/v1alpha1"
@@ -23,8 +26,14 @@ import (
opregistry "github.com/operator-framework/operator-registry/pkg/registry"
)
+var testGVKKey = opregistry.APIKey{Group: "g", Version: "v", Kind: "k", Plural: "ks"}
+
+func init() {
+ rand.Seed(time.Now().UnixNano())
+}
+
func TestSolveOperators(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{Group: "g", Version: "v", Kind: "k", Plural: "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
const namespace = "test-namespace"
@@ -86,7 +95,7 @@ func TestPropertiesAnnotationHonored(t *testing.T) {
const (
namespace = "olm"
)
- community := cache.SourceKey{"community", namespace}
+ community := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", nil, nil, nil, nil)
csv.Annotations = map[string]string{"operatorframework.io/properties": `{"properties":[{"type":"olm.package","value":{"packageName":"packageA","version":"1.0.0"}}]}`}
@@ -116,11 +125,11 @@ func TestPropertiesAnnotationHonored(t *testing.T) {
}
func TestSolveOperators_MultipleChannels(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -153,11 +162,11 @@ func TestSolveOperators_MultipleChannels(t *testing.T) {
}
func TestSolveOperators_FindLatestVersion(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -200,11 +209,11 @@ func TestSolveOperators_FindLatestVersion(t *testing.T) {
}
func TestSolveOperators_FindLatestVersionWithDependencies(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -259,11 +268,11 @@ func TestSolveOperators_FindLatestVersionWithDependencies(t *testing.T) {
}
func TestSolveOperators_FindLatestVersionWithNestedDependencies(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -367,7 +376,7 @@ func TestSolveOperators_CatsrcPrioritySorting(t *testing.T) {
}
namespace := "olm"
- customCatalog := cache.SourceKey{"community", namespace}
+ customCatalog := cache.SourceKey{Name: "community", Namespace: namespace}
newSub := newSub(namespace, "packageA", "alpha", customCatalog)
subs := []*v1alpha1.Subscription{newSub}
@@ -502,12 +511,12 @@ func TestSolveOperators_CatsrcPrioritySorting(t *testing.T) {
}
-func TestSolveOperators_WithDependencies(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+func TestSolveOperators_WithPackageDependencies(t *testing.T) {
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -551,11 +560,11 @@ func TestSolveOperators_WithDependencies(t *testing.T) {
}
func TestSolveOperators_WithGVKDependencies(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- community := cache.SourceKey{"community", namespace}
+ community := cache.SourceKey{Name: "community", Namespace: namespace}
csvs := []*v1alpha1.ClusterServiceVersion{
existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", nil, nil, nil, nil),
@@ -601,7 +610,7 @@ func TestSolveOperators_WithGVKDependencies(t *testing.T) {
func TestSolveOperators_WithLabelDependencies(t *testing.T) {
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
newSub := newSub(namespace, "packageA", "alpha", catalog)
subs := []*v1alpha1.Subscription{newSub}
@@ -652,7 +661,7 @@ func TestSolveOperators_WithLabelDependencies(t *testing.T) {
func TestSolveOperators_WithUnsatisfiableLabelDependencies(t *testing.T) {
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
newSub := newSub(namespace, "packageA", "alpha", catalog)
subs := []*v1alpha1.Subscription{newSub}
@@ -681,11 +690,11 @@ func TestSolveOperators_WithUnsatisfiableLabelDependencies(t *testing.T) {
}
func TestSolveOperators_WithNestedGVKDependencies(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -757,10 +766,315 @@ func TestSolveOperators_WithNestedGVKDependencies(t *testing.T) {
}
}
+type operatorGenerator struct {
+ name, version string
+ replaces string
+ pkg, channel, defaultChannel string
+ catName, catNamespace string
+ requiredAPIs, providedAPIs cache.APISet
+ properties []*api.Property
+ deprecated bool
+}
+
+func (g operatorGenerator) gen() *cache.Entry {
+ entry := genOperator(g.name, g.version, g.replaces, g.pkg, g.channel, g.catName, g.catNamespace, g.requiredAPIs, g.providedAPIs, nil, g.defaultChannel, g.deprecated)
+ entry.Properties = append(entry.Properties, g.properties...)
+ return entry
+}
+
+func genOperatorsRandom(ops ...operatorGenerator) []*cache.Entry {
+ entries := make([]*cache.Entry, len(ops))
+ // Randomize entry order to fuzz input operators over time.
+ idxs := rand.Perm(len(ops))
+ for destIdx, srcIdx := range idxs {
+ entries[destIdx] = ops[srcIdx].gen()
+ }
+ return entries
+}
+
+func TestSolveOperators_OLMConstraint_CompoundAll(t *testing.T) {
+ namespace := "olm"
+ csName := "community"
+ catalog := cache.SourceKey{Name: csName, Namespace: namespace}
+
+ newOperatorGens := []operatorGenerator{{
+ name: "bar.v1.0.0", version: "1.0.0",
+ pkg: "bar", channel: "stable",
+ catName: csName, catNamespace: namespace,
+ properties: []*api.Property{{
+ Type: constraints.OLMConstraintType,
+ Value: `{"message": "all constraint",
+ "all": {"constraints": [
+ {"package": {"packageName": "foo", "versionRange": ">=1.0.0"}},
+ {"gvk": {"group": "g1", "version": "v1", "kind": "k1"}},
+ {"gvk": {"group": "g2", "version": "v2", "kind": "k2"}}
+ ]}
+ }`,
+ }},
+ }}
+ dependeeOperatorGens := []operatorGenerator{{
+ name: "foo.v1.0.1", version: "1.0.1",
+ pkg: "foo", channel: "stable", replaces: "foo.v1.0.0",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g1", Version: "v1", Kind: "k1"}: {},
+ opregistry.APIKey{Group: "g2", Version: "v2", Kind: "k2"}: {},
+ opregistry.APIKey{Group: "g3", Version: "v3", Kind: "k3"}: {},
+ },
+ }}
+
+ inputs := append(dependeeOperatorGens, newOperatorGens...)
+
+ satResolver := SatResolver{
+ cache: cache.New(cache.StaticSourceProvider{
+ catalog: &cache.Snapshot{
+ Entries: genOperatorsRandom(append(
+ inputs,
+ operatorGenerator{
+ name: "foo.v0.99.0", version: "0.99.0",
+ pkg: "foo", channel: "stable",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g1", Version: "v1", Kind: "k1"}: {},
+ opregistry.APIKey{Group: "g2", Version: "v2", Kind: "k2"}: {},
+ opregistry.APIKey{Group: "g3", Version: "v3", Kind: "k3"}: {},
+ },
+ },
+ operatorGenerator{
+ name: "foo.v1.0.0", version: "1.0.0",
+ pkg: "foo", channel: "stable", replaces: "foo.v0.99.0",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g2", Version: "v2", Kind: "k2"}: {},
+ opregistry.APIKey{Group: "g3", Version: "v3", Kind: "k3"}: {},
+ },
+ },
+ )...),
+ },
+ }),
+ log: logrus.New(),
+ }
+
+ newSub := newSub(namespace, "bar", "stable", catalog)
+ subs := []*v1alpha1.Subscription{newSub}
+
+ operators, err := satResolver.SolveOperators([]string{namespace}, nil, subs)
+ require.NoError(t, err)
+ assert.Equal(t, 2, len(operators))
+
+ expected := make(cache.OperatorSet, len(inputs))
+ for _, gen := range inputs {
+ op := gen.gen()
+ expected[op.Name] = op
+ }
+ for k := range expected {
+ if assert.Contains(t, operators, k) {
+ assert.EqualValues(t, k, operators[k].Name)
+ }
+ }
+}
+
+func TestSolveOperators_OLMConstraint_CompoundAny(t *testing.T) {
+ namespace := "olm"
+ csName := "community"
+ catalog := cache.SourceKey{Name: csName, Namespace: namespace}
+
+ newOperatorGens := []operatorGenerator{{
+ name: "bar.v1.0.0", version: "1.0.0",
+ pkg: "bar", channel: "stable",
+ catName: csName, catNamespace: namespace,
+ properties: []*api.Property{{
+ Type: constraints.OLMConstraintType,
+ Value: `{"message": "any constraint",
+ "any": {"constraints": [
+ {"gvk": {"group": "g1", "version": "v1", "kind": "k1"}},
+ {"gvk": {"group": "g2", "version": "v2", "kind": "k2"}}
+ ]}
+ }`,
+ }},
+ }}
+ dependeeOperatorGens := []operatorGenerator{{
+ name: "foo.v1.0.1", version: "1.0.1",
+ pkg: "foo", channel: "stable", replaces: "foo.v1.0.0",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g1", Version: "v1", Kind: "k1"}: {},
+ opregistry.APIKey{Group: "g2", Version: "v2", Kind: "k2"}: {},
+ opregistry.APIKey{Group: "g3", Version: "v3", Kind: "k3"}: {},
+ },
+ }}
+
+ inputs := append(dependeeOperatorGens, newOperatorGens...)
+
+ satResolver := SatResolver{
+ cache: cache.New(cache.StaticSourceProvider{
+ catalog: &cache.Snapshot{
+ Entries: genOperatorsRandom(append(
+ inputs,
+ operatorGenerator{
+ name: "foo.v0.99.0", version: "0.99.0",
+ pkg: "foo", channel: "stable",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g0", Version: "v0", Kind: "k0"}: {},
+ },
+ },
+ operatorGenerator{
+ name: "foo.v1.0.0", version: "1.0.0",
+ pkg: "foo", channel: "stable", replaces: "foo.v0.99.0",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g1", Version: "v1", Kind: "k1"}: {},
+ opregistry.APIKey{Group: "g2", Version: "v2", Kind: "k2"}: {},
+ },
+ },
+ )...),
+ },
+ }),
+ log: logrus.New(),
+ }
+
+ newSub := newSub(namespace, "bar", "stable", catalog)
+ subs := []*v1alpha1.Subscription{newSub}
+
+ operators, err := satResolver.SolveOperators([]string{namespace}, nil, subs)
+ require.NoError(t, err)
+ assert.Equal(t, 2, len(operators))
+
+ expected := make(cache.OperatorSet, len(inputs))
+ for _, gen := range inputs {
+ op := gen.gen()
+ expected[op.Name] = op
+ }
+ for k := range expected {
+ if assert.Contains(t, operators, k) {
+ assert.EqualValues(t, k, operators[k].Name)
+ }
+ }
+}
+
+func TestSolveOperators_OLMConstraint_CompoundNone(t *testing.T) {
+ namespace := "olm"
+ csName := "community"
+ catalog := cache.SourceKey{Name: csName, Namespace: namespace}
+
+ newOperatorGens := []operatorGenerator{{
+ name: "bar.v1.0.0", version: "1.0.0",
+ pkg: "bar", channel: "stable",
+ catName: csName, catNamespace: namespace,
+ properties: []*api.Property{
+ {
+ Type: constraints.OLMConstraintType,
+ Value: `{"message": "compound none constraint",
+ "all": {"constraints": [
+ {"gvk": {"group": "g0", "version": "v0", "kind": "k0"}},
+ {"none": {"constraints": [
+ {"gvk": {"group": "g1", "version": "v1", "kind": "k1"}},
+ {"gvk": {"group": "g2", "version": "v2", "kind": "k2"}}
+ ]}}
+ ]}
+ }`,
+ },
+ },
+ }}
+ dependeeOperatorGens := []operatorGenerator{{
+ name: "foo.v0.99.0", version: "0.99.0",
+ pkg: "foo", channel: "stable",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g0", Version: "v0", Kind: "k0"}: {},
+ },
+ }}
+
+ inputs := append(dependeeOperatorGens, newOperatorGens...)
+
+ satResolver := SatResolver{
+ cache: cache.New(cache.StaticSourceProvider{
+ catalog: &cache.Snapshot{
+ Entries: genOperatorsRandom(append(
+ inputs,
+ operatorGenerator{
+ name: "foo.v1.0.0", version: "1.0.0",
+ pkg: "foo", channel: "stable", replaces: "foo.v0.99.0",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g0", Version: "v0", Kind: "k0"}: {},
+ opregistry.APIKey{Group: "g1", Version: "v1", Kind: "k1"}: {},
+ opregistry.APIKey{Group: "g2", Version: "v2", Kind: "k2"}: {},
+ },
+ },
+ operatorGenerator{
+ name: "foo.v1.0.1", version: "1.0.1",
+ pkg: "foo", channel: "stable", replaces: "foo.v1.0.0",
+ catName: csName, catNamespace: namespace,
+ providedAPIs: cache.APISet{
+ opregistry.APIKey{Group: "g0", Version: "v0", Kind: "k0"}: {},
+ opregistry.APIKey{Group: "g1", Version: "v1", Kind: "k1"}: {},
+ opregistry.APIKey{Group: "g2", Version: "v2", Kind: "k2"}: {},
+ opregistry.APIKey{Group: "g3", Version: "v3", Kind: "k3"}: {},
+ },
+ },
+ )...),
+ },
+ }),
+ log: logrus.New(),
+ }
+
+ newSub := newSub(namespace, "bar", "stable", catalog)
+ subs := []*v1alpha1.Subscription{newSub}
+
+ operators, err := satResolver.SolveOperators([]string{namespace}, nil, subs)
+ require.NoError(t, err)
+ assert.Equal(t, 2, len(operators))
+
+ expected := make(cache.OperatorSet, len(inputs))
+ for _, gen := range inputs {
+ op := gen.gen()
+ expected[op.Name] = op
+ }
+ for k := range expected {
+ if assert.Contains(t, operators, k) {
+ assert.EqualValues(t, k, operators[k].Name)
+ }
+ }
+}
+
+func TestSolveOperators_OLMConstraint_Unknown(t *testing.T) {
+ namespace := "olm"
+ csName := "community"
+ catalog := cache.SourceKey{Name: csName, Namespace: namespace}
+
+ newOperatorGens := []operatorGenerator{{
+ name: "bar.v1.0.0", version: "1.0.0",
+ pkg: "bar", channel: "stable",
+ catName: csName, catNamespace: namespace,
+ properties: []*api.Property{{
+ Type: constraints.OLMConstraintType,
+ Value: `{"message": "unknown constraint", "unknown": {"foo": "bar"}}`,
+ }},
+ }}
+
+ satResolver := SatResolver{
+ cache: cache.New(cache.StaticSourceProvider{
+ catalog: &cache.Snapshot{
+ Entries: genOperatorsRandom(newOperatorGens...),
+ },
+ }),
+ log: logrus.New(),
+ }
+
+ newSub := newSub(namespace, "bar", "stable", catalog)
+ subs := []*v1alpha1.Subscription{newSub}
+
+ _, err := satResolver.SolveOperators([]string{namespace}, nil, subs)
+ require.Error(t, err)
+ require.Contains(t, err.Error(), `json: unknown field "unknown"`)
+}
+
func TestSolveOperators_IgnoreUnsatisfiableDependencies(t *testing.T) {
const namespace = "olm"
- Provides := cache.APISet{opregistry.APIKey{Group: "g", Version: "v", Kind: "k", Plural: "ks"}: struct{}{}}
+ Provides := cache.APISet{testGVKKey: struct{}{}}
community := cache.SourceKey{Name: "community", Namespace: namespace}
csvs := []*v1alpha1.ClusterServiceVersion{
existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil),
@@ -819,13 +1133,13 @@ func TestSolveOperators_IgnoreUnsatisfiableDependencies(t *testing.T) {
// Behavior: The resolver should prefer catalogs in the same namespace as the subscription.
// It should also prefer the same catalog over global catalogs in terms of the operator cache.
func TestSolveOperators_PreferCatalogInSameNamespace(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
altNamespace := "alt-olm"
- catalog := cache.SourceKey{"community", namespace}
- altnsCatalog := cache.SourceKey{"alt-community", altNamespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
+ altnsCatalog := cache.SourceKey{Name: "alt-community", Namespace: altNamespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -860,11 +1174,11 @@ func TestSolveOperators_PreferCatalogInSameNamespace(t *testing.T) {
// Behavior: The resolver should not look in catalogs not in the same namespace or the global catalog namespace when resolving the subscription.
// This test should not result in a successful resolution because the catalog fulfilling the subscription is not in the operator cache.
func TestSolveOperators_ResolveOnlyInCachedNamespaces(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
otherCatalog := cache.SourceKey{Name: "secret", Namespace: "secret"}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
@@ -891,7 +1205,7 @@ func TestSolveOperators_ResolveOnlyInCachedNamespaces(t *testing.T) {
// Behavior: the resolver should always prefer the default channel for the subscribed bundle (unless we implement ordering for channels)
func TestSolveOperators_PreferDefaultChannelInResolution(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
@@ -929,7 +1243,7 @@ func TestSolveOperators_PreferDefaultChannelInResolution(t *testing.T) {
// Behavior: the resolver should always prefer the default channel for bundles satisfying transitive dependencies
func TestSolveOperators_PreferDefaultChannelInResolutionForTransitiveDependencies(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
@@ -967,11 +1281,11 @@ func TestSolveOperators_PreferDefaultChannelInResolutionForTransitiveDependencie
}
func TestSolveOperators_SubscriptionlessOperatorsSatisfyDependencies(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -1010,11 +1324,11 @@ func TestSolveOperators_SubscriptionlessOperatorsSatisfyDependencies(t *testing.
}
func TestSolveOperators_SubscriptionlessOperatorsCanConflict(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
csv := existingOperator(namespace, "packageA.v1", "packageA", "alpha", "", Provides, nil, nil, nil)
csvs := []*v1alpha1.ClusterServiceVersion{csv}
@@ -1038,10 +1352,10 @@ func TestSolveOperators_SubscriptionlessOperatorsCanConflict(t *testing.T) {
}
func TestSolveOperators_PackageCannotSelfSatisfy(t *testing.T) {
- Provides1 := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
- Requires1 := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
- Provides2 := cache.APISet{opregistry.APIKey{"g2", "v", "k", "ks"}: struct{}{}}
- Requires2 := cache.APISet{opregistry.APIKey{"g2", "v", "k", "ks"}: struct{}{}}
+ Provides1 := cache.APISet{testGVKKey: struct{}{}}
+ Requires1 := cache.APISet{testGVKKey: struct{}{}}
+ Provides2 := cache.APISet{opregistry.APIKey{Group: "g2", Version: "v", Kind: "k", Plural: "ks"}: struct{}{}}
+ Requires2 := cache.APISet{opregistry.APIKey{Group: "g2", Version: "v", Kind: "k", Plural: "ks"}: struct{}{}}
ProvidesBoth := Provides1.Union(Provides2)
RequiresBoth := Requires1.Union(Requires2)
@@ -1090,9 +1404,9 @@ func TestSolveOperators_PackageCannotSelfSatisfy(t *testing.T) {
}
func TestSolveOperators_TransferApiOwnership(t *testing.T) {
- Provides1 := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
- Requires1 := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
- Provides2 := cache.APISet{opregistry.APIKey{"g2", "v", "k", "ks"}: struct{}{}}
+ Provides1 := cache.APISet{testGVKKey: struct{}{}}
+ Requires1 := cache.APISet{testGVKKey: struct{}{}}
+ Provides2 := cache.APISet{opregistry.APIKey{Group: "g2", Version: "v", Kind: "k", Plural: "ks"}: struct{}{}}
ProvidesBoth := Provides1.Union(Provides2)
namespace := "olm"
@@ -1271,11 +1585,11 @@ func TestSolveOperatorsWithDeprecatedInnerChannelEntry(t *testing.T) {
}
func TestSolveOperators_WithSkipsAndStartingCSV(t *testing.T) {
- APISet := cache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet := cache.APISet{testGVKKey: struct{}{}}
Provides := APISet
namespace := "olm"
- catalog := cache.SourceKey{"community", namespace}
+ catalog := cache.SourceKey{Name: "community", Namespace: namespace}
newSub := newSub(namespace, "packageB", "alpha", catalog, withStartingCSV("packageB.v1"))
subs := []*v1alpha1.Subscription{newSub}
@@ -1353,7 +1667,7 @@ func TestSolveOperators_WithSkips(t *testing.T) {
func TestSolveOperatorsWithSkipsPreventingSelection(t *testing.T) {
const namespace = "test-namespace"
catalog := cache.SourceKey{Name: "test-catalog", Namespace: namespace}
- gvks := cache.APISet{opregistry.APIKey{Group: "g", Version: "v", Kind: "k", Plural: "ks"}: struct{}{}}
+ gvks := cache.APISet{testGVKKey: struct{}{}}
// Subscription candidate a-1 requires a GVK provided
// exclusively by b-1, but b-1 is skipped by b-3 and can't be
diff --git a/pkg/controller/registry/resolver/step_resolver_test.go b/pkg/controller/registry/resolver/step_resolver_test.go
index f85056192f..6c29c127ea 100644
--- a/pkg/controller/registry/resolver/step_resolver_test.go
+++ b/pkg/controller/registry/resolver/step_resolver_test.go
@@ -33,16 +33,16 @@ var (
// conventions for tests: packages are letters (a,b,c) and apis are numbers (1,2,3)
// APISets used for tests
- APISet1 = resolvercache.APISet{opregistry.APIKey{"g", "v", "k", "ks"}: struct{}{}}
+ APISet1 = resolvercache.APISet{testGVKKey: struct{}{}}
Provides1 = APISet1
Requires1 = APISet1
- APISet2 = resolvercache.APISet{opregistry.APIKey{"g2", "v2", "k2", "k2s"}: struct{}{}}
+ APISet2 = resolvercache.APISet{opregistry.APIKey{Group: "g2", Version: "v2", Kind: "k2", Plural: "k2s"}: struct{}{}}
Provides2 = APISet2
Requires2 = APISet2
- APISet3 = resolvercache.APISet{opregistry.APIKey{"g3", "v3", "k3", "k3s"}: struct{}{}}
+ APISet3 = resolvercache.APISet{opregistry.APIKey{Group: "g3", Version: "v3", Kind: "k3", Plural: "k3s"}: struct{}{}}
Provides3 = APISet3
Requires3 = APISet3
- APISet4 = resolvercache.APISet{opregistry.APIKey{"g4", "v4", "k4", "k4s"}: struct{}{}}
+ APISet4 = resolvercache.APISet{opregistry.APIKey{Group: "g4", Version: "v4", Kind: "k4", Plural: "k4s"}: struct{}{}}
Provides4 = APISet4
Requires4 = APISet4
)
@@ -886,7 +886,7 @@ func (stub *stubOperatorCacheProvider) Expire(key resolvercache.SourceKey) {
func TestNamespaceResolverRBAC(t *testing.T) {
namespace := "catsrc-namespace"
- catalog := resolvercache.SourceKey{"catsrc", namespace}
+ catalog := resolvercache.SourceKey{Name: "catsrc", Namespace: namespace}
simplePermissions := []v1alpha1.StrategyDeploymentPermissions{
{
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/LICENSE b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/LICENSE
new file mode 100644
index 0000000000..52cf18e425
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/LICENSE
@@ -0,0 +1,26 @@
+Copyright 2021 The ANTLR Project
+
+Redistribution and use in source and binary forms, with or without modification,
+are permitted provided that the following conditions are met:
+
+ 1. Redistributions of source code must retain the above copyright notice,
+ this list of conditions and the following disclaimer.
+
+ 2. Redistributions in binary form must reproduce the above copyright notice,
+ this list of conditions and the following disclaimer in the documentation
+ and/or other materials provided with the distribution.
+
+ 3. Neither the name of the copyright holder nor the names of its
+ contributors may be used to endorse or promote products derived from this
+ software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn.go
new file mode 100644
index 0000000000..1592212e14
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn.go
@@ -0,0 +1,152 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+var ATNInvalidAltNumber int
+
+type ATN struct {
+ // DecisionToState is the decision points for all rules, subrules, optional
+ // blocks, ()+, ()*, etc. Used to build DFA predictors for them.
+ DecisionToState []DecisionState
+
+ // grammarType is the ATN type and is used for deserializing ATNs from strings.
+ grammarType int
+
+ // lexerActions is referenced by action transitions in the ATN for lexer ATNs.
+ lexerActions []LexerAction
+
+ // maxTokenType is the maximum value for any symbol recognized by a transition in the ATN.
+ maxTokenType int
+
+ modeNameToStartState map[string]*TokensStartState
+
+ modeToStartState []*TokensStartState
+
+ // ruleToStartState maps from rule index to starting state number.
+ ruleToStartState []*RuleStartState
+
+ // ruleToStopState maps from rule index to stop state number.
+ ruleToStopState []*RuleStopState
+
+ // ruleToTokenType maps the rule index to the resulting token type for lexer
+ // ATNs. For parser ATNs, it maps the rule index to the generated bypass token
+ // type if ATNDeserializationOptions.isGenerateRuleBypassTransitions was
+ // specified, and otherwise is nil.
+ ruleToTokenType []int
+
+ states []ATNState
+}
+
+func NewATN(grammarType int, maxTokenType int) *ATN {
+ return &ATN{
+ grammarType: grammarType,
+ maxTokenType: maxTokenType,
+ modeNameToStartState: make(map[string]*TokensStartState),
+ }
+}
+
+// NextTokensInContext computes the set of valid tokens that can occur starting
+// in state s. If ctx is nil, the set of tokens will not include what can follow
+// the rule surrounding s. In other words, the set will be restricted to tokens
+// reachable staying within the rule of s.
+func (a *ATN) NextTokensInContext(s ATNState, ctx RuleContext) *IntervalSet {
+ return NewLL1Analyzer(a).Look(s, nil, ctx)
+}
+
+// NextTokensNoContext computes the set of valid tokens that can occur starting
+// in s and staying in same rule. Token.EPSILON is in set if we reach end of
+// rule.
+func (a *ATN) NextTokensNoContext(s ATNState) *IntervalSet {
+ if s.GetNextTokenWithinRule() != nil {
+ return s.GetNextTokenWithinRule()
+ }
+
+ s.SetNextTokenWithinRule(a.NextTokensInContext(s, nil))
+ s.GetNextTokenWithinRule().readOnly = true
+
+ return s.GetNextTokenWithinRule()
+}
+
+func (a *ATN) NextTokens(s ATNState, ctx RuleContext) *IntervalSet {
+ if ctx == nil {
+ return a.NextTokensNoContext(s)
+ }
+
+ return a.NextTokensInContext(s, ctx)
+}
+
+func (a *ATN) addState(state ATNState) {
+ if state != nil {
+ state.SetATN(a)
+ state.SetStateNumber(len(a.states))
+ }
+
+ a.states = append(a.states, state)
+}
+
+func (a *ATN) removeState(state ATNState) {
+ a.states[state.GetStateNumber()] = nil // Just free the memory; don't shift states in the slice
+}
+
+func (a *ATN) defineDecisionState(s DecisionState) int {
+ a.DecisionToState = append(a.DecisionToState, s)
+ s.setDecision(len(a.DecisionToState) - 1)
+
+ return s.getDecision()
+}
+
+func (a *ATN) getDecisionState(decision int) DecisionState {
+ if len(a.DecisionToState) == 0 {
+ return nil
+ }
+
+ return a.DecisionToState[decision]
+}
+
+// getExpectedTokens computes the set of input symbols which could follow ATN
+// state number stateNumber in the specified full parse context ctx and returns
+// the set of potentially valid input symbols which could follow the specified
+// state in the specified context. This method considers the complete parser
+// context, but does not evaluate semantic predicates (i.e. all predicates
+// encountered during the calculation are assumed true). If a path in the ATN
+// exists from the starting state to the RuleStopState of the outermost context
+// without Matching any symbols, Token.EOF is added to the returned set.
+//
+// A nil ctx defaults to ParserRuleContext.EMPTY.
+//
+// It panics if the ATN does not contain state stateNumber.
+func (a *ATN) getExpectedTokens(stateNumber int, ctx RuleContext) *IntervalSet {
+ if stateNumber < 0 || stateNumber >= len(a.states) {
+ panic("Invalid state number.")
+ }
+
+ s := a.states[stateNumber]
+ following := a.NextTokens(s, nil)
+
+ if !following.contains(TokenEpsilon) {
+ return following
+ }
+
+ expected := NewIntervalSet()
+
+ expected.addSet(following)
+ expected.removeOne(TokenEpsilon)
+
+ for ctx != nil && ctx.GetInvokingState() >= 0 && following.contains(TokenEpsilon) {
+ invokingState := a.states[ctx.GetInvokingState()]
+ rt := invokingState.GetTransitions()[0]
+
+ following = a.NextTokens(rt.(*RuleTransition).followState, nil)
+ expected.addSet(following)
+ expected.removeOne(TokenEpsilon)
+ ctx = ctx.GetParent().(RuleContext)
+ }
+
+ if following.contains(TokenEpsilon) {
+ expected.addOne(TokenEOF)
+ }
+
+ return expected
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_config.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_config.go
new file mode 100644
index 0000000000..0535d5246c
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_config.go
@@ -0,0 +1,295 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+)
+
+type comparable interface {
+ equals(other interface{}) bool
+}
+
+// ATNConfig is a tuple: (ATN state, predicted alt, syntactic, semantic
+// context). The syntactic context is a graph-structured stack node whose
+// path(s) to the root is the rule invocation(s) chain used to arrive at the
+// state. The semantic context is the tree of semantic predicates encountered
+// before reaching an ATN state.
+type ATNConfig interface {
+ comparable
+
+ hash() int
+
+ GetState() ATNState
+ GetAlt() int
+ GetSemanticContext() SemanticContext
+
+ GetContext() PredictionContext
+ SetContext(PredictionContext)
+
+ GetReachesIntoOuterContext() int
+ SetReachesIntoOuterContext(int)
+
+ String() string
+
+ getPrecedenceFilterSuppressed() bool
+ setPrecedenceFilterSuppressed(bool)
+}
+
+type BaseATNConfig struct {
+ precedenceFilterSuppressed bool
+ state ATNState
+ alt int
+ context PredictionContext
+ semanticContext SemanticContext
+ reachesIntoOuterContext int
+}
+
+func NewBaseATNConfig7(old *BaseATNConfig) *BaseATNConfig { // TODO: Dup
+ return &BaseATNConfig{
+ state: old.state,
+ alt: old.alt,
+ context: old.context,
+ semanticContext: old.semanticContext,
+ reachesIntoOuterContext: old.reachesIntoOuterContext,
+ }
+}
+
+func NewBaseATNConfig6(state ATNState, alt int, context PredictionContext) *BaseATNConfig {
+ return NewBaseATNConfig5(state, alt, context, SemanticContextNone)
+}
+
+func NewBaseATNConfig5(state ATNState, alt int, context PredictionContext, semanticContext SemanticContext) *BaseATNConfig {
+ if semanticContext == nil {
+ panic("semanticContext cannot be nil") // TODO: Necessary?
+ }
+
+ return &BaseATNConfig{state: state, alt: alt, context: context, semanticContext: semanticContext}
+}
+
+func NewBaseATNConfig4(c ATNConfig, state ATNState) *BaseATNConfig {
+ return NewBaseATNConfig(c, state, c.GetContext(), c.GetSemanticContext())
+}
+
+func NewBaseATNConfig3(c ATNConfig, state ATNState, semanticContext SemanticContext) *BaseATNConfig {
+ return NewBaseATNConfig(c, state, c.GetContext(), semanticContext)
+}
+
+func NewBaseATNConfig2(c ATNConfig, semanticContext SemanticContext) *BaseATNConfig {
+ return NewBaseATNConfig(c, c.GetState(), c.GetContext(), semanticContext)
+}
+
+func NewBaseATNConfig1(c ATNConfig, state ATNState, context PredictionContext) *BaseATNConfig {
+ return NewBaseATNConfig(c, state, context, c.GetSemanticContext())
+}
+
+func NewBaseATNConfig(c ATNConfig, state ATNState, context PredictionContext, semanticContext SemanticContext) *BaseATNConfig {
+ if semanticContext == nil {
+ panic("semanticContext cannot be nil")
+ }
+
+ return &BaseATNConfig{
+ state: state,
+ alt: c.GetAlt(),
+ context: context,
+ semanticContext: semanticContext,
+ reachesIntoOuterContext: c.GetReachesIntoOuterContext(),
+ precedenceFilterSuppressed: c.getPrecedenceFilterSuppressed(),
+ }
+}
+
+func (b *BaseATNConfig) getPrecedenceFilterSuppressed() bool {
+ return b.precedenceFilterSuppressed
+}
+
+func (b *BaseATNConfig) setPrecedenceFilterSuppressed(v bool) {
+ b.precedenceFilterSuppressed = v
+}
+
+func (b *BaseATNConfig) GetState() ATNState {
+ return b.state
+}
+
+func (b *BaseATNConfig) GetAlt() int {
+ return b.alt
+}
+
+func (b *BaseATNConfig) SetContext(v PredictionContext) {
+ b.context = v
+}
+func (b *BaseATNConfig) GetContext() PredictionContext {
+ return b.context
+}
+
+func (b *BaseATNConfig) GetSemanticContext() SemanticContext {
+ return b.semanticContext
+}
+
+func (b *BaseATNConfig) GetReachesIntoOuterContext() int {
+ return b.reachesIntoOuterContext
+}
+
+func (b *BaseATNConfig) SetReachesIntoOuterContext(v int) {
+ b.reachesIntoOuterContext = v
+}
+
+// An ATN configuration is equal to another if both have the same state, they
+// predict the same alternative, and syntactic/semantic contexts are the same.
+func (b *BaseATNConfig) equals(o interface{}) bool {
+ if b == o {
+ return true
+ }
+
+ var other, ok = o.(*BaseATNConfig)
+
+ if !ok {
+ return false
+ }
+
+ var equal bool
+
+ if b.context == nil {
+ equal = other.context == nil
+ } else {
+ equal = b.context.equals(other.context)
+ }
+
+ var (
+ nums = b.state.GetStateNumber() == other.state.GetStateNumber()
+ alts = b.alt == other.alt
+ cons = b.semanticContext.equals(other.semanticContext)
+ sups = b.precedenceFilterSuppressed == other.precedenceFilterSuppressed
+ )
+
+ return nums && alts && cons && sups && equal
+}
+
+func (b *BaseATNConfig) hash() int {
+ var c int
+ if b.context != nil {
+ c = b.context.hash()
+ }
+
+ h := murmurInit(7)
+ h = murmurUpdate(h, b.state.GetStateNumber())
+ h = murmurUpdate(h, b.alt)
+ h = murmurUpdate(h, c)
+ h = murmurUpdate(h, b.semanticContext.hash())
+ return murmurFinish(h, 4)
+}
+
+func (b *BaseATNConfig) String() string {
+ var s1, s2, s3 string
+
+ if b.context != nil {
+ s1 = ",[" + fmt.Sprint(b.context) + "]"
+ }
+
+ if b.semanticContext != SemanticContextNone {
+ s2 = "," + fmt.Sprint(b.semanticContext)
+ }
+
+ if b.reachesIntoOuterContext > 0 {
+ s3 = ",up=" + fmt.Sprint(b.reachesIntoOuterContext)
+ }
+
+ return fmt.Sprintf("(%v,%v%v%v%v)", b.state, b.alt, s1, s2, s3)
+}
+
+type LexerATNConfig struct {
+ *BaseATNConfig
+ lexerActionExecutor *LexerActionExecutor
+ passedThroughNonGreedyDecision bool
+}
+
+func NewLexerATNConfig6(state ATNState, alt int, context PredictionContext) *LexerATNConfig {
+ return &LexerATNConfig{BaseATNConfig: NewBaseATNConfig5(state, alt, context, SemanticContextNone)}
+}
+
+func NewLexerATNConfig5(state ATNState, alt int, context PredictionContext, lexerActionExecutor *LexerActionExecutor) *LexerATNConfig {
+ return &LexerATNConfig{
+ BaseATNConfig: NewBaseATNConfig5(state, alt, context, SemanticContextNone),
+ lexerActionExecutor: lexerActionExecutor,
+ }
+}
+
+func NewLexerATNConfig4(c *LexerATNConfig, state ATNState) *LexerATNConfig {
+ return &LexerATNConfig{
+ BaseATNConfig: NewBaseATNConfig(c, state, c.GetContext(), c.GetSemanticContext()),
+ lexerActionExecutor: c.lexerActionExecutor,
+ passedThroughNonGreedyDecision: checkNonGreedyDecision(c, state),
+ }
+}
+
+func NewLexerATNConfig3(c *LexerATNConfig, state ATNState, lexerActionExecutor *LexerActionExecutor) *LexerATNConfig {
+ return &LexerATNConfig{
+ BaseATNConfig: NewBaseATNConfig(c, state, c.GetContext(), c.GetSemanticContext()),
+ lexerActionExecutor: lexerActionExecutor,
+ passedThroughNonGreedyDecision: checkNonGreedyDecision(c, state),
+ }
+}
+
+func NewLexerATNConfig2(c *LexerATNConfig, state ATNState, context PredictionContext) *LexerATNConfig {
+ return &LexerATNConfig{
+ BaseATNConfig: NewBaseATNConfig(c, state, context, c.GetSemanticContext()),
+ lexerActionExecutor: c.lexerActionExecutor,
+ passedThroughNonGreedyDecision: checkNonGreedyDecision(c, state),
+ }
+}
+
+func NewLexerATNConfig1(state ATNState, alt int, context PredictionContext) *LexerATNConfig {
+ return &LexerATNConfig{BaseATNConfig: NewBaseATNConfig5(state, alt, context, SemanticContextNone)}
+}
+
+func (l *LexerATNConfig) hash() int {
+ var f int
+ if l.passedThroughNonGreedyDecision {
+ f = 1
+ } else {
+ f = 0
+ }
+ h := murmurInit(7)
+ h = murmurUpdate(h, l.state.hash())
+ h = murmurUpdate(h, l.alt)
+ h = murmurUpdate(h, l.context.hash())
+ h = murmurUpdate(h, l.semanticContext.hash())
+ h = murmurUpdate(h, f)
+ h = murmurUpdate(h, l.lexerActionExecutor.hash())
+ h = murmurFinish(h, 6)
+ return h
+}
+
+func (l *LexerATNConfig) equals(other interface{}) bool {
+ var othert, ok = other.(*LexerATNConfig)
+
+ if l == other {
+ return true
+ } else if !ok {
+ return false
+ } else if l.passedThroughNonGreedyDecision != othert.passedThroughNonGreedyDecision {
+ return false
+ }
+
+ var b bool
+
+ if l.lexerActionExecutor != nil {
+ b = !l.lexerActionExecutor.equals(othert.lexerActionExecutor)
+ } else {
+ b = othert.lexerActionExecutor != nil
+ }
+
+ if b {
+ return false
+ }
+
+ return l.BaseATNConfig.equals(othert.BaseATNConfig)
+}
+
+
+func checkNonGreedyDecision(source *LexerATNConfig, target ATNState) bool {
+ var ds, ok = target.(DecisionState)
+
+ return source.passedThroughNonGreedyDecision || (ok && ds.getNonGreedy())
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_config_set.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_config_set.go
new file mode 100644
index 0000000000..d9f74755fa
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_config_set.go
@@ -0,0 +1,387 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import "fmt"
+
+type ATNConfigSet interface {
+ hash() int
+ Add(ATNConfig, *DoubleDict) bool
+ AddAll([]ATNConfig) bool
+
+ GetStates() *Set
+ GetPredicates() []SemanticContext
+ GetItems() []ATNConfig
+
+ OptimizeConfigs(interpreter *BaseATNSimulator)
+
+ Equals(other interface{}) bool
+
+ Length() int
+ IsEmpty() bool
+ Contains(ATNConfig) bool
+ ContainsFast(ATNConfig) bool
+ Clear()
+ String() string
+
+ HasSemanticContext() bool
+ SetHasSemanticContext(v bool)
+
+ ReadOnly() bool
+ SetReadOnly(bool)
+
+ GetConflictingAlts() *BitSet
+ SetConflictingAlts(*BitSet)
+
+ FullContext() bool
+
+ GetUniqueAlt() int
+ SetUniqueAlt(int)
+
+ GetDipsIntoOuterContext() bool
+ SetDipsIntoOuterContext(bool)
+}
+
+// BaseATNConfigSet is a specialized set of ATNConfig that tracks information
+// about its elements and can combine similar configurations using a
+// graph-structured stack.
+type BaseATNConfigSet struct {
+ cachedHash int
+
+ // configLookup is used to determine whether two BaseATNConfigSets are equal. We
+ // need all configurations with the same (s, i, _, semctx) to be equal. A key
+ // effectively doubles the number of objects associated with ATNConfigs. All
+ // keys are hashed by (s, i, _, pi), not including the context. Wiped out when
+ // read-only because a set becomes a DFA state.
+ configLookup *Set
+
+ // configs is the added elements.
+ configs []ATNConfig
+
+ // TODO: These fields make me pretty uncomfortable, but it is nice to pack up
+ // info together because it saves recomputation. Can we track conflicts as they
+ // are added to save scanning configs later?
+ conflictingAlts *BitSet
+
+ // dipsIntoOuterContext is used by parsers and lexers. In a lexer, it indicates
+ // we hit a pred while computing a closure operation. Do not make a DFA state
+ // from the BaseATNConfigSet in this case. TODO: How is this used by parsers?
+ dipsIntoOuterContext bool
+
+ // fullCtx is whether it is part of a full context LL prediction. Used to
+ // determine how to merge $. It is a wildcard with SLL, but not for an LL
+ // context merge.
+ fullCtx bool
+
+ // Used in parser and lexer. In lexer, it indicates we hit a pred
+ // while computing a closure operation. Don't make a DFA state from a.
+ hasSemanticContext bool
+
+ // readOnly is whether it is read-only. Do not
+ // allow any code to manipulate the set if true because DFA states will point at
+ // sets and those must not change. It not protect other fields; conflictingAlts
+ // in particular, which is assigned after readOnly.
+ readOnly bool
+
+ // TODO: These fields make me pretty uncomfortable, but it is nice to pack up
+ // info together because it saves recomputation. Can we track conflicts as they
+ // are added to save scanning configs later?
+ uniqueAlt int
+}
+
+func NewBaseATNConfigSet(fullCtx bool) *BaseATNConfigSet {
+ return &BaseATNConfigSet{
+ cachedHash: -1,
+ configLookup: NewSet(nil, equalATNConfigs),
+ fullCtx: fullCtx,
+ }
+}
+
+// Add merges contexts with existing configs for (s, i, pi, _), where s is the
+// ATNConfig.state, i is the ATNConfig.alt, and pi is the
+// ATNConfig.semanticContext. We use (s,i,pi) as the key. Updates
+// dipsIntoOuterContext and hasSemanticContext when necessary.
+func (b *BaseATNConfigSet) Add(config ATNConfig, mergeCache *DoubleDict) bool {
+ if b.readOnly {
+ panic("set is read-only")
+ }
+
+ if config.GetSemanticContext() != SemanticContextNone {
+ b.hasSemanticContext = true
+ }
+
+ if config.GetReachesIntoOuterContext() > 0 {
+ b.dipsIntoOuterContext = true
+ }
+
+ existing := b.configLookup.add(config).(ATNConfig)
+
+ if existing == config {
+ b.cachedHash = -1
+ b.configs = append(b.configs, config) // Track order here
+
+ return true
+ }
+
+ // Merge a previous (s, i, pi, _) with it and save the result
+ rootIsWildcard := !b.fullCtx
+ merged := merge(existing.GetContext(), config.GetContext(), rootIsWildcard, mergeCache)
+
+ // No need to check for existing.context because config.context is in the cache,
+ // since the only way to create new graphs is the "call rule" and here. We cache
+ // at both places.
+ existing.SetReachesIntoOuterContext(intMax(existing.GetReachesIntoOuterContext(), config.GetReachesIntoOuterContext()))
+
+ // Preserve the precedence filter suppression during the merge
+ if config.getPrecedenceFilterSuppressed() {
+ existing.setPrecedenceFilterSuppressed(true)
+ }
+
+ // Replace the context because there is no need to do alt mapping
+ existing.SetContext(merged)
+
+ return true
+}
+
+func (b *BaseATNConfigSet) GetStates() *Set {
+ states := NewSet(nil, nil)
+
+ for i := 0; i < len(b.configs); i++ {
+ states.add(b.configs[i].GetState())
+ }
+
+ return states
+}
+
+func (b *BaseATNConfigSet) HasSemanticContext() bool {
+ return b.hasSemanticContext
+}
+
+func (b *BaseATNConfigSet) SetHasSemanticContext(v bool) {
+ b.hasSemanticContext = v
+}
+
+func (b *BaseATNConfigSet) GetPredicates() []SemanticContext {
+ preds := make([]SemanticContext, 0)
+
+ for i := 0; i < len(b.configs); i++ {
+ c := b.configs[i].GetSemanticContext()
+
+ if c != SemanticContextNone {
+ preds = append(preds, c)
+ }
+ }
+
+ return preds
+}
+
+func (b *BaseATNConfigSet) GetItems() []ATNConfig {
+ return b.configs
+}
+
+func (b *BaseATNConfigSet) OptimizeConfigs(interpreter *BaseATNSimulator) {
+ if b.readOnly {
+ panic("set is read-only")
+ }
+
+ if b.configLookup.length() == 0 {
+ return
+ }
+
+ for i := 0; i < len(b.configs); i++ {
+ config := b.configs[i]
+
+ config.SetContext(interpreter.getCachedContext(config.GetContext()))
+ }
+}
+
+func (b *BaseATNConfigSet) AddAll(coll []ATNConfig) bool {
+ for i := 0; i < len(coll); i++ {
+ b.Add(coll[i], nil)
+ }
+
+ return false
+}
+
+func (b *BaseATNConfigSet) Equals(other interface{}) bool {
+ if b == other {
+ return true
+ } else if _, ok := other.(*BaseATNConfigSet); !ok {
+ return false
+ }
+
+ other2 := other.(*BaseATNConfigSet)
+
+ return b.configs != nil &&
+ // TODO: b.configs.equals(other2.configs) && // TODO: Is b necessary?
+ b.fullCtx == other2.fullCtx &&
+ b.uniqueAlt == other2.uniqueAlt &&
+ b.conflictingAlts == other2.conflictingAlts &&
+ b.hasSemanticContext == other2.hasSemanticContext &&
+ b.dipsIntoOuterContext == other2.dipsIntoOuterContext
+}
+
+func (b *BaseATNConfigSet) hash() int {
+ if b.readOnly {
+ if b.cachedHash == -1 {
+ b.cachedHash = b.hashCodeConfigs()
+ }
+
+ return b.cachedHash
+ }
+
+ return b.hashCodeConfigs()
+}
+
+func (b *BaseATNConfigSet) hashCodeConfigs() int {
+ h := murmurInit(1)
+ for _, c := range b.configs {
+ if c != nil {
+ h = murmurUpdate(h, c.hash())
+ }
+ }
+ return murmurFinish(h, len(b.configs))
+}
+
+func (b *BaseATNConfigSet) Length() int {
+ return len(b.configs)
+}
+
+func (b *BaseATNConfigSet) IsEmpty() bool {
+ return len(b.configs) == 0
+}
+
+func (b *BaseATNConfigSet) Contains(item ATNConfig) bool {
+ if b.configLookup == nil {
+ panic("not implemented for read-only sets")
+ }
+
+ return b.configLookup.contains(item)
+}
+
+func (b *BaseATNConfigSet) ContainsFast(item ATNConfig) bool {
+ if b.configLookup == nil {
+ panic("not implemented for read-only sets")
+ }
+
+ return b.configLookup.contains(item) // TODO: containsFast is not implemented for Set
+}
+
+func (b *BaseATNConfigSet) Clear() {
+ if b.readOnly {
+ panic("set is read-only")
+ }
+
+ b.configs = make([]ATNConfig, 0)
+ b.cachedHash = -1
+ b.configLookup = NewSet(nil, equalATNConfigs)
+}
+
+func (b *BaseATNConfigSet) FullContext() bool {
+ return b.fullCtx
+}
+
+func (b *BaseATNConfigSet) GetDipsIntoOuterContext() bool {
+ return b.dipsIntoOuterContext
+}
+
+func (b *BaseATNConfigSet) SetDipsIntoOuterContext(v bool) {
+ b.dipsIntoOuterContext = v
+}
+
+func (b *BaseATNConfigSet) GetUniqueAlt() int {
+ return b.uniqueAlt
+}
+
+func (b *BaseATNConfigSet) SetUniqueAlt(v int) {
+ b.uniqueAlt = v
+}
+
+func (b *BaseATNConfigSet) GetConflictingAlts() *BitSet {
+ return b.conflictingAlts
+}
+
+func (b *BaseATNConfigSet) SetConflictingAlts(v *BitSet) {
+ b.conflictingAlts = v
+}
+
+func (b *BaseATNConfigSet) ReadOnly() bool {
+ return b.readOnly
+}
+
+func (b *BaseATNConfigSet) SetReadOnly(readOnly bool) {
+ b.readOnly = readOnly
+
+ if readOnly {
+ b.configLookup = nil // Read only, so no need for the lookup cache
+ }
+}
+
+func (b *BaseATNConfigSet) String() string {
+ s := "["
+
+ for i, c := range b.configs {
+ s += c.String()
+
+ if i != len(b.configs)-1 {
+ s += ", "
+ }
+ }
+
+ s += "]"
+
+ if b.hasSemanticContext {
+ s += ",hasSemanticContext=" + fmt.Sprint(b.hasSemanticContext)
+ }
+
+ if b.uniqueAlt != ATNInvalidAltNumber {
+ s += ",uniqueAlt=" + fmt.Sprint(b.uniqueAlt)
+ }
+
+ if b.conflictingAlts != nil {
+ s += ",conflictingAlts=" + b.conflictingAlts.String()
+ }
+
+ if b.dipsIntoOuterContext {
+ s += ",dipsIntoOuterContext"
+ }
+
+ return s
+}
+
+type OrderedATNConfigSet struct {
+ *BaseATNConfigSet
+}
+
+func NewOrderedATNConfigSet() *OrderedATNConfigSet {
+ b := NewBaseATNConfigSet(false)
+
+ b.configLookup = NewSet(nil, nil)
+
+ return &OrderedATNConfigSet{BaseATNConfigSet: b}
+}
+
+func equalATNConfigs(a, b interface{}) bool {
+ if a == nil || b == nil {
+ return false
+ }
+
+ if a == b {
+ return true
+ }
+
+ var ai, ok = a.(ATNConfig)
+ var bi, ok1 = b.(ATNConfig)
+
+ if !ok || !ok1 {
+ return false
+ }
+
+ nums := ai.GetState().GetStateNumber() == bi.GetState().GetStateNumber()
+ alts := ai.GetAlt() == bi.GetAlt()
+ cons := ai.GetSemanticContext().equals(bi.GetSemanticContext())
+
+ return nums && alts && cons
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_deserialization_options.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_deserialization_options.go
new file mode 100644
index 0000000000..18b89efafb
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_deserialization_options.go
@@ -0,0 +1,25 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+var ATNDeserializationOptionsdefaultOptions = &ATNDeserializationOptions{true, false, false}
+
+type ATNDeserializationOptions struct {
+ readOnly bool
+ verifyATN bool
+ generateRuleBypassTransitions bool
+}
+
+func NewATNDeserializationOptions(CopyFrom *ATNDeserializationOptions) *ATNDeserializationOptions {
+ o := new(ATNDeserializationOptions)
+
+ if CopyFrom != nil {
+ o.readOnly = CopyFrom.readOnly
+ o.verifyATN = CopyFrom.verifyATN
+ o.generateRuleBypassTransitions = CopyFrom.generateRuleBypassTransitions
+ }
+
+ return o
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_deserializer.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_deserializer.go
new file mode 100644
index 0000000000..884d39cf7c
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_deserializer.go
@@ -0,0 +1,828 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "encoding/hex"
+ "fmt"
+ "strconv"
+ "strings"
+ "unicode/utf16"
+)
+
+// This is the earliest supported serialized UUID.
+// stick to serialized version for now, we don't need a UUID instance
+var BaseSerializedUUID = "AADB8D7E-AEEF-4415-AD2B-8204D6CF042E"
+var AddedUnicodeSMP = "59627784-3BE5-417A-B9EB-8131A7286089"
+
+// This list contains all of the currently supported UUIDs, ordered by when
+// the feature first appeared in this branch.
+var SupportedUUIDs = []string{BaseSerializedUUID, AddedUnicodeSMP}
+
+var SerializedVersion = 3
+
+// This is the current serialized UUID.
+var SerializedUUID = AddedUnicodeSMP
+
+type LoopEndStateIntPair struct {
+ item0 *LoopEndState
+ item1 int
+}
+
+type BlockStartStateIntPair struct {
+ item0 BlockStartState
+ item1 int
+}
+
+type ATNDeserializer struct {
+ deserializationOptions *ATNDeserializationOptions
+ data []rune
+ pos int
+ uuid string
+}
+
+func NewATNDeserializer(options *ATNDeserializationOptions) *ATNDeserializer {
+ if options == nil {
+ options = ATNDeserializationOptionsdefaultOptions
+ }
+
+ return &ATNDeserializer{deserializationOptions: options}
+}
+
+func stringInSlice(a string, list []string) int {
+ for i, b := range list {
+ if b == a {
+ return i
+ }
+ }
+
+ return -1
+}
+
+// isFeatureSupported determines if a particular serialized representation of an
+// ATN supports a particular feature, identified by the UUID used for
+// serializing the ATN at the time the feature was first introduced. Feature is
+// the UUID marking the first time the feature was supported in the serialized
+// ATN. ActualUuid is the UUID of the actual serialized ATN which is currently
+// being deserialized. It returns true if actualUuid represents a serialized ATN
+// at or after the feature identified by feature was introduced, and otherwise
+// false.
+func (a *ATNDeserializer) isFeatureSupported(feature, actualUUID string) bool {
+ idx1 := stringInSlice(feature, SupportedUUIDs)
+
+ if idx1 < 0 {
+ return false
+ }
+
+ idx2 := stringInSlice(actualUUID, SupportedUUIDs)
+
+ return idx2 >= idx1
+}
+
+func (a *ATNDeserializer) DeserializeFromUInt16(data []uint16) *ATN {
+ a.reset(utf16.Decode(data))
+ a.checkVersion()
+ a.checkUUID()
+
+ atn := a.readATN()
+
+ a.readStates(atn)
+ a.readRules(atn)
+ a.readModes(atn)
+
+ sets := make([]*IntervalSet, 0)
+
+ // First, deserialize sets with 16-bit arguments <= U+FFFF.
+ sets = a.readSets(atn, sets, a.readInt)
+ // Next, if the ATN was serialized with the Unicode SMP feature,
+ // deserialize sets with 32-bit arguments <= U+10FFFF.
+ if (a.isFeatureSupported(AddedUnicodeSMP, a.uuid)) {
+ sets = a.readSets(atn, sets, a.readInt32)
+ }
+
+ a.readEdges(atn, sets)
+ a.readDecisions(atn)
+ a.readLexerActions(atn)
+ a.markPrecedenceDecisions(atn)
+ a.verifyATN(atn)
+
+ if a.deserializationOptions.generateRuleBypassTransitions && atn.grammarType == ATNTypeParser {
+ a.generateRuleBypassTransitions(atn)
+ // Re-verify after modification
+ a.verifyATN(atn)
+ }
+
+ return atn
+
+}
+
+func (a *ATNDeserializer) reset(data []rune) {
+ temp := make([]rune, len(data))
+
+ for i, c := range data {
+ // Don't adjust the first value since that's the version number
+ if i == 0 {
+ temp[i] = c
+ } else if c > 1 {
+ temp[i] = c - 2
+ } else {
+ temp[i] = c + 65533
+ }
+ }
+
+ a.data = temp
+ a.pos = 0
+}
+
+func (a *ATNDeserializer) checkVersion() {
+ version := a.readInt()
+
+ if version != SerializedVersion {
+ panic("Could not deserialize ATN with version " + strconv.Itoa(version) + " (expected " + strconv.Itoa(SerializedVersion) + ").")
+ }
+}
+
+func (a *ATNDeserializer) checkUUID() {
+ uuid := a.readUUID()
+
+ if stringInSlice(uuid, SupportedUUIDs) < 0 {
+ panic("Could not deserialize ATN with UUID: " + uuid + " (expected " + SerializedUUID + " or a legacy UUID).")
+ }
+
+ a.uuid = uuid
+}
+
+func (a *ATNDeserializer) readATN() *ATN {
+ grammarType := a.readInt()
+ maxTokenType := a.readInt()
+
+ return NewATN(grammarType, maxTokenType)
+}
+
+func (a *ATNDeserializer) readStates(atn *ATN) {
+ loopBackStateNumbers := make([]LoopEndStateIntPair, 0)
+ endStateNumbers := make([]BlockStartStateIntPair, 0)
+
+ nstates := a.readInt()
+
+ for i := 0; i < nstates; i++ {
+ stype := a.readInt()
+
+ // Ignore bad types of states
+ if stype == ATNStateInvalidType {
+ atn.addState(nil)
+
+ continue
+ }
+
+ ruleIndex := a.readInt()
+
+ if ruleIndex == 0xFFFF {
+ ruleIndex = -1
+ }
+
+ s := a.stateFactory(stype, ruleIndex)
+
+ if stype == ATNStateLoopEnd {
+ loopBackStateNumber := a.readInt()
+
+ loopBackStateNumbers = append(loopBackStateNumbers, LoopEndStateIntPair{s.(*LoopEndState), loopBackStateNumber})
+ } else if s2, ok := s.(BlockStartState); ok {
+ endStateNumber := a.readInt()
+
+ endStateNumbers = append(endStateNumbers, BlockStartStateIntPair{s2, endStateNumber})
+ }
+
+ atn.addState(s)
+ }
+
+ // Delay the assignment of loop back and end states until we know all the state
+ // instances have been initialized
+ for j := 0; j < len(loopBackStateNumbers); j++ {
+ pair := loopBackStateNumbers[j]
+
+ pair.item0.loopBackState = atn.states[pair.item1]
+ }
+
+ for j := 0; j < len(endStateNumbers); j++ {
+ pair := endStateNumbers[j]
+
+ pair.item0.setEndState(atn.states[pair.item1].(*BlockEndState))
+ }
+
+ numNonGreedyStates := a.readInt()
+
+ for j := 0; j < numNonGreedyStates; j++ {
+ stateNumber := a.readInt()
+
+ atn.states[stateNumber].(DecisionState).setNonGreedy(true)
+ }
+
+ numPrecedenceStates := a.readInt()
+
+ for j := 0; j < numPrecedenceStates; j++ {
+ stateNumber := a.readInt()
+
+ atn.states[stateNumber].(*RuleStartState).isPrecedenceRule = true
+ }
+}
+
+func (a *ATNDeserializer) readRules(atn *ATN) {
+ nrules := a.readInt()
+
+ if atn.grammarType == ATNTypeLexer {
+ atn.ruleToTokenType = make([]int, nrules) // TODO: initIntArray(nrules, 0)
+ }
+
+ atn.ruleToStartState = make([]*RuleStartState, nrules) // TODO: initIntArray(nrules, 0)
+
+ for i := 0; i < nrules; i++ {
+ s := a.readInt()
+ startState := atn.states[s].(*RuleStartState)
+
+ atn.ruleToStartState[i] = startState
+
+ if atn.grammarType == ATNTypeLexer {
+ tokenType := a.readInt()
+
+ if tokenType == 0xFFFF {
+ tokenType = TokenEOF
+ }
+
+ atn.ruleToTokenType[i] = tokenType
+ }
+ }
+
+ atn.ruleToStopState = make([]*RuleStopState, nrules) //initIntArray(nrules, 0)
+
+ for i := 0; i < len(atn.states); i++ {
+ state := atn.states[i]
+
+ if s2, ok := state.(*RuleStopState); ok {
+ atn.ruleToStopState[s2.ruleIndex] = s2
+ atn.ruleToStartState[s2.ruleIndex].stopState = s2
+ }
+ }
+}
+
+func (a *ATNDeserializer) readModes(atn *ATN) {
+ nmodes := a.readInt()
+
+ for i := 0; i < nmodes; i++ {
+ s := a.readInt()
+
+ atn.modeToStartState = append(atn.modeToStartState, atn.states[s].(*TokensStartState))
+ }
+}
+
+func (a *ATNDeserializer) readSets(atn *ATN, sets []*IntervalSet, readUnicode func() int) []*IntervalSet {
+ m := a.readInt()
+
+ for i := 0; i < m; i++ {
+ iset := NewIntervalSet()
+
+ sets = append(sets, iset)
+
+ n := a.readInt()
+ containsEOF := a.readInt()
+
+ if containsEOF != 0 {
+ iset.addOne(-1)
+ }
+
+ for j := 0; j < n; j++ {
+ i1 := readUnicode()
+ i2 := readUnicode()
+
+ iset.addRange(i1, i2)
+ }
+ }
+
+ return sets
+}
+
+func (a *ATNDeserializer) readEdges(atn *ATN, sets []*IntervalSet) {
+ nedges := a.readInt()
+
+ for i := 0; i < nedges; i++ {
+ var (
+ src = a.readInt()
+ trg = a.readInt()
+ ttype = a.readInt()
+ arg1 = a.readInt()
+ arg2 = a.readInt()
+ arg3 = a.readInt()
+ trans = a.edgeFactory(atn, ttype, src, trg, arg1, arg2, arg3, sets)
+ srcState = atn.states[src]
+ )
+
+ srcState.AddTransition(trans, -1)
+ }
+
+ // Edges for rule stop states can be derived, so they are not serialized
+ for i := 0; i < len(atn.states); i++ {
+ state := atn.states[i]
+
+ for j := 0; j < len(state.GetTransitions()); j++ {
+ var t, ok = state.GetTransitions()[j].(*RuleTransition)
+
+ if !ok {
+ continue
+ }
+
+ outermostPrecedenceReturn := -1
+
+ if atn.ruleToStartState[t.getTarget().GetRuleIndex()].isPrecedenceRule {
+ if t.precedence == 0 {
+ outermostPrecedenceReturn = t.getTarget().GetRuleIndex()
+ }
+ }
+
+ trans := NewEpsilonTransition(t.followState, outermostPrecedenceReturn)
+
+ atn.ruleToStopState[t.getTarget().GetRuleIndex()].AddTransition(trans, -1)
+ }
+ }
+
+ for i := 0; i < len(atn.states); i++ {
+ state := atn.states[i]
+
+ if s2, ok := state.(*BaseBlockStartState); ok {
+ // We need to know the end state to set its start state
+ if s2.endState == nil {
+ panic("IllegalState")
+ }
+
+ // Block end states can only be associated to a single block start state
+ if s2.endState.startState != nil {
+ panic("IllegalState")
+ }
+
+ s2.endState.startState = state
+ }
+
+ if s2, ok := state.(*PlusLoopbackState); ok {
+ for j := 0; j < len(s2.GetTransitions()); j++ {
+ target := s2.GetTransitions()[j].getTarget()
+
+ if t2, ok := target.(*PlusBlockStartState); ok {
+ t2.loopBackState = state
+ }
+ }
+ } else if s2, ok := state.(*StarLoopbackState); ok {
+ for j := 0; j < len(s2.GetTransitions()); j++ {
+ target := s2.GetTransitions()[j].getTarget()
+
+ if t2, ok := target.(*StarLoopEntryState); ok {
+ t2.loopBackState = state
+ }
+ }
+ }
+ }
+}
+
+func (a *ATNDeserializer) readDecisions(atn *ATN) {
+ ndecisions := a.readInt()
+
+ for i := 0; i < ndecisions; i++ {
+ s := a.readInt()
+ decState := atn.states[s].(DecisionState)
+
+ atn.DecisionToState = append(atn.DecisionToState, decState)
+ decState.setDecision(i)
+ }
+}
+
+func (a *ATNDeserializer) readLexerActions(atn *ATN) {
+ if atn.grammarType == ATNTypeLexer {
+ count := a.readInt()
+
+ atn.lexerActions = make([]LexerAction, count) // initIntArray(count, nil)
+
+ for i := 0; i < count; i++ {
+ actionType := a.readInt()
+ data1 := a.readInt()
+
+ if data1 == 0xFFFF {
+ data1 = -1
+ }
+
+ data2 := a.readInt()
+
+ if data2 == 0xFFFF {
+ data2 = -1
+ }
+
+ lexerAction := a.lexerActionFactory(actionType, data1, data2)
+
+ atn.lexerActions[i] = lexerAction
+ }
+ }
+}
+
+func (a *ATNDeserializer) generateRuleBypassTransitions(atn *ATN) {
+ count := len(atn.ruleToStartState)
+
+ for i := 0; i < count; i++ {
+ atn.ruleToTokenType[i] = atn.maxTokenType + i + 1
+ }
+
+ for i := 0; i < count; i++ {
+ a.generateRuleBypassTransition(atn, i)
+ }
+}
+
+func (a *ATNDeserializer) generateRuleBypassTransition(atn *ATN, idx int) {
+ bypassStart := NewBasicBlockStartState()
+
+ bypassStart.ruleIndex = idx
+ atn.addState(bypassStart)
+
+ bypassStop := NewBlockEndState()
+
+ bypassStop.ruleIndex = idx
+ atn.addState(bypassStop)
+
+ bypassStart.endState = bypassStop
+
+ atn.defineDecisionState(bypassStart.BaseDecisionState)
+
+ bypassStop.startState = bypassStart
+
+ var excludeTransition Transition
+ var endState ATNState
+
+ if atn.ruleToStartState[idx].isPrecedenceRule {
+ // Wrap from the beginning of the rule to the StarLoopEntryState
+ endState = nil
+
+ for i := 0; i < len(atn.states); i++ {
+ state := atn.states[i]
+
+ if a.stateIsEndStateFor(state, idx) != nil {
+ endState = state
+ excludeTransition = state.(*StarLoopEntryState).loopBackState.GetTransitions()[0]
+
+ break
+ }
+ }
+
+ if excludeTransition == nil {
+ panic("Couldn't identify final state of the precedence rule prefix section.")
+ }
+ } else {
+ endState = atn.ruleToStopState[idx]
+ }
+
+ // All non-excluded transitions that currently target end state need to target
+ // blockEnd instead
+ for i := 0; i < len(atn.states); i++ {
+ state := atn.states[i]
+
+ for j := 0; j < len(state.GetTransitions()); j++ {
+ transition := state.GetTransitions()[j]
+
+ if transition == excludeTransition {
+ continue
+ }
+
+ if transition.getTarget() == endState {
+ transition.setTarget(bypassStop)
+ }
+ }
+ }
+
+ // All transitions leaving the rule start state need to leave blockStart instead
+ ruleToStartState := atn.ruleToStartState[idx]
+ count := len(ruleToStartState.GetTransitions())
+
+ for count > 0 {
+ bypassStart.AddTransition(ruleToStartState.GetTransitions()[count-1], -1)
+ ruleToStartState.SetTransitions([]Transition{ruleToStartState.GetTransitions()[len(ruleToStartState.GetTransitions())-1]})
+ }
+
+ // Link the new states
+ atn.ruleToStartState[idx].AddTransition(NewEpsilonTransition(bypassStart, -1), -1)
+ bypassStop.AddTransition(NewEpsilonTransition(endState, -1), -1)
+
+ MatchState := NewBasicState()
+
+ atn.addState(MatchState)
+ MatchState.AddTransition(NewAtomTransition(bypassStop, atn.ruleToTokenType[idx]), -1)
+ bypassStart.AddTransition(NewEpsilonTransition(MatchState, -1), -1)
+}
+
+func (a *ATNDeserializer) stateIsEndStateFor(state ATNState, idx int) ATNState {
+ if state.GetRuleIndex() != idx {
+ return nil
+ }
+
+ if _, ok := state.(*StarLoopEntryState); !ok {
+ return nil
+ }
+
+ maybeLoopEndState := state.GetTransitions()[len(state.GetTransitions())-1].getTarget()
+
+ if _, ok := maybeLoopEndState.(*LoopEndState); !ok {
+ return nil
+ }
+
+ var _, ok = maybeLoopEndState.GetTransitions()[0].getTarget().(*RuleStopState)
+
+ if maybeLoopEndState.(*LoopEndState).epsilonOnlyTransitions && ok {
+ return state
+ }
+
+ return nil
+}
+
+// markPrecedenceDecisions analyzes the StarLoopEntryState states in the
+// specified ATN to set the StarLoopEntryState.precedenceRuleDecision field to
+// the correct value.
+func (a *ATNDeserializer) markPrecedenceDecisions(atn *ATN) {
+ for _, state := range atn.states {
+ if _, ok := state.(*StarLoopEntryState); !ok {
+ continue
+ }
+
+ // We analyze the ATN to determine if a ATN decision state is the
+ // decision for the closure block that determines whether a
+ // precedence rule should continue or complete.
+ if atn.ruleToStartState[state.GetRuleIndex()].isPrecedenceRule {
+ maybeLoopEndState := state.GetTransitions()[len(state.GetTransitions())-1].getTarget()
+
+ if s3, ok := maybeLoopEndState.(*LoopEndState); ok {
+ var _, ok2 = maybeLoopEndState.GetTransitions()[0].getTarget().(*RuleStopState)
+
+ if s3.epsilonOnlyTransitions && ok2 {
+ state.(*StarLoopEntryState).precedenceRuleDecision = true
+ }
+ }
+ }
+ }
+}
+
+func (a *ATNDeserializer) verifyATN(atn *ATN) {
+ if !a.deserializationOptions.verifyATN {
+ return
+ }
+
+ // Verify assumptions
+ for i := 0; i < len(atn.states); i++ {
+ state := atn.states[i]
+
+ if state == nil {
+ continue
+ }
+
+ a.checkCondition(state.GetEpsilonOnlyTransitions() || len(state.GetTransitions()) <= 1, "")
+
+ switch s2 := state.(type) {
+ case *PlusBlockStartState:
+ a.checkCondition(s2.loopBackState != nil, "")
+
+ case *StarLoopEntryState:
+ a.checkCondition(s2.loopBackState != nil, "")
+ a.checkCondition(len(s2.GetTransitions()) == 2, "")
+
+ switch s2 := state.(type) {
+ case *StarBlockStartState:
+ var _, ok2 = s2.GetTransitions()[1].getTarget().(*LoopEndState)
+
+ a.checkCondition(ok2, "")
+ a.checkCondition(!s2.nonGreedy, "")
+
+ case *LoopEndState:
+ var s3, ok2 = s2.GetTransitions()[1].getTarget().(*StarBlockStartState)
+
+ a.checkCondition(ok2, "")
+ a.checkCondition(s3.nonGreedy, "")
+
+ default:
+ panic("IllegalState")
+ }
+
+ case *StarLoopbackState:
+ a.checkCondition(len(state.GetTransitions()) == 1, "")
+
+ var _, ok2 = state.GetTransitions()[0].getTarget().(*StarLoopEntryState)
+
+ a.checkCondition(ok2, "")
+
+ case *LoopEndState:
+ a.checkCondition(s2.loopBackState != nil, "")
+
+ case *RuleStartState:
+ a.checkCondition(s2.stopState != nil, "")
+
+ case *BaseBlockStartState:
+ a.checkCondition(s2.endState != nil, "")
+
+ case *BlockEndState:
+ a.checkCondition(s2.startState != nil, "")
+
+ case DecisionState:
+ a.checkCondition(len(s2.GetTransitions()) <= 1 || s2.getDecision() >= 0, "")
+
+ default:
+ var _, ok = s2.(*RuleStopState)
+
+ a.checkCondition(len(s2.GetTransitions()) <= 1 || ok, "")
+ }
+ }
+}
+
+func (a *ATNDeserializer) checkCondition(condition bool, message string) {
+ if !condition {
+ if message == "" {
+ message = "IllegalState"
+ }
+
+ panic(message)
+ }
+}
+
+func (a *ATNDeserializer) readInt() int {
+ v := a.data[a.pos]
+
+ a.pos++
+
+ return int(v)
+}
+
+func (a *ATNDeserializer) readInt32() int {
+ var low = a.readInt()
+ var high = a.readInt()
+ return low | (high << 16)
+}
+
+//TODO
+//func (a *ATNDeserializer) readLong() int64 {
+// panic("Not implemented")
+// var low = a.readInt32()
+// var high = a.readInt32()
+// return (low & 0x00000000FFFFFFFF) | (high << int32)
+//}
+
+func createByteToHex() []string {
+ bth := make([]string, 256)
+
+ for i := 0; i < 256; i++ {
+ bth[i] = strings.ToUpper(hex.EncodeToString([]byte{byte(i)}))
+ }
+
+ return bth
+}
+
+var byteToHex = createByteToHex()
+
+func (a *ATNDeserializer) readUUID() string {
+ bb := make([]int, 16)
+
+ for i := 7; i >= 0; i-- {
+ integer := a.readInt()
+
+ bb[(2*i)+1] = integer & 0xFF
+ bb[2*i] = (integer >> 8) & 0xFF
+ }
+
+ return byteToHex[bb[0]] + byteToHex[bb[1]] +
+ byteToHex[bb[2]] + byteToHex[bb[3]] + "-" +
+ byteToHex[bb[4]] + byteToHex[bb[5]] + "-" +
+ byteToHex[bb[6]] + byteToHex[bb[7]] + "-" +
+ byteToHex[bb[8]] + byteToHex[bb[9]] + "-" +
+ byteToHex[bb[10]] + byteToHex[bb[11]] +
+ byteToHex[bb[12]] + byteToHex[bb[13]] +
+ byteToHex[bb[14]] + byteToHex[bb[15]]
+}
+
+func (a *ATNDeserializer) edgeFactory(atn *ATN, typeIndex, src, trg, arg1, arg2, arg3 int, sets []*IntervalSet) Transition {
+ target := atn.states[trg]
+
+ switch typeIndex {
+ case TransitionEPSILON:
+ return NewEpsilonTransition(target, -1)
+
+ case TransitionRANGE:
+ if arg3 != 0 {
+ return NewRangeTransition(target, TokenEOF, arg2)
+ }
+
+ return NewRangeTransition(target, arg1, arg2)
+
+ case TransitionRULE:
+ return NewRuleTransition(atn.states[arg1], arg2, arg3, target)
+
+ case TransitionPREDICATE:
+ return NewPredicateTransition(target, arg1, arg2, arg3 != 0)
+
+ case TransitionPRECEDENCE:
+ return NewPrecedencePredicateTransition(target, arg1)
+
+ case TransitionATOM:
+ if arg3 != 0 {
+ return NewAtomTransition(target, TokenEOF)
+ }
+
+ return NewAtomTransition(target, arg1)
+
+ case TransitionACTION:
+ return NewActionTransition(target, arg1, arg2, arg3 != 0)
+
+ case TransitionSET:
+ return NewSetTransition(target, sets[arg1])
+
+ case TransitionNOTSET:
+ return NewNotSetTransition(target, sets[arg1])
+
+ case TransitionWILDCARD:
+ return NewWildcardTransition(target)
+ }
+
+ panic("The specified transition type is not valid.")
+}
+
+func (a *ATNDeserializer) stateFactory(typeIndex, ruleIndex int) ATNState {
+ var s ATNState
+
+ switch typeIndex {
+ case ATNStateInvalidType:
+ return nil
+
+ case ATNStateBasic:
+ s = NewBasicState()
+
+ case ATNStateRuleStart:
+ s = NewRuleStartState()
+
+ case ATNStateBlockStart:
+ s = NewBasicBlockStartState()
+
+ case ATNStatePlusBlockStart:
+ s = NewPlusBlockStartState()
+
+ case ATNStateStarBlockStart:
+ s = NewStarBlockStartState()
+
+ case ATNStateTokenStart:
+ s = NewTokensStartState()
+
+ case ATNStateRuleStop:
+ s = NewRuleStopState()
+
+ case ATNStateBlockEnd:
+ s = NewBlockEndState()
+
+ case ATNStateStarLoopBack:
+ s = NewStarLoopbackState()
+
+ case ATNStateStarLoopEntry:
+ s = NewStarLoopEntryState()
+
+ case ATNStatePlusLoopBack:
+ s = NewPlusLoopbackState()
+
+ case ATNStateLoopEnd:
+ s = NewLoopEndState()
+
+ default:
+ panic(fmt.Sprintf("state type %d is invalid", typeIndex))
+ }
+
+ s.SetRuleIndex(ruleIndex)
+
+ return s
+}
+
+func (a *ATNDeserializer) lexerActionFactory(typeIndex, data1, data2 int) LexerAction {
+ switch typeIndex {
+ case LexerActionTypeChannel:
+ return NewLexerChannelAction(data1)
+
+ case LexerActionTypeCustom:
+ return NewLexerCustomAction(data1, data2)
+
+ case LexerActionTypeMode:
+ return NewLexerModeAction(data1)
+
+ case LexerActionTypeMore:
+ return LexerMoreActionINSTANCE
+
+ case LexerActionTypePopMode:
+ return LexerPopModeActionINSTANCE
+
+ case LexerActionTypePushMode:
+ return NewLexerPushModeAction(data1)
+
+ case LexerActionTypeSkip:
+ return LexerSkipActionINSTANCE
+
+ case LexerActionTypeType:
+ return NewLexerTypeAction(data1)
+
+ default:
+ panic(fmt.Sprintf("lexer action %d is invalid", typeIndex))
+ }
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_simulator.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_simulator.go
new file mode 100644
index 0000000000..d5454d6d5d
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_simulator.go
@@ -0,0 +1,50 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+var ATNSimulatorError = NewDFAState(0x7FFFFFFF, NewBaseATNConfigSet(false))
+
+type IATNSimulator interface {
+ SharedContextCache() *PredictionContextCache
+ ATN() *ATN
+ DecisionToDFA() []*DFA
+}
+
+type BaseATNSimulator struct {
+ atn *ATN
+ sharedContextCache *PredictionContextCache
+ decisionToDFA []*DFA
+}
+
+func NewBaseATNSimulator(atn *ATN, sharedContextCache *PredictionContextCache) *BaseATNSimulator {
+ b := new(BaseATNSimulator)
+
+ b.atn = atn
+ b.sharedContextCache = sharedContextCache
+
+ return b
+}
+
+func (b *BaseATNSimulator) getCachedContext(context PredictionContext) PredictionContext {
+ if b.sharedContextCache == nil {
+ return context
+ }
+
+ visited := make(map[PredictionContext]PredictionContext)
+
+ return getCachedBasePredictionContext(context, b.sharedContextCache, visited)
+}
+
+func (b *BaseATNSimulator) SharedContextCache() *PredictionContextCache {
+ return b.sharedContextCache
+}
+
+func (b *BaseATNSimulator) ATN() *ATN {
+ return b.atn
+}
+
+func (b *BaseATNSimulator) DecisionToDFA() []*DFA {
+ return b.decisionToDFA
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_state.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_state.go
new file mode 100644
index 0000000000..563d5db38d
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_state.go
@@ -0,0 +1,386 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import "strconv"
+
+// Constants for serialization.
+const (
+ ATNStateInvalidType = 0
+ ATNStateBasic = 1
+ ATNStateRuleStart = 2
+ ATNStateBlockStart = 3
+ ATNStatePlusBlockStart = 4
+ ATNStateStarBlockStart = 5
+ ATNStateTokenStart = 6
+ ATNStateRuleStop = 7
+ ATNStateBlockEnd = 8
+ ATNStateStarLoopBack = 9
+ ATNStateStarLoopEntry = 10
+ ATNStatePlusLoopBack = 11
+ ATNStateLoopEnd = 12
+
+ ATNStateInvalidStateNumber = -1
+)
+
+var ATNStateInitialNumTransitions = 4
+
+type ATNState interface {
+ GetEpsilonOnlyTransitions() bool
+
+ GetRuleIndex() int
+ SetRuleIndex(int)
+
+ GetNextTokenWithinRule() *IntervalSet
+ SetNextTokenWithinRule(*IntervalSet)
+
+ GetATN() *ATN
+ SetATN(*ATN)
+
+ GetStateType() int
+
+ GetStateNumber() int
+ SetStateNumber(int)
+
+ GetTransitions() []Transition
+ SetTransitions([]Transition)
+ AddTransition(Transition, int)
+
+ String() string
+ hash() int
+}
+
+type BaseATNState struct {
+ // NextTokenWithinRule caches lookahead during parsing. Not used during construction.
+ NextTokenWithinRule *IntervalSet
+
+ // atn is the current ATN.
+ atn *ATN
+
+ epsilonOnlyTransitions bool
+
+ // ruleIndex tracks the Rule index because there are no Rule objects at runtime.
+ ruleIndex int
+
+ stateNumber int
+
+ stateType int
+
+ // Track the transitions emanating from this ATN state.
+ transitions []Transition
+}
+
+func NewBaseATNState() *BaseATNState {
+ return &BaseATNState{stateNumber: ATNStateInvalidStateNumber, stateType: ATNStateInvalidType}
+}
+
+func (as *BaseATNState) GetRuleIndex() int {
+ return as.ruleIndex
+}
+
+func (as *BaseATNState) SetRuleIndex(v int) {
+ as.ruleIndex = v
+}
+func (as *BaseATNState) GetEpsilonOnlyTransitions() bool {
+ return as.epsilonOnlyTransitions
+}
+
+func (as *BaseATNState) GetATN() *ATN {
+ return as.atn
+}
+
+func (as *BaseATNState) SetATN(atn *ATN) {
+ as.atn = atn
+}
+
+func (as *BaseATNState) GetTransitions() []Transition {
+ return as.transitions
+}
+
+func (as *BaseATNState) SetTransitions(t []Transition) {
+ as.transitions = t
+}
+
+func (as *BaseATNState) GetStateType() int {
+ return as.stateType
+}
+
+func (as *BaseATNState) GetStateNumber() int {
+ return as.stateNumber
+}
+
+func (as *BaseATNState) SetStateNumber(stateNumber int) {
+ as.stateNumber = stateNumber
+}
+
+func (as *BaseATNState) GetNextTokenWithinRule() *IntervalSet {
+ return as.NextTokenWithinRule
+}
+
+func (as *BaseATNState) SetNextTokenWithinRule(v *IntervalSet) {
+ as.NextTokenWithinRule = v
+}
+
+func (as *BaseATNState) hash() int {
+ return as.stateNumber
+}
+
+func (as *BaseATNState) String() string {
+ return strconv.Itoa(as.stateNumber)
+}
+
+func (as *BaseATNState) equals(other interface{}) bool {
+ if ot, ok := other.(ATNState); ok {
+ return as.stateNumber == ot.GetStateNumber()
+ }
+
+ return false
+}
+
+func (as *BaseATNState) isNonGreedyExitState() bool {
+ return false
+}
+
+func (as *BaseATNState) AddTransition(trans Transition, index int) {
+ if len(as.transitions) == 0 {
+ as.epsilonOnlyTransitions = trans.getIsEpsilon()
+ } else if as.epsilonOnlyTransitions != trans.getIsEpsilon() {
+ as.epsilonOnlyTransitions = false
+ }
+
+ if index == -1 {
+ as.transitions = append(as.transitions, trans)
+ } else {
+ as.transitions = append(as.transitions[:index], append([]Transition{trans}, as.transitions[index:]...)...)
+ // TODO: as.transitions.splice(index, 1, trans)
+ }
+}
+
+type BasicState struct {
+ *BaseATNState
+}
+
+func NewBasicState() *BasicState {
+ b := NewBaseATNState()
+
+ b.stateType = ATNStateBasic
+
+ return &BasicState{BaseATNState: b}
+}
+
+type DecisionState interface {
+ ATNState
+
+ getDecision() int
+ setDecision(int)
+
+ getNonGreedy() bool
+ setNonGreedy(bool)
+}
+
+type BaseDecisionState struct {
+ *BaseATNState
+ decision int
+ nonGreedy bool
+}
+
+func NewBaseDecisionState() *BaseDecisionState {
+ return &BaseDecisionState{BaseATNState: NewBaseATNState(), decision: -1}
+}
+
+func (s *BaseDecisionState) getDecision() int {
+ return s.decision
+}
+
+func (s *BaseDecisionState) setDecision(b int) {
+ s.decision = b
+}
+
+func (s *BaseDecisionState) getNonGreedy() bool {
+ return s.nonGreedy
+}
+
+func (s *BaseDecisionState) setNonGreedy(b bool) {
+ s.nonGreedy = b
+}
+
+type BlockStartState interface {
+ DecisionState
+
+ getEndState() *BlockEndState
+ setEndState(*BlockEndState)
+}
+
+// BaseBlockStartState is the start of a regular (...) block.
+type BaseBlockStartState struct {
+ *BaseDecisionState
+ endState *BlockEndState
+}
+
+func NewBlockStartState() *BaseBlockStartState {
+ return &BaseBlockStartState{BaseDecisionState: NewBaseDecisionState()}
+}
+
+func (s *BaseBlockStartState) getEndState() *BlockEndState {
+ return s.endState
+}
+
+func (s *BaseBlockStartState) setEndState(b *BlockEndState) {
+ s.endState = b
+}
+
+type BasicBlockStartState struct {
+ *BaseBlockStartState
+}
+
+func NewBasicBlockStartState() *BasicBlockStartState {
+ b := NewBlockStartState()
+
+ b.stateType = ATNStateBlockStart
+
+ return &BasicBlockStartState{BaseBlockStartState: b}
+}
+
+// BlockEndState is a terminal node of a simple (a|b|c) block.
+type BlockEndState struct {
+ *BaseATNState
+ startState ATNState
+}
+
+func NewBlockEndState() *BlockEndState {
+ b := NewBaseATNState()
+
+ b.stateType = ATNStateBlockEnd
+
+ return &BlockEndState{BaseATNState: b}
+}
+
+// RuleStopState is the last node in the ATN for a rule, unless that rule is the
+// start symbol. In that case, there is one transition to EOF. Later, we might
+// encode references to all calls to this rule to compute FOLLOW sets for error
+// handling.
+type RuleStopState struct {
+ *BaseATNState
+}
+
+func NewRuleStopState() *RuleStopState {
+ b := NewBaseATNState()
+
+ b.stateType = ATNStateRuleStop
+
+ return &RuleStopState{BaseATNState: b}
+}
+
+type RuleStartState struct {
+ *BaseATNState
+ stopState ATNState
+ isPrecedenceRule bool
+}
+
+func NewRuleStartState() *RuleStartState {
+ b := NewBaseATNState()
+
+ b.stateType = ATNStateRuleStart
+
+ return &RuleStartState{BaseATNState: b}
+}
+
+// PlusLoopbackState is a decision state for A+ and (A|B)+. It has two
+// transitions: one to the loop back to start of the block, and one to exit.
+type PlusLoopbackState struct {
+ *BaseDecisionState
+}
+
+func NewPlusLoopbackState() *PlusLoopbackState {
+ b := NewBaseDecisionState()
+
+ b.stateType = ATNStatePlusLoopBack
+
+ return &PlusLoopbackState{BaseDecisionState: b}
+}
+
+// PlusBlockStartState is the start of a (A|B|...)+ loop. Technically it is a
+// decision state; we don't use it for code generation. Somebody might need it,
+// it is included for completeness. In reality, PlusLoopbackState is the real
+// decision-making node for A+.
+type PlusBlockStartState struct {
+ *BaseBlockStartState
+ loopBackState ATNState
+}
+
+func NewPlusBlockStartState() *PlusBlockStartState {
+ b := NewBlockStartState()
+
+ b.stateType = ATNStatePlusBlockStart
+
+ return &PlusBlockStartState{BaseBlockStartState: b}
+}
+
+// StarBlockStartState is the block that begins a closure loop.
+type StarBlockStartState struct {
+ *BaseBlockStartState
+}
+
+func NewStarBlockStartState() *StarBlockStartState {
+ b := NewBlockStartState()
+
+ b.stateType = ATNStateStarBlockStart
+
+ return &StarBlockStartState{BaseBlockStartState: b}
+}
+
+type StarLoopbackState struct {
+ *BaseATNState
+}
+
+func NewStarLoopbackState() *StarLoopbackState {
+ b := NewBaseATNState()
+
+ b.stateType = ATNStateStarLoopBack
+
+ return &StarLoopbackState{BaseATNState: b}
+}
+
+type StarLoopEntryState struct {
+ *BaseDecisionState
+ loopBackState ATNState
+ precedenceRuleDecision bool
+}
+
+func NewStarLoopEntryState() *StarLoopEntryState {
+ b := NewBaseDecisionState()
+
+ b.stateType = ATNStateStarLoopEntry
+
+ // False precedenceRuleDecision indicates whether s state can benefit from a precedence DFA during SLL decision making.
+ return &StarLoopEntryState{BaseDecisionState: b}
+}
+
+// LoopEndState marks the end of a * or + loop.
+type LoopEndState struct {
+ *BaseATNState
+ loopBackState ATNState
+}
+
+func NewLoopEndState() *LoopEndState {
+ b := NewBaseATNState()
+
+ b.stateType = ATNStateLoopEnd
+
+ return &LoopEndState{BaseATNState: b}
+}
+
+// TokensStartState is the Tokens rule start state linking to each lexer rule start state.
+type TokensStartState struct {
+ *BaseDecisionState
+}
+
+func NewTokensStartState() *TokensStartState {
+ b := NewBaseDecisionState()
+
+ b.stateType = ATNStateTokenStart
+
+ return &TokensStartState{BaseDecisionState: b}
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_type.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_type.go
new file mode 100644
index 0000000000..a7b48976b3
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/atn_type.go
@@ -0,0 +1,11 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+// Represent the type of recognizer an ATN applies to.
+const (
+ ATNTypeLexer = 0
+ ATNTypeParser = 1
+)
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/char_stream.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/char_stream.go
new file mode 100644
index 0000000000..70c1207f7f
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/char_stream.go
@@ -0,0 +1,12 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+type CharStream interface {
+ IntStream
+ GetText(int, int) string
+ GetTextFromTokens(start, end Token) string
+ GetTextFromInterval(*Interval) string
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/common_token_factory.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/common_token_factory.go
new file mode 100644
index 0000000000..330ff8f31f
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/common_token_factory.go
@@ -0,0 +1,56 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+// TokenFactory creates CommonToken objects.
+type TokenFactory interface {
+ Create(source *TokenSourceCharStreamPair, ttype int, text string, channel, start, stop, line, column int) Token
+}
+
+// CommonTokenFactory is the default TokenFactory implementation.
+type CommonTokenFactory struct {
+ // copyText indicates whether CommonToken.setText should be called after
+ // constructing tokens to explicitly set the text. This is useful for cases
+ // where the input stream might not be able to provide arbitrary substrings of
+ // text from the input after the lexer creates a token (e.g. the
+ // implementation of CharStream.GetText in UnbufferedCharStream panics an
+ // UnsupportedOperationException). Explicitly setting the token text allows
+ // Token.GetText to be called at any time regardless of the input stream
+ // implementation.
+ //
+ // The default value is false to avoid the performance and memory overhead of
+ // copying text for every token unless explicitly requested.
+ copyText bool
+}
+
+func NewCommonTokenFactory(copyText bool) *CommonTokenFactory {
+ return &CommonTokenFactory{copyText: copyText}
+}
+
+// CommonTokenFactoryDEFAULT is the default CommonTokenFactory. It does not
+// explicitly copy token text when constructing tokens.
+var CommonTokenFactoryDEFAULT = NewCommonTokenFactory(false)
+
+func (c *CommonTokenFactory) Create(source *TokenSourceCharStreamPair, ttype int, text string, channel, start, stop, line, column int) Token {
+ t := NewCommonToken(source, ttype, channel, start, stop)
+
+ t.line = line
+ t.column = column
+
+ if text != "" {
+ t.SetText(text)
+ } else if c.copyText && source.charStream != nil {
+ t.SetText(source.charStream.GetTextFromInterval(NewInterval(start, stop)))
+ }
+
+ return t
+}
+
+func (c *CommonTokenFactory) createThin(ttype int, text string) Token {
+ t := NewCommonToken(nil, ttype, TokenDefaultChannel, -1, -1)
+ t.SetText(text)
+
+ return t
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/common_token_stream.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/common_token_stream.go
new file mode 100644
index 0000000000..c90e9b8904
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/common_token_stream.go
@@ -0,0 +1,447 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "strconv"
+)
+
+// CommonTokenStream is an implementation of TokenStream that loads tokens from
+// a TokenSource on-demand and places the tokens in a buffer to provide access
+// to any previous token by index. This token stream ignores the value of
+// Token.getChannel. If your parser requires the token stream filter tokens to
+// only those on a particular channel, such as Token.DEFAULT_CHANNEL or
+// Token.HIDDEN_CHANNEL, use a filtering token stream such a CommonTokenStream.
+type CommonTokenStream struct {
+ channel int
+
+ // fetchedEOF indicates whether the Token.EOF token has been fetched from
+ // tokenSource and added to tokens. This field improves performance for the
+ // following cases:
+ //
+ // consume: The lookahead check in consume to preven consuming the EOF symbol is
+ // optimized by checking the values of fetchedEOF and p instead of calling LA.
+ //
+ // fetch: The check to prevent adding multiple EOF symbols into tokens is
+ // trivial with bt field.
+ fetchedEOF bool
+
+ // index indexs into tokens of the current token (next token to consume).
+ // tokens[p] should be LT(1). It is set to -1 when the stream is first
+ // constructed or when SetTokenSource is called, indicating that the first token
+ // has not yet been fetched from the token source. For additional information,
+ // see the documentation of IntStream for a description of initializing methods.
+ index int
+
+ // tokenSource is the TokenSource from which tokens for the bt stream are
+ // fetched.
+ tokenSource TokenSource
+
+ // tokens is all tokens fetched from the token source. The list is considered a
+ // complete view of the input once fetchedEOF is set to true.
+ tokens []Token
+}
+
+func NewCommonTokenStream(lexer Lexer, channel int) *CommonTokenStream {
+ return &CommonTokenStream{
+ channel: channel,
+ index: -1,
+ tokenSource: lexer,
+ tokens: make([]Token, 0),
+ }
+}
+
+func (c *CommonTokenStream) GetAllTokens() []Token {
+ return c.tokens
+}
+
+func (c *CommonTokenStream) Mark() int {
+ return 0
+}
+
+func (c *CommonTokenStream) Release(marker int) {}
+
+func (c *CommonTokenStream) reset() {
+ c.Seek(0)
+}
+
+func (c *CommonTokenStream) Seek(index int) {
+ c.lazyInit()
+ c.index = c.adjustSeekIndex(index)
+}
+
+func (c *CommonTokenStream) Get(index int) Token {
+ c.lazyInit()
+
+ return c.tokens[index]
+}
+
+func (c *CommonTokenStream) Consume() {
+ SkipEOFCheck := false
+
+ if c.index >= 0 {
+ if c.fetchedEOF {
+ // The last token in tokens is EOF. Skip the check if p indexes any fetched.
+ // token except the last.
+ SkipEOFCheck = c.index < len(c.tokens)-1
+ } else {
+ // No EOF token in tokens. Skip the check if p indexes a fetched token.
+ SkipEOFCheck = c.index < len(c.tokens)
+ }
+ } else {
+ // Not yet initialized
+ SkipEOFCheck = false
+ }
+
+ if !SkipEOFCheck && c.LA(1) == TokenEOF {
+ panic("cannot consume EOF")
+ }
+
+ if c.Sync(c.index + 1) {
+ c.index = c.adjustSeekIndex(c.index + 1)
+ }
+}
+
+// Sync makes sure index i in tokens has a token and returns true if a token is
+// located at index i and otherwise false.
+func (c *CommonTokenStream) Sync(i int) bool {
+ n := i - len(c.tokens) + 1 // TODO: How many more elements do we need?
+
+ if n > 0 {
+ fetched := c.fetch(n)
+ return fetched >= n
+ }
+
+ return true
+}
+
+// fetch adds n elements to buffer and returns the actual number of elements
+// added to the buffer.
+func (c *CommonTokenStream) fetch(n int) int {
+ if c.fetchedEOF {
+ return 0
+ }
+
+ for i := 0; i < n; i++ {
+ t := c.tokenSource.NextToken()
+
+ t.SetTokenIndex(len(c.tokens))
+ c.tokens = append(c.tokens, t)
+
+ if t.GetTokenType() == TokenEOF {
+ c.fetchedEOF = true
+
+ return i + 1
+ }
+ }
+
+ return n
+}
+
+// GetTokens gets all tokens from start to stop inclusive.
+func (c *CommonTokenStream) GetTokens(start int, stop int, types *IntervalSet) []Token {
+ if start < 0 || stop < 0 {
+ return nil
+ }
+
+ c.lazyInit()
+
+ subset := make([]Token, 0)
+
+ if stop >= len(c.tokens) {
+ stop = len(c.tokens) - 1
+ }
+
+ for i := start; i < stop; i++ {
+ t := c.tokens[i]
+
+ if t.GetTokenType() == TokenEOF {
+ break
+ }
+
+ if types == nil || types.contains(t.GetTokenType()) {
+ subset = append(subset, t)
+ }
+ }
+
+ return subset
+}
+
+func (c *CommonTokenStream) LA(i int) int {
+ return c.LT(i).GetTokenType()
+}
+
+func (c *CommonTokenStream) lazyInit() {
+ if c.index == -1 {
+ c.setup()
+ }
+}
+
+func (c *CommonTokenStream) setup() {
+ c.Sync(0)
+ c.index = c.adjustSeekIndex(0)
+}
+
+func (c *CommonTokenStream) GetTokenSource() TokenSource {
+ return c.tokenSource
+}
+
+// SetTokenSource resets the c token stream by setting its token source.
+func (c *CommonTokenStream) SetTokenSource(tokenSource TokenSource) {
+ c.tokenSource = tokenSource
+ c.tokens = make([]Token, 0)
+ c.index = -1
+}
+
+// NextTokenOnChannel returns the index of the next token on channel given a
+// starting index. Returns i if tokens[i] is on channel. Returns -1 if there are
+// no tokens on channel between i and EOF.
+func (c *CommonTokenStream) NextTokenOnChannel(i, channel int) int {
+ c.Sync(i)
+
+ if i >= len(c.tokens) {
+ return -1
+ }
+
+ token := c.tokens[i]
+
+ for token.GetChannel() != c.channel {
+ if token.GetTokenType() == TokenEOF {
+ return -1
+ }
+
+ i++
+ c.Sync(i)
+ token = c.tokens[i]
+ }
+
+ return i
+}
+
+// previousTokenOnChannel returns the index of the previous token on channel
+// given a starting index. Returns i if tokens[i] is on channel. Returns -1 if
+// there are no tokens on channel between i and 0.
+func (c *CommonTokenStream) previousTokenOnChannel(i, channel int) int {
+ for i >= 0 && c.tokens[i].GetChannel() != channel {
+ i--
+ }
+
+ return i
+}
+
+// GetHiddenTokensToRight collects all tokens on a specified channel to the
+// right of the current token up until we see a token on DEFAULT_TOKEN_CHANNEL
+// or EOF. If channel is -1, it finds any non-default channel token.
+func (c *CommonTokenStream) GetHiddenTokensToRight(tokenIndex, channel int) []Token {
+ c.lazyInit()
+
+ if tokenIndex < 0 || tokenIndex >= len(c.tokens) {
+ panic(strconv.Itoa(tokenIndex) + " not in 0.." + strconv.Itoa(len(c.tokens)-1))
+ }
+
+ nextOnChannel := c.NextTokenOnChannel(tokenIndex+1, LexerDefaultTokenChannel)
+ from := tokenIndex + 1
+
+ // If no onchannel to the right, then nextOnChannel == -1, so set to to last token
+ var to int
+
+ if nextOnChannel == -1 {
+ to = len(c.tokens) - 1
+ } else {
+ to = nextOnChannel
+ }
+
+ return c.filterForChannel(from, to, channel)
+}
+
+// GetHiddenTokensToLeft collects all tokens on channel to the left of the
+// current token until we see a token on DEFAULT_TOKEN_CHANNEL. If channel is
+// -1, it finds any non default channel token.
+func (c *CommonTokenStream) GetHiddenTokensToLeft(tokenIndex, channel int) []Token {
+ c.lazyInit()
+
+ if tokenIndex < 0 || tokenIndex >= len(c.tokens) {
+ panic(strconv.Itoa(tokenIndex) + " not in 0.." + strconv.Itoa(len(c.tokens)-1))
+ }
+
+ prevOnChannel := c.previousTokenOnChannel(tokenIndex-1, LexerDefaultTokenChannel)
+
+ if prevOnChannel == tokenIndex-1 {
+ return nil
+ }
+
+ // If there are none on channel to the left and prevOnChannel == -1 then from = 0
+ from := prevOnChannel + 1
+ to := tokenIndex - 1
+
+ return c.filterForChannel(from, to, channel)
+}
+
+func (c *CommonTokenStream) filterForChannel(left, right, channel int) []Token {
+ hidden := make([]Token, 0)
+
+ for i := left; i < right+1; i++ {
+ t := c.tokens[i]
+
+ if channel == -1 {
+ if t.GetChannel() != LexerDefaultTokenChannel {
+ hidden = append(hidden, t)
+ }
+ } else if t.GetChannel() == channel {
+ hidden = append(hidden, t)
+ }
+ }
+
+ if len(hidden) == 0 {
+ return nil
+ }
+
+ return hidden
+}
+
+func (c *CommonTokenStream) GetSourceName() string {
+ return c.tokenSource.GetSourceName()
+}
+
+func (c *CommonTokenStream) Size() int {
+ return len(c.tokens)
+}
+
+func (c *CommonTokenStream) Index() int {
+ return c.index
+}
+
+func (c *CommonTokenStream) GetAllText() string {
+ return c.GetTextFromInterval(nil)
+}
+
+func (c *CommonTokenStream) GetTextFromTokens(start, end Token) string {
+ if start == nil || end == nil {
+ return ""
+ }
+
+ return c.GetTextFromInterval(NewInterval(start.GetTokenIndex(), end.GetTokenIndex()))
+}
+
+func (c *CommonTokenStream) GetTextFromRuleContext(interval RuleContext) string {
+ return c.GetTextFromInterval(interval.GetSourceInterval())
+}
+
+func (c *CommonTokenStream) GetTextFromInterval(interval *Interval) string {
+ c.lazyInit()
+ c.Fill()
+
+ if interval == nil {
+ interval = NewInterval(0, len(c.tokens)-1)
+ }
+
+ start := interval.Start
+ stop := interval.Stop
+
+ if start < 0 || stop < 0 {
+ return ""
+ }
+
+ if stop >= len(c.tokens) {
+ stop = len(c.tokens) - 1
+ }
+
+ s := ""
+
+ for i := start; i < stop+1; i++ {
+ t := c.tokens[i]
+
+ if t.GetTokenType() == TokenEOF {
+ break
+ }
+
+ s += t.GetText()
+ }
+
+ return s
+}
+
+// Fill gets all tokens from the lexer until EOF.
+func (c *CommonTokenStream) Fill() {
+ c.lazyInit()
+
+ for c.fetch(1000) == 1000 {
+ continue
+ }
+}
+
+func (c *CommonTokenStream) adjustSeekIndex(i int) int {
+ return c.NextTokenOnChannel(i, c.channel)
+}
+
+func (c *CommonTokenStream) LB(k int) Token {
+ if k == 0 || c.index-k < 0 {
+ return nil
+ }
+
+ i := c.index
+ n := 1
+
+ // Find k good tokens looking backward
+ for n <= k {
+ // Skip off-channel tokens
+ i = c.previousTokenOnChannel(i-1, c.channel)
+ n++
+ }
+
+ if i < 0 {
+ return nil
+ }
+
+ return c.tokens[i]
+}
+
+func (c *CommonTokenStream) LT(k int) Token {
+ c.lazyInit()
+
+ if k == 0 {
+ return nil
+ }
+
+ if k < 0 {
+ return c.LB(-k)
+ }
+
+ i := c.index
+ n := 1 // We know tokens[n] is valid
+
+ // Find k good tokens
+ for n < k {
+ // Skip off-channel tokens, but make sure to not look past EOF
+ if c.Sync(i + 1) {
+ i = c.NextTokenOnChannel(i+1, c.channel)
+ }
+
+ n++
+ }
+
+ return c.tokens[i]
+}
+
+// getNumberOfOnChannelTokens counts EOF once.
+func (c *CommonTokenStream) getNumberOfOnChannelTokens() int {
+ var n int
+
+ c.Fill()
+
+ for i := 0; i < len(c.tokens); i++ {
+ t := c.tokens[i]
+
+ if t.GetChannel() == c.channel {
+ n++
+ }
+
+ if t.GetTokenType() == TokenEOF {
+ break
+ }
+ }
+
+ return n
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa.go
new file mode 100644
index 0000000000..770c32a6bb
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa.go
@@ -0,0 +1,183 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "sort"
+ "sync"
+)
+
+type DFA struct {
+ // atnStartState is the ATN state in which this was created
+ atnStartState DecisionState
+
+ decision int
+
+ // states is all the DFA states. Use Map to get the old state back; Set can only
+ // indicate whether it is there.
+ states map[int]*DFAState
+ statesMu sync.RWMutex
+
+ s0 *DFAState
+ s0Mu sync.RWMutex
+
+ // precedenceDfa is the backing field for isPrecedenceDfa and setPrecedenceDfa.
+ // True if the DFA is for a precedence decision and false otherwise.
+ precedenceDfa bool
+ precedenceDfaMu sync.RWMutex
+}
+
+func NewDFA(atnStartState DecisionState, decision int) *DFA {
+ return &DFA{
+ atnStartState: atnStartState,
+ decision: decision,
+ states: make(map[int]*DFAState),
+ }
+}
+
+// getPrecedenceStartState gets the start state for the current precedence and
+// returns the start state corresponding to the specified precedence if a start
+// state exists for the specified precedence and nil otherwise. d must be a
+// precedence DFA. See also isPrecedenceDfa.
+func (d *DFA) getPrecedenceStartState(precedence int) *DFAState {
+ if !d.getPrecedenceDfa() {
+ panic("only precedence DFAs may contain a precedence start state")
+ }
+
+ // s0.edges is never nil for a precedence DFA
+ if precedence < 0 || precedence >= len(d.getS0().getEdges()) {
+ return nil
+ }
+
+ return d.getS0().getIthEdge(precedence)
+}
+
+// setPrecedenceStartState sets the start state for the current precedence. d
+// must be a precedence DFA. See also isPrecedenceDfa.
+func (d *DFA) setPrecedenceStartState(precedence int, startState *DFAState) {
+ if !d.getPrecedenceDfa() {
+ panic("only precedence DFAs may contain a precedence start state")
+ }
+
+ if precedence < 0 {
+ return
+ }
+
+ // Synchronization on s0 here is ok. When the DFA is turned into a
+ // precedence DFA, s0 will be initialized once and not updated again. s0.edges
+ // is never nil for a precedence DFA.
+ s0 := d.getS0()
+ if precedence >= s0.numEdges() {
+ edges := append(s0.getEdges(), make([]*DFAState, precedence+1-s0.numEdges())...)
+ s0.setEdges(edges)
+ d.setS0(s0)
+ }
+
+ s0.setIthEdge(precedence, startState)
+}
+
+func (d *DFA) getPrecedenceDfa() bool {
+ d.precedenceDfaMu.RLock()
+ defer d.precedenceDfaMu.RUnlock()
+ return d.precedenceDfa
+}
+
+// setPrecedenceDfa sets whether d is a precedence DFA. If precedenceDfa differs
+// from the current DFA configuration, then d.states is cleared, the initial
+// state s0 is set to a new DFAState with an empty outgoing DFAState.edges to
+// store the start states for individual precedence values if precedenceDfa is
+// true or nil otherwise, and d.precedenceDfa is updated.
+func (d *DFA) setPrecedenceDfa(precedenceDfa bool) {
+ if d.getPrecedenceDfa() != precedenceDfa {
+ d.setStates(make(map[int]*DFAState))
+
+ if precedenceDfa {
+ precedenceState := NewDFAState(-1, NewBaseATNConfigSet(false))
+
+ precedenceState.setEdges(make([]*DFAState, 0))
+ precedenceState.isAcceptState = false
+ precedenceState.requiresFullContext = false
+ d.setS0(precedenceState)
+ } else {
+ d.setS0(nil)
+ }
+
+ d.precedenceDfaMu.Lock()
+ defer d.precedenceDfaMu.Unlock()
+ d.precedenceDfa = precedenceDfa
+ }
+}
+
+func (d *DFA) getS0() *DFAState {
+ d.s0Mu.RLock()
+ defer d.s0Mu.RUnlock()
+ return d.s0
+}
+
+func (d *DFA) setS0(s *DFAState) {
+ d.s0Mu.Lock()
+ defer d.s0Mu.Unlock()
+ d.s0 = s
+}
+
+func (d *DFA) getState(hash int) (*DFAState, bool) {
+ d.statesMu.RLock()
+ defer d.statesMu.RUnlock()
+ s, ok := d.states[hash]
+ return s, ok
+}
+
+func (d *DFA) setStates(states map[int]*DFAState) {
+ d.statesMu.Lock()
+ defer d.statesMu.Unlock()
+ d.states = states
+}
+
+func (d *DFA) setState(hash int, state *DFAState) {
+ d.statesMu.Lock()
+ defer d.statesMu.Unlock()
+ d.states[hash] = state
+}
+
+func (d *DFA) numStates() int {
+ d.statesMu.RLock()
+ defer d.statesMu.RUnlock()
+ return len(d.states)
+}
+
+type dfaStateList []*DFAState
+
+func (d dfaStateList) Len() int { return len(d) }
+func (d dfaStateList) Less(i, j int) bool { return d[i].stateNumber < d[j].stateNumber }
+func (d dfaStateList) Swap(i, j int) { d[i], d[j] = d[j], d[i] }
+
+// sortedStates returns the states in d sorted by their state number.
+func (d *DFA) sortedStates() []*DFAState {
+ vs := make([]*DFAState, 0, len(d.states))
+
+ for _, v := range d.states {
+ vs = append(vs, v)
+ }
+
+ sort.Sort(dfaStateList(vs))
+
+ return vs
+}
+
+func (d *DFA) String(literalNames []string, symbolicNames []string) string {
+ if d.getS0() == nil {
+ return ""
+ }
+
+ return NewDFASerializer(d, literalNames, symbolicNames).String()
+}
+
+func (d *DFA) ToLexerString() string {
+ if d.getS0() == nil {
+ return ""
+ }
+
+ return NewLexerDFASerializer(d).String()
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa_serializer.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa_serializer.go
new file mode 100644
index 0000000000..fcfef975c2
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa_serializer.go
@@ -0,0 +1,152 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "strconv"
+)
+
+// DFASerializer is a DFA walker that knows how to dump them to serialized
+// strings.
+type DFASerializer struct {
+ dfa *DFA
+ literalNames []string
+ symbolicNames []string
+}
+
+func NewDFASerializer(dfa *DFA, literalNames, symbolicNames []string) *DFASerializer {
+ if literalNames == nil {
+ literalNames = make([]string, 0)
+ }
+
+ if symbolicNames == nil {
+ symbolicNames = make([]string, 0)
+ }
+
+ return &DFASerializer{
+ dfa: dfa,
+ literalNames: literalNames,
+ symbolicNames: symbolicNames,
+ }
+}
+
+func (d *DFASerializer) String() string {
+ if d.dfa.getS0() == nil {
+ return ""
+ }
+
+ buf := ""
+ states := d.dfa.sortedStates()
+
+ for _, s := range states {
+ if s.edges != nil {
+ n := len(s.edges)
+
+ for j := 0; j < n; j++ {
+ t := s.edges[j]
+
+ if t != nil && t.stateNumber != 0x7FFFFFFF {
+ buf += d.GetStateString(s)
+ buf += "-"
+ buf += d.getEdgeLabel(j)
+ buf += "->"
+ buf += d.GetStateString(t)
+ buf += "\n"
+ }
+ }
+ }
+ }
+
+ if len(buf) == 0 {
+ return ""
+ }
+
+ return buf
+}
+
+func (d *DFASerializer) getEdgeLabel(i int) string {
+ if i == 0 {
+ return "EOF"
+ } else if d.literalNames != nil && i-1 < len(d.literalNames) {
+ return d.literalNames[i-1]
+ } else if d.symbolicNames != nil && i-1 < len(d.symbolicNames) {
+ return d.symbolicNames[i-1]
+ }
+
+ return strconv.Itoa(i - 1)
+}
+
+func (d *DFASerializer) GetStateString(s *DFAState) string {
+ var a, b string
+
+ if s.isAcceptState {
+ a = ":"
+ }
+
+ if s.requiresFullContext {
+ b = "^"
+ }
+
+ baseStateStr := a + "s" + strconv.Itoa(s.stateNumber) + b
+
+ if s.isAcceptState {
+ if s.predicates != nil {
+ return baseStateStr + "=>" + fmt.Sprint(s.predicates)
+ }
+
+ return baseStateStr + "=>" + fmt.Sprint(s.prediction)
+ }
+
+ return baseStateStr
+}
+
+type LexerDFASerializer struct {
+ *DFASerializer
+}
+
+func NewLexerDFASerializer(dfa *DFA) *LexerDFASerializer {
+ return &LexerDFASerializer{DFASerializer: NewDFASerializer(dfa, nil, nil)}
+}
+
+func (l *LexerDFASerializer) getEdgeLabel(i int) string {
+ return "'" + string(i) + "'"
+}
+
+func (l *LexerDFASerializer) String() string {
+ if l.dfa.getS0() == nil {
+ return ""
+ }
+
+ buf := ""
+ states := l.dfa.sortedStates()
+
+ for i := 0; i < len(states); i++ {
+ s := states[i]
+
+ if s.edges != nil {
+ n := len(s.edges)
+
+ for j := 0; j < n; j++ {
+ t := s.edges[j]
+
+ if t != nil && t.stateNumber != 0x7FFFFFFF {
+ buf += l.GetStateString(s)
+ buf += "-"
+ buf += l.getEdgeLabel(j)
+ buf += "->"
+ buf += l.GetStateString(t)
+ buf += "\n"
+ }
+ }
+ }
+ }
+
+ if len(buf) == 0 {
+ return ""
+ }
+
+ return buf
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa_state.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa_state.go
new file mode 100644
index 0000000000..680ce9ace4
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/dfa_state.go
@@ -0,0 +1,198 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "sync"
+)
+
+// PredPrediction maps a predicate to a predicted alternative.
+type PredPrediction struct {
+ alt int
+ pred SemanticContext
+}
+
+func NewPredPrediction(pred SemanticContext, alt int) *PredPrediction {
+ return &PredPrediction{alt: alt, pred: pred}
+}
+
+func (p *PredPrediction) String() string {
+ return "(" + fmt.Sprint(p.pred) + ", " + fmt.Sprint(p.alt) + ")"
+}
+
+// DFAState represents a set of possible ATN configurations. As Aho, Sethi,
+// Ullman p. 117 says: "The DFA uses its state to keep track of all possible
+// states the ATN can be in after reading each input symbol. That is to say,
+// after reading input a1a2..an, the DFA is in a state that represents the
+// subset T of the states of the ATN that are reachable from the ATN's start
+// state along some path labeled a1a2..an." In conventional NFA-to-DFA
+// conversion, therefore, the subset T would be a bitset representing the set of
+// states the ATN could be in. We need to track the alt predicted by each state
+// as well, however. More importantly, we need to maintain a stack of states,
+// tracking the closure operations as they jump from rule to rule, emulating
+// rule invocations (method calls). I have to add a stack to simulate the proper
+// lookahead sequences for the underlying LL grammar from which the ATN was
+// derived.
+//
+// I use a set of ATNConfig objects, not simple states. An ATNConfig is both a
+// state (ala normal conversion) and a RuleContext describing the chain of rules
+// (if any) followed to arrive at that state.
+//
+// A DFAState may have multiple references to a particular state, but with
+// different ATN contexts (with same or different alts) meaning that state was
+// reached via a different set of rule invocations.
+type DFAState struct {
+ stateNumber int
+ configs ATNConfigSet
+
+ // edges elements point to the target of the symbol. Shift up by 1 so (-1)
+ // Token.EOF maps to the first element.
+ edges []*DFAState
+ edgesMu sync.RWMutex
+
+ isAcceptState bool
+
+ // prediction is the ttype we match or alt we predict if the state is accept.
+ // Set to ATN.INVALID_ALT_NUMBER when predicates != nil or
+ // requiresFullContext.
+ prediction int
+
+ lexerActionExecutor *LexerActionExecutor
+
+ // requiresFullContext indicates it was created during an SLL prediction that
+ // discovered a conflict between the configurations in the state. Future
+ // ParserATNSimulator.execATN invocations immediately jump doing
+ // full context prediction if true.
+ requiresFullContext bool
+
+ // predicates is the predicates associated with the ATN configurations of the
+ // DFA state during SLL parsing. When we have predicates, requiresFullContext
+ // is false, since full context prediction evaluates predicates on-the-fly. If
+ // d is
+ // not nil, then prediction is ATN.INVALID_ALT_NUMBER.
+ //
+ // We only use these for non-requiresFullContext but conflicting states. That
+ // means we know from the context (it's $ or we don't dip into outer context)
+ // that it's an ambiguity not a conflict.
+ //
+ // This list is computed by
+ // ParserATNSimulator.predicateDFAState.
+ predicates []*PredPrediction
+}
+
+func NewDFAState(stateNumber int, configs ATNConfigSet) *DFAState {
+ if configs == nil {
+ configs = NewBaseATNConfigSet(false)
+ }
+
+ return &DFAState{configs: configs, stateNumber: stateNumber}
+}
+
+// GetAltSet gets the set of all alts mentioned by all ATN configurations in d.
+func (d *DFAState) GetAltSet() *Set {
+ alts := NewSet(nil, nil)
+
+ if d.configs != nil {
+ for _, c := range d.configs.GetItems() {
+ alts.add(c.GetAlt())
+ }
+ }
+
+ if alts.length() == 0 {
+ return nil
+ }
+
+ return alts
+}
+
+func (d *DFAState) getEdges() []*DFAState {
+ d.edgesMu.RLock()
+ defer d.edgesMu.RUnlock()
+ return d.edges
+}
+
+func (d *DFAState) numEdges() int {
+ d.edgesMu.RLock()
+ defer d.edgesMu.RUnlock()
+ return len(d.edges)
+}
+
+func (d *DFAState) getIthEdge(i int) *DFAState {
+ d.edgesMu.RLock()
+ defer d.edgesMu.RUnlock()
+ return d.edges[i]
+}
+
+func (d *DFAState) setEdges(newEdges []*DFAState) {
+ d.edgesMu.Lock()
+ defer d.edgesMu.Unlock()
+ d.edges = newEdges
+}
+
+func (d *DFAState) setIthEdge(i int, edge *DFAState) {
+ d.edgesMu.Lock()
+ defer d.edgesMu.Unlock()
+ d.edges[i] = edge
+}
+
+func (d *DFAState) setPrediction(v int) {
+ d.prediction = v
+}
+
+// equals returns whether d equals other. Two DFAStates are equal if their ATN
+// configuration sets are the same. This method is used to see if a state
+// already exists.
+//
+// Because the number of alternatives and number of ATN configurations are
+// finite, there is a finite number of DFA states that can be processed. This is
+// necessary to show that the algorithm terminates.
+//
+// Cannot test the DFA state numbers here because in
+// ParserATNSimulator.addDFAState we need to know if any other state exists that
+// has d exact set of ATN configurations. The stateNumber is irrelevant.
+func (d *DFAState) equals(other interface{}) bool {
+ if d == other {
+ return true
+ } else if _, ok := other.(*DFAState); !ok {
+ return false
+ }
+
+ return d.configs.Equals(other.(*DFAState).configs)
+}
+
+func (d *DFAState) String() string {
+ var s string
+ if d.isAcceptState {
+ if d.predicates != nil {
+ s = "=>" + fmt.Sprint(d.predicates)
+ } else {
+ s = "=>" + fmt.Sprint(d.prediction)
+ }
+ }
+
+ return fmt.Sprintf("%d:%s%s", fmt.Sprint(d.configs), s)
+}
+
+func (d *DFAState) hash() int {
+ h := murmurInit(11)
+
+ c := 1
+ if d.isAcceptState {
+ if d.predicates != nil {
+ for _, p := range d.predicates {
+ h = murmurUpdate(h, p.alt)
+ h = murmurUpdate(h, p.pred.hash())
+ c += 2
+ }
+ } else {
+ h = murmurUpdate(h, d.prediction)
+ c += 1
+ }
+ }
+
+ h = murmurUpdate(h, d.configs.hash())
+ return murmurFinish(h, c)
+}
\ No newline at end of file
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/diagnostic_error_listener.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/diagnostic_error_listener.go
new file mode 100644
index 0000000000..1fec43d9dc
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/diagnostic_error_listener.go
@@ -0,0 +1,111 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "strconv"
+)
+
+//
+// This implementation of {@link ANTLRErrorListener} can be used to identify
+// certain potential correctness and performance problems in grammars. "reports"
+// are made by calling {@link Parser//NotifyErrorListeners} with the appropriate
+// message.
+//
+//
+//
Ambiguities: These are cases where more than one path through the
+// grammar can Match the input.
+//
Weak context sensitivity: These are cases where full-context
+// prediction resolved an SLL conflict to a unique alternative which equaled the
+// minimum alternative of the SLL conflict.
+//
Strong (forced) context sensitivity: These are cases where the
+// full-context prediction resolved an SLL conflict to a unique alternative,
+// and the minimum alternative of the SLL conflict was found to not be
+// a truly viable alternative. Two-stage parsing cannot be used for inputs where
+// d situation occurs.
+//
+
+type DiagnosticErrorListener struct {
+ *DefaultErrorListener
+
+ exactOnly bool
+}
+
+func NewDiagnosticErrorListener(exactOnly bool) *DiagnosticErrorListener {
+
+ n := new(DiagnosticErrorListener)
+
+ // whether all ambiguities or only exact ambiguities are Reported.
+ n.exactOnly = exactOnly
+ return n
+}
+
+func (d *DiagnosticErrorListener) ReportAmbiguity(recognizer Parser, dfa *DFA, startIndex, stopIndex int, exact bool, ambigAlts *BitSet, configs ATNConfigSet) {
+ if d.exactOnly && !exact {
+ return
+ }
+ msg := "reportAmbiguity d=" +
+ d.getDecisionDescription(recognizer, dfa) +
+ ": ambigAlts=" +
+ d.getConflictingAlts(ambigAlts, configs).String() +
+ ", input='" +
+ recognizer.GetTokenStream().GetTextFromInterval(NewInterval(startIndex, stopIndex)) + "'"
+ recognizer.NotifyErrorListeners(msg, nil, nil)
+}
+
+func (d *DiagnosticErrorListener) ReportAttemptingFullContext(recognizer Parser, dfa *DFA, startIndex, stopIndex int, conflictingAlts *BitSet, configs ATNConfigSet) {
+
+ msg := "reportAttemptingFullContext d=" +
+ d.getDecisionDescription(recognizer, dfa) +
+ ", input='" +
+ recognizer.GetTokenStream().GetTextFromInterval(NewInterval(startIndex, stopIndex)) + "'"
+ recognizer.NotifyErrorListeners(msg, nil, nil)
+}
+
+func (d *DiagnosticErrorListener) ReportContextSensitivity(recognizer Parser, dfa *DFA, startIndex, stopIndex, prediction int, configs ATNConfigSet) {
+ msg := "reportContextSensitivity d=" +
+ d.getDecisionDescription(recognizer, dfa) +
+ ", input='" +
+ recognizer.GetTokenStream().GetTextFromInterval(NewInterval(startIndex, stopIndex)) + "'"
+ recognizer.NotifyErrorListeners(msg, nil, nil)
+}
+
+func (d *DiagnosticErrorListener) getDecisionDescription(recognizer Parser, dfa *DFA) string {
+ decision := dfa.decision
+ ruleIndex := dfa.atnStartState.GetRuleIndex()
+
+ ruleNames := recognizer.GetRuleNames()
+ if ruleIndex < 0 || ruleIndex >= len(ruleNames) {
+ return strconv.Itoa(decision)
+ }
+ ruleName := ruleNames[ruleIndex]
+ if ruleName == "" {
+ return strconv.Itoa(decision)
+ }
+ return strconv.Itoa(decision) + " (" + ruleName + ")"
+}
+
+//
+// Computes the set of conflicting or ambiguous alternatives from a
+// configuration set, if that information was not already provided by the
+// parser.
+//
+// @param ReportedAlts The set of conflicting or ambiguous alternatives, as
+// Reported by the parser.
+// @param configs The conflicting or ambiguous configuration set.
+// @return Returns {@code ReportedAlts} if it is not {@code nil}, otherwise
+// returns the set of alternatives represented in {@code configs}.
+//
+func (d *DiagnosticErrorListener) getConflictingAlts(ReportedAlts *BitSet, set ATNConfigSet) *BitSet {
+ if ReportedAlts != nil {
+ return ReportedAlts
+ }
+ result := NewBitSet()
+ for _, c := range set.GetItems() {
+ result.add(c.GetAlt())
+ }
+
+ return result
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/error_listener.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/error_listener.go
new file mode 100644
index 0000000000..028e1a9d7f
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/error_listener.go
@@ -0,0 +1,108 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "os"
+ "strconv"
+)
+
+// Provides an empty default implementation of {@link ANTLRErrorListener}. The
+// default implementation of each method does nothing, but can be overridden as
+// necessary.
+
+type ErrorListener interface {
+ SyntaxError(recognizer Recognizer, offendingSymbol interface{}, line, column int, msg string, e RecognitionException)
+ ReportAmbiguity(recognizer Parser, dfa *DFA, startIndex, stopIndex int, exact bool, ambigAlts *BitSet, configs ATNConfigSet)
+ ReportAttemptingFullContext(recognizer Parser, dfa *DFA, startIndex, stopIndex int, conflictingAlts *BitSet, configs ATNConfigSet)
+ ReportContextSensitivity(recognizer Parser, dfa *DFA, startIndex, stopIndex, prediction int, configs ATNConfigSet)
+}
+
+type DefaultErrorListener struct {
+}
+
+func NewDefaultErrorListener() *DefaultErrorListener {
+ return new(DefaultErrorListener)
+}
+
+func (d *DefaultErrorListener) SyntaxError(recognizer Recognizer, offendingSymbol interface{}, line, column int, msg string, e RecognitionException) {
+}
+
+func (d *DefaultErrorListener) ReportAmbiguity(recognizer Parser, dfa *DFA, startIndex, stopIndex int, exact bool, ambigAlts *BitSet, configs ATNConfigSet) {
+}
+
+func (d *DefaultErrorListener) ReportAttemptingFullContext(recognizer Parser, dfa *DFA, startIndex, stopIndex int, conflictingAlts *BitSet, configs ATNConfigSet) {
+}
+
+func (d *DefaultErrorListener) ReportContextSensitivity(recognizer Parser, dfa *DFA, startIndex, stopIndex, prediction int, configs ATNConfigSet) {
+}
+
+type ConsoleErrorListener struct {
+ *DefaultErrorListener
+}
+
+func NewConsoleErrorListener() *ConsoleErrorListener {
+ return new(ConsoleErrorListener)
+}
+
+//
+// Provides a default instance of {@link ConsoleErrorListener}.
+//
+var ConsoleErrorListenerINSTANCE = NewConsoleErrorListener()
+
+//
+// {@inheritDoc}
+//
+//
+// This implementation prints messages to {@link System//err} containing the
+// values of {@code line}, {@code charPositionInLine}, and {@code msg} using
+// the following format.
+//
+//
+// line line:charPositionInLinemsg
+//
+//
+func (c *ConsoleErrorListener) SyntaxError(recognizer Recognizer, offendingSymbol interface{}, line, column int, msg string, e RecognitionException) {
+ fmt.Fprintln(os.Stderr, "line "+strconv.Itoa(line)+":"+strconv.Itoa(column)+" "+msg)
+}
+
+type ProxyErrorListener struct {
+ *DefaultErrorListener
+ delegates []ErrorListener
+}
+
+func NewProxyErrorListener(delegates []ErrorListener) *ProxyErrorListener {
+ if delegates == nil {
+ panic("delegates is not provided")
+ }
+ l := new(ProxyErrorListener)
+ l.delegates = delegates
+ return l
+}
+
+func (p *ProxyErrorListener) SyntaxError(recognizer Recognizer, offendingSymbol interface{}, line, column int, msg string, e RecognitionException) {
+ for _, d := range p.delegates {
+ d.SyntaxError(recognizer, offendingSymbol, line, column, msg, e)
+ }
+}
+
+func (p *ProxyErrorListener) ReportAmbiguity(recognizer Parser, dfa *DFA, startIndex, stopIndex int, exact bool, ambigAlts *BitSet, configs ATNConfigSet) {
+ for _, d := range p.delegates {
+ d.ReportAmbiguity(recognizer, dfa, startIndex, stopIndex, exact, ambigAlts, configs)
+ }
+}
+
+func (p *ProxyErrorListener) ReportAttemptingFullContext(recognizer Parser, dfa *DFA, startIndex, stopIndex int, conflictingAlts *BitSet, configs ATNConfigSet) {
+ for _, d := range p.delegates {
+ d.ReportAttemptingFullContext(recognizer, dfa, startIndex, stopIndex, conflictingAlts, configs)
+ }
+}
+
+func (p *ProxyErrorListener) ReportContextSensitivity(recognizer Parser, dfa *DFA, startIndex, stopIndex, prediction int, configs ATNConfigSet) {
+ for _, d := range p.delegates {
+ d.ReportContextSensitivity(recognizer, dfa, startIndex, stopIndex, prediction, configs)
+ }
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/error_strategy.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/error_strategy.go
new file mode 100644
index 0000000000..977a6e4549
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/error_strategy.go
@@ -0,0 +1,758 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "reflect"
+ "strconv"
+ "strings"
+)
+
+type ErrorStrategy interface {
+ reset(Parser)
+ RecoverInline(Parser) Token
+ Recover(Parser, RecognitionException)
+ Sync(Parser)
+ inErrorRecoveryMode(Parser) bool
+ ReportError(Parser, RecognitionException)
+ ReportMatch(Parser)
+}
+
+// This is the default implementation of {@link ANTLRErrorStrategy} used for
+// error Reporting and recovery in ANTLR parsers.
+//
+type DefaultErrorStrategy struct {
+ errorRecoveryMode bool
+ lastErrorIndex int
+ lastErrorStates *IntervalSet
+}
+
+var _ ErrorStrategy = &DefaultErrorStrategy{}
+
+func NewDefaultErrorStrategy() *DefaultErrorStrategy {
+
+ d := new(DefaultErrorStrategy)
+
+ // Indicates whether the error strategy is currently "recovering from an
+ // error". This is used to suppress Reporting multiple error messages while
+ // attempting to recover from a detected syntax error.
+ //
+ // @see //inErrorRecoveryMode
+ //
+ d.errorRecoveryMode = false
+
+ // The index into the input stream where the last error occurred.
+ // This is used to prevent infinite loops where an error is found
+ // but no token is consumed during recovery...another error is found,
+ // ad nauseum. This is a failsafe mechanism to guarantee that at least
+ // one token/tree node is consumed for two errors.
+ //
+ d.lastErrorIndex = -1
+ d.lastErrorStates = nil
+ return d
+}
+
+//
The default implementation simply calls {@link //endErrorCondition} to
+// ensure that the handler is not in error recovery mode.
+func (d *DefaultErrorStrategy) reset(recognizer Parser) {
+ d.endErrorCondition(recognizer)
+}
+
+//
+// This method is called to enter error recovery mode when a recognition
+// exception is Reported.
+//
+// @param recognizer the parser instance
+//
+func (d *DefaultErrorStrategy) beginErrorCondition(recognizer Parser) {
+ d.errorRecoveryMode = true
+}
+
+func (d *DefaultErrorStrategy) inErrorRecoveryMode(recognizer Parser) bool {
+ return d.errorRecoveryMode
+}
+
+//
+// This method is called to leave error recovery mode after recovering from
+// a recognition exception.
+//
+// @param recognizer
+//
+func (d *DefaultErrorStrategy) endErrorCondition(recognizer Parser) {
+ d.errorRecoveryMode = false
+ d.lastErrorStates = nil
+ d.lastErrorIndex = -1
+}
+
+//
+// {@inheritDoc}
+//
+//
The default implementation simply calls {@link //endErrorCondition}.
The default implementation returns immediately if the handler is already
+// in error recovery mode. Otherwise, it calls {@link //beginErrorCondition}
+// and dispatches the Reporting task based on the runtime type of {@code e}
+// according to the following table.
+//
+//
+//
{@link NoViableAltException}: Dispatches the call to
+// {@link //ReportNoViableAlternative}
+//
{@link InputMisMatchException}: Dispatches the call to
+// {@link //ReportInputMisMatch}
+//
{@link FailedPredicateException}: Dispatches the call to
+// {@link //ReportFailedPredicate}
+//
All other types: calls {@link Parser//NotifyErrorListeners} to Report
+// the exception
+//
+//
+func (d *DefaultErrorStrategy) ReportError(recognizer Parser, e RecognitionException) {
+ // if we've already Reported an error and have not Matched a token
+ // yet successfully, don't Report any errors.
+ if d.inErrorRecoveryMode(recognizer) {
+ return // don't Report spurious errors
+ }
+ d.beginErrorCondition(recognizer)
+
+ switch t := e.(type) {
+ default:
+ fmt.Println("unknown recognition error type: " + reflect.TypeOf(e).Name())
+ // fmt.Println(e.stack)
+ recognizer.NotifyErrorListeners(e.GetMessage(), e.GetOffendingToken(), e)
+ case *NoViableAltException:
+ d.ReportNoViableAlternative(recognizer, t)
+ case *InputMisMatchException:
+ d.ReportInputMisMatch(recognizer, t)
+ case *FailedPredicateException:
+ d.ReportFailedPredicate(recognizer, t)
+ }
+}
+
+// {@inheritDoc}
+//
+//
The default implementation reSynchronizes the parser by consuming tokens
+// until we find one in the reSynchronization set--loosely the set of tokens
+// that can follow the current rule.
+//
+func (d *DefaultErrorStrategy) Recover(recognizer Parser, e RecognitionException) {
+
+ if d.lastErrorIndex == recognizer.GetInputStream().Index() &&
+ d.lastErrorStates != nil && d.lastErrorStates.contains(recognizer.GetState()) {
+ // uh oh, another error at same token index and previously-Visited
+ // state in ATN must be a case where LT(1) is in the recovery
+ // token set so nothing got consumed. Consume a single token
+ // at least to prevent an infinite loop d is a failsafe.
+ recognizer.Consume()
+ }
+ d.lastErrorIndex = recognizer.GetInputStream().Index()
+ if d.lastErrorStates == nil {
+ d.lastErrorStates = NewIntervalSet()
+ }
+ d.lastErrorStates.addOne(recognizer.GetState())
+ followSet := d.getErrorRecoverySet(recognizer)
+ d.consumeUntil(recognizer, followSet)
+}
+
+// The default implementation of {@link ANTLRErrorStrategy//Sync} makes sure
+// that the current lookahead symbol is consistent with what were expecting
+// at d point in the ATN. You can call d anytime but ANTLR only
+// generates code to check before subrules/loops and each iteration.
+//
+//
Implements Jim Idle's magic Sync mechanism in closures and optional
+// subrules. E.g.,
+//
+//
+// a : Sync ( stuff Sync )*
+// Sync : {consume to what can follow Sync}
+//
+//
+// At the start of a sub rule upon error, {@link //Sync} performs single
+// token deletion, if possible. If it can't do that, it bails on the current
+// rule and uses the default error recovery, which consumes until the
+// reSynchronization set of the current rule.
+//
+//
If the sub rule is optional ({@code (...)?}, {@code (...)*}, or block
+// with an empty alternative), then the expected set includes what follows
+// the subrule.
+//
+//
During loop iteration, it consumes until it sees a token that can start a
+// sub rule or what follows loop. Yes, that is pretty aggressive. We opt to
+// stay in the loop as long as possible.
+//
+//
ORIGINS
+//
+//
Previous versions of ANTLR did a poor job of their recovery within loops.
+// A single mismatch token or missing token would force the parser to bail
+// out of the entire rules surrounding the loop. So, for rule
+//
+//
+// classfunc : 'class' ID '{' member* '}'
+//
+//
+// input with an extra token between members would force the parser to
+// consume until it found the next class definition rather than the next
+// member definition of the current class.
+//
+//
This functionality cost a little bit of effort because the parser has to
+// compare token set at the start of the loop and at each iteration. If for
+// some reason speed is suffering for you, you can turn off d
+// functionality by simply overriding d method as a blank { }.
+//
+func (d *DefaultErrorStrategy) Sync(recognizer Parser) {
+ // If already recovering, don't try to Sync
+ if d.inErrorRecoveryMode(recognizer) {
+ return
+ }
+
+ s := recognizer.GetInterpreter().atn.states[recognizer.GetState()]
+ la := recognizer.GetTokenStream().LA(1)
+
+ // try cheaper subset first might get lucky. seems to shave a wee bit off
+ nextTokens := recognizer.GetATN().NextTokens(s, nil)
+ if nextTokens.contains(TokenEpsilon) || nextTokens.contains(la) {
+ return
+ }
+
+ switch s.GetStateType() {
+ case ATNStateBlockStart, ATNStateStarBlockStart, ATNStatePlusBlockStart, ATNStateStarLoopEntry:
+ // Report error and recover if possible
+ if d.SingleTokenDeletion(recognizer) != nil {
+ return
+ }
+ panic(NewInputMisMatchException(recognizer))
+ case ATNStatePlusLoopBack, ATNStateStarLoopBack:
+ d.ReportUnwantedToken(recognizer)
+ expecting := NewIntervalSet()
+ expecting.addSet(recognizer.GetExpectedTokens())
+ whatFollowsLoopIterationOrRule := expecting.addSet(d.getErrorRecoverySet(recognizer))
+ d.consumeUntil(recognizer, whatFollowsLoopIterationOrRule)
+ default:
+ // do nothing if we can't identify the exact kind of ATN state
+ }
+}
+
+// This is called by {@link //ReportError} when the exception is a
+// {@link NoViableAltException}.
+//
+// @see //ReportError
+//
+// @param recognizer the parser instance
+// @param e the recognition exception
+//
+func (d *DefaultErrorStrategy) ReportNoViableAlternative(recognizer Parser, e *NoViableAltException) {
+ tokens := recognizer.GetTokenStream()
+ var input string
+ if tokens != nil {
+ if e.startToken.GetTokenType() == TokenEOF {
+ input = ""
+ } else {
+ input = tokens.GetTextFromTokens(e.startToken, e.offendingToken)
+ }
+ } else {
+ input = ""
+ }
+ msg := "no viable alternative at input " + d.escapeWSAndQuote(input)
+ recognizer.NotifyErrorListeners(msg, e.offendingToken, e)
+}
+
+//
+// This is called by {@link //ReportError} when the exception is an
+// {@link InputMisMatchException}.
+//
+// @see //ReportError
+//
+// @param recognizer the parser instance
+// @param e the recognition exception
+//
+func (this *DefaultErrorStrategy) ReportInputMisMatch(recognizer Parser, e *InputMisMatchException) {
+ msg := "mismatched input " + this.GetTokenErrorDisplay(e.offendingToken) +
+ " expecting " + e.getExpectedTokens().StringVerbose(recognizer.GetLiteralNames(), recognizer.GetSymbolicNames(), false)
+ recognizer.NotifyErrorListeners(msg, e.offendingToken, e)
+}
+
+//
+// This is called by {@link //ReportError} when the exception is a
+// {@link FailedPredicateException}.
+//
+// @see //ReportError
+//
+// @param recognizer the parser instance
+// @param e the recognition exception
+//
+func (d *DefaultErrorStrategy) ReportFailedPredicate(recognizer Parser, e *FailedPredicateException) {
+ ruleName := recognizer.GetRuleNames()[recognizer.GetParserRuleContext().GetRuleIndex()]
+ msg := "rule " + ruleName + " " + e.message
+ recognizer.NotifyErrorListeners(msg, e.offendingToken, e)
+}
+
+// This method is called to Report a syntax error which requires the removal
+// of a token from the input stream. At the time d method is called, the
+// erroneous symbol is current {@code LT(1)} symbol and has not yet been
+// removed from the input stream. When d method returns,
+// {@code recognizer} is in error recovery mode.
+//
+//
This method is called when {@link //singleTokenDeletion} identifies
+// single-token deletion as a viable recovery strategy for a mismatched
+// input error.
+//
+//
The default implementation simply returns if the handler is already in
+// error recovery mode. Otherwise, it calls {@link //beginErrorCondition} to
+// enter error recovery mode, followed by calling
+// {@link Parser//NotifyErrorListeners}.
+//
+// @param recognizer the parser instance
+//
+func (d *DefaultErrorStrategy) ReportUnwantedToken(recognizer Parser) {
+ if d.inErrorRecoveryMode(recognizer) {
+ return
+ }
+ d.beginErrorCondition(recognizer)
+ t := recognizer.GetCurrentToken()
+ tokenName := d.GetTokenErrorDisplay(t)
+ expecting := d.GetExpectedTokens(recognizer)
+ msg := "extraneous input " + tokenName + " expecting " +
+ expecting.StringVerbose(recognizer.GetLiteralNames(), recognizer.GetSymbolicNames(), false)
+ recognizer.NotifyErrorListeners(msg, t, nil)
+}
+
+// This method is called to Report a syntax error which requires the
+// insertion of a missing token into the input stream. At the time d
+// method is called, the missing token has not yet been inserted. When d
+// method returns, {@code recognizer} is in error recovery mode.
+//
+//
This method is called when {@link //singleTokenInsertion} identifies
+// single-token insertion as a viable recovery strategy for a mismatched
+// input error.
+//
+//
The default implementation simply returns if the handler is already in
+// error recovery mode. Otherwise, it calls {@link //beginErrorCondition} to
+// enter error recovery mode, followed by calling
+// {@link Parser//NotifyErrorListeners}.
The default implementation attempts to recover from the mismatched input
+// by using single token insertion and deletion as described below. If the
+// recovery attempt fails, d method panics an
+// {@link InputMisMatchException}.
+//
+//
EXTRA TOKEN (single token deletion)
+//
+//
{@code LA(1)} is not what we are looking for. If {@code LA(2)} has the
+// right token, however, then assume {@code LA(1)} is some extra spurious
+// token and delete it. Then consume and return the next token (which was
+// the {@code LA(2)} token) as the successful result of the Match operation.
+//
+//
This recovery strategy is implemented by {@link
+// //singleTokenDeletion}.
+//
+//
MISSING TOKEN (single token insertion)
+//
+//
If current token (at {@code LA(1)}) is consistent with what could come
+// after the expected {@code LA(1)} token, then assume the token is missing
+// and use the parser's {@link TokenFactory} to create it on the fly. The
+// "insertion" is performed by returning the created token as the successful
+// result of the Match operation.
+//
+//
This recovery strategy is implemented by {@link
+// //singleTokenInsertion}.
+//
+//
EXAMPLE
+//
+//
For example, Input {@code i=(3} is clearly missing the {@code ')'}. When
+// the parser returns from the nested call to {@code expr}, it will have
+// call chain:
+//
+//
+// stat &rarr expr &rarr atom
+//
+//
+// and it will be trying to Match the {@code ')'} at d point in the
+// derivation:
+//
+//
+// => ID '=' '(' INT ')' ('+' atom)* ''
+// ^
+//
+//
+// The attempt to Match {@code ')'} will fail when it sees {@code ''} and
+// call {@link //recoverInline}. To recover, it sees that {@code LA(1)==''}
+// is in the set of tokens that can follow the {@code ')'} token reference
+// in rule {@code atom}. It can assume that you forgot the {@code ')'}.
+//
+func (d *DefaultErrorStrategy) RecoverInline(recognizer Parser) Token {
+ // SINGLE TOKEN DELETION
+ MatchedSymbol := d.SingleTokenDeletion(recognizer)
+ if MatchedSymbol != nil {
+ // we have deleted the extra token.
+ // now, move past ttype token as if all were ok
+ recognizer.Consume()
+ return MatchedSymbol
+ }
+ // SINGLE TOKEN INSERTION
+ if d.SingleTokenInsertion(recognizer) {
+ return d.GetMissingSymbol(recognizer)
+ }
+ // even that didn't work must panic the exception
+ panic(NewInputMisMatchException(recognizer))
+}
+
+//
+// This method implements the single-token insertion inline error recovery
+// strategy. It is called by {@link //recoverInline} if the single-token
+// deletion strategy fails to recover from the mismatched input. If this
+// method returns {@code true}, {@code recognizer} will be in error recovery
+// mode.
+//
+//
This method determines whether or not single-token insertion is viable by
+// checking if the {@code LA(1)} input symbol could be successfully Matched
+// if it were instead the {@code LA(2)} symbol. If d method returns
+// {@code true}, the caller is responsible for creating and inserting a
+// token with the correct type to produce d behavior.
+//
+// @param recognizer the parser instance
+// @return {@code true} if single-token insertion is a viable recovery
+// strategy for the current mismatched input, otherwise {@code false}
+//
+func (d *DefaultErrorStrategy) SingleTokenInsertion(recognizer Parser) bool {
+ currentSymbolType := recognizer.GetTokenStream().LA(1)
+ // if current token is consistent with what could come after current
+ // ATN state, then we know we're missing a token error recovery
+ // is free to conjure up and insert the missing token
+ atn := recognizer.GetInterpreter().atn
+ currentState := atn.states[recognizer.GetState()]
+ next := currentState.GetTransitions()[0].getTarget()
+ expectingAtLL2 := atn.NextTokens(next, recognizer.GetParserRuleContext())
+ if expectingAtLL2.contains(currentSymbolType) {
+ d.ReportMissingToken(recognizer)
+ return true
+ }
+
+ return false
+}
+
+// This method implements the single-token deletion inline error recovery
+// strategy. It is called by {@link //recoverInline} to attempt to recover
+// from mismatched input. If this method returns nil, the parser and error
+// handler state will not have changed. If this method returns non-nil,
+// {@code recognizer} will not be in error recovery mode since the
+// returned token was a successful Match.
+//
+//
If the single-token deletion is successful, d method calls
+// {@link //ReportUnwantedToken} to Report the error, followed by
+// {@link Parser//consume} to actually "delete" the extraneous token. Then,
+// before returning {@link //ReportMatch} is called to signal a successful
+// Match.
+//
+// @param recognizer the parser instance
+// @return the successfully Matched {@link Token} instance if single-token
+// deletion successfully recovers from the mismatched input, otherwise
+// {@code nil}
+//
+func (d *DefaultErrorStrategy) SingleTokenDeletion(recognizer Parser) Token {
+ NextTokenType := recognizer.GetTokenStream().LA(2)
+ expecting := d.GetExpectedTokens(recognizer)
+ if expecting.contains(NextTokenType) {
+ d.ReportUnwantedToken(recognizer)
+ // print("recoverFromMisMatchedToken deleting " \
+ // + str(recognizer.GetTokenStream().LT(1)) \
+ // + " since " + str(recognizer.GetTokenStream().LT(2)) \
+ // + " is what we want", file=sys.stderr)
+ recognizer.Consume() // simply delete extra token
+ // we want to return the token we're actually Matching
+ MatchedSymbol := recognizer.GetCurrentToken()
+ d.ReportMatch(recognizer) // we know current token is correct
+ return MatchedSymbol
+ }
+
+ return nil
+}
+
+// Conjure up a missing token during error recovery.
+//
+// The recognizer attempts to recover from single missing
+// symbols. But, actions might refer to that missing symbol.
+// For example, x=ID {f($x)}. The action clearly assumes
+// that there has been an identifier Matched previously and that
+// $x points at that token. If that token is missing, but
+// the next token in the stream is what we want we assume that
+// d token is missing and we keep going. Because we
+// have to return some token to replace the missing token,
+// we have to conjure one up. This method gives the user control
+// over the tokens returned for missing tokens. Mostly,
+// you will want to create something special for identifier
+// tokens. For literals such as '{' and ',', the default
+// action in the parser or tree parser works. It simply creates
+// a CommonToken of the appropriate type. The text will be the token.
+// If you change what tokens must be created by the lexer,
+// override d method to create the appropriate tokens.
+//
+func (d *DefaultErrorStrategy) GetMissingSymbol(recognizer Parser) Token {
+ currentSymbol := recognizer.GetCurrentToken()
+ expecting := d.GetExpectedTokens(recognizer)
+ expectedTokenType := expecting.first()
+ var tokenText string
+
+ if expectedTokenType == TokenEOF {
+ tokenText = ""
+ } else {
+ ln := recognizer.GetLiteralNames()
+ if expectedTokenType > 0 && expectedTokenType < len(ln) {
+ tokenText = ""
+ } else {
+ tokenText = "" // TODO matches the JS impl
+ }
+ }
+ current := currentSymbol
+ lookback := recognizer.GetTokenStream().LT(-1)
+ if current.GetTokenType() == TokenEOF && lookback != nil {
+ current = lookback
+ }
+
+ tf := recognizer.GetTokenFactory()
+
+ return tf.Create(current.GetSource(), expectedTokenType, tokenText, TokenDefaultChannel, -1, -1, current.GetLine(), current.GetColumn())
+}
+
+func (d *DefaultErrorStrategy) GetExpectedTokens(recognizer Parser) *IntervalSet {
+ return recognizer.GetExpectedTokens()
+}
+
+// How should a token be displayed in an error message? The default
+// is to display just the text, but during development you might
+// want to have a lot of information spit out. Override in that case
+// to use t.String() (which, for CommonToken, dumps everything about
+// the token). This is better than forcing you to override a method in
+// your token objects because you don't have to go modify your lexer
+// so that it creates a NewJava type.
+//
+func (d *DefaultErrorStrategy) GetTokenErrorDisplay(t Token) string {
+ if t == nil {
+ return ""
+ }
+ s := t.GetText()
+ if s == "" {
+ if t.GetTokenType() == TokenEOF {
+ s = ""
+ } else {
+ s = "<" + strconv.Itoa(t.GetTokenType()) + ">"
+ }
+ }
+ return d.escapeWSAndQuote(s)
+}
+
+func (d *DefaultErrorStrategy) escapeWSAndQuote(s string) string {
+ s = strings.Replace(s, "\t", "\\t", -1)
+ s = strings.Replace(s, "\n", "\\n", -1)
+ s = strings.Replace(s, "\r", "\\r", -1)
+ return "'" + s + "'"
+}
+
+// Compute the error recovery set for the current rule. During
+// rule invocation, the parser pushes the set of tokens that can
+// follow that rule reference on the stack d amounts to
+// computing FIRST of what follows the rule reference in the
+// enclosing rule. See LinearApproximator.FIRST().
+// This local follow set only includes tokens
+// from within the rule i.e., the FIRST computation done by
+// ANTLR stops at the end of a rule.
+//
+// EXAMPLE
+//
+// When you find a "no viable alt exception", the input is not
+// consistent with any of the alternatives for rule r. The best
+// thing to do is to consume tokens until you see something that
+// can legally follow a call to r//or* any rule that called r.
+// You don't want the exact set of viable next tokens because the
+// input might just be missing a token--you might consume the
+// rest of the input looking for one of the missing tokens.
+//
+// Consider grammar:
+//
+// a : '[' b ']'
+// | '(' b ')'
+//
+// b : c '^' INT
+// c : ID
+// | INT
+//
+//
+// At each rule invocation, the set of tokens that could follow
+// that rule is pushed on a stack. Here are the various
+// context-sensitive follow sets:
+//
+// FOLLOW(b1_in_a) = FIRST(']') = ']'
+// FOLLOW(b2_in_a) = FIRST(')') = ')'
+// FOLLOW(c_in_b) = FIRST('^') = '^'
+//
+// Upon erroneous input "[]", the call chain is
+//
+// a -> b -> c
+//
+// and, hence, the follow context stack is:
+//
+// depth follow set start of rule execution
+// 0 a (from main())
+// 1 ']' b
+// 2 '^' c
+//
+// Notice that ')' is not included, because b would have to have
+// been called from a different context in rule a for ')' to be
+// included.
+//
+// For error recovery, we cannot consider FOLLOW(c)
+// (context-sensitive or otherwise). We need the combined set of
+// all context-sensitive FOLLOW sets--the set of all tokens that
+// could follow any reference in the call chain. We need to
+// reSync to one of those tokens. Note that FOLLOW(c)='^' and if
+// we reSync'd to that token, we'd consume until EOF. We need to
+// Sync to context-sensitive FOLLOWs for a, b, and c: {']','^'}.
+// In this case, for input "[]", LA(1) is ']' and in the set, so we would
+// not consume anything. After printing an error, rule c would
+// return normally. Rule b would not find the required '^' though.
+// At this point, it gets a mismatched token error and panics an
+// exception (since LA(1) is not in the viable following token
+// set). The rule exception handler tries to recover, but finds
+// the same recovery set and doesn't consume anything. Rule b
+// exits normally returning to rule a. Now it finds the ']' (and
+// with the successful Match exits errorRecovery mode).
+//
+// So, you can see that the parser walks up the call chain looking
+// for the token that was a member of the recovery set.
+//
+// Errors are not generated in errorRecovery mode.
+//
+// ANTLR's error recovery mechanism is based upon original ideas:
+//
+// "Algorithms + Data Structures = Programs" by Niklaus Wirth
+//
+// and
+//
+// "A note on error recovery in recursive descent parsers":
+// http://portal.acm.org/citation.cfm?id=947902.947905
+//
+// Later, Josef Grosch had some good ideas:
+//
+// "Efficient and Comfortable Error Recovery in Recursive Descent
+// Parsers":
+// ftp://www.cocolab.com/products/cocktail/doca4.ps/ell.ps.zip
+//
+// Like Grosch I implement context-sensitive FOLLOW sets that are combined
+// at run-time upon error to avoid overhead during parsing.
+//
+func (d *DefaultErrorStrategy) getErrorRecoverySet(recognizer Parser) *IntervalSet {
+ atn := recognizer.GetInterpreter().atn
+ ctx := recognizer.GetParserRuleContext()
+ recoverSet := NewIntervalSet()
+ for ctx != nil && ctx.GetInvokingState() >= 0 {
+ // compute what follows who invoked us
+ invokingState := atn.states[ctx.GetInvokingState()]
+ rt := invokingState.GetTransitions()[0]
+ follow := atn.NextTokens(rt.(*RuleTransition).followState, nil)
+ recoverSet.addSet(follow)
+ ctx = ctx.GetParent().(ParserRuleContext)
+ }
+ recoverSet.removeOne(TokenEpsilon)
+ return recoverSet
+}
+
+// Consume tokens until one Matches the given token set.//
+func (d *DefaultErrorStrategy) consumeUntil(recognizer Parser, set *IntervalSet) {
+ ttype := recognizer.GetTokenStream().LA(1)
+ for ttype != TokenEOF && !set.contains(ttype) {
+ recognizer.Consume()
+ ttype = recognizer.GetTokenStream().LA(1)
+ }
+}
+
+//
+// This implementation of {@link ANTLRErrorStrategy} responds to syntax errors
+// by immediately canceling the parse operation with a
+// {@link ParseCancellationException}. The implementation ensures that the
+// {@link ParserRuleContext//exception} field is set for all parse tree nodes
+// that were not completed prior to encountering the error.
+//
+//
+// This error strategy is useful in the following scenarios.
+//
+//
+//
Two-stage parsing: This error strategy allows the first
+// stage of two-stage parsing to immediately terminate if an error is
+// encountered, and immediately fall back to the second stage. In addition to
+// avoiding wasted work by attempting to recover from errors here, the empty
+// implementation of {@link BailErrorStrategy//Sync} improves the performance of
+// the first stage.
+//
Silent validation: When syntax errors are not being
+// Reported or logged, and the parse result is simply ignored if errors occur,
+// the {@link BailErrorStrategy} avoids wasting work on recovering from errors
+// when the result will be ignored either way.
+//
+// @see Parser//setErrorHandler(ANTLRErrorStrategy)
+
+type BailErrorStrategy struct {
+ *DefaultErrorStrategy
+}
+
+var _ ErrorStrategy = &BailErrorStrategy{}
+
+func NewBailErrorStrategy() *BailErrorStrategy {
+
+ b := new(BailErrorStrategy)
+
+ b.DefaultErrorStrategy = NewDefaultErrorStrategy()
+
+ return b
+}
+
+// Instead of recovering from exception {@code e}, re-panic it wrapped
+// in a {@link ParseCancellationException} so it is not caught by the
+// rule func catches. Use {@link Exception//getCause()} to get the
+// original {@link RecognitionException}.
+//
+func (b *BailErrorStrategy) Recover(recognizer Parser, e RecognitionException) {
+ context := recognizer.GetParserRuleContext()
+ for context != nil {
+ context.SetException(e)
+ context = context.GetParent().(ParserRuleContext)
+ }
+ panic(NewParseCancellationException()) // TODO we don't emit e properly
+}
+
+// Make sure we don't attempt to recover inline if the parser
+// successfully recovers, it won't panic an exception.
+//
+func (b *BailErrorStrategy) RecoverInline(recognizer Parser) Token {
+ b.Recover(recognizer, NewInputMisMatchException(recognizer))
+
+ return nil
+}
+
+// Make sure we don't attempt to recover from problems in subrules.//
+func (b *BailErrorStrategy) Sync(recognizer Parser) {
+ // pass
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/errors.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/errors.go
new file mode 100644
index 0000000000..2ef74926ec
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/errors.go
@@ -0,0 +1,241 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+// The root of the ANTLR exception hierarchy. In general, ANTLR tracks just
+// 3 kinds of errors: prediction errors, failed predicate errors, and
+// mismatched input errors. In each case, the parser knows where it is
+// in the input, where it is in the ATN, the rule invocation stack,
+// and what kind of problem occurred.
+
+type RecognitionException interface {
+ GetOffendingToken() Token
+ GetMessage() string
+ GetInputStream() IntStream
+}
+
+type BaseRecognitionException struct {
+ message string
+ recognizer Recognizer
+ offendingToken Token
+ offendingState int
+ ctx RuleContext
+ input IntStream
+}
+
+func NewBaseRecognitionException(message string, recognizer Recognizer, input IntStream, ctx RuleContext) *BaseRecognitionException {
+
+ // todo
+ // Error.call(this)
+ //
+ // if (!!Error.captureStackTrace) {
+ // Error.captureStackTrace(this, RecognitionException)
+ // } else {
+ // stack := NewError().stack
+ // }
+ // TODO may be able to use - "runtime" func Stack(buf []byte, all bool) int
+
+ t := new(BaseRecognitionException)
+
+ t.message = message
+ t.recognizer = recognizer
+ t.input = input
+ t.ctx = ctx
+ // The current {@link Token} when an error occurred. Since not all streams
+ // support accessing symbols by index, we have to track the {@link Token}
+ // instance itself.
+ t.offendingToken = nil
+ // Get the ATN state number the parser was in at the time the error
+ // occurred. For {@link NoViableAltException} and
+ // {@link LexerNoViableAltException} exceptions, this is the
+ // {@link DecisionState} number. For others, it is the state whose outgoing
+ // edge we couldn't Match.
+ t.offendingState = -1
+ if t.recognizer != nil {
+ t.offendingState = t.recognizer.GetState()
+ }
+
+ return t
+}
+
+func (b *BaseRecognitionException) GetMessage() string {
+ return b.message
+}
+
+func (b *BaseRecognitionException) GetOffendingToken() Token {
+ return b.offendingToken
+}
+
+func (b *BaseRecognitionException) GetInputStream() IntStream {
+ return b.input
+}
+
+//
If the state number is not known, b method returns -1.
+
+//
+// Gets the set of input symbols which could potentially follow the
+// previously Matched symbol at the time b exception was panicn.
+//
+//
If the set of expected tokens is not known and could not be computed,
+// b method returns {@code nil}.
+//
+// @return The set of token types that could potentially follow the current
+// state in the ATN, or {@code nil} if the information is not available.
+// /
+func (b *BaseRecognitionException) getExpectedTokens() *IntervalSet {
+ if b.recognizer != nil {
+ return b.recognizer.GetATN().getExpectedTokens(b.offendingState, b.ctx)
+ }
+
+ return nil
+}
+
+func (b *BaseRecognitionException) String() string {
+ return b.message
+}
+
+type LexerNoViableAltException struct {
+ *BaseRecognitionException
+
+ startIndex int
+ deadEndConfigs ATNConfigSet
+}
+
+func NewLexerNoViableAltException(lexer Lexer, input CharStream, startIndex int, deadEndConfigs ATNConfigSet) *LexerNoViableAltException {
+
+ l := new(LexerNoViableAltException)
+
+ l.BaseRecognitionException = NewBaseRecognitionException("", lexer, input, nil)
+
+ l.startIndex = startIndex
+ l.deadEndConfigs = deadEndConfigs
+
+ return l
+}
+
+func (l *LexerNoViableAltException) String() string {
+ symbol := ""
+ if l.startIndex >= 0 && l.startIndex < l.input.Size() {
+ symbol = l.input.(CharStream).GetTextFromInterval(NewInterval(l.startIndex, l.startIndex))
+ }
+ return "LexerNoViableAltException" + symbol
+}
+
+type NoViableAltException struct {
+ *BaseRecognitionException
+
+ startToken Token
+ offendingToken Token
+ ctx ParserRuleContext
+ deadEndConfigs ATNConfigSet
+}
+
+// Indicates that the parser could not decide which of two or more paths
+// to take based upon the remaining input. It tracks the starting token
+// of the offending input and also knows where the parser was
+// in the various paths when the error. Reported by ReportNoViableAlternative()
+//
+func NewNoViableAltException(recognizer Parser, input TokenStream, startToken Token, offendingToken Token, deadEndConfigs ATNConfigSet, ctx ParserRuleContext) *NoViableAltException {
+
+ if ctx == nil {
+ ctx = recognizer.GetParserRuleContext()
+ }
+
+ if offendingToken == nil {
+ offendingToken = recognizer.GetCurrentToken()
+ }
+
+ if startToken == nil {
+ startToken = recognizer.GetCurrentToken()
+ }
+
+ if input == nil {
+ input = recognizer.GetInputStream().(TokenStream)
+ }
+
+ n := new(NoViableAltException)
+ n.BaseRecognitionException = NewBaseRecognitionException("", recognizer, input, ctx)
+
+ // Which configurations did we try at input.Index() that couldn't Match
+ // input.LT(1)?//
+ n.deadEndConfigs = deadEndConfigs
+ // The token object at the start index the input stream might
+ // not be buffering tokens so get a reference to it. (At the
+ // time the error occurred, of course the stream needs to keep a
+ // buffer all of the tokens but later we might not have access to those.)
+ n.startToken = startToken
+ n.offendingToken = offendingToken
+
+ return n
+}
+
+type InputMisMatchException struct {
+ *BaseRecognitionException
+}
+
+// This signifies any kind of mismatched input exceptions such as
+// when the current input does not Match the expected token.
+//
+func NewInputMisMatchException(recognizer Parser) *InputMisMatchException {
+
+ i := new(InputMisMatchException)
+ i.BaseRecognitionException = NewBaseRecognitionException("", recognizer, recognizer.GetInputStream(), recognizer.GetParserRuleContext())
+
+ i.offendingToken = recognizer.GetCurrentToken()
+
+ return i
+
+}
+
+// A semantic predicate failed during validation. Validation of predicates
+// occurs when normally parsing the alternative just like Matching a token.
+// Disambiguating predicate evaluation occurs when we test a predicate during
+// prediction.
+
+type FailedPredicateException struct {
+ *BaseRecognitionException
+
+ ruleIndex int
+ predicateIndex int
+ predicate string
+}
+
+func NewFailedPredicateException(recognizer Parser, predicate string, message string) *FailedPredicateException {
+
+ f := new(FailedPredicateException)
+
+ f.BaseRecognitionException = NewBaseRecognitionException(f.formatMessage(predicate, message), recognizer, recognizer.GetInputStream(), recognizer.GetParserRuleContext())
+
+ s := recognizer.GetInterpreter().atn.states[recognizer.GetState()]
+ trans := s.GetTransitions()[0]
+ if trans2, ok := trans.(*PredicateTransition); ok {
+ f.ruleIndex = trans2.ruleIndex
+ f.predicateIndex = trans2.predIndex
+ } else {
+ f.ruleIndex = 0
+ f.predicateIndex = 0
+ }
+ f.predicate = predicate
+ f.offendingToken = recognizer.GetCurrentToken()
+
+ return f
+}
+
+func (f *FailedPredicateException) formatMessage(predicate, message string) string {
+ if message != "" {
+ return message
+ }
+
+ return "failed predicate: {" + predicate + "}?"
+}
+
+type ParseCancellationException struct {
+}
+
+func NewParseCancellationException() *ParseCancellationException {
+ // Error.call(this)
+ // Error.captureStackTrace(this, ParseCancellationException)
+ return new(ParseCancellationException)
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/file_stream.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/file_stream.go
new file mode 100644
index 0000000000..842170c086
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/file_stream.go
@@ -0,0 +1,49 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "bytes"
+ "io"
+ "os"
+)
+
+// This is an InputStream that is loaded from a file all at once
+// when you construct the object.
+
+type FileStream struct {
+ *InputStream
+
+ filename string
+}
+
+func NewFileStream(fileName string) (*FileStream, error) {
+
+ buf := bytes.NewBuffer(nil)
+
+ f, err := os.Open(fileName)
+ if err != nil {
+ return nil, err
+ }
+ defer f.Close()
+ _, err = io.Copy(buf, f)
+ if err != nil {
+ return nil, err
+ }
+
+ fs := new(FileStream)
+
+ fs.filename = fileName
+ s := string(buf.Bytes())
+
+ fs.InputStream = NewInputStream(s)
+
+ return fs, nil
+
+}
+
+func (f *FileStream) GetSourceName() string {
+ return f.filename
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/go.mod b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/go.mod
new file mode 100644
index 0000000000..004cf34655
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/go.mod
@@ -0,0 +1,3 @@
+module github.com/antlr/antlr4/runtime/Go/antlr
+
+go 1.16
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/input_stream.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/input_stream.go
new file mode 100644
index 0000000000..5ff270f536
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/input_stream.go
@@ -0,0 +1,113 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+type InputStream struct {
+ name string
+ index int
+ data []rune
+ size int
+}
+
+func NewInputStream(data string) *InputStream {
+
+ is := new(InputStream)
+
+ is.name = ""
+ is.index = 0
+ is.data = []rune(data)
+ is.size = len(is.data) // number of runes
+
+ return is
+}
+
+func (is *InputStream) reset() {
+ is.index = 0
+}
+
+func (is *InputStream) Consume() {
+ if is.index >= is.size {
+ // assert is.LA(1) == TokenEOF
+ panic("cannot consume EOF")
+ }
+ is.index++
+}
+
+func (is *InputStream) LA(offset int) int {
+
+ if offset == 0 {
+ return 0 // nil
+ }
+ if offset < 0 {
+ offset++ // e.g., translate LA(-1) to use offset=0
+ }
+ pos := is.index + offset - 1
+
+ if pos < 0 || pos >= is.size { // invalid
+ return TokenEOF
+ }
+
+ return int(is.data[pos])
+}
+
+func (is *InputStream) LT(offset int) int {
+ return is.LA(offset)
+}
+
+func (is *InputStream) Index() int {
+ return is.index
+}
+
+func (is *InputStream) Size() int {
+ return is.size
+}
+
+// mark/release do nothing we have entire buffer
+func (is *InputStream) Mark() int {
+ return -1
+}
+
+func (is *InputStream) Release(marker int) {
+}
+
+func (is *InputStream) Seek(index int) {
+ if index <= is.index {
+ is.index = index // just jump don't update stream state (line,...)
+ return
+ }
+ // seek forward
+ is.index = intMin(index, is.size)
+}
+
+func (is *InputStream) GetText(start int, stop int) string {
+ if stop >= is.size {
+ stop = is.size - 1
+ }
+ if start >= is.size {
+ return ""
+ }
+
+ return string(is.data[start : stop+1])
+}
+
+func (is *InputStream) GetTextFromTokens(start, stop Token) string {
+ if start != nil && stop != nil {
+ return is.GetTextFromInterval(NewInterval(start.GetTokenIndex(), stop.GetTokenIndex()))
+ }
+
+ return ""
+}
+
+func (is *InputStream) GetTextFromInterval(i *Interval) string {
+ return is.GetText(i.Start, i.Stop)
+}
+
+func (*InputStream) GetSourceName() string {
+ return "Obtained from string"
+}
+
+func (is *InputStream) String() string {
+ return string(is.data)
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/int_stream.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/int_stream.go
new file mode 100644
index 0000000000..438e0ea6e7
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/int_stream.go
@@ -0,0 +1,16 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+type IntStream interface {
+ Consume()
+ LA(int) int
+ Mark() int
+ Release(marker int)
+ Index() int
+ Seek(index int)
+ Size() int
+ GetSourceName() string
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/interval_set.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/interval_set.go
new file mode 100644
index 0000000000..510d909114
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/interval_set.go
@@ -0,0 +1,296 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "strconv"
+ "strings"
+)
+
+type Interval struct {
+ Start int
+ Stop int
+}
+
+/* stop is not included! */
+func NewInterval(start, stop int) *Interval {
+ i := new(Interval)
+
+ i.Start = start
+ i.Stop = stop
+ return i
+}
+
+func (i *Interval) Contains(item int) bool {
+ return item >= i.Start && item < i.Stop
+}
+
+func (i *Interval) String() string {
+ if i.Start == i.Stop-1 {
+ return strconv.Itoa(i.Start)
+ }
+
+ return strconv.Itoa(i.Start) + ".." + strconv.Itoa(i.Stop-1)
+}
+
+func (i *Interval) length() int {
+ return i.Stop - i.Start
+}
+
+type IntervalSet struct {
+ intervals []*Interval
+ readOnly bool
+}
+
+func NewIntervalSet() *IntervalSet {
+
+ i := new(IntervalSet)
+
+ i.intervals = nil
+ i.readOnly = false
+
+ return i
+}
+
+func (i *IntervalSet) first() int {
+ if len(i.intervals) == 0 {
+ return TokenInvalidType
+ }
+
+ return i.intervals[0].Start
+}
+
+func (i *IntervalSet) addOne(v int) {
+ i.addInterval(NewInterval(v, v+1))
+}
+
+func (i *IntervalSet) addRange(l, h int) {
+ i.addInterval(NewInterval(l, h+1))
+}
+
+func (i *IntervalSet) addInterval(v *Interval) {
+ if i.intervals == nil {
+ i.intervals = make([]*Interval, 0)
+ i.intervals = append(i.intervals, v)
+ } else {
+ // find insert pos
+ for k, interval := range i.intervals {
+ // distinct range -> insert
+ if v.Stop < interval.Start {
+ i.intervals = append(i.intervals[0:k], append([]*Interval{v}, i.intervals[k:]...)...)
+ return
+ } else if v.Stop == interval.Start {
+ i.intervals[k].Start = v.Start
+ return
+ } else if v.Start <= interval.Stop {
+ i.intervals[k] = NewInterval(intMin(interval.Start, v.Start), intMax(interval.Stop, v.Stop))
+
+ // if not applying to end, merge potential overlaps
+ if k < len(i.intervals)-1 {
+ l := i.intervals[k]
+ r := i.intervals[k+1]
+ // if r contained in l
+ if l.Stop >= r.Stop {
+ i.intervals = append(i.intervals[0:k+1], i.intervals[k+2:]...)
+ } else if l.Stop >= r.Start { // partial overlap
+ i.intervals[k] = NewInterval(l.Start, r.Stop)
+ i.intervals = append(i.intervals[0:k+1], i.intervals[k+2:]...)
+ }
+ }
+ return
+ }
+ }
+ // greater than any exiting
+ i.intervals = append(i.intervals, v)
+ }
+}
+
+func (i *IntervalSet) addSet(other *IntervalSet) *IntervalSet {
+ if other.intervals != nil {
+ for k := 0; k < len(other.intervals); k++ {
+ i2 := other.intervals[k]
+ i.addInterval(NewInterval(i2.Start, i2.Stop))
+ }
+ }
+ return i
+}
+
+func (i *IntervalSet) complement(start int, stop int) *IntervalSet {
+ result := NewIntervalSet()
+ result.addInterval(NewInterval(start, stop+1))
+ for j := 0; j < len(i.intervals); j++ {
+ result.removeRange(i.intervals[j])
+ }
+ return result
+}
+
+func (i *IntervalSet) contains(item int) bool {
+ if i.intervals == nil {
+ return false
+ }
+ for k := 0; k < len(i.intervals); k++ {
+ if i.intervals[k].Contains(item) {
+ return true
+ }
+ }
+ return false
+}
+
+func (i *IntervalSet) length() int {
+ len := 0
+
+ for _, v := range i.intervals {
+ len += v.length()
+ }
+
+ return len
+}
+
+func (i *IntervalSet) removeRange(v *Interval) {
+ if v.Start == v.Stop-1 {
+ i.removeOne(v.Start)
+ } else if i.intervals != nil {
+ k := 0
+ for n := 0; n < len(i.intervals); n++ {
+ ni := i.intervals[k]
+ // intervals are ordered
+ if v.Stop <= ni.Start {
+ return
+ } else if v.Start > ni.Start && v.Stop < ni.Stop {
+ i.intervals[k] = NewInterval(ni.Start, v.Start)
+ x := NewInterval(v.Stop, ni.Stop)
+ // i.intervals.splice(k, 0, x)
+ i.intervals = append(i.intervals[0:k], append([]*Interval{x}, i.intervals[k:]...)...)
+ return
+ } else if v.Start <= ni.Start && v.Stop >= ni.Stop {
+ // i.intervals.splice(k, 1)
+ i.intervals = append(i.intervals[0:k], i.intervals[k+1:]...)
+ k = k - 1 // need another pass
+ } else if v.Start < ni.Stop {
+ i.intervals[k] = NewInterval(ni.Start, v.Start)
+ } else if v.Stop < ni.Stop {
+ i.intervals[k] = NewInterval(v.Stop, ni.Stop)
+ }
+ k++
+ }
+ }
+}
+
+func (i *IntervalSet) removeOne(v int) {
+ if i.intervals != nil {
+ for k := 0; k < len(i.intervals); k++ {
+ ki := i.intervals[k]
+ // intervals i ordered
+ if v < ki.Start {
+ return
+ } else if v == ki.Start && v == ki.Stop-1 {
+ // i.intervals.splice(k, 1)
+ i.intervals = append(i.intervals[0:k], i.intervals[k+1:]...)
+ return
+ } else if v == ki.Start {
+ i.intervals[k] = NewInterval(ki.Start+1, ki.Stop)
+ return
+ } else if v == ki.Stop-1 {
+ i.intervals[k] = NewInterval(ki.Start, ki.Stop-1)
+ return
+ } else if v < ki.Stop-1 {
+ x := NewInterval(ki.Start, v)
+ ki.Start = v + 1
+ // i.intervals.splice(k, 0, x)
+ i.intervals = append(i.intervals[0:k], append([]*Interval{x}, i.intervals[k:]...)...)
+ return
+ }
+ }
+ }
+}
+
+func (i *IntervalSet) String() string {
+ return i.StringVerbose(nil, nil, false)
+}
+
+func (i *IntervalSet) StringVerbose(literalNames []string, symbolicNames []string, elemsAreChar bool) string {
+
+ if i.intervals == nil {
+ return "{}"
+ } else if literalNames != nil || symbolicNames != nil {
+ return i.toTokenString(literalNames, symbolicNames)
+ } else if elemsAreChar {
+ return i.toCharString()
+ }
+
+ return i.toIndexString()
+}
+
+func (i *IntervalSet) toCharString() string {
+ names := make([]string, len(i.intervals))
+
+ for j := 0; j < len(i.intervals); j++ {
+ v := i.intervals[j]
+ if v.Stop == v.Start+1 {
+ if v.Start == TokenEOF {
+ names = append(names, "")
+ } else {
+ names = append(names, ("'" + string(v.Start) + "'"))
+ }
+ } else {
+ names = append(names, "'"+string(v.Start)+"'..'"+string(v.Stop-1)+"'")
+ }
+ }
+ if len(names) > 1 {
+ return "{" + strings.Join(names, ", ") + "}"
+ }
+
+ return names[0]
+}
+
+func (i *IntervalSet) toIndexString() string {
+
+ names := make([]string, 0)
+ for j := 0; j < len(i.intervals); j++ {
+ v := i.intervals[j]
+ if v.Stop == v.Start+1 {
+ if v.Start == TokenEOF {
+ names = append(names, "")
+ } else {
+ names = append(names, strconv.Itoa(v.Start))
+ }
+ } else {
+ names = append(names, strconv.Itoa(v.Start)+".."+strconv.Itoa(v.Stop-1))
+ }
+ }
+ if len(names) > 1 {
+ return "{" + strings.Join(names, ", ") + "}"
+ }
+
+ return names[0]
+}
+
+func (i *IntervalSet) toTokenString(literalNames []string, symbolicNames []string) string {
+ names := make([]string, 0)
+ for _, v := range i.intervals {
+ for j := v.Start; j < v.Stop; j++ {
+ names = append(names, i.elementName(literalNames, symbolicNames, j))
+ }
+ }
+ if len(names) > 1 {
+ return "{" + strings.Join(names, ", ") + "}"
+ }
+
+ return names[0]
+}
+
+func (i *IntervalSet) elementName(literalNames []string, symbolicNames []string, a int) string {
+ if a == TokenEOF {
+ return ""
+ } else if a == TokenEpsilon {
+ return ""
+ } else {
+ if a < len(literalNames) && literalNames[a] != "" {
+ return literalNames[a]
+ }
+
+ return symbolicNames[a]
+ }
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer.go
new file mode 100644
index 0000000000..b04f04572f
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer.go
@@ -0,0 +1,418 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "strconv"
+)
+
+// A lexer is recognizer that draws input symbols from a character stream.
+// lexer grammars result in a subclass of this object. A Lexer object
+// uses simplified Match() and error recovery mechanisms in the interest
+// of speed.
+///
+
+type Lexer interface {
+ TokenSource
+ Recognizer
+
+ Emit() Token
+
+ SetChannel(int)
+ PushMode(int)
+ PopMode() int
+ SetType(int)
+ SetMode(int)
+}
+
+type BaseLexer struct {
+ *BaseRecognizer
+
+ Interpreter ILexerATNSimulator
+ TokenStartCharIndex int
+ TokenStartLine int
+ TokenStartColumn int
+ ActionType int
+ Virt Lexer // The most derived lexer implementation. Allows virtual method calls.
+
+ input CharStream
+ factory TokenFactory
+ tokenFactorySourcePair *TokenSourceCharStreamPair
+ token Token
+ hitEOF bool
+ channel int
+ thetype int
+ modeStack IntStack
+ mode int
+ text string
+}
+
+func NewBaseLexer(input CharStream) *BaseLexer {
+
+ lexer := new(BaseLexer)
+
+ lexer.BaseRecognizer = NewBaseRecognizer()
+
+ lexer.input = input
+ lexer.factory = CommonTokenFactoryDEFAULT
+ lexer.tokenFactorySourcePair = &TokenSourceCharStreamPair{lexer, input}
+
+ lexer.Virt = lexer
+
+ lexer.Interpreter = nil // child classes must populate it
+
+ // The goal of all lexer rules/methods is to create a token object.
+ // l is an instance variable as multiple rules may collaborate to
+ // create a single token. NextToken will return l object after
+ // Matching lexer rule(s). If you subclass to allow multiple token
+ // emissions, then set l to the last token to be Matched or
+ // something nonnil so that the auto token emit mechanism will not
+ // emit another token.
+ lexer.token = nil
+
+ // What character index in the stream did the current token start at?
+ // Needed, for example, to get the text for current token. Set at
+ // the start of NextToken.
+ lexer.TokenStartCharIndex = -1
+
+ // The line on which the first character of the token resides///
+ lexer.TokenStartLine = -1
+
+ // The character position of first character within the line///
+ lexer.TokenStartColumn = -1
+
+ // Once we see EOF on char stream, next token will be EOF.
+ // If you have DONE : EOF then you see DONE EOF.
+ lexer.hitEOF = false
+
+ // The channel number for the current token///
+ lexer.channel = TokenDefaultChannel
+
+ // The token type for the current token///
+ lexer.thetype = TokenInvalidType
+
+ lexer.modeStack = make([]int, 0)
+ lexer.mode = LexerDefaultMode
+
+ // You can set the text for the current token to override what is in
+ // the input char buffer. Use setText() or can set l instance var.
+ // /
+ lexer.text = ""
+
+ return lexer
+}
+
+const (
+ LexerDefaultMode = 0
+ LexerMore = -2
+ LexerSkip = -3
+)
+
+const (
+ LexerDefaultTokenChannel = TokenDefaultChannel
+ LexerHidden = TokenHiddenChannel
+ LexerMinCharValue = 0x0000
+ LexerMaxCharValue = 0x10FFFF
+)
+
+func (b *BaseLexer) reset() {
+ // wack Lexer state variables
+ if b.input != nil {
+ b.input.Seek(0) // rewind the input
+ }
+ b.token = nil
+ b.thetype = TokenInvalidType
+ b.channel = TokenDefaultChannel
+ b.TokenStartCharIndex = -1
+ b.TokenStartColumn = -1
+ b.TokenStartLine = -1
+ b.text = ""
+
+ b.hitEOF = false
+ b.mode = LexerDefaultMode
+ b.modeStack = make([]int, 0)
+
+ b.Interpreter.reset()
+}
+
+func (b *BaseLexer) GetInterpreter() ILexerATNSimulator {
+ return b.Interpreter
+}
+
+func (b *BaseLexer) GetInputStream() CharStream {
+ return b.input
+}
+
+func (b *BaseLexer) GetSourceName() string {
+ return b.GrammarFileName
+}
+
+func (b *BaseLexer) SetChannel(v int) {
+ b.channel = v
+}
+
+func (b *BaseLexer) GetTokenFactory() TokenFactory {
+ return b.factory
+}
+
+func (b *BaseLexer) setTokenFactory(f TokenFactory) {
+ b.factory = f
+}
+
+func (b *BaseLexer) safeMatch() (ret int) {
+ defer func() {
+ if e := recover(); e != nil {
+ if re, ok := e.(RecognitionException); ok {
+ b.notifyListeners(re) // Report error
+ b.Recover(re)
+ ret = LexerSkip // default
+ }
+ }
+ }()
+
+ return b.Interpreter.Match(b.input, b.mode)
+}
+
+// Return a token from l source i.e., Match a token on the char stream.
+func (b *BaseLexer) NextToken() Token {
+ if b.input == nil {
+ panic("NextToken requires a non-nil input stream.")
+ }
+
+ tokenStartMarker := b.input.Mark()
+
+ // previously in finally block
+ defer func() {
+ // make sure we release marker after Match or
+ // unbuffered char stream will keep buffering
+ b.input.Release(tokenStartMarker)
+ }()
+
+ for {
+ if b.hitEOF {
+ b.EmitEOF()
+ return b.token
+ }
+ b.token = nil
+ b.channel = TokenDefaultChannel
+ b.TokenStartCharIndex = b.input.Index()
+ b.TokenStartColumn = b.Interpreter.GetCharPositionInLine()
+ b.TokenStartLine = b.Interpreter.GetLine()
+ b.text = ""
+ continueOuter := false
+ for {
+ b.thetype = TokenInvalidType
+ ttype := LexerSkip
+
+ ttype = b.safeMatch()
+
+ if b.input.LA(1) == TokenEOF {
+ b.hitEOF = true
+ }
+ if b.thetype == TokenInvalidType {
+ b.thetype = ttype
+ }
+ if b.thetype == LexerSkip {
+ continueOuter = true
+ break
+ }
+ if b.thetype != LexerMore {
+ break
+ }
+ }
+
+ if continueOuter {
+ continue
+ }
+ if b.token == nil {
+ b.Virt.Emit()
+ }
+ return b.token
+ }
+
+ return nil
+}
+
+// Instruct the lexer to Skip creating a token for current lexer rule
+// and look for another token. NextToken() knows to keep looking when
+// a lexer rule finishes with token set to SKIPTOKEN. Recall that
+// if token==nil at end of any token rule, it creates one for you
+// and emits it.
+// /
+func (b *BaseLexer) Skip() {
+ b.thetype = LexerSkip
+}
+
+func (b *BaseLexer) More() {
+ b.thetype = LexerMore
+}
+
+func (b *BaseLexer) SetMode(m int) {
+ b.mode = m
+}
+
+func (b *BaseLexer) PushMode(m int) {
+ if LexerATNSimulatorDebug {
+ fmt.Println("pushMode " + strconv.Itoa(m))
+ }
+ b.modeStack.Push(b.mode)
+ b.mode = m
+}
+
+func (b *BaseLexer) PopMode() int {
+ if len(b.modeStack) == 0 {
+ panic("Empty Stack")
+ }
+ if LexerATNSimulatorDebug {
+ fmt.Println("popMode back to " + fmt.Sprint(b.modeStack[0:len(b.modeStack)-1]))
+ }
+ i, _ := b.modeStack.Pop()
+ b.mode = i
+ return b.mode
+}
+
+func (b *BaseLexer) inputStream() CharStream {
+ return b.input
+}
+
+// SetInputStream resets the lexer input stream and associated lexer state.
+func (b *BaseLexer) SetInputStream(input CharStream) {
+ b.input = nil
+ b.tokenFactorySourcePair = &TokenSourceCharStreamPair{b, b.input}
+ b.reset()
+ b.input = input
+ b.tokenFactorySourcePair = &TokenSourceCharStreamPair{b, b.input}
+}
+
+func (b *BaseLexer) GetTokenSourceCharStreamPair() *TokenSourceCharStreamPair {
+ return b.tokenFactorySourcePair
+}
+
+// By default does not support multiple emits per NextToken invocation
+// for efficiency reasons. Subclass and override l method, NextToken,
+// and GetToken (to push tokens into a list and pull from that list
+// rather than a single variable as l implementation does).
+// /
+func (b *BaseLexer) EmitToken(token Token) {
+ b.token = token
+}
+
+// The standard method called to automatically emit a token at the
+// outermost lexical rule. The token object should point into the
+// char buffer start..stop. If there is a text override in 'text',
+// use that to set the token's text. Override l method to emit
+// custom Token objects or provide a Newfactory.
+// /
+func (b *BaseLexer) Emit() Token {
+ t := b.factory.Create(b.tokenFactorySourcePair, b.thetype, b.text, b.channel, b.TokenStartCharIndex, b.GetCharIndex()-1, b.TokenStartLine, b.TokenStartColumn)
+ b.EmitToken(t)
+ return t
+}
+
+func (b *BaseLexer) EmitEOF() Token {
+ cpos := b.GetCharPositionInLine()
+ lpos := b.GetLine()
+ eof := b.factory.Create(b.tokenFactorySourcePair, TokenEOF, "", TokenDefaultChannel, b.input.Index(), b.input.Index()-1, lpos, cpos)
+ b.EmitToken(eof)
+ return eof
+}
+
+func (b *BaseLexer) GetCharPositionInLine() int {
+ return b.Interpreter.GetCharPositionInLine()
+}
+
+func (b *BaseLexer) GetLine() int {
+ return b.Interpreter.GetLine()
+}
+
+func (b *BaseLexer) GetType() int {
+ return b.thetype
+}
+
+func (b *BaseLexer) SetType(t int) {
+ b.thetype = t
+}
+
+// What is the index of the current character of lookahead?///
+func (b *BaseLexer) GetCharIndex() int {
+ return b.input.Index()
+}
+
+// Return the text Matched so far for the current token or any text override.
+//Set the complete text of l token it wipes any previous changes to the text.
+func (b *BaseLexer) GetText() string {
+ if b.text != "" {
+ return b.text
+ }
+
+ return b.Interpreter.GetText(b.input)
+}
+
+func (b *BaseLexer) SetText(text string) {
+ b.text = text
+}
+
+func (b *BaseLexer) GetATN() *ATN {
+ return b.Interpreter.ATN()
+}
+
+// Return a list of all Token objects in input char stream.
+// Forces load of all tokens. Does not include EOF token.
+// /
+func (b *BaseLexer) GetAllTokens() []Token {
+ vl := b.Virt
+ tokens := make([]Token, 0)
+ t := vl.NextToken()
+ for t.GetTokenType() != TokenEOF {
+ tokens = append(tokens, t)
+ t = vl.NextToken()
+ }
+ return tokens
+}
+
+func (b *BaseLexer) notifyListeners(e RecognitionException) {
+ start := b.TokenStartCharIndex
+ stop := b.input.Index()
+ text := b.input.GetTextFromInterval(NewInterval(start, stop))
+ msg := "token recognition error at: '" + text + "'"
+ listener := b.GetErrorListenerDispatch()
+ listener.SyntaxError(b, nil, b.TokenStartLine, b.TokenStartColumn, msg, e)
+}
+
+func (b *BaseLexer) getErrorDisplayForChar(c rune) string {
+ if c == TokenEOF {
+ return ""
+ } else if c == '\n' {
+ return "\\n"
+ } else if c == '\t' {
+ return "\\t"
+ } else if c == '\r' {
+ return "\\r"
+ } else {
+ return string(c)
+ }
+}
+
+func (b *BaseLexer) getCharErrorDisplay(c rune) string {
+ return "'" + b.getErrorDisplayForChar(c) + "'"
+}
+
+// Lexers can normally Match any char in it's vocabulary after Matching
+// a token, so do the easy thing and just kill a character and hope
+// it all works out. You can instead use the rule invocation stack
+// to do sophisticated error recovery if you are in a fragment rule.
+// /
+func (b *BaseLexer) Recover(re RecognitionException) {
+ if b.input.LA(1) != TokenEOF {
+ if _, ok := re.(*LexerNoViableAltException); ok {
+ // Skip a char and try again
+ b.Interpreter.Consume(b.input)
+ } else {
+ // TODO: Do we lose character or line position information?
+ b.input.Consume()
+ }
+ }
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_action.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_action.go
new file mode 100644
index 0000000000..20df84f943
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_action.go
@@ -0,0 +1,431 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import "strconv"
+
+const (
+ LexerActionTypeChannel = 0 //The type of a {@link LexerChannelAction} action.
+ LexerActionTypeCustom = 1 //The type of a {@link LexerCustomAction} action.
+ LexerActionTypeMode = 2 //The type of a {@link LexerModeAction} action.
+ LexerActionTypeMore = 3 //The type of a {@link LexerMoreAction} action.
+ LexerActionTypePopMode = 4 //The type of a {@link LexerPopModeAction} action.
+ LexerActionTypePushMode = 5 //The type of a {@link LexerPushModeAction} action.
+ LexerActionTypeSkip = 6 //The type of a {@link LexerSkipAction} action.
+ LexerActionTypeType = 7 //The type of a {@link LexerTypeAction} action.
+)
+
+type LexerAction interface {
+ getActionType() int
+ getIsPositionDependent() bool
+ execute(lexer Lexer)
+ hash() int
+ equals(other LexerAction) bool
+}
+
+type BaseLexerAction struct {
+ actionType int
+ isPositionDependent bool
+}
+
+func NewBaseLexerAction(action int) *BaseLexerAction {
+ la := new(BaseLexerAction)
+
+ la.actionType = action
+ la.isPositionDependent = false
+
+ return la
+}
+
+func (b *BaseLexerAction) execute(lexer Lexer) {
+ panic("Not implemented")
+}
+
+func (b *BaseLexerAction) getActionType() int {
+ return b.actionType
+}
+
+func (b *BaseLexerAction) getIsPositionDependent() bool {
+ return b.isPositionDependent
+}
+
+func (b *BaseLexerAction) hash() int {
+ return b.actionType
+}
+
+func (b *BaseLexerAction) equals(other LexerAction) bool {
+ return b == other
+}
+
+//
+// Implements the {@code Skip} lexer action by calling {@link Lexer//Skip}.
+//
+//
The {@code Skip} command does not have any parameters, so l action is
+// implemented as a singleton instance exposed by {@link //INSTANCE}.
+type LexerSkipAction struct {
+ *BaseLexerAction
+}
+
+func NewLexerSkipAction() *LexerSkipAction {
+ la := new(LexerSkipAction)
+ la.BaseLexerAction = NewBaseLexerAction(LexerActionTypeSkip)
+ return la
+}
+
+// Provides a singleton instance of l parameterless lexer action.
+var LexerSkipActionINSTANCE = NewLexerSkipAction()
+
+func (l *LexerSkipAction) execute(lexer Lexer) {
+ lexer.Skip()
+}
+
+func (l *LexerSkipAction) String() string {
+ return "skip"
+}
+
+// Implements the {@code type} lexer action by calling {@link Lexer//setType}
+// with the assigned type.
+type LexerTypeAction struct {
+ *BaseLexerAction
+
+ thetype int
+}
+
+func NewLexerTypeAction(thetype int) *LexerTypeAction {
+ l := new(LexerTypeAction)
+ l.BaseLexerAction = NewBaseLexerAction(LexerActionTypeType)
+ l.thetype = thetype
+ return l
+}
+
+func (l *LexerTypeAction) execute(lexer Lexer) {
+ lexer.SetType(l.thetype)
+}
+
+func (l *LexerTypeAction) hash() int {
+ h := murmurInit(0)
+ h = murmurUpdate(h, l.actionType)
+ h = murmurUpdate(h, l.thetype)
+ return murmurFinish(h, 2)
+}
+
+func (l *LexerTypeAction) equals(other LexerAction) bool {
+ if l == other {
+ return true
+ } else if _, ok := other.(*LexerTypeAction); !ok {
+ return false
+ } else {
+ return l.thetype == other.(*LexerTypeAction).thetype
+ }
+}
+
+func (l *LexerTypeAction) String() string {
+ return "actionType(" + strconv.Itoa(l.thetype) + ")"
+}
+
+// Implements the {@code pushMode} lexer action by calling
+// {@link Lexer//pushMode} with the assigned mode.
+type LexerPushModeAction struct {
+ *BaseLexerAction
+
+ mode int
+}
+
+func NewLexerPushModeAction(mode int) *LexerPushModeAction {
+
+ l := new(LexerPushModeAction)
+ l.BaseLexerAction = NewBaseLexerAction(LexerActionTypePushMode)
+
+ l.mode = mode
+ return l
+}
+
+//
This action is implemented by calling {@link Lexer//pushMode} with the
+// value provided by {@link //getMode}.
+func (l *LexerPushModeAction) execute(lexer Lexer) {
+ lexer.PushMode(l.mode)
+}
+
+func (l *LexerPushModeAction) hash() int {
+ h := murmurInit(0)
+ h = murmurUpdate(h, l.actionType)
+ h = murmurUpdate(h, l.mode)
+ return murmurFinish(h, 2)
+}
+
+func (l *LexerPushModeAction) equals(other LexerAction) bool {
+ if l == other {
+ return true
+ } else if _, ok := other.(*LexerPushModeAction); !ok {
+ return false
+ } else {
+ return l.mode == other.(*LexerPushModeAction).mode
+ }
+}
+
+func (l *LexerPushModeAction) String() string {
+ return "pushMode(" + strconv.Itoa(l.mode) + ")"
+}
+
+// Implements the {@code popMode} lexer action by calling {@link Lexer//popMode}.
+//
+//
The {@code popMode} command does not have any parameters, so l action is
+// implemented as a singleton instance exposed by {@link //INSTANCE}.
This action is implemented by calling {@link Lexer//mode} with the
+// value provided by {@link //getMode}.
+func (l *LexerModeAction) execute(lexer Lexer) {
+ lexer.SetMode(l.mode)
+}
+
+func (l *LexerModeAction) hash() int {
+ h := murmurInit(0)
+ h = murmurUpdate(h, l.actionType)
+ h = murmurUpdate(h, l.mode)
+ return murmurFinish(h, 2)
+}
+
+func (l *LexerModeAction) equals(other LexerAction) bool {
+ if l == other {
+ return true
+ } else if _, ok := other.(*LexerModeAction); !ok {
+ return false
+ } else {
+ return l.mode == other.(*LexerModeAction).mode
+ }
+}
+
+func (l *LexerModeAction) String() string {
+ return "mode(" + strconv.Itoa(l.mode) + ")"
+}
+
+// Executes a custom lexer action by calling {@link Recognizer//action} with the
+// rule and action indexes assigned to the custom action. The implementation of
+// a custom action is added to the generated code for the lexer in an override
+// of {@link Recognizer//action} when the grammar is compiled.
+//
+//
This class may represent embedded actions created with the {...}
+// syntax in ANTLR 4, as well as actions created for lexer commands where the
+// command argument could not be evaluated when the grammar was compiled.
+
+// Constructs a custom lexer action with the specified rule and action
+// indexes.
+//
+// @param ruleIndex The rule index to use for calls to
+// {@link Recognizer//action}.
+// @param actionIndex The action index to use for calls to
+// {@link Recognizer//action}.
+
+type LexerCustomAction struct {
+ *BaseLexerAction
+ ruleIndex, actionIndex int
+}
+
+func NewLexerCustomAction(ruleIndex, actionIndex int) *LexerCustomAction {
+ l := new(LexerCustomAction)
+ l.BaseLexerAction = NewBaseLexerAction(LexerActionTypeCustom)
+ l.ruleIndex = ruleIndex
+ l.actionIndex = actionIndex
+ l.isPositionDependent = true
+ return l
+}
+
+//
Custom actions are implemented by calling {@link Lexer//action} with the
+// appropriate rule and action indexes.
+func (l *LexerCustomAction) execute(lexer Lexer) {
+ lexer.Action(nil, l.ruleIndex, l.actionIndex)
+}
+
+func (l *LexerCustomAction) hash() int {
+ h := murmurInit(0)
+ h = murmurUpdate(h, l.actionType)
+ h = murmurUpdate(h, l.ruleIndex)
+ h = murmurUpdate(h, l.actionIndex)
+ return murmurFinish(h, 3)
+}
+
+func (l *LexerCustomAction) equals(other LexerAction) bool {
+ if l == other {
+ return true
+ } else if _, ok := other.(*LexerCustomAction); !ok {
+ return false
+ } else {
+ return l.ruleIndex == other.(*LexerCustomAction).ruleIndex && l.actionIndex == other.(*LexerCustomAction).actionIndex
+ }
+}
+
+// Implements the {@code channel} lexer action by calling
+// {@link Lexer//setChannel} with the assigned channel.
+// Constructs a New{@code channel} action with the specified channel value.
+// @param channel The channel value to pass to {@link Lexer//setChannel}.
+type LexerChannelAction struct {
+ *BaseLexerAction
+
+ channel int
+}
+
+func NewLexerChannelAction(channel int) *LexerChannelAction {
+ l := new(LexerChannelAction)
+ l.BaseLexerAction = NewBaseLexerAction(LexerActionTypeChannel)
+ l.channel = channel
+ return l
+}
+
+//
This action is implemented by calling {@link Lexer//setChannel} with the
+// value provided by {@link //getChannel}.
+func (l *LexerChannelAction) execute(lexer Lexer) {
+ lexer.SetChannel(l.channel)
+}
+
+func (l *LexerChannelAction) hash() int {
+ h := murmurInit(0)
+ h = murmurUpdate(h, l.actionType)
+ h = murmurUpdate(h, l.channel)
+ return murmurFinish(h, 2)
+}
+
+func (l *LexerChannelAction) equals(other LexerAction) bool {
+ if l == other {
+ return true
+ } else if _, ok := other.(*LexerChannelAction); !ok {
+ return false
+ } else {
+ return l.channel == other.(*LexerChannelAction).channel
+ }
+}
+
+func (l *LexerChannelAction) String() string {
+ return "channel(" + strconv.Itoa(l.channel) + ")"
+}
+
+// This implementation of {@link LexerAction} is used for tracking input offsets
+// for position-dependent actions within a {@link LexerActionExecutor}.
+//
+//
This action is not serialized as part of the ATN, and is only required for
+// position-dependent lexer actions which appear at a location other than the
+// end of a rule. For more information about DFA optimizations employed for
+// lexer actions, see {@link LexerActionExecutor//append} and
+// {@link LexerActionExecutor//fixOffsetBeforeMatch}.
+
+// Constructs a Newindexed custom action by associating a character offset
+// with a {@link LexerAction}.
+//
+//
Note: This class is only required for lexer actions for which
+// {@link LexerAction//isPositionDependent} returns {@code true}.
+//
+// @param offset The offset into the input {@link CharStream}, relative to
+// the token start index, at which the specified lexer action should be
+// executed.
+// @param action The lexer action to execute at a particular offset in the
+// input {@link CharStream}.
+type LexerIndexedCustomAction struct {
+ *BaseLexerAction
+
+ offset int
+ lexerAction LexerAction
+ isPositionDependent bool
+}
+
+func NewLexerIndexedCustomAction(offset int, lexerAction LexerAction) *LexerIndexedCustomAction {
+
+ l := new(LexerIndexedCustomAction)
+ l.BaseLexerAction = NewBaseLexerAction(lexerAction.getActionType())
+
+ l.offset = offset
+ l.lexerAction = lexerAction
+ l.isPositionDependent = true
+
+ return l
+}
+
+//
This method calls {@link //execute} on the result of {@link //getAction}
+// using the provided {@code lexer}.
+func (l *LexerIndexedCustomAction) execute(lexer Lexer) {
+ // assume the input stream position was properly set by the calling code
+ l.lexerAction.execute(lexer)
+}
+
+func (l *LexerIndexedCustomAction) hash() int {
+ h := murmurInit(0)
+ h = murmurUpdate(h, l.actionType)
+ h = murmurUpdate(h, l.offset)
+ h = murmurUpdate(h, l.lexerAction.hash())
+ return murmurFinish(h, 3)
+}
+
+func (l *LexerIndexedCustomAction) equals(other LexerAction) bool {
+ if l == other {
+ return true
+ } else if _, ok := other.(*LexerIndexedCustomAction); !ok {
+ return false
+ } else {
+ return l.offset == other.(*LexerIndexedCustomAction).offset && l.lexerAction == other.(*LexerIndexedCustomAction).lexerAction
+ }
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_action_executor.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_action_executor.go
new file mode 100644
index 0000000000..80b949a1a5
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_action_executor.go
@@ -0,0 +1,170 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+// Represents an executor for a sequence of lexer actions which traversed during
+// the Matching operation of a lexer rule (token).
+//
+//
The executor tracks position information for position-dependent lexer actions
+// efficiently, ensuring that actions appearing only at the end of the rule do
+// not cause bloating of the {@link DFA} created for the lexer.
+
+type LexerActionExecutor struct {
+ lexerActions []LexerAction
+ cachedHash int
+}
+
+func NewLexerActionExecutor(lexerActions []LexerAction) *LexerActionExecutor {
+
+ if lexerActions == nil {
+ lexerActions = make([]LexerAction, 0)
+ }
+
+ l := new(LexerActionExecutor)
+
+ l.lexerActions = lexerActions
+
+ // Caches the result of {@link //hashCode} since the hash code is an element
+ // of the performance-critical {@link LexerATNConfig//hashCode} operation.
+ l.cachedHash = murmurInit(57)
+ for _, a := range lexerActions {
+ l.cachedHash = murmurUpdate(l.cachedHash, a.hash())
+ }
+
+ return l
+}
+
+// Creates a {@link LexerActionExecutor} which executes the actions for
+// the input {@code lexerActionExecutor} followed by a specified
+// {@code lexerAction}.
+//
+// @param lexerActionExecutor The executor for actions already traversed by
+// the lexer while Matching a token within a particular
+// {@link LexerATNConfig}. If this is {@code nil}, the method behaves as
+// though it were an empty executor.
+// @param lexerAction The lexer action to execute after the actions
+// specified in {@code lexerActionExecutor}.
+//
+// @return A {@link LexerActionExecutor} for executing the combine actions
+// of {@code lexerActionExecutor} and {@code lexerAction}.
+func LexerActionExecutorappend(lexerActionExecutor *LexerActionExecutor, lexerAction LexerAction) *LexerActionExecutor {
+ if lexerActionExecutor == nil {
+ return NewLexerActionExecutor([]LexerAction{lexerAction})
+ }
+
+ return NewLexerActionExecutor(append(lexerActionExecutor.lexerActions, lexerAction))
+}
+
+// Creates a {@link LexerActionExecutor} which encodes the current offset
+// for position-dependent lexer actions.
+//
+//
Normally, when the executor encounters lexer actions where
+// {@link LexerAction//isPositionDependent} returns {@code true}, it calls
+// {@link IntStream//seek} on the input {@link CharStream} to set the input
+// position to the end of the current token. This behavior provides
+// for efficient DFA representation of lexer actions which appear at the end
+// of a lexer rule, even when the lexer rule Matches a variable number of
+// characters.
+//
+//
Prior to traversing a Match transition in the ATN, the current offset
+// from the token start index is assigned to all position-dependent lexer
+// actions which have not already been assigned a fixed offset. By storing
+// the offsets relative to the token start index, the DFA representation of
+// lexer actions which appear in the middle of tokens remains efficient due
+// to sharing among tokens of the same length, regardless of their absolute
+// position in the input stream.
+//
+//
If the current executor already has offsets assigned to all
+// position-dependent lexer actions, the method returns {@code this}.
+//
+// @param offset The current offset to assign to all position-dependent
+// lexer actions which do not already have offsets assigned.
+//
+// @return A {@link LexerActionExecutor} which stores input stream offsets
+// for all position-dependent lexer actions.
+// /
+func (l *LexerActionExecutor) fixOffsetBeforeMatch(offset int) *LexerActionExecutor {
+ var updatedLexerActions []LexerAction
+ for i := 0; i < len(l.lexerActions); i++ {
+ _, ok := l.lexerActions[i].(*LexerIndexedCustomAction)
+ if l.lexerActions[i].getIsPositionDependent() && !ok {
+ if updatedLexerActions == nil {
+ updatedLexerActions = make([]LexerAction, 0)
+
+ for _, a := range l.lexerActions {
+ updatedLexerActions = append(updatedLexerActions, a)
+ }
+ }
+
+ updatedLexerActions[i] = NewLexerIndexedCustomAction(offset, l.lexerActions[i])
+ }
+ }
+ if updatedLexerActions == nil {
+ return l
+ }
+
+ return NewLexerActionExecutor(updatedLexerActions)
+}
+
+// Execute the actions encapsulated by l executor within the context of a
+// particular {@link Lexer}.
+//
+//
This method calls {@link IntStream//seek} to set the position of the
+// {@code input} {@link CharStream} prior to calling
+// {@link LexerAction//execute} on a position-dependent action. Before the
+// method returns, the input position will be restored to the same position
+// it was in when the method was invoked.
+//
+// @param lexer The lexer instance.
+// @param input The input stream which is the source for the current token.
+// When l method is called, the current {@link IntStream//index} for
+// {@code input} should be the start of the following token, i.e. 1
+// character past the end of the current token.
+// @param startIndex The token start index. This value may be passed to
+// {@link IntStream//seek} to set the {@code input} position to the beginning
+// of the token.
+// /
+func (l *LexerActionExecutor) execute(lexer Lexer, input CharStream, startIndex int) {
+ requiresSeek := false
+ stopIndex := input.Index()
+
+ defer func() {
+ if requiresSeek {
+ input.Seek(stopIndex)
+ }
+ }()
+
+ for i := 0; i < len(l.lexerActions); i++ {
+ lexerAction := l.lexerActions[i]
+ if la, ok := lexerAction.(*LexerIndexedCustomAction); ok {
+ offset := la.offset
+ input.Seek(startIndex + offset)
+ lexerAction = la.lexerAction
+ requiresSeek = (startIndex + offset) != stopIndex
+ } else if lexerAction.getIsPositionDependent() {
+ input.Seek(stopIndex)
+ requiresSeek = false
+ }
+ lexerAction.execute(lexer)
+ }
+}
+
+func (l *LexerActionExecutor) hash() int {
+ if l == nil {
+ return 61
+ }
+ return l.cachedHash
+}
+
+func (l *LexerActionExecutor) equals(other interface{}) bool {
+ if l == other {
+ return true
+ } else if _, ok := other.(*LexerActionExecutor); !ok {
+ return false
+ } else {
+ return l.cachedHash == other.(*LexerActionExecutor).cachedHash &&
+ &l.lexerActions == &other.(*LexerActionExecutor).lexerActions
+ }
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_atn_simulator.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_atn_simulator.go
new file mode 100644
index 0000000000..32d69e1b87
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/lexer_atn_simulator.go
@@ -0,0 +1,658 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "strconv"
+)
+
+var (
+ LexerATNSimulatorDebug = false
+ LexerATNSimulatorDFADebug = false
+
+ LexerATNSimulatorMinDFAEdge = 0
+ LexerATNSimulatorMaxDFAEdge = 127 // forces unicode to stay in ATN
+
+ LexerATNSimulatorMatchCalls = 0
+)
+
+type ILexerATNSimulator interface {
+ IATNSimulator
+
+ reset()
+ Match(input CharStream, mode int) int
+ GetCharPositionInLine() int
+ GetLine() int
+ GetText(input CharStream) string
+ Consume(input CharStream)
+}
+
+type LexerATNSimulator struct {
+ *BaseATNSimulator
+
+ recog Lexer
+ predictionMode int
+ mergeCache DoubleDict
+ startIndex int
+ Line int
+ CharPositionInLine int
+ mode int
+ prevAccept *SimState
+ MatchCalls int
+}
+
+func NewLexerATNSimulator(recog Lexer, atn *ATN, decisionToDFA []*DFA, sharedContextCache *PredictionContextCache) *LexerATNSimulator {
+ l := new(LexerATNSimulator)
+
+ l.BaseATNSimulator = NewBaseATNSimulator(atn, sharedContextCache)
+
+ l.decisionToDFA = decisionToDFA
+ l.recog = recog
+ // The current token's starting index into the character stream.
+ // Shared across DFA to ATN simulation in case the ATN fails and the
+ // DFA did not have a previous accept state. In l case, we use the
+ // ATN-generated exception object.
+ l.startIndex = -1
+ // line number 1..n within the input///
+ l.Line = 1
+ // The index of the character relative to the beginning of the line
+ // 0..n-1///
+ l.CharPositionInLine = 0
+ l.mode = LexerDefaultMode
+ // Used during DFA/ATN exec to record the most recent accept configuration
+ // info
+ l.prevAccept = NewSimState()
+ // done
+ return l
+}
+
+func (l *LexerATNSimulator) copyState(simulator *LexerATNSimulator) {
+ l.CharPositionInLine = simulator.CharPositionInLine
+ l.Line = simulator.Line
+ l.mode = simulator.mode
+ l.startIndex = simulator.startIndex
+}
+
+func (l *LexerATNSimulator) Match(input CharStream, mode int) int {
+ l.MatchCalls++
+ l.mode = mode
+ mark := input.Mark()
+
+ defer func() {
+ input.Release(mark)
+ }()
+
+ l.startIndex = input.Index()
+ l.prevAccept.reset()
+
+ dfa := l.decisionToDFA[mode]
+
+ if dfa.getS0() == nil {
+ return l.MatchATN(input)
+ }
+
+ return l.execATN(input, dfa.getS0())
+}
+
+func (l *LexerATNSimulator) reset() {
+ l.prevAccept.reset()
+ l.startIndex = -1
+ l.Line = 1
+ l.CharPositionInLine = 0
+ l.mode = LexerDefaultMode
+}
+
+func (l *LexerATNSimulator) MatchATN(input CharStream) int {
+ startState := l.atn.modeToStartState[l.mode]
+
+ if LexerATNSimulatorDebug {
+ fmt.Println("MatchATN mode " + strconv.Itoa(l.mode) + " start: " + startState.String())
+ }
+ oldMode := l.mode
+ s0Closure := l.computeStartState(input, startState)
+ suppressEdge := s0Closure.hasSemanticContext
+ s0Closure.hasSemanticContext = false
+
+ next := l.addDFAState(s0Closure)
+
+ if !suppressEdge {
+ l.decisionToDFA[l.mode].setS0(next)
+ }
+
+ predict := l.execATN(input, next)
+
+ if LexerATNSimulatorDebug {
+ fmt.Println("DFA after MatchATN: " + l.decisionToDFA[oldMode].ToLexerString())
+ }
+ return predict
+}
+
+func (l *LexerATNSimulator) execATN(input CharStream, ds0 *DFAState) int {
+
+ if LexerATNSimulatorDebug {
+ fmt.Println("start state closure=" + ds0.configs.String())
+ }
+ if ds0.isAcceptState {
+ // allow zero-length tokens
+ l.captureSimState(l.prevAccept, input, ds0)
+ }
+ t := input.LA(1)
+ s := ds0 // s is current/from DFA state
+
+ for { // while more work
+ if LexerATNSimulatorDebug {
+ fmt.Println("execATN loop starting closure: " + s.configs.String())
+ }
+
+ // As we move src->trg, src->trg, we keep track of the previous trg to
+ // avoid looking up the DFA state again, which is expensive.
+ // If the previous target was already part of the DFA, we might
+ // be able to avoid doing a reach operation upon t. If s!=nil,
+ // it means that semantic predicates didn't prevent us from
+ // creating a DFA state. Once we know s!=nil, we check to see if
+ // the DFA state has an edge already for t. If so, we can just reuse
+ // it's configuration set there's no point in re-computing it.
+ // This is kind of like doing DFA simulation within the ATN
+ // simulation because DFA simulation is really just a way to avoid
+ // computing reach/closure sets. Technically, once we know that
+ // we have a previously added DFA state, we could jump over to
+ // the DFA simulator. But, that would mean popping back and forth
+ // a lot and making things more complicated algorithmically.
+ // This optimization makes a lot of sense for loops within DFA.
+ // A character will take us back to an existing DFA state
+ // that already has lots of edges out of it. e.g., .* in comments.
+ target := l.getExistingTargetState(s, t)
+ if target == nil {
+ target = l.computeTargetState(input, s, t)
+ // print("Computed:" + str(target))
+ }
+ if target == ATNSimulatorError {
+ break
+ }
+ // If l is a consumable input element, make sure to consume before
+ // capturing the accept state so the input index, line, and char
+ // position accurately reflect the state of the interpreter at the
+ // end of the token.
+ if t != TokenEOF {
+ l.Consume(input)
+ }
+ if target.isAcceptState {
+ l.captureSimState(l.prevAccept, input, target)
+ if t == TokenEOF {
+ break
+ }
+ }
+ t = input.LA(1)
+ s = target // flip current DFA target becomes Newsrc/from state
+ }
+
+ return l.failOrAccept(l.prevAccept, input, s.configs, t)
+}
+
+// Get an existing target state for an edge in the DFA. If the target state
+// for the edge has not yet been computed or is otherwise not available,
+// l method returns {@code nil}.
+//
+// @param s The current DFA state
+// @param t The next input symbol
+// @return The existing target DFA state for the given input symbol
+// {@code t}, or {@code nil} if the target state for l edge is not
+// already cached
+func (l *LexerATNSimulator) getExistingTargetState(s *DFAState, t int) *DFAState {
+ if s.getEdges() == nil || t < LexerATNSimulatorMinDFAEdge || t > LexerATNSimulatorMaxDFAEdge {
+ return nil
+ }
+
+ target := s.getIthEdge(t-LexerATNSimulatorMinDFAEdge)
+ if LexerATNSimulatorDebug && target != nil {
+ fmt.Println("reuse state " + strconv.Itoa(s.stateNumber) + " edge to " + strconv.Itoa(target.stateNumber))
+ }
+ return target
+}
+
+// Compute a target state for an edge in the DFA, and attempt to add the
+// computed state and corresponding edge to the DFA.
+//
+// @param input The input stream
+// @param s The current DFA state
+// @param t The next input symbol
+//
+// @return The computed target DFA state for the given input symbol
+// {@code t}. If {@code t} does not lead to a valid DFA state, l method
+// returns {@link //ERROR}.
+func (l *LexerATNSimulator) computeTargetState(input CharStream, s *DFAState, t int) *DFAState {
+ reach := NewOrderedATNConfigSet()
+
+ // if we don't find an existing DFA state
+ // Fill reach starting from closure, following t transitions
+ l.getReachableConfigSet(input, s.configs, reach.BaseATNConfigSet, t)
+
+ if len(reach.configs) == 0 { // we got nowhere on t from s
+ if !reach.hasSemanticContext {
+ // we got nowhere on t, don't panic out l knowledge it'd
+ // cause a failover from DFA later.
+ l.addDFAEdge(s, t, ATNSimulatorError, nil)
+ }
+ // stop when we can't Match any more char
+ return ATNSimulatorError
+ }
+ // Add an edge from s to target DFA found/created for reach
+ return l.addDFAEdge(s, t, nil, reach.BaseATNConfigSet)
+}
+
+func (l *LexerATNSimulator) failOrAccept(prevAccept *SimState, input CharStream, reach ATNConfigSet, t int) int {
+ if l.prevAccept.dfaState != nil {
+ lexerActionExecutor := prevAccept.dfaState.lexerActionExecutor
+ l.accept(input, lexerActionExecutor, l.startIndex, prevAccept.index, prevAccept.line, prevAccept.column)
+ return prevAccept.dfaState.prediction
+ }
+
+ // if no accept and EOF is first char, return EOF
+ if t == TokenEOF && input.Index() == l.startIndex {
+ return TokenEOF
+ }
+
+ panic(NewLexerNoViableAltException(l.recog, input, l.startIndex, reach))
+}
+
+// Given a starting configuration set, figure out all ATN configurations
+// we can reach upon input {@code t}. Parameter {@code reach} is a return
+// parameter.
+func (l *LexerATNSimulator) getReachableConfigSet(input CharStream, closure ATNConfigSet, reach ATNConfigSet, t int) {
+ // l is used to Skip processing for configs which have a lower priority
+ // than a config that already reached an accept state for the same rule
+ SkipAlt := ATNInvalidAltNumber
+
+ for _, cfg := range closure.GetItems() {
+ currentAltReachedAcceptState := (cfg.GetAlt() == SkipAlt)
+ if currentAltReachedAcceptState && cfg.(*LexerATNConfig).passedThroughNonGreedyDecision {
+ continue
+ }
+
+ if LexerATNSimulatorDebug {
+
+ fmt.Printf("testing %s at %s\n", l.GetTokenName(t), cfg.String()) // l.recog, true))
+ }
+
+ for _, trans := range cfg.GetState().GetTransitions() {
+ target := l.getReachableTarget(trans, t)
+ if target != nil {
+ lexerActionExecutor := cfg.(*LexerATNConfig).lexerActionExecutor
+ if lexerActionExecutor != nil {
+ lexerActionExecutor = lexerActionExecutor.fixOffsetBeforeMatch(input.Index() - l.startIndex)
+ }
+ treatEOFAsEpsilon := (t == TokenEOF)
+ config := NewLexerATNConfig3(cfg.(*LexerATNConfig), target, lexerActionExecutor)
+ if l.closure(input, config, reach,
+ currentAltReachedAcceptState, true, treatEOFAsEpsilon) {
+ // any remaining configs for l alt have a lower priority
+ // than the one that just reached an accept state.
+ SkipAlt = cfg.GetAlt()
+ }
+ }
+ }
+ }
+}
+
+func (l *LexerATNSimulator) accept(input CharStream, lexerActionExecutor *LexerActionExecutor, startIndex, index, line, charPos int) {
+ if LexerATNSimulatorDebug {
+ fmt.Printf("ACTION %s\n", lexerActionExecutor)
+ }
+ // seek to after last char in token
+ input.Seek(index)
+ l.Line = line
+ l.CharPositionInLine = charPos
+ if lexerActionExecutor != nil && l.recog != nil {
+ lexerActionExecutor.execute(l.recog, input, startIndex)
+ }
+}
+
+func (l *LexerATNSimulator) getReachableTarget(trans Transition, t int) ATNState {
+ if trans.Matches(t, 0, LexerMaxCharValue) {
+ return trans.getTarget()
+ }
+
+ return nil
+}
+
+func (l *LexerATNSimulator) computeStartState(input CharStream, p ATNState) *OrderedATNConfigSet {
+ configs := NewOrderedATNConfigSet()
+ for i := 0; i < len(p.GetTransitions()); i++ {
+ target := p.GetTransitions()[i].getTarget()
+ cfg := NewLexerATNConfig6(target, i+1, BasePredictionContextEMPTY)
+ l.closure(input, cfg, configs, false, false, false)
+ }
+
+ return configs
+}
+
+// Since the alternatives within any lexer decision are ordered by
+// preference, l method stops pursuing the closure as soon as an accept
+// state is reached. After the first accept state is reached by depth-first
+// search from {@code config}, all other (potentially reachable) states for
+// l rule would have a lower priority.
+//
+// @return {@code true} if an accept state is reached, otherwise
+// {@code false}.
+func (l *LexerATNSimulator) closure(input CharStream, config *LexerATNConfig, configs ATNConfigSet,
+ currentAltReachedAcceptState, speculative, treatEOFAsEpsilon bool) bool {
+
+ if LexerATNSimulatorDebug {
+ fmt.Println("closure(" + config.String() + ")") // config.String(l.recog, true) + ")")
+ }
+
+ _, ok := config.state.(*RuleStopState)
+ if ok {
+
+ if LexerATNSimulatorDebug {
+ if l.recog != nil {
+ fmt.Printf("closure at %s rule stop %s\n", l.recog.GetRuleNames()[config.state.GetRuleIndex()], config)
+ } else {
+ fmt.Printf("closure at rule stop %s\n", config)
+ }
+ }
+
+ if config.context == nil || config.context.hasEmptyPath() {
+ if config.context == nil || config.context.isEmpty() {
+ configs.Add(config, nil)
+ return true
+ }
+
+ configs.Add(NewLexerATNConfig2(config, config.state, BasePredictionContextEMPTY), nil)
+ currentAltReachedAcceptState = true
+ }
+ if config.context != nil && !config.context.isEmpty() {
+ for i := 0; i < config.context.length(); i++ {
+ if config.context.getReturnState(i) != BasePredictionContextEmptyReturnState {
+ newContext := config.context.GetParent(i) // "pop" return state
+ returnState := l.atn.states[config.context.getReturnState(i)]
+ cfg := NewLexerATNConfig2(config, returnState, newContext)
+ currentAltReachedAcceptState = l.closure(input, cfg, configs, currentAltReachedAcceptState, speculative, treatEOFAsEpsilon)
+ }
+ }
+ }
+ return currentAltReachedAcceptState
+ }
+ // optimization
+ if !config.state.GetEpsilonOnlyTransitions() {
+ if !currentAltReachedAcceptState || !config.passedThroughNonGreedyDecision {
+ configs.Add(config, nil)
+ }
+ }
+ for j := 0; j < len(config.state.GetTransitions()); j++ {
+ trans := config.state.GetTransitions()[j]
+ cfg := l.getEpsilonTarget(input, config, trans, configs, speculative, treatEOFAsEpsilon)
+ if cfg != nil {
+ currentAltReachedAcceptState = l.closure(input, cfg, configs,
+ currentAltReachedAcceptState, speculative, treatEOFAsEpsilon)
+ }
+ }
+ return currentAltReachedAcceptState
+}
+
+// side-effect: can alter configs.hasSemanticContext
+func (l *LexerATNSimulator) getEpsilonTarget(input CharStream, config *LexerATNConfig, trans Transition,
+ configs ATNConfigSet, speculative, treatEOFAsEpsilon bool) *LexerATNConfig {
+
+ var cfg *LexerATNConfig
+
+ if trans.getSerializationType() == TransitionRULE {
+
+ rt := trans.(*RuleTransition)
+ newContext := SingletonBasePredictionContextCreate(config.context, rt.followState.GetStateNumber())
+ cfg = NewLexerATNConfig2(config, trans.getTarget(), newContext)
+
+ } else if trans.getSerializationType() == TransitionPRECEDENCE {
+ panic("Precedence predicates are not supported in lexers.")
+ } else if trans.getSerializationType() == TransitionPREDICATE {
+ // Track traversing semantic predicates. If we traverse,
+ // we cannot add a DFA state for l "reach" computation
+ // because the DFA would not test the predicate again in the
+ // future. Rather than creating collections of semantic predicates
+ // like v3 and testing them on prediction, v4 will test them on the
+ // fly all the time using the ATN not the DFA. This is slower but
+ // semantically it's not used that often. One of the key elements to
+ // l predicate mechanism is not adding DFA states that see
+ // predicates immediately afterwards in the ATN. For example,
+
+ // a : ID {p1}? | ID {p2}?
+
+ // should create the start state for rule 'a' (to save start state
+ // competition), but should not create target of ID state. The
+ // collection of ATN states the following ID references includes
+ // states reached by traversing predicates. Since l is when we
+ // test them, we cannot cash the DFA state target of ID.
+
+ pt := trans.(*PredicateTransition)
+
+ if LexerATNSimulatorDebug {
+ fmt.Println("EVAL rule " + strconv.Itoa(trans.(*PredicateTransition).ruleIndex) + ":" + strconv.Itoa(pt.predIndex))
+ }
+ configs.SetHasSemanticContext(true)
+ if l.evaluatePredicate(input, pt.ruleIndex, pt.predIndex, speculative) {
+ cfg = NewLexerATNConfig4(config, trans.getTarget())
+ }
+ } else if trans.getSerializationType() == TransitionACTION {
+ if config.context == nil || config.context.hasEmptyPath() {
+ // execute actions anywhere in the start rule for a token.
+ //
+ // TODO: if the entry rule is invoked recursively, some
+ // actions may be executed during the recursive call. The
+ // problem can appear when hasEmptyPath() is true but
+ // isEmpty() is false. In l case, the config needs to be
+ // split into two contexts - one with just the empty path
+ // and another with everything but the empty path.
+ // Unfortunately, the current algorithm does not allow
+ // getEpsilonTarget to return two configurations, so
+ // additional modifications are needed before we can support
+ // the split operation.
+ lexerActionExecutor := LexerActionExecutorappend(config.lexerActionExecutor, l.atn.lexerActions[trans.(*ActionTransition).actionIndex])
+ cfg = NewLexerATNConfig3(config, trans.getTarget(), lexerActionExecutor)
+ } else {
+ // ignore actions in referenced rules
+ cfg = NewLexerATNConfig4(config, trans.getTarget())
+ }
+ } else if trans.getSerializationType() == TransitionEPSILON {
+ cfg = NewLexerATNConfig4(config, trans.getTarget())
+ } else if trans.getSerializationType() == TransitionATOM ||
+ trans.getSerializationType() == TransitionRANGE ||
+ trans.getSerializationType() == TransitionSET {
+ if treatEOFAsEpsilon {
+ if trans.Matches(TokenEOF, 0, LexerMaxCharValue) {
+ cfg = NewLexerATNConfig4(config, trans.getTarget())
+ }
+ }
+ }
+ return cfg
+}
+
+// Evaluate a predicate specified in the lexer.
+//
+//
If {@code speculative} is {@code true}, l method was called before
+// {@link //consume} for the Matched character. This method should call
+// {@link //consume} before evaluating the predicate to ensure position
+// sensitive values, including {@link Lexer//GetText}, {@link Lexer//GetLine},
+// and {@link Lexer//getcolumn}, properly reflect the current
+// lexer state. This method should restore {@code input} and the simulator
+// to the original state before returning (i.e. undo the actions made by the
+// call to {@link //consume}.
+//
+// @param input The input stream.
+// @param ruleIndex The rule containing the predicate.
+// @param predIndex The index of the predicate within the rule.
+// @param speculative {@code true} if the current index in {@code input} is
+// one character before the predicate's location.
+//
+// @return {@code true} if the specified predicate evaluates to
+// {@code true}.
+// /
+func (l *LexerATNSimulator) evaluatePredicate(input CharStream, ruleIndex, predIndex int, speculative bool) bool {
+ // assume true if no recognizer was provided
+ if l.recog == nil {
+ return true
+ }
+ if !speculative {
+ return l.recog.Sempred(nil, ruleIndex, predIndex)
+ }
+ savedcolumn := l.CharPositionInLine
+ savedLine := l.Line
+ index := input.Index()
+ marker := input.Mark()
+
+ defer func() {
+ l.CharPositionInLine = savedcolumn
+ l.Line = savedLine
+ input.Seek(index)
+ input.Release(marker)
+ }()
+
+ l.Consume(input)
+ return l.recog.Sempred(nil, ruleIndex, predIndex)
+}
+
+func (l *LexerATNSimulator) captureSimState(settings *SimState, input CharStream, dfaState *DFAState) {
+ settings.index = input.Index()
+ settings.line = l.Line
+ settings.column = l.CharPositionInLine
+ settings.dfaState = dfaState
+}
+
+func (l *LexerATNSimulator) addDFAEdge(from *DFAState, tk int, to *DFAState, cfgs ATNConfigSet) *DFAState {
+ if to == nil && cfgs != nil {
+ // leading to l call, ATNConfigSet.hasSemanticContext is used as a
+ // marker indicating dynamic predicate evaluation makes l edge
+ // dependent on the specific input sequence, so the static edge in the
+ // DFA should be omitted. The target DFAState is still created since
+ // execATN has the ability to reSynchronize with the DFA state cache
+ // following the predicate evaluation step.
+ //
+ // TJP notes: next time through the DFA, we see a pred again and eval.
+ // If that gets us to a previously created (but dangling) DFA
+ // state, we can continue in pure DFA mode from there.
+ // /
+ suppressEdge := cfgs.HasSemanticContext()
+ cfgs.SetHasSemanticContext(false)
+
+ to = l.addDFAState(cfgs)
+
+ if suppressEdge {
+ return to
+ }
+ }
+ // add the edge
+ if tk < LexerATNSimulatorMinDFAEdge || tk > LexerATNSimulatorMaxDFAEdge {
+ // Only track edges within the DFA bounds
+ return to
+ }
+ if LexerATNSimulatorDebug {
+ fmt.Println("EDGE " + from.String() + " -> " + to.String() + " upon " + strconv.Itoa(tk))
+ }
+ if from.getEdges() == nil {
+ // make room for tokens 1..n and -1 masquerading as index 0
+ from.setEdges(make([]*DFAState, LexerATNSimulatorMaxDFAEdge-LexerATNSimulatorMinDFAEdge+1))
+ }
+ from.setIthEdge(tk-LexerATNSimulatorMinDFAEdge, to) // connect
+
+ return to
+}
+
+// Add a NewDFA state if there isn't one with l set of
+// configurations already. This method also detects the first
+// configuration containing an ATN rule stop state. Later, when
+// traversing the DFA, we will know which rule to accept.
+func (l *LexerATNSimulator) addDFAState(configs ATNConfigSet) *DFAState {
+
+ proposed := NewDFAState(-1, configs)
+ var firstConfigWithRuleStopState ATNConfig
+
+ for _, cfg := range configs.GetItems() {
+
+ _, ok := cfg.GetState().(*RuleStopState)
+
+ if ok {
+ firstConfigWithRuleStopState = cfg
+ break
+ }
+ }
+ if firstConfigWithRuleStopState != nil {
+ proposed.isAcceptState = true
+ proposed.lexerActionExecutor = firstConfigWithRuleStopState.(*LexerATNConfig).lexerActionExecutor
+ proposed.setPrediction(l.atn.ruleToTokenType[firstConfigWithRuleStopState.GetState().GetRuleIndex()])
+ }
+ hash := proposed.hash()
+ dfa := l.decisionToDFA[l.mode]
+ existing, ok := dfa.getState(hash)
+ if ok {
+ return existing
+ }
+ newState := proposed
+ newState.stateNumber = dfa.numStates()
+ configs.SetReadOnly(true)
+ newState.configs = configs
+ dfa.setState(hash, newState)
+ return newState
+}
+
+func (l *LexerATNSimulator) getDFA(mode int) *DFA {
+ return l.decisionToDFA[mode]
+}
+
+// Get the text Matched so far for the current token.
+func (l *LexerATNSimulator) GetText(input CharStream) string {
+ // index is first lookahead char, don't include.
+ return input.GetTextFromInterval(NewInterval(l.startIndex, input.Index()-1))
+}
+
+func (l *LexerATNSimulator) Consume(input CharStream) {
+ curChar := input.LA(1)
+ if curChar == int('\n') {
+ l.Line++
+ l.CharPositionInLine = 0
+ } else {
+ l.CharPositionInLine++
+ }
+ input.Consume()
+}
+
+func (l *LexerATNSimulator) GetCharPositionInLine() int {
+ return l.CharPositionInLine
+}
+
+func (l *LexerATNSimulator) GetLine() int {
+ return l.Line
+}
+
+func (l *LexerATNSimulator) GetTokenName(tt int) string {
+ if tt == -1 {
+ return "EOF"
+ }
+
+ return "'" + string(tt) + "'"
+}
+
+func resetSimState(sim *SimState) {
+ sim.index = -1
+ sim.line = 0
+ sim.column = -1
+ sim.dfaState = nil
+}
+
+type SimState struct {
+ index int
+ line int
+ column int
+ dfaState *DFAState
+}
+
+func NewSimState() *SimState {
+ s := new(SimState)
+ resetSimState(s)
+ return s
+}
+
+func (s *SimState) reset() {
+ resetSimState(s)
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/ll1_analyzer.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/ll1_analyzer.go
new file mode 100644
index 0000000000..3ebc40a76b
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/ll1_analyzer.go
@@ -0,0 +1,212 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+type LL1Analyzer struct {
+ atn *ATN
+}
+
+func NewLL1Analyzer(atn *ATN) *LL1Analyzer {
+ la := new(LL1Analyzer)
+ la.atn = atn
+ return la
+}
+
+//* Special value added to the lookahead sets to indicate that we hit
+// a predicate during analysis if {@code seeThruPreds==false}.
+///
+const (
+ LL1AnalyzerHitPred = TokenInvalidType
+)
+
+//*
+// Calculates the SLL(1) expected lookahead set for each outgoing transition
+// of an {@link ATNState}. The returned array has one element for each
+// outgoing transition in {@code s}. If the closure from transition
+// i leads to a semantic predicate before Matching a symbol, the
+// element at index i of the result will be {@code nil}.
+//
+// @param s the ATN state
+// @return the expected symbols for each outgoing transition of {@code s}.
+func (la *LL1Analyzer) getDecisionLookahead(s ATNState) []*IntervalSet {
+ if s == nil {
+ return nil
+ }
+ count := len(s.GetTransitions())
+ look := make([]*IntervalSet, count)
+ for alt := 0; alt < count; alt++ {
+ look[alt] = NewIntervalSet()
+ lookBusy := NewSet(nil, nil)
+ seeThruPreds := false // fail to get lookahead upon pred
+ la.look1(s.GetTransitions()[alt].getTarget(), nil, BasePredictionContextEMPTY, look[alt], lookBusy, NewBitSet(), seeThruPreds, false)
+ // Wipe out lookahead for la alternative if we found nothing
+ // or we had a predicate when we !seeThruPreds
+ if look[alt].length() == 0 || look[alt].contains(LL1AnalyzerHitPred) {
+ look[alt] = nil
+ }
+ }
+ return look
+}
+
+//*
+// Compute set of tokens that can follow {@code s} in the ATN in the
+// specified {@code ctx}.
+//
+//
If {@code ctx} is {@code nil} and the end of the rule containing
+// {@code s} is reached, {@link Token//EPSILON} is added to the result set.
+// If {@code ctx} is not {@code nil} and the end of the outermost rule is
+// reached, {@link Token//EOF} is added to the result set.
+//
+// @param s the ATN state
+// @param stopState the ATN state to stop at. This can be a
+// {@link BlockEndState} to detect epsilon paths through a closure.
+// @param ctx the complete parser context, or {@code nil} if the context
+// should be ignored
+//
+// @return The set of tokens that can follow {@code s} in the ATN in the
+// specified {@code ctx}.
+///
+func (la *LL1Analyzer) Look(s, stopState ATNState, ctx RuleContext) *IntervalSet {
+ r := NewIntervalSet()
+ seeThruPreds := true // ignore preds get all lookahead
+ var lookContext PredictionContext
+ if ctx != nil {
+ lookContext = predictionContextFromRuleContext(s.GetATN(), ctx)
+ }
+ la.look1(s, stopState, lookContext, r, NewSet(nil, nil), NewBitSet(), seeThruPreds, true)
+ return r
+}
+
+//*
+// Compute set of tokens that can follow {@code s} in the ATN in the
+// specified {@code ctx}.
+//
+//
If {@code ctx} is {@code nil} and {@code stopState} or the end of the
+// rule containing {@code s} is reached, {@link Token//EPSILON} is added to
+// the result set. If {@code ctx} is not {@code nil} and {@code addEOF} is
+// {@code true} and {@code stopState} or the end of the outermost rule is
+// reached, {@link Token//EOF} is added to the result set.
+//
+// @param s the ATN state.
+// @param stopState the ATN state to stop at. This can be a
+// {@link BlockEndState} to detect epsilon paths through a closure.
+// @param ctx The outer context, or {@code nil} if the outer context should
+// not be used.
+// @param look The result lookahead set.
+// @param lookBusy A set used for preventing epsilon closures in the ATN
+// from causing a stack overflow. Outside code should pass
+// {@code NewSet} for la argument.
+// @param calledRuleStack A set used for preventing left recursion in the
+// ATN from causing a stack overflow. Outside code should pass
+// {@code NewBitSet()} for la argument.
+// @param seeThruPreds {@code true} to true semantic predicates as
+// implicitly {@code true} and "see through them", otherwise {@code false}
+// to treat semantic predicates as opaque and add {@link //HitPred} to the
+// result if one is encountered.
+// @param addEOF Add {@link Token//EOF} to the result if the end of the
+// outermost context is reached. This parameter has no effect if {@code ctx}
+// is {@code nil}.
+
+func (la *LL1Analyzer) look2(s, stopState ATNState, ctx PredictionContext, look *IntervalSet, lookBusy *Set, calledRuleStack *BitSet, seeThruPreds, addEOF bool, i int) {
+
+ returnState := la.atn.states[ctx.getReturnState(i)]
+ la.look1(returnState, stopState, ctx.GetParent(i), look, lookBusy, calledRuleStack, seeThruPreds, addEOF)
+
+}
+
+func (la *LL1Analyzer) look1(s, stopState ATNState, ctx PredictionContext, look *IntervalSet, lookBusy *Set, calledRuleStack *BitSet, seeThruPreds, addEOF bool) {
+
+ c := NewBaseATNConfig6(s, 0, ctx)
+
+ if lookBusy.contains(c) {
+ return
+ }
+
+ lookBusy.add(c)
+
+ if s == stopState {
+ if ctx == nil {
+ look.addOne(TokenEpsilon)
+ return
+ } else if ctx.isEmpty() && addEOF {
+ look.addOne(TokenEOF)
+ return
+ }
+ }
+
+ _, ok := s.(*RuleStopState)
+
+ if ok {
+ if ctx == nil {
+ look.addOne(TokenEpsilon)
+ return
+ } else if ctx.isEmpty() && addEOF {
+ look.addOne(TokenEOF)
+ return
+ }
+
+ if ctx != BasePredictionContextEMPTY {
+ removed := calledRuleStack.contains(s.GetRuleIndex())
+ defer func() {
+ if removed {
+ calledRuleStack.add(s.GetRuleIndex())
+ }
+ }()
+ calledRuleStack.remove(s.GetRuleIndex())
+ // run thru all possible stack tops in ctx
+ for i := 0; i < ctx.length(); i++ {
+ returnState := la.atn.states[ctx.getReturnState(i)]
+ la.look2(returnState, stopState, ctx, look, lookBusy, calledRuleStack, seeThruPreds, addEOF, i)
+ }
+ return
+ }
+ }
+
+ n := len(s.GetTransitions())
+
+ for i := 0; i < n; i++ {
+ t := s.GetTransitions()[i]
+
+ if t1, ok := t.(*RuleTransition); ok {
+ if calledRuleStack.contains(t1.getTarget().GetRuleIndex()) {
+ continue
+ }
+
+ newContext := SingletonBasePredictionContextCreate(ctx, t1.followState.GetStateNumber())
+ la.look3(stopState, newContext, look, lookBusy, calledRuleStack, seeThruPreds, addEOF, t1)
+ } else if t2, ok := t.(AbstractPredicateTransition); ok {
+ if seeThruPreds {
+ la.look1(t2.getTarget(), stopState, ctx, look, lookBusy, calledRuleStack, seeThruPreds, addEOF)
+ } else {
+ look.addOne(LL1AnalyzerHitPred)
+ }
+ } else if t.getIsEpsilon() {
+ la.look1(t.getTarget(), stopState, ctx, look, lookBusy, calledRuleStack, seeThruPreds, addEOF)
+ } else if _, ok := t.(*WildcardTransition); ok {
+ look.addRange(TokenMinUserTokenType, la.atn.maxTokenType)
+ } else {
+ set := t.getLabel()
+ if set != nil {
+ if _, ok := t.(*NotSetTransition); ok {
+ set = set.complement(TokenMinUserTokenType, la.atn.maxTokenType)
+ }
+ look.addSet(set)
+ }
+ }
+ }
+}
+
+func (la *LL1Analyzer) look3(stopState ATNState, ctx PredictionContext, look *IntervalSet, lookBusy *Set, calledRuleStack *BitSet, seeThruPreds, addEOF bool, t1 *RuleTransition) {
+
+ newContext := SingletonBasePredictionContextCreate(ctx, t1.followState.GetStateNumber())
+
+ defer func() {
+ calledRuleStack.remove(t1.getTarget().GetRuleIndex())
+ }()
+
+ calledRuleStack.add(t1.getTarget().GetRuleIndex())
+ la.look1(t1.getTarget(), stopState, newContext, look, lookBusy, calledRuleStack, seeThruPreds, addEOF)
+
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser.go
new file mode 100644
index 0000000000..fb60258e33
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser.go
@@ -0,0 +1,718 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "strconv"
+)
+
+type Parser interface {
+ Recognizer
+
+ GetInterpreter() *ParserATNSimulator
+
+ GetTokenStream() TokenStream
+ GetTokenFactory() TokenFactory
+ GetParserRuleContext() ParserRuleContext
+ SetParserRuleContext(ParserRuleContext)
+ Consume() Token
+ GetParseListeners() []ParseTreeListener
+
+ GetErrorHandler() ErrorStrategy
+ SetErrorHandler(ErrorStrategy)
+ GetInputStream() IntStream
+ GetCurrentToken() Token
+ GetExpectedTokens() *IntervalSet
+ NotifyErrorListeners(string, Token, RecognitionException)
+ IsExpectedToken(int) bool
+ GetPrecedence() int
+ GetRuleInvocationStack(ParserRuleContext) []string
+}
+
+type BaseParser struct {
+ *BaseRecognizer
+
+ Interpreter *ParserATNSimulator
+ BuildParseTrees bool
+
+ input TokenStream
+ errHandler ErrorStrategy
+ precedenceStack IntStack
+ ctx ParserRuleContext
+
+ tracer *TraceListener
+ parseListeners []ParseTreeListener
+ _SyntaxErrors int
+}
+
+// p.is all the parsing support code essentially most of it is error
+// recovery stuff.//
+func NewBaseParser(input TokenStream) *BaseParser {
+
+ p := new(BaseParser)
+
+ p.BaseRecognizer = NewBaseRecognizer()
+
+ // The input stream.
+ p.input = nil
+ // The error handling strategy for the parser. The default value is a new
+ // instance of {@link DefaultErrorStrategy}.
+ p.errHandler = NewDefaultErrorStrategy()
+ p.precedenceStack = make([]int, 0)
+ p.precedenceStack.Push(0)
+ // The {@link ParserRuleContext} object for the currently executing rule.
+ // p.is always non-nil during the parsing process.
+ p.ctx = nil
+ // Specifies whether or not the parser should construct a parse tree during
+ // the parsing process. The default value is {@code true}.
+ p.BuildParseTrees = true
+ // When {@link //setTrace}{@code (true)} is called, a reference to the
+ // {@link TraceListener} is stored here so it can be easily removed in a
+ // later call to {@link //setTrace}{@code (false)}. The listener itself is
+ // implemented as a parser listener so p.field is not directly used by
+ // other parser methods.
+ p.tracer = nil
+ // The list of {@link ParseTreeListener} listeners registered to receive
+ // events during the parse.
+ p.parseListeners = nil
+ // The number of syntax errors Reported during parsing. p.value is
+ // incremented each time {@link //NotifyErrorListeners} is called.
+ p._SyntaxErrors = 0
+ p.SetInputStream(input)
+
+ return p
+}
+
+// p.field maps from the serialized ATN string to the deserialized {@link
+// ATN} with
+// bypass alternatives.
+//
+// @see ATNDeserializationOptions//isGenerateRuleBypassTransitions()
+//
+var bypassAltsAtnCache = make(map[string]int)
+
+// reset the parser's state//
+func (p *BaseParser) reset() {
+ if p.input != nil {
+ p.input.Seek(0)
+ }
+ p.errHandler.reset(p)
+ p.ctx = nil
+ p._SyntaxErrors = 0
+ p.SetTrace(nil)
+ p.precedenceStack = make([]int, 0)
+ p.precedenceStack.Push(0)
+ if p.Interpreter != nil {
+ p.Interpreter.reset()
+ }
+}
+
+func (p *BaseParser) GetErrorHandler() ErrorStrategy {
+ return p.errHandler
+}
+
+func (p *BaseParser) SetErrorHandler(e ErrorStrategy) {
+ p.errHandler = e
+}
+
+// Match current input symbol against {@code ttype}. If the symbol type
+// Matches, {@link ANTLRErrorStrategy//ReportMatch} and {@link //consume} are
+// called to complete the Match process.
+//
+//
If the symbol type does not Match,
+// {@link ANTLRErrorStrategy//recoverInline} is called on the current error
+// strategy to attempt recovery. If {@link //getBuildParseTree} is
+// {@code true} and the token index of the symbol returned by
+// {@link ANTLRErrorStrategy//recoverInline} is -1, the symbol is added to
+// the parse tree by calling {@link ParserRuleContext//addErrorNode}.
+//
+// @param ttype the token type to Match
+// @return the Matched symbol
+// @panics RecognitionException if the current input symbol did not Match
+// {@code ttype} and the error strategy could not recover from the
+// mismatched symbol
+
+func (p *BaseParser) Match(ttype int) Token {
+
+ t := p.GetCurrentToken()
+
+ if t.GetTokenType() == ttype {
+ p.errHandler.ReportMatch(p)
+ p.Consume()
+ } else {
+ t = p.errHandler.RecoverInline(p)
+ if p.BuildParseTrees && t.GetTokenIndex() == -1 {
+ // we must have conjured up a Newtoken during single token
+ // insertion
+ // if it's not the current symbol
+ p.ctx.AddErrorNode(t)
+ }
+ }
+
+ return t
+}
+
+// Match current input symbol as a wildcard. If the symbol type Matches
+// (i.e. has a value greater than 0), {@link ANTLRErrorStrategy//ReportMatch}
+// and {@link //consume} are called to complete the Match process.
+//
+//
If the symbol type does not Match,
+// {@link ANTLRErrorStrategy//recoverInline} is called on the current error
+// strategy to attempt recovery. If {@link //getBuildParseTree} is
+// {@code true} and the token index of the symbol returned by
+// {@link ANTLRErrorStrategy//recoverInline} is -1, the symbol is added to
+// the parse tree by calling {@link ParserRuleContext//addErrorNode}.
+//
+// @return the Matched symbol
+// @panics RecognitionException if the current input symbol did not Match
+// a wildcard and the error strategy could not recover from the mismatched
+// symbol
+
+func (p *BaseParser) MatchWildcard() Token {
+ t := p.GetCurrentToken()
+ if t.GetTokenType() > 0 {
+ p.errHandler.ReportMatch(p)
+ p.Consume()
+ } else {
+ t = p.errHandler.RecoverInline(p)
+ if p.BuildParseTrees && t.GetTokenIndex() == -1 {
+ // we must have conjured up a Newtoken during single token
+ // insertion
+ // if it's not the current symbol
+ p.ctx.AddErrorNode(t)
+ }
+ }
+ return t
+}
+
+func (p *BaseParser) GetParserRuleContext() ParserRuleContext {
+ return p.ctx
+}
+
+func (p *BaseParser) SetParserRuleContext(v ParserRuleContext) {
+ p.ctx = v
+}
+
+func (p *BaseParser) GetParseListeners() []ParseTreeListener {
+ if p.parseListeners == nil {
+ return make([]ParseTreeListener, 0)
+ }
+ return p.parseListeners
+}
+
+// Registers {@code listener} to receive events during the parsing process.
+//
+//
To support output-preserving grammar transformations (including but not
+// limited to left-recursion removal, automated left-factoring, and
+// optimized code generation), calls to listener methods during the parse
+// may differ substantially from calls made by
+// {@link ParseTreeWalker//DEFAULT} used after the parse is complete. In
+// particular, rule entry and exit events may occur in a different order
+// during the parse than after the parser. In addition, calls to certain
+// rule entry methods may be omitted.
+//
+//
With the following specific exceptions, calls to listener events are
+// deterministic, i.e. for identical input the calls to listener
+// methods will be the same.
+//
+//
+//
Alterations to the grammar used to generate code may change the
+// behavior of the listener calls.
+//
Alterations to the command line options passed to ANTLR 4 when
+// generating the parser may change the behavior of the listener calls.
+//
Changing the version of the ANTLR Tool used to generate the parser
+// may change the behavior of the listener calls.
+//
+//
+// @param listener the listener to add
+//
+// @panics nilPointerException if {@code} listener is {@code nil}
+//
+func (p *BaseParser) AddParseListener(listener ParseTreeListener) {
+ if listener == nil {
+ panic("listener")
+ }
+ if p.parseListeners == nil {
+ p.parseListeners = make([]ParseTreeListener, 0)
+ }
+ p.parseListeners = append(p.parseListeners, listener)
+}
+
+//
+// Remove {@code listener} from the list of parse listeners.
+//
+//
If {@code listener} is {@code nil} or has not been added as a parse
+// listener, p.method does nothing.
+// @param listener the listener to remove
+//
+func (p *BaseParser) RemoveParseListener(listener ParseTreeListener) {
+
+ if p.parseListeners != nil {
+
+ idx := -1
+ for i, v := range p.parseListeners {
+ if v == listener {
+ idx = i
+ break
+ }
+ }
+
+ if idx == -1 {
+ return
+ }
+
+ // remove the listener from the slice
+ p.parseListeners = append(p.parseListeners[0:idx], p.parseListeners[idx+1:]...)
+
+ if len(p.parseListeners) == 0 {
+ p.parseListeners = nil
+ }
+ }
+}
+
+// Remove all parse listeners.
+func (p *BaseParser) removeParseListeners() {
+ p.parseListeners = nil
+}
+
+// Notify any parse listeners of an enter rule event.
+func (p *BaseParser) TriggerEnterRuleEvent() {
+ if p.parseListeners != nil {
+ ctx := p.ctx
+ for _, listener := range p.parseListeners {
+ listener.EnterEveryRule(ctx)
+ ctx.EnterRule(listener)
+ }
+ }
+}
+
+//
+// Notify any parse listeners of an exit rule event.
+//
+// @see //addParseListener
+//
+func (p *BaseParser) TriggerExitRuleEvent() {
+ if p.parseListeners != nil {
+ // reverse order walk of listeners
+ ctx := p.ctx
+ l := len(p.parseListeners) - 1
+
+ for i := range p.parseListeners {
+ listener := p.parseListeners[l-i]
+ ctx.ExitRule(listener)
+ listener.ExitEveryRule(ctx)
+ }
+ }
+}
+
+func (p *BaseParser) GetInterpreter() *ParserATNSimulator {
+ return p.Interpreter
+}
+
+func (p *BaseParser) GetATN() *ATN {
+ return p.Interpreter.atn
+}
+
+func (p *BaseParser) GetTokenFactory() TokenFactory {
+ return p.input.GetTokenSource().GetTokenFactory()
+}
+
+// Tell our token source and error strategy about a Newway to create tokens.//
+func (p *BaseParser) setTokenFactory(factory TokenFactory) {
+ p.input.GetTokenSource().setTokenFactory(factory)
+}
+
+// The ATN with bypass alternatives is expensive to create so we create it
+// lazily.
+//
+// @panics UnsupportedOperationException if the current parser does not
+// implement the {@link //getSerializedATN()} method.
+//
+func (p *BaseParser) GetATNWithBypassAlts() {
+
+ // TODO
+ panic("Not implemented!")
+
+ // serializedAtn := p.getSerializedATN()
+ // if (serializedAtn == nil) {
+ // panic("The current parser does not support an ATN with bypass alternatives.")
+ // }
+ // result := p.bypassAltsAtnCache[serializedAtn]
+ // if (result == nil) {
+ // deserializationOptions := NewATNDeserializationOptions(nil)
+ // deserializationOptions.generateRuleBypassTransitions = true
+ // result = NewATNDeserializer(deserializationOptions).deserialize(serializedAtn)
+ // p.bypassAltsAtnCache[serializedAtn] = result
+ // }
+ // return result
+}
+
+// The preferred method of getting a tree pattern. For example, here's a
+// sample use:
+//
+//
+// ParseTree t = parser.expr()
+// ParseTreePattern p = parser.compileParseTreePattern("<ID>+0",
+// MyParser.RULE_expr)
+// ParseTreeMatch m = p.Match(t)
+// String id = m.Get("ID")
+//
+
+func (p *BaseParser) compileParseTreePattern(pattern, patternRuleIndex, lexer Lexer) {
+
+ panic("NewParseTreePatternMatcher not implemented!")
+ //
+ // if (lexer == nil) {
+ // if (p.GetTokenStream() != nil) {
+ // tokenSource := p.GetTokenStream().GetTokenSource()
+ // if _, ok := tokenSource.(ILexer); ok {
+ // lexer = tokenSource
+ // }
+ // }
+ // }
+ // if (lexer == nil) {
+ // panic("Parser can't discover a lexer to use")
+ // }
+
+ // m := NewParseTreePatternMatcher(lexer, p)
+ // return m.compile(pattern, patternRuleIndex)
+}
+
+func (p *BaseParser) GetInputStream() IntStream {
+ return p.GetTokenStream()
+}
+
+func (p *BaseParser) SetInputStream(input TokenStream) {
+ p.SetTokenStream(input)
+}
+
+func (p *BaseParser) GetTokenStream() TokenStream {
+ return p.input
+}
+
+// Set the token stream and reset the parser.//
+func (p *BaseParser) SetTokenStream(input TokenStream) {
+ p.input = nil
+ p.reset()
+ p.input = input
+}
+
+// Match needs to return the current input symbol, which gets put
+// into the label for the associated token ref e.g., x=ID.
+//
+func (p *BaseParser) GetCurrentToken() Token {
+ return p.input.LT(1)
+}
+
+func (p *BaseParser) NotifyErrorListeners(msg string, offendingToken Token, err RecognitionException) {
+ if offendingToken == nil {
+ offendingToken = p.GetCurrentToken()
+ }
+ p._SyntaxErrors++
+ line := offendingToken.GetLine()
+ column := offendingToken.GetColumn()
+ listener := p.GetErrorListenerDispatch()
+ listener.SyntaxError(p, offendingToken, line, column, msg, err)
+}
+
+func (p *BaseParser) Consume() Token {
+ o := p.GetCurrentToken()
+ if o.GetTokenType() != TokenEOF {
+ p.GetInputStream().Consume()
+ }
+ hasListener := p.parseListeners != nil && len(p.parseListeners) > 0
+ if p.BuildParseTrees || hasListener {
+ if p.errHandler.inErrorRecoveryMode(p) {
+ node := p.ctx.AddErrorNode(o)
+ if p.parseListeners != nil {
+ for _, l := range p.parseListeners {
+ l.VisitErrorNode(node)
+ }
+ }
+
+ } else {
+ node := p.ctx.AddTokenNode(o)
+ if p.parseListeners != nil {
+ for _, l := range p.parseListeners {
+ l.VisitTerminal(node)
+ }
+ }
+ }
+ // node.invokingState = p.state
+ }
+
+ return o
+}
+
+func (p *BaseParser) addContextToParseTree() {
+ // add current context to parent if we have a parent
+ if p.ctx.GetParent() != nil {
+ p.ctx.GetParent().(ParserRuleContext).AddChild(p.ctx)
+ }
+}
+
+func (p *BaseParser) EnterRule(localctx ParserRuleContext, state, ruleIndex int) {
+ p.SetState(state)
+ p.ctx = localctx
+ p.ctx.SetStart(p.input.LT(1))
+ if p.BuildParseTrees {
+ p.addContextToParseTree()
+ }
+ if p.parseListeners != nil {
+ p.TriggerEnterRuleEvent()
+ }
+}
+
+func (p *BaseParser) ExitRule() {
+ p.ctx.SetStop(p.input.LT(-1))
+ // trigger event on ctx, before it reverts to parent
+ if p.parseListeners != nil {
+ p.TriggerExitRuleEvent()
+ }
+ p.SetState(p.ctx.GetInvokingState())
+ if p.ctx.GetParent() != nil {
+ p.ctx = p.ctx.GetParent().(ParserRuleContext)
+ } else {
+ p.ctx = nil
+ }
+}
+
+func (p *BaseParser) EnterOuterAlt(localctx ParserRuleContext, altNum int) {
+ localctx.SetAltNumber(altNum)
+ // if we have Newlocalctx, make sure we replace existing ctx
+ // that is previous child of parse tree
+ if p.BuildParseTrees && p.ctx != localctx {
+ if p.ctx.GetParent() != nil {
+ p.ctx.GetParent().(ParserRuleContext).RemoveLastChild()
+ p.ctx.GetParent().(ParserRuleContext).AddChild(localctx)
+ }
+ }
+ p.ctx = localctx
+}
+
+// Get the precedence level for the top-most precedence rule.
+//
+// @return The precedence level for the top-most precedence rule, or -1 if
+// the parser context is not nested within a precedence rule.
+
+func (p *BaseParser) GetPrecedence() int {
+ if len(p.precedenceStack) == 0 {
+ return -1
+ }
+
+ return p.precedenceStack[len(p.precedenceStack)-1]
+}
+
+func (p *BaseParser) EnterRecursionRule(localctx ParserRuleContext, state, ruleIndex, precedence int) {
+ p.SetState(state)
+ p.precedenceStack.Push(precedence)
+ p.ctx = localctx
+ p.ctx.SetStart(p.input.LT(1))
+ if p.parseListeners != nil {
+ p.TriggerEnterRuleEvent() // simulates rule entry for
+ // left-recursive rules
+ }
+}
+
+//
+// Like {@link //EnterRule} but for recursive rules.
+
+func (p *BaseParser) PushNewRecursionContext(localctx ParserRuleContext, state, ruleIndex int) {
+ previous := p.ctx
+ previous.SetParent(localctx)
+ previous.SetInvokingState(state)
+ previous.SetStop(p.input.LT(-1))
+
+ p.ctx = localctx
+ p.ctx.SetStart(previous.GetStart())
+ if p.BuildParseTrees {
+ p.ctx.AddChild(previous)
+ }
+ if p.parseListeners != nil {
+ p.TriggerEnterRuleEvent() // simulates rule entry for
+ // left-recursive rules
+ }
+}
+
+func (p *BaseParser) UnrollRecursionContexts(parentCtx ParserRuleContext) {
+ p.precedenceStack.Pop()
+ p.ctx.SetStop(p.input.LT(-1))
+ retCtx := p.ctx // save current ctx (return value)
+ // unroll so ctx is as it was before call to recursive method
+ if p.parseListeners != nil {
+ for p.ctx != parentCtx {
+ p.TriggerExitRuleEvent()
+ p.ctx = p.ctx.GetParent().(ParserRuleContext)
+ }
+ } else {
+ p.ctx = parentCtx
+ }
+ // hook into tree
+ retCtx.SetParent(parentCtx)
+ if p.BuildParseTrees && parentCtx != nil {
+ // add return ctx into invoking rule's tree
+ parentCtx.AddChild(retCtx)
+ }
+}
+
+func (p *BaseParser) GetInvokingContext(ruleIndex int) ParserRuleContext {
+ ctx := p.ctx
+ for ctx != nil {
+ if ctx.GetRuleIndex() == ruleIndex {
+ return ctx
+ }
+ ctx = ctx.GetParent().(ParserRuleContext)
+ }
+ return nil
+}
+
+func (p *BaseParser) Precpred(localctx RuleContext, precedence int) bool {
+ return precedence >= p.precedenceStack[len(p.precedenceStack)-1]
+}
+
+func (p *BaseParser) inContext(context ParserRuleContext) bool {
+ // TODO: useful in parser?
+ return false
+}
+
+//
+// Checks whether or not {@code symbol} can follow the current state in the
+// ATN. The behavior of p.method is equivalent to the following, but is
+// implemented such that the complete context-sensitive follow set does not
+// need to be explicitly constructed.
+//
+//
+//
+// @param symbol the symbol type to check
+// @return {@code true} if {@code symbol} can follow the current state in
+// the ATN, otherwise {@code false}.
+
+func (p *BaseParser) IsExpectedToken(symbol int) bool {
+ atn := p.Interpreter.atn
+ ctx := p.ctx
+ s := atn.states[p.state]
+ following := atn.NextTokens(s, nil)
+ if following.contains(symbol) {
+ return true
+ }
+ if !following.contains(TokenEpsilon) {
+ return false
+ }
+ for ctx != nil && ctx.GetInvokingState() >= 0 && following.contains(TokenEpsilon) {
+ invokingState := atn.states[ctx.GetInvokingState()]
+ rt := invokingState.GetTransitions()[0]
+ following = atn.NextTokens(rt.(*RuleTransition).followState, nil)
+ if following.contains(symbol) {
+ return true
+ }
+ ctx = ctx.GetParent().(ParserRuleContext)
+ }
+ if following.contains(TokenEpsilon) && symbol == TokenEOF {
+ return true
+ }
+
+ return false
+}
+
+// Computes the set of input symbols which could follow the current parser
+// state and context, as given by {@link //GetState} and {@link //GetContext},
+// respectively.
+//
+// @see ATN//getExpectedTokens(int, RuleContext)
+//
+func (p *BaseParser) GetExpectedTokens() *IntervalSet {
+ return p.Interpreter.atn.getExpectedTokens(p.state, p.ctx)
+}
+
+func (p *BaseParser) GetExpectedTokensWithinCurrentRule() *IntervalSet {
+ atn := p.Interpreter.atn
+ s := atn.states[p.state]
+ return atn.NextTokens(s, nil)
+}
+
+// Get a rule's index (i.e., {@code RULE_ruleName} field) or -1 if not found.//
+func (p *BaseParser) GetRuleIndex(ruleName string) int {
+ var ruleIndex, ok = p.GetRuleIndexMap()[ruleName]
+ if ok {
+ return ruleIndex
+ }
+
+ return -1
+}
+
+// Return List<String> of the rule names in your parser instance
+// leading up to a call to the current rule. You could override if
+// you want more details such as the file/line info of where
+// in the ATN a rule is invoked.
+//
+// this very useful for error messages.
+
+func (p *BaseParser) GetRuleInvocationStack(c ParserRuleContext) []string {
+ if c == nil {
+ c = p.ctx
+ }
+ stack := make([]string, 0)
+ for c != nil {
+ // compute what follows who invoked us
+ ruleIndex := c.GetRuleIndex()
+ if ruleIndex < 0 {
+ stack = append(stack, "n/a")
+ } else {
+ stack = append(stack, p.GetRuleNames()[ruleIndex])
+ }
+
+ vp := c.GetParent()
+
+ if vp == nil {
+ break
+ }
+
+ c = vp.(ParserRuleContext)
+ }
+ return stack
+}
+
+// For debugging and other purposes.//
+func (p *BaseParser) GetDFAStrings() string {
+ return fmt.Sprint(p.Interpreter.decisionToDFA)
+}
+
+// For debugging and other purposes.//
+func (p *BaseParser) DumpDFA() {
+ seenOne := false
+ for _, dfa := range p.Interpreter.decisionToDFA {
+ if dfa.numStates() > 0 {
+ if seenOne {
+ fmt.Println()
+ }
+ fmt.Println("Decision " + strconv.Itoa(dfa.decision) + ":")
+ fmt.Print(dfa.String(p.LiteralNames, p.SymbolicNames))
+ seenOne = true
+ }
+ }
+}
+
+func (p *BaseParser) GetSourceName() string {
+ return p.GrammarFileName
+}
+
+// During a parse is sometimes useful to listen in on the rule entry and exit
+// events as well as token Matches. p.is for quick and dirty debugging.
+//
+func (p *BaseParser) SetTrace(trace *TraceListener) {
+ if trace == nil {
+ p.RemoveParseListener(p.tracer)
+ p.tracer = nil
+ } else {
+ if p.tracer != nil {
+ p.RemoveParseListener(p.tracer)
+ }
+ p.tracer = NewTraceListener(p)
+ p.AddParseListener(p.tracer)
+ }
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser_atn_simulator.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser_atn_simulator.go
new file mode 100644
index 0000000000..c83e8137b6
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser_atn_simulator.go
@@ -0,0 +1,1473 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "strconv"
+ "strings"
+)
+
+var (
+ ParserATNSimulatorDebug = false
+ ParserATNSimulatorListATNDecisions = false
+ ParserATNSimulatorDFADebug = false
+ ParserATNSimulatorRetryDebug = false
+)
+
+type ParserATNSimulator struct {
+ *BaseATNSimulator
+
+ parser Parser
+ predictionMode int
+ input TokenStream
+ startIndex int
+ dfa *DFA
+ mergeCache *DoubleDict
+ outerContext ParserRuleContext
+}
+
+func NewParserATNSimulator(parser Parser, atn *ATN, decisionToDFA []*DFA, sharedContextCache *PredictionContextCache) *ParserATNSimulator {
+
+ p := new(ParserATNSimulator)
+
+ p.BaseATNSimulator = NewBaseATNSimulator(atn, sharedContextCache)
+
+ p.parser = parser
+ p.decisionToDFA = decisionToDFA
+ // SLL, LL, or LL + exact ambig detection?//
+ p.predictionMode = PredictionModeLL
+ // LAME globals to avoid parameters!!!!! I need these down deep in predTransition
+ p.input = nil
+ p.startIndex = 0
+ p.outerContext = nil
+ p.dfa = nil
+ // Each prediction operation uses a cache for merge of prediction contexts.
+ // Don't keep around as it wastes huge amounts of memory. DoubleKeyMap
+ // isn't Synchronized but we're ok since two threads shouldn't reuse same
+ // parser/atnsim object because it can only handle one input at a time.
+ // This maps graphs a and b to merged result c. (a,b)&rarrc. We can avoid
+ // the merge if we ever see a and b again. Note that (b,a)&rarrc should
+ // also be examined during cache lookup.
+ //
+ p.mergeCache = nil
+
+ return p
+}
+
+func (p *ParserATNSimulator) GetPredictionMode() int {
+ return p.predictionMode
+}
+
+func (p *ParserATNSimulator) SetPredictionMode(v int) {
+ p.predictionMode = v
+}
+
+func (p *ParserATNSimulator) reset() {
+}
+
+func (p *ParserATNSimulator) AdaptivePredict(input TokenStream, decision int, outerContext ParserRuleContext) int {
+ if ParserATNSimulatorDebug || ParserATNSimulatorListATNDecisions {
+ fmt.Println("AdaptivePredict decision " + strconv.Itoa(decision) +
+ " exec LA(1)==" + p.getLookaheadName(input) +
+ " line " + strconv.Itoa(input.LT(1).GetLine()) + ":" +
+ strconv.Itoa(input.LT(1).GetColumn()))
+ }
+
+ p.input = input
+ p.startIndex = input.Index()
+ p.outerContext = outerContext
+
+ dfa := p.decisionToDFA[decision]
+ p.dfa = dfa
+ m := input.Mark()
+ index := input.Index()
+
+ defer func() {
+ p.dfa = nil
+ p.mergeCache = nil // wack cache after each prediction
+ input.Seek(index)
+ input.Release(m)
+ }()
+
+ // Now we are certain to have a specific decision's DFA
+ // But, do we still need an initial state?
+ var s0 *DFAState
+ if dfa.getPrecedenceDfa() {
+ // the start state for a precedence DFA depends on the current
+ // parser precedence, and is provided by a DFA method.
+ s0 = dfa.getPrecedenceStartState(p.parser.GetPrecedence())
+ } else {
+ // the start state for a "regular" DFA is just s0
+ s0 = dfa.getS0()
+ }
+
+ if s0 == nil {
+ if outerContext == nil {
+ outerContext = RuleContextEmpty
+ }
+ if ParserATNSimulatorDebug || ParserATNSimulatorListATNDecisions {
+ fmt.Println("predictATN decision " + strconv.Itoa(dfa.decision) +
+ " exec LA(1)==" + p.getLookaheadName(input) +
+ ", outerContext=" + outerContext.String(p.parser.GetRuleNames(), nil))
+ }
+ // If p is not a precedence DFA, we check the ATN start state
+ // to determine if p ATN start state is the decision for the
+ // closure block that determines whether a precedence rule
+ // should continue or complete.
+
+ t2 := dfa.atnStartState
+ t, ok := t2.(*StarLoopEntryState)
+ if !dfa.getPrecedenceDfa() && ok {
+ if t.precedenceRuleDecision {
+ dfa.setPrecedenceDfa(true)
+ }
+ }
+ fullCtx := false
+ s0Closure := p.computeStartState(dfa.atnStartState, RuleContextEmpty, fullCtx)
+
+ if dfa.getPrecedenceDfa() {
+ // If p is a precedence DFA, we use applyPrecedenceFilter
+ // to convert the computed start state to a precedence start
+ // state. We then use DFA.setPrecedenceStartState to set the
+ // appropriate start state for the precedence level rather
+ // than simply setting DFA.s0.
+ //
+ s0Closure = p.applyPrecedenceFilter(s0Closure)
+ s0 = p.addDFAState(dfa, NewDFAState(-1, s0Closure))
+ dfa.setPrecedenceStartState(p.parser.GetPrecedence(), s0)
+ } else {
+ s0 = p.addDFAState(dfa, NewDFAState(-1, s0Closure))
+ dfa.setS0(s0)
+ }
+ }
+ alt := p.execATN(dfa, s0, input, index, outerContext)
+ if ParserATNSimulatorDebug {
+ fmt.Println("DFA after predictATN: " + dfa.String(p.parser.GetLiteralNames(), nil))
+ }
+ return alt
+
+}
+
+// Performs ATN simulation to compute a predicted alternative based
+// upon the remaining input, but also updates the DFA cache to avoid
+// having to traverse the ATN again for the same input sequence.
+
+// There are some key conditions we're looking for after computing a new
+// set of ATN configs (proposed DFA state):
+// if the set is empty, there is no viable alternative for current symbol
+// does the state uniquely predict an alternative?
+// does the state have a conflict that would prevent us from
+// putting it on the work list?
+
+// We also have some key operations to do:
+// add an edge from previous DFA state to potentially NewDFA state, D,
+// upon current symbol but only if adding to work list, which means in all
+// cases except no viable alternative (and possibly non-greedy decisions?)
+// collecting predicates and adding semantic context to DFA accept states
+// adding rule context to context-sensitive DFA accept states
+// consuming an input symbol
+// Reporting a conflict
+// Reporting an ambiguity
+// Reporting a context sensitivity
+// Reporting insufficient predicates
+
+// cover these cases:
+// dead end
+// single alt
+// single alt + preds
+// conflict
+// conflict + preds
+//
+func (p *ParserATNSimulator) execATN(dfa *DFA, s0 *DFAState, input TokenStream, startIndex int, outerContext ParserRuleContext) int {
+
+ if ParserATNSimulatorDebug || ParserATNSimulatorListATNDecisions {
+ fmt.Println("execATN decision " + strconv.Itoa(dfa.decision) +
+ " exec LA(1)==" + p.getLookaheadName(input) +
+ " line " + strconv.Itoa(input.LT(1).GetLine()) + ":" + strconv.Itoa(input.LT(1).GetColumn()))
+ }
+
+ previousD := s0
+
+ if ParserATNSimulatorDebug {
+ fmt.Println("s0 = " + s0.String())
+ }
+ t := input.LA(1)
+ for { // for more work
+ D := p.getExistingTargetState(previousD, t)
+ if D == nil {
+ D = p.computeTargetState(dfa, previousD, t)
+ }
+ if D == ATNSimulatorError {
+ // if any configs in previous dipped into outer context, that
+ // means that input up to t actually finished entry rule
+ // at least for SLL decision. Full LL doesn't dip into outer
+ // so don't need special case.
+ // We will get an error no matter what so delay until after
+ // decision better error message. Also, no reachable target
+ // ATN states in SLL implies LL will also get nowhere.
+ // If conflict in states that dip out, choose min since we
+ // will get error no matter what.
+ e := p.noViableAlt(input, outerContext, previousD.configs, startIndex)
+ input.Seek(startIndex)
+ alt := p.getSynValidOrSemInvalidAltThatFinishedDecisionEntryRule(previousD.configs, outerContext)
+ if alt != ATNInvalidAltNumber {
+ return alt
+ }
+
+ panic(e)
+ }
+ if D.requiresFullContext && p.predictionMode != PredictionModeSLL {
+ // IF PREDS, MIGHT RESOLVE TO SINGLE ALT => SLL (or syntax error)
+ conflictingAlts := D.configs.GetConflictingAlts()
+ if D.predicates != nil {
+ if ParserATNSimulatorDebug {
+ fmt.Println("DFA state has preds in DFA sim LL failover")
+ }
+ conflictIndex := input.Index()
+ if conflictIndex != startIndex {
+ input.Seek(startIndex)
+ }
+ conflictingAlts = p.evalSemanticContext(D.predicates, outerContext, true)
+ if conflictingAlts.length() == 1 {
+ if ParserATNSimulatorDebug {
+ fmt.Println("Full LL avoided")
+ }
+ return conflictingAlts.minValue()
+ }
+ if conflictIndex != startIndex {
+ // restore the index so Reporting the fallback to full
+ // context occurs with the index at the correct spot
+ input.Seek(conflictIndex)
+ }
+ }
+ if ParserATNSimulatorDFADebug {
+ fmt.Println("ctx sensitive state " + outerContext.String(nil, nil) + " in " + D.String())
+ }
+ fullCtx := true
+ s0Closure := p.computeStartState(dfa.atnStartState, outerContext, fullCtx)
+ p.ReportAttemptingFullContext(dfa, conflictingAlts, D.configs, startIndex, input.Index())
+ alt := p.execATNWithFullContext(dfa, D, s0Closure, input, startIndex, outerContext)
+ return alt
+ }
+ if D.isAcceptState {
+ if D.predicates == nil {
+ return D.prediction
+ }
+ stopIndex := input.Index()
+ input.Seek(startIndex)
+ alts := p.evalSemanticContext(D.predicates, outerContext, true)
+ if alts.length() == 0 {
+ panic(p.noViableAlt(input, outerContext, D.configs, startIndex))
+ } else if alts.length() == 1 {
+ return alts.minValue()
+ } else {
+ // Report ambiguity after predicate evaluation to make sure the correct set of ambig alts is Reported.
+ p.ReportAmbiguity(dfa, D, startIndex, stopIndex, false, alts, D.configs)
+ return alts.minValue()
+ }
+ }
+ previousD = D
+
+ if t != TokenEOF {
+ input.Consume()
+ t = input.LA(1)
+ }
+ }
+
+ panic("Should not have reached p state")
+}
+
+// Get an existing target state for an edge in the DFA. If the target state
+// for the edge has not yet been computed or is otherwise not available,
+// p method returns {@code nil}.
+//
+// @param previousD The current DFA state
+// @param t The next input symbol
+// @return The existing target DFA state for the given input symbol
+// {@code t}, or {@code nil} if the target state for p edge is not
+// already cached
+
+func (p *ParserATNSimulator) getExistingTargetState(previousD *DFAState, t int) *DFAState {
+ edges := previousD.getEdges()
+ if edges == nil {
+ return nil
+ }
+
+ return previousD.getIthEdge(t+1)
+}
+
+// Compute a target state for an edge in the DFA, and attempt to add the
+// computed state and corresponding edge to the DFA.
+//
+// @param dfa The DFA
+// @param previousD The current DFA state
+// @param t The next input symbol
+//
+// @return The computed target DFA state for the given input symbol
+// {@code t}. If {@code t} does not lead to a valid DFA state, p method
+// returns {@link //ERROR}.
+
+func (p *ParserATNSimulator) computeTargetState(dfa *DFA, previousD *DFAState, t int) *DFAState {
+ reach := p.computeReachSet(previousD.configs, t, false)
+
+ if reach == nil {
+ p.addDFAEdge(dfa, previousD, t, ATNSimulatorError)
+ return ATNSimulatorError
+ }
+ // create Newtarget state we'll add to DFA after it's complete
+ D := NewDFAState(-1, reach)
+
+ predictedAlt := p.getUniqueAlt(reach)
+
+ if ParserATNSimulatorDebug {
+ altSubSets := PredictionModegetConflictingAltSubsets(reach)
+ fmt.Println("SLL altSubSets=" + fmt.Sprint(altSubSets) +
+ ", previous=" + previousD.configs.String() +
+ ", configs=" + reach.String() +
+ ", predict=" + strconv.Itoa(predictedAlt) +
+ ", allSubsetsConflict=" +
+ fmt.Sprint(PredictionModeallSubsetsConflict(altSubSets)) +
+ ", conflictingAlts=" + p.getConflictingAlts(reach).String())
+ }
+ if predictedAlt != ATNInvalidAltNumber {
+ // NO CONFLICT, UNIQUELY PREDICTED ALT
+ D.isAcceptState = true
+ D.configs.SetUniqueAlt(predictedAlt)
+ D.setPrediction(predictedAlt)
+ } else if PredictionModehasSLLConflictTerminatingPrediction(p.predictionMode, reach) {
+ // MORE THAN ONE VIABLE ALTERNATIVE
+ D.configs.SetConflictingAlts(p.getConflictingAlts(reach))
+ D.requiresFullContext = true
+ // in SLL-only mode, we will stop at p state and return the minimum alt
+ D.isAcceptState = true
+ D.setPrediction(D.configs.GetConflictingAlts().minValue())
+ }
+ if D.isAcceptState && D.configs.HasSemanticContext() {
+ p.predicateDFAState(D, p.atn.getDecisionState(dfa.decision))
+ if D.predicates != nil {
+ D.setPrediction(ATNInvalidAltNumber)
+ }
+ }
+ // all adds to dfa are done after we've created full D state
+ D = p.addDFAEdge(dfa, previousD, t, D)
+ return D
+}
+
+func (p *ParserATNSimulator) predicateDFAState(dfaState *DFAState, decisionState DecisionState) {
+ // We need to test all predicates, even in DFA states that
+ // uniquely predict alternative.
+ nalts := len(decisionState.GetTransitions())
+ // Update DFA so reach becomes accept state with (predicate,alt)
+ // pairs if preds found for conflicting alts
+ altsToCollectPredsFrom := p.getConflictingAltsOrUniqueAlt(dfaState.configs)
+ altToPred := p.getPredsForAmbigAlts(altsToCollectPredsFrom, dfaState.configs, nalts)
+ if altToPred != nil {
+ dfaState.predicates = p.getPredicatePredictions(altsToCollectPredsFrom, altToPred)
+ dfaState.setPrediction(ATNInvalidAltNumber) // make sure we use preds
+ } else {
+ // There are preds in configs but they might go away
+ // when OR'd together like {p}? || NONE == NONE. If neither
+ // alt has preds, resolve to min alt
+ dfaState.setPrediction(altsToCollectPredsFrom.minValue())
+ }
+}
+
+// comes back with reach.uniqueAlt set to a valid alt
+func (p *ParserATNSimulator) execATNWithFullContext(dfa *DFA, D *DFAState, s0 ATNConfigSet, input TokenStream, startIndex int, outerContext ParserRuleContext) int {
+
+ if ParserATNSimulatorDebug || ParserATNSimulatorListATNDecisions {
+ fmt.Println("execATNWithFullContext " + s0.String())
+ }
+
+ fullCtx := true
+ foundExactAmbig := false
+ var reach ATNConfigSet
+ previous := s0
+ input.Seek(startIndex)
+ t := input.LA(1)
+ predictedAlt := -1
+
+ for { // for more work
+ reach = p.computeReachSet(previous, t, fullCtx)
+ if reach == nil {
+ // if any configs in previous dipped into outer context, that
+ // means that input up to t actually finished entry rule
+ // at least for LL decision. Full LL doesn't dip into outer
+ // so don't need special case.
+ // We will get an error no matter what so delay until after
+ // decision better error message. Also, no reachable target
+ // ATN states in SLL implies LL will also get nowhere.
+ // If conflict in states that dip out, choose min since we
+ // will get error no matter what.
+ e := p.noViableAlt(input, outerContext, previous, startIndex)
+ input.Seek(startIndex)
+ alt := p.getSynValidOrSemInvalidAltThatFinishedDecisionEntryRule(previous, outerContext)
+ if alt != ATNInvalidAltNumber {
+ return alt
+ }
+
+ panic(e)
+ }
+ altSubSets := PredictionModegetConflictingAltSubsets(reach)
+ if ParserATNSimulatorDebug {
+ fmt.Println("LL altSubSets=" + fmt.Sprint(altSubSets) + ", predict=" +
+ strconv.Itoa(PredictionModegetUniqueAlt(altSubSets)) + ", resolvesToJustOneViableAlt=" +
+ fmt.Sprint(PredictionModeresolvesToJustOneViableAlt(altSubSets)))
+ }
+ reach.SetUniqueAlt(p.getUniqueAlt(reach))
+ // unique prediction?
+ if reach.GetUniqueAlt() != ATNInvalidAltNumber {
+ predictedAlt = reach.GetUniqueAlt()
+ break
+ } else if p.predictionMode != PredictionModeLLExactAmbigDetection {
+ predictedAlt = PredictionModeresolvesToJustOneViableAlt(altSubSets)
+ if predictedAlt != ATNInvalidAltNumber {
+ break
+ }
+ } else {
+ // In exact ambiguity mode, we never try to terminate early.
+ // Just keeps scarfing until we know what the conflict is
+ if PredictionModeallSubsetsConflict(altSubSets) && PredictionModeallSubsetsEqual(altSubSets) {
+ foundExactAmbig = true
+ predictedAlt = PredictionModegetSingleViableAlt(altSubSets)
+ break
+ }
+ // else there are multiple non-conflicting subsets or
+ // we're not sure what the ambiguity is yet.
+ // So, keep going.
+ }
+ previous = reach
+ if t != TokenEOF {
+ input.Consume()
+ t = input.LA(1)
+ }
+ }
+ // If the configuration set uniquely predicts an alternative,
+ // without conflict, then we know that it's a full LL decision
+ // not SLL.
+ if reach.GetUniqueAlt() != ATNInvalidAltNumber {
+ p.ReportContextSensitivity(dfa, predictedAlt, reach, startIndex, input.Index())
+ return predictedAlt
+ }
+ // We do not check predicates here because we have checked them
+ // on-the-fly when doing full context prediction.
+
+ //
+ // In non-exact ambiguity detection mode, we might actually be able to
+ // detect an exact ambiguity, but I'm not going to spend the cycles
+ // needed to check. We only emit ambiguity warnings in exact ambiguity
+ // mode.
+ //
+ // For example, we might know that we have conflicting configurations.
+ // But, that does not mean that there is no way forward without a
+ // conflict. It's possible to have nonconflicting alt subsets as in:
+
+ // altSubSets=[{1, 2}, {1, 2}, {1}, {1, 2}]
+
+ // from
+ //
+ // [(17,1,[5 $]), (13,1,[5 10 $]), (21,1,[5 10 $]), (11,1,[$]),
+ // (13,2,[5 10 $]), (21,2,[5 10 $]), (11,2,[$])]
+ //
+ // In p case, (17,1,[5 $]) indicates there is some next sequence that
+ // would resolve p without conflict to alternative 1. Any other viable
+ // next sequence, however, is associated with a conflict. We stop
+ // looking for input because no amount of further lookahead will alter
+ // the fact that we should predict alternative 1. We just can't say for
+ // sure that there is an ambiguity without looking further.
+
+ p.ReportAmbiguity(dfa, D, startIndex, input.Index(), foundExactAmbig, nil, reach)
+
+ return predictedAlt
+}
+
+func (p *ParserATNSimulator) computeReachSet(closure ATNConfigSet, t int, fullCtx bool) ATNConfigSet {
+ if ParserATNSimulatorDebug {
+ fmt.Println("in computeReachSet, starting closure: " + closure.String())
+ }
+ if p.mergeCache == nil {
+ p.mergeCache = NewDoubleDict()
+ }
+ intermediate := NewBaseATNConfigSet(fullCtx)
+
+ // Configurations already in a rule stop state indicate reaching the end
+ // of the decision rule (local context) or end of the start rule (full
+ // context). Once reached, these configurations are never updated by a
+ // closure operation, so they are handled separately for the performance
+ // advantage of having a smaller intermediate set when calling closure.
+ //
+ // For full-context reach operations, separate handling is required to
+ // ensure that the alternative Matching the longest overall sequence is
+ // chosen when multiple such configurations can Match the input.
+
+ var SkippedStopStates []*BaseATNConfig
+
+ // First figure out where we can reach on input t
+ for _, c := range closure.GetItems() {
+ if ParserATNSimulatorDebug {
+ fmt.Println("testing " + p.GetTokenName(t) + " at " + c.String())
+ }
+
+ _, ok := c.GetState().(*RuleStopState)
+
+ if ok {
+ if fullCtx || t == TokenEOF {
+ if SkippedStopStates == nil {
+ SkippedStopStates = make([]*BaseATNConfig, 0)
+ }
+ SkippedStopStates = append(SkippedStopStates, c.(*BaseATNConfig))
+ if ParserATNSimulatorDebug {
+ fmt.Println("added " + c.String() + " to SkippedStopStates")
+ }
+ }
+ continue
+ }
+
+ for j := 0; j < len(c.GetState().GetTransitions()); j++ {
+ trans := c.GetState().GetTransitions()[j]
+ target := p.getReachableTarget(trans, t)
+ if target != nil {
+ cfg := NewBaseATNConfig4(c, target)
+ intermediate.Add(cfg, p.mergeCache)
+ if ParserATNSimulatorDebug {
+ fmt.Println("added " + cfg.String() + " to intermediate")
+ }
+ }
+ }
+ }
+ // Now figure out where the reach operation can take us...
+ var reach ATNConfigSet
+
+ // This block optimizes the reach operation for intermediate sets which
+ // trivially indicate a termination state for the overall
+ // AdaptivePredict operation.
+ //
+ // The conditions assume that intermediate
+ // contains all configurations relevant to the reach set, but p
+ // condition is not true when one or more configurations have been
+ // withheld in SkippedStopStates, or when the current symbol is EOF.
+ //
+ if SkippedStopStates == nil && t != TokenEOF {
+ if len(intermediate.configs) == 1 {
+ // Don't pursue the closure if there is just one state.
+ // It can only have one alternative just add to result
+ // Also don't pursue the closure if there is unique alternative
+ // among the configurations.
+ reach = intermediate
+ } else if p.getUniqueAlt(intermediate) != ATNInvalidAltNumber {
+ // Also don't pursue the closure if there is unique alternative
+ // among the configurations.
+ reach = intermediate
+ }
+ }
+ // If the reach set could not be trivially determined, perform a closure
+ // operation on the intermediate set to compute its initial value.
+ //
+ if reach == nil {
+ reach = NewBaseATNConfigSet(fullCtx)
+ closureBusy := NewSet(nil, nil)
+ treatEOFAsEpsilon := t == TokenEOF
+ for k := 0; k < len(intermediate.configs); k++ {
+ p.closure(intermediate.configs[k], reach, closureBusy, false, fullCtx, treatEOFAsEpsilon)
+ }
+ }
+ if t == TokenEOF {
+ // After consuming EOF no additional input is possible, so we are
+ // only interested in configurations which reached the end of the
+ // decision rule (local context) or end of the start rule (full
+ // context). Update reach to contain only these configurations. This
+ // handles both explicit EOF transitions in the grammar and implicit
+ // EOF transitions following the end of the decision or start rule.
+ //
+ // When reach==intermediate, no closure operation was performed. In
+ // p case, removeAllConfigsNotInRuleStopState needs to check for
+ // reachable rule stop states as well as configurations already in
+ // a rule stop state.
+ //
+ // This is handled before the configurations in SkippedStopStates,
+ // because any configurations potentially added from that list are
+ // already guaranteed to meet p condition whether or not it's
+ // required.
+ //
+ reach = p.removeAllConfigsNotInRuleStopState(reach, reach == intermediate)
+ }
+ // If SkippedStopStates!=nil, then it contains at least one
+ // configuration. For full-context reach operations, these
+ // configurations reached the end of the start rule, in which case we
+ // only add them back to reach if no configuration during the current
+ // closure operation reached such a state. This ensures AdaptivePredict
+ // chooses an alternative Matching the longest overall sequence when
+ // multiple alternatives are viable.
+ //
+ if SkippedStopStates != nil && ((!fullCtx) || (!PredictionModehasConfigInRuleStopState(reach))) {
+ for l := 0; l < len(SkippedStopStates); l++ {
+ reach.Add(SkippedStopStates[l], p.mergeCache)
+ }
+ }
+ if len(reach.GetItems()) == 0 {
+ return nil
+ }
+
+ return reach
+}
+
+//
+// Return a configuration set containing only the configurations from
+// {@code configs} which are in a {@link RuleStopState}. If all
+// configurations in {@code configs} are already in a rule stop state, p
+// method simply returns {@code configs}.
+//
+//
When {@code lookToEndOfRule} is true, p method uses
+// {@link ATN//NextTokens} for each configuration in {@code configs} which is
+// not already in a rule stop state to see if a rule stop state is reachable
+// from the configuration via epsilon-only transitions.
+//
+// @param configs the configuration set to update
+// @param lookToEndOfRule when true, p method checks for rule stop states
+// reachable by epsilon-only transitions from each configuration in
+// {@code configs}.
+//
+// @return {@code configs} if all configurations in {@code configs} are in a
+// rule stop state, otherwise return a Newconfiguration set containing only
+// the configurations from {@code configs} which are in a rule stop state
+//
+func (p *ParserATNSimulator) removeAllConfigsNotInRuleStopState(configs ATNConfigSet, lookToEndOfRule bool) ATNConfigSet {
+ if PredictionModeallConfigsInRuleStopStates(configs) {
+ return configs
+ }
+ result := NewBaseATNConfigSet(configs.FullContext())
+ for _, config := range configs.GetItems() {
+
+ _, ok := config.GetState().(*RuleStopState)
+
+ if ok {
+ result.Add(config, p.mergeCache)
+ continue
+ }
+ if lookToEndOfRule && config.GetState().GetEpsilonOnlyTransitions() {
+ NextTokens := p.atn.NextTokens(config.GetState(), nil)
+ if NextTokens.contains(TokenEpsilon) {
+ endOfRuleState := p.atn.ruleToStopState[config.GetState().GetRuleIndex()]
+ result.Add(NewBaseATNConfig4(config, endOfRuleState), p.mergeCache)
+ }
+ }
+ }
+ return result
+}
+
+func (p *ParserATNSimulator) computeStartState(a ATNState, ctx RuleContext, fullCtx bool) ATNConfigSet {
+ // always at least the implicit call to start rule
+ initialContext := predictionContextFromRuleContext(p.atn, ctx)
+ configs := NewBaseATNConfigSet(fullCtx)
+ for i := 0; i < len(a.GetTransitions()); i++ {
+ target := a.GetTransitions()[i].getTarget()
+ c := NewBaseATNConfig6(target, i+1, initialContext)
+ closureBusy := NewSet(nil, nil)
+ p.closure(c, configs, closureBusy, true, fullCtx, false)
+ }
+ return configs
+}
+
+//
+// This method transforms the start state computed by
+// {@link //computeStartState} to the special start state used by a
+// precedence DFA for a particular precedence value. The transformation
+// process applies the following changes to the start state's configuration
+// set.
+//
+//
+//
Evaluate the precedence predicates for each configuration using
+// {@link SemanticContext//evalPrecedence}.
+//
Remove all configurations which predict an alternative greater than
+// 1, for which another configuration that predicts alternative 1 is in the
+// same ATN state with the same prediction context. This transformation is
+// valid for the following reasons:
+//
+//
The closure block cannot contain any epsilon transitions which bypass
+// the body of the closure, so all states reachable via alternative 1 are
+// part of the precedence alternatives of the transformed left-recursive
+// rule.
+//
The "primary" portion of a left recursive rule cannot contain an
+// epsilon transition, so the only way an alternative other than 1 can exist
+// in a state that is also reachable via alternative 1 is by nesting calls
+// to the left-recursive rule, with the outer calls not being at the
+// preferred precedence level.
+//
+//
+//
+//
+//
+// The prediction context must be considered by p filter to address
+// situations like the following.
+//
+// If the above grammar, the ATN state immediately before the token
+// reference {@code 'a'} in {@code letterA} is reachable from the left edge
+// of both the primary and closure blocks of the left-recursive rule
+// {@code statement}. The prediction context associated with each of these
+// configurations distinguishes between them, and prevents the alternative
+// which stepped out to {@code prog} (and then back in to {@code statement}
+// from being eliminated by the filter.
+//
+//
+// @param configs The configuration set computed by
+// {@link //computeStartState} as the start state for the DFA.
+// @return The transformed configuration set representing the start state
+// for a precedence DFA at a particular precedence level (determined by
+// calling {@link Parser//getPrecedence}).
+//
+func (p *ParserATNSimulator) applyPrecedenceFilter(configs ATNConfigSet) ATNConfigSet {
+
+ statesFromAlt1 := make(map[int]PredictionContext)
+ configSet := NewBaseATNConfigSet(configs.FullContext())
+
+ for _, config := range configs.GetItems() {
+ // handle alt 1 first
+ if config.GetAlt() != 1 {
+ continue
+ }
+ updatedContext := config.GetSemanticContext().evalPrecedence(p.parser, p.outerContext)
+ if updatedContext == nil {
+ // the configuration was eliminated
+ continue
+ }
+ statesFromAlt1[config.GetState().GetStateNumber()] = config.GetContext()
+ if updatedContext != config.GetSemanticContext() {
+ configSet.Add(NewBaseATNConfig2(config, updatedContext), p.mergeCache)
+ } else {
+ configSet.Add(config, p.mergeCache)
+ }
+ }
+ for _, config := range configs.GetItems() {
+
+ if config.GetAlt() == 1 {
+ // already handled
+ continue
+ }
+ // In the future, p elimination step could be updated to also
+ // filter the prediction context for alternatives predicting alt>1
+ // (basically a graph subtraction algorithm).
+ if !config.getPrecedenceFilterSuppressed() {
+ context := statesFromAlt1[config.GetState().GetStateNumber()]
+ if context != nil && context.equals(config.GetContext()) {
+ // eliminated
+ continue
+ }
+ }
+ configSet.Add(config, p.mergeCache)
+ }
+ return configSet
+}
+
+func (p *ParserATNSimulator) getReachableTarget(trans Transition, ttype int) ATNState {
+ if trans.Matches(ttype, 0, p.atn.maxTokenType) {
+ return trans.getTarget()
+ }
+
+ return nil
+}
+
+func (p *ParserATNSimulator) getPredsForAmbigAlts(ambigAlts *BitSet, configs ATNConfigSet, nalts int) []SemanticContext {
+
+ altToPred := make([]SemanticContext, nalts+1)
+ for _, c := range configs.GetItems() {
+ if ambigAlts.contains(c.GetAlt()) {
+ altToPred[c.GetAlt()] = SemanticContextorContext(altToPred[c.GetAlt()], c.GetSemanticContext())
+ }
+ }
+ nPredAlts := 0
+ for i := 1; i < nalts+1; i++ {
+ pred := altToPred[i]
+ if pred == nil {
+ altToPred[i] = SemanticContextNone
+ } else if pred != SemanticContextNone {
+ nPredAlts++
+ }
+ }
+ // nonambig alts are nil in altToPred
+ if nPredAlts == 0 {
+ altToPred = nil
+ }
+ if ParserATNSimulatorDebug {
+ fmt.Println("getPredsForAmbigAlts result " + fmt.Sprint(altToPred))
+ }
+ return altToPred
+}
+
+func (p *ParserATNSimulator) getPredicatePredictions(ambigAlts *BitSet, altToPred []SemanticContext) []*PredPrediction {
+ pairs := make([]*PredPrediction, 0)
+ containsPredicate := false
+ for i := 1; i < len(altToPred); i++ {
+ pred := altToPred[i]
+ // unpredicated is indicated by SemanticContextNONE
+ if ambigAlts != nil && ambigAlts.contains(i) {
+ pairs = append(pairs, NewPredPrediction(pred, i))
+ }
+ if pred != SemanticContextNone {
+ containsPredicate = true
+ }
+ }
+ if !containsPredicate {
+ return nil
+ }
+ return pairs
+}
+
+//
+// This method is used to improve the localization of error messages by
+// choosing an alternative rather than panicing a
+// {@link NoViableAltException} in particular prediction scenarios where the
+// {@link //ERROR} state was reached during ATN simulation.
+//
+//
+// The default implementation of p method uses the following
+// algorithm to identify an ATN configuration which successfully parsed the
+// decision entry rule. Choosing such an alternative ensures that the
+// {@link ParserRuleContext} returned by the calling rule will be complete
+// and valid, and the syntax error will be Reported later at a more
+// localized location.
+//
+//
+//
If a syntactically valid path or paths reach the end of the decision rule and
+// they are semantically valid if predicated, return the min associated alt.
+//
Else, if a semantically invalid but syntactically valid path exist
+// or paths exist, return the minimum associated alt.
+//
+// In some scenarios, the algorithm described above could predict an
+// alternative which will result in a {@link FailedPredicateException} in
+// the parser. Specifically, p could occur if the only configuration
+// capable of successfully parsing to the end of the decision rule is
+// blocked by a semantic predicate. By choosing p alternative within
+// {@link //AdaptivePredict} instead of panicing a
+// {@link NoViableAltException}, the resulting
+// {@link FailedPredicateException} in the parser will identify the specific
+// predicate which is preventing the parser from successfully parsing the
+// decision rule, which helps developers identify and correct logic errors
+// in semantic predicates.
+//
+//
+// @param configs The ATN configurations which were valid immediately before
+// the {@link //ERROR} state was reached
+// @param outerContext The is the \gamma_0 initial parser context from the paper
+// or the parser stack at the instant before prediction commences.
+//
+// @return The value to return from {@link //AdaptivePredict}, or
+// {@link ATN//INVALID_ALT_NUMBER} if a suitable alternative was not
+// identified and {@link //AdaptivePredict} should Report an error instead.
+//
+func (p *ParserATNSimulator) getSynValidOrSemInvalidAltThatFinishedDecisionEntryRule(configs ATNConfigSet, outerContext ParserRuleContext) int {
+ cfgs := p.splitAccordingToSemanticValidity(configs, outerContext)
+ semValidConfigs := cfgs[0]
+ semInvalidConfigs := cfgs[1]
+ alt := p.GetAltThatFinishedDecisionEntryRule(semValidConfigs)
+ if alt != ATNInvalidAltNumber { // semantically/syntactically viable path exists
+ return alt
+ }
+ // Is there a syntactically valid path with a failed pred?
+ if len(semInvalidConfigs.GetItems()) > 0 {
+ alt = p.GetAltThatFinishedDecisionEntryRule(semInvalidConfigs)
+ if alt != ATNInvalidAltNumber { // syntactically viable path exists
+ return alt
+ }
+ }
+ return ATNInvalidAltNumber
+}
+
+func (p *ParserATNSimulator) GetAltThatFinishedDecisionEntryRule(configs ATNConfigSet) int {
+ alts := NewIntervalSet()
+
+ for _, c := range configs.GetItems() {
+ _, ok := c.GetState().(*RuleStopState)
+
+ if c.GetReachesIntoOuterContext() > 0 || (ok && c.GetContext().hasEmptyPath()) {
+ alts.addOne(c.GetAlt())
+ }
+ }
+ if alts.length() == 0 {
+ return ATNInvalidAltNumber
+ }
+
+ return alts.first()
+}
+
+// Walk the list of configurations and split them according to
+// those that have preds evaluating to true/false. If no pred, assume
+// true pred and include in succeeded set. Returns Pair of sets.
+//
+// Create a NewSet so as not to alter the incoming parameter.
+//
+// Assumption: the input stream has been restored to the starting point
+// prediction, which is where predicates need to evaluate.
+
+type ATNConfigSetPair struct {
+ item0, item1 ATNConfigSet
+}
+
+func (p *ParserATNSimulator) splitAccordingToSemanticValidity(configs ATNConfigSet, outerContext ParserRuleContext) []ATNConfigSet {
+ succeeded := NewBaseATNConfigSet(configs.FullContext())
+ failed := NewBaseATNConfigSet(configs.FullContext())
+
+ for _, c := range configs.GetItems() {
+ if c.GetSemanticContext() != SemanticContextNone {
+ predicateEvaluationResult := c.GetSemanticContext().evaluate(p.parser, outerContext)
+ if predicateEvaluationResult {
+ succeeded.Add(c, nil)
+ } else {
+ failed.Add(c, nil)
+ }
+ } else {
+ succeeded.Add(c, nil)
+ }
+ }
+ return []ATNConfigSet{succeeded, failed}
+}
+
+// Look through a list of predicate/alt pairs, returning alts for the
+// pairs that win. A {@code NONE} predicate indicates an alt containing an
+// unpredicated config which behaves as "always true." If !complete
+// then we stop at the first predicate that evaluates to true. This
+// includes pairs with nil predicates.
+//
+func (p *ParserATNSimulator) evalSemanticContext(predPredictions []*PredPrediction, outerContext ParserRuleContext, complete bool) *BitSet {
+ predictions := NewBitSet()
+ for i := 0; i < len(predPredictions); i++ {
+ pair := predPredictions[i]
+ if pair.pred == SemanticContextNone {
+ predictions.add(pair.alt)
+ if !complete {
+ break
+ }
+ continue
+ }
+
+ predicateEvaluationResult := pair.pred.evaluate(p.parser, outerContext)
+ if ParserATNSimulatorDebug || ParserATNSimulatorDFADebug {
+ fmt.Println("eval pred " + pair.String() + "=" + fmt.Sprint(predicateEvaluationResult))
+ }
+ if predicateEvaluationResult {
+ if ParserATNSimulatorDebug || ParserATNSimulatorDFADebug {
+ fmt.Println("PREDICT " + fmt.Sprint(pair.alt))
+ }
+ predictions.add(pair.alt)
+ if !complete {
+ break
+ }
+ }
+ }
+ return predictions
+}
+
+func (p *ParserATNSimulator) closure(config ATNConfig, configs ATNConfigSet, closureBusy *Set, collectPredicates, fullCtx, treatEOFAsEpsilon bool) {
+ initialDepth := 0
+ p.closureCheckingStopState(config, configs, closureBusy, collectPredicates,
+ fullCtx, initialDepth, treatEOFAsEpsilon)
+}
+
+func (p *ParserATNSimulator) closureCheckingStopState(config ATNConfig, configs ATNConfigSet, closureBusy *Set, collectPredicates, fullCtx bool, depth int, treatEOFAsEpsilon bool) {
+
+ if ParserATNSimulatorDebug {
+ fmt.Println("closure(" + config.String() + ")")
+ fmt.Println("configs(" + configs.String() + ")")
+ if config.GetReachesIntoOuterContext() > 50 {
+ panic("problem")
+ }
+ }
+
+ _, ok := config.GetState().(*RuleStopState)
+ if ok {
+ // We hit rule end. If we have context info, use it
+ // run thru all possible stack tops in ctx
+ if !config.GetContext().isEmpty() {
+ for i := 0; i < config.GetContext().length(); i++ {
+ if config.GetContext().getReturnState(i) == BasePredictionContextEmptyReturnState {
+ if fullCtx {
+ configs.Add(NewBaseATNConfig1(config, config.GetState(), BasePredictionContextEMPTY), p.mergeCache)
+ continue
+ } else {
+ // we have no context info, just chase follow links (if greedy)
+ if ParserATNSimulatorDebug {
+ fmt.Println("FALLING off rule " + p.getRuleName(config.GetState().GetRuleIndex()))
+ }
+ p.closureWork(config, configs, closureBusy, collectPredicates, fullCtx, depth, treatEOFAsEpsilon)
+ }
+ continue
+ }
+ returnState := p.atn.states[config.GetContext().getReturnState(i)]
+ newContext := config.GetContext().GetParent(i) // "pop" return state
+
+ c := NewBaseATNConfig5(returnState, config.GetAlt(), newContext, config.GetSemanticContext())
+ // While we have context to pop back from, we may have
+ // gotten that context AFTER having falling off a rule.
+ // Make sure we track that we are now out of context.
+ c.SetReachesIntoOuterContext(config.GetReachesIntoOuterContext())
+ p.closureCheckingStopState(c, configs, closureBusy, collectPredicates, fullCtx, depth-1, treatEOFAsEpsilon)
+ }
+ return
+ } else if fullCtx {
+ // reached end of start rule
+ configs.Add(config, p.mergeCache)
+ return
+ } else {
+ // else if we have no context info, just chase follow links (if greedy)
+ if ParserATNSimulatorDebug {
+ fmt.Println("FALLING off rule " + p.getRuleName(config.GetState().GetRuleIndex()))
+ }
+ }
+ }
+ p.closureWork(config, configs, closureBusy, collectPredicates, fullCtx, depth, treatEOFAsEpsilon)
+}
+
+// Do the actual work of walking epsilon edges//
+func (p *ParserATNSimulator) closureWork(config ATNConfig, configs ATNConfigSet, closureBusy *Set, collectPredicates, fullCtx bool, depth int, treatEOFAsEpsilon bool) {
+ state := config.GetState()
+ // optimization
+ if !state.GetEpsilonOnlyTransitions() {
+ configs.Add(config, p.mergeCache)
+ // make sure to not return here, because EOF transitions can act as
+ // both epsilon transitions and non-epsilon transitions.
+ }
+ for i := 0; i < len(state.GetTransitions()); i++ {
+ t := state.GetTransitions()[i]
+ _, ok := t.(*ActionTransition)
+ continueCollecting := collectPredicates && !ok
+ c := p.getEpsilonTarget(config, t, continueCollecting, depth == 0, fullCtx, treatEOFAsEpsilon)
+ if ci, ok := c.(*BaseATNConfig); ok && ci != nil {
+ if !t.getIsEpsilon() && closureBusy.add(c) != c {
+ // avoid infinite recursion for EOF* and EOF+
+ continue
+ }
+ newDepth := depth
+
+ if _, ok := config.GetState().(*RuleStopState); ok {
+
+ // target fell off end of rule mark resulting c as having dipped into outer context
+ // We can't get here if incoming config was rule stop and we had context
+ // track how far we dip into outer context. Might
+ // come in handy and we avoid evaluating context dependent
+ // preds if p is > 0.
+
+ if closureBusy.add(c) != c {
+ // avoid infinite recursion for right-recursive rules
+ continue
+ }
+
+ if p.dfa != nil && p.dfa.getPrecedenceDfa() {
+ if t.(*EpsilonTransition).outermostPrecedenceReturn == p.dfa.atnStartState.GetRuleIndex() {
+ c.setPrecedenceFilterSuppressed(true)
+ }
+ }
+
+ c.SetReachesIntoOuterContext(c.GetReachesIntoOuterContext() + 1)
+ configs.SetDipsIntoOuterContext(true) // TODO: can remove? only care when we add to set per middle of p method
+ newDepth--
+ if ParserATNSimulatorDebug {
+ fmt.Println("dips into outer ctx: " + c.String())
+ }
+ } else if _, ok := t.(*RuleTransition); ok {
+ // latch when newDepth goes negative - once we step out of the entry context we can't return
+ if newDepth >= 0 {
+ newDepth++
+ }
+ }
+ p.closureCheckingStopState(c, configs, closureBusy, continueCollecting, fullCtx, newDepth, treatEOFAsEpsilon)
+ }
+ }
+}
+
+func (p *ParserATNSimulator) getRuleName(index int) string {
+ if p.parser != nil && index >= 0 {
+ return p.parser.GetRuleNames()[index]
+ }
+
+ return ""
+}
+
+func (p *ParserATNSimulator) getEpsilonTarget(config ATNConfig, t Transition, collectPredicates, inContext, fullCtx, treatEOFAsEpsilon bool) ATNConfig {
+
+ switch t.getSerializationType() {
+ case TransitionRULE:
+ return p.ruleTransition(config, t.(*RuleTransition))
+ case TransitionPRECEDENCE:
+ return p.precedenceTransition(config, t.(*PrecedencePredicateTransition), collectPredicates, inContext, fullCtx)
+ case TransitionPREDICATE:
+ return p.predTransition(config, t.(*PredicateTransition), collectPredicates, inContext, fullCtx)
+ case TransitionACTION:
+ return p.actionTransition(config, t.(*ActionTransition))
+ case TransitionEPSILON:
+ return NewBaseATNConfig4(config, t.getTarget())
+ case TransitionATOM:
+ // EOF transitions act like epsilon transitions after the first EOF
+ // transition is traversed
+ if treatEOFAsEpsilon {
+ if t.Matches(TokenEOF, 0, 1) {
+ return NewBaseATNConfig4(config, t.getTarget())
+ }
+ }
+ return nil
+ case TransitionRANGE:
+ // EOF transitions act like epsilon transitions after the first EOF
+ // transition is traversed
+ if treatEOFAsEpsilon {
+ if t.Matches(TokenEOF, 0, 1) {
+ return NewBaseATNConfig4(config, t.getTarget())
+ }
+ }
+ return nil
+ case TransitionSET:
+ // EOF transitions act like epsilon transitions after the first EOF
+ // transition is traversed
+ if treatEOFAsEpsilon {
+ if t.Matches(TokenEOF, 0, 1) {
+ return NewBaseATNConfig4(config, t.getTarget())
+ }
+ }
+ return nil
+ default:
+ return nil
+ }
+}
+
+func (p *ParserATNSimulator) actionTransition(config ATNConfig, t *ActionTransition) *BaseATNConfig {
+ if ParserATNSimulatorDebug {
+ fmt.Println("ACTION edge " + strconv.Itoa(t.ruleIndex) + ":" + strconv.Itoa(t.actionIndex))
+ }
+ return NewBaseATNConfig4(config, t.getTarget())
+}
+
+func (p *ParserATNSimulator) precedenceTransition(config ATNConfig,
+ pt *PrecedencePredicateTransition, collectPredicates, inContext, fullCtx bool) *BaseATNConfig {
+
+ if ParserATNSimulatorDebug {
+ fmt.Println("PRED (collectPredicates=" + fmt.Sprint(collectPredicates) + ") " +
+ strconv.Itoa(pt.precedence) + ">=_p, ctx dependent=true")
+ if p.parser != nil {
+ fmt.Println("context surrounding pred is " + fmt.Sprint(p.parser.GetRuleInvocationStack(nil)))
+ }
+ }
+ var c *BaseATNConfig
+ if collectPredicates && inContext {
+ if fullCtx {
+ // In full context mode, we can evaluate predicates on-the-fly
+ // during closure, which dramatically reduces the size of
+ // the config sets. It also obviates the need to test predicates
+ // later during conflict resolution.
+ currentPosition := p.input.Index()
+ p.input.Seek(p.startIndex)
+ predSucceeds := pt.getPredicate().evaluate(p.parser, p.outerContext)
+ p.input.Seek(currentPosition)
+ if predSucceeds {
+ c = NewBaseATNConfig4(config, pt.getTarget()) // no pred context
+ }
+ } else {
+ newSemCtx := SemanticContextandContext(config.GetSemanticContext(), pt.getPredicate())
+ c = NewBaseATNConfig3(config, pt.getTarget(), newSemCtx)
+ }
+ } else {
+ c = NewBaseATNConfig4(config, pt.getTarget())
+ }
+ if ParserATNSimulatorDebug {
+ fmt.Println("config from pred transition=" + c.String())
+ }
+ return c
+}
+
+func (p *ParserATNSimulator) predTransition(config ATNConfig, pt *PredicateTransition, collectPredicates, inContext, fullCtx bool) *BaseATNConfig {
+
+ if ParserATNSimulatorDebug {
+ fmt.Println("PRED (collectPredicates=" + fmt.Sprint(collectPredicates) + ") " + strconv.Itoa(pt.ruleIndex) +
+ ":" + strconv.Itoa(pt.predIndex) + ", ctx dependent=" + fmt.Sprint(pt.isCtxDependent))
+ if p.parser != nil {
+ fmt.Println("context surrounding pred is " + fmt.Sprint(p.parser.GetRuleInvocationStack(nil)))
+ }
+ }
+ var c *BaseATNConfig
+ if collectPredicates && ((pt.isCtxDependent && inContext) || !pt.isCtxDependent) {
+ if fullCtx {
+ // In full context mode, we can evaluate predicates on-the-fly
+ // during closure, which dramatically reduces the size of
+ // the config sets. It also obviates the need to test predicates
+ // later during conflict resolution.
+ currentPosition := p.input.Index()
+ p.input.Seek(p.startIndex)
+ predSucceeds := pt.getPredicate().evaluate(p.parser, p.outerContext)
+ p.input.Seek(currentPosition)
+ if predSucceeds {
+ c = NewBaseATNConfig4(config, pt.getTarget()) // no pred context
+ }
+ } else {
+ newSemCtx := SemanticContextandContext(config.GetSemanticContext(), pt.getPredicate())
+ c = NewBaseATNConfig3(config, pt.getTarget(), newSemCtx)
+ }
+ } else {
+ c = NewBaseATNConfig4(config, pt.getTarget())
+ }
+ if ParserATNSimulatorDebug {
+ fmt.Println("config from pred transition=" + c.String())
+ }
+ return c
+}
+
+func (p *ParserATNSimulator) ruleTransition(config ATNConfig, t *RuleTransition) *BaseATNConfig {
+ if ParserATNSimulatorDebug {
+ fmt.Println("CALL rule " + p.getRuleName(t.getTarget().GetRuleIndex()) + ", ctx=" + config.GetContext().String())
+ }
+ returnState := t.followState
+ newContext := SingletonBasePredictionContextCreate(config.GetContext(), returnState.GetStateNumber())
+ return NewBaseATNConfig1(config, t.getTarget(), newContext)
+}
+
+func (p *ParserATNSimulator) getConflictingAlts(configs ATNConfigSet) *BitSet {
+ altsets := PredictionModegetConflictingAltSubsets(configs)
+ return PredictionModeGetAlts(altsets)
+}
+
+// Sam pointed out a problem with the previous definition, v3, of
+// ambiguous states. If we have another state associated with conflicting
+// alternatives, we should keep going. For example, the following grammar
+//
+// s : (ID | ID ID?) ''
+//
+// When the ATN simulation reaches the state before '', it has a DFA
+// state that looks like: [12|1|[], 6|2|[], 12|2|[]]. Naturally
+// 12|1|[] and 12|2|[] conflict, but we cannot stop processing p node
+// because alternative to has another way to continue, via [6|2|[]].
+// The key is that we have a single state that has config's only associated
+// with a single alternative, 2, and crucially the state transitions
+// among the configurations are all non-epsilon transitions. That means
+// we don't consider any conflicts that include alternative 2. So, we
+// ignore the conflict between alts 1 and 2. We ignore a set of
+// conflicting alts when there is an intersection with an alternative
+// associated with a single alt state in the state&rarrconfig-list map.
+//
+// It's also the case that we might have two conflicting configurations but
+// also a 3rd nonconflicting configuration for a different alternative:
+// [1|1|[], 1|2|[], 8|3|[]]. This can come about from grammar:
+//
+// a : A | A | A B
+//
+// After Matching input A, we reach the stop state for rule A, state 1.
+// State 8 is the state right before B. Clearly alternatives 1 and 2
+// conflict and no amount of further lookahead will separate the two.
+// However, alternative 3 will be able to continue and so we do not
+// stop working on p state. In the previous example, we're concerned
+// with states associated with the conflicting alternatives. Here alt
+// 3 is not associated with the conflicting configs, but since we can continue
+// looking for input reasonably, I don't declare the state done. We
+// ignore a set of conflicting alts when we have an alternative
+// that we still need to pursue.
+//
+
+func (p *ParserATNSimulator) getConflictingAltsOrUniqueAlt(configs ATNConfigSet) *BitSet {
+ var conflictingAlts *BitSet
+ if configs.GetUniqueAlt() != ATNInvalidAltNumber {
+ conflictingAlts = NewBitSet()
+ conflictingAlts.add(configs.GetUniqueAlt())
+ } else {
+ conflictingAlts = configs.GetConflictingAlts()
+ }
+ return conflictingAlts
+}
+
+func (p *ParserATNSimulator) GetTokenName(t int) string {
+ if t == TokenEOF {
+ return "EOF"
+ }
+
+ if p.parser != nil && p.parser.GetLiteralNames() != nil {
+ if t >= len(p.parser.GetLiteralNames()) {
+ fmt.Println(strconv.Itoa(t) + " ttype out of range: " + strings.Join(p.parser.GetLiteralNames(), ","))
+ // fmt.Println(p.parser.GetInputStream().(TokenStream).GetAllText()) // p seems incorrect
+ } else {
+ return p.parser.GetLiteralNames()[t] + "<" + strconv.Itoa(t) + ">"
+ }
+ }
+
+ return strconv.Itoa(t)
+}
+
+func (p *ParserATNSimulator) getLookaheadName(input TokenStream) string {
+ return p.GetTokenName(input.LA(1))
+}
+
+// Used for debugging in AdaptivePredict around execATN but I cut
+// it out for clarity now that alg. works well. We can leave p
+// "dead" code for a bit.
+//
+func (p *ParserATNSimulator) dumpDeadEndConfigs(nvae *NoViableAltException) {
+
+ panic("Not implemented")
+
+ // fmt.Println("dead end configs: ")
+ // var decs = nvae.deadEndConfigs
+ //
+ // for i:=0; i0) {
+ // var t = c.state.GetTransitions()[0]
+ // if t2, ok := t.(*AtomTransition); ok {
+ // trans = "Atom "+ p.GetTokenName(t2.label)
+ // } else if t3, ok := t.(SetTransition); ok {
+ // _, ok := t.(*NotSetTransition)
+ //
+ // var s string
+ // if (ok){
+ // s = "~"
+ // }
+ //
+ // trans = s + "Set " + t3.set
+ // }
+ // }
+ // fmt.Errorf(c.String(p.parser, true) + ":" + trans)
+ // }
+}
+
+func (p *ParserATNSimulator) noViableAlt(input TokenStream, outerContext ParserRuleContext, configs ATNConfigSet, startIndex int) *NoViableAltException {
+ return NewNoViableAltException(p.parser, input, input.Get(startIndex), input.LT(1), configs, outerContext)
+}
+
+func (p *ParserATNSimulator) getUniqueAlt(configs ATNConfigSet) int {
+ alt := ATNInvalidAltNumber
+ for _, c := range configs.GetItems() {
+ if alt == ATNInvalidAltNumber {
+ alt = c.GetAlt() // found first alt
+ } else if c.GetAlt() != alt {
+ return ATNInvalidAltNumber
+ }
+ }
+ return alt
+}
+
+//
+// Add an edge to the DFA, if possible. This method calls
+// {@link //addDFAState} to ensure the {@code to} state is present in the
+// DFA. If {@code from} is {@code nil}, or if {@code t} is outside the
+// range of edges that can be represented in the DFA tables, p method
+// returns without adding the edge to the DFA.
+//
+//
If {@code to} is {@code nil}, p method returns {@code nil}.
+// Otherwise, p method returns the {@link DFAState} returned by calling
+// {@link //addDFAState} for the {@code to} state.
+//
+// @param dfa The DFA
+// @param from The source state for the edge
+// @param t The input symbol
+// @param to The target state for the edge
+//
+// @return If {@code to} is {@code nil}, p method returns {@code nil}
+// otherwise p method returns the result of calling {@link //addDFAState}
+// on {@code to}
+//
+func (p *ParserATNSimulator) addDFAEdge(dfa *DFA, from *DFAState, t int, to *DFAState) *DFAState {
+ if ParserATNSimulatorDebug {
+ fmt.Println("EDGE " + from.String() + " -> " + to.String() + " upon " + p.GetTokenName(t))
+ }
+ if to == nil {
+ return nil
+ }
+ to = p.addDFAState(dfa, to) // used existing if possible not incoming
+ if from == nil || t < -1 || t > p.atn.maxTokenType {
+ return to
+ }
+ if from.getEdges() == nil {
+ from.setEdges(make([]*DFAState, p.atn.maxTokenType+1+1))
+ }
+ from.setIthEdge(t+1, to) // connect
+
+ if ParserATNSimulatorDebug {
+ var names []string
+ if p.parser != nil {
+ names = p.parser.GetLiteralNames()
+ }
+
+ fmt.Println("DFA=\n" + dfa.String(names, nil))
+ }
+ return to
+}
+
+//
+// Add state {@code D} to the DFA if it is not already present, and return
+// the actual instance stored in the DFA. If a state equivalent to {@code D}
+// is already in the DFA, the existing state is returned. Otherwise p
+// method returns {@code D} after adding it to the DFA.
+//
+//
If {@code D} is {@link //ERROR}, p method returns {@link //ERROR} and
+// does not change the DFA.
+//
+// @param dfa The dfa
+// @param D The DFA state to add
+// @return The state stored in the DFA. This will be either the existing
+// state if {@code D} is already in the DFA, or {@code D} itself if the
+// state was not already present.
+//
+func (p *ParserATNSimulator) addDFAState(dfa *DFA, d *DFAState) *DFAState {
+ if d == ATNSimulatorError {
+ return d
+ }
+ hash := d.hash()
+ existing, ok := dfa.getState(hash)
+ if ok {
+ return existing
+ }
+ d.stateNumber = dfa.numStates()
+ if !d.configs.ReadOnly() {
+ d.configs.OptimizeConfigs(p.BaseATNSimulator)
+ d.configs.SetReadOnly(true)
+ }
+ dfa.setState(hash, d)
+ if ParserATNSimulatorDebug {
+ fmt.Println("adding NewDFA state: " + d.String())
+ }
+ return d
+}
+
+func (p *ParserATNSimulator) ReportAttemptingFullContext(dfa *DFA, conflictingAlts *BitSet, configs ATNConfigSet, startIndex, stopIndex int) {
+ if ParserATNSimulatorDebug || ParserATNSimulatorRetryDebug {
+ interval := NewInterval(startIndex, stopIndex+1)
+ fmt.Println("ReportAttemptingFullContext decision=" + strconv.Itoa(dfa.decision) + ":" + configs.String() +
+ ", input=" + p.parser.GetTokenStream().GetTextFromInterval(interval))
+ }
+ if p.parser != nil {
+ p.parser.GetErrorListenerDispatch().ReportAttemptingFullContext(p.parser, dfa, startIndex, stopIndex, conflictingAlts, configs)
+ }
+}
+
+func (p *ParserATNSimulator) ReportContextSensitivity(dfa *DFA, prediction int, configs ATNConfigSet, startIndex, stopIndex int) {
+ if ParserATNSimulatorDebug || ParserATNSimulatorRetryDebug {
+ interval := NewInterval(startIndex, stopIndex+1)
+ fmt.Println("ReportContextSensitivity decision=" + strconv.Itoa(dfa.decision) + ":" + configs.String() +
+ ", input=" + p.parser.GetTokenStream().GetTextFromInterval(interval))
+ }
+ if p.parser != nil {
+ p.parser.GetErrorListenerDispatch().ReportContextSensitivity(p.parser, dfa, startIndex, stopIndex, prediction, configs)
+ }
+}
+
+// If context sensitive parsing, we know it's ambiguity not conflict//
+func (p *ParserATNSimulator) ReportAmbiguity(dfa *DFA, D *DFAState, startIndex, stopIndex int,
+ exact bool, ambigAlts *BitSet, configs ATNConfigSet) {
+ if ParserATNSimulatorDebug || ParserATNSimulatorRetryDebug {
+ interval := NewInterval(startIndex, stopIndex+1)
+ fmt.Println("ReportAmbiguity " + ambigAlts.String() + ":" + configs.String() +
+ ", input=" + p.parser.GetTokenStream().GetTextFromInterval(interval))
+ }
+ if p.parser != nil {
+ p.parser.GetErrorListenerDispatch().ReportAmbiguity(p.parser, dfa, startIndex, stopIndex, exact, ambigAlts, configs)
+ }
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser_rule_context.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser_rule_context.go
new file mode 100644
index 0000000000..49cd10c5ff
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/parser_rule_context.go
@@ -0,0 +1,362 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "reflect"
+ "strconv"
+)
+
+type ParserRuleContext interface {
+ RuleContext
+
+ SetException(RecognitionException)
+
+ AddTokenNode(token Token) *TerminalNodeImpl
+ AddErrorNode(badToken Token) *ErrorNodeImpl
+
+ EnterRule(listener ParseTreeListener)
+ ExitRule(listener ParseTreeListener)
+
+ SetStart(Token)
+ GetStart() Token
+
+ SetStop(Token)
+ GetStop() Token
+
+ AddChild(child RuleContext) RuleContext
+ RemoveLastChild()
+}
+
+type BaseParserRuleContext struct {
+ *BaseRuleContext
+
+ start, stop Token
+ exception RecognitionException
+ children []Tree
+}
+
+func NewBaseParserRuleContext(parent ParserRuleContext, invokingStateNumber int) *BaseParserRuleContext {
+ prc := new(BaseParserRuleContext)
+
+ prc.BaseRuleContext = NewBaseRuleContext(parent, invokingStateNumber)
+
+ prc.RuleIndex = -1
+ // * If we are debugging or building a parse tree for a Visitor,
+ // we need to track all of the tokens and rule invocations associated
+ // with prc rule's context. This is empty for parsing w/o tree constr.
+ // operation because we don't the need to track the details about
+ // how we parse prc rule.
+ // /
+ prc.children = nil
+ prc.start = nil
+ prc.stop = nil
+ // The exception that forced prc rule to return. If the rule successfully
+ // completed, prc is {@code nil}.
+ prc.exception = nil
+
+ return prc
+}
+
+func (prc *BaseParserRuleContext) SetException(e RecognitionException) {
+ prc.exception = e
+}
+
+func (prc *BaseParserRuleContext) GetChildren() []Tree {
+ return prc.children
+}
+
+func (prc *BaseParserRuleContext) CopyFrom(ctx *BaseParserRuleContext) {
+ // from RuleContext
+ prc.parentCtx = ctx.parentCtx
+ prc.invokingState = ctx.invokingState
+ prc.children = nil
+ prc.start = ctx.start
+ prc.stop = ctx.stop
+}
+
+func (prc *BaseParserRuleContext) GetText() string {
+ if prc.GetChildCount() == 0 {
+ return ""
+ }
+
+ var s string
+ for _, child := range prc.children {
+ s += child.(ParseTree).GetText()
+ }
+
+ return s
+}
+
+// Double dispatch methods for listeners
+func (prc *BaseParserRuleContext) EnterRule(listener ParseTreeListener) {
+}
+
+func (prc *BaseParserRuleContext) ExitRule(listener ParseTreeListener) {
+}
+
+// * Does not set parent link other add methods do that///
+func (prc *BaseParserRuleContext) addTerminalNodeChild(child TerminalNode) TerminalNode {
+ if prc.children == nil {
+ prc.children = make([]Tree, 0)
+ }
+ if child == nil {
+ panic("Child may not be null")
+ }
+ prc.children = append(prc.children, child)
+ return child
+}
+
+func (prc *BaseParserRuleContext) AddChild(child RuleContext) RuleContext {
+ if prc.children == nil {
+ prc.children = make([]Tree, 0)
+ }
+ if child == nil {
+ panic("Child may not be null")
+ }
+ prc.children = append(prc.children, child)
+ return child
+}
+
+// * Used by EnterOuterAlt to toss out a RuleContext previously added as
+// we entered a rule. If we have // label, we will need to remove
+// generic ruleContext object.
+// /
+func (prc *BaseParserRuleContext) RemoveLastChild() {
+ if prc.children != nil && len(prc.children) > 0 {
+ prc.children = prc.children[0 : len(prc.children)-1]
+ }
+}
+
+func (prc *BaseParserRuleContext) AddTokenNode(token Token) *TerminalNodeImpl {
+
+ node := NewTerminalNodeImpl(token)
+ prc.addTerminalNodeChild(node)
+ node.parentCtx = prc
+ return node
+
+}
+
+func (prc *BaseParserRuleContext) AddErrorNode(badToken Token) *ErrorNodeImpl {
+ node := NewErrorNodeImpl(badToken)
+ prc.addTerminalNodeChild(node)
+ node.parentCtx = prc
+ return node
+}
+
+func (prc *BaseParserRuleContext) GetChild(i int) Tree {
+ if prc.children != nil && len(prc.children) >= i {
+ return prc.children[i]
+ }
+
+ return nil
+}
+
+func (prc *BaseParserRuleContext) GetChildOfType(i int, childType reflect.Type) RuleContext {
+ if childType == nil {
+ return prc.GetChild(i).(RuleContext)
+ }
+
+ for j := 0; j < len(prc.children); j++ {
+ child := prc.children[j]
+ if reflect.TypeOf(child) == childType {
+ if i == 0 {
+ return child.(RuleContext)
+ }
+
+ i--
+ }
+ }
+
+ return nil
+}
+
+func (prc *BaseParserRuleContext) ToStringTree(ruleNames []string, recog Recognizer) string {
+ return TreesStringTree(prc, ruleNames, recog)
+}
+
+func (prc *BaseParserRuleContext) GetRuleContext() RuleContext {
+ return prc
+}
+
+func (prc *BaseParserRuleContext) Accept(visitor ParseTreeVisitor) interface{} {
+ return visitor.VisitChildren(prc)
+}
+
+func (prc *BaseParserRuleContext) SetStart(t Token) {
+ prc.start = t
+}
+
+func (prc *BaseParserRuleContext) GetStart() Token {
+ return prc.start
+}
+
+func (prc *BaseParserRuleContext) SetStop(t Token) {
+ prc.stop = t
+}
+
+func (prc *BaseParserRuleContext) GetStop() Token {
+ return prc.stop
+}
+
+func (prc *BaseParserRuleContext) GetToken(ttype int, i int) TerminalNode {
+
+ for j := 0; j < len(prc.children); j++ {
+ child := prc.children[j]
+ if c2, ok := child.(TerminalNode); ok {
+ if c2.GetSymbol().GetTokenType() == ttype {
+ if i == 0 {
+ return c2
+ }
+
+ i--
+ }
+ }
+ }
+ return nil
+}
+
+func (prc *BaseParserRuleContext) GetTokens(ttype int) []TerminalNode {
+ if prc.children == nil {
+ return make([]TerminalNode, 0)
+ }
+
+ tokens := make([]TerminalNode, 0)
+
+ for j := 0; j < len(prc.children); j++ {
+ child := prc.children[j]
+ if tchild, ok := child.(TerminalNode); ok {
+ if tchild.GetSymbol().GetTokenType() == ttype {
+ tokens = append(tokens, tchild)
+ }
+ }
+ }
+
+ return tokens
+}
+
+func (prc *BaseParserRuleContext) GetPayload() interface{} {
+ return prc
+}
+
+func (prc *BaseParserRuleContext) getChild(ctxType reflect.Type, i int) RuleContext {
+ if prc.children == nil || i < 0 || i >= len(prc.children) {
+ return nil
+ }
+
+ j := -1 // what element have we found with ctxType?
+ for _, o := range prc.children {
+
+ childType := reflect.TypeOf(o)
+
+ if childType.Implements(ctxType) {
+ j++
+ if j == i {
+ return o.(RuleContext)
+ }
+ }
+ }
+ return nil
+}
+
+// Go lacks generics, so it's not possible for us to return the child with the correct type, but we do
+// check for convertibility
+
+func (prc *BaseParserRuleContext) GetTypedRuleContext(ctxType reflect.Type, i int) RuleContext {
+ return prc.getChild(ctxType, i)
+}
+
+func (prc *BaseParserRuleContext) GetTypedRuleContexts(ctxType reflect.Type) []RuleContext {
+ if prc.children == nil {
+ return make([]RuleContext, 0)
+ }
+
+ contexts := make([]RuleContext, 0)
+
+ for _, child := range prc.children {
+ childType := reflect.TypeOf(child)
+
+ if childType.ConvertibleTo(ctxType) {
+ contexts = append(contexts, child.(RuleContext))
+ }
+ }
+ return contexts
+}
+
+func (prc *BaseParserRuleContext) GetChildCount() int {
+ if prc.children == nil {
+ return 0
+ }
+
+ return len(prc.children)
+}
+
+func (prc *BaseParserRuleContext) GetSourceInterval() *Interval {
+ if prc.start == nil || prc.stop == nil {
+ return TreeInvalidInterval
+ }
+
+ return NewInterval(prc.start.GetTokenIndex(), prc.stop.GetTokenIndex())
+}
+
+//need to manage circular dependencies, so export now
+
+// Print out a whole tree, not just a node, in LISP format
+// (root child1 .. childN). Print just a node if b is a leaf.
+//
+
+func (prc *BaseParserRuleContext) String(ruleNames []string, stop RuleContext) string {
+
+ var p ParserRuleContext = prc
+ s := "["
+ for p != nil && p != stop {
+ if ruleNames == nil {
+ if !p.IsEmpty() {
+ s += strconv.Itoa(p.GetInvokingState())
+ }
+ } else {
+ ri := p.GetRuleIndex()
+ var ruleName string
+ if ri >= 0 && ri < len(ruleNames) {
+ ruleName = ruleNames[ri]
+ } else {
+ ruleName = strconv.Itoa(ri)
+ }
+ s += ruleName
+ }
+ if p.GetParent() != nil && (ruleNames != nil || !p.GetParent().(ParserRuleContext).IsEmpty()) {
+ s += " "
+ }
+ pi := p.GetParent()
+ if pi != nil {
+ p = pi.(ParserRuleContext)
+ } else {
+ p = nil
+ }
+ }
+ s += "]"
+ return s
+}
+
+var RuleContextEmpty = NewBaseParserRuleContext(nil, -1)
+
+type InterpreterRuleContext interface {
+ ParserRuleContext
+}
+
+type BaseInterpreterRuleContext struct {
+ *BaseParserRuleContext
+}
+
+func NewBaseInterpreterRuleContext(parent BaseInterpreterRuleContext, invokingStateNumber, ruleIndex int) *BaseInterpreterRuleContext {
+
+ prc := new(BaseInterpreterRuleContext)
+
+ prc.BaseParserRuleContext = NewBaseParserRuleContext(parent, invokingStateNumber)
+
+ prc.RuleIndex = ruleIndex
+
+ return prc
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/prediction_context.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/prediction_context.go
new file mode 100644
index 0000000000..99acb333fa
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/prediction_context.go
@@ -0,0 +1,756 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "strconv"
+)
+
+// Represents {@code $} in local context prediction, which means wildcard.
+// {@code//+x =//}.
+// /
+const (
+ BasePredictionContextEmptyReturnState = 0x7FFFFFFF
+)
+
+// Represents {@code $} in an array in full context mode, when {@code $}
+// doesn't mean wildcard: {@code $ + x = [$,x]}. Here,
+// {@code $} = {@link //EmptyReturnState}.
+// /
+
+var (
+ BasePredictionContextglobalNodeCount = 1
+ BasePredictionContextid = BasePredictionContextglobalNodeCount
+)
+
+type PredictionContext interface {
+ hash() int
+ GetParent(int) PredictionContext
+ getReturnState(int) int
+ equals(PredictionContext) bool
+ length() int
+ isEmpty() bool
+ hasEmptyPath() bool
+ String() string
+}
+
+type BasePredictionContext struct {
+ cachedHash int
+}
+
+func NewBasePredictionContext(cachedHash int) *BasePredictionContext {
+ pc := new(BasePredictionContext)
+ pc.cachedHash = cachedHash
+
+ return pc
+}
+
+func (b *BasePredictionContext) isEmpty() bool {
+ return false
+}
+
+func calculateHash(parent PredictionContext, returnState int) int {
+ h := murmurInit(1)
+ h = murmurUpdate(h, parent.hash())
+ h = murmurUpdate(h, returnState)
+ return murmurFinish(h, 2)
+}
+
+func calculateEmptyHash() int {
+ h := murmurInit(1)
+ return murmurFinish(h, 0)
+}
+
+// Used to cache {@link BasePredictionContext} objects. Its used for the shared
+// context cash associated with contexts in DFA states. This cache
+// can be used for both lexers and parsers.
+
+type PredictionContextCache struct {
+ cache map[PredictionContext]PredictionContext
+}
+
+func NewPredictionContextCache() *PredictionContextCache {
+ t := new(PredictionContextCache)
+ t.cache = make(map[PredictionContext]PredictionContext)
+ return t
+}
+
+// Add a context to the cache and return it. If the context already exists,
+// return that one instead and do not add a Newcontext to the cache.
+// Protect shared cache from unsafe thread access.
+//
+func (p *PredictionContextCache) add(ctx PredictionContext) PredictionContext {
+ if ctx == BasePredictionContextEMPTY {
+ return BasePredictionContextEMPTY
+ }
+ existing := p.cache[ctx]
+ if existing != nil {
+ return existing
+ }
+ p.cache[ctx] = ctx
+ return ctx
+}
+
+func (p *PredictionContextCache) Get(ctx PredictionContext) PredictionContext {
+ return p.cache[ctx]
+}
+
+func (p *PredictionContextCache) length() int {
+ return len(p.cache)
+}
+
+type SingletonPredictionContext interface {
+ PredictionContext
+}
+
+type BaseSingletonPredictionContext struct {
+ *BasePredictionContext
+
+ parentCtx PredictionContext
+ returnState int
+}
+
+func NewBaseSingletonPredictionContext(parent PredictionContext, returnState int) *BaseSingletonPredictionContext {
+
+ s := new(BaseSingletonPredictionContext)
+ s.BasePredictionContext = NewBasePredictionContext(37)
+
+ if parent != nil {
+ s.cachedHash = calculateHash(parent, returnState)
+ } else {
+ s.cachedHash = calculateEmptyHash()
+ }
+
+ s.parentCtx = parent
+ s.returnState = returnState
+
+ return s
+}
+
+func SingletonBasePredictionContextCreate(parent PredictionContext, returnState int) PredictionContext {
+ if returnState == BasePredictionContextEmptyReturnState && parent == nil {
+ // someone can pass in the bits of an array ctx that mean $
+ return BasePredictionContextEMPTY
+ }
+
+ return NewBaseSingletonPredictionContext(parent, returnState)
+}
+
+func (b *BaseSingletonPredictionContext) length() int {
+ return 1
+}
+
+func (b *BaseSingletonPredictionContext) GetParent(index int) PredictionContext {
+ return b.parentCtx
+}
+
+func (b *BaseSingletonPredictionContext) getReturnState(index int) int {
+ return b.returnState
+}
+
+func (b *BaseSingletonPredictionContext) hasEmptyPath() bool {
+ return b.returnState == BasePredictionContextEmptyReturnState
+}
+
+func (b *BaseSingletonPredictionContext) equals(other PredictionContext) bool {
+ if b == other {
+ return true
+ } else if _, ok := other.(*BaseSingletonPredictionContext); !ok {
+ return false
+ } else if b.hash() != other.hash() {
+ return false // can't be same if hash is different
+ }
+
+ otherP := other.(*BaseSingletonPredictionContext)
+
+ if b.returnState != other.getReturnState(0) {
+ return false
+ } else if b.parentCtx == nil {
+ return otherP.parentCtx == nil
+ }
+
+ return b.parentCtx.equals(otherP.parentCtx)
+}
+
+func (b *BaseSingletonPredictionContext) hash() int {
+ h := murmurInit(1)
+
+ if b.parentCtx == nil {
+ return murmurFinish(h, 0)
+ }
+
+ h = murmurUpdate(h, b.parentCtx.hash())
+ h = murmurUpdate(h, b.returnState)
+ return murmurFinish(h, 2)
+}
+
+func (b *BaseSingletonPredictionContext) String() string {
+ var up string
+
+ if b.parentCtx == nil {
+ up = ""
+ } else {
+ up = b.parentCtx.String()
+ }
+
+ if len(up) == 0 {
+ if b.returnState == BasePredictionContextEmptyReturnState {
+ return "$"
+ }
+
+ return strconv.Itoa(b.returnState)
+ }
+
+ return strconv.Itoa(b.returnState) + " " + up
+}
+
+var BasePredictionContextEMPTY = NewEmptyPredictionContext()
+
+type EmptyPredictionContext struct {
+ *BaseSingletonPredictionContext
+}
+
+func NewEmptyPredictionContext() *EmptyPredictionContext {
+
+ p := new(EmptyPredictionContext)
+
+ p.BaseSingletonPredictionContext = NewBaseSingletonPredictionContext(nil, BasePredictionContextEmptyReturnState)
+
+ return p
+}
+
+func (e *EmptyPredictionContext) isEmpty() bool {
+ return true
+}
+
+func (e *EmptyPredictionContext) GetParent(index int) PredictionContext {
+ return nil
+}
+
+func (e *EmptyPredictionContext) getReturnState(index int) int {
+ return e.returnState
+}
+
+func (e *EmptyPredictionContext) equals(other PredictionContext) bool {
+ return e == other
+}
+
+func (e *EmptyPredictionContext) String() string {
+ return "$"
+}
+
+type ArrayPredictionContext struct {
+ *BasePredictionContext
+
+ parents []PredictionContext
+ returnStates []int
+}
+
+func NewArrayPredictionContext(parents []PredictionContext, returnStates []int) *ArrayPredictionContext {
+ // Parent can be nil only if full ctx mode and we make an array
+ // from {@link //EMPTY} and non-empty. We merge {@link //EMPTY} by using
+ // nil parent and
+ // returnState == {@link //EmptyReturnState}.
+
+ c := new(ArrayPredictionContext)
+ c.BasePredictionContext = NewBasePredictionContext(37)
+
+ for i := range parents {
+ c.cachedHash += calculateHash(parents[i], returnStates[i])
+ }
+
+ c.parents = parents
+ c.returnStates = returnStates
+
+ return c
+}
+
+func (a *ArrayPredictionContext) GetReturnStates() []int {
+ return a.returnStates
+}
+
+func (a *ArrayPredictionContext) hasEmptyPath() bool {
+ return a.getReturnState(a.length()-1) == BasePredictionContextEmptyReturnState
+}
+
+func (a *ArrayPredictionContext) isEmpty() bool {
+ // since EmptyReturnState can only appear in the last position, we
+ // don't need to verify that size==1
+ return a.returnStates[0] == BasePredictionContextEmptyReturnState
+}
+
+func (a *ArrayPredictionContext) length() int {
+ return len(a.returnStates)
+}
+
+func (a *ArrayPredictionContext) GetParent(index int) PredictionContext {
+ return a.parents[index]
+}
+
+func (a *ArrayPredictionContext) getReturnState(index int) int {
+ return a.returnStates[index]
+}
+
+func (a *ArrayPredictionContext) equals(other PredictionContext) bool {
+ if _, ok := other.(*ArrayPredictionContext); !ok {
+ return false
+ } else if a.cachedHash != other.hash() {
+ return false // can't be same if hash is different
+ } else {
+ otherP := other.(*ArrayPredictionContext)
+ return &a.returnStates == &otherP.returnStates && &a.parents == &otherP.parents
+ }
+}
+
+func (a *ArrayPredictionContext) hash() int {
+ h := murmurInit(1)
+
+ for _, p := range a.parents {
+ h = murmurUpdate(h, p.hash())
+ }
+
+ for _, r := range a.returnStates {
+ h = murmurUpdate(h, r)
+ }
+
+ return murmurFinish(h, 2 * len(a.parents))
+}
+
+func (a *ArrayPredictionContext) String() string {
+ if a.isEmpty() {
+ return "[]"
+ }
+
+ s := "["
+ for i := 0; i < len(a.returnStates); i++ {
+ if i > 0 {
+ s = s + ", "
+ }
+ if a.returnStates[i] == BasePredictionContextEmptyReturnState {
+ s = s + "$"
+ continue
+ }
+ s = s + strconv.Itoa(a.returnStates[i])
+ if a.parents[i] != nil {
+ s = s + " " + a.parents[i].String()
+ } else {
+ s = s + "nil"
+ }
+ }
+
+ return s + "]"
+}
+
+// Convert a {@link RuleContext} tree to a {@link BasePredictionContext} graph.
+// Return {@link //EMPTY} if {@code outerContext} is empty or nil.
+// /
+func predictionContextFromRuleContext(a *ATN, outerContext RuleContext) PredictionContext {
+ if outerContext == nil {
+ outerContext = RuleContextEmpty
+ }
+ // if we are in RuleContext of start rule, s, then BasePredictionContext
+ // is EMPTY. Nobody called us. (if we are empty, return empty)
+ if outerContext.GetParent() == nil || outerContext == RuleContextEmpty {
+ return BasePredictionContextEMPTY
+ }
+ // If we have a parent, convert it to a BasePredictionContext graph
+ parent := predictionContextFromRuleContext(a, outerContext.GetParent().(RuleContext))
+ state := a.states[outerContext.GetInvokingState()]
+ transition := state.GetTransitions()[0]
+
+ return SingletonBasePredictionContextCreate(parent, transition.(*RuleTransition).followState.GetStateNumber())
+}
+
+func merge(a, b PredictionContext, rootIsWildcard bool, mergeCache *DoubleDict) PredictionContext {
+ // share same graph if both same
+ if a == b {
+ return a
+ }
+
+ ac, ok1 := a.(*BaseSingletonPredictionContext)
+ bc, ok2 := b.(*BaseSingletonPredictionContext)
+
+ if ok1 && ok2 {
+ return mergeSingletons(ac, bc, rootIsWildcard, mergeCache)
+ }
+ // At least one of a or b is array
+ // If one is $ and rootIsWildcard, return $ as// wildcard
+ if rootIsWildcard {
+ if _, ok := a.(*EmptyPredictionContext); ok {
+ return a
+ }
+ if _, ok := b.(*EmptyPredictionContext); ok {
+ return b
+ }
+ }
+ // convert singleton so both are arrays to normalize
+ if _, ok := a.(*BaseSingletonPredictionContext); ok {
+ a = NewArrayPredictionContext([]PredictionContext{a.GetParent(0)}, []int{a.getReturnState(0)})
+ }
+ if _, ok := b.(*BaseSingletonPredictionContext); ok {
+ b = NewArrayPredictionContext([]PredictionContext{b.GetParent(0)}, []int{b.getReturnState(0)})
+ }
+ return mergeArrays(a.(*ArrayPredictionContext), b.(*ArrayPredictionContext), rootIsWildcard, mergeCache)
+}
+
+//
+// Merge two {@link SingletonBasePredictionContext} instances.
+//
+//
Stack tops equal, parents merge is same return left graph.
+//
+//
+//
Same stack top, parents differ merge parents giving array node, then
+// remainders of those graphs. A Newroot node is created to point to the
+// merged parents.
+//
+//
+//
Different stack tops pointing to same parent. Make array node for the
+// root where both element in the root point to the same (original)
+// parent.
+//
+//
+//
Different stack tops pointing to different parents. Make array node for
+// the root where each element points to the corresponding original
+// parent.
+//
+//
+// @param a the first {@link SingletonBasePredictionContext}
+// @param b the second {@link SingletonBasePredictionContext}
+// @param rootIsWildcard {@code true} if this is a local-context merge,
+// otherwise false to indicate a full-context merge
+// @param mergeCache
+// /
+func mergeSingletons(a, b *BaseSingletonPredictionContext, rootIsWildcard bool, mergeCache *DoubleDict) PredictionContext {
+ if mergeCache != nil {
+ previous := mergeCache.Get(a.hash(), b.hash())
+ if previous != nil {
+ return previous.(PredictionContext)
+ }
+ previous = mergeCache.Get(b.hash(), a.hash())
+ if previous != nil {
+ return previous.(PredictionContext)
+ }
+ }
+
+ rootMerge := mergeRoot(a, b, rootIsWildcard)
+ if rootMerge != nil {
+ if mergeCache != nil {
+ mergeCache.set(a.hash(), b.hash(), rootMerge)
+ }
+ return rootMerge
+ }
+ if a.returnState == b.returnState {
+ parent := merge(a.parentCtx, b.parentCtx, rootIsWildcard, mergeCache)
+ // if parent is same as existing a or b parent or reduced to a parent,
+ // return it
+ if parent == a.parentCtx {
+ return a // ax + bx = ax, if a=b
+ }
+ if parent == b.parentCtx {
+ return b // ax + bx = bx, if a=b
+ }
+ // else: ax + ay = a'[x,y]
+ // merge parents x and y, giving array node with x,y then remainders
+ // of those graphs. dup a, a' points at merged array
+ // Newjoined parent so create Newsingleton pointing to it, a'
+ spc := SingletonBasePredictionContextCreate(parent, a.returnState)
+ if mergeCache != nil {
+ mergeCache.set(a.hash(), b.hash(), spc)
+ }
+ return spc
+ }
+ // a != b payloads differ
+ // see if we can collapse parents due to $+x parents if local ctx
+ var singleParent PredictionContext
+ if a == b || (a.parentCtx != nil && a.parentCtx == b.parentCtx) { // ax +
+ // bx =
+ // [a,b]x
+ singleParent = a.parentCtx
+ }
+ if singleParent != nil { // parents are same
+ // sort payloads and use same parent
+ payloads := []int{a.returnState, b.returnState}
+ if a.returnState > b.returnState {
+ payloads[0] = b.returnState
+ payloads[1] = a.returnState
+ }
+ parents := []PredictionContext{singleParent, singleParent}
+ apc := NewArrayPredictionContext(parents, payloads)
+ if mergeCache != nil {
+ mergeCache.set(a.hash(), b.hash(), apc)
+ }
+ return apc
+ }
+ // parents differ and can't merge them. Just pack together
+ // into array can't merge.
+ // ax + by = [ax,by]
+ payloads := []int{a.returnState, b.returnState}
+ parents := []PredictionContext{a.parentCtx, b.parentCtx}
+ if a.returnState > b.returnState { // sort by payload
+ payloads[0] = b.returnState
+ payloads[1] = a.returnState
+ parents = []PredictionContext{b.parentCtx, a.parentCtx}
+ }
+ apc := NewArrayPredictionContext(parents, payloads)
+ if mergeCache != nil {
+ mergeCache.set(a.hash(), b.hash(), apc)
+ }
+ return apc
+}
+
+//
+// Handle case where at least one of {@code a} or {@code b} is
+// {@link //EMPTY}. In the following diagrams, the symbol {@code $} is used
+// to represent {@link //EMPTY}.
+//
+//
Local-Context Merges
+//
+//
These local-context merge operations are used when {@code rootIsWildcard}
+// is true.
+//
+//
{@link //EMPTY} is superset of any graph return {@link //EMPTY}.
+//
+//
+//
{@link //EMPTY} and anything is {@code //EMPTY}, so merged parent is
+// {@code //EMPTY} return left graph.
+//
+//
+//
Special case of last merge if local context.
+//
+//
+//
Full-Context Merges
+//
+//
These full-context merge operations are used when {@code rootIsWildcard}
+// is false.
+//
+//
+//
+//
Must keep all contexts {@link //EMPTY} in array is a special value (and
+// nil parent).
+//
+//
+//
+//
+// @param a the first {@link SingletonBasePredictionContext}
+// @param b the second {@link SingletonBasePredictionContext}
+// @param rootIsWildcard {@code true} if this is a local-context merge,
+// otherwise false to indicate a full-context merge
+// /
+func mergeRoot(a, b SingletonPredictionContext, rootIsWildcard bool) PredictionContext {
+ if rootIsWildcard {
+ if a == BasePredictionContextEMPTY {
+ return BasePredictionContextEMPTY // // + b =//
+ }
+ if b == BasePredictionContextEMPTY {
+ return BasePredictionContextEMPTY // a +// =//
+ }
+ } else {
+ if a == BasePredictionContextEMPTY && b == BasePredictionContextEMPTY {
+ return BasePredictionContextEMPTY // $ + $ = $
+ } else if a == BasePredictionContextEMPTY { // $ + x = [$,x]
+ payloads := []int{b.getReturnState(-1), BasePredictionContextEmptyReturnState}
+ parents := []PredictionContext{b.GetParent(-1), nil}
+ return NewArrayPredictionContext(parents, payloads)
+ } else if b == BasePredictionContextEMPTY { // x + $ = [$,x] ($ is always first if present)
+ payloads := []int{a.getReturnState(-1), BasePredictionContextEmptyReturnState}
+ parents := []PredictionContext{a.GetParent(-1), nil}
+ return NewArrayPredictionContext(parents, payloads)
+ }
+ }
+ return nil
+}
+
+//
+// Merge two {@link ArrayBasePredictionContext} instances.
+//
+//
Different tops, different parents.
+//
+//
+//
Shared top, same parents.
+//
+//
+//
Shared top, different parents.
+//
+//
+//
Shared top, all shared parents.
+//
+//
+//
Equal tops, merge parents and reduce top to
+// {@link SingletonBasePredictionContext}.
+//
+// /
+func mergeArrays(a, b *ArrayPredictionContext, rootIsWildcard bool, mergeCache *DoubleDict) PredictionContext {
+ if mergeCache != nil {
+ previous := mergeCache.Get(a.hash(), b.hash())
+ if previous != nil {
+ return previous.(PredictionContext)
+ }
+ previous = mergeCache.Get(b.hash(), a.hash())
+ if previous != nil {
+ return previous.(PredictionContext)
+ }
+ }
+ // merge sorted payloads a + b => M
+ i := 0 // walks a
+ j := 0 // walks b
+ k := 0 // walks target M array
+
+ mergedReturnStates := make([]int, len(a.returnStates)+len(b.returnStates))
+ mergedParents := make([]PredictionContext, len(a.returnStates)+len(b.returnStates))
+ // walk and merge to yield mergedParents, mergedReturnStates
+ for i < len(a.returnStates) && j < len(b.returnStates) {
+ aParent := a.parents[i]
+ bParent := b.parents[j]
+ if a.returnStates[i] == b.returnStates[j] {
+ // same payload (stack tops are equal), must yield merged singleton
+ payload := a.returnStates[i]
+ // $+$ = $
+ bothDollars := payload == BasePredictionContextEmptyReturnState && aParent == nil && bParent == nil
+ axAX := (aParent != nil && bParent != nil && aParent == bParent) // ax+ax
+ // ->
+ // ax
+ if bothDollars || axAX {
+ mergedParents[k] = aParent // choose left
+ mergedReturnStates[k] = payload
+ } else { // ax+ay -> a'[x,y]
+ mergedParent := merge(aParent, bParent, rootIsWildcard, mergeCache)
+ mergedParents[k] = mergedParent
+ mergedReturnStates[k] = payload
+ }
+ i++ // hop over left one as usual
+ j++ // but also Skip one in right side since we merge
+ } else if a.returnStates[i] < b.returnStates[j] { // copy a[i] to M
+ mergedParents[k] = aParent
+ mergedReturnStates[k] = a.returnStates[i]
+ i++
+ } else { // b > a, copy b[j] to M
+ mergedParents[k] = bParent
+ mergedReturnStates[k] = b.returnStates[j]
+ j++
+ }
+ k++
+ }
+ // copy over any payloads remaining in either array
+ if i < len(a.returnStates) {
+ for p := i; p < len(a.returnStates); p++ {
+ mergedParents[k] = a.parents[p]
+ mergedReturnStates[k] = a.returnStates[p]
+ k++
+ }
+ } else {
+ for p := j; p < len(b.returnStates); p++ {
+ mergedParents[k] = b.parents[p]
+ mergedReturnStates[k] = b.returnStates[p]
+ k++
+ }
+ }
+ // trim merged if we combined a few that had same stack tops
+ if k < len(mergedParents) { // write index < last position trim
+ if k == 1 { // for just one merged element, return singleton top
+ pc := SingletonBasePredictionContextCreate(mergedParents[0], mergedReturnStates[0])
+ if mergeCache != nil {
+ mergeCache.set(a.hash(), b.hash(), pc)
+ }
+ return pc
+ }
+ mergedParents = mergedParents[0:k]
+ mergedReturnStates = mergedReturnStates[0:k]
+ }
+
+ M := NewArrayPredictionContext(mergedParents, mergedReturnStates)
+
+ // if we created same array as a or b, return that instead
+ // TODO: track whether this is possible above during merge sort for speed
+ if M == a {
+ if mergeCache != nil {
+ mergeCache.set(a.hash(), b.hash(), a)
+ }
+ return a
+ }
+ if M == b {
+ if mergeCache != nil {
+ mergeCache.set(a.hash(), b.hash(), b)
+ }
+ return b
+ }
+ combineCommonParents(mergedParents)
+
+ if mergeCache != nil {
+ mergeCache.set(a.hash(), b.hash(), M)
+ }
+ return M
+}
+
+//
+// Make pass over all M {@code parents} merge any {@code equals()}
+// ones.
+// /
+func combineCommonParents(parents []PredictionContext) {
+ uniqueParents := make(map[PredictionContext]PredictionContext)
+
+ for p := 0; p < len(parents); p++ {
+ parent := parents[p]
+ if uniqueParents[parent] == nil {
+ uniqueParents[parent] = parent
+ }
+ }
+ for q := 0; q < len(parents); q++ {
+ parents[q] = uniqueParents[parents[q]]
+ }
+}
+
+func getCachedBasePredictionContext(context PredictionContext, contextCache *PredictionContextCache, visited map[PredictionContext]PredictionContext) PredictionContext {
+
+ if context.isEmpty() {
+ return context
+ }
+ existing := visited[context]
+ if existing != nil {
+ return existing
+ }
+ existing = contextCache.Get(context)
+ if existing != nil {
+ visited[context] = existing
+ return existing
+ }
+ changed := false
+ parents := make([]PredictionContext, context.length())
+ for i := 0; i < len(parents); i++ {
+ parent := getCachedBasePredictionContext(context.GetParent(i), contextCache, visited)
+ if changed || parent != context.GetParent(i) {
+ if !changed {
+ parents = make([]PredictionContext, context.length())
+ for j := 0; j < context.length(); j++ {
+ parents[j] = context.GetParent(j)
+ }
+ changed = true
+ }
+ parents[i] = parent
+ }
+ }
+ if !changed {
+ contextCache.add(context)
+ visited[context] = context
+ return context
+ }
+ var updated PredictionContext
+ if len(parents) == 0 {
+ updated = BasePredictionContextEMPTY
+ } else if len(parents) == 1 {
+ updated = SingletonBasePredictionContextCreate(parents[0], context.getReturnState(0))
+ } else {
+ updated = NewArrayPredictionContext(parents, context.(*ArrayPredictionContext).GetReturnStates())
+ }
+ contextCache.add(updated)
+ visited[updated] = updated
+ visited[context] = updated
+
+ return updated
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/prediction_mode.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/prediction_mode.go
new file mode 100644
index 0000000000..15718f912b
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/prediction_mode.go
@@ -0,0 +1,553 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+// This enumeration defines the prediction modes available in ANTLR 4 along with
+// utility methods for analyzing configuration sets for conflicts and/or
+// ambiguities.
+
+const (
+ //
+ // The SLL(*) prediction mode. This prediction mode ignores the current
+ // parser context when making predictions. This is the fastest prediction
+ // mode, and provides correct results for many grammars. This prediction
+ // mode is more powerful than the prediction mode provided by ANTLR 3, but
+ // may result in syntax errors for grammar and input combinations which are
+ // not SLL.
+ //
+ //
+ // When using this prediction mode, the parser will either return a correct
+ // parse tree (i.e. the same parse tree that would be returned with the
+ // {@link //LL} prediction mode), or it will Report a syntax error. If a
+ // syntax error is encountered when using the {@link //SLL} prediction mode,
+ // it may be due to either an actual syntax error in the input or indicate
+ // that the particular combination of grammar and input requires the more
+ // powerful {@link //LL} prediction abilities to complete successfully.
+ //
+ //
+ // This prediction mode does not provide any guarantees for prediction
+ // behavior for syntactically-incorrect inputs.
+ //
+ PredictionModeSLL = 0
+ //
+ // The LL(*) prediction mode. This prediction mode allows the current parser
+ // context to be used for resolving SLL conflicts that occur during
+ // prediction. This is the fastest prediction mode that guarantees correct
+ // parse results for all combinations of grammars with syntactically correct
+ // inputs.
+ //
+ //
+ // When using this prediction mode, the parser will make correct decisions
+ // for all syntactically-correct grammar and input combinations. However, in
+ // cases where the grammar is truly ambiguous this prediction mode might not
+ // Report a precise answer for exactly which alternatives are
+ // ambiguous.
+ //
+ //
+ // This prediction mode does not provide any guarantees for prediction
+ // behavior for syntactically-incorrect inputs.
+ //
+ PredictionModeLL = 1
+ //
+ // The LL(*) prediction mode with exact ambiguity detection. In addition to
+ // the correctness guarantees provided by the {@link //LL} prediction mode,
+ // this prediction mode instructs the prediction algorithm to determine the
+ // complete and exact set of ambiguous alternatives for every ambiguous
+ // decision encountered while parsing.
+ //
+ //
+ // This prediction mode may be used for diagnosing ambiguities during
+ // grammar development. Due to the performance overhead of calculating sets
+ // of ambiguous alternatives, this prediction mode should be avoided when
+ // the exact results are not necessary.
+ //
+ //
+ // This prediction mode does not provide any guarantees for prediction
+ // behavior for syntactically-incorrect inputs.
+// This method computes the SLL prediction termination condition for both of
+// the following cases.
+//
+//
+//
The usual SLL+LL fallback upon SLL conflict
+//
Pure SLL without LL fallback
+//
+//
+//
COMBINED SLL+LL PARSING
+//
+//
When LL-fallback is enabled upon SLL conflict, correct predictions are
+// ensured regardless of how the termination condition is computed by this
+// method. Due to the substantially higher cost of LL prediction, the
+// prediction should only fall back to LL when the additional lookahead
+// cannot lead to a unique SLL prediction.
+//
+//
Assuming combined SLL+LL parsing, an SLL configuration set with only
+// conflicting subsets should fall back to full LL, even if the
+// configuration sets don't resolve to the same alternative (e.g.
+// {@code {1,2}} and {@code {3,4}}. If there is at least one non-conflicting
+// configuration, SLL could continue with the hopes that more lookahead will
+// resolve via one of those non-conflicting configurations.
+//
+//
Here's the prediction termination rule them: SLL (for SLL+LL parsing)
+// stops when it sees only conflicting configuration subsets. In contrast,
+// full LL keeps going when there is uncertainty.
+//
+//
HEURISTIC
+//
+//
As a heuristic, we stop prediction when we see any conflicting subset
+// unless we see a state that only has one alternative associated with it.
+// The single-alt-state thing lets prediction continue upon rules like
+// (otherwise, it would admit defeat too soon):
+//
+//
{@code [12|1|[], 6|2|[], 12|2|[]]. s : (ID | ID ID?) '' }
+//
+//
When the ATN simulation reaches the state before {@code ''}, it has a
+// DFA state that looks like: {@code [12|1|[], 6|2|[], 12|2|[]]}. Naturally
+// {@code 12|1|[]} and {@code 12|2|[]} conflict, but we cannot stop
+// processing this node because alternative to has another way to continue,
+// via {@code [6|2|[]]}.
+//
+//
It also let's us continue for this rule:
+//
+//
{@code [1|1|[], 1|2|[], 8|3|[]] a : A | A | A B }
+//
+//
After Matching input A, we reach the stop state for rule A, state 1.
+// State 8 is the state right before B. Clearly alternatives 1 and 2
+// conflict and no amount of further lookahead will separate the two.
+// However, alternative 3 will be able to continue and so we do not stop
+// working on this state. In the previous example, we're concerned with
+// states associated with the conflicting alternatives. Here alt 3 is not
+// associated with the conflicting configs, but since we can continue
+// looking for input reasonably, don't declare the state done.
+//
+//
PURE SLL PARSING
+//
+//
To handle pure SLL parsing, all we have to do is make sure that we
+// combine stack contexts for configurations that differ only by semantic
+// predicate. From there, we can do the usual SLL termination heuristic.
+//
+//
PREDICATES IN SLL+LL PARSING
+//
+//
SLL decisions don't evaluate predicates until after they reach DFA stop
+// states because they need to create the DFA cache that works in all
+// semantic situations. In contrast, full LL evaluates predicates collected
+// during start state computation so it can ignore predicates thereafter.
+// This means that SLL termination detection can totally ignore semantic
+// predicates.
+//
+//
Implementation-wise, {@link ATNConfigSet} combines stack contexts but not
+// semantic predicate contexts so we might see two configurations like the
+// following.
+//
+//
{@code (s, 1, x, {}), (s, 1, x', {p})}
+//
+//
Before testing these configurations against others, we have to merge
+// {@code x} and {@code x'} (without modifying the existing configurations).
+// For example, we test {@code (x+x')==x''} when looking for conflicts in
+// the following configurations.
If the configuration set has predicates (as indicated by
+// {@link ATNConfigSet//hasSemanticContext}), this algorithm makes a copy of
+// the configurations to strip out all of the predicates so that a standard
+// {@link ATNConfigSet} will merge everything ignoring predicates.
+//
+func PredictionModehasSLLConflictTerminatingPrediction(mode int, configs ATNConfigSet) bool {
+ // Configs in rule stop states indicate reaching the end of the decision
+ // rule (local context) or end of start rule (full context). If all
+ // configs meet this condition, then none of the configurations is able
+ // to Match additional input so we terminate prediction.
+ //
+ if PredictionModeallConfigsInRuleStopStates(configs) {
+ return true
+ }
+ // pure SLL mode parsing
+ if mode == PredictionModeSLL {
+ // Don't bother with combining configs from different semantic
+ // contexts if we can fail over to full LL costs more time
+ // since we'll often fail over anyway.
+ if configs.HasSemanticContext() {
+ // dup configs, tossing out semantic predicates
+ dup := NewBaseATNConfigSet(false)
+ for _, c := range configs.GetItems() {
+
+ // NewBaseATNConfig({semanticContext:}, c)
+ c = NewBaseATNConfig2(c, SemanticContextNone)
+ dup.Add(c, nil)
+ }
+ configs = dup
+ }
+ // now we have combined contexts for configs with dissimilar preds
+ }
+ // pure SLL or combined SLL+LL mode parsing
+ altsets := PredictionModegetConflictingAltSubsets(configs)
+ return PredictionModehasConflictingAltSet(altsets) && !PredictionModehasStateAssociatedWithOneAlt(configs)
+}
+
+// Checks if any configuration in {@code configs} is in a
+// {@link RuleStopState}. Configurations meeting this condition have reached
+// the end of the decision rule (local context) or end of start rule (full
+// context).
+//
+// @param configs the configuration set to test
+// @return {@code true} if any configuration in {@code configs} is in a
+// {@link RuleStopState}, otherwise {@code false}
+func PredictionModehasConfigInRuleStopState(configs ATNConfigSet) bool {
+ for _, c := range configs.GetItems() {
+ if _, ok := c.GetState().(*RuleStopState); ok {
+ return true
+ }
+ }
+ return false
+}
+
+// Checks if all configurations in {@code configs} are in a
+// {@link RuleStopState}. Configurations meeting this condition have reached
+// the end of the decision rule (local context) or end of start rule (full
+// context).
+//
+// @param configs the configuration set to test
+// @return {@code true} if all configurations in {@code configs} are in a
+// {@link RuleStopState}, otherwise {@code false}
+func PredictionModeallConfigsInRuleStopStates(configs ATNConfigSet) bool {
+
+ for _, c := range configs.GetItems() {
+ if _, ok := c.GetState().(*RuleStopState); !ok {
+ return false
+ }
+ }
+ return true
+}
+
+//
+// Full LL prediction termination.
+//
+//
Can we stop looking ahead during ATN simulation or is there some
+// uncertainty as to which alternative we will ultimately pick, after
+// consuming more input? Even if there are partial conflicts, we might know
+// that everything is going to resolve to the same minimum alternative. That
+// means we can stop since no more lookahead will change that fact. On the
+// other hand, there might be multiple conflicts that resolve to different
+// minimums. That means we need more look ahead to decide which of those
+// alternatives we should predict.
+//
+//
The basic idea is to split the set of configurations {@code C}, into
+// conflicting subsets {@code (s, _, ctx, _)} and singleton subsets with
+// non-conflicting configurations. Two configurations conflict if they have
+// identical {@link ATNConfig//state} and {@link ATNConfig//context} values
+// but different {@link ATNConfig//alt} value, e.g. {@code (s, i, ctx, _)}
+// and {@code (s, j, ctx, _)} for {@code i!=j}.
+//
+//
Reduce these configuration subsets to the set of possible alternatives.
+// You can compute the alternative subsets in one pass as follows:
+//
+//
{@code A_s,ctx = {i | (s, i, ctx, _)}} for each configuration in
+// {@code C} holding {@code s} and {@code ctx} fixed.
+//
+//
Or in pseudo-code, for each configuration {@code c} in {@code C}:
+//
+//
+// map[c] U= c.{@link ATNConfig//alt alt} // map hash/equals uses s and x, not
+// alt and not pred
+//
+//
+//
The values in {@code map} are the set of {@code A_s,ctx} sets.
+//
+//
If {@code |A_s,ctx|=1} then there is no conflict associated with
+// {@code s} and {@code ctx}.
+//
+//
Reduce the subsets to singletons by choosing a minimum of each subset. If
+// the union of these alternative subsets is a singleton, then no amount of
+// more lookahead will help us. We will always pick that alternative. If,
+// however, there is more than one alternative, then we are uncertain which
+// alternative to predict and must continue looking for resolution. We may
+// or may not discover an ambiguity in the future, even if there are no
+// conflicting subsets this round.
+//
+//
The biggest sin is to terminate early because it means we've made a
+// decision but were uncertain as to the eventual outcome. We haven't used
+// enough lookahead. On the other hand, announcing a conflict too late is no
+// big deal you will still have the conflict. It's just inefficient. It
+// might even look until the end of file.
+//
+//
No special consideration for semantic predicates is required because
+// predicates are evaluated on-the-fly for full LL prediction, ensuring that
+// no configuration contains a semantic context during the termination
+// check.
+//
+//
CONFLICTING CONFIGS
+//
+//
Two configurations {@code (s, i, x)} and {@code (s, j, x')}, conflict
+// when {@code i!=j} but {@code x=x'}. Because we merge all
+// {@code (s, i, _)} configurations together, that means that there are at
+// most {@code n} configurations associated with state {@code s} for
+// {@code n} possible alternatives in the decision. The merged stacks
+// complicate the comparison of configuration contexts {@code x} and
+// {@code x'}. Sam checks to see if one is a subset of the other by calling
+// merge and checking to see if the merged result is either {@code x} or
+// {@code x'}. If the {@code x} associated with lowest alternative {@code i}
+// is the superset, then {@code i} is the only possible prediction since the
+// others resolve to {@code min(i)} as well. However, if {@code x} is
+// associated with {@code j>i} then at least one stack configuration for
+// {@code j} is not in conflict with alternative {@code i}. The algorithm
+// should keep going, looking for more lookahead due to the uncertainty.
+//
+//
For simplicity, I'm doing a equality check between {@code x} and
+// {@code x'} that lets the algorithm continue to consume lookahead longer
+// than necessary. The reason I like the equality is of course the
+// simplicity but also because that is the test you need to detect the
+// alternatives that are actually in conflict.
+//
+//
CONTINUE/STOP RULE
+//
+//
Continue if union of resolved alternative sets from non-conflicting and
+// conflicting alternative subsets has more than one alternative. We are
+// uncertain about which alternative to predict.
+//
+//
The complete set of alternatives, {@code [i for (_,i,_)]}, tells us which
+// alternatives are still in the running for the amount of input we've
+// consumed at this point. The conflicting sets let us to strip away
+// configurations that won't lead to more states because we resolve
+// conflicts to the configuration with a minimum alternate for the
+// conflicting set.
+//
+//
CASES
+//
+//
+//
+//
no conflicts and more than 1 alternative in set => continue
If all states Report the same conflicting set of alternatives, then we
+// know we have the exact ambiguity set.
+//
+//
|A_i|>1 and
+// A_i = A_j for all i, j.
+//
+//
In other words, we continue examining lookahead until all {@code A_i}
+// have more than one alternative and all {@code A_i} are the same. If
+// {@code A={{1,2}, {1,3}}}, then regular LL prediction would terminate
+// because the resolved set is {@code {1}}. To determine what the real
+// ambiguity is, we have to know whether the ambiguity is between one and
+// two or one and three so we keep going. We can only stop prediction when
+// we need exact ambiguity detection when the sets look like
+// {@code A={{1,2}}} or {@code {{1,2},{1,2}}}, etc...
+//
+func PredictionModeresolvesToJustOneViableAlt(altsets []*BitSet) int {
+ return PredictionModegetSingleViableAlt(altsets)
+}
+
+//
+// Determines if every alternative subset in {@code altsets} contains more
+// than one alternative.
+//
+// @param altsets a collection of alternative subsets
+// @return {@code true} if every {@link BitSet} in {@code altsets} has
+// {@link BitSet//cardinality cardinality} > 1, otherwise {@code false}
+//
+func PredictionModeallSubsetsConflict(altsets []*BitSet) bool {
+ return !PredictionModehasNonConflictingAltSet(altsets)
+}
+
+//
+// Determines if any single alternative subset in {@code altsets} contains
+// exactly one alternative.
+//
+// @param altsets a collection of alternative subsets
+// @return {@code true} if {@code altsets} contains a {@link BitSet} with
+// {@link BitSet//cardinality cardinality} 1, otherwise {@code false}
+//
+func PredictionModehasNonConflictingAltSet(altsets []*BitSet) bool {
+ for i := 0; i < len(altsets); i++ {
+ alts := altsets[i]
+ if alts.length() == 1 {
+ return true
+ }
+ }
+ return false
+}
+
+//
+// Determines if any single alternative subset in {@code altsets} contains
+// more than one alternative.
+//
+// @param altsets a collection of alternative subsets
+// @return {@code true} if {@code altsets} contains a {@link BitSet} with
+// {@link BitSet//cardinality cardinality} > 1, otherwise {@code false}
+//
+func PredictionModehasConflictingAltSet(altsets []*BitSet) bool {
+ for i := 0; i < len(altsets); i++ {
+ alts := altsets[i]
+ if alts.length() > 1 {
+ return true
+ }
+ }
+ return false
+}
+
+//
+// Determines if every alternative subset in {@code altsets} is equivalent.
+//
+// @param altsets a collection of alternative subsets
+// @return {@code true} if every member of {@code altsets} is equal to the
+// others, otherwise {@code false}
+//
+func PredictionModeallSubsetsEqual(altsets []*BitSet) bool {
+ var first *BitSet
+
+ for i := 0; i < len(altsets); i++ {
+ alts := altsets[i]
+ if first == nil {
+ first = alts
+ } else if alts != first {
+ return false
+ }
+ }
+
+ return true
+}
+
+//
+// Returns the unique alternative predicted by all alternative subsets in
+// {@code altsets}. If no such alternative exists, this method returns
+// {@link ATN//INVALID_ALT_NUMBER}.
+//
+// @param altsets a collection of alternative subsets
+//
+func PredictionModegetUniqueAlt(altsets []*BitSet) int {
+ all := PredictionModeGetAlts(altsets)
+ if all.length() == 1 {
+ return all.minValue()
+ }
+
+ return ATNInvalidAltNumber
+}
+
+// Gets the complete set of represented alternatives for a collection of
+// alternative subsets. This method returns the union of each {@link BitSet}
+// in {@code altsets}.
+//
+// @param altsets a collection of alternative subsets
+// @return the set of represented alternatives in {@code altsets}
+//
+func PredictionModeGetAlts(altsets []*BitSet) *BitSet {
+ all := NewBitSet()
+ for _, alts := range altsets {
+ all.or(alts)
+ }
+ return all
+}
+
+//
+// This func gets the conflicting alt subsets from a configuration set.
+// For each configuration {@code c} in {@code configs}:
+//
+//
+// map[c] U= c.{@link ATNConfig//alt alt} // map hash/equals uses s and x, not
+// alt and not pred
+//
+//
+func PredictionModegetConflictingAltSubsets(configs ATNConfigSet) []*BitSet {
+ configToAlts := make(map[int]*BitSet)
+
+ for _, c := range configs.GetItems() {
+ key := 31 * c.GetState().GetStateNumber() + c.GetContext().hash()
+
+ alts, ok := configToAlts[key]
+ if !ok {
+ alts = NewBitSet()
+ configToAlts[key] = alts
+ }
+ alts.add(c.GetAlt())
+ }
+
+ values := make([]*BitSet, 0, 10)
+ for _, v := range configToAlts {
+ values = append(values, v)
+ }
+ return values
+}
+
+//
+// Get a map from state to alt subset from a configuration set. For each
+// configuration {@code c} in {@code configs}:
+//
+//
+//
+func PredictionModeGetStateToAltMap(configs ATNConfigSet) *AltDict {
+ m := NewAltDict()
+
+ for _, c := range configs.GetItems() {
+ alts := m.Get(c.GetState().String())
+ if alts == nil {
+ alts = NewBitSet()
+ m.put(c.GetState().String(), alts)
+ }
+ alts.(*BitSet).add(c.GetAlt())
+ }
+ return m
+}
+
+func PredictionModehasStateAssociatedWithOneAlt(configs ATNConfigSet) bool {
+ values := PredictionModeGetStateToAltMap(configs).values()
+ for i := 0; i < len(values); i++ {
+ if values[i].(*BitSet).length() == 1 {
+ return true
+ }
+ }
+ return false
+}
+
+func PredictionModegetSingleViableAlt(altsets []*BitSet) int {
+ result := ATNInvalidAltNumber
+
+ for i := 0; i < len(altsets); i++ {
+ alts := altsets[i]
+ minAlt := alts.minValue()
+ if result == ATNInvalidAltNumber {
+ result = minAlt
+ } else if result != minAlt { // more than 1 viable alt
+ return ATNInvalidAltNumber
+ }
+ }
+ return result
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/recognizer.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/recognizer.go
new file mode 100644
index 0000000000..89d35244a2
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/recognizer.go
@@ -0,0 +1,217 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "strings"
+
+ "strconv"
+)
+
+type Recognizer interface {
+ GetLiteralNames() []string
+ GetSymbolicNames() []string
+ GetRuleNames() []string
+
+ Sempred(RuleContext, int, int) bool
+ Precpred(RuleContext, int) bool
+
+ GetState() int
+ SetState(int)
+ Action(RuleContext, int, int)
+ AddErrorListener(ErrorListener)
+ RemoveErrorListeners()
+ GetATN() *ATN
+ GetErrorListenerDispatch() ErrorListener
+}
+
+type BaseRecognizer struct {
+ listeners []ErrorListener
+ state int
+
+ RuleNames []string
+ LiteralNames []string
+ SymbolicNames []string
+ GrammarFileName string
+}
+
+func NewBaseRecognizer() *BaseRecognizer {
+ rec := new(BaseRecognizer)
+ rec.listeners = []ErrorListener{ConsoleErrorListenerINSTANCE}
+ rec.state = -1
+ return rec
+}
+
+var tokenTypeMapCache = make(map[string]int)
+var ruleIndexMapCache = make(map[string]int)
+
+func (b *BaseRecognizer) checkVersion(toolVersion string) {
+ runtimeVersion := "4.9.2"
+ if runtimeVersion != toolVersion {
+ fmt.Println("ANTLR runtime and generated code versions disagree: " + runtimeVersion + "!=" + toolVersion)
+ }
+}
+
+func (b *BaseRecognizer) Action(context RuleContext, ruleIndex, actionIndex int) {
+ panic("action not implemented on Recognizer!")
+}
+
+func (b *BaseRecognizer) AddErrorListener(listener ErrorListener) {
+ b.listeners = append(b.listeners, listener)
+}
+
+func (b *BaseRecognizer) RemoveErrorListeners() {
+ b.listeners = make([]ErrorListener, 0)
+}
+
+func (b *BaseRecognizer) GetRuleNames() []string {
+ return b.RuleNames
+}
+
+func (b *BaseRecognizer) GetTokenNames() []string {
+ return b.LiteralNames
+}
+
+func (b *BaseRecognizer) GetSymbolicNames() []string {
+ return b.SymbolicNames
+}
+
+func (b *BaseRecognizer) GetLiteralNames() []string {
+ return b.LiteralNames
+}
+
+func (b *BaseRecognizer) GetState() int {
+ return b.state
+}
+
+func (b *BaseRecognizer) SetState(v int) {
+ b.state = v
+}
+
+//func (b *Recognizer) GetTokenTypeMap() {
+// var tokenNames = b.GetTokenNames()
+// if (tokenNames==nil) {
+// panic("The current recognizer does not provide a list of token names.")
+// }
+// var result = tokenTypeMapCache[tokenNames]
+// if(result==nil) {
+// result = tokenNames.reduce(function(o, k, i) { o[k] = i })
+// result.EOF = TokenEOF
+// tokenTypeMapCache[tokenNames] = result
+// }
+// return result
+//}
+
+// Get a map from rule names to rule indexes.
+//
+//
Used for XPath and tree pattern compilation.
+//
+func (b *BaseRecognizer) GetRuleIndexMap() map[string]int {
+
+ panic("Method not defined!")
+ // var ruleNames = b.GetRuleNames()
+ // if (ruleNames==nil) {
+ // panic("The current recognizer does not provide a list of rule names.")
+ // }
+ //
+ // var result = ruleIndexMapCache[ruleNames]
+ // if(result==nil) {
+ // result = ruleNames.reduce(function(o, k, i) { o[k] = i })
+ // ruleIndexMapCache[ruleNames] = result
+ // }
+ // return result
+}
+
+func (b *BaseRecognizer) GetTokenType(tokenName string) int {
+ panic("Method not defined!")
+ // var ttype = b.GetTokenTypeMap()[tokenName]
+ // if (ttype !=nil) {
+ // return ttype
+ // } else {
+ // return TokenInvalidType
+ // }
+}
+
+//func (b *Recognizer) GetTokenTypeMap() map[string]int {
+// Vocabulary vocabulary = getVocabulary()
+//
+// Synchronized (tokenTypeMapCache) {
+// Map result = tokenTypeMapCache.Get(vocabulary)
+// if (result == null) {
+// result = new HashMap()
+// for (int i = 0; i < GetATN().maxTokenType; i++) {
+// String literalName = vocabulary.getLiteralName(i)
+// if (literalName != null) {
+// result.put(literalName, i)
+// }
+//
+// String symbolicName = vocabulary.GetSymbolicName(i)
+// if (symbolicName != null) {
+// result.put(symbolicName, i)
+// }
+// }
+//
+// result.put("EOF", Token.EOF)
+// result = Collections.unmodifiableMap(result)
+// tokenTypeMapCache.put(vocabulary, result)
+// }
+//
+// return result
+// }
+//}
+
+// What is the error header, normally line/character position information?//
+func (b *BaseRecognizer) GetErrorHeader(e RecognitionException) string {
+ line := e.GetOffendingToken().GetLine()
+ column := e.GetOffendingToken().GetColumn()
+ return "line " + strconv.Itoa(line) + ":" + strconv.Itoa(column)
+}
+
+// How should a token be displayed in an error message? The default
+// is to display just the text, but during development you might
+// want to have a lot of information spit out. Override in that case
+// to use t.String() (which, for CommonToken, dumps everything about
+// the token). This is better than forcing you to override a method in
+// your token objects because you don't have to go modify your lexer
+// so that it creates a NewJava type.
+//
+// @deprecated This method is not called by the ANTLR 4 Runtime. Specific
+// implementations of {@link ANTLRErrorStrategy} may provide a similar
+// feature when necessary. For example, see
+// {@link DefaultErrorStrategy//GetTokenErrorDisplay}.
+//
+func (b *BaseRecognizer) GetTokenErrorDisplay(t Token) string {
+ if t == nil {
+ return ""
+ }
+ s := t.GetText()
+ if s == "" {
+ if t.GetTokenType() == TokenEOF {
+ s = ""
+ } else {
+ s = "<" + strconv.Itoa(t.GetTokenType()) + ">"
+ }
+ }
+ s = strings.Replace(s, "\t", "\\t", -1)
+ s = strings.Replace(s, "\n", "\\n", -1)
+ s = strings.Replace(s, "\r", "\\r", -1)
+
+ return "'" + s + "'"
+}
+
+func (b *BaseRecognizer) GetErrorListenerDispatch() ErrorListener {
+ return NewProxyErrorListener(b.listeners)
+}
+
+// subclass needs to override these if there are sempreds or actions
+// that the ATN interp needs to execute
+func (b *BaseRecognizer) Sempred(localctx RuleContext, ruleIndex int, actionIndex int) bool {
+ return true
+}
+
+func (b *BaseRecognizer) Precpred(localctx RuleContext, precedence int) bool {
+ return true
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/rule_context.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/rule_context.go
new file mode 100644
index 0000000000..600cf8c062
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/rule_context.go
@@ -0,0 +1,114 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+// A rule context is a record of a single rule invocation. It knows
+// which context invoked it, if any. If there is no parent context, then
+// naturally the invoking state is not valid. The parent link
+// provides a chain upwards from the current rule invocation to the root
+// of the invocation tree, forming a stack. We actually carry no
+// information about the rule associated with b context (except
+// when parsing). We keep only the state number of the invoking state from
+// the ATN submachine that invoked b. Contrast b with the s
+// pointer inside ParserRuleContext that tracks the current state
+// being "executed" for the current rule.
+//
+// The parent contexts are useful for computing lookahead sets and
+// getting error information.
+//
+// These objects are used during parsing and prediction.
+// For the special case of parsers, we use the subclass
+// ParserRuleContext.
+//
+// @see ParserRuleContext
+//
+
+type RuleContext interface {
+ RuleNode
+
+ GetInvokingState() int
+ SetInvokingState(int)
+
+ GetRuleIndex() int
+ IsEmpty() bool
+
+ GetAltNumber() int
+ SetAltNumber(altNumber int)
+
+ String([]string, RuleContext) string
+}
+
+type BaseRuleContext struct {
+ parentCtx RuleContext
+ invokingState int
+ RuleIndex int
+}
+
+func NewBaseRuleContext(parent RuleContext, invokingState int) *BaseRuleContext {
+
+ rn := new(BaseRuleContext)
+
+ // What context invoked b rule?
+ rn.parentCtx = parent
+
+ // What state invoked the rule associated with b context?
+ // The "return address" is the followState of invokingState
+ // If parent is nil, b should be -1.
+ if parent == nil {
+ rn.invokingState = -1
+ } else {
+ rn.invokingState = invokingState
+ }
+
+ return rn
+}
+
+func (b *BaseRuleContext) GetBaseRuleContext() *BaseRuleContext {
+ return b
+}
+
+func (b *BaseRuleContext) SetParent(v Tree) {
+ if v == nil {
+ b.parentCtx = nil
+ } else {
+ b.parentCtx = v.(RuleContext)
+ }
+}
+
+func (b *BaseRuleContext) GetInvokingState() int {
+ return b.invokingState
+}
+
+func (b *BaseRuleContext) SetInvokingState(t int) {
+ b.invokingState = t
+}
+
+func (b *BaseRuleContext) GetRuleIndex() int {
+ return b.RuleIndex
+}
+
+func (b *BaseRuleContext) GetAltNumber() int {
+ return ATNInvalidAltNumber
+}
+
+func (b *BaseRuleContext) SetAltNumber(altNumber int) {}
+
+// A context is empty if there is no invoking state meaning nobody call
+// current context.
+func (b *BaseRuleContext) IsEmpty() bool {
+ return b.invokingState == -1
+}
+
+// Return the combined text of all child nodes. This method only considers
+// tokens which have been added to the parse tree.
+//
+// Since tokens on hidden channels (e.g. whitespace or comments) are not
+// added to the parse trees, they will not appear in the output of b
+// method.
+//
+
+func (b *BaseRuleContext) GetParent() Tree {
+ return b.parentCtx
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/semantic_context.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/semantic_context.go
new file mode 100644
index 0000000000..49205a1624
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/semantic_context.go
@@ -0,0 +1,455 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "fmt"
+ "strconv"
+)
+
+// A tree structure used to record the semantic context in which
+// an ATN configuration is valid. It's either a single predicate,
+// a conjunction {@code p1&&p2}, or a sum of products {@code p1||p2}.
+//
+//
I have scoped the {@link AND}, {@link OR}, and {@link Predicate} subclasses of
+// {@link SemanticContext} within the scope of this outer class.
+//
+
+type SemanticContext interface {
+ comparable
+
+ evaluate(parser Recognizer, outerContext RuleContext) bool
+ evalPrecedence(parser Recognizer, outerContext RuleContext) SemanticContext
+
+ hash() int
+ String() string
+}
+
+func SemanticContextandContext(a, b SemanticContext) SemanticContext {
+ if a == nil || a == SemanticContextNone {
+ return b
+ }
+ if b == nil || b == SemanticContextNone {
+ return a
+ }
+ result := NewAND(a, b)
+ if len(result.opnds) == 1 {
+ return result.opnds[0]
+ }
+
+ return result
+}
+
+func SemanticContextorContext(a, b SemanticContext) SemanticContext {
+ if a == nil {
+ return b
+ }
+ if b == nil {
+ return a
+ }
+ if a == SemanticContextNone || b == SemanticContextNone {
+ return SemanticContextNone
+ }
+ result := NewOR(a, b)
+ if len(result.opnds) == 1 {
+ return result.opnds[0]
+ }
+
+ return result
+}
+
+type Predicate struct {
+ ruleIndex int
+ predIndex int
+ isCtxDependent bool
+}
+
+func NewPredicate(ruleIndex, predIndex int, isCtxDependent bool) *Predicate {
+ p := new(Predicate)
+
+ p.ruleIndex = ruleIndex
+ p.predIndex = predIndex
+ p.isCtxDependent = isCtxDependent // e.g., $i ref in pred
+ return p
+}
+
+//The default {@link SemanticContext}, which is semantically equivalent to
+//a predicate of the form {@code {true}?}.
+
+var SemanticContextNone SemanticContext = NewPredicate(-1, -1, false)
+
+func (p *Predicate) evalPrecedence(parser Recognizer, outerContext RuleContext) SemanticContext {
+ return p
+}
+
+func (p *Predicate) evaluate(parser Recognizer, outerContext RuleContext) bool {
+
+ var localctx RuleContext
+
+ if p.isCtxDependent {
+ localctx = outerContext
+ }
+
+ return parser.Sempred(localctx, p.ruleIndex, p.predIndex)
+}
+
+func (p *Predicate) equals(other interface{}) bool {
+ if p == other {
+ return true
+ } else if _, ok := other.(*Predicate); !ok {
+ return false
+ } else {
+ return p.ruleIndex == other.(*Predicate).ruleIndex &&
+ p.predIndex == other.(*Predicate).predIndex &&
+ p.isCtxDependent == other.(*Predicate).isCtxDependent
+ }
+}
+
+func (p *Predicate) hash() int {
+ return p.ruleIndex*43 + p.predIndex*47
+}
+
+func (p *Predicate) String() string {
+ return "{" + strconv.Itoa(p.ruleIndex) + ":" + strconv.Itoa(p.predIndex) + "}?"
+}
+
+type PrecedencePredicate struct {
+ precedence int
+}
+
+func NewPrecedencePredicate(precedence int) *PrecedencePredicate {
+
+ p := new(PrecedencePredicate)
+ p.precedence = precedence
+
+ return p
+}
+
+func (p *PrecedencePredicate) evaluate(parser Recognizer, outerContext RuleContext) bool {
+ return parser.Precpred(outerContext, p.precedence)
+}
+
+func (p *PrecedencePredicate) evalPrecedence(parser Recognizer, outerContext RuleContext) SemanticContext {
+ if parser.Precpred(outerContext, p.precedence) {
+ return SemanticContextNone
+ }
+
+ return nil
+}
+
+func (p *PrecedencePredicate) compareTo(other *PrecedencePredicate) int {
+ return p.precedence - other.precedence
+}
+
+func (p *PrecedencePredicate) equals(other interface{}) bool {
+ if p == other {
+ return true
+ } else if _, ok := other.(*PrecedencePredicate); !ok {
+ return false
+ } else {
+ return p.precedence == other.(*PrecedencePredicate).precedence
+ }
+}
+
+func (p *PrecedencePredicate) hash() int {
+ return p.precedence * 51
+}
+
+func (p *PrecedencePredicate) String() string {
+ return "{" + strconv.Itoa(p.precedence) + ">=prec}?"
+}
+
+func PrecedencePredicatefilterPrecedencePredicates(set *Set) []*PrecedencePredicate {
+ result := make([]*PrecedencePredicate, 0)
+
+ for _, v := range set.values() {
+ if c2, ok := v.(*PrecedencePredicate); ok {
+ result = append(result, c2)
+ }
+ }
+
+ return result
+}
+
+// A semantic context which is true whenever none of the contained contexts
+// is false.`
+
+type AND struct {
+ opnds []SemanticContext
+}
+
+func NewAND(a, b SemanticContext) *AND {
+
+ operands := NewSet(nil, nil)
+ if aa, ok := a.(*AND); ok {
+ for _, o := range aa.opnds {
+ operands.add(o)
+ }
+ } else {
+ operands.add(a)
+ }
+
+ if ba, ok := b.(*AND); ok {
+ for _, o := range ba.opnds {
+ operands.add(o)
+ }
+ } else {
+ operands.add(b)
+ }
+ precedencePredicates := PrecedencePredicatefilterPrecedencePredicates(operands)
+ if len(precedencePredicates) > 0 {
+ // interested in the transition with the lowest precedence
+ var reduced *PrecedencePredicate
+
+ for _, p := range precedencePredicates {
+ if reduced == nil || p.precedence < reduced.precedence {
+ reduced = p
+ }
+ }
+
+ operands.add(reduced)
+ }
+
+ vs := operands.values()
+ opnds := make([]SemanticContext, len(vs))
+ for i, v := range vs {
+ opnds[i] = v.(SemanticContext)
+ }
+
+ and := new(AND)
+ and.opnds = opnds
+
+ return and
+}
+
+func (a *AND) equals(other interface{}) bool {
+ if a == other {
+ return true
+ } else if _, ok := other.(*AND); !ok {
+ return false
+ } else {
+ for i, v := range other.(*AND).opnds {
+ if !a.opnds[i].equals(v) {
+ return false
+ }
+ }
+ return true
+ }
+}
+
+//
+// {@inheritDoc}
+//
+//
+// The evaluation of predicates by a context is short-circuiting, but
+// unordered.
+//
+func (a *AND) evaluate(parser Recognizer, outerContext RuleContext) bool {
+ for i := 0; i < len(a.opnds); i++ {
+ if !a.opnds[i].evaluate(parser, outerContext) {
+ return false
+ }
+ }
+ return true
+}
+
+func (a *AND) evalPrecedence(parser Recognizer, outerContext RuleContext) SemanticContext {
+ differs := false
+ operands := make([]SemanticContext, 0)
+
+ for i := 0; i < len(a.opnds); i++ {
+ context := a.opnds[i]
+ evaluated := context.evalPrecedence(parser, outerContext)
+ differs = differs || (evaluated != context)
+ if evaluated == nil {
+ // The AND context is false if any element is false
+ return nil
+ } else if evaluated != SemanticContextNone {
+ // Reduce the result by Skipping true elements
+ operands = append(operands, evaluated)
+ }
+ }
+ if !differs {
+ return a
+ }
+
+ if len(operands) == 0 {
+ // all elements were true, so the AND context is true
+ return SemanticContextNone
+ }
+
+ var result SemanticContext
+
+ for _, o := range operands {
+ if result == nil {
+ result = o
+ } else {
+ result = SemanticContextandContext(result, o)
+ }
+ }
+
+ return result
+}
+
+func (a *AND) hash() int {
+ h := murmurInit(37) // Init with a value different from OR
+ for _, op := range a.opnds {
+ h = murmurUpdate(h, op.hash())
+ }
+ return murmurFinish(h, len(a.opnds))
+}
+
+func (a *OR) hash() int {
+ h := murmurInit(41) // Init with a value different from AND
+ for _, op := range a.opnds {
+ h = murmurUpdate(h, op.hash())
+ }
+ return murmurFinish(h, len(a.opnds))
+}
+
+func (a *AND) String() string {
+ s := ""
+
+ for _, o := range a.opnds {
+ s += "&& " + fmt.Sprint(o)
+ }
+
+ if len(s) > 3 {
+ return s[0:3]
+ }
+
+ return s
+}
+
+//
+// A semantic context which is true whenever at least one of the contained
+// contexts is true.
+//
+
+type OR struct {
+ opnds []SemanticContext
+}
+
+func NewOR(a, b SemanticContext) *OR {
+
+ operands := NewSet(nil, nil)
+ if aa, ok := a.(*OR); ok {
+ for _, o := range aa.opnds {
+ operands.add(o)
+ }
+ } else {
+ operands.add(a)
+ }
+
+ if ba, ok := b.(*OR); ok {
+ for _, o := range ba.opnds {
+ operands.add(o)
+ }
+ } else {
+ operands.add(b)
+ }
+ precedencePredicates := PrecedencePredicatefilterPrecedencePredicates(operands)
+ if len(precedencePredicates) > 0 {
+ // interested in the transition with the lowest precedence
+ var reduced *PrecedencePredicate
+
+ for _, p := range precedencePredicates {
+ if reduced == nil || p.precedence > reduced.precedence {
+ reduced = p
+ }
+ }
+
+ operands.add(reduced)
+ }
+
+ vs := operands.values()
+
+ opnds := make([]SemanticContext, len(vs))
+ for i, v := range vs {
+ opnds[i] = v.(SemanticContext)
+ }
+
+ o := new(OR)
+ o.opnds = opnds
+
+ return o
+}
+
+func (o *OR) equals(other interface{}) bool {
+ if o == other {
+ return true
+ } else if _, ok := other.(*OR); !ok {
+ return false
+ } else {
+ for i, v := range other.(*OR).opnds {
+ if !o.opnds[i].equals(v) {
+ return false
+ }
+ }
+ return true
+ }
+}
+
+//
+// The evaluation of predicates by o context is short-circuiting, but
+// unordered.
+//
+func (o *OR) evaluate(parser Recognizer, outerContext RuleContext) bool {
+ for i := 0; i < len(o.opnds); i++ {
+ if o.opnds[i].evaluate(parser, outerContext) {
+ return true
+ }
+ }
+ return false
+}
+
+func (o *OR) evalPrecedence(parser Recognizer, outerContext RuleContext) SemanticContext {
+ differs := false
+ operands := make([]SemanticContext, 0)
+ for i := 0; i < len(o.opnds); i++ {
+ context := o.opnds[i]
+ evaluated := context.evalPrecedence(parser, outerContext)
+ differs = differs || (evaluated != context)
+ if evaluated == SemanticContextNone {
+ // The OR context is true if any element is true
+ return SemanticContextNone
+ } else if evaluated != nil {
+ // Reduce the result by Skipping false elements
+ operands = append(operands, evaluated)
+ }
+ }
+ if !differs {
+ return o
+ }
+ if len(operands) == 0 {
+ // all elements were false, so the OR context is false
+ return nil
+ }
+ var result SemanticContext
+
+ for _, o := range operands {
+ if result == nil {
+ result = o
+ } else {
+ result = SemanticContextorContext(result, o)
+ }
+ }
+
+ return result
+}
+
+func (o *OR) String() string {
+ s := ""
+
+ for _, o := range o.opnds {
+ s += "|| " + fmt.Sprint(o)
+ }
+
+ if len(s) > 3 {
+ return s[0:3]
+ }
+
+ return s
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token.go
new file mode 100644
index 0000000000..2d8e99095d
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token.go
@@ -0,0 +1,210 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "strconv"
+ "strings"
+)
+
+type TokenSourceCharStreamPair struct {
+ tokenSource TokenSource
+ charStream CharStream
+}
+
+// A token has properties: text, type, line, character position in the line
+// (so we can ignore tabs), token channel, index, and source from which
+// we obtained this token.
+
+type Token interface {
+ GetSource() *TokenSourceCharStreamPair
+ GetTokenType() int
+ GetChannel() int
+ GetStart() int
+ GetStop() int
+ GetLine() int
+ GetColumn() int
+
+ GetText() string
+ SetText(s string)
+
+ GetTokenIndex() int
+ SetTokenIndex(v int)
+
+ GetTokenSource() TokenSource
+ GetInputStream() CharStream
+}
+
+type BaseToken struct {
+ source *TokenSourceCharStreamPair
+ tokenType int // token type of the token
+ channel int // The parser ignores everything not on DEFAULT_CHANNEL
+ start int // optional return -1 if not implemented.
+ stop int // optional return -1 if not implemented.
+ tokenIndex int // from 0..n-1 of the token object in the input stream
+ line int // line=1..n of the 1st character
+ column int // beginning of the line at which it occurs, 0..n-1
+ text string // text of the token.
+ readOnly bool
+}
+
+const (
+ TokenInvalidType = 0
+
+ // During lookahead operations, this "token" signifies we hit rule end ATN state
+ // and did not follow it despite needing to.
+ TokenEpsilon = -2
+
+ TokenMinUserTokenType = 1
+
+ TokenEOF = -1
+
+ // All tokens go to the parser (unless Skip() is called in that rule)
+ // on a particular "channel". The parser tunes to a particular channel
+ // so that whitespace etc... can go to the parser on a "hidden" channel.
+
+ TokenDefaultChannel = 0
+
+ // Anything on different channel than DEFAULT_CHANNEL is not parsed
+ // by parser.
+
+ TokenHiddenChannel = 1
+)
+
+func (b *BaseToken) GetChannel() int {
+ return b.channel
+}
+
+func (b *BaseToken) GetStart() int {
+ return b.start
+}
+
+func (b *BaseToken) GetStop() int {
+ return b.stop
+}
+
+func (b *BaseToken) GetLine() int {
+ return b.line
+}
+
+func (b *BaseToken) GetColumn() int {
+ return b.column
+}
+
+func (b *BaseToken) GetTokenType() int {
+ return b.tokenType
+}
+
+func (b *BaseToken) GetSource() *TokenSourceCharStreamPair {
+ return b.source
+}
+
+func (b *BaseToken) GetTokenIndex() int {
+ return b.tokenIndex
+}
+
+func (b *BaseToken) SetTokenIndex(v int) {
+ b.tokenIndex = v
+}
+
+func (b *BaseToken) GetTokenSource() TokenSource {
+ return b.source.tokenSource
+}
+
+func (b *BaseToken) GetInputStream() CharStream {
+ return b.source.charStream
+}
+
+type CommonToken struct {
+ *BaseToken
+}
+
+func NewCommonToken(source *TokenSourceCharStreamPair, tokenType, channel, start, stop int) *CommonToken {
+
+ t := new(CommonToken)
+
+ t.BaseToken = new(BaseToken)
+
+ t.source = source
+ t.tokenType = tokenType
+ t.channel = channel
+ t.start = start
+ t.stop = stop
+ t.tokenIndex = -1
+ if t.source.tokenSource != nil {
+ t.line = source.tokenSource.GetLine()
+ t.column = source.tokenSource.GetCharPositionInLine()
+ } else {
+ t.column = -1
+ }
+ return t
+}
+
+// An empty {@link Pair} which is used as the default value of
+// {@link //source} for tokens that do not have a source.
+
+//CommonToken.EMPTY_SOURCE = [ nil, nil ]
+
+// Constructs a New{@link CommonToken} as a copy of another {@link Token}.
+//
+//
+// If {@code oldToken} is also a {@link CommonToken} instance, the newly
+// constructed token will share a reference to the {@link //text} field and
+// the {@link Pair} stored in {@link //source}. Otherwise, {@link //text} will
+// be assigned the result of calling {@link //GetText}, and {@link //source}
+// will be constructed from the result of {@link Token//GetTokenSource} and
+// {@link Token//GetInputStream}.
+//
+// @param oldToken The token to copy.
+//
+func (c *CommonToken) clone() *CommonToken {
+ t := NewCommonToken(c.source, c.tokenType, c.channel, c.start, c.stop)
+ t.tokenIndex = c.GetTokenIndex()
+ t.line = c.GetLine()
+ t.column = c.GetColumn()
+ t.text = c.GetText()
+ return t
+}
+
+func (c *CommonToken) GetText() string {
+ if c.text != "" {
+ return c.text
+ }
+ input := c.GetInputStream()
+ if input == nil {
+ return ""
+ }
+ n := input.Size()
+ if c.start < n && c.stop < n {
+ return input.GetTextFromInterval(NewInterval(c.start, c.stop))
+ }
+ return ""
+}
+
+func (c *CommonToken) SetText(text string) {
+ c.text = text
+}
+
+func (c *CommonToken) String() string {
+ txt := c.GetText()
+ if txt != "" {
+ txt = strings.Replace(txt, "\n", "\\n", -1)
+ txt = strings.Replace(txt, "\r", "\\r", -1)
+ txt = strings.Replace(txt, "\t", "\\t", -1)
+ } else {
+ txt = ""
+ }
+
+ var ch string
+ if c.channel > 0 {
+ ch = ",channel=" + strconv.Itoa(c.channel)
+ } else {
+ ch = ""
+ }
+
+ return "[@" + strconv.Itoa(c.tokenIndex) + "," + strconv.Itoa(c.start) + ":" + strconv.Itoa(c.stop) + "='" +
+ txt + "',<" + strconv.Itoa(c.tokenType) + ">" +
+ ch + "," + strconv.Itoa(c.line) + ":" + strconv.Itoa(c.column) + "]"
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token_source.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token_source.go
new file mode 100644
index 0000000000..e023978fef
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token_source.go
@@ -0,0 +1,17 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+type TokenSource interface {
+ NextToken() Token
+ Skip()
+ More()
+ GetLine() int
+ GetCharPositionInLine() int
+ GetInputStream() CharStream
+ GetSourceName() string
+ setTokenFactory(factory TokenFactory)
+ GetTokenFactory() TokenFactory
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token_stream.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token_stream.go
new file mode 100644
index 0000000000..df92c81478
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/token_stream.go
@@ -0,0 +1,20 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+type TokenStream interface {
+ IntStream
+
+ LT(k int) Token
+
+ Get(index int) Token
+ GetTokenSource() TokenSource
+ SetTokenSource(TokenSource)
+
+ GetAllText() string
+ GetTextFromInterval(*Interval) string
+ GetTextFromRuleContext(RuleContext) string
+ GetTextFromTokens(Token, Token) string
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/tokenstream_rewriter.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/tokenstream_rewriter.go
new file mode 100644
index 0000000000..96a03f02aa
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/tokenstream_rewriter.go
@@ -0,0 +1,649 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+package antlr
+
+import (
+"bytes"
+"fmt"
+)
+
+
+//
+// Useful for rewriting out a buffered input token stream after doing some
+// augmentation or other manipulations on it.
+
+//
+// You can insert stuff, replace, and delete chunks. Note that the operations
+// are done lazily--only if you convert the buffer to a {@link String} with
+// {@link TokenStream#getText()}. This is very efficient because you are not
+// moving data around all the time. As the buffer of tokens is converted to
+// strings, the {@link #getText()} method(s) scan the input token stream and
+// check to see if there is an operation at the current index. If so, the
+// operation is done and then normal {@link String} rendering continues on the
+// buffer. This is like having multiple Turing machine instruction streams
+// (programs) operating on a single input tape. :)
+//
+
+// This rewriter makes no modifications to the token stream. It does not ask the
+// stream to fill itself up nor does it advance the input cursor. The token
+// stream {@link TokenStream#index()} will return the same value before and
+// after any {@link #getText()} call.
+
+//
+// The rewriter only works on tokens that you have in the buffer and ignores the
+// current input cursor. If you are buffering tokens on-demand, calling
+// {@link #getText()} halfway through the input will only do rewrites for those
+// tokens in the first half of the file.
+
+//
+// Since the operations are done lazily at {@link #getText}-time, operations do
+// not screw up the token index values. That is, an insert operation at token
+// index {@code i} does not change the index values for tokens
+// {@code i}+1..n-1.
+
+//
+// Because operations never actually alter the buffer, you may always get the
+// original token stream back without undoing anything. Since the instructions
+// are queued up, you can easily simulate transactions and roll back any changes
+// if there is an error just by removing instructions. For example,
+
+//
+// CharStream input = new ANTLRFileStream("input");
+// TLexer lex = new TLexer(input);
+// CommonTokenStream tokens = new CommonTokenStream(lex);
+// T parser = new T(tokens);
+// TokenStreamRewriter rewriter = new TokenStreamRewriter(tokens);
+// parser.startRule();
+//
+
+//
+// Then in the rules, you can execute (assuming rewriter is visible):
+
+//
+// Token t,u;
+// ...
+// rewriter.insertAfter(t, "text to put after t");}
+// rewriter.insertAfter(u, "text after u");}
+// System.out.println(rewriter.getText());
+//
+
+//
+// You can also have multiple "instruction streams" and get multiple rewrites
+// from a single pass over the input. Just name the instruction streams and use
+// that name again when printing the buffer. This could be useful for generating
+// a C file and also its header file--all from the same buffer:
+
+//
+// rewriter.insertAfter("pass1", t, "text to put after t");}
+// rewriter.insertAfter("pass2", u, "text after u");}
+// System.out.println(rewriter.getText("pass1"));
+// System.out.println(rewriter.getText("pass2"));
+//
+
+//
+// If you don't use named rewrite streams, a "default" stream is used as the
+// first example shows.
+
+
+
+const(
+ Default_Program_Name = "default"
+ Program_Init_Size = 100
+ Min_Token_Index = 0
+)
+
+// Define the rewrite operation hierarchy
+
+type RewriteOperation interface {
+ // Execute the rewrite operation by possibly adding to the buffer.
+ // Return the index of the next token to operate on.
+ Execute(buffer *bytes.Buffer) int
+ String() string
+ GetInstructionIndex() int
+ GetIndex() int
+ GetText() string
+ GetOpName() string
+ GetTokens() TokenStream
+ SetInstructionIndex(val int)
+ SetIndex(int)
+ SetText(string)
+ SetOpName(string)
+ SetTokens(TokenStream)
+}
+
+type BaseRewriteOperation struct {
+ //Current index of rewrites list
+ instruction_index int
+ //Token buffer index
+ index int
+ //Substitution text
+ text string
+ //Actual operation name
+ op_name string
+ //Pointer to token steam
+ tokens TokenStream
+}
+
+func (op *BaseRewriteOperation)GetInstructionIndex() int{
+ return op.instruction_index
+}
+
+func (op *BaseRewriteOperation)GetIndex() int{
+ return op.index
+}
+
+func (op *BaseRewriteOperation)GetText() string{
+ return op.text
+}
+
+func (op *BaseRewriteOperation)GetOpName() string{
+ return op.op_name
+}
+
+func (op *BaseRewriteOperation)GetTokens() TokenStream{
+ return op.tokens
+}
+
+func (op *BaseRewriteOperation)SetInstructionIndex(val int){
+ op.instruction_index = val
+}
+
+func (op *BaseRewriteOperation)SetIndex(val int) {
+ op.index = val
+}
+
+func (op *BaseRewriteOperation)SetText(val string){
+ op.text = val
+}
+
+func (op *BaseRewriteOperation)SetOpName(val string){
+ op.op_name = val
+}
+
+func (op *BaseRewriteOperation)SetTokens(val TokenStream) {
+ op.tokens = val
+}
+
+
+func (op *BaseRewriteOperation) Execute(buffer *bytes.Buffer) int{
+ return op.index
+}
+
+func (op *BaseRewriteOperation) String() string {
+ return fmt.Sprintf("<%s@%d:\"%s\">",
+ op.op_name,
+ op.tokens.Get(op.GetIndex()),
+ op.text,
+ )
+
+}
+
+
+type InsertBeforeOp struct {
+ BaseRewriteOperation
+}
+
+func NewInsertBeforeOp(index int, text string, stream TokenStream) *InsertBeforeOp{
+ return &InsertBeforeOp{BaseRewriteOperation:BaseRewriteOperation{
+ index:index,
+ text:text,
+ op_name:"InsertBeforeOp",
+ tokens:stream,
+ }}
+}
+
+func (op *InsertBeforeOp) Execute(buffer *bytes.Buffer) int{
+ buffer.WriteString(op.text)
+ if op.tokens.Get(op.index).GetTokenType() != TokenEOF{
+ buffer.WriteString(op.tokens.Get(op.index).GetText())
+ }
+ return op.index+1
+}
+
+func (op *InsertBeforeOp) String() string {
+ return op.BaseRewriteOperation.String()
+}
+
+// Distinguish between insert after/before to do the "insert afters"
+// first and then the "insert befores" at same index. Implementation
+// of "insert after" is "insert before index+1".
+
+type InsertAfterOp struct {
+ BaseRewriteOperation
+}
+
+func NewInsertAfterOp(index int, text string, stream TokenStream) *InsertAfterOp{
+ return &InsertAfterOp{BaseRewriteOperation:BaseRewriteOperation{
+ index:index+1,
+ text:text,
+ tokens:stream,
+ }}
+}
+
+func (op *InsertAfterOp) Execute(buffer *bytes.Buffer) int {
+ buffer.WriteString(op.text)
+ if op.tokens.Get(op.index).GetTokenType() != TokenEOF{
+ buffer.WriteString(op.tokens.Get(op.index).GetText())
+ }
+ return op.index+1
+}
+
+func (op *InsertAfterOp) String() string {
+ return op.BaseRewriteOperation.String()
+}
+
+// I'm going to try replacing range from x..y with (y-x)+1 ReplaceOp
+// instructions.
+type ReplaceOp struct{
+ BaseRewriteOperation
+ LastIndex int
+}
+
+func NewReplaceOp(from, to int, text string, stream TokenStream)*ReplaceOp {
+ return &ReplaceOp{
+ BaseRewriteOperation:BaseRewriteOperation{
+ index:from,
+ text:text,
+ op_name:"ReplaceOp",
+ tokens:stream,
+ },
+ LastIndex:to,
+ }
+}
+
+func (op *ReplaceOp)Execute(buffer *bytes.Buffer) int{
+ if op.text != ""{
+ buffer.WriteString(op.text)
+ }
+ return op.LastIndex +1
+}
+
+func (op *ReplaceOp) String() string {
+ if op.text == "" {
+ return fmt.Sprintf("",
+ op.tokens.Get(op.index), op.tokens.Get(op.LastIndex))
+ }
+ return fmt.Sprintf("",
+ op.tokens.Get(op.index), op.tokens.Get(op.LastIndex), op.text)
+}
+
+
+type TokenStreamRewriter struct {
+ //Our source stream
+ tokens TokenStream
+ // You may have multiple, named streams of rewrite operations.
+ // I'm calling these things "programs."
+ // Maps String (name) → rewrite (List)
+ programs map[string][]RewriteOperation
+ last_rewrite_token_indexes map[string]int
+}
+
+func NewTokenStreamRewriter(tokens TokenStream) *TokenStreamRewriter{
+ return &TokenStreamRewriter{
+ tokens: tokens,
+ programs: map[string][]RewriteOperation{
+ Default_Program_Name:make([]RewriteOperation,0, Program_Init_Size),
+ },
+ last_rewrite_token_indexes: map[string]int{},
+ }
+}
+
+func (tsr *TokenStreamRewriter) GetTokenStream() TokenStream{
+ return tsr.tokens
+}
+
+// Rollback the instruction stream for a program so that
+// the indicated instruction (via instructionIndex) is no
+// longer in the stream. UNTESTED!
+func (tsr *TokenStreamRewriter) Rollback(program_name string, instruction_index int){
+ is, ok := tsr.programs[program_name]
+ if ok{
+ tsr.programs[program_name] = is[Min_Token_Index:instruction_index]
+ }
+}
+
+func (tsr *TokenStreamRewriter) RollbackDefault(instruction_index int){
+ tsr.Rollback(Default_Program_Name, instruction_index)
+}
+//Reset the program so that no instructions exist
+func (tsr *TokenStreamRewriter) DeleteProgram(program_name string){
+ tsr.Rollback(program_name, Min_Token_Index) //TODO: double test on that cause lower bound is not included
+}
+
+func (tsr *TokenStreamRewriter) DeleteProgramDefault(){
+ tsr.DeleteProgram(Default_Program_Name)
+}
+
+func (tsr *TokenStreamRewriter) InsertAfter(program_name string, index int, text string){
+ // to insert after, just insert before next index (even if past end)
+ var op RewriteOperation = NewInsertAfterOp(index, text, tsr.tokens)
+ rewrites := tsr.GetProgram(program_name)
+ op.SetInstructionIndex(len(rewrites))
+ tsr.AddToProgram(program_name, op)
+}
+
+func (tsr *TokenStreamRewriter) InsertAfterDefault(index int, text string){
+ tsr.InsertAfter(Default_Program_Name, index, text)
+}
+
+func (tsr *TokenStreamRewriter) InsertAfterToken(program_name string, token Token, text string){
+ tsr.InsertAfter(program_name, token.GetTokenIndex(), text)
+}
+
+func (tsr* TokenStreamRewriter) InsertBefore(program_name string, index int, text string){
+ var op RewriteOperation = NewInsertBeforeOp(index, text, tsr.tokens)
+ rewrites := tsr.GetProgram(program_name)
+ op.SetInstructionIndex(len(rewrites))
+ tsr.AddToProgram(program_name, op)
+}
+
+func (tsr *TokenStreamRewriter) InsertBeforeDefault(index int, text string){
+ tsr.InsertBefore(Default_Program_Name, index, text)
+}
+
+func (tsr *TokenStreamRewriter) InsertBeforeToken(program_name string,token Token, text string){
+ tsr.InsertBefore(program_name, token.GetTokenIndex(), text)
+}
+
+func (tsr *TokenStreamRewriter) Replace(program_name string, from, to int, text string){
+ if from > to || from < 0 || to < 0 || to >= tsr.tokens.Size(){
+ panic(fmt.Sprintf("replace: range invalid: %d..%d(size=%d)",
+ from, to, tsr.tokens.Size()))
+ }
+ var op RewriteOperation = NewReplaceOp(from, to, text, tsr.tokens)
+ rewrites := tsr.GetProgram(program_name)
+ op.SetInstructionIndex(len(rewrites))
+ tsr.AddToProgram(program_name, op)
+}
+
+func (tsr *TokenStreamRewriter)ReplaceDefault(from, to int, text string) {
+ tsr.Replace(Default_Program_Name, from, to, text)
+}
+
+func (tsr *TokenStreamRewriter)ReplaceDefaultPos(index int, text string){
+ tsr.ReplaceDefault(index, index, text)
+}
+
+func (tsr *TokenStreamRewriter)ReplaceToken(program_name string, from, to Token, text string){
+ tsr.Replace(program_name, from.GetTokenIndex(), to.GetTokenIndex(), text)
+}
+
+func (tsr *TokenStreamRewriter)ReplaceTokenDefault(from, to Token, text string){
+ tsr.ReplaceToken(Default_Program_Name, from, to, text)
+}
+
+func (tsr *TokenStreamRewriter)ReplaceTokenDefaultPos(index Token, text string){
+ tsr.ReplaceTokenDefault(index, index, text)
+}
+
+func (tsr *TokenStreamRewriter)Delete(program_name string, from, to int){
+ tsr.Replace(program_name, from, to, "" )
+}
+
+func (tsr *TokenStreamRewriter)DeleteDefault(from, to int){
+ tsr.Delete(Default_Program_Name, from, to)
+}
+
+func (tsr *TokenStreamRewriter)DeleteDefaultPos(index int){
+ tsr.DeleteDefault(index,index)
+}
+
+func (tsr *TokenStreamRewriter)DeleteToken(program_name string, from, to Token) {
+ tsr.ReplaceToken(program_name, from, to, "")
+}
+
+func (tsr *TokenStreamRewriter)DeleteTokenDefault(from,to Token){
+ tsr.DeleteToken(Default_Program_Name, from, to)
+}
+
+func (tsr *TokenStreamRewriter)GetLastRewriteTokenIndex(program_name string)int {
+ i, ok := tsr.last_rewrite_token_indexes[program_name]
+ if !ok{
+ return -1
+ }
+ return i
+}
+
+func (tsr *TokenStreamRewriter)GetLastRewriteTokenIndexDefault()int{
+ return tsr.GetLastRewriteTokenIndex(Default_Program_Name)
+}
+
+func (tsr *TokenStreamRewriter)SetLastRewriteTokenIndex(program_name string, i int){
+ tsr.last_rewrite_token_indexes[program_name] = i
+}
+
+func (tsr *TokenStreamRewriter)InitializeProgram(name string)[]RewriteOperation{
+ is := make([]RewriteOperation, 0, Program_Init_Size)
+ tsr.programs[name] = is
+ return is
+}
+
+func (tsr *TokenStreamRewriter)AddToProgram(name string, op RewriteOperation){
+ is := tsr.GetProgram(name)
+ is = append(is, op)
+ tsr.programs[name] = is
+}
+
+func (tsr *TokenStreamRewriter)GetProgram(name string) []RewriteOperation {
+ is, ok := tsr.programs[name]
+ if !ok{
+ is = tsr.InitializeProgram(name)
+ }
+ return is
+}
+// Return the text from the original tokens altered per the
+// instructions given to this rewriter.
+func (tsr *TokenStreamRewriter)GetTextDefault() string{
+ return tsr.GetText(
+ Default_Program_Name,
+ NewInterval(0, tsr.tokens.Size()-1))
+}
+// Return the text from the original tokens altered per the
+// instructions given to this rewriter.
+func (tsr *TokenStreamRewriter)GetText(program_name string, interval *Interval) string {
+ rewrites := tsr.programs[program_name]
+ start := interval.Start
+ stop := interval.Stop
+ // ensure start/end are in range
+ stop = min(stop, tsr.tokens.Size()-1)
+ start = max(start,0)
+ if rewrites == nil || len(rewrites) == 0{
+ return tsr.tokens.GetTextFromInterval(interval) // no instructions to execute
+ }
+ buf := bytes.Buffer{}
+ // First, optimize instruction stream
+ indexToOp := reduceToSingleOperationPerIndex(rewrites)
+ // Walk buffer, executing instructions and emitting tokens
+ for i:=start; i<=stop && i= tsr.tokens.Size()-1 {buf.WriteString(op.GetText())}
+ }
+ }
+ return buf.String()
+}
+
+// We need to combine operations and report invalid operations (like
+// overlapping replaces that are not completed nested). Inserts to
+// same index need to be combined etc... Here are the cases:
+//
+// I.i.u I.j.v leave alone, nonoverlapping
+// I.i.u I.i.v combine: Iivu
+//
+// R.i-j.u R.x-y.v | i-j in x-y delete first R
+// R.i-j.u R.i-j.v delete first R
+// R.i-j.u R.x-y.v | x-y in i-j ERROR
+// R.i-j.u R.x-y.v | boundaries overlap ERROR
+//
+// Delete special case of replace (text==null):
+// D.i-j.u D.x-y.v | boundaries overlap combine to max(min)..max(right)
+//
+// I.i.u R.x-y.v | i in (x+1)-y delete I (since insert before
+// we're not deleting i)
+// I.i.u R.x-y.v | i not in (x+1)-y leave alone, nonoverlapping
+// R.x-y.v I.i.u | i in x-y ERROR
+// R.x-y.v I.x.u R.x-y.uv (combine, delete I)
+// R.x-y.v I.i.u | i not in x-y leave alone, nonoverlapping
+//
+// I.i.u = insert u before op @ index i
+// R.x-y.u = replace x-y indexed tokens with u
+//
+// First we need to examine replaces. For any replace op:
+//
+// 1. wipe out any insertions before op within that range.
+// 2. Drop any replace op before that is contained completely within
+// that range.
+// 3. Throw exception upon boundary overlap with any previous replace.
+//
+// Then we can deal with inserts:
+//
+// 1. for any inserts to same index, combine even if not adjacent.
+// 2. for any prior replace with same left boundary, combine this
+// insert with replace and delete this replace.
+// 3. throw exception if index in same range as previous replace
+//
+// Don't actually delete; make op null in list. Easier to walk list.
+// Later we can throw as we add to index → op map.
+//
+// Note that I.2 R.2-2 will wipe out I.2 even though, technically, the
+// inserted stuff would be before the replace range. But, if you
+// add tokens in front of a method body '{' and then delete the method
+// body, I think the stuff before the '{' you added should disappear too.
+//
+// Return a map from token index to operation.
+//
+func reduceToSingleOperationPerIndex(rewrites []RewriteOperation) map[int]RewriteOperation{
+ // WALK REPLACES
+ for i:=0; i < len(rewrites); i++{
+ op := rewrites[i]
+ if op == nil{continue}
+ rop, ok := op.(*ReplaceOp)
+ if !ok{continue}
+ // Wipe prior inserts within range
+ for j:=0; j rop.index && iop.index <=rop.LastIndex{
+ // delete insert as it's a no-op.
+ rewrites[iop.instruction_index] = nil
+ }
+ }
+ }
+ // Drop any prior replaces contained within
+ for j:=0; j=rop.index && prevop.LastIndex <= rop.LastIndex{
+ // delete replace as it's a no-op.
+ rewrites[prevop.instruction_index] = nil
+ continue
+ }
+ // throw exception unless disjoint or identical
+ disjoint := prevop.LastIndex < rop.index || prevop.index > rop.LastIndex
+ // Delete special case of replace (text==null):
+ // D.i-j.u D.x-y.v | boundaries overlap combine to max(min)..max(right)
+ if prevop.text == "" && rop.text == "" && !disjoint{
+ rewrites[prevop.instruction_index] = nil
+ rop.index = min(prevop.index, rop.index)
+ rop.LastIndex = max(prevop.LastIndex, rop.LastIndex)
+ println("new rop" + rop.String()) //TODO: remove console write, taken from Java version
+ }else if !disjoint{
+ panic("replace op boundaries of " + rop.String() + " overlap with previous " + prevop.String())
+ }
+ }
+ }
+ }
+ // WALK INSERTS
+ for i:=0; i < len(rewrites); i++ {
+ op := rewrites[i]
+ if op == nil{continue}
+ //hack to replicate inheritance in composition
+ _, iok := rewrites[i].(*InsertBeforeOp)
+ _, aok := rewrites[i].(*InsertAfterOp)
+ if !iok && !aok{continue}
+ iop := rewrites[i]
+ // combine current insert with prior if any at same index
+ // deviating a bit from TokenStreamRewriter.java - hard to incorporate inheritance logic
+ for j:=0; j= rop.index && iop.GetIndex() <= rop.LastIndex{
+ panic("insert op "+iop.String()+" within boundaries of previous "+rop.String())
+ }
+ }
+ }
+ }
+ m := map[int]RewriteOperation{}
+ for i:=0; i < len(rewrites); i++{
+ op := rewrites[i]
+ if op == nil {continue}
+ if _, ok := m[op.GetIndex()]; ok{
+ panic("should only be one op per index")
+ }
+ m[op.GetIndex()] = op
+ }
+ return m
+}
+
+
+/*
+ Quick fixing Go lack of overloads
+ */
+
+func max(a,b int)int{
+ if a>b{
+ return a
+ }else {
+ return b
+ }
+}
+func min(a,b int)int{
+ if aThis is a one way link. It emanates from a state (usually via a list of
+// transitions) and has a target state.
+//
+//
Since we never have to change the ATN transitions once we construct it,
+// the states. We'll use the term Edge for the DFA to distinguish them from
+// ATN transitions.
+
+type Transition interface {
+ getTarget() ATNState
+ setTarget(ATNState)
+ getIsEpsilon() bool
+ getLabel() *IntervalSet
+ getSerializationType() int
+ Matches(int, int, int) bool
+}
+
+type BaseTransition struct {
+ target ATNState
+ isEpsilon bool
+ label int
+ intervalSet *IntervalSet
+ serializationType int
+}
+
+func NewBaseTransition(target ATNState) *BaseTransition {
+
+ if target == nil {
+ panic("target cannot be nil.")
+ }
+
+ t := new(BaseTransition)
+
+ t.target = target
+ // Are we epsilon, action, sempred?
+ t.isEpsilon = false
+ t.intervalSet = nil
+
+ return t
+}
+
+func (t *BaseTransition) getTarget() ATNState {
+ return t.target
+}
+
+func (t *BaseTransition) setTarget(s ATNState) {
+ t.target = s
+}
+
+func (t *BaseTransition) getIsEpsilon() bool {
+ return t.isEpsilon
+}
+
+func (t *BaseTransition) getLabel() *IntervalSet {
+ return t.intervalSet
+}
+
+func (t *BaseTransition) getSerializationType() int {
+ return t.serializationType
+}
+
+func (t *BaseTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ panic("Not implemented")
+}
+
+const (
+ TransitionEPSILON = 1
+ TransitionRANGE = 2
+ TransitionRULE = 3
+ TransitionPREDICATE = 4 // e.g., {isType(input.LT(1))}?
+ TransitionATOM = 5
+ TransitionACTION = 6
+ TransitionSET = 7 // ~(A|B) or ~atom, wildcard, which convert to next 2
+ TransitionNOTSET = 8
+ TransitionWILDCARD = 9
+ TransitionPRECEDENCE = 10
+)
+
+var TransitionserializationNames = []string{
+ "INVALID",
+ "EPSILON",
+ "RANGE",
+ "RULE",
+ "PREDICATE",
+ "ATOM",
+ "ACTION",
+ "SET",
+ "NOT_SET",
+ "WILDCARD",
+ "PRECEDENCE",
+}
+
+//var TransitionserializationTypes struct {
+// EpsilonTransition int
+// RangeTransition int
+// RuleTransition int
+// PredicateTransition int
+// AtomTransition int
+// ActionTransition int
+// SetTransition int
+// NotSetTransition int
+// WildcardTransition int
+// PrecedencePredicateTransition int
+//}{
+// TransitionEPSILON,
+// TransitionRANGE,
+// TransitionRULE,
+// TransitionPREDICATE,
+// TransitionATOM,
+// TransitionACTION,
+// TransitionSET,
+// TransitionNOTSET,
+// TransitionWILDCARD,
+// TransitionPRECEDENCE
+//}
+
+// TODO: make all transitions sets? no, should remove set edges
+type AtomTransition struct {
+ *BaseTransition
+}
+
+func NewAtomTransition(target ATNState, intervalSet int) *AtomTransition {
+
+ t := new(AtomTransition)
+ t.BaseTransition = NewBaseTransition(target)
+
+ t.label = intervalSet // The token type or character value or, signifies special intervalSet.
+ t.intervalSet = t.makeLabel()
+ t.serializationType = TransitionATOM
+
+ return t
+}
+
+func (t *AtomTransition) makeLabel() *IntervalSet {
+ s := NewIntervalSet()
+ s.addOne(t.label)
+ return s
+}
+
+func (t *AtomTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return t.label == symbol
+}
+
+func (t *AtomTransition) String() string {
+ return strconv.Itoa(t.label)
+}
+
+type RuleTransition struct {
+ *BaseTransition
+
+ followState ATNState
+ ruleIndex, precedence int
+}
+
+func NewRuleTransition(ruleStart ATNState, ruleIndex, precedence int, followState ATNState) *RuleTransition {
+
+ t := new(RuleTransition)
+ t.BaseTransition = NewBaseTransition(ruleStart)
+
+ t.ruleIndex = ruleIndex
+ t.precedence = precedence
+ t.followState = followState
+ t.serializationType = TransitionRULE
+ t.isEpsilon = true
+
+ return t
+}
+
+func (t *RuleTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return false
+}
+
+type EpsilonTransition struct {
+ *BaseTransition
+
+ outermostPrecedenceReturn int
+}
+
+func NewEpsilonTransition(target ATNState, outermostPrecedenceReturn int) *EpsilonTransition {
+
+ t := new(EpsilonTransition)
+ t.BaseTransition = NewBaseTransition(target)
+
+ t.serializationType = TransitionEPSILON
+ t.isEpsilon = true
+ t.outermostPrecedenceReturn = outermostPrecedenceReturn
+ return t
+}
+
+func (t *EpsilonTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return false
+}
+
+func (t *EpsilonTransition) String() string {
+ return "epsilon"
+}
+
+type RangeTransition struct {
+ *BaseTransition
+
+ start, stop int
+}
+
+func NewRangeTransition(target ATNState, start, stop int) *RangeTransition {
+
+ t := new(RangeTransition)
+ t.BaseTransition = NewBaseTransition(target)
+
+ t.serializationType = TransitionRANGE
+ t.start = start
+ t.stop = stop
+ t.intervalSet = t.makeLabel()
+ return t
+}
+
+func (t *RangeTransition) makeLabel() *IntervalSet {
+ s := NewIntervalSet()
+ s.addRange(t.start, t.stop)
+ return s
+}
+
+func (t *RangeTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return symbol >= t.start && symbol <= t.stop
+}
+
+func (t *RangeTransition) String() string {
+ return "'" + string(t.start) + "'..'" + string(t.stop) + "'"
+}
+
+type AbstractPredicateTransition interface {
+ Transition
+ IAbstractPredicateTransitionFoo()
+}
+
+type BaseAbstractPredicateTransition struct {
+ *BaseTransition
+}
+
+func NewBasePredicateTransition(target ATNState) *BaseAbstractPredicateTransition {
+
+ t := new(BaseAbstractPredicateTransition)
+ t.BaseTransition = NewBaseTransition(target)
+
+ return t
+}
+
+func (a *BaseAbstractPredicateTransition) IAbstractPredicateTransitionFoo() {}
+
+type PredicateTransition struct {
+ *BaseAbstractPredicateTransition
+
+ isCtxDependent bool
+ ruleIndex, predIndex int
+}
+
+func NewPredicateTransition(target ATNState, ruleIndex, predIndex int, isCtxDependent bool) *PredicateTransition {
+
+ t := new(PredicateTransition)
+ t.BaseAbstractPredicateTransition = NewBasePredicateTransition(target)
+
+ t.serializationType = TransitionPREDICATE
+ t.ruleIndex = ruleIndex
+ t.predIndex = predIndex
+ t.isCtxDependent = isCtxDependent // e.g., $i ref in pred
+ t.isEpsilon = true
+ return t
+}
+
+func (t *PredicateTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return false
+}
+
+func (t *PredicateTransition) getPredicate() *Predicate {
+ return NewPredicate(t.ruleIndex, t.predIndex, t.isCtxDependent)
+}
+
+func (t *PredicateTransition) String() string {
+ return "pred_" + strconv.Itoa(t.ruleIndex) + ":" + strconv.Itoa(t.predIndex)
+}
+
+type ActionTransition struct {
+ *BaseTransition
+
+ isCtxDependent bool
+ ruleIndex, actionIndex, predIndex int
+}
+
+func NewActionTransition(target ATNState, ruleIndex, actionIndex int, isCtxDependent bool) *ActionTransition {
+
+ t := new(ActionTransition)
+ t.BaseTransition = NewBaseTransition(target)
+
+ t.serializationType = TransitionACTION
+ t.ruleIndex = ruleIndex
+ t.actionIndex = actionIndex
+ t.isCtxDependent = isCtxDependent // e.g., $i ref in pred
+ t.isEpsilon = true
+ return t
+}
+
+func (t *ActionTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return false
+}
+
+func (t *ActionTransition) String() string {
+ return "action_" + strconv.Itoa(t.ruleIndex) + ":" + strconv.Itoa(t.actionIndex)
+}
+
+type SetTransition struct {
+ *BaseTransition
+}
+
+func NewSetTransition(target ATNState, set *IntervalSet) *SetTransition {
+
+ t := new(SetTransition)
+ t.BaseTransition = NewBaseTransition(target)
+
+ t.serializationType = TransitionSET
+ if set != nil {
+ t.intervalSet = set
+ } else {
+ t.intervalSet = NewIntervalSet()
+ t.intervalSet.addOne(TokenInvalidType)
+ }
+
+ return t
+}
+
+func (t *SetTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return t.intervalSet.contains(symbol)
+}
+
+func (t *SetTransition) String() string {
+ return t.intervalSet.String()
+}
+
+type NotSetTransition struct {
+ *SetTransition
+}
+
+func NewNotSetTransition(target ATNState, set *IntervalSet) *NotSetTransition {
+
+ t := new(NotSetTransition)
+
+ t.SetTransition = NewSetTransition(target, set)
+
+ t.serializationType = TransitionNOTSET
+
+ return t
+}
+
+func (t *NotSetTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return symbol >= minVocabSymbol && symbol <= maxVocabSymbol && !t.intervalSet.contains(symbol)
+}
+
+func (t *NotSetTransition) String() string {
+ return "~" + t.intervalSet.String()
+}
+
+type WildcardTransition struct {
+ *BaseTransition
+}
+
+func NewWildcardTransition(target ATNState) *WildcardTransition {
+
+ t := new(WildcardTransition)
+ t.BaseTransition = NewBaseTransition(target)
+
+ t.serializationType = TransitionWILDCARD
+ return t
+}
+
+func (t *WildcardTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return symbol >= minVocabSymbol && symbol <= maxVocabSymbol
+}
+
+func (t *WildcardTransition) String() string {
+ return "."
+}
+
+type PrecedencePredicateTransition struct {
+ *BaseAbstractPredicateTransition
+
+ precedence int
+}
+
+func NewPrecedencePredicateTransition(target ATNState, precedence int) *PrecedencePredicateTransition {
+
+ t := new(PrecedencePredicateTransition)
+ t.BaseAbstractPredicateTransition = NewBasePredicateTransition(target)
+
+ t.serializationType = TransitionPRECEDENCE
+ t.precedence = precedence
+ t.isEpsilon = true
+
+ return t
+}
+
+func (t *PrecedencePredicateTransition) Matches(symbol, minVocabSymbol, maxVocabSymbol int) bool {
+ return false
+}
+
+func (t *PrecedencePredicateTransition) getPredicate() *PrecedencePredicate {
+ return NewPrecedencePredicate(t.precedence)
+}
+
+func (t *PrecedencePredicateTransition) String() string {
+ return fmt.Sprint(t.precedence) + " >= _p"
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/tree.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/tree.go
new file mode 100644
index 0000000000..bdeb6d7881
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/tree.go
@@ -0,0 +1,256 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+// The basic notion of a tree has a parent, a payload, and a list of children.
+// It is the most abstract interface for all the trees used by ANTLR.
+///
+
+var TreeInvalidInterval = NewInterval(-1, -2)
+
+type Tree interface {
+ GetParent() Tree
+ SetParent(Tree)
+ GetPayload() interface{}
+ GetChild(i int) Tree
+ GetChildCount() int
+ GetChildren() []Tree
+}
+
+type SyntaxTree interface {
+ Tree
+
+ GetSourceInterval() *Interval
+}
+
+type ParseTree interface {
+ SyntaxTree
+
+ Accept(Visitor ParseTreeVisitor) interface{}
+ GetText() string
+
+ ToStringTree([]string, Recognizer) string
+}
+
+type RuleNode interface {
+ ParseTree
+
+ GetRuleContext() RuleContext
+ GetBaseRuleContext() *BaseRuleContext
+}
+
+type TerminalNode interface {
+ ParseTree
+
+ GetSymbol() Token
+}
+
+type ErrorNode interface {
+ TerminalNode
+
+ errorNode()
+}
+
+type ParseTreeVisitor interface {
+ Visit(tree ParseTree) interface{}
+ VisitChildren(node RuleNode) interface{}
+ VisitTerminal(node TerminalNode) interface{}
+ VisitErrorNode(node ErrorNode) interface{}
+}
+
+type BaseParseTreeVisitor struct{}
+
+var _ ParseTreeVisitor = &BaseParseTreeVisitor{}
+
+func (v *BaseParseTreeVisitor) Visit(tree ParseTree) interface{} { return nil }
+func (v *BaseParseTreeVisitor) VisitChildren(node RuleNode) interface{} { return nil }
+func (v *BaseParseTreeVisitor) VisitTerminal(node TerminalNode) interface{} { return nil }
+func (v *BaseParseTreeVisitor) VisitErrorNode(node ErrorNode) interface{} { return nil }
+
+// TODO
+//func (this ParseTreeVisitor) Visit(ctx) {
+// if (Utils.isArray(ctx)) {
+// self := this
+// return ctx.map(function(child) { return VisitAtom(self, child)})
+// } else {
+// return VisitAtom(this, ctx)
+// }
+//}
+//
+//func VisitAtom(Visitor, ctx) {
+// if (ctx.parser == nil) { //is terminal
+// return
+// }
+//
+// name := ctx.parser.ruleNames[ctx.ruleIndex]
+// funcName := "Visit" + Utils.titleCase(name)
+//
+// return Visitor[funcName](ctx)
+//}
+
+type ParseTreeListener interface {
+ VisitTerminal(node TerminalNode)
+ VisitErrorNode(node ErrorNode)
+ EnterEveryRule(ctx ParserRuleContext)
+ ExitEveryRule(ctx ParserRuleContext)
+}
+
+type BaseParseTreeListener struct{}
+
+var _ ParseTreeListener = &BaseParseTreeListener{}
+
+func (l *BaseParseTreeListener) VisitTerminal(node TerminalNode) {}
+func (l *BaseParseTreeListener) VisitErrorNode(node ErrorNode) {}
+func (l *BaseParseTreeListener) EnterEveryRule(ctx ParserRuleContext) {}
+func (l *BaseParseTreeListener) ExitEveryRule(ctx ParserRuleContext) {}
+
+type TerminalNodeImpl struct {
+ parentCtx RuleContext
+
+ symbol Token
+}
+
+var _ TerminalNode = &TerminalNodeImpl{}
+
+func NewTerminalNodeImpl(symbol Token) *TerminalNodeImpl {
+ tn := new(TerminalNodeImpl)
+
+ tn.parentCtx = nil
+ tn.symbol = symbol
+
+ return tn
+}
+
+func (t *TerminalNodeImpl) GetChild(i int) Tree {
+ return nil
+}
+
+func (t *TerminalNodeImpl) GetChildren() []Tree {
+ return nil
+}
+
+func (t *TerminalNodeImpl) SetChildren(tree []Tree) {
+ panic("Cannot set children on terminal node")
+}
+
+func (t *TerminalNodeImpl) GetSymbol() Token {
+ return t.symbol
+}
+
+func (t *TerminalNodeImpl) GetParent() Tree {
+ return t.parentCtx
+}
+
+func (t *TerminalNodeImpl) SetParent(tree Tree) {
+ t.parentCtx = tree.(RuleContext)
+}
+
+func (t *TerminalNodeImpl) GetPayload() interface{} {
+ return t.symbol
+}
+
+func (t *TerminalNodeImpl) GetSourceInterval() *Interval {
+ if t.symbol == nil {
+ return TreeInvalidInterval
+ }
+ tokenIndex := t.symbol.GetTokenIndex()
+ return NewInterval(tokenIndex, tokenIndex)
+}
+
+func (t *TerminalNodeImpl) GetChildCount() int {
+ return 0
+}
+
+func (t *TerminalNodeImpl) Accept(v ParseTreeVisitor) interface{} {
+ return v.VisitTerminal(t)
+}
+
+func (t *TerminalNodeImpl) GetText() string {
+ return t.symbol.GetText()
+}
+
+func (t *TerminalNodeImpl) String() string {
+ if t.symbol.GetTokenType() == TokenEOF {
+ return ""
+ }
+
+ return t.symbol.GetText()
+}
+
+func (t *TerminalNodeImpl) ToStringTree(s []string, r Recognizer) string {
+ return t.String()
+}
+
+// Represents a token that was consumed during reSynchronization
+// rather than during a valid Match operation. For example,
+// we will create this kind of a node during single token insertion
+// and deletion as well as during "consume until error recovery set"
+// upon no viable alternative exceptions.
+
+type ErrorNodeImpl struct {
+ *TerminalNodeImpl
+}
+
+var _ ErrorNode = &ErrorNodeImpl{}
+
+func NewErrorNodeImpl(token Token) *ErrorNodeImpl {
+ en := new(ErrorNodeImpl)
+ en.TerminalNodeImpl = NewTerminalNodeImpl(token)
+ return en
+}
+
+func (e *ErrorNodeImpl) errorNode() {}
+
+func (e *ErrorNodeImpl) Accept(v ParseTreeVisitor) interface{} {
+ return v.VisitErrorNode(e)
+}
+
+type ParseTreeWalker struct {
+}
+
+func NewParseTreeWalker() *ParseTreeWalker {
+ return new(ParseTreeWalker)
+}
+
+// Performs a walk on the given parse tree starting at the root and going down recursively
+// with depth-first search. On each node, EnterRule is called before
+// recursively walking down into child nodes, then
+// ExitRule is called after the recursive call to wind up.
+func (p *ParseTreeWalker) Walk(listener ParseTreeListener, t Tree) {
+ switch tt := t.(type) {
+ case ErrorNode:
+ listener.VisitErrorNode(tt)
+ case TerminalNode:
+ listener.VisitTerminal(tt)
+ default:
+ p.EnterRule(listener, t.(RuleNode))
+ for i := 0; i < t.GetChildCount(); i++ {
+ child := t.GetChild(i)
+ p.Walk(listener, child)
+ }
+ p.ExitRule(listener, t.(RuleNode))
+ }
+}
+
+//
+// Enters a grammar rule by first triggering the generic event {@link ParseTreeListener//EnterEveryRule}
+// then by triggering the event specific to the given parse tree node
+//
+func (p *ParseTreeWalker) EnterRule(listener ParseTreeListener, r RuleNode) {
+ ctx := r.GetRuleContext().(ParserRuleContext)
+ listener.EnterEveryRule(ctx)
+ ctx.EnterRule(listener)
+}
+
+// Exits a grammar rule by first triggering the event specific to the given parse tree node
+// then by triggering the generic event {@link ParseTreeListener//ExitEveryRule}
+//
+func (p *ParseTreeWalker) ExitRule(listener ParseTreeListener, r RuleNode) {
+ ctx := r.GetRuleContext().(ParserRuleContext)
+ ctx.ExitRule(listener)
+ listener.ExitEveryRule(ctx)
+}
+
+var ParseTreeWalkerDefault = NewParseTreeWalker()
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/trees.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/trees.go
new file mode 100644
index 0000000000..80144ecade
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/trees.go
@@ -0,0 +1,137 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import "fmt"
+
+/** A set of utility routines useful for all kinds of ANTLR trees. */
+
+// Print out a whole tree in LISP form. {@link //getNodeText} is used on the
+// node payloads to get the text for the nodes. Detect
+// parse trees and extract data appropriately.
+func TreesStringTree(tree Tree, ruleNames []string, recog Recognizer) string {
+
+ if recog != nil {
+ ruleNames = recog.GetRuleNames()
+ }
+
+ s := TreesGetNodeText(tree, ruleNames, nil)
+
+ s = EscapeWhitespace(s, false)
+ c := tree.GetChildCount()
+ if c == 0 {
+ return s
+ }
+ res := "(" + s + " "
+ if c > 0 {
+ s = TreesStringTree(tree.GetChild(0), ruleNames, nil)
+ res += s
+ }
+ for i := 1; i < c; i++ {
+ s = TreesStringTree(tree.GetChild(i), ruleNames, nil)
+ res += (" " + s)
+ }
+ res += ")"
+ return res
+}
+
+func TreesGetNodeText(t Tree, ruleNames []string, recog Parser) string {
+ if recog != nil {
+ ruleNames = recog.GetRuleNames()
+ }
+
+ if ruleNames != nil {
+ switch t2 := t.(type) {
+ case RuleNode:
+ t3 := t2.GetRuleContext()
+ altNumber := t3.GetAltNumber()
+
+ if altNumber != ATNInvalidAltNumber {
+ return fmt.Sprintf("%s:%d", ruleNames[t3.GetRuleIndex()], altNumber)
+ }
+ return ruleNames[t3.GetRuleIndex()]
+ case ErrorNode:
+ return fmt.Sprint(t2)
+ case TerminalNode:
+ if t2.GetSymbol() != nil {
+ return t2.GetSymbol().GetText()
+ }
+ }
+ }
+
+ // no recog for rule names
+ payload := t.GetPayload()
+ if p2, ok := payload.(Token); ok {
+ return p2.GetText()
+ }
+
+ return fmt.Sprint(t.GetPayload())
+}
+
+// Return ordered list of all children of this node
+func TreesGetChildren(t Tree) []Tree {
+ list := make([]Tree, 0)
+ for i := 0; i < t.GetChildCount(); i++ {
+ list = append(list, t.GetChild(i))
+ }
+ return list
+}
+
+// Return a list of all ancestors of this node. The first node of
+// list is the root and the last is the parent of this node.
+//
+func TreesgetAncestors(t Tree) []Tree {
+ ancestors := make([]Tree, 0)
+ t = t.GetParent()
+ for t != nil {
+ f := []Tree{t}
+ ancestors = append(f, ancestors...)
+ t = t.GetParent()
+ }
+ return ancestors
+}
+
+func TreesFindAllTokenNodes(t ParseTree, ttype int) []ParseTree {
+ return TreesfindAllNodes(t, ttype, true)
+}
+
+func TreesfindAllRuleNodes(t ParseTree, ruleIndex int) []ParseTree {
+ return TreesfindAllNodes(t, ruleIndex, false)
+}
+
+func TreesfindAllNodes(t ParseTree, index int, findTokens bool) []ParseTree {
+ nodes := make([]ParseTree, 0)
+ treesFindAllNodes(t, index, findTokens, &nodes)
+ return nodes
+}
+
+func treesFindAllNodes(t ParseTree, index int, findTokens bool, nodes *[]ParseTree) {
+ // check this node (the root) first
+
+ t2, ok := t.(TerminalNode)
+ t3, ok2 := t.(ParserRuleContext)
+
+ if findTokens && ok {
+ if t2.GetSymbol().GetTokenType() == index {
+ *nodes = append(*nodes, t2)
+ }
+ } else if !findTokens && ok2 {
+ if t3.GetRuleIndex() == index {
+ *nodes = append(*nodes, t3)
+ }
+ }
+ // check children
+ for i := 0; i < t.GetChildCount(); i++ {
+ treesFindAllNodes(t.GetChild(i).(ParseTree), index, findTokens, nodes)
+ }
+}
+
+func TreesDescendants(t ParseTree) []ParseTree {
+ nodes := []ParseTree{t}
+ for i := 0; i < t.GetChildCount(); i++ {
+ nodes = append(nodes, TreesDescendants(t.GetChild(i).(ParseTree))...)
+ }
+ return nodes
+}
diff --git a/vendor/github.com/antlr/antlr4/runtime/Go/antlr/utils.go b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/utils.go
new file mode 100644
index 0000000000..bba2ffae79
--- /dev/null
+++ b/vendor/github.com/antlr/antlr4/runtime/Go/antlr/utils.go
@@ -0,0 +1,417 @@
+// Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
+// Use of this file is governed by the BSD 3-clause license that
+// can be found in the LICENSE.txt file in the project root.
+
+package antlr
+
+import (
+ "bytes"
+ "errors"
+ "fmt"
+ "sort"
+ "strconv"
+ "strings"
+)
+
+func intMin(a, b int) int {
+ if a < b {
+ return a
+ }
+ return b
+}
+
+func intMax(a, b int) int {
+ if a > b {
+ return a
+ }
+ return b
+}
+
+// A simple integer stack
+
+type IntStack []int
+
+var ErrEmptyStack = errors.New("Stack is empty")
+
+func (s *IntStack) Pop() (int, error) {
+ l := len(*s) - 1
+ if l < 0 {
+ return 0, ErrEmptyStack
+ }
+ v := (*s)[l]
+ *s = (*s)[0:l]
+ return v, nil
+}
+
+func (s *IntStack) Push(e int) {
+ *s = append(*s, e)
+}
+
+type Set struct {
+ data map[int][]interface{}
+ hashcodeFunction func(interface{}) int
+ equalsFunction func(interface{}, interface{}) bool
+}
+
+func NewSet(
+ hashcodeFunction func(interface{}) int,
+ equalsFunction func(interface{}, interface{}) bool) *Set {
+
+ s := new(Set)
+
+ s.data = make(map[int][]interface{})
+
+ if hashcodeFunction != nil {
+ s.hashcodeFunction = hashcodeFunction
+ } else {
+ s.hashcodeFunction = standardHashFunction
+ }
+
+ if equalsFunction == nil {
+ s.equalsFunction = standardEqualsFunction
+ } else {
+ s.equalsFunction = equalsFunction
+ }
+
+ return s
+}
+
+func standardEqualsFunction(a interface{}, b interface{}) bool {
+
+ ac, oka := a.(comparable)
+ bc, okb := b.(comparable)
+
+ if !oka || !okb {
+ panic("Not Comparable")
+ }
+
+ return ac.equals(bc)
+}
+
+func standardHashFunction(a interface{}) int {
+ if h, ok := a.(hasher); ok {
+ return h.hash()
+ }
+
+ panic("Not Hasher")
+}
+
+type hasher interface {
+ hash() int
+}
+
+func (s *Set) length() int {
+ return len(s.data)
+}
+
+func (s *Set) add(value interface{}) interface{} {
+
+ key := s.hashcodeFunction(value)
+
+ values := s.data[key]
+
+ if s.data[key] != nil {
+ for i := 0; i < len(values); i++ {
+ if s.equalsFunction(value, values[i]) {
+ return values[i]
+ }
+ }
+
+ s.data[key] = append(s.data[key], value)
+ return value
+ }
+
+ v := make([]interface{}, 1, 10)
+ v[0] = value
+ s.data[key] = v
+
+ return value
+}
+
+func (s *Set) contains(value interface{}) bool {
+
+ key := s.hashcodeFunction(value)
+
+ values := s.data[key]
+
+ if s.data[key] != nil {
+ for i := 0; i < len(values); i++ {
+ if s.equalsFunction(value, values[i]) {
+ return true
+ }
+ }
+ }
+ return false
+}
+
+func (s *Set) values() []interface{} {
+ var l []interface{}
+
+ for _, v := range s.data {
+ l = append(l, v...)
+ }
+
+ return l
+}
+
+func (s *Set) String() string {
+ r := ""
+
+ for _, av := range s.data {
+ for _, v := range av {
+ r += fmt.Sprint(v)
+ }
+ }
+
+ return r
+}
+
+type BitSet struct {
+ data map[int]bool
+}
+
+func NewBitSet() *BitSet {
+ b := new(BitSet)
+ b.data = make(map[int]bool)
+ return b
+}
+
+func (b *BitSet) add(value int) {
+ b.data[value] = true
+}
+
+func (b *BitSet) clear(index int) {
+ delete(b.data, index)
+}
+
+func (b *BitSet) or(set *BitSet) {
+ for k := range set.data {
+ b.add(k)
+ }
+}
+
+func (b *BitSet) remove(value int) {
+ delete(b.data, value)
+}
+
+func (b *BitSet) contains(value int) bool {
+ return b.data[value]
+}
+
+func (b *BitSet) values() []int {
+ ks := make([]int, len(b.data))
+ i := 0
+ for k := range b.data {
+ ks[i] = k
+ i++
+ }
+ sort.Ints(ks)
+ return ks
+}
+
+func (b *BitSet) minValue() int {
+ min := 2147483647
+
+ for k := range b.data {
+ if k < min {
+ min = k
+ }
+ }
+
+ return min
+}
+
+func (b *BitSet) equals(other interface{}) bool {
+ otherBitSet, ok := other.(*BitSet)
+ if !ok {
+ return false
+ }
+
+ if len(b.data) != len(otherBitSet.data) {
+ return false
+ }
+
+ for k, v := range b.data {
+ if otherBitSet.data[k] != v {
+ return false
+ }
+ }
+
+ return true
+}
+
+func (b *BitSet) length() int {
+ return len(b.data)
+}
+
+func (b *BitSet) String() string {
+ vals := b.values()
+ valsS := make([]string, len(vals))
+
+ for i, val := range vals {
+ valsS[i] = strconv.Itoa(val)
+ }
+ return "{" + strings.Join(valsS, ", ") + "}"
+}
+
+type AltDict struct {
+ data map[string]interface{}
+}
+
+func NewAltDict() *AltDict {
+ d := new(AltDict)
+ d.data = make(map[string]interface{})
+ return d
+}
+
+func (a *AltDict) Get(key string) interface{} {
+ key = "k-" + key
+ return a.data[key]
+}
+
+func (a *AltDict) put(key string, value interface{}) {
+ key = "k-" + key
+ a.data[key] = value
+}
+
+func (a *AltDict) values() []interface{} {
+ vs := make([]interface{}, len(a.data))
+ i := 0
+ for _, v := range a.data {
+ vs[i] = v
+ i++
+ }
+ return vs
+}
+
+type DoubleDict struct {
+ data map[int]map[int]interface{}
+}
+
+func NewDoubleDict() *DoubleDict {
+ dd := new(DoubleDict)
+ dd.data = make(map[int]map[int]interface{})
+ return dd
+}
+
+func (d *DoubleDict) Get(a, b int) interface{} {
+ data := d.data[a]
+
+ if data == nil {
+ return nil
+ }
+
+ return data[b]
+}
+
+func (d *DoubleDict) set(a, b int, o interface{}) {
+ data := d.data[a]
+
+ if data == nil {
+ data = make(map[int]interface{})
+ d.data[a] = data
+ }
+
+ data[b] = o
+}
+
+func EscapeWhitespace(s string, escapeSpaces bool) string {
+
+ s = strings.Replace(s, "\t", "\\t", -1)
+ s = strings.Replace(s, "\n", "\\n", -1)
+ s = strings.Replace(s, "\r", "\\r", -1)
+ if escapeSpaces {
+ s = strings.Replace(s, " ", "\u00B7", -1)
+ }
+ return s
+}
+
+func TerminalNodeToStringArray(sa []TerminalNode) []string {
+ st := make([]string, len(sa))
+
+ for i, s := range sa {
+ st[i] = fmt.Sprintf("%v", s)
+ }
+
+ return st
+}
+
+func PrintArrayJavaStyle(sa []string) string {
+ var buffer bytes.Buffer
+
+ buffer.WriteString("[")
+
+ for i, s := range sa {
+ buffer.WriteString(s)
+ if i != len(sa)-1 {
+ buffer.WriteString(", ")
+ }
+ }
+
+ buffer.WriteString("]")
+
+ return buffer.String()
+}
+
+// The following routines were lifted from bits.rotate* available in Go 1.9.
+
+const uintSize = 32 << (^uint(0) >> 32 & 1) // 32 or 64
+
+// rotateLeft returns the value of x rotated left by (k mod UintSize) bits.
+// To rotate x right by k bits, call RotateLeft(x, -k).
+func rotateLeft(x uint, k int) uint {
+ if uintSize == 32 {
+ return uint(rotateLeft32(uint32(x), k))
+ }
+ return uint(rotateLeft64(uint64(x), k))
+}
+
+// rotateLeft32 returns the value of x rotated left by (k mod 32) bits.
+func rotateLeft32(x uint32, k int) uint32 {
+ const n = 32
+ s := uint(k) & (n - 1)
+ return x<>(n-s)
+}
+
+// rotateLeft64 returns the value of x rotated left by (k mod 64) bits.
+func rotateLeft64(x uint64, k int) uint64 {
+ const n = 64
+ s := uint(k) & (n - 1)
+ return x<>(n-s)
+}
+
+
+// murmur hash
+const (
+ c1_32 uint = 0xCC9E2D51
+ c2_32 uint = 0x1B873593
+ n1_32 uint = 0xE6546B64
+)
+
+func murmurInit(seed int) int {
+ return seed
+}
+
+func murmurUpdate(h1 int, k1 int) int {
+ var k1u uint
+ k1u = uint(k1) * c1_32
+ k1u = rotateLeft(k1u, 15)
+ k1u *= c2_32
+
+ var h1u = uint(h1) ^ k1u
+ k1u = rotateLeft(k1u, 13)
+ h1u = h1u*5 + 0xe6546b64
+ return int(h1u)
+}
+
+func murmurFinish(h1 int, numberOfWords int) int {
+ var h1u uint = uint(h1)
+ h1u ^= uint(numberOfWords * 4)
+ h1u ^= h1u >> 16
+ h1u *= uint(0x85ebca6b)
+ h1u ^= h1u >> 13
+ h1u *= 0xc2b2ae35
+ h1u ^= h1u >> 16
+
+ return int(h1u)
+}
diff --git a/vendor/github.com/google/cel-go/LICENSE b/vendor/github.com/google/cel-go/LICENSE
new file mode 100644
index 0000000000..d645695673
--- /dev/null
+++ b/vendor/github.com/google/cel-go/LICENSE
@@ -0,0 +1,202 @@
+
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
diff --git a/vendor/github.com/google/cel-go/cel/BUILD.bazel b/vendor/github.com/google/cel-go/cel/BUILD.bazel
new file mode 100644
index 0000000000..aed8274449
--- /dev/null
+++ b/vendor/github.com/google/cel-go/cel/BUILD.bazel
@@ -0,0 +1,64 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "cel.go",
+ "env.go",
+ "io.go",
+ "library.go",
+ "options.go",
+ "program.go",
+ ],
+ importpath = "github.com/google/cel-go/cel",
+ visibility = ["//visibility:public"],
+ deps = [
+ "//checker:go_default_library",
+ "//checker/decls:go_default_library",
+ "//common:go_default_library",
+ "//common/containers:go_default_library",
+ "//common/types:go_default_library",
+ "//common/types/pb:go_default_library",
+ "//common/types/ref:go_default_library",
+ "//interpreter:go_default_library",
+ "//interpreter/functions:go_default_library",
+ "//parser:go_default_library",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//proto:go_default_library",
+ "@org_golang_google_protobuf//reflect/protodesc:go_default_library",
+ "@org_golang_google_protobuf//reflect/protoreflect:go_default_library",
+ "@org_golang_google_protobuf//reflect/protoregistry:go_default_library",
+ "@org_golang_google_protobuf//types/descriptorpb:go_default_library",
+ "@org_golang_google_protobuf//types/dynamicpb:go_default_library",
+ ],
+)
+
+go_test(
+ name = "go_default_test",
+ srcs = [
+ "cel_test.go",
+ ],
+ data = [
+ "//cel/testdata:gen_test_fds",
+ ],
+ embed = [
+ ":go_default_library",
+ ],
+ deps = [
+ "//checker/decls:go_default_library",
+ "//common/operators:go_default_library",
+ "//common/overloads:go_default_library",
+ "//common/types:go_default_library",
+ "//common/types/ref:go_default_library",
+ "//common/types/traits:go_default_library",
+ "//interpreter/functions:go_default_library",
+ "//test/proto2pb:go_default_library",
+ "//test/proto3pb:go_default_library",
+ "@io_bazel_rules_go//proto/wkt:descriptor_go_proto",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/cel/cel.go b/vendor/github.com/google/cel-go/cel/cel.go
new file mode 100644
index 0000000000..eb5a9f4cc5
--- /dev/null
+++ b/vendor/github.com/google/cel-go/cel/cel.go
@@ -0,0 +1,19 @@
+// Copyright 2019 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package cel defines the top-level interface for the Common Expression Language (CEL).
+//
+// CEL is a non-Turing complete expression language designed to parse, check, and evaluate
+// expressions against user-defined environments.
+package cel
diff --git a/vendor/github.com/google/cel-go/cel/env.go b/vendor/github.com/google/cel-go/cel/env.go
new file mode 100644
index 0000000000..a35ac190fb
--- /dev/null
+++ b/vendor/github.com/google/cel-go/cel/env.go
@@ -0,0 +1,466 @@
+// Copyright 2019 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package cel
+
+import (
+ "errors"
+ "sync"
+
+ "github.com/google/cel-go/checker"
+ "github.com/google/cel-go/checker/decls"
+ "github.com/google/cel-go/common"
+ "github.com/google/cel-go/common/containers"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/interpreter"
+ "github.com/google/cel-go/parser"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// Source interface representing a user-provided expression.
+type Source interface {
+ common.Source
+}
+
+// Ast representing the checked or unchecked expression, its source, and related metadata such as
+// source position information.
+type Ast struct {
+ expr *exprpb.Expr
+ info *exprpb.SourceInfo
+ source Source
+ refMap map[int64]*exprpb.Reference
+ typeMap map[int64]*exprpb.Type
+}
+
+// Expr returns the proto serializable instance of the parsed/checked expression.
+func (ast *Ast) Expr() *exprpb.Expr {
+ return ast.expr
+}
+
+// IsChecked returns whether the Ast value has been successfully type-checked.
+func (ast *Ast) IsChecked() bool {
+ return ast.typeMap != nil && len(ast.typeMap) > 0
+}
+
+// SourceInfo returns character offset and newling position information about expression elements.
+func (ast *Ast) SourceInfo() *exprpb.SourceInfo {
+ return ast.info
+}
+
+// ResultType returns the output type of the expression if the Ast has been type-checked, else
+// returns decls.Dyn as the parse step cannot infer the type.
+func (ast *Ast) ResultType() *exprpb.Type {
+ if !ast.IsChecked() {
+ return decls.Dyn
+ }
+ return ast.typeMap[ast.expr.Id]
+}
+
+// Source returns a view of the input used to create the Ast. This source may be complete or
+// constructed from the SourceInfo.
+func (ast *Ast) Source() Source {
+ return ast.source
+}
+
+// FormatType converts a type message into a string representation.
+func FormatType(t *exprpb.Type) string {
+ return checker.FormatCheckedType(t)
+}
+
+// Env encapsulates the context necessary to perform parsing, type checking, or generation of
+// evaluable programs for different expressions.
+type Env struct {
+ Container *containers.Container
+ declarations []*exprpb.Decl
+ macros []parser.Macro
+ adapter ref.TypeAdapter
+ provider ref.TypeProvider
+ features map[int]bool
+ // program options tied to the environment.
+ progOpts []ProgramOption
+
+ // Internal checker representation
+ chk *checker.Env
+ chkErr error
+ once sync.Once
+}
+
+// NewEnv creates a program environment configured with the standard library of CEL functions and
+// macros. The Env value returned can parse and check any CEL program which builds upon the core
+// features documented in the CEL specification.
+//
+// See the EnvOption helper functions for the options that can be used to configure the
+// environment.
+func NewEnv(opts ...EnvOption) (*Env, error) {
+ stdOpts := append([]EnvOption{StdLib()}, opts...)
+ return NewCustomEnv(stdOpts...)
+}
+
+// NewCustomEnv creates a custom program environment which is not automatically configured with the
+// standard library of functions and macros documented in the CEL spec.
+//
+// The purpose for using a custom environment might be for subsetting the standard library produced
+// by the cel.StdLib() function. Subsetting CEL is a core aspect of its design that allows users to
+// limit the compute and memory impact of a CEL program by controlling the functions and macros
+// that may appear in a given expression.
+//
+// See the EnvOption helper functions for the options that can be used to configure the
+// environment.
+func NewCustomEnv(opts ...EnvOption) (*Env, error) {
+ registry, err := types.NewRegistry()
+ if err != nil {
+ return nil, err
+ }
+ return (&Env{
+ declarations: []*exprpb.Decl{},
+ macros: []parser.Macro{},
+ Container: containers.DefaultContainer,
+ adapter: registry,
+ provider: registry,
+ features: map[int]bool{},
+ progOpts: []ProgramOption{},
+ }).configure(opts)
+}
+
+// Check performs type-checking on the input Ast and yields a checked Ast and/or set of Issues.
+//
+// Checking has failed if the returned Issues value and its Issues.Err() value are non-nil.
+// Issues should be inspected if they are non-nil, but may not represent a fatal error.
+//
+// It is possible to have both non-nil Ast and Issues values returned from this call: however,
+// the mere presence of an Ast does not imply that it is valid for use.
+func (e *Env) Check(ast *Ast) (*Ast, *Issues) {
+ // Note, errors aren't currently possible on the Ast to ParsedExpr conversion.
+ pe, _ := AstToParsedExpr(ast)
+
+ // Construct the internal checker env, erroring if there is an issue adding the declarations.
+ e.once.Do(func() {
+ ce := checker.NewEnv(e.Container, e.provider)
+ ce.EnableDynamicAggregateLiterals(true)
+ if e.HasFeature(FeatureDisableDynamicAggregateLiterals) {
+ ce.EnableDynamicAggregateLiterals(false)
+ }
+ err := ce.Add(e.declarations...)
+ if err != nil {
+ e.chkErr = err
+ } else {
+ e.chk = ce
+ }
+ })
+ // The once call will ensure that this value is set or nil for all invocations.
+ if e.chkErr != nil {
+ errs := common.NewErrors(ast.Source())
+ errs.ReportError(common.NoLocation, e.chkErr.Error())
+ return nil, NewIssues(errs)
+ }
+
+ res, errs := checker.Check(pe, ast.Source(), e.chk)
+ if len(errs.GetErrors()) > 0 {
+ return nil, NewIssues(errs)
+ }
+ // Manually create the Ast to ensure that the Ast source information (which may be more
+ // detailed than the information provided by Check), is returned to the caller.
+ return &Ast{
+ source: ast.Source(),
+ expr: res.GetExpr(),
+ info: res.GetSourceInfo(),
+ refMap: res.GetReferenceMap(),
+ typeMap: res.GetTypeMap()}, nil
+}
+
+// Compile combines the Parse and Check phases CEL program compilation to produce an Ast and
+// associated issues.
+//
+// If an error is encountered during parsing the Compile step will not continue with the Check
+// phase. If non-error issues are encountered during Parse, they may be combined with any issues
+// discovered during Check.
+//
+// Note, for parse-only uses of CEL use Parse.
+func (e *Env) Compile(txt string) (*Ast, *Issues) {
+ return e.CompileSource(common.NewTextSource(txt))
+}
+
+// CompileSource combines the Parse and Check phases CEL program compilation to produce an Ast and
+// associated issues.
+//
+// If an error is encountered during parsing the CompileSource step will not continue with the
+// Check phase. If non-error issues are encountered during Parse, they may be combined with any
+// issues discovered during Check.
+//
+// Note, for parse-only uses of CEL use Parse.
+func (e *Env) CompileSource(src common.Source) (*Ast, *Issues) {
+ ast, iss := e.ParseSource(src)
+ if iss.Err() != nil {
+ return nil, iss
+ }
+ checked, iss2 := e.Check(ast)
+ iss = iss.Append(iss2)
+ if iss.Err() != nil {
+ return nil, iss
+ }
+ return checked, iss
+}
+
+// Extend the current environment with additional options to produce a new Env.
+//
+// Note, the extended Env value should not share memory with the original. It is possible, however,
+// that a CustomTypeAdapter or CustomTypeProvider options could provide values which are mutable.
+// To ensure separation of state between extended environments either make sure the TypeAdapter and
+// TypeProvider are immutable, or that their underlying implementations are based on the
+// ref.TypeRegistry which provides a Copy method which will be invoked by this method.
+func (e *Env) Extend(opts ...EnvOption) (*Env, error) {
+ if e.chkErr != nil {
+ return nil, e.chkErr
+ }
+ // Copy slices.
+ decsCopy := make([]*exprpb.Decl, len(e.declarations))
+ macsCopy := make([]parser.Macro, len(e.macros))
+ progOptsCopy := make([]ProgramOption, len(e.progOpts))
+ copy(decsCopy, e.declarations)
+ copy(macsCopy, e.macros)
+ copy(progOptsCopy, e.progOpts)
+
+ // Copy the adapter / provider if they appear to be mutable.
+ adapter := e.adapter
+ provider := e.provider
+ adapterReg, isAdapterReg := e.adapter.(ref.TypeRegistry)
+ providerReg, isProviderReg := e.provider.(ref.TypeRegistry)
+ // In most cases the provider and adapter will be a ref.TypeRegistry;
+ // however, in the rare cases where they are not, they are assumed to
+ // be immutable. Since it is possible to set the TypeProvider separately
+ // from the TypeAdapter, the possible configurations which could use a
+ // TypeRegistry as the base implementation are captured below.
+ if isAdapterReg && isProviderReg {
+ reg := providerReg.Copy()
+ provider = reg
+ // If the adapter and provider are the same object, set the adapter
+ // to the same ref.TypeRegistry as the provider.
+ if adapterReg == providerReg {
+ adapter = reg
+ } else {
+ // Otherwise, make a copy of the adapter.
+ adapter = adapterReg.Copy()
+ }
+ } else if isProviderReg {
+ provider = providerReg.Copy()
+ } else if isAdapterReg {
+ adapter = adapterReg.Copy()
+ }
+
+ featuresCopy := make(map[int]bool, len(e.features))
+ for k, v := range e.features {
+ featuresCopy[k] = v
+ }
+
+ ext := &Env{
+ Container: e.Container,
+ declarations: decsCopy,
+ macros: macsCopy,
+ progOpts: progOptsCopy,
+ adapter: adapter,
+ features: featuresCopy,
+ provider: provider,
+ }
+ return ext.configure(opts)
+}
+
+// HasFeature checks whether the environment enables the given feature
+// flag, as enumerated in options.go.
+func (e *Env) HasFeature(flag int) bool {
+ _, has := e.features[flag]
+ return has
+}
+
+// Parse parses the input expression value `txt` to a Ast and/or a set of Issues.
+//
+// This form of Parse creates a common.Source value for the input `txt` and forwards to the
+// ParseSource method.
+func (e *Env) Parse(txt string) (*Ast, *Issues) {
+ src := common.NewTextSource(txt)
+ return e.ParseSource(src)
+}
+
+// ParseSource parses the input source to an Ast and/or set of Issues.
+//
+// Parsing has failed if the returned Issues value and its Issues.Err() value is non-nil.
+// Issues should be inspected if they are non-nil, but may not represent a fatal error.
+//
+// It is possible to have both non-nil Ast and Issues values returned from this call; however,
+// the mere presence of an Ast does not imply that it is valid for use.
+func (e *Env) ParseSource(src common.Source) (*Ast, *Issues) {
+ res, errs := parser.ParseWithMacros(src, e.macros)
+ if len(errs.GetErrors()) > 0 {
+ return nil, &Issues{errs: errs}
+ }
+ // Manually create the Ast to ensure that the text source information is propagated on
+ // subsequent calls to Check.
+ return &Ast{
+ source: Source(src),
+ expr: res.GetExpr(),
+ info: res.GetSourceInfo()}, nil
+}
+
+// Program generates an evaluable instance of the Ast within the environment (Env).
+func (e *Env) Program(ast *Ast, opts ...ProgramOption) (Program, error) {
+ optSet := e.progOpts
+ if len(opts) != 0 {
+ mergedOpts := []ProgramOption{}
+ mergedOpts = append(mergedOpts, e.progOpts...)
+ mergedOpts = append(mergedOpts, opts...)
+ optSet = mergedOpts
+ }
+ return newProgram(e, ast, optSet)
+}
+
+// SetFeature sets the given feature flag, as enumerated in options.go.
+func (e *Env) SetFeature(flag int) {
+ e.features[flag] = true
+}
+
+// TypeAdapter returns the `ref.TypeAdapter` configured for the environment.
+func (e *Env) TypeAdapter() ref.TypeAdapter {
+ return e.adapter
+}
+
+// TypeProvider returns the `ref.TypeProvider` configured for the environment.
+func (e *Env) TypeProvider() ref.TypeProvider {
+ return e.provider
+}
+
+// UnknownVars returns an interpreter.PartialActivation which marks all variables
+// declared in the Env as unknown AttributePattern values.
+//
+// Note, the UnknownVars will behave the same as an interpreter.EmptyActivation
+// unless the PartialAttributes option is provided as a ProgramOption.
+func (e *Env) UnknownVars() interpreter.PartialActivation {
+ var unknownPatterns []*interpreter.AttributePattern
+ for _, d := range e.declarations {
+ switch d.GetDeclKind().(type) {
+ case *exprpb.Decl_Ident:
+ unknownPatterns = append(unknownPatterns,
+ interpreter.NewAttributePattern(d.GetName()))
+ }
+ }
+ part, _ := PartialVars(
+ interpreter.EmptyActivation(),
+ unknownPatterns...)
+ return part
+}
+
+// ResidualAst takes an Ast and its EvalDetails to produce a new Ast which only contains the
+// attribute references which are unknown.
+//
+// Residual expressions are beneficial in a few scenarios:
+//
+// - Optimizing constant expression evaluations away.
+// - Indexing and pruning expressions based on known input arguments.
+// - Surfacing additional requirements that are needed in order to complete an evaluation.
+// - Sharing the evaluation of an expression across multiple machines/nodes.
+//
+// For example, if an expression targets a 'resource' and 'request' attribute and the possible
+// values for the resource are known, a PartialActivation could mark the 'request' as an unknown
+// interpreter.AttributePattern and the resulting ResidualAst would be reduced to only the parts
+// of the expression that reference the 'request'.
+//
+// Note, the expression ids within the residual AST generated through this method have no
+// correlation to the expression ids of the original AST.
+//
+// See the PartialVars helper for how to construct a PartialActivation.
+//
+// TODO: Consider adding an option to generate a Program.Residual to avoid round-tripping to an
+// Ast format and then Program again.
+func (e *Env) ResidualAst(a *Ast, details *EvalDetails) (*Ast, error) {
+ pruned := interpreter.PruneAst(a.Expr(), details.State())
+ expr, err := AstToString(ParsedExprToAst(&exprpb.ParsedExpr{Expr: pruned}))
+ if err != nil {
+ return nil, err
+ }
+ parsed, iss := e.Parse(expr)
+ if iss != nil && iss.Err() != nil {
+ return nil, iss.Err()
+ }
+ if !a.IsChecked() {
+ return parsed, nil
+ }
+ checked, iss := e.Check(parsed)
+ if iss != nil && iss.Err() != nil {
+ return nil, iss.Err()
+ }
+ return checked, nil
+}
+
+// configure applies a series of EnvOptions to the current environment.
+func (e *Env) configure(opts []EnvOption) (*Env, error) {
+ // Customized the environment using the provided EnvOption values. If an error is
+ // generated at any step this, will be returned as a nil Env with a non-nil error.
+ var err error
+ for _, opt := range opts {
+ e, err = opt(e)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return e, nil
+}
+
+// Issues defines methods for inspecting the error details of parse and check calls.
+//
+// Note: in the future, non-fatal warnings and notices may be inspectable via the Issues struct.
+type Issues struct {
+ errs *common.Errors
+}
+
+// NewIssues returns an Issues struct from a common.Errors object.
+func NewIssues(errs *common.Errors) *Issues {
+ return &Issues{
+ errs: errs,
+ }
+}
+
+// Err returns an error value if the issues list contains one or more errors.
+func (i *Issues) Err() error {
+ if i == nil {
+ return nil
+ }
+ if len(i.Errors()) > 0 {
+ return errors.New(i.String())
+ }
+ return nil
+}
+
+// Errors returns the collection of errors encountered in more granular detail.
+func (i *Issues) Errors() []common.Error {
+ if i == nil {
+ return []common.Error{}
+ }
+ return i.errs.GetErrors()
+}
+
+// Append collects the issues from another Issues struct into a new Issues object.
+func (i *Issues) Append(other *Issues) *Issues {
+ if i == nil {
+ return other
+ }
+ return NewIssues(i.errs.Append(other.errs.GetErrors()))
+}
+
+// String converts the issues to a suitable display string.
+func (i *Issues) String() string {
+ if i == nil {
+ return ""
+ }
+ return i.errs.ToDisplayString()
+}
diff --git a/vendor/github.com/google/cel-go/cel/io.go b/vendor/github.com/google/cel-go/cel/io.go
new file mode 100644
index 0000000000..4df33c0648
--- /dev/null
+++ b/vendor/github.com/google/cel-go/cel/io.go
@@ -0,0 +1,122 @@
+// Copyright 2019 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package cel
+
+import (
+ "fmt"
+
+ "github.com/google/cel-go/common"
+ "github.com/google/cel-go/parser"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// CheckedExprToAst converts a checked expression proto message to an Ast.
+func CheckedExprToAst(checkedExpr *exprpb.CheckedExpr) *Ast {
+ return CheckedExprToAstWithSource(checkedExpr, nil)
+}
+
+// CheckedExprToAstWithSource converts a checked expression proto message to an Ast,
+// using the provided Source as the textual contents.
+//
+// In general the source is not necessary unless the AST has been modified between the
+// `Parse` and `Check` calls as an `Ast` created from the `Parse` step will carry the source
+// through future calls.
+//
+// Prefer CheckedExprToAst if loading expressions from storage.
+func CheckedExprToAstWithSource(checkedExpr *exprpb.CheckedExpr, src common.Source) *Ast {
+ refMap := checkedExpr.GetReferenceMap()
+ if refMap == nil {
+ refMap = map[int64]*exprpb.Reference{}
+ }
+ typeMap := checkedExpr.GetTypeMap()
+ if typeMap == nil {
+ typeMap = map[int64]*exprpb.Type{}
+ }
+ si := checkedExpr.GetSourceInfo()
+ if si == nil {
+ si = &exprpb.SourceInfo{}
+ }
+ if src == nil {
+ src = common.NewInfoSource(si)
+ }
+ return &Ast{
+ expr: checkedExpr.GetExpr(),
+ info: si,
+ source: src,
+ refMap: refMap,
+ typeMap: typeMap,
+ }
+}
+
+// AstToCheckedExpr converts an Ast to an protobuf CheckedExpr value.
+//
+// If the Ast.IsChecked() returns false, this conversion method will return an error.
+func AstToCheckedExpr(a *Ast) (*exprpb.CheckedExpr, error) {
+ if !a.IsChecked() {
+ return nil, fmt.Errorf("cannot convert unchecked ast")
+ }
+ return &exprpb.CheckedExpr{
+ Expr: a.Expr(),
+ SourceInfo: a.SourceInfo(),
+ ReferenceMap: a.refMap,
+ TypeMap: a.typeMap,
+ }, nil
+}
+
+// ParsedExprToAst converts a parsed expression proto message to an Ast.
+func ParsedExprToAst(parsedExpr *exprpb.ParsedExpr) *Ast {
+ return ParsedExprToAstWithSource(parsedExpr, nil)
+}
+
+// ParsedExprToAstWithSource converts a parsed expression proto message to an Ast,
+// using the provided Source as the textual contents.
+//
+// In general you only need this if you need to recheck a previously checked
+// expression, or if you need to separately check a subset of an expression.
+//
+// Prefer ParsedExprToAst if loading expressions from storage.
+func ParsedExprToAstWithSource(parsedExpr *exprpb.ParsedExpr, src common.Source) *Ast {
+ si := parsedExpr.GetSourceInfo()
+ if si == nil {
+ si = &exprpb.SourceInfo{}
+ }
+ if src == nil {
+ src = common.NewInfoSource(si)
+ }
+ return &Ast{
+ expr: parsedExpr.GetExpr(),
+ info: si,
+ source: src,
+ }
+}
+
+// AstToParsedExpr converts an Ast to an protobuf ParsedExpr value.
+func AstToParsedExpr(a *Ast) (*exprpb.ParsedExpr, error) {
+ return &exprpb.ParsedExpr{
+ Expr: a.Expr(),
+ SourceInfo: a.SourceInfo(),
+ }, nil
+}
+
+// AstToString converts an Ast back to a string if possible.
+//
+// Note, the conversion may not be an exact replica of the original expression, but will produce
+// a string that is semantically equivalent and whose textual representation is stable.
+func AstToString(a *Ast) (string, error) {
+ expr := a.Expr()
+ info := a.SourceInfo()
+ return parser.Unparse(expr, info)
+}
diff --git a/vendor/github.com/google/cel-go/cel/library.go b/vendor/github.com/google/cel-go/cel/library.go
new file mode 100644
index 0000000000..cef161d6a2
--- /dev/null
+++ b/vendor/github.com/google/cel-go/cel/library.go
@@ -0,0 +1,77 @@
+// Copyright 2020 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package cel
+
+import (
+ "github.com/google/cel-go/checker"
+ "github.com/google/cel-go/interpreter/functions"
+ "github.com/google/cel-go/parser"
+)
+
+// Library provides a collection of EnvOption and ProgramOption values used to confiugre a CEL
+// environment for a particular use case or with a related set of functionality.
+//
+// Note, the ProgramOption values provided by a library are expected to be static and not vary
+// between calls to Env.Program(). If there is a need for such dynamic configuration, prefer to
+// configure these options outside the Library and within the Env.Program() call directly.
+type Library interface {
+ // CompileOptions returns a collection of funcitional options for configuring the Parse / Check
+ // environment.
+ CompileOptions() []EnvOption
+
+ // ProgramOptions returns a collection of functional options which should be included in every
+ // Program generated from the Env.Program() call.
+ ProgramOptions() []ProgramOption
+}
+
+// Lib creates an EnvOption out of a Library, allowing libraries to be provided as functional args,
+// and to be linked to each other.
+func Lib(l Library) EnvOption {
+ return func(e *Env) (*Env, error) {
+ var err error
+ for _, opt := range l.CompileOptions() {
+ e, err = opt(e)
+ if err != nil {
+ return nil, err
+ }
+ }
+ e.progOpts = append(e.progOpts, l.ProgramOptions()...)
+ return e, nil
+ }
+}
+
+// StdLib returns an EnvOption for the standard library of CEL functions and macros.
+func StdLib() EnvOption {
+ return Lib(stdLibrary{})
+}
+
+// stdLibrary implements the Library interface and provides functional options for the core CEL
+// features documented in the specification.
+type stdLibrary struct{}
+
+// EnvOptions returns options for the standard CEL function declarations and macros.
+func (stdLibrary) CompileOptions() []EnvOption {
+ return []EnvOption{
+ Declarations(checker.StandardDeclarations()...),
+ Macros(parser.AllMacros...),
+ }
+}
+
+// ProgramOptions returns function implementations for the standard CEL functions.
+func (stdLibrary) ProgramOptions() []ProgramOption {
+ return []ProgramOption{
+ Functions(functions.StandardOverloads()...),
+ }
+}
diff --git a/vendor/github.com/google/cel-go/cel/options.go b/vendor/github.com/google/cel-go/cel/options.go
new file mode 100644
index 0000000000..78a6d7493c
--- /dev/null
+++ b/vendor/github.com/google/cel-go/cel/options.go
@@ -0,0 +1,451 @@
+// Copyright 2019 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package cel
+
+import (
+ "fmt"
+
+ "github.com/google/cel-go/checker/decls"
+ "github.com/google/cel-go/common/containers"
+ "github.com/google/cel-go/common/types/pb"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/interpreter"
+ "github.com/google/cel-go/interpreter/functions"
+ "github.com/google/cel-go/parser"
+ "google.golang.org/protobuf/proto"
+ "google.golang.org/protobuf/reflect/protodesc"
+ "google.golang.org/protobuf/reflect/protoreflect"
+ "google.golang.org/protobuf/reflect/protoregistry"
+ "google.golang.org/protobuf/types/dynamicpb"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+ descpb "google.golang.org/protobuf/types/descriptorpb"
+)
+
+// These constants beginning with "Feature" enable optional behavior in
+// the library. See the documentation for each constant to see its
+// effects, compatibility restrictions, and standard conformance.
+const (
+ _ = iota
+
+ // Disallow heterogeneous aggregate (list, map) literals.
+ // Note, it is still possible to have heterogeneous aggregates when
+ // provided as variables to the expression, as well as via conversion
+ // of well-known dynamic types, or with unchecked expressions.
+ // Affects checking. Provides a subset of standard behavior.
+ FeatureDisableDynamicAggregateLiterals
+)
+
+// EnvOption is a functional interface for configuring the environment.
+type EnvOption func(e *Env) (*Env, error)
+
+// ClearMacros options clears all parser macros.
+//
+// Clearing macros will ensure CEL expressions can only contain linear evaluation paths, as
+// comprehensions such as `all` and `exists` are enabled only via macros.
+func ClearMacros() EnvOption {
+ return func(e *Env) (*Env, error) {
+ e.macros = parser.NoMacros
+ return e, nil
+ }
+}
+
+// CustomTypeAdapter swaps the default ref.TypeAdapter implementation with a custom one.
+//
+// Note: This option must be specified before the Types and TypeDescs options when used together.
+func CustomTypeAdapter(adapter ref.TypeAdapter) EnvOption {
+ return func(e *Env) (*Env, error) {
+ e.adapter = adapter
+ return e, nil
+ }
+}
+
+// CustomTypeProvider swaps the default ref.TypeProvider implementation with a custom one.
+//
+// Note: This option must be specified before the Types and TypeDescs options when used together.
+func CustomTypeProvider(provider ref.TypeProvider) EnvOption {
+ return func(e *Env) (*Env, error) {
+ e.provider = provider
+ return e, nil
+ }
+}
+
+// Declarations option extends the declaration set configured in the environment.
+//
+// Note: Declarations will by default be appended to the pre-existing declaration set configured
+// for the environment. The NewEnv call builds on top of the standard CEL declarations. For a
+// purely custom set of declarations use NewCustomEnv.
+func Declarations(decls ...*exprpb.Decl) EnvOption {
+ // TODO: provide an alternative means of specifying declarations that doesn't refer
+ // to the underlying proto implementations.
+ return func(e *Env) (*Env, error) {
+ e.declarations = append(e.declarations, decls...)
+ return e, nil
+ }
+}
+
+// Features sets the given feature flags. See list of Feature constants above.
+func Features(flags ...int) EnvOption {
+ return func(e *Env) (*Env, error) {
+ for _, flag := range flags {
+ e.SetFeature(flag)
+ }
+ return e, nil
+ }
+}
+
+// HomogeneousAggregateLiterals option ensures that list and map literal entry types must agree
+// during type-checking.
+//
+// Note, it is still possible to have heterogeneous aggregates when provided as variables to the
+// expression, as well as via conversion of well-known dynamic types, or with unchecked
+// expressions.
+func HomogeneousAggregateLiterals() EnvOption {
+ return Features(FeatureDisableDynamicAggregateLiterals)
+}
+
+// Macros option extends the macro set configured in the environment.
+//
+// Note: This option must be specified after ClearMacros if used together.
+func Macros(macros ...parser.Macro) EnvOption {
+ return func(e *Env) (*Env, error) {
+ e.macros = append(e.macros, macros...)
+ return e, nil
+ }
+}
+
+// Container sets the container for resolving variable names. Defaults to an empty container.
+//
+// If all references within an expression are relative to a protocol buffer package, then
+// specifying a container of `google.type` would make it possible to write expressions such as
+// `Expr{expression: 'a < b'}` instead of having to write `google.type.Expr{...}`.
+func Container(name string) EnvOption {
+ return func(e *Env) (*Env, error) {
+ cont, err := e.Container.Extend(containers.Name(name))
+ if err != nil {
+ return nil, err
+ }
+ e.Container = cont
+ return e, nil
+ }
+}
+
+// Abbrevs configures a set of simple names as abbreviations for fully-qualified names.
+//
+// An abbreviation (abbrev for short) is a simple name that expands to a fully-qualified name.
+// Abbreviations can be useful when working with variables, functions, and especially types from
+// multiple namespaces:
+//
+// // CEL object construction
+// qual.pkg.version.ObjTypeName{
+// field: alt.container.ver.FieldTypeName{value: ...}
+// }
+//
+// Only one the qualified names above may be used as the CEL container, so at least one of these
+// references must be a long qualified name within an otherwise short CEL program. Using the
+// following abbreviations, the program becomes much simpler:
+//
+// // CEL Go option
+// Abbrevs("qual.pkg.version.ObjTypeName", "alt.container.ver.FieldTypeName")
+// // Simplified Object construction
+// ObjTypeName{field: FieldTypeName{value: ...}}
+//
+// There are a few rules for the qualified names and the simple abbreviations generated from them:
+// - Qualified names must be dot-delimited, e.g. `package.subpkg.name`.
+// - The last element in the qualified name is the abbreviation.
+// - Abbreviations must not collide with each other.
+// - The abbreviation must not collide with unqualified names in use.
+//
+// Abbreviations are distinct from container-based references in the following important ways:
+// - Abbreviations must expand to a fully-qualified name.
+// - Expanded abbreviations do not participate in namespace resolution.
+// - Abbreviation expansion is done instead of the container search for a matching identifier.
+// - Containers follow C++ namespace resolution rules with searches from the most qualified name
+// to the least qualified name.
+// - Container references within the CEL program may be relative, and are resolved to fully
+// qualified names at either type-check time or program plan time, whichever comes first.
+//
+// If there is ever a case where an identifier could be in both the container and as an
+// abbreviation, the abbreviation wins as this will ensure that the meaning of a program is
+// preserved between compilations even as the container evolves.
+func Abbrevs(qualifiedNames ...string) EnvOption {
+ return func(e *Env) (*Env, error) {
+ cont, err := e.Container.Extend(containers.Abbrevs(qualifiedNames...))
+ if err != nil {
+ return nil, err
+ }
+ e.Container = cont
+ return e, nil
+ }
+}
+
+// Types adds one or more type declarations to the environment, allowing for construction of
+// type-literals whose definitions are included in the common expression built-in set.
+//
+// The input types may either be instances of `proto.Message` or `ref.Type`. Any other type
+// provided to this option will result in an error.
+//
+// Well-known protobuf types within the `google.protobuf.*` package are included in the standard
+// environment by default.
+//
+// Note: This option must be specified after the CustomTypeProvider option when used together.
+func Types(addTypes ...interface{}) EnvOption {
+ return func(e *Env) (*Env, error) {
+ reg, isReg := e.provider.(ref.TypeRegistry)
+ if !isReg {
+ return nil, fmt.Errorf("custom types not supported by provider: %T", e.provider)
+ }
+ for _, t := range addTypes {
+ switch v := t.(type) {
+ case proto.Message:
+ fdMap := pb.CollectFileDescriptorSet(v)
+ for _, fd := range fdMap {
+ err := reg.RegisterDescriptor(fd)
+ if err != nil {
+ return nil, err
+ }
+ }
+ case ref.Type:
+ err := reg.RegisterType(v)
+ if err != nil {
+ return nil, err
+ }
+ default:
+ return nil, fmt.Errorf("unsupported type: %T", t)
+ }
+ }
+ return e, nil
+ }
+}
+
+// TypeDescs adds type declarations from any protoreflect.FileDescriptor, protoregistry.Files,
+// google.protobuf.FileDescriptorProto or google.protobuf.FileDescriptorSet provided.
+//
+// Note that messages instantiated from these descriptors will be *dynamicpb.Message values
+// rather than the concrete message type.
+//
+// TypeDescs are hermetic to a single Env object, but may be copied to other Env values via
+// extension or by re-using the same EnvOption with another NewEnv() call.
+func TypeDescs(descs ...interface{}) EnvOption {
+ return func(e *Env) (*Env, error) {
+ reg, isReg := e.provider.(ref.TypeRegistry)
+ if !isReg {
+ return nil, fmt.Errorf("custom types not supported by provider: %T", e.provider)
+ }
+ // Scan the input descriptors for FileDescriptorProto messages and accumulate them into a
+ // synthetic FileDescriptorSet as the FileDescriptorProto messages may refer to each other
+ // and will not resolve properly unless they are part of the same set.
+ var fds *descpb.FileDescriptorSet
+ for _, d := range descs {
+ switch f := d.(type) {
+ case *descpb.FileDescriptorProto:
+ if fds == nil {
+ fds = &descpb.FileDescriptorSet{
+ File: []*descpb.FileDescriptorProto{},
+ }
+ }
+ fds.File = append(fds.File, f)
+ }
+ }
+ if fds != nil {
+ if err := registerFileSet(reg, fds); err != nil {
+ return nil, err
+ }
+ }
+ for _, d := range descs {
+ switch f := d.(type) {
+ case *protoregistry.Files:
+ if err := registerFiles(reg, f); err != nil {
+ return nil, err
+ }
+ case protoreflect.FileDescriptor:
+ if err := reg.RegisterDescriptor(f); err != nil {
+ return nil, err
+ }
+ case *descpb.FileDescriptorSet:
+ if err := registerFileSet(reg, f); err != nil {
+ return nil, err
+ }
+ case *descpb.FileDescriptorProto:
+ // skip, handled as a synthetic file descriptor set.
+ default:
+ return nil, fmt.Errorf("unsupported type descriptor: %T", d)
+ }
+ }
+ return e, nil
+ }
+}
+
+func registerFileSet(reg ref.TypeRegistry, fileSet *descpb.FileDescriptorSet) error {
+ files, err := protodesc.NewFiles(fileSet)
+ if err != nil {
+ return fmt.Errorf("protodesc.NewFiles(%v) failed: %v", fileSet, err)
+ }
+ return registerFiles(reg, files)
+}
+
+func registerFiles(reg ref.TypeRegistry, files *protoregistry.Files) error {
+ var err error
+ files.RangeFiles(func(fd protoreflect.FileDescriptor) bool {
+ err = reg.RegisterDescriptor(fd)
+ return err == nil
+ })
+ return err
+}
+
+// ProgramOption is a functional interface for configuring evaluation bindings and behaviors.
+type ProgramOption func(p *prog) (*prog, error)
+
+// CustomDecorator appends an InterpreterDecorator to the program.
+//
+// InterpretableDecorators can be used to inspect, alter, or replace the Program plan.
+func CustomDecorator(dec interpreter.InterpretableDecorator) ProgramOption {
+ return func(p *prog) (*prog, error) {
+ p.decorators = append(p.decorators, dec)
+ return p, nil
+ }
+}
+
+// Functions adds function overloads that extend or override the set of CEL built-ins.
+func Functions(funcs ...*functions.Overload) ProgramOption {
+ return func(p *prog) (*prog, error) {
+ if err := p.dispatcher.Add(funcs...); err != nil {
+ return nil, err
+ }
+ return p, nil
+ }
+}
+
+// Globals sets the global variable values for a given program. These values may be shadowed by
+// variables with the same name provided to the Eval() call.
+//
+// The vars value may either be an `interpreter.Activation` instance or a `map[string]interface{}`.
+func Globals(vars interface{}) ProgramOption {
+ return func(p *prog) (*prog, error) {
+ defaultVars, err :=
+ interpreter.NewActivation(vars)
+ if err != nil {
+ return nil, err
+ }
+ p.defaultVars = defaultVars
+ return p, nil
+ }
+}
+
+// EvalOption indicates an evaluation option that may affect the evaluation behavior or information
+// in the output result.
+type EvalOption int
+
+const (
+ // OptTrackState will cause the runtime to return an immutable EvalState value in the Result.
+ OptTrackState EvalOption = 1 << iota
+
+ // OptExhaustiveEval causes the runtime to disable short-circuits and track state.
+ OptExhaustiveEval EvalOption = 1< 0 {
+ // Instantiate overload's type with fresh type variables.
+ substitutions := newMapping()
+ for _, typePar := range overload.TypeParams {
+ substitutions.add(decls.NewTypeParamType(typePar), c.newTypeVar())
+ }
+ overloadType = substitute(substitutions, overloadType, false)
+ }
+
+ candidateArgTypes := overloadType.GetFunction().ArgTypes
+ if c.isAssignableList(argTypes, candidateArgTypes) {
+ if checkedRef == nil {
+ checkedRef = newFunctionReference(overload.OverloadId)
+ } else {
+ checkedRef.OverloadId = append(checkedRef.OverloadId, overload.OverloadId)
+ }
+
+ // First matching overload, determines result type.
+ fnResultType := substitute(c.mappings,
+ overloadType.GetFunction().ResultType,
+ false)
+ if resultType == nil {
+ resultType = fnResultType
+ } else if !isDyn(resultType) && !proto.Equal(fnResultType, resultType) {
+ resultType = decls.Dyn
+ }
+ }
+ }
+
+ if resultType == nil {
+ c.errors.noMatchingOverload(loc, fn.GetName(), argTypes, target != nil)
+ resultType = decls.Error
+ return nil
+ }
+
+ return newResolution(checkedRef, resultType)
+}
+
+func (c *checker) checkCreateList(e *exprpb.Expr) {
+ create := e.GetListExpr()
+ var elemType *exprpb.Type
+ for _, e := range create.Elements {
+ c.check(e)
+ elemType = c.joinTypes(c.location(e), elemType, c.getType(e))
+ }
+ if elemType == nil {
+ // If the list is empty, assign free type var to elem type.
+ elemType = c.newTypeVar()
+ }
+ c.setType(e, decls.NewListType(elemType))
+}
+
+func (c *checker) checkCreateStruct(e *exprpb.Expr) {
+ str := e.GetStructExpr()
+ if str.MessageName != "" {
+ c.checkCreateMessage(e)
+ } else {
+ c.checkCreateMap(e)
+ }
+}
+
+func (c *checker) checkCreateMap(e *exprpb.Expr) {
+ mapVal := e.GetStructExpr()
+ var keyType *exprpb.Type
+ var valueType *exprpb.Type
+ for _, ent := range mapVal.GetEntries() {
+ key := ent.GetMapKey()
+ c.check(key)
+ keyType = c.joinTypes(c.location(key), keyType, c.getType(key))
+
+ c.check(ent.Value)
+ valueType = c.joinTypes(c.location(ent.Value), valueType, c.getType(ent.Value))
+ }
+ if keyType == nil {
+ // If the map is empty, assign free type variables to typeKey and value type.
+ keyType = c.newTypeVar()
+ valueType = c.newTypeVar()
+ }
+ c.setType(e, decls.NewMapType(keyType, valueType))
+}
+
+func (c *checker) checkCreateMessage(e *exprpb.Expr) {
+ msgVal := e.GetStructExpr()
+ // Determine the type of the message.
+ messageType := decls.Error
+ decl := c.env.LookupIdent(msgVal.MessageName)
+ if decl == nil {
+ c.errors.undeclaredReference(
+ c.location(e), c.env.container.Name(), msgVal.MessageName)
+ return
+ }
+ // Ensure the type name is fully qualified in the AST.
+ msgVal.MessageName = decl.GetName()
+ c.setReference(e, newIdentReference(decl.GetName(), nil))
+ ident := decl.GetIdent()
+ identKind := kindOf(ident.Type)
+ if identKind != kindError {
+ if identKind != kindType {
+ c.errors.notAType(c.location(e), ident.Type)
+ } else {
+ messageType = ident.Type.GetType()
+ if kindOf(messageType) != kindObject {
+ c.errors.notAMessageType(c.location(e), messageType)
+ messageType = decls.Error
+ }
+ }
+ }
+ if isObjectWellKnownType(messageType) {
+ c.setType(e, getObjectWellKnownType(messageType))
+ } else {
+ c.setType(e, messageType)
+ }
+
+ // Check the field initializers.
+ for _, ent := range msgVal.GetEntries() {
+ field := ent.GetFieldKey()
+ value := ent.Value
+ c.check(value)
+
+ fieldType := decls.Error
+ if t, found := c.lookupFieldType(
+ c.locationByID(ent.Id),
+ messageType.GetMessageType(),
+ field); found {
+ fieldType = t.Type
+ }
+ if !c.isAssignable(fieldType, c.getType(value)) {
+ c.errors.fieldTypeMismatch(
+ c.locationByID(ent.Id), field, fieldType, c.getType(value))
+ }
+ }
+}
+
+func (c *checker) checkComprehension(e *exprpb.Expr) {
+ comp := e.GetComprehensionExpr()
+ c.check(comp.IterRange)
+ c.check(comp.AccuInit)
+ accuType := c.getType(comp.AccuInit)
+ rangeType := c.getType(comp.IterRange)
+ var varType *exprpb.Type
+
+ switch kindOf(rangeType) {
+ case kindList:
+ varType = rangeType.GetListType().ElemType
+ case kindMap:
+ // Ranges over the keys.
+ varType = rangeType.GetMapType().KeyType
+ case kindDyn, kindError, kindTypeParam:
+ // Set the range type to DYN to prevent assignment to a potentionally incorrect type
+ // at a later point in type-checking. The isAssignable call will update the type
+ // substitutions for the type param under the covers.
+ c.isAssignable(decls.Dyn, rangeType)
+ // Set the range iteration variable to type DYN as well.
+ varType = decls.Dyn
+ default:
+ c.errors.notAComprehensionRange(c.location(comp.IterRange), rangeType)
+ varType = decls.Error
+ }
+
+ // Create a scope for the comprehension since it has a local accumulation variable.
+ // This scope will contain the accumulation variable used to compute the result.
+ c.env = c.env.enterScope()
+ c.env.Add(decls.NewVar(comp.AccuVar, accuType))
+ // Create a block scope for the loop.
+ c.env = c.env.enterScope()
+ c.env.Add(decls.NewVar(comp.IterVar, varType))
+ // Check the variable references in the condition and step.
+ c.check(comp.LoopCondition)
+ c.assertType(comp.LoopCondition, decls.Bool)
+ c.check(comp.LoopStep)
+ c.assertType(comp.LoopStep, accuType)
+ // Exit the loop's block scope before checking the result.
+ c.env = c.env.exitScope()
+ c.check(comp.Result)
+ // Exit the comprehension scope.
+ c.env = c.env.exitScope()
+ c.setType(e, c.getType(comp.Result))
+}
+
+// Checks compatibility of joined types, and returns the most general common type.
+func (c *checker) joinTypes(loc common.Location,
+ previous *exprpb.Type,
+ current *exprpb.Type) *exprpb.Type {
+ if previous == nil {
+ return current
+ }
+ if c.isAssignable(previous, current) {
+ return mostGeneral(previous, current)
+ }
+ if c.dynAggregateLiteralElementTypesEnabled() {
+ return decls.Dyn
+ }
+ c.errors.typeMismatch(loc, previous, current)
+ return decls.Error
+}
+
+func (c *checker) dynAggregateLiteralElementTypesEnabled() bool {
+ return c.env.aggLitElemType == dynElementType
+}
+
+func (c *checker) newTypeVar() *exprpb.Type {
+ id := c.freeTypeVarCounter
+ c.freeTypeVarCounter++
+ return decls.NewTypeParamType(fmt.Sprintf("_var%d", id))
+}
+
+func (c *checker) isAssignable(t1 *exprpb.Type, t2 *exprpb.Type) bool {
+ subs := isAssignable(c.mappings, t1, t2)
+ if subs != nil {
+ c.mappings = subs
+ return true
+ }
+
+ return false
+}
+
+func (c *checker) isAssignableList(l1 []*exprpb.Type, l2 []*exprpb.Type) bool {
+ subs := isAssignableList(c.mappings, l1, l2)
+ if subs != nil {
+ c.mappings = subs
+ return true
+ }
+
+ return false
+}
+
+func (c *checker) lookupFieldType(l common.Location, messageType string, fieldName string) (*ref.FieldType, bool) {
+ if _, found := c.env.provider.FindType(messageType); !found {
+ // This should not happen, anyway, report an error.
+ c.errors.unexpectedFailedResolution(l, messageType)
+ return nil, false
+ }
+
+ if ft, found := c.env.provider.FindFieldType(messageType, fieldName); found {
+ return ft, found
+ }
+
+ c.errors.undefinedField(l, fieldName)
+ return nil, false
+}
+
+func (c *checker) setType(e *exprpb.Expr, t *exprpb.Type) {
+ if old, found := c.types[e.Id]; found && !proto.Equal(old, t) {
+ c.errors.ReportError(c.location(e),
+ "(Incompatible) Type already exists for expression: %v(%d) old:%v, new:%v", e, e.GetId(), old, t)
+ return
+ }
+ c.types[e.Id] = t
+}
+
+func (c *checker) getType(e *exprpb.Expr) *exprpb.Type {
+ return c.types[e.Id]
+}
+
+func (c *checker) setReference(e *exprpb.Expr, r *exprpb.Reference) {
+ if old, found := c.references[e.Id]; found && !proto.Equal(old, r) {
+ c.errors.ReportError(c.location(e),
+ "Reference already exists for expression: %v(%d) old:%v, new:%v", e, e.Id, old, r)
+ return
+ }
+ c.references[e.Id] = r
+}
+
+func (c *checker) assertType(e *exprpb.Expr, t *exprpb.Type) {
+ if !c.isAssignable(t, c.getType(e)) {
+ c.errors.typeMismatch(c.location(e), t, c.getType(e))
+ }
+}
+
+type overloadResolution struct {
+ Reference *exprpb.Reference
+ Type *exprpb.Type
+}
+
+func newResolution(checkedRef *exprpb.Reference, t *exprpb.Type) *overloadResolution {
+ return &overloadResolution{
+ Reference: checkedRef,
+ Type: t,
+ }
+}
+
+func (c *checker) location(e *exprpb.Expr) common.Location {
+ return c.locationByID(e.Id)
+}
+
+func (c *checker) locationByID(id int64) common.Location {
+ positions := c.sourceInfo.GetPositions()
+ var line = 1
+ if offset, found := positions[id]; found {
+ col := int(offset)
+ for _, lineOffset := range c.sourceInfo.LineOffsets {
+ if lineOffset < offset {
+ line++
+ col = int(offset - lineOffset)
+ } else {
+ break
+ }
+ }
+ return common.NewLocation(line, col)
+ }
+ return common.NoLocation
+}
+
+func newIdentReference(name string, value *exprpb.Constant) *exprpb.Reference {
+ return &exprpb.Reference{Name: name, Value: value}
+}
+
+func newFunctionReference(overloads ...string) *exprpb.Reference {
+ return &exprpb.Reference{OverloadId: overloads}
+}
diff --git a/vendor/github.com/google/cel-go/checker/decls/BUILD.bazel b/vendor/github.com/google/cel-go/checker/decls/BUILD.bazel
new file mode 100644
index 0000000000..5a24f1da80
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/decls/BUILD.bazel
@@ -0,0 +1,20 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "decls.go",
+ "scopes.go",
+ ],
+ importpath = "github.com/google/cel-go/checker/decls",
+ deps = [
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//types/known/emptypb:go_default_library",
+ "@org_golang_google_protobuf//types/known/structpb:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/checker/decls/decls.go b/vendor/github.com/google/cel-go/checker/decls/decls.go
new file mode 100644
index 0000000000..88a99282d9
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/decls/decls.go
@@ -0,0 +1,231 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package decls provides helpers for creating variable and function declarations.
+package decls
+
+import (
+ emptypb "google.golang.org/protobuf/types/known/emptypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+var (
+ // Error type used to communicate issues during type-checking.
+ Error = &exprpb.Type{
+ TypeKind: &exprpb.Type_Error{
+ Error: &emptypb.Empty{}}}
+
+ // Dyn is a top-type used to represent any value.
+ Dyn = &exprpb.Type{
+ TypeKind: &exprpb.Type_Dyn{
+ Dyn: &emptypb.Empty{}}}
+)
+
+// Commonly used types.
+var (
+ Bool = NewPrimitiveType(exprpb.Type_BOOL)
+ Bytes = NewPrimitiveType(exprpb.Type_BYTES)
+ Double = NewPrimitiveType(exprpb.Type_DOUBLE)
+ Int = NewPrimitiveType(exprpb.Type_INT64)
+ Null = &exprpb.Type{
+ TypeKind: &exprpb.Type_Null{
+ Null: structpb.NullValue_NULL_VALUE}}
+ String = NewPrimitiveType(exprpb.Type_STRING)
+ Uint = NewPrimitiveType(exprpb.Type_UINT64)
+)
+
+// Well-known types.
+// TODO: Replace with an abstract type registry.
+var (
+ Any = NewWellKnownType(exprpb.Type_ANY)
+ Duration = NewWellKnownType(exprpb.Type_DURATION)
+ Timestamp = NewWellKnownType(exprpb.Type_TIMESTAMP)
+)
+
+// NewAbstractType creates an abstract type declaration which references a proto
+// message name and may also include type parameters.
+func NewAbstractType(name string, paramTypes ...*exprpb.Type) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_AbstractType_{
+ AbstractType: &exprpb.Type_AbstractType{
+ Name: name,
+ ParameterTypes: paramTypes}}}
+}
+
+// NewFunctionType creates a function invocation contract, typically only used
+// by type-checking steps after overload resolution.
+func NewFunctionType(resultType *exprpb.Type,
+ argTypes ...*exprpb.Type) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_Function{
+ Function: &exprpb.Type_FunctionType{
+ ResultType: resultType,
+ ArgTypes: argTypes}}}
+}
+
+// NewFunction creates a named function declaration with one or more overloads.
+func NewFunction(name string,
+ overloads ...*exprpb.Decl_FunctionDecl_Overload) *exprpb.Decl {
+ return &exprpb.Decl{
+ Name: name,
+ DeclKind: &exprpb.Decl_Function{
+ Function: &exprpb.Decl_FunctionDecl{
+ Overloads: overloads}}}
+}
+
+// NewIdent creates a named identifier declaration with an optional literal
+// value.
+//
+// Literal values are typically only associated with enum identifiers.
+//
+// Deprecated: Use NewVar or NewConst instead.
+func NewIdent(name string, t *exprpb.Type, v *exprpb.Constant) *exprpb.Decl {
+ return &exprpb.Decl{
+ Name: name,
+ DeclKind: &exprpb.Decl_Ident{
+ Ident: &exprpb.Decl_IdentDecl{
+ Type: t,
+ Value: v}}}
+}
+
+// NewConst creates a constant identifier with a CEL constant literal value.
+func NewConst(name string, t *exprpb.Type, v *exprpb.Constant) *exprpb.Decl {
+ return NewIdent(name, t, v)
+}
+
+// NewVar creates a variable identifier.
+func NewVar(name string, t *exprpb.Type) *exprpb.Decl {
+ return NewIdent(name, t, nil)
+}
+
+// NewInstanceOverload creates a instance function overload contract.
+// First element of argTypes is instance.
+func NewInstanceOverload(id string, argTypes []*exprpb.Type,
+ resultType *exprpb.Type) *exprpb.Decl_FunctionDecl_Overload {
+ return &exprpb.Decl_FunctionDecl_Overload{
+ OverloadId: id,
+ ResultType: resultType,
+ Params: argTypes,
+ IsInstanceFunction: true}
+}
+
+// NewListType generates a new list with elements of a certain type.
+func NewListType(elem *exprpb.Type) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_ListType_{
+ ListType: &exprpb.Type_ListType{
+ ElemType: elem}}}
+}
+
+// NewMapType generates a new map with typed keys and values.
+func NewMapType(key *exprpb.Type, value *exprpb.Type) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_MapType_{
+ MapType: &exprpb.Type_MapType{
+ KeyType: key,
+ ValueType: value}}}
+}
+
+// NewObjectType creates an object type for a qualified type name.
+func NewObjectType(typeName string) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_MessageType{
+ MessageType: typeName}}
+}
+
+// NewOverload creates a function overload declaration which contains a unique
+// overload id as well as the expected argument and result types. Overloads
+// must be aggregated within a Function declaration.
+func NewOverload(id string, argTypes []*exprpb.Type,
+ resultType *exprpb.Type) *exprpb.Decl_FunctionDecl_Overload {
+ return &exprpb.Decl_FunctionDecl_Overload{
+ OverloadId: id,
+ ResultType: resultType,
+ Params: argTypes,
+ IsInstanceFunction: false}
+}
+
+// NewParameterizedInstanceOverload creates a parametric function instance overload type.
+func NewParameterizedInstanceOverload(id string,
+ argTypes []*exprpb.Type,
+ resultType *exprpb.Type,
+ typeParams []string) *exprpb.Decl_FunctionDecl_Overload {
+ return &exprpb.Decl_FunctionDecl_Overload{
+ OverloadId: id,
+ ResultType: resultType,
+ Params: argTypes,
+ TypeParams: typeParams,
+ IsInstanceFunction: true}
+}
+
+// NewParameterizedOverload creates a parametric function overload type.
+func NewParameterizedOverload(id string,
+ argTypes []*exprpb.Type,
+ resultType *exprpb.Type,
+ typeParams []string) *exprpb.Decl_FunctionDecl_Overload {
+ return &exprpb.Decl_FunctionDecl_Overload{
+ OverloadId: id,
+ ResultType: resultType,
+ Params: argTypes,
+ TypeParams: typeParams,
+ IsInstanceFunction: false}
+}
+
+// NewPrimitiveType creates a type for a primitive value. See the var declarations
+// for Int, Uint, etc.
+func NewPrimitiveType(primitive exprpb.Type_PrimitiveType) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_Primitive{
+ Primitive: primitive}}
+}
+
+// NewTypeType creates a new type designating a type.
+func NewTypeType(nested *exprpb.Type) *exprpb.Type {
+ if nested == nil {
+ // must set the nested field for a valid oneof option
+ nested = &exprpb.Type{}
+ }
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_Type{
+ Type: nested}}
+}
+
+// NewTypeParamType creates a type corresponding to a named, contextual parameter.
+func NewTypeParamType(name string) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_TypeParam{
+ TypeParam: name}}
+}
+
+// NewWellKnownType creates a type corresponding to a protobuf well-known type
+// value.
+func NewWellKnownType(wellKnown exprpb.Type_WellKnownType) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_WellKnown{
+ WellKnown: wellKnown}}
+}
+
+// NewWrapperType creates a wrapped primitive type instance. Wrapped types
+// are roughly equivalent to a nullable, or optionally valued type.
+func NewWrapperType(wrapped *exprpb.Type) *exprpb.Type {
+ primitive := wrapped.GetPrimitive()
+ if primitive == exprpb.Type_PRIMITIVE_TYPE_UNSPECIFIED {
+ // TODO: return an error
+ panic("Wrapped type must be a primitive")
+ }
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_Wrapper{
+ Wrapper: primitive}}
+}
diff --git a/vendor/github.com/google/cel-go/checker/decls/scopes.go b/vendor/github.com/google/cel-go/checker/decls/scopes.go
new file mode 100644
index 0000000000..1064c73b1f
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/decls/scopes.go
@@ -0,0 +1,115 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package decls
+
+import exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+
+// Scopes represents nested Decl sets where the Scopes value contains a Groups containing all
+// identifiers in scope and an optional parent representing outer scopes.
+// Each Groups value is a mapping of names to Decls in the ident and function namespaces.
+// Lookups are performed such that bindings in inner scopes shadow those in outer scopes.
+type Scopes struct {
+ parent *Scopes
+ scopes *Group
+}
+
+// NewScopes creates a new, empty Scopes.
+// Some operations can't be safely performed until a Group is added with Push.
+func NewScopes() *Scopes {
+ return &Scopes{
+ scopes: newGroup(),
+ }
+}
+
+// Push creates a new Scopes value which references the current Scope as its parent.
+func (s *Scopes) Push() *Scopes {
+ return &Scopes{
+ parent: s,
+ scopes: newGroup(),
+ }
+}
+
+// Pop returns the parent Scopes value for the current scope, or the current scope if the parent
+// is nil.
+func (s *Scopes) Pop() *Scopes {
+ if s.parent != nil {
+ return s.parent
+ }
+ // TODO: Consider whether this should be an error / panic.
+ return s
+}
+
+// AddIdent adds the ident Decl in the current scope.
+// Note: If the name collides with an existing identifier in the scope, the Decl is overwritten.
+func (s *Scopes) AddIdent(decl *exprpb.Decl) {
+ s.scopes.idents[decl.Name] = decl
+}
+
+// FindIdent finds the first ident Decl with a matching name in Scopes, or nil if one cannot be
+// found.
+// Note: The search is performed from innermost to outermost.
+func (s *Scopes) FindIdent(name string) *exprpb.Decl {
+ if ident, found := s.scopes.idents[name]; found {
+ return ident
+ }
+ if s.parent != nil {
+ return s.parent.FindIdent(name)
+ }
+ return nil
+}
+
+// FindIdentInScope finds the first ident Decl with a matching name in the current Scopes value, or
+// nil if one does not exist.
+// Note: The search is only performed on the current scope and does not search outer scopes.
+func (s *Scopes) FindIdentInScope(name string) *exprpb.Decl {
+ if ident, found := s.scopes.idents[name]; found {
+ return ident
+ }
+ return nil
+}
+
+// AddFunction adds the function Decl to the current scope.
+// Note: Any previous entry for a function in the current scope with the same name is overwritten.
+func (s *Scopes) AddFunction(fn *exprpb.Decl) {
+ s.scopes.functions[fn.Name] = fn
+}
+
+// FindFunction finds the first function Decl with a matching name in Scopes.
+// The search is performed from innermost to outermost.
+// Returns nil if no such function in Scopes.
+func (s *Scopes) FindFunction(name string) *exprpb.Decl {
+ if fn, found := s.scopes.functions[name]; found {
+ return fn
+ }
+ if s.parent != nil {
+ return s.parent.FindFunction(name)
+ }
+ return nil
+}
+
+// Group is a set of Decls that is pushed on or popped off a Scopes as a unit.
+// Contains separate namespaces for idenifier and function Decls.
+// (Should be named "Scope" perhaps?)
+type Group struct {
+ idents map[string]*exprpb.Decl
+ functions map[string]*exprpb.Decl
+}
+
+func newGroup() *Group {
+ return &Group{
+ idents: make(map[string]*exprpb.Decl),
+ functions: make(map[string]*exprpb.Decl),
+ }
+}
diff --git a/vendor/github.com/google/cel-go/checker/env.go b/vendor/github.com/google/cel-go/checker/env.go
new file mode 100644
index 0000000000..e8bce7b06e
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/env.go
@@ -0,0 +1,346 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package checker
+
+import (
+ "fmt"
+ "strings"
+
+ "github.com/google/cel-go/checker/decls"
+ "github.com/google/cel-go/common/containers"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/pb"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/parser"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+type aggregateLiteralElementType int
+
+const (
+ dynElementType aggregateLiteralElementType = iota
+ homogenousElementType aggregateLiteralElementType = 1 << iota
+)
+
+// Env is the environment for type checking.
+//
+// The Env is comprised of a container, type provider, declarations, and other related objects
+// which can be used to assist with type-checking.
+type Env struct {
+ container *containers.Container
+ provider ref.TypeProvider
+ declarations *decls.Scopes
+ aggLitElemType aggregateLiteralElementType
+}
+
+// NewEnv returns a new *Env with the given parameters.
+func NewEnv(container *containers.Container, provider ref.TypeProvider) *Env {
+ declarations := decls.NewScopes()
+ declarations.Push()
+
+ return &Env{
+ container: container,
+ provider: provider,
+ declarations: declarations,
+ }
+}
+
+// NewStandardEnv returns a new *Env with the given params plus standard declarations.
+func NewStandardEnv(container *containers.Container, provider ref.TypeProvider) *Env {
+ e := NewEnv(container, provider)
+ if err := e.Add(StandardDeclarations()...); err != nil {
+ // The standard declaration set should never have duplicate declarations.
+ panic(err)
+ }
+ // TODO: isolate standard declarations from the custom set which may be provided layer.
+ return e
+}
+
+// EnableDynamicAggregateLiterals detmerines whether list and map literals may support mixed
+// element types at check-time. This does not preclude the presence of a dynamic list or map
+// somewhere in the CEL evaluation process.
+func (e *Env) EnableDynamicAggregateLiterals(enabled bool) *Env {
+ e.aggLitElemType = dynElementType
+ if !enabled {
+ e.aggLitElemType = homogenousElementType
+ }
+ return e
+}
+
+// Add adds new Decl protos to the Env.
+// Returns an error for identifier redeclarations.
+func (e *Env) Add(decls ...*exprpb.Decl) error {
+ errMsgs := make([]errorMsg, 0)
+ for _, decl := range decls {
+ switch decl.DeclKind.(type) {
+ case *exprpb.Decl_Ident:
+ errMsgs = append(errMsgs, e.addIdent(sanitizeIdent(decl)))
+ case *exprpb.Decl_Function:
+ errMsgs = append(errMsgs, e.addFunction(sanitizeFunction(decl))...)
+ }
+ }
+ return formatError(errMsgs)
+}
+
+// LookupIdent returns a Decl proto for typeName as an identifier in the Env.
+// Returns nil if no such identifier is found in the Env.
+func (e *Env) LookupIdent(name string) *exprpb.Decl {
+ for _, candidate := range e.container.ResolveCandidateNames(name) {
+ if ident := e.declarations.FindIdent(candidate); ident != nil {
+ return ident
+ }
+
+ // Next try to import the name as a reference to a message type. If found,
+ // the declaration is added to the outest (global) scope of the
+ // environment, so next time we can access it faster.
+ if t, found := e.provider.FindType(candidate); found {
+ decl := decls.NewVar(candidate, t)
+ e.declarations.AddIdent(decl)
+ return decl
+ }
+
+ // Next try to import this as an enum value by splitting the name in a type prefix and
+ // the enum inside.
+ if enumValue := e.provider.EnumValue(candidate); enumValue.Type() != types.ErrType {
+ decl := decls.NewIdent(candidate,
+ decls.Int,
+ &exprpb.Constant{
+ ConstantKind: &exprpb.Constant_Int64Value{
+ Int64Value: int64(enumValue.(types.Int))}})
+ e.declarations.AddIdent(decl)
+ return decl
+ }
+ }
+ return nil
+}
+
+// LookupFunction returns a Decl proto for typeName as a function in env.
+// Returns nil if no such function is found in env.
+func (e *Env) LookupFunction(name string) *exprpb.Decl {
+ for _, candidate := range e.container.ResolveCandidateNames(name) {
+ if fn := e.declarations.FindFunction(candidate); fn != nil {
+ return fn
+ }
+ }
+ return nil
+}
+
+// addOverload adds overload to function declaration f.
+// Returns one or more errorMsg values if the overload overlaps with an existing overload or macro.
+func (e *Env) addOverload(f *exprpb.Decl, overload *exprpb.Decl_FunctionDecl_Overload) []errorMsg {
+ errMsgs := make([]errorMsg, 0)
+ function := f.GetFunction()
+ emptyMappings := newMapping()
+ overloadFunction := decls.NewFunctionType(overload.GetResultType(),
+ overload.GetParams()...)
+ overloadErased := substitute(emptyMappings, overloadFunction, true)
+ for _, existing := range function.GetOverloads() {
+ existingFunction := decls.NewFunctionType(existing.GetResultType(),
+ existing.GetParams()...)
+ existingErased := substitute(emptyMappings, existingFunction, true)
+ overlap := isAssignable(emptyMappings, overloadErased, existingErased) != nil ||
+ isAssignable(emptyMappings, existingErased, overloadErased) != nil
+ if overlap &&
+ overload.GetIsInstanceFunction() == existing.GetIsInstanceFunction() {
+ errMsgs = append(errMsgs,
+ overlappingOverloadError(f.Name,
+ overload.GetOverloadId(), overloadFunction,
+ existing.GetOverloadId(), existingFunction))
+ }
+ }
+
+ for _, macro := range parser.AllMacros {
+ if macro.Function() == f.Name &&
+ macro.IsReceiverStyle() == overload.GetIsInstanceFunction() &&
+ macro.ArgCount() == len(overload.GetParams()) {
+ errMsgs = append(errMsgs, overlappingMacroError(f.Name, macro.ArgCount()))
+ }
+ }
+ if len(errMsgs) > 0 {
+ return errMsgs
+ }
+ function.Overloads = append(function.GetOverloads(), overload)
+ return errMsgs
+}
+
+// addFunction adds the function Decl to the Env.
+// Adds a function decl if one doesn't already exist, then adds all overloads from the Decl.
+// If overload overlaps with an existing overload, adds to the errors in the Env instead.
+func (e *Env) addFunction(decl *exprpb.Decl) []errorMsg {
+ current := e.declarations.FindFunction(decl.Name)
+ if current == nil {
+ //Add the function declaration without overloads and check the overloads below.
+ current = decls.NewFunction(decl.Name)
+ e.declarations.AddFunction(current)
+ }
+
+ errorMsgs := make([]errorMsg, 0)
+ for _, overload := range decl.GetFunction().GetOverloads() {
+ errorMsgs = append(errorMsgs, e.addOverload(current, overload)...)
+ }
+ return errorMsgs
+}
+
+// addIdent adds the Decl to the declarations in the Env.
+// Returns a non-empty errorMsg if the identifier is already declared in the scope.
+func (e *Env) addIdent(decl *exprpb.Decl) errorMsg {
+ current := e.declarations.FindIdentInScope(decl.Name)
+ if current != nil {
+ return overlappingIdentifierError(decl.Name)
+ }
+ e.declarations.AddIdent(decl)
+ return ""
+}
+
+// sanitizeFunction replaces well-known types referenced by message name with their equivalent
+// CEL built-in type instances.
+func sanitizeFunction(decl *exprpb.Decl) *exprpb.Decl {
+ fn := decl.GetFunction()
+ // Determine whether the declaration requires replacements from proto-based message type
+ // references to well-known CEL type references.
+ var needsSanitizing bool
+ for _, o := range fn.GetOverloads() {
+ if isObjectWellKnownType(o.GetResultType()) {
+ needsSanitizing = true
+ break
+ }
+ for _, p := range o.GetParams() {
+ if isObjectWellKnownType(p) {
+ needsSanitizing = true
+ break
+ }
+ }
+ }
+
+ // Early return if the declaration requires no modification.
+ if !needsSanitizing {
+ return decl
+ }
+
+ // Sanitize all of the overloads if any overload requires an update to its type references.
+ overloads := make([]*exprpb.Decl_FunctionDecl_Overload, len(fn.GetOverloads()))
+ for i, o := range fn.GetOverloads() {
+ rt := o.GetResultType()
+ if isObjectWellKnownType(rt) {
+ rt = getObjectWellKnownType(rt)
+ }
+ params := make([]*exprpb.Type, len(o.GetParams()))
+ copy(params, o.GetParams())
+ for j, p := range params {
+ if isObjectWellKnownType(p) {
+ params[j] = getObjectWellKnownType(p)
+ }
+ }
+ // If sanitized, replace the overload definition.
+ if o.IsInstanceFunction {
+ overloads[i] =
+ decls.NewInstanceOverload(o.GetOverloadId(), params, rt)
+ } else {
+ overloads[i] =
+ decls.NewOverload(o.GetOverloadId(), params, rt)
+ }
+ }
+ return decls.NewFunction(decl.GetName(), overloads...)
+}
+
+// sanitizeIdent replaces the identifier's well-known types referenced by message name with
+// references to CEL built-in type instances.
+func sanitizeIdent(decl *exprpb.Decl) *exprpb.Decl {
+ id := decl.GetIdent()
+ t := id.GetType()
+ if !isObjectWellKnownType(t) {
+ return decl
+ }
+ return decls.NewIdent(decl.GetName(), getObjectWellKnownType(t), id.GetValue())
+}
+
+// isObjectWellKnownType returns true if the input type is an OBJECT type with a message name
+// that corresponds the message name of a built-in CEL type.
+func isObjectWellKnownType(t *exprpb.Type) bool {
+ if kindOf(t) != kindObject {
+ return false
+ }
+ _, found := pb.CheckedWellKnowns[t.GetMessageType()]
+ return found
+}
+
+// getObjectWellKnownType returns the built-in CEL type declaration for input type's message name.
+func getObjectWellKnownType(t *exprpb.Type) *exprpb.Type {
+ return pb.CheckedWellKnowns[t.GetMessageType()]
+}
+
+// enterScope creates a new Env instance with a new innermost declaration scope.
+func (e *Env) enterScope() *Env {
+ childDecls := e.declarations.Push()
+ return &Env{
+ declarations: childDecls,
+ container: e.container,
+ provider: e.provider,
+ aggLitElemType: e.aggLitElemType,
+ }
+}
+
+// exitScope creates a new Env instance with the nearest outer declaration scope.
+func (e *Env) exitScope() *Env {
+ parentDecls := e.declarations.Pop()
+ return &Env{
+ declarations: parentDecls,
+ container: e.container,
+ provider: e.provider,
+ aggLitElemType: e.aggLitElemType,
+ }
+}
+
+// errorMsg is a type alias meant to represent error-based return values which
+// may be accumulated into an error at a later point in execution.
+type errorMsg string
+
+func overlappingIdentifierError(name string) errorMsg {
+ return errorMsg(fmt.Sprintf("overlapping identifier for name '%s'", name))
+}
+
+func overlappingOverloadError(name string,
+ overloadID1 string, f1 *exprpb.Type,
+ overloadID2 string, f2 *exprpb.Type) errorMsg {
+ return errorMsg(fmt.Sprintf(
+ "overlapping overload for name '%s' (type '%s' with overloadId: '%s' "+
+ "cannot be distinguished from '%s' with overloadId: '%s')",
+ name,
+ FormatCheckedType(f1),
+ overloadID1,
+ FormatCheckedType(f2),
+ overloadID2))
+}
+
+func overlappingMacroError(name string, argCount int) errorMsg {
+ return errorMsg(fmt.Sprintf(
+ "overlapping macro for name '%s' with %d args", name, argCount))
+}
+
+func formatError(errMsgs []errorMsg) error {
+ errStrs := make([]string, 0)
+ if len(errMsgs) > 0 {
+ for i := 0; i < len(errMsgs); i++ {
+ if errMsgs[i] != "" {
+ errStrs = append(errStrs, string(errMsgs[i]))
+ }
+ }
+ }
+ if len(errStrs) > 0 {
+ return fmt.Errorf("%s", strings.Join(errStrs, "\n"))
+ }
+ return nil
+}
diff --git a/vendor/github.com/google/cel-go/checker/errors.go b/vendor/github.com/google/cel-go/checker/errors.go
new file mode 100644
index 0000000000..06566aecfb
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/errors.go
@@ -0,0 +1,100 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package checker
+
+import (
+ "github.com/google/cel-go/common"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// typeErrors is a specialization of Errors.
+type typeErrors struct {
+ *common.Errors
+}
+
+func (e *typeErrors) undeclaredReference(l common.Location, container string, name string) {
+ e.ReportError(l, "undeclared reference to '%s' (in container '%s')", name, container)
+}
+
+func (e *typeErrors) expressionDoesNotSelectField(l common.Location) {
+ e.ReportError(l, "expression does not select a field")
+}
+
+func (e *typeErrors) typeDoesNotSupportFieldSelection(l common.Location, t *exprpb.Type) {
+ e.ReportError(l, "type '%s' does not support field selection", t)
+}
+
+func (e *typeErrors) undefinedField(l common.Location, field string) {
+ e.ReportError(l, "undefined field '%s'", field)
+}
+
+func (e *typeErrors) noMatchingOverload(l common.Location, name string, args []*exprpb.Type, isInstance bool) {
+ signature := formatFunction(nil, args, isInstance)
+ e.ReportError(l, "found no matching overload for '%s' applied to '%s'", name, signature)
+}
+
+func (e *typeErrors) notAType(l common.Location, t *exprpb.Type) {
+ e.ReportError(l, "'%s(%v)' is not a type", FormatCheckedType(t), t)
+}
+
+func (e *typeErrors) notAMessageType(l common.Location, t *exprpb.Type) {
+ e.ReportError(l, "'%s' is not a message type", FormatCheckedType(t))
+}
+
+func (e *typeErrors) fieldTypeMismatch(l common.Location, name string, field *exprpb.Type, value *exprpb.Type) {
+ e.ReportError(l, "expected type of field '%s' is '%s' but provided type is '%s'",
+ name, FormatCheckedType(field), FormatCheckedType(value))
+}
+
+func (e *typeErrors) unexpectedFailedResolution(l common.Location, typeName string) {
+ e.ReportError(l, "[internal] unexpected failed resolution of '%s'", typeName)
+}
+
+func (e *typeErrors) notAComprehensionRange(l common.Location, t *exprpb.Type) {
+ e.ReportError(l, "expression of type '%s' cannot be range of a comprehension (must be list, map, or dynamic)",
+ FormatCheckedType(t))
+}
+
+func (e *typeErrors) typeMismatch(l common.Location, expected *exprpb.Type, actual *exprpb.Type) {
+ e.ReportError(l, "expected type '%s' but found '%s'",
+ FormatCheckedType(expected), FormatCheckedType(actual))
+}
+
+func formatFunction(resultType *exprpb.Type, argTypes []*exprpb.Type, isInstance bool) string {
+ result := ""
+ if isInstance {
+ target := argTypes[0]
+ argTypes = argTypes[1:]
+
+ result += FormatCheckedType(target)
+ result += "."
+ }
+
+ result += "("
+ for i, arg := range argTypes {
+ if i > 0 {
+ result += ", "
+ }
+ result += FormatCheckedType(arg)
+ }
+ result += ")"
+ if resultType != nil {
+ result += " -> "
+ result += FormatCheckedType(resultType)
+ }
+
+ return result
+}
diff --git a/vendor/github.com/google/cel-go/checker/mapping.go b/vendor/github.com/google/cel-go/checker/mapping.go
new file mode 100644
index 0000000000..fbc55a28d9
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/mapping.go
@@ -0,0 +1,49 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package checker
+
+import (
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+type mapping struct {
+ mapping map[string]*exprpb.Type
+}
+
+func newMapping() *mapping {
+ return &mapping{
+ mapping: make(map[string]*exprpb.Type),
+ }
+}
+
+func (m *mapping) add(from *exprpb.Type, to *exprpb.Type) {
+ m.mapping[typeKey(from)] = to
+}
+
+func (m *mapping) find(from *exprpb.Type) (*exprpb.Type, bool) {
+ if r, found := m.mapping[typeKey(from)]; found {
+ return r, found
+ }
+ return nil, false
+}
+
+func (m *mapping) copy() *mapping {
+ c := newMapping()
+
+ for k, v := range m.mapping {
+ c.mapping[k] = v
+ }
+ return c
+}
diff --git a/vendor/github.com/google/cel-go/checker/printer.go b/vendor/github.com/google/cel-go/checker/printer.go
new file mode 100644
index 0000000000..15c25ecc68
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/printer.go
@@ -0,0 +1,71 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package checker
+
+import (
+ "github.com/google/cel-go/common/debug"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+type semanticAdorner struct {
+ checks *exprpb.CheckedExpr
+}
+
+var _ debug.Adorner = &semanticAdorner{}
+
+func (a *semanticAdorner) GetMetadata(elem interface{}) string {
+ result := ""
+ e, isExpr := elem.(*exprpb.Expr)
+ if !isExpr {
+ return result
+ }
+ t := a.checks.TypeMap[e.Id]
+ if t != nil {
+ result += "~"
+ result += FormatCheckedType(t)
+ }
+
+ switch e.ExprKind.(type) {
+ case *exprpb.Expr_IdentExpr,
+ *exprpb.Expr_CallExpr,
+ *exprpb.Expr_StructExpr,
+ *exprpb.Expr_SelectExpr:
+ if ref, found := a.checks.ReferenceMap[e.Id]; found {
+ if len(ref.GetOverloadId()) == 0 {
+ result += "^" + ref.Name
+ } else {
+ for i, overload := range ref.OverloadId {
+ if i == 0 {
+ result += "^"
+ } else {
+ result += "|"
+ }
+ result += overload
+ }
+ }
+ }
+ }
+
+ return result
+}
+
+// Print returns a string representation of the Expr message,
+// annotated with types from the CheckedExpr. The Expr must
+// be a sub-expression embedded in the CheckedExpr.
+func Print(e *exprpb.Expr, checks *exprpb.CheckedExpr) string {
+ a := &semanticAdorner{checks: checks}
+ return debug.ToAdornedDebugString(e, a)
+}
diff --git a/vendor/github.com/google/cel-go/checker/standard.go b/vendor/github.com/google/cel-go/checker/standard.go
new file mode 100644
index 0000000000..769de7511f
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/standard.go
@@ -0,0 +1,440 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package checker
+
+import (
+ "github.com/google/cel-go/checker/decls"
+ "github.com/google/cel-go/common/operators"
+ "github.com/google/cel-go/common/overloads"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// StandardDeclarations returns the Decls for all functions and constants in the evaluator.
+func StandardDeclarations() []*exprpb.Decl {
+ // Some shortcuts we use when building declarations.
+ paramA := decls.NewTypeParamType("A")
+ typeParamAList := []string{"A"}
+ listOfA := decls.NewListType(paramA)
+ paramB := decls.NewTypeParamType("B")
+ typeParamABList := []string{"A", "B"}
+ mapOfAB := decls.NewMapType(paramA, paramB)
+
+ var idents []*exprpb.Decl
+ for _, t := range []*exprpb.Type{
+ decls.Int, decls.Uint, decls.Bool,
+ decls.Double, decls.Bytes, decls.String} {
+ idents = append(idents,
+ decls.NewVar(FormatCheckedType(t), decls.NewTypeType(t)))
+ }
+ idents = append(idents,
+ decls.NewVar("list", decls.NewTypeType(listOfA)),
+ decls.NewVar("map", decls.NewTypeType(mapOfAB)),
+ decls.NewVar("null_type", decls.NewTypeType(decls.Null)),
+ decls.NewVar("type", decls.NewTypeType(decls.NewTypeType(nil))))
+
+ // Booleans
+ // TODO: allow the conditional to return a heterogenous type.
+ return append(idents, []*exprpb.Decl{
+ decls.NewFunction(operators.Conditional,
+ decls.NewParameterizedOverload(overloads.Conditional,
+ []*exprpb.Type{decls.Bool, paramA, paramA}, paramA,
+ typeParamAList)),
+
+ decls.NewFunction(operators.LogicalAnd,
+ decls.NewOverload(overloads.LogicalAnd,
+ []*exprpb.Type{decls.Bool, decls.Bool}, decls.Bool)),
+
+ decls.NewFunction(operators.LogicalOr,
+ decls.NewOverload(overloads.LogicalOr,
+ []*exprpb.Type{decls.Bool, decls.Bool}, decls.Bool)),
+
+ decls.NewFunction(operators.LogicalNot,
+ decls.NewOverload(overloads.LogicalNot,
+ []*exprpb.Type{decls.Bool}, decls.Bool)),
+
+ decls.NewFunction(operators.NotStrictlyFalse,
+ decls.NewOverload(overloads.NotStrictlyFalse,
+ []*exprpb.Type{decls.Bool}, decls.Bool)),
+
+ // Relations.
+
+ decls.NewFunction(operators.Less,
+ decls.NewOverload(overloads.LessBool,
+ []*exprpb.Type{decls.Bool, decls.Bool}, decls.Bool),
+ decls.NewOverload(overloads.LessInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Bool),
+ decls.NewOverload(overloads.LessUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Bool),
+ decls.NewOverload(overloads.LessDouble,
+ []*exprpb.Type{decls.Double, decls.Double}, decls.Bool),
+ decls.NewOverload(overloads.LessString,
+ []*exprpb.Type{decls.String, decls.String}, decls.Bool),
+ decls.NewOverload(overloads.LessBytes,
+ []*exprpb.Type{decls.Bytes, decls.Bytes}, decls.Bool),
+ decls.NewOverload(overloads.LessTimestamp,
+ []*exprpb.Type{decls.Timestamp, decls.Timestamp}, decls.Bool),
+ decls.NewOverload(overloads.LessDuration,
+ []*exprpb.Type{decls.Duration, decls.Duration}, decls.Bool)),
+
+ decls.NewFunction(operators.LessEquals,
+ decls.NewOverload(overloads.LessEqualsBool,
+ []*exprpb.Type{decls.Bool, decls.Bool}, decls.Bool),
+ decls.NewOverload(overloads.LessEqualsInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Bool),
+ decls.NewOverload(overloads.LessEqualsUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Bool),
+ decls.NewOverload(overloads.LessEqualsDouble,
+ []*exprpb.Type{decls.Double, decls.Double}, decls.Bool),
+ decls.NewOverload(overloads.LessEqualsString,
+ []*exprpb.Type{decls.String, decls.String}, decls.Bool),
+ decls.NewOverload(overloads.LessEqualsBytes,
+ []*exprpb.Type{decls.Bytes, decls.Bytes}, decls.Bool),
+ decls.NewOverload(overloads.LessEqualsTimestamp,
+ []*exprpb.Type{decls.Timestamp, decls.Timestamp}, decls.Bool),
+ decls.NewOverload(overloads.LessEqualsDuration,
+ []*exprpb.Type{decls.Duration, decls.Duration}, decls.Bool)),
+
+ decls.NewFunction(operators.Greater,
+ decls.NewOverload(overloads.GreaterBool,
+ []*exprpb.Type{decls.Bool, decls.Bool}, decls.Bool),
+ decls.NewOverload(overloads.GreaterInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Bool),
+ decls.NewOverload(overloads.GreaterUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Bool),
+ decls.NewOverload(overloads.GreaterDouble,
+ []*exprpb.Type{decls.Double, decls.Double}, decls.Bool),
+ decls.NewOverload(overloads.GreaterString,
+ []*exprpb.Type{decls.String, decls.String}, decls.Bool),
+ decls.NewOverload(overloads.GreaterBytes,
+ []*exprpb.Type{decls.Bytes, decls.Bytes}, decls.Bool),
+ decls.NewOverload(overloads.GreaterTimestamp,
+ []*exprpb.Type{decls.Timestamp, decls.Timestamp}, decls.Bool),
+ decls.NewOverload(overloads.GreaterDuration,
+ []*exprpb.Type{decls.Duration, decls.Duration}, decls.Bool)),
+
+ decls.NewFunction(operators.GreaterEquals,
+ decls.NewOverload(overloads.GreaterEqualsBool,
+ []*exprpb.Type{decls.Bool, decls.Bool}, decls.Bool),
+ decls.NewOverload(overloads.GreaterEqualsInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Bool),
+ decls.NewOverload(overloads.GreaterEqualsUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Bool),
+ decls.NewOverload(overloads.GreaterEqualsDouble,
+ []*exprpb.Type{decls.Double, decls.Double}, decls.Bool),
+ decls.NewOverload(overloads.GreaterEqualsString,
+ []*exprpb.Type{decls.String, decls.String}, decls.Bool),
+ decls.NewOverload(overloads.GreaterEqualsBytes,
+ []*exprpb.Type{decls.Bytes, decls.Bytes}, decls.Bool),
+ decls.NewOverload(overloads.GreaterEqualsTimestamp,
+ []*exprpb.Type{decls.Timestamp, decls.Timestamp}, decls.Bool),
+ decls.NewOverload(overloads.GreaterEqualsDuration,
+ []*exprpb.Type{decls.Duration, decls.Duration}, decls.Bool)),
+
+ decls.NewFunction(operators.Equals,
+ decls.NewParameterizedOverload(overloads.Equals,
+ []*exprpb.Type{paramA, paramA}, decls.Bool,
+ typeParamAList)),
+
+ decls.NewFunction(operators.NotEquals,
+ decls.NewParameterizedOverload(overloads.NotEquals,
+ []*exprpb.Type{paramA, paramA}, decls.Bool,
+ typeParamAList)),
+
+ // Algebra.
+
+ decls.NewFunction(operators.Subtract,
+ decls.NewOverload(overloads.SubtractInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Int),
+ decls.NewOverload(overloads.SubtractUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Uint),
+ decls.NewOverload(overloads.SubtractDouble,
+ []*exprpb.Type{decls.Double, decls.Double}, decls.Double),
+ decls.NewOverload(overloads.SubtractTimestampTimestamp,
+ []*exprpb.Type{decls.Timestamp, decls.Timestamp}, decls.Duration),
+ decls.NewOverload(overloads.SubtractTimestampDuration,
+ []*exprpb.Type{decls.Timestamp, decls.Duration}, decls.Timestamp),
+ decls.NewOverload(overloads.SubtractDurationDuration,
+ []*exprpb.Type{decls.Duration, decls.Duration}, decls.Duration)),
+
+ decls.NewFunction(operators.Multiply,
+ decls.NewOverload(overloads.MultiplyInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Int),
+ decls.NewOverload(overloads.MultiplyUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Uint),
+ decls.NewOverload(overloads.MultiplyDouble,
+ []*exprpb.Type{decls.Double, decls.Double}, decls.Double)),
+
+ decls.NewFunction(operators.Divide,
+ decls.NewOverload(overloads.DivideInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Int),
+ decls.NewOverload(overloads.DivideUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Uint),
+ decls.NewOverload(overloads.DivideDouble,
+ []*exprpb.Type{decls.Double, decls.Double}, decls.Double)),
+
+ decls.NewFunction(operators.Modulo,
+ decls.NewOverload(overloads.ModuloInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Int),
+ decls.NewOverload(overloads.ModuloUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Uint)),
+
+ decls.NewFunction(operators.Add,
+ decls.NewOverload(overloads.AddInt64,
+ []*exprpb.Type{decls.Int, decls.Int}, decls.Int),
+ decls.NewOverload(overloads.AddUint64,
+ []*exprpb.Type{decls.Uint, decls.Uint}, decls.Uint),
+ decls.NewOverload(overloads.AddDouble,
+ []*exprpb.Type{decls.Double, decls.Double}, decls.Double),
+ decls.NewOverload(overloads.AddString,
+ []*exprpb.Type{decls.String, decls.String}, decls.String),
+ decls.NewOverload(overloads.AddBytes,
+ []*exprpb.Type{decls.Bytes, decls.Bytes}, decls.Bytes),
+ decls.NewParameterizedOverload(overloads.AddList,
+ []*exprpb.Type{listOfA, listOfA}, listOfA,
+ typeParamAList),
+ decls.NewOverload(overloads.AddTimestampDuration,
+ []*exprpb.Type{decls.Timestamp, decls.Duration}, decls.Timestamp),
+ decls.NewOverload(overloads.AddDurationTimestamp,
+ []*exprpb.Type{decls.Duration, decls.Timestamp}, decls.Timestamp),
+ decls.NewOverload(overloads.AddDurationDuration,
+ []*exprpb.Type{decls.Duration, decls.Duration}, decls.Duration)),
+
+ decls.NewFunction(operators.Negate,
+ decls.NewOverload(overloads.NegateInt64,
+ []*exprpb.Type{decls.Int}, decls.Int),
+ decls.NewOverload(overloads.NegateDouble,
+ []*exprpb.Type{decls.Double}, decls.Double)),
+
+ // Index.
+
+ decls.NewFunction(operators.Index,
+ decls.NewParameterizedOverload(overloads.IndexList,
+ []*exprpb.Type{listOfA, decls.Int}, paramA,
+ typeParamAList),
+ decls.NewParameterizedOverload(overloads.IndexMap,
+ []*exprpb.Type{mapOfAB, paramA}, paramB,
+ typeParamABList)),
+ //decls.NewOverload(overloads.IndexMessage,
+ // []*expr.Type{decls.Dyn, decls.String}, decls.Dyn)),
+
+ // Collections.
+
+ decls.NewFunction(overloads.Size,
+ decls.NewInstanceOverload(overloads.SizeStringInst,
+ []*exprpb.Type{decls.String}, decls.Int),
+ decls.NewInstanceOverload(overloads.SizeBytesInst,
+ []*exprpb.Type{decls.Bytes}, decls.Int),
+ decls.NewParameterizedInstanceOverload(overloads.SizeListInst,
+ []*exprpb.Type{listOfA}, decls.Int, typeParamAList),
+ decls.NewParameterizedInstanceOverload(overloads.SizeMapInst,
+ []*exprpb.Type{mapOfAB}, decls.Int, typeParamABList),
+ decls.NewOverload(overloads.SizeString,
+ []*exprpb.Type{decls.String}, decls.Int),
+ decls.NewOverload(overloads.SizeBytes,
+ []*exprpb.Type{decls.Bytes}, decls.Int),
+ decls.NewParameterizedOverload(overloads.SizeList,
+ []*exprpb.Type{listOfA}, decls.Int, typeParamAList),
+ decls.NewParameterizedOverload(overloads.SizeMap,
+ []*exprpb.Type{mapOfAB}, decls.Int, typeParamABList)),
+
+ decls.NewFunction(operators.In,
+ decls.NewParameterizedOverload(overloads.InList,
+ []*exprpb.Type{paramA, listOfA}, decls.Bool,
+ typeParamAList),
+ decls.NewParameterizedOverload(overloads.InMap,
+ []*exprpb.Type{paramA, mapOfAB}, decls.Bool,
+ typeParamABList)),
+
+ // Deprecated 'in()' function.
+
+ decls.NewFunction(overloads.DeprecatedIn,
+ decls.NewParameterizedOverload(overloads.InList,
+ []*exprpb.Type{paramA, listOfA}, decls.Bool,
+ typeParamAList),
+ decls.NewParameterizedOverload(overloads.InMap,
+ []*exprpb.Type{paramA, mapOfAB}, decls.Bool,
+ typeParamABList)),
+ //decls.NewOverload(overloads.InMessage,
+ // []*expr.Type{Dyn, decls.String},decls.Bool)),
+
+ // Conversions to type.
+
+ decls.NewFunction(overloads.TypeConvertType,
+ decls.NewParameterizedOverload(overloads.TypeConvertType,
+ []*exprpb.Type{paramA}, decls.NewTypeType(paramA), typeParamAList)),
+
+ // Conversions to int.
+
+ decls.NewFunction(overloads.TypeConvertInt,
+ decls.NewOverload(overloads.IntToInt, []*exprpb.Type{decls.Int}, decls.Int),
+ decls.NewOverload(overloads.UintToInt, []*exprpb.Type{decls.Uint}, decls.Int),
+ decls.NewOverload(overloads.DoubleToInt, []*exprpb.Type{decls.Double}, decls.Int),
+ decls.NewOverload(overloads.StringToInt, []*exprpb.Type{decls.String}, decls.Int),
+ decls.NewOverload(overloads.TimestampToInt, []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewOverload(overloads.DurationToInt, []*exprpb.Type{decls.Duration}, decls.Int)),
+
+ // Conversions to uint.
+
+ decls.NewFunction(overloads.TypeConvertUint,
+ decls.NewOverload(overloads.UintToUint, []*exprpb.Type{decls.Uint}, decls.Uint),
+ decls.NewOverload(overloads.IntToUint, []*exprpb.Type{decls.Int}, decls.Uint),
+ decls.NewOverload(overloads.DoubleToUint, []*exprpb.Type{decls.Double}, decls.Uint),
+ decls.NewOverload(overloads.StringToUint, []*exprpb.Type{decls.String}, decls.Uint)),
+
+ // Conversions to double.
+
+ decls.NewFunction(overloads.TypeConvertDouble,
+ decls.NewOverload(overloads.DoubleToDouble, []*exprpb.Type{decls.Double}, decls.Double),
+ decls.NewOverload(overloads.IntToDouble, []*exprpb.Type{decls.Int}, decls.Double),
+ decls.NewOverload(overloads.UintToDouble, []*exprpb.Type{decls.Uint}, decls.Double),
+ decls.NewOverload(overloads.StringToDouble, []*exprpb.Type{decls.String}, decls.Double)),
+
+ // Conversions to bool.
+
+ decls.NewFunction(overloads.TypeConvertBool,
+ decls.NewOverload(overloads.BoolToBool, []*exprpb.Type{decls.Bool}, decls.Bool),
+ decls.NewOverload(overloads.StringToBool, []*exprpb.Type{decls.String}, decls.Bool)),
+
+ // Conversions to string.
+
+ decls.NewFunction(overloads.TypeConvertString,
+ decls.NewOverload(overloads.StringToString, []*exprpb.Type{decls.String}, decls.String),
+ decls.NewOverload(overloads.BoolToString, []*exprpb.Type{decls.Bool}, decls.String),
+ decls.NewOverload(overloads.IntToString, []*exprpb.Type{decls.Int}, decls.String),
+ decls.NewOverload(overloads.UintToString, []*exprpb.Type{decls.Uint}, decls.String),
+ decls.NewOverload(overloads.DoubleToString, []*exprpb.Type{decls.Double}, decls.String),
+ decls.NewOverload(overloads.BytesToString, []*exprpb.Type{decls.Bytes}, decls.String),
+ decls.NewOverload(overloads.TimestampToString, []*exprpb.Type{decls.Timestamp}, decls.String),
+ decls.NewOverload(overloads.DurationToString, []*exprpb.Type{decls.Duration}, decls.String)),
+
+ // Conversions to bytes.
+
+ decls.NewFunction(overloads.TypeConvertBytes,
+ decls.NewOverload(overloads.BytesToBytes, []*exprpb.Type{decls.Bytes}, decls.Bytes),
+ decls.NewOverload(overloads.StringToBytes, []*exprpb.Type{decls.String}, decls.Bytes)),
+
+ // Conversions to timestamps.
+
+ decls.NewFunction(overloads.TypeConvertTimestamp,
+ decls.NewOverload(overloads.TimestampToTimestamp,
+ []*exprpb.Type{decls.Timestamp}, decls.Timestamp),
+ decls.NewOverload(overloads.StringToTimestamp,
+ []*exprpb.Type{decls.String}, decls.Timestamp),
+ decls.NewOverload(overloads.IntToTimestamp,
+ []*exprpb.Type{decls.Int}, decls.Timestamp)),
+
+ // Conversions to durations.
+
+ decls.NewFunction(overloads.TypeConvertDuration,
+ decls.NewOverload(overloads.DurationToDuration,
+ []*exprpb.Type{decls.Duration}, decls.Duration),
+ decls.NewOverload(overloads.StringToDuration,
+ []*exprpb.Type{decls.String}, decls.Duration),
+ decls.NewOverload(overloads.IntToDuration,
+ []*exprpb.Type{decls.Int}, decls.Duration)),
+
+ // Conversions to Dyn.
+
+ decls.NewFunction(overloads.TypeConvertDyn,
+ decls.NewParameterizedOverload(overloads.ToDyn,
+ []*exprpb.Type{paramA}, decls.Dyn,
+ typeParamAList)),
+
+ // String functions.
+
+ decls.NewFunction(overloads.Contains,
+ decls.NewInstanceOverload(overloads.ContainsString,
+ []*exprpb.Type{decls.String, decls.String}, decls.Bool)),
+ decls.NewFunction(overloads.EndsWith,
+ decls.NewInstanceOverload(overloads.EndsWithString,
+ []*exprpb.Type{decls.String, decls.String}, decls.Bool)),
+ decls.NewFunction(overloads.Matches,
+ decls.NewInstanceOverload(overloads.MatchesString,
+ []*exprpb.Type{decls.String, decls.String}, decls.Bool)),
+ decls.NewFunction(overloads.StartsWith,
+ decls.NewInstanceOverload(overloads.StartsWithString,
+ []*exprpb.Type{decls.String, decls.String}, decls.Bool)),
+
+ // Date/time functions.
+
+ decls.NewFunction(overloads.TimeGetFullYear,
+ decls.NewInstanceOverload(overloads.TimestampToYear,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToYearWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetMonth,
+ decls.NewInstanceOverload(overloads.TimestampToMonth,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToMonthWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetDayOfYear,
+ decls.NewInstanceOverload(overloads.TimestampToDayOfYear,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToDayOfYearWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetDayOfMonth,
+ decls.NewInstanceOverload(overloads.TimestampToDayOfMonthZeroBased,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToDayOfMonthZeroBasedWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetDate,
+ decls.NewInstanceOverload(overloads.TimestampToDayOfMonthOneBased,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToDayOfMonthOneBasedWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetDayOfWeek,
+ decls.NewInstanceOverload(overloads.TimestampToDayOfWeek,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToDayOfWeekWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetHours,
+ decls.NewInstanceOverload(overloads.TimestampToHours,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToHoursWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int),
+ decls.NewInstanceOverload(overloads.DurationToHours,
+ []*exprpb.Type{decls.Duration}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetMinutes,
+ decls.NewInstanceOverload(overloads.TimestampToMinutes,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToMinutesWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int),
+ decls.NewInstanceOverload(overloads.DurationToMinutes,
+ []*exprpb.Type{decls.Duration}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetSeconds,
+ decls.NewInstanceOverload(overloads.TimestampToSeconds,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToSecondsWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int),
+ decls.NewInstanceOverload(overloads.DurationToSeconds,
+ []*exprpb.Type{decls.Duration}, decls.Int)),
+
+ decls.NewFunction(overloads.TimeGetMilliseconds,
+ decls.NewInstanceOverload(overloads.TimestampToMilliseconds,
+ []*exprpb.Type{decls.Timestamp}, decls.Int),
+ decls.NewInstanceOverload(overloads.TimestampToMillisecondsWithTz,
+ []*exprpb.Type{decls.Timestamp, decls.String}, decls.Int),
+ decls.NewInstanceOverload(overloads.DurationToMilliseconds,
+ []*exprpb.Type{decls.Duration}, decls.Int))}...)
+}
diff --git a/vendor/github.com/google/cel-go/checker/types.go b/vendor/github.com/google/cel-go/checker/types.go
new file mode 100644
index 0000000000..38c11d41a0
--- /dev/null
+++ b/vendor/github.com/google/cel-go/checker/types.go
@@ -0,0 +1,505 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package checker
+
+import (
+ "fmt"
+ "strings"
+
+ "github.com/google/cel-go/checker/decls"
+
+ "google.golang.org/protobuf/proto"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+const (
+ kindUnknown = iota + 1
+ kindError
+ kindFunction
+ kindDyn
+ kindPrimitive
+ kindWellKnown
+ kindWrapper
+ kindNull
+ kindAbstract
+ kindType
+ kindList
+ kindMap
+ kindObject
+ kindTypeParam
+)
+
+// FormatCheckedType converts a type message into a string representation.
+func FormatCheckedType(t *exprpb.Type) string {
+ switch kindOf(t) {
+ case kindDyn:
+ return "dyn"
+ case kindFunction:
+ return formatFunction(t.GetFunction().GetResultType(),
+ t.GetFunction().GetArgTypes(),
+ false)
+ case kindList:
+ return fmt.Sprintf("list(%s)", FormatCheckedType(t.GetListType().ElemType))
+ case kindObject:
+ return t.GetMessageType()
+ case kindMap:
+ return fmt.Sprintf("map(%s, %s)",
+ FormatCheckedType(t.GetMapType().KeyType),
+ FormatCheckedType(t.GetMapType().ValueType))
+ case kindNull:
+ return "null"
+ case kindPrimitive:
+ switch t.GetPrimitive() {
+ case exprpb.Type_UINT64:
+ return "uint"
+ case exprpb.Type_INT64:
+ return "int"
+ }
+ return strings.Trim(strings.ToLower(t.GetPrimitive().String()), " ")
+ case kindType:
+ if t.GetType() == nil {
+ return "type"
+ }
+ return fmt.Sprintf("type(%s)", FormatCheckedType(t.GetType()))
+ case kindWellKnown:
+ switch t.GetWellKnown() {
+ case exprpb.Type_ANY:
+ return "any"
+ case exprpb.Type_DURATION:
+ return "duration"
+ case exprpb.Type_TIMESTAMP:
+ return "timestamp"
+ }
+ case kindWrapper:
+ return fmt.Sprintf("wrapper(%s)",
+ FormatCheckedType(decls.NewPrimitiveType(t.GetWrapper())))
+ case kindError:
+ return "!error!"
+ }
+ return t.String()
+}
+
+// isDyn returns true if the input t is either type DYN or a well-known ANY message.
+func isDyn(t *exprpb.Type) bool {
+ // Note: object type values that are well-known and map to a DYN value in practice
+ // are sanitized prior to being added to the environment.
+ switch kindOf(t) {
+ case kindDyn:
+ return true
+ case kindWellKnown:
+ return t.GetWellKnown() == exprpb.Type_ANY
+ default:
+ return false
+ }
+}
+
+// isDynOrError returns true if the input is either an Error, DYN, or well-known ANY message.
+func isDynOrError(t *exprpb.Type) bool {
+ switch kindOf(t) {
+ case kindError:
+ return true
+ default:
+ return isDyn(t)
+ }
+}
+
+// isEqualOrLessSpecific checks whether one type is equal or less specific than the other one.
+// A type is less specific if it matches the other type using the DYN type.
+func isEqualOrLessSpecific(t1 *exprpb.Type, t2 *exprpb.Type) bool {
+ kind1, kind2 := kindOf(t1), kindOf(t2)
+ // The first type is less specific.
+ if isDyn(t1) || kind1 == kindTypeParam {
+ return true
+ }
+ // The first type is not less specific.
+ if isDyn(t2) || kind2 == kindTypeParam {
+ return false
+ }
+ // Types must be of the same kind to be equal.
+ if kind1 != kind2 {
+ return false
+ }
+
+ // With limited exceptions for ANY and JSON values, the types must agree and be equivalent in
+ // order to return true.
+ switch kind1 {
+ case kindAbstract:
+ a1 := t1.GetAbstractType()
+ a2 := t2.GetAbstractType()
+ if a1.GetName() != a2.GetName() ||
+ len(a1.GetParameterTypes()) != len(a2.GetParameterTypes()) {
+ return false
+ }
+ for i, p1 := range a1.GetParameterTypes() {
+ if !isEqualOrLessSpecific(p1, a2.GetParameterTypes()[i]) {
+ return false
+ }
+ }
+ return true
+ case kindFunction:
+ fn1 := t1.GetFunction()
+ fn2 := t2.GetFunction()
+ if len(fn1.ArgTypes) != len(fn2.ArgTypes) {
+ return false
+ }
+ if !isEqualOrLessSpecific(fn1.ResultType, fn2.ResultType) {
+ return false
+ }
+ for i, a1 := range fn1.ArgTypes {
+ if !isEqualOrLessSpecific(a1, fn2.ArgTypes[i]) {
+ return false
+ }
+ }
+ return true
+ case kindList:
+ return isEqualOrLessSpecific(t1.GetListType().ElemType, t2.GetListType().ElemType)
+ case kindMap:
+ m1 := t1.GetMapType()
+ m2 := t2.GetMapType()
+ return isEqualOrLessSpecific(m1.KeyType, m2.KeyType) &&
+ isEqualOrLessSpecific(m1.ValueType, m2.ValueType)
+ case kindType:
+ return true
+ default:
+ return proto.Equal(t1, t2)
+ }
+}
+
+/// internalIsAssignable returns true if t1 is assignable to t2.
+func internalIsAssignable(m *mapping, t1 *exprpb.Type, t2 *exprpb.Type) bool {
+ // A type is always assignable to itself.
+ // Early terminate the call to avoid cases of infinite recursion.
+ if proto.Equal(t1, t2) {
+ return true
+ }
+ // Process type parameters.
+ kind1, kind2 := kindOf(t1), kindOf(t2)
+ if kind2 == kindTypeParam {
+ if t2Sub, found := m.find(t2); found {
+ // If the types are compatible, pick the more general type and return true
+ if !internalIsAssignable(m, t1, t2Sub) {
+ return false
+ }
+ m.add(t2, mostGeneral(t1, t2Sub))
+ return true
+ }
+ if notReferencedIn(m, t2, t1) {
+ m.add(t2, t1)
+ return true
+ }
+ }
+ if kind1 == kindTypeParam {
+ // For the lower type bound, we currently do not perform adjustment. The restricted
+ // way we use type parameters in lower type bounds, it is not necessary, but may
+ // become if we generalize type unification.
+ if t1Sub, found := m.find(t1); found {
+ // If the types are compatible, pick the more general type and return true
+ if !internalIsAssignable(m, t1Sub, t2) {
+ return false
+ }
+ m.add(t1, mostGeneral(t1Sub, t2))
+ return true
+ }
+ if notReferencedIn(m, t1, t2) {
+ m.add(t1, t2)
+ return true
+ }
+ }
+
+ // Next check for wildcard types.
+ if isDynOrError(t1) || isDynOrError(t2) {
+ return true
+ }
+
+ // Test for when the types do not need to agree, but are more specific than dyn.
+ switch kind1 {
+ case kindNull:
+ return internalIsAssignableNull(t2)
+ case kindPrimitive:
+ return internalIsAssignablePrimitive(t1.GetPrimitive(), t2)
+ case kindWrapper:
+ return internalIsAssignable(m, decls.NewPrimitiveType(t1.GetWrapper()), t2)
+ default:
+ if kind1 != kind2 {
+ return false
+ }
+ }
+
+ // Test for when the types must agree.
+ switch kind1 {
+ // ERROR, TYPE_PARAM, and DYN handled above.
+ case kindAbstract:
+ return internalIsAssignableAbstractType(m, t1.GetAbstractType(), t2.GetAbstractType())
+ case kindFunction:
+ return internalIsAssignableFunction(m, t1.GetFunction(), t2.GetFunction())
+ case kindList:
+ return internalIsAssignable(m, t1.GetListType().GetElemType(), t2.GetListType().GetElemType())
+ case kindMap:
+ return internalIsAssignableMap(m, t1.GetMapType(), t2.GetMapType())
+ case kindObject:
+ return t1.GetMessageType() == t2.GetMessageType()
+ case kindType:
+ // A type is a type is a type, any additional parameterization of the
+ // type cannot affect method resolution or assignability.
+ return true
+ case kindWellKnown:
+ return t1.GetWellKnown() == t2.GetWellKnown()
+ default:
+ return false
+ }
+}
+
+// internalIsAssignableAbstractType returns true if the abstract type names agree and all type
+// parameters are assignable.
+func internalIsAssignableAbstractType(m *mapping,
+ a1 *exprpb.Type_AbstractType,
+ a2 *exprpb.Type_AbstractType) bool {
+ if a1.GetName() != a2.GetName() {
+ return false
+ }
+ if internalIsAssignableList(m, a1.GetParameterTypes(), a2.GetParameterTypes()) {
+ return true
+ }
+ return false
+}
+
+// internalIsAssignableFunction returns true if the function return type and arg types are
+// assignable.
+func internalIsAssignableFunction(m *mapping,
+ f1 *exprpb.Type_FunctionType,
+ f2 *exprpb.Type_FunctionType) bool {
+ f1ArgTypes := flattenFunctionTypes(f1)
+ f2ArgTypes := flattenFunctionTypes(f2)
+ if internalIsAssignableList(m, f1ArgTypes, f2ArgTypes) {
+ return true
+ }
+ return false
+}
+
+// internalIsAssignableList returns true if the element types at each index in the list are
+// assignable from l1[i] to l2[i]. The list lengths must also agree for the lists to be
+// assignable.
+func internalIsAssignableList(m *mapping, l1 []*exprpb.Type, l2 []*exprpb.Type) bool {
+ if len(l1) != len(l2) {
+ return false
+ }
+ for i, t1 := range l1 {
+ if !internalIsAssignable(m, t1, l2[i]) {
+ return false
+ }
+ }
+ return true
+}
+
+// internalIsAssignableMap returns true if map m1 may be assigned to map m2.
+func internalIsAssignableMap(m *mapping, m1 *exprpb.Type_MapType, m2 *exprpb.Type_MapType) bool {
+ if internalIsAssignableList(m,
+ []*exprpb.Type{m1.GetKeyType(), m1.GetValueType()},
+ []*exprpb.Type{m2.GetKeyType(), m2.GetValueType()}) {
+ return true
+ }
+ return false
+}
+
+// internalIsAssignableNull returns true if the type is nullable.
+func internalIsAssignableNull(t *exprpb.Type) bool {
+ switch kindOf(t) {
+ case kindAbstract, kindObject, kindNull, kindWellKnown, kindWrapper:
+ return true
+ default:
+ return false
+ }
+}
+
+// internalIsAssignablePrimitive returns true if the target type is the same or if it is a wrapper
+// for the primitive type.
+func internalIsAssignablePrimitive(p exprpb.Type_PrimitiveType, target *exprpb.Type) bool {
+ switch kindOf(target) {
+ case kindPrimitive:
+ return p == target.GetPrimitive()
+ case kindWrapper:
+ return p == target.GetWrapper()
+ default:
+ return false
+ }
+}
+
+// isAssignable returns an updated type substitution mapping if t1 is assignable to t2.
+func isAssignable(m *mapping, t1 *exprpb.Type, t2 *exprpb.Type) *mapping {
+ mCopy := m.copy()
+ if internalIsAssignable(mCopy, t1, t2) {
+ return mCopy
+ }
+ return nil
+}
+
+// isAssignableList returns an updated type substitution mapping if l1 is assignable to l2.
+func isAssignableList(m *mapping, l1 []*exprpb.Type, l2 []*exprpb.Type) *mapping {
+ mCopy := m.copy()
+ if internalIsAssignableList(mCopy, l1, l2) {
+ return mCopy
+ }
+ return nil
+}
+
+// kindOf returns the kind of the type as defined in the checked.proto.
+func kindOf(t *exprpb.Type) int {
+ if t == nil || t.TypeKind == nil {
+ return kindUnknown
+ }
+ switch t.TypeKind.(type) {
+ case *exprpb.Type_Error:
+ return kindError
+ case *exprpb.Type_Function:
+ return kindFunction
+ case *exprpb.Type_Dyn:
+ return kindDyn
+ case *exprpb.Type_Primitive:
+ return kindPrimitive
+ case *exprpb.Type_WellKnown:
+ return kindWellKnown
+ case *exprpb.Type_Wrapper:
+ return kindWrapper
+ case *exprpb.Type_Null:
+ return kindNull
+ case *exprpb.Type_Type:
+ return kindType
+ case *exprpb.Type_ListType_:
+ return kindList
+ case *exprpb.Type_MapType_:
+ return kindMap
+ case *exprpb.Type_MessageType:
+ return kindObject
+ case *exprpb.Type_TypeParam:
+ return kindTypeParam
+ case *exprpb.Type_AbstractType_:
+ return kindAbstract
+ }
+ return kindUnknown
+}
+
+// mostGeneral returns the more general of two types which are known to unify.
+func mostGeneral(t1 *exprpb.Type, t2 *exprpb.Type) *exprpb.Type {
+ if isEqualOrLessSpecific(t1, t2) {
+ return t1
+ }
+ return t2
+}
+
+// notReferencedIn checks whether the type doesn't appear directly or transitively within the other
+// type. This is a standard requirement for type unification, commonly referred to as the "occurs
+// check".
+func notReferencedIn(m *mapping, t *exprpb.Type, withinType *exprpb.Type) bool {
+ if proto.Equal(t, withinType) {
+ return false
+ }
+ withinKind := kindOf(withinType)
+ switch withinKind {
+ case kindTypeParam:
+ wtSub, found := m.find(withinType)
+ if !found {
+ return true
+ }
+ return notReferencedIn(m, t, wtSub)
+ case kindAbstract:
+ for _, pt := range withinType.GetAbstractType().GetParameterTypes() {
+ if !notReferencedIn(m, t, pt) {
+ return false
+ }
+ }
+ return true
+ case kindFunction:
+ fn := withinType.GetFunction()
+ types := flattenFunctionTypes(fn)
+ for _, a := range types {
+ if !notReferencedIn(m, t, a) {
+ return false
+ }
+ }
+ return true
+ case kindList:
+ return notReferencedIn(m, t, withinType.GetListType().ElemType)
+ case kindMap:
+ mt := withinType.GetMapType()
+ return notReferencedIn(m, t, mt.KeyType) && notReferencedIn(m, t, mt.ValueType)
+ case kindWrapper:
+ return notReferencedIn(m, t, decls.NewPrimitiveType(withinType.GetWrapper()))
+ default:
+ return true
+ }
+}
+
+// substitute replaces all direct and indirect occurrences of bound type parameters. Unbound type
+// parameters are replaced by DYN if typeParamToDyn is true.
+func substitute(m *mapping, t *exprpb.Type, typeParamToDyn bool) *exprpb.Type {
+ if tSub, found := m.find(t); found {
+ return substitute(m, tSub, typeParamToDyn)
+ }
+ kind := kindOf(t)
+ if typeParamToDyn && kind == kindTypeParam {
+ return decls.Dyn
+ }
+ switch kind {
+ case kindAbstract:
+ // TODO: implement!
+ at := t.GetAbstractType()
+ params := make([]*exprpb.Type, len(at.GetParameterTypes()))
+ for i, p := range at.GetParameterTypes() {
+ params[i] = substitute(m, p, typeParamToDyn)
+ }
+ return decls.NewAbstractType(at.GetName(), params...)
+ case kindFunction:
+ fn := t.GetFunction()
+ rt := substitute(m, fn.ResultType, typeParamToDyn)
+ args := make([]*exprpb.Type, len(fn.ArgTypes))
+ for i, a := range fn.ArgTypes {
+ args[i] = substitute(m, a, typeParamToDyn)
+ }
+ return decls.NewFunctionType(rt, args...)
+ case kindList:
+ return decls.NewListType(substitute(m, t.GetListType().ElemType, typeParamToDyn))
+ case kindMap:
+ mt := t.GetMapType()
+ return decls.NewMapType(substitute(m, mt.KeyType, typeParamToDyn),
+ substitute(m, mt.ValueType, typeParamToDyn))
+ case kindType:
+ if t.GetType() != nil {
+ return decls.NewTypeType(substitute(m, t.GetType(), typeParamToDyn))
+ }
+ return t
+ default:
+ return t
+ }
+}
+
+func typeKey(t *exprpb.Type) string {
+ return FormatCheckedType(t)
+}
+
+// flattenFunctionTypes takes a function with arg types T1, T2, ..., TN and result type TR
+// and returns a slice containing {T1, T2, ..., TN, TR}.
+func flattenFunctionTypes(f *exprpb.Type_FunctionType) []*exprpb.Type {
+ argTypes := f.GetArgTypes()
+ if len(argTypes) == 0 {
+ return []*exprpb.Type{f.GetResultType()}
+ }
+ flattend := make([]*exprpb.Type, len(argTypes)+1, len(argTypes)+1)
+ for i, at := range argTypes {
+ flattend[i] = at
+ }
+ flattend[len(argTypes)] = f.GetResultType()
+ return flattend
+}
diff --git a/vendor/github.com/google/cel-go/common/BUILD.bazel b/vendor/github.com/google/cel-go/common/BUILD.bazel
new file mode 100644
index 0000000000..9e4ad65e9a
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/BUILD.bazel
@@ -0,0 +1,34 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "error.go",
+ "errors.go",
+ "location.go",
+ "source.go",
+ ],
+ importpath = "github.com/google/cel-go/common",
+ deps = [
+ "//common/runes:go_default_library",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_x_text//width:go_default_library",
+ ],
+)
+
+go_test(
+ name = "go_default_test",
+ size = "small",
+ srcs = [
+ "errors_test.go",
+ "source_test.go",
+ ],
+ embed = [
+ ":go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/common/containers/BUILD.bazel b/vendor/github.com/google/cel-go/common/containers/BUILD.bazel
new file mode 100644
index 0000000000..18142d94ef
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/containers/BUILD.bazel
@@ -0,0 +1,31 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "container.go",
+ ],
+ importpath = "github.com/google/cel-go/common/containers",
+ deps = [
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ ],
+)
+
+go_test(
+ name = "go_default_test",
+ size = "small",
+ srcs = [
+ "container_test.go",
+ ],
+ embed = [
+ ":go_default_library",
+ ],
+ deps = [
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/common/containers/container.go b/vendor/github.com/google/cel-go/common/containers/container.go
new file mode 100644
index 0000000000..07ae72c81b
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/containers/container.go
@@ -0,0 +1,316 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package containers defines types and functions for resolving qualified names within a namespace
+// or type provided to CEL.
+package containers
+
+import (
+ "fmt"
+ "strings"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+var (
+ // DefaultContainer has an empty container name.
+ DefaultContainer *Container = nil
+
+ // Empty map to search for aliases when needed.
+ noAliases = make(map[string]string)
+)
+
+// NewContainer creates a new Container with the fully-qualified name.
+func NewContainer(opts ...ContainerOption) (*Container, error) {
+ var c *Container
+ var err error
+ for _, opt := range opts {
+ c, err = opt(c)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return c, nil
+}
+
+// Container holds a reference to an optional qualified container name and set of aliases.
+//
+// The program container can be used to simplify variable, function, and type specification within
+// CEL programs and behaves more or less like a C++ namespace. See ResolveCandidateNames for more
+// details.
+type Container struct {
+ name string
+ aliases map[string]string
+}
+
+// Extend creates a new Container with the existing settings and applies a series of
+// ContainerOptions to further configure the new container.
+func (c *Container) Extend(opts ...ContainerOption) (*Container, error) {
+ if c == nil {
+ return NewContainer(opts...)
+ }
+ // Copy the name and aliases of the existing container.
+ ext := &Container{name: c.Name()}
+ if len(c.aliasSet()) > 0 {
+ aliasSet := make(map[string]string, len(c.aliasSet()))
+ for k, v := range c.aliasSet() {
+ aliasSet[k] = v
+ }
+ ext.aliases = aliasSet
+ }
+ // Apply the new options to the container.
+ var err error
+ for _, opt := range opts {
+ ext, err = opt(ext)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return ext, nil
+}
+
+// Name returns the fully-qualified name of the container.
+//
+// The name may conceptually be a namespace, package, or type.
+func (c *Container) Name() string {
+ if c == nil {
+ return ""
+ }
+ return c.name
+}
+
+// ResolveCandidateNames returns the candidates name of namespaced identifiers in C++ resolution
+// order.
+//
+// Names which shadow other names are returned first. If a name includes a leading dot ('.'),
+// the name is treated as an absolute identifier which cannot be shadowed.
+//
+// Given a container name a.b.c.M.N and a type name R.s, this will deliver in order:
+//
+// a.b.c.M.N.R.s
+// a.b.c.M.R.s
+// a.b.c.R.s
+// a.b.R.s
+// a.R.s
+// R.s
+//
+// If aliases or abbreviations are configured for the container, then alias names will take
+// precedence over containerized names.
+func (c *Container) ResolveCandidateNames(name string) []string {
+ if strings.HasPrefix(name, ".") {
+ qn := name[1:]
+ alias, isAlias := c.findAlias(qn)
+ if isAlias {
+ return []string{alias}
+ }
+ return []string{qn}
+ }
+ alias, isAlias := c.findAlias(name)
+ if isAlias {
+ return []string{alias}
+ }
+ if c.Name() == "" {
+ return []string{name}
+ }
+ nextCont := c.Name()
+ candidates := []string{nextCont + "." + name}
+ for i := strings.LastIndex(nextCont, "."); i >= 0; i = strings.LastIndex(nextCont, ".") {
+ nextCont = nextCont[:i]
+ candidates = append(candidates, nextCont+"."+name)
+ }
+ return append(candidates, name)
+}
+
+// aliasSet returns the alias to fully-qualified name mapping stored in the container.
+func (c *Container) aliasSet() map[string]string {
+ if c == nil || c.aliases == nil {
+ return noAliases
+ }
+ return c.aliases
+}
+
+// findAlias takes a name as input and returns an alias expansion if one exists.
+//
+// If the name is qualified, the first component of the qualified name is checked against known
+// aliases. Any alias that is found in a qualified name is expanded in the result:
+//
+// alias: R -> my.alias.R
+// name: R.S.T
+// output: my.alias.R.S.T
+//
+// Note, the name must not have a leading dot.
+func (c *Container) findAlias(name string) (string, bool) {
+ // If an alias exists for the name, ensure it is searched last.
+ simple := name
+ qualifier := ""
+ dot := strings.Index(name, ".")
+ if dot >= 0 {
+ simple = name[0:dot]
+ qualifier = name[dot:]
+ }
+ alias, found := c.aliasSet()[simple]
+ if !found {
+ return "", false
+ }
+ return alias + qualifier, true
+}
+
+// ContainerOption specifies a functional configuration option for a Container.
+//
+// Note, ContainerOption implementations must be able to handle nil container inputs.
+type ContainerOption func(*Container) (*Container, error)
+
+// Abbrevs configures a set of simple names as abbreviations for fully-qualified names.
+//
+// An abbreviation (abbrev for short) is a simple name that expands to a fully-qualified name.
+// Abbreviations can be useful when working with variables, functions, and especially types from
+// multiple namespaces:
+//
+// // CEL object construction
+// qual.pkg.version.ObjTypeName{
+// field: alt.container.ver.FieldTypeName{value: ...}
+// }
+//
+// Only one the qualified names above may be used as the CEL container, so at least one of these
+// references must be a long qualified name within an otherwise short CEL program. Using the
+// following abbreviations, the program becomes much simpler:
+//
+// // CEL Go option
+// Abbrevs("qual.pkg.version.ObjTypeName", "alt.container.ver.FieldTypeName")
+// // Simplified Object construction
+// ObjTypeName{field: FieldTypeName{value: ...}}
+//
+// There are a few rules for the qualified names and the simple abbreviations generated from them:
+// - Qualified names must be dot-delimited, e.g. `package.subpkg.name`.
+// - The last element in the qualified name is the abbreviation.
+// - Abbreviations must not collide with each other.
+// - The abbreviation must not collide with unqualified names in use.
+//
+// Abbreviations are distinct from container-based references in the following important ways:
+// - Abbreviations must expand to a fully-qualified name.
+// - Expanded abbreviations do not participate in namespace resolution.
+// - Abbreviation expansion is done instead of the container search for a matching identifier.
+// - Containers follow C++ namespace resolution rules with searches from the most qualified name
+// to the least qualified name.
+// - Container references within the CEL program may be relative, and are resolved to fully
+// qualified names at either type-check time or program plan time, whichever comes first.
+//
+// If there is ever a case where an identifier could be in both the container and as an
+// abbreviation, the abbreviation wins as this will ensure that the meaning of a program is
+// preserved between compilations even as the container evolves.
+func Abbrevs(qualifiedNames ...string) ContainerOption {
+ return func(c *Container) (*Container, error) {
+ for _, qn := range qualifiedNames {
+ ind := strings.LastIndex(qn, ".")
+ if ind <= 0 || ind >= len(qn)-1 {
+ return nil, fmt.Errorf(
+ "invalid qualified name: %s, wanted name of the form 'qualified.name'", qn)
+ }
+ alias := qn[ind+1:]
+ var err error
+ c, err = aliasAs("abbreviation", qn, alias)(c)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return c, nil
+ }
+}
+
+// Alias associates a fully-qualified name with a user-defined alias.
+//
+// In general, Abbrevs is preferred to Alias since the names generated from the Abbrevs option
+// are more easily traced back to source code. The Alias option is useful for propagating alias
+// configuration from one Container instance to another, and may also be useful for remapping
+// poorly chosen protobuf message / package names.
+//
+// Note: all of the rules that apply to Abbrevs also apply to Alias.
+func Alias(qualifiedName, alias string) ContainerOption {
+ return aliasAs("alias", qualifiedName, alias)
+}
+
+func aliasAs(kind, qualifiedName, alias string) ContainerOption {
+ return func(c *Container) (*Container, error) {
+ if len(alias) == 0 || strings.Contains(alias, ".") {
+ return nil, fmt.Errorf(
+ "%s must be non-empty and simple (not qualified): %s=%s", kind, kind, alias)
+ }
+
+ if qualifiedName[0:1] == "." {
+ return nil, fmt.Errorf("qualified name must not begin with a leading '.': %s",
+ qualifiedName)
+ }
+ ind := strings.LastIndex(qualifiedName, ".")
+ if ind <= 0 || ind == len(qualifiedName)-1 {
+ return nil, fmt.Errorf("%s must refer to a valid qualified name: %s",
+ kind, qualifiedName)
+ }
+ aliasRef, found := c.aliasSet()[alias]
+ if found {
+ return nil, fmt.Errorf(
+ "%s collides with existing reference: name=%s, %s=%s, existing=%s",
+ kind, qualifiedName, kind, alias, aliasRef)
+ }
+ if strings.HasPrefix(c.Name(), alias+".") || c.Name() == alias {
+ return nil, fmt.Errorf(
+ "%s collides with container name: name=%s, %s=%s, container=%s",
+ kind, qualifiedName, kind, alias, c.Name())
+ }
+ if c == nil {
+ c = &Container{}
+ }
+ if c.aliases == nil {
+ c.aliases = make(map[string]string)
+ }
+ c.aliases[alias] = qualifiedName
+ return c, nil
+ }
+}
+
+// Name sets the fully-qualified name of the Container.
+func Name(name string) ContainerOption {
+ return func(c *Container) (*Container, error) {
+ if len(name) > 0 && name[0:1] == "." {
+ return nil, fmt.Errorf("container name must not contain a leading '.': %s", name)
+ }
+ if c.Name() == name {
+ return c, nil
+ }
+ if c == nil {
+ return &Container{name: name}, nil
+ }
+ c.name = name
+ return c, nil
+ }
+}
+
+// ToQualifiedName converts an expression AST into a qualified name if possible, with a boolean
+// 'found' value that indicates if the conversion is successful.
+func ToQualifiedName(e *exprpb.Expr) (string, bool) {
+ switch e.ExprKind.(type) {
+ case *exprpb.Expr_IdentExpr:
+ id := e.GetIdentExpr()
+ return id.Name, true
+ case *exprpb.Expr_SelectExpr:
+ sel := e.GetSelectExpr()
+ // Test only expressions are not valid as qualified names.
+ if sel.GetTestOnly() {
+ return "", false
+ }
+ if qual, found := ToQualifiedName(sel.Operand); found {
+ return qual + "." + sel.Field, true
+ }
+ }
+ return "", false
+}
diff --git a/vendor/github.com/google/cel-go/common/debug/BUILD.bazel b/vendor/github.com/google/cel-go/common/debug/BUILD.bazel
new file mode 100644
index 0000000000..cf5c5d2467
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/debug/BUILD.bazel
@@ -0,0 +1,18 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "debug.go",
+ ],
+ importpath = "github.com/google/cel-go/common/debug",
+ deps = [
+ "//common:go_default_library",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/common/debug/debug.go b/vendor/github.com/google/cel-go/common/debug/debug.go
new file mode 100644
index 0000000000..5a4894733d
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/debug/debug.go
@@ -0,0 +1,305 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package debug provides tools to print a parsed expression graph and
+// adorn each expression element with additional metadata.
+package debug
+
+import (
+ "bytes"
+ "fmt"
+ "strconv"
+ "strings"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// Adorner returns debug metadata that will be tacked on to the string
+// representation of an expression.
+type Adorner interface {
+ // GetMetadata for the input context.
+ GetMetadata(ctx interface{}) string
+}
+
+// Writer manages writing expressions to an internal string.
+type Writer interface {
+ fmt.Stringer
+
+ // Buffer pushes an expression into an internal queue of expressions to
+ // write to a string.
+ Buffer(e *exprpb.Expr)
+}
+
+type emptyDebugAdorner struct {
+}
+
+var emptyAdorner Adorner = &emptyDebugAdorner{}
+
+func (a *emptyDebugAdorner) GetMetadata(e interface{}) string {
+ return ""
+}
+
+// ToDebugString gives the unadorned string representation of the Expr.
+func ToDebugString(e *exprpb.Expr) string {
+ return ToAdornedDebugString(e, emptyAdorner)
+}
+
+// ToAdornedDebugString gives the adorned string representation of the Expr.
+func ToAdornedDebugString(e *exprpb.Expr, adorner Adorner) string {
+ w := newDebugWriter(adorner)
+ w.Buffer(e)
+ return w.String()
+}
+
+// debugWriter is used to print out pretty-printed debug strings.
+type debugWriter struct {
+ adorner Adorner
+ buffer bytes.Buffer
+ indent int
+ lineStart bool
+}
+
+func newDebugWriter(a Adorner) *debugWriter {
+ return &debugWriter{
+ adorner: a,
+ indent: 0,
+ lineStart: true,
+ }
+}
+
+func (w *debugWriter) Buffer(e *exprpb.Expr) {
+ if e == nil {
+ return
+ }
+ switch e.ExprKind.(type) {
+ case *exprpb.Expr_ConstExpr:
+ w.append(formatLiteral(e.GetConstExpr()))
+ case *exprpb.Expr_IdentExpr:
+ w.append(e.GetIdentExpr().Name)
+ case *exprpb.Expr_SelectExpr:
+ w.appendSelect(e.GetSelectExpr())
+ case *exprpb.Expr_CallExpr:
+ w.appendCall(e.GetCallExpr())
+ case *exprpb.Expr_ListExpr:
+ w.appendList(e.GetListExpr())
+ case *exprpb.Expr_StructExpr:
+ w.appendStruct(e.GetStructExpr())
+ case *exprpb.Expr_ComprehensionExpr:
+ w.appendComprehension(e.GetComprehensionExpr())
+ }
+ w.adorn(e)
+}
+
+func (w *debugWriter) appendSelect(sel *exprpb.Expr_Select) {
+ w.Buffer(sel.Operand)
+ w.append(".")
+ w.append(sel.Field)
+ if sel.TestOnly {
+ w.append("~test-only~")
+ }
+}
+
+func (w *debugWriter) appendCall(call *exprpb.Expr_Call) {
+ if call.Target != nil {
+ w.Buffer(call.Target)
+ w.append(".")
+ }
+ w.append(call.Function)
+ w.append("(")
+ if len(call.GetArgs()) > 0 {
+ w.addIndent()
+ w.appendLine()
+ for i, arg := range call.Args {
+ if i > 0 {
+ w.append(",")
+ w.appendLine()
+ }
+ w.Buffer(arg)
+ }
+ w.removeIndent()
+ w.appendLine()
+ }
+ w.append(")")
+}
+
+func (w *debugWriter) appendList(list *exprpb.Expr_CreateList) {
+ w.append("[")
+ if len(list.GetElements()) > 0 {
+ w.appendLine()
+ w.addIndent()
+ for i, elem := range list.Elements {
+ if i > 0 {
+ w.append(",")
+ w.appendLine()
+ }
+ w.Buffer(elem)
+ }
+ w.removeIndent()
+ w.appendLine()
+ }
+ w.append("]")
+}
+
+func (w *debugWriter) appendStruct(obj *exprpb.Expr_CreateStruct) {
+ if obj.MessageName != "" {
+ w.appendObject(obj)
+ } else {
+ w.appendMap(obj)
+ }
+}
+
+func (w *debugWriter) appendObject(obj *exprpb.Expr_CreateStruct) {
+ w.append(obj.MessageName)
+ w.append("{")
+ if len(obj.Entries) > 0 {
+ w.appendLine()
+ w.addIndent()
+ for i, entry := range obj.Entries {
+ if i > 0 {
+ w.append(",")
+ w.appendLine()
+ }
+ w.append(entry.GetFieldKey())
+ w.append(":")
+ w.Buffer(entry.Value)
+ w.adorn(entry)
+ }
+ w.removeIndent()
+ w.appendLine()
+ }
+ w.append("}")
+}
+
+func (w *debugWriter) appendMap(obj *exprpb.Expr_CreateStruct) {
+ w.append("{")
+ if len(obj.Entries) > 0 {
+ w.appendLine()
+ w.addIndent()
+ for i, entry := range obj.Entries {
+ if i > 0 {
+ w.append(",")
+ w.appendLine()
+ }
+ w.Buffer(entry.GetMapKey())
+ w.append(":")
+ w.Buffer(entry.Value)
+ w.adorn(entry)
+ }
+ w.removeIndent()
+ w.appendLine()
+ }
+ w.append("}")
+}
+
+func (w *debugWriter) appendComprehension(comprehension *exprpb.Expr_Comprehension) {
+ w.append("__comprehension__(")
+ w.addIndent()
+ w.appendLine()
+ w.append("// Variable")
+ w.appendLine()
+ w.append(comprehension.IterVar)
+ w.append(",")
+ w.appendLine()
+ w.append("// Target")
+ w.appendLine()
+ w.Buffer(comprehension.IterRange)
+ w.append(",")
+ w.appendLine()
+ w.append("// Accumulator")
+ w.appendLine()
+ w.append(comprehension.AccuVar)
+ w.append(",")
+ w.appendLine()
+ w.append("// Init")
+ w.appendLine()
+ w.Buffer(comprehension.AccuInit)
+ w.append(",")
+ w.appendLine()
+ w.append("// LoopCondition")
+ w.appendLine()
+ w.Buffer(comprehension.LoopCondition)
+ w.append(",")
+ w.appendLine()
+ w.append("// LoopStep")
+ w.appendLine()
+ w.Buffer(comprehension.LoopStep)
+ w.append(",")
+ w.appendLine()
+ w.append("// Result")
+ w.appendLine()
+ w.Buffer(comprehension.Result)
+ w.append(")")
+ w.removeIndent()
+}
+
+func formatLiteral(c *exprpb.Constant) string {
+ switch c.ConstantKind.(type) {
+ case *exprpb.Constant_BoolValue:
+ return fmt.Sprintf("%t", c.GetBoolValue())
+ case *exprpb.Constant_BytesValue:
+ return fmt.Sprintf("b\"%s\"", string(c.GetBytesValue()))
+ case *exprpb.Constant_DoubleValue:
+ return fmt.Sprintf("%v", c.GetDoubleValue())
+ case *exprpb.Constant_Int64Value:
+ return fmt.Sprintf("%d", c.GetInt64Value())
+ case *exprpb.Constant_StringValue:
+ return strconv.Quote(c.GetStringValue())
+ case *exprpb.Constant_Uint64Value:
+ return fmt.Sprintf("%du", c.GetUint64Value())
+ case *exprpb.Constant_NullValue:
+ return "null"
+ default:
+ panic("Unknown constant type")
+ }
+}
+
+func (w *debugWriter) append(s string) {
+ w.doIndent()
+ w.buffer.WriteString(s)
+}
+
+func (w *debugWriter) appendFormat(f string, args ...interface{}) {
+ w.append(fmt.Sprintf(f, args...))
+}
+
+func (w *debugWriter) doIndent() {
+ if w.lineStart {
+ w.lineStart = false
+ w.buffer.WriteString(strings.Repeat(" ", w.indent))
+ }
+}
+
+func (w *debugWriter) adorn(e interface{}) {
+ w.append(w.adorner.GetMetadata(e))
+}
+
+func (w *debugWriter) appendLine() {
+ w.buffer.WriteString("\n")
+ w.lineStart = true
+}
+
+func (w *debugWriter) addIndent() {
+ w.indent++
+}
+
+func (w *debugWriter) removeIndent() {
+ w.indent--
+ if w.indent < 0 {
+ panic("negative indent")
+ }
+}
+
+func (w *debugWriter) String() string {
+ return w.buffer.String()
+}
diff --git a/vendor/github.com/google/cel-go/common/doc.go b/vendor/github.com/google/cel-go/common/doc.go
new file mode 100644
index 0000000000..5362fdfe4b
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/doc.go
@@ -0,0 +1,17 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package common defines types and utilities common to expression parsing,
+// checking, and interpretation
+package common
diff --git a/vendor/github.com/google/cel-go/common/error.go b/vendor/github.com/google/cel-go/common/error.go
new file mode 100644
index 0000000000..bfe93d9737
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/error.go
@@ -0,0 +1,70 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package common
+
+import (
+ "fmt"
+ "strings"
+ "unicode/utf8"
+
+ "golang.org/x/text/width"
+)
+
+// Error type which references a location within source and a message.
+type Error struct {
+ Location Location
+ Message string
+}
+
+const (
+ dot = "."
+ ind = "^"
+)
+
+var (
+ wideDot = width.Widen.String(dot)
+ wideInd = width.Widen.String(ind)
+)
+
+// ToDisplayString decorates the error message with the source location.
+func (e *Error) ToDisplayString(source Source) string {
+ var result = fmt.Sprintf("ERROR: %s:%d:%d: %s",
+ source.Description(),
+ e.Location.Line(),
+ e.Location.Column()+1, // add one to the 0-based column for display
+ e.Message)
+ if snippet, found := source.Snippet(e.Location.Line()); found {
+ snippet := strings.Replace(snippet, "\t", " ", -1)
+ srcLine := "\n | " + snippet
+ var bytes = []byte(snippet)
+ var indLine = "\n | "
+ for i := 0; i < e.Location.Column() && len(bytes) > 0; i++ {
+ _, sz := utf8.DecodeRune(bytes)
+ bytes = bytes[sz:]
+ if sz > 1 {
+ indLine += wideDot
+ } else {
+ indLine += dot
+ }
+ }
+ if _, sz := utf8.DecodeRune(bytes); sz > 1 {
+ indLine += wideInd
+ } else {
+ indLine += ind
+ }
+ result += srcLine + indLine
+ }
+ return result
+}
diff --git a/vendor/github.com/google/cel-go/common/errors.go b/vendor/github.com/google/cel-go/common/errors.go
new file mode 100644
index 0000000000..6be0fdef32
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/errors.go
@@ -0,0 +1,74 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package common
+
+import (
+ "fmt"
+ "sort"
+)
+
+// Errors type which contains a list of errors observed during parsing.
+type Errors struct {
+ errors []Error
+ source Source
+}
+
+// NewErrors creates a new instance of the Errors type.
+func NewErrors(source Source) *Errors {
+ return &Errors{
+ errors: []Error{},
+ source: source}
+}
+
+// ReportError records an error at a source location.
+func (e *Errors) ReportError(l Location, format string, args ...interface{}) {
+ err := Error{
+ Location: l,
+ Message: fmt.Sprintf(format, args...),
+ }
+ e.errors = append(e.errors, err)
+}
+
+// GetErrors returns the list of observed errors.
+func (e *Errors) GetErrors() []Error {
+ return e.errors[:]
+}
+
+// Append takes an Errors object as input creates a new Errors object with the current and input
+// errors.
+func (e *Errors) Append(errs []Error) *Errors {
+ return &Errors{
+ errors: append(e.errors, errs...),
+ source: e.source,
+ }
+}
+
+// ToDisplayString returns the error set to a newline delimited string.
+func (e *Errors) ToDisplayString() string {
+ var result = ""
+ sort.SliceStable(e.errors, func(i, j int) bool {
+ ei := e.errors[i].Location
+ ej := e.errors[j].Location
+ return ei.Line() < ej.Line() ||
+ (ei.Line() == ej.Line() && ei.Column() < ej.Column())
+ })
+ for i, err := range e.errors {
+ if i >= 1 {
+ result += "\n"
+ }
+ result += err.ToDisplayString(e.source)
+ }
+ return result
+}
diff --git a/vendor/github.com/google/cel-go/common/location.go b/vendor/github.com/google/cel-go/common/location.go
new file mode 100644
index 0000000000..31fce6cd31
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/location.go
@@ -0,0 +1,51 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package common
+
+// Location interface to represent a location within Source.
+type Location interface {
+ Line() int // 1-based line number within source.
+ Column() int // 0-based column number within source.
+}
+
+// SourceLocation helper type to manually construct a location.
+type SourceLocation struct {
+ line int
+ column int
+}
+
+var (
+ // Location implements the SourcceLocation interface.
+ _ Location = &SourceLocation{}
+ // NoLocation is a particular illegal location.
+ NoLocation = &SourceLocation{-1, -1}
+)
+
+// NewLocation creates a new location.
+func NewLocation(line, column int) Location {
+ return &SourceLocation{
+ line: line,
+ column: column}
+}
+
+// Line returns the 1-based line of the location.
+func (l *SourceLocation) Line() int {
+ return l.line
+}
+
+// Column returns the 0-based column number of the location.
+func (l *SourceLocation) Column() int {
+ return l.column
+}
diff --git a/vendor/github.com/google/cel-go/common/operators/BUILD.bazel b/vendor/github.com/google/cel-go/common/operators/BUILD.bazel
new file mode 100644
index 0000000000..b5b67f0623
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/operators/BUILD.bazel
@@ -0,0 +1,14 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "operators.go",
+ ],
+ importpath = "github.com/google/cel-go/common/operators",
+)
diff --git a/vendor/github.com/google/cel-go/common/operators/operators.go b/vendor/github.com/google/cel-go/common/operators/operators.go
new file mode 100644
index 0000000000..8f832c4d44
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/operators/operators.go
@@ -0,0 +1,145 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package operators defines the internal function names of operators.
+//
+// ALl operators in the expression language are modelled as function calls.
+package operators
+
+// String "names" for CEL operators.
+const (
+ // Symbolic operators.
+ Conditional = "_?_:_"
+ LogicalAnd = "_&&_"
+ LogicalOr = "_||_"
+ LogicalNot = "!_"
+ Equals = "_==_"
+ NotEquals = "_!=_"
+ Less = "_<_"
+ LessEquals = "_<=_"
+ Greater = "_>_"
+ GreaterEquals = "_>=_"
+ Add = "_+_"
+ Subtract = "_-_"
+ Multiply = "_*_"
+ Divide = "_/_"
+ Modulo = "_%_"
+ Negate = "-_"
+ Index = "_[_]"
+
+ // Macros, must have a valid identifier.
+ Has = "has"
+ All = "all"
+ Exists = "exists"
+ ExistsOne = "exists_one"
+ Map = "map"
+ Filter = "filter"
+
+ // Named operators, must not have be valid identifiers.
+ NotStrictlyFalse = "@not_strictly_false"
+ In = "@in"
+
+ // Deprecated: named operators with valid identifiers.
+ OldNotStrictlyFalse = "__not_strictly_false__"
+ OldIn = "_in_"
+)
+
+var (
+ operators = map[string]string{
+ "+": Add,
+ "/": Divide,
+ "==": Equals,
+ ">": Greater,
+ ">=": GreaterEquals,
+ "in": In,
+ "<": Less,
+ "<=": LessEquals,
+ "%": Modulo,
+ "*": Multiply,
+ "!=": NotEquals,
+ "-": Subtract,
+ }
+ reverseOperators = map[string]string{
+ Add: "+",
+ Divide: "/",
+ Equals: "==",
+ Greater: ">",
+ GreaterEquals: ">=",
+ In: "in",
+ Less: "<",
+ LessEquals: "<=",
+ LogicalAnd: "&&",
+ LogicalNot: "!",
+ LogicalOr: "||",
+ Modulo: "%",
+ Multiply: "*",
+ Negate: "-",
+ NotEquals: "!=",
+ OldIn: "in",
+ Subtract: "-",
+ }
+ // precedence of the operator, where the higher value means higher.
+ precedence = map[string]int{
+ Conditional: 8,
+ LogicalOr: 7,
+ LogicalAnd: 6,
+ Equals: 5,
+ Greater: 5,
+ GreaterEquals: 5,
+ In: 5,
+ Less: 5,
+ LessEquals: 5,
+ NotEquals: 5,
+ OldIn: 5,
+ Add: 4,
+ Subtract: 4,
+ Divide: 3,
+ Modulo: 3,
+ Multiply: 3,
+ LogicalNot: 2,
+ Negate: 2,
+ Index: 1,
+ }
+)
+
+// Find the internal function name for an operator, if the input text is one.
+func Find(text string) (string, bool) {
+ op, found := operators[text]
+ return op, found
+}
+
+// FindReverse returns the unmangled, text representation of the operator.
+func FindReverse(op string) (string, bool) {
+ txt, found := reverseOperators[op]
+ return txt, found
+}
+
+// FindReverseBinaryOperator returns the unmangled, text representation of a binary operator.
+func FindReverseBinaryOperator(op string) (string, bool) {
+ if op == LogicalNot || op == Negate {
+ return "", false
+ }
+ txt, found := reverseOperators[op]
+ return txt, found
+}
+
+// Precedence returns the operator precedence, where the higher the number indicates
+// higher precedence operations.
+func Precedence(op string) int {
+ p, found := precedence[op]
+ if found {
+ return p
+ }
+ return 0
+}
diff --git a/vendor/github.com/google/cel-go/common/overloads/BUILD.bazel b/vendor/github.com/google/cel-go/common/overloads/BUILD.bazel
new file mode 100644
index 0000000000..e46e2f4830
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/overloads/BUILD.bazel
@@ -0,0 +1,14 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "overloads.go",
+ ],
+ importpath = "github.com/google/cel-go/common/overloads",
+)
diff --git a/vendor/github.com/google/cel-go/common/overloads/overloads.go b/vendor/github.com/google/cel-go/common/overloads/overloads.go
new file mode 100644
index 0000000000..a1c01ee725
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/overloads/overloads.go
@@ -0,0 +1,293 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package overloads defines the internal overload identifiers for function and
+// operator overloads.
+package overloads
+
+// Boolean logic overloads
+const (
+ Conditional = "conditional"
+ LogicalAnd = "logical_and"
+ LogicalOr = "logical_or"
+ LogicalNot = "logical_not"
+ NotStrictlyFalse = "not_strictly_false"
+ Equals = "equals"
+ NotEquals = "not_equals"
+ LessBool = "less_bool"
+ LessInt64 = "less_int64"
+ LessUint64 = "less_uint64"
+ LessDouble = "less_double"
+ LessString = "less_string"
+ LessBytes = "less_bytes"
+ LessTimestamp = "less_timestamp"
+ LessDuration = "less_duration"
+ LessEqualsBool = "less_equals_bool"
+ LessEqualsInt64 = "less_equals_int64"
+ LessEqualsUint64 = "less_equals_uint64"
+ LessEqualsDouble = "less_equals_double"
+ LessEqualsString = "less_equals_string"
+ LessEqualsBytes = "less_equals_bytes"
+ LessEqualsTimestamp = "less_equals_timestamp"
+ LessEqualsDuration = "less_equals_duration"
+ GreaterBool = "greater_bool"
+ GreaterInt64 = "greater_int64"
+ GreaterUint64 = "greater_uint64"
+ GreaterDouble = "greater_double"
+ GreaterString = "greater_string"
+ GreaterBytes = "greater_bytes"
+ GreaterTimestamp = "greater_timestamp"
+ GreaterDuration = "greater_duration"
+ GreaterEqualsBool = "greater_equals_bool"
+ GreaterEqualsInt64 = "greater_equals_int64"
+ GreaterEqualsUint64 = "greater_equals_uint64"
+ GreaterEqualsDouble = "greater_equals_double"
+ GreaterEqualsString = "greater_equals_string"
+ GreaterEqualsBytes = "greater_equals_bytes"
+ GreaterEqualsTimestamp = "greater_equals_timestamp"
+ GreaterEqualsDuration = "greater_equals_duration"
+)
+
+// Math overloads
+const (
+ AddInt64 = "add_int64"
+ AddUint64 = "add_uint64"
+ AddDouble = "add_double"
+ AddString = "add_string"
+ AddBytes = "add_bytes"
+ AddList = "add_list"
+ AddTimestampDuration = "add_timestamp_duration"
+ AddDurationTimestamp = "add_duration_timestamp"
+ AddDurationDuration = "add_duration_duration"
+ SubtractInt64 = "subtract_int64"
+ SubtractUint64 = "subtract_uint64"
+ SubtractDouble = "subtract_double"
+ SubtractTimestampTimestamp = "subtract_timestamp_timestamp"
+ SubtractTimestampDuration = "subtract_timestamp_duration"
+ SubtractDurationDuration = "subtract_duration_duration"
+ MultiplyInt64 = "multiply_int64"
+ MultiplyUint64 = "multiply_uint64"
+ MultiplyDouble = "multiply_double"
+ DivideInt64 = "divide_int64"
+ DivideUint64 = "divide_uint64"
+ DivideDouble = "divide_double"
+ ModuloInt64 = "modulo_int64"
+ ModuloUint64 = "modulo_uint64"
+ NegateInt64 = "negate_int64"
+ NegateDouble = "negate_double"
+)
+
+// Index overloads
+const (
+ IndexList = "index_list"
+ IndexMap = "index_map"
+ IndexMessage = "index_message" // TODO: introduce concept of types.Message
+)
+
+// In operators
+const (
+ DeprecatedIn = "in"
+ InList = "in_list"
+ InMap = "in_map"
+ InMessage = "in_message" // TODO: introduce concept of types.Message
+)
+
+// Size overloads
+const (
+ Size = "size"
+ SizeString = "size_string"
+ SizeBytes = "size_bytes"
+ SizeList = "size_list"
+ SizeMap = "size_map"
+ SizeStringInst = "string_size"
+ SizeBytesInst = "bytes_size"
+ SizeListInst = "list_size"
+ SizeMapInst = "map_size"
+)
+
+// String function names.
+const (
+ Contains = "contains"
+ EndsWith = "endsWith"
+ Matches = "matches"
+ StartsWith = "startsWith"
+)
+
+// String function overload names.
+const (
+ ContainsString = "contains_string"
+ EndsWithString = "ends_with_string"
+ MatchesString = "matches_string"
+ StartsWithString = "starts_with_string"
+)
+
+// Time-based functions.
+const (
+ TimeGetFullYear = "getFullYear"
+ TimeGetMonth = "getMonth"
+ TimeGetDayOfYear = "getDayOfYear"
+ TimeGetDate = "getDate"
+ TimeGetDayOfMonth = "getDayOfMonth"
+ TimeGetDayOfWeek = "getDayOfWeek"
+ TimeGetHours = "getHours"
+ TimeGetMinutes = "getMinutes"
+ TimeGetSeconds = "getSeconds"
+ TimeGetMilliseconds = "getMilliseconds"
+)
+
+// Timestamp overloads for time functions without timezones.
+const (
+ TimestampToYear = "timestamp_to_year"
+ TimestampToMonth = "timestamp_to_month"
+ TimestampToDayOfYear = "timestamp_to_day_of_year"
+ TimestampToDayOfMonthZeroBased = "timestamp_to_day_of_month"
+ TimestampToDayOfMonthOneBased = "timestamp_to_day_of_month_1_based"
+ TimestampToDayOfWeek = "timestamp_to_day_of_week"
+ TimestampToHours = "timestamp_to_hours"
+ TimestampToMinutes = "timestamp_to_minutes"
+ TimestampToSeconds = "timestamp_to_seconds"
+ TimestampToMilliseconds = "timestamp_to_milliseconds"
+)
+
+// Timestamp overloads for time functions with timezones.
+const (
+ TimestampToYearWithTz = "timestamp_to_year_with_tz"
+ TimestampToMonthWithTz = "timestamp_to_month_with_tz"
+ TimestampToDayOfYearWithTz = "timestamp_to_day_of_year_with_tz"
+ TimestampToDayOfMonthZeroBasedWithTz = "timestamp_to_day_of_month_with_tz"
+ TimestampToDayOfMonthOneBasedWithTz = "timestamp_to_day_of_month_1_based_with_tz"
+ TimestampToDayOfWeekWithTz = "timestamp_to_day_of_week_with_tz"
+ TimestampToHoursWithTz = "timestamp_to_hours_with_tz"
+ TimestampToMinutesWithTz = "timestamp_to_minutes_with_tz"
+ TimestampToSecondsWithTz = "timestamp_to_seconds_tz"
+ TimestampToMillisecondsWithTz = "timestamp_to_milliseconds_with_tz"
+)
+
+// Duration overloads for time functions.
+const (
+ DurationToHours = "duration_to_hours"
+ DurationToMinutes = "duration_to_minutes"
+ DurationToSeconds = "duration_to_seconds"
+ DurationToMilliseconds = "duration_to_milliseconds"
+)
+
+// Type conversion methods and overloads
+const (
+ TypeConvertInt = "int"
+ TypeConvertUint = "uint"
+ TypeConvertDouble = "double"
+ TypeConvertBool = "bool"
+ TypeConvertString = "string"
+ TypeConvertBytes = "bytes"
+ TypeConvertTimestamp = "timestamp"
+ TypeConvertDuration = "duration"
+ TypeConvertType = "type"
+ TypeConvertDyn = "dyn"
+)
+
+// Int conversion functions.
+const (
+ IntToInt = "int64_to_int64"
+ UintToInt = "uint64_to_int64"
+ DoubleToInt = "double_to_int64"
+ StringToInt = "string_to_int64"
+ TimestampToInt = "timestamp_to_int64"
+ DurationToInt = "duration_to_int64"
+)
+
+// Uint conversion functions.
+const (
+ UintToUint = "uint64_to_uint64"
+ IntToUint = "int64_to_uint64"
+ DoubleToUint = "double_to_uint64"
+ StringToUint = "string_to_uint64"
+)
+
+// Double conversion functions.
+const (
+ DoubleToDouble = "double_to_double"
+ IntToDouble = "int64_to_double"
+ UintToDouble = "uint64_to_double"
+ StringToDouble = "string_to_double"
+)
+
+// Bool conversion functions.
+const (
+ BoolToBool = "bool_to_bool"
+ StringToBool = "string_to_bool"
+)
+
+// Bytes conversion functions.
+const (
+ BytesToBytes = "bytes_to_bytes"
+ StringToBytes = "string_to_bytes"
+)
+
+// String conversion functions.
+const (
+ StringToString = "string_to_string"
+ BoolToString = "bool_to_string"
+ IntToString = "int64_to_string"
+ UintToString = "uint64_to_string"
+ DoubleToString = "double_to_string"
+ BytesToString = "bytes_to_string"
+ TimestampToString = "timestamp_to_string"
+ DurationToString = "duration_to_string"
+)
+
+// Timestamp conversion functions
+const (
+ TimestampToTimestamp = "timestamp_to_timestamp"
+ StringToTimestamp = "string_to_timestamp"
+ IntToTimestamp = "int64_to_timestamp"
+)
+
+// Convert duration from string
+const (
+ DurationToDuration = "duration_to_duration"
+ StringToDuration = "string_to_duration"
+ IntToDuration = "int64_to_duration"
+)
+
+// Convert to dyn
+const (
+ ToDyn = "to_dyn"
+)
+
+// Comprehensions helper methods, not directly accessible via a developer.
+const (
+ Iterator = "@iterator"
+ HasNext = "@hasNext"
+ Next = "@next"
+)
+
+// IsTypeConversionFunction returns whether the input function is a standard library type
+// conversion function.
+func IsTypeConversionFunction(function string) bool {
+ switch function {
+ case TypeConvertBool,
+ TypeConvertBytes,
+ TypeConvertDouble,
+ TypeConvertDuration,
+ TypeConvertDyn,
+ TypeConvertInt,
+ TypeConvertString,
+ TypeConvertTimestamp,
+ TypeConvertType,
+ TypeConvertUint:
+ return true
+ default:
+ return false
+ }
+}
diff --git a/vendor/github.com/google/cel-go/common/runes/BUILD.bazel b/vendor/github.com/google/cel-go/common/runes/BUILD.bazel
new file mode 100644
index 0000000000..bb30242cfa
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/runes/BUILD.bazel
@@ -0,0 +1,25 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "buffer.go",
+ ],
+ importpath = "github.com/google/cel-go/common/runes",
+)
+
+go_test(
+ name = "go_default_test",
+ size = "small",
+ srcs = [
+ "buffer_test.go",
+ ],
+ embed = [
+ ":go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/common/runes/buffer.go b/vendor/github.com/google/cel-go/common/runes/buffer.go
new file mode 100644
index 0000000000..50aac0b273
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/runes/buffer.go
@@ -0,0 +1,194 @@
+// Copyright 2021 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package runes provides interfaces and utilities for working with runes.
+package runes
+
+import (
+ "strings"
+ "unicode/utf8"
+)
+
+// Buffer is an interface for accessing a contiguous array of code points.
+type Buffer interface {
+ Get(i int) rune
+ Slice(i, j int) string
+ Len() int
+}
+
+type emptyBuffer struct{}
+
+func (e *emptyBuffer) Get(i int) rune {
+ panic("slice index out of bounds")
+}
+
+func (e *emptyBuffer) Slice(i, j int) string {
+ if i != 0 || i != j {
+ panic("slice index out of bounds")
+ }
+ return ""
+}
+
+func (e *emptyBuffer) Len() int {
+ return 0
+}
+
+var _ Buffer = &emptyBuffer{}
+
+// asciiBuffer is an implementation for an array of code points that contain code points only from
+// the ASCII character set.
+type asciiBuffer struct {
+ arr []byte
+}
+
+func (a *asciiBuffer) Get(i int) rune {
+ return rune(uint32(a.arr[i]))
+}
+
+func (a *asciiBuffer) Slice(i, j int) string {
+ return string(a.arr[i:j])
+}
+
+func (a *asciiBuffer) Len() int {
+ return len(a.arr)
+}
+
+var _ Buffer = &asciiBuffer{}
+
+// basicBuffer is an implementation for an array of code points that contain code points from both
+// the Latin-1 character set and Basic Multilingual Plane.
+type basicBuffer struct {
+ arr []uint16
+}
+
+func (b *basicBuffer) Get(i int) rune {
+ return rune(uint32(b.arr[i]))
+}
+
+func (b *basicBuffer) Slice(i, j int) string {
+ var str strings.Builder
+ str.Grow((j - i) * 3) // Worst case encoding size for 0xffff is 3.
+ for ; i < j; i++ {
+ str.WriteRune(rune(uint32(b.arr[i])))
+ }
+ return str.String()
+}
+
+func (b *basicBuffer) Len() int {
+ return len(b.arr)
+}
+
+var _ Buffer = &basicBuffer{}
+
+// supplementalBuffer is an implementation for an array of code points that contain code points from
+// the Latin-1 character set, Basic Multilingual Plane, or the Supplemental Multilingual Plane.
+type supplementalBuffer struct {
+ arr []rune
+}
+
+func (s *supplementalBuffer) Get(i int) rune {
+ return rune(uint32(s.arr[i]))
+}
+
+func (s *supplementalBuffer) Slice(i, j int) string {
+ return string(s.arr[i:j])
+}
+
+func (s *supplementalBuffer) Len() int {
+ return len(s.arr)
+}
+
+var _ Buffer = &supplementalBuffer{}
+
+var nilBuffer = &emptyBuffer{}
+
+// NewBuffer returns an efficient implementation of Buffer for the given text based on the ranges of
+// the encoded code points contained within.
+//
+// Code points are represented as an array of byte, uint16, or rune. This approach ensures that
+// each index represents a code point by itself without needing to use an array of rune. At first
+// we assume all code points are less than or equal to '\u007f'. If this holds true, the
+// underlying storage is a byte array containing only ASCII characters. If we encountered a code
+// point above this range but less than or equal to '\uffff' we allocate a uint16 array, copy the
+// elements of previous byte array to the uint16 array, and continue. If this holds true, the
+// underlying storage is a uint16 array containing only Unicode characters in the Basic Multilingual
+// Plane. If we encounter a code point above '\uffff' we allocate an rune array, copy the previous
+// elements of the byte or uint16 array, and continue. The underlying storage is an rune array
+// containing any Unicode character.
+func NewBuffer(data string) Buffer {
+ if len(data) == 0 {
+ return nilBuffer
+ }
+ var (
+ idx = 0
+ buf8 = make([]byte, 0, len(data))
+ buf16 []uint16
+ buf32 []rune
+ )
+ for idx < len(data) {
+ r, s := utf8.DecodeRuneInString(data[idx:])
+ idx += s
+ if r < utf8.RuneSelf {
+ buf8 = append(buf8, byte(r))
+ continue
+ }
+ if r <= 0xffff {
+ buf16 = make([]uint16, len(buf8), len(data))
+ for i, v := range buf8 {
+ buf16[i] = uint16(v)
+ }
+ buf8 = nil
+ buf16 = append(buf16, uint16(r))
+ goto copy16
+ }
+ buf32 = make([]rune, len(buf8), len(data))
+ for i, v := range buf8 {
+ buf32[i] = rune(uint32(v))
+ }
+ buf8 = nil
+ buf32 = append(buf32, r)
+ goto copy32
+ }
+ return &asciiBuffer{
+ arr: buf8,
+ }
+copy16:
+ for idx < len(data) {
+ r, s := utf8.DecodeRuneInString(data[idx:])
+ idx += s
+ if r <= 0xffff {
+ buf16 = append(buf16, uint16(r))
+ continue
+ }
+ buf32 = make([]rune, len(buf16), len(data))
+ for i, v := range buf16 {
+ buf32[i] = rune(uint32(v))
+ }
+ buf16 = nil
+ buf32 = append(buf32, r)
+ goto copy32
+ }
+ return &basicBuffer{
+ arr: buf16,
+ }
+copy32:
+ for idx < len(data) {
+ r, s := utf8.DecodeRuneInString(data[idx:])
+ idx += s
+ buf32 = append(buf32, r)
+ }
+ return &supplementalBuffer{
+ arr: buf32,
+ }
+}
diff --git a/vendor/github.com/google/cel-go/common/source.go b/vendor/github.com/google/cel-go/common/source.go
new file mode 100644
index 0000000000..52377d9308
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/source.go
@@ -0,0 +1,186 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package common
+
+import (
+ "strings"
+ "unicode/utf8"
+
+ "github.com/google/cel-go/common/runes"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// Source interface for filter source contents.
+type Source interface {
+ // Content returns the source content represented as a string.
+ // Examples contents are the single file contents, textbox field,
+ // or url parameter.
+ Content() string
+
+ // Description gives a brief description of the source.
+ // Example descriptions are a file name or ui element.
+ Description() string
+
+ // LineOffsets gives the character offsets at which lines occur.
+ // The zero-th entry should refer to the break between the first
+ // and second line, or EOF if there is only one line of source.
+ LineOffsets() []int32
+
+ // LocationOffset translates a Location to an offset.
+ // Given the line and column of the Location returns the
+ // Location's character offset in the Source, and a bool
+ // indicating whether the Location was found.
+ LocationOffset(location Location) (int32, bool)
+
+ // OffsetLocation translates a character offset to a Location, or
+ // false if the conversion was not feasible.
+ OffsetLocation(offset int32) (Location, bool)
+
+ // NewLocation takes an input line and column and produces a Location.
+ // The default behavior is to treat the line and column as absolute,
+ // but concrete derivations may use this method to convert a relative
+ // line and column position into an absolute location.
+ NewLocation(line, col int) Location
+
+ // Snippet returns a line of content and whether the line was found.
+ Snippet(line int) (string, bool)
+}
+
+// The sourceImpl type implementation of the Source interface.
+type sourceImpl struct {
+ runes.Buffer
+ description string
+ lineOffsets []int32
+ idOffsets map[int64]int32
+}
+
+var _ runes.Buffer = &sourceImpl{}
+
+// TODO(jimlarson) "Character offsets" should index the code points
+// within the UTF-8 encoded string. It currently indexes bytes.
+// Can be accomplished by using rune[] instead of string for contents.
+
+// NewTextSource creates a new Source from the input text string.
+func NewTextSource(text string) Source {
+ return NewStringSource(text, "")
+}
+
+// NewStringSource creates a new Source from the given contents and description.
+func NewStringSource(contents string, description string) Source {
+ // Compute line offsets up front as they are referred to frequently.
+ lines := strings.Split(contents, "\n")
+ offsets := make([]int32, len(lines))
+ var offset int32
+ for i, line := range lines {
+ offset = offset + int32(utf8.RuneCountInString(line)) + 1
+ offsets[int32(i)] = offset
+ }
+ return &sourceImpl{
+ Buffer: runes.NewBuffer(contents),
+ description: description,
+ lineOffsets: offsets,
+ idOffsets: map[int64]int32{},
+ }
+}
+
+// NewInfoSource creates a new Source from a SourceInfo.
+func NewInfoSource(info *exprpb.SourceInfo) Source {
+ return &sourceImpl{
+ Buffer: runes.NewBuffer(""),
+ description: info.GetLocation(),
+ lineOffsets: info.GetLineOffsets(),
+ idOffsets: info.GetPositions(),
+ }
+}
+
+// Content implements the Source interface method.
+func (s *sourceImpl) Content() string {
+ return s.Slice(0, s.Len())
+}
+
+// Description implements the Source interface method.
+func (s *sourceImpl) Description() string {
+ return s.description
+}
+
+// LineOffsets implements the Source interface method.
+func (s *sourceImpl) LineOffsets() []int32 {
+ return s.lineOffsets
+}
+
+// LocationOffset implements the Source interface method.
+func (s *sourceImpl) LocationOffset(location Location) (int32, bool) {
+ if lineOffset, found := s.findLineOffset(location.Line()); found {
+ return lineOffset + int32(location.Column()), true
+ }
+ return -1, false
+}
+
+// NewLocation implements the Source interface method.
+func (s *sourceImpl) NewLocation(line, col int) Location {
+ return NewLocation(line, col)
+}
+
+// OffsetLocation implements the Source interface method.
+func (s *sourceImpl) OffsetLocation(offset int32) (Location, bool) {
+ line, lineOffset := s.findLine(offset)
+ return NewLocation(int(line), int(offset-lineOffset)), true
+}
+
+// Snippet implements the Source interface method.
+func (s *sourceImpl) Snippet(line int) (string, bool) {
+ charStart, found := s.findLineOffset(line)
+ if !found || s.Len() == 0 {
+ return "", false
+ }
+ charEnd, found := s.findLineOffset(line + 1)
+ if found {
+ return s.Slice(int(charStart), int(charEnd-1)), true
+ }
+ return s.Slice(int(charStart), s.Len()), true
+}
+
+// findLineOffset returns the offset where the (1-indexed) line begins,
+// or false if line doesn't exist.
+func (s *sourceImpl) findLineOffset(line int) (int32, bool) {
+ if line == 1 {
+ return 0, true
+ }
+ if line > 1 && line <= int(len(s.lineOffsets)) {
+ offset := s.lineOffsets[line-2]
+ return offset, true
+ }
+ return -1, false
+}
+
+// findLine finds the line that contains the given character offset and
+// returns the line number and offset of the beginning of that line.
+// Note that the last line is treated as if it contains all offsets
+// beyond the end of the actual source.
+func (s *sourceImpl) findLine(characterOffset int32) (int32, int32) {
+ var line int32 = 1
+ for _, lineOffset := range s.lineOffsets {
+ if lineOffset > characterOffset {
+ break
+ } else {
+ line++
+ }
+ }
+ if line == 1 {
+ return line, 0
+ }
+ return line, s.lineOffsets[line-2]
+}
diff --git a/vendor/github.com/google/cel-go/common/types/BUILD.bazel b/vendor/github.com/google/cel-go/common/types/BUILD.bazel
new file mode 100644
index 0000000000..32789f54a0
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/BUILD.bazel
@@ -0,0 +1,84 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "any_value.go",
+ "bool.go",
+ "bytes.go",
+ "double.go",
+ "duration.go",
+ "err.go",
+ "int.go",
+ "iterator.go",
+ "json_value.go",
+ "list.go",
+ "map.go",
+ "null.go",
+ "object.go",
+ "overflow.go",
+ "provider.go",
+ "string.go",
+ "timestamp.go",
+ "type.go",
+ "uint.go",
+ "unknown.go",
+ "util.go",
+ ],
+ importpath = "github.com/google/cel-go/common/types",
+ deps = [
+ "//common/overloads:go_default_library",
+ "//common/types/pb:go_default_library",
+ "//common/types/ref:go_default_library",
+ "//common/types/traits:go_default_library",
+ "@com_github_stoewer_go_strcase//:go_default_library",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//encoding/protojson:go_default_library",
+ "@org_golang_google_protobuf//proto:go_default_library",
+ "@org_golang_google_protobuf//reflect/protoreflect:go_default_library",
+ "@org_golang_google_protobuf//types/known/anypb:go_default_library",
+ "@org_golang_google_protobuf//types/known/durationpb:go_default_library",
+ "@org_golang_google_protobuf//types/known/structpb:go_default_library",
+ "@org_golang_google_protobuf//types/known/timestamppb:go_default_library",
+ "@org_golang_google_protobuf//types/known/wrapperspb:go_default_library",
+ ],
+)
+
+go_test(
+ name = "go_default_test",
+ size = "small",
+ srcs = [
+ "bool_test.go",
+ "bytes_test.go",
+ "double_test.go",
+ "duration_test.go",
+ "int_test.go",
+ "json_list_test.go",
+ "json_struct_test.go",
+ "list_test.go",
+ "map_test.go",
+ "null_test.go",
+ "object_test.go",
+ "provider_test.go",
+ "string_test.go",
+ "timestamp_test.go",
+ "type_test.go",
+ "uint_test.go",
+ ],
+ embed = [":go_default_library"],
+ deps = [
+ "//common/types/ref:go_default_library",
+ "//test:go_default_library",
+ "//test/proto3pb:test_all_types_go_proto",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//encoding/protojson:go_default_library",
+ "@org_golang_google_protobuf//types/known/anypb:go_default_library",
+ "@org_golang_google_protobuf//types/known/durationpb:go_default_library",
+ "@org_golang_google_protobuf//types/known/timestamppb:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/common/types/any_value.go b/vendor/github.com/google/cel-go/common/types/any_value.go
new file mode 100644
index 0000000000..cda0f13acf
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/any_value.go
@@ -0,0 +1,24 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "reflect"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+)
+
+// anyValueType constant representing the reflected type of google.protobuf.Any.
+var anyValueType = reflect.TypeOf(&anypb.Any{})
diff --git a/vendor/github.com/google/cel-go/common/types/bool.go b/vendor/github.com/google/cel-go/common/types/bool.go
new file mode 100644
index 0000000000..34c557b146
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/bool.go
@@ -0,0 +1,144 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+ "strconv"
+
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ wrapperspb "google.golang.org/protobuf/types/known/wrapperspb"
+)
+
+// Bool type that implements ref.Val and supports comparison and negation.
+type Bool bool
+
+var (
+ // BoolType singleton.
+ BoolType = NewTypeValue("bool",
+ traits.ComparerType,
+ traits.NegatorType)
+
+ // boolWrapperType golang reflected type for protobuf bool wrapper type.
+ boolWrapperType = reflect.TypeOf(&wrapperspb.BoolValue{})
+)
+
+// Boolean constants
+const (
+ False = Bool(false)
+ True = Bool(true)
+)
+
+// Compare implements the traits.Comparer interface method.
+func (b Bool) Compare(other ref.Val) ref.Val {
+ otherBool, ok := other.(Bool)
+ if !ok {
+ return ValOrErr(other, "no such overload")
+ }
+ if b == otherBool {
+ return IntZero
+ }
+ if !b && otherBool {
+ return IntNegOne
+ }
+ return IntOne
+}
+
+// ConvertToNative implements the ref.Val interface method.
+func (b Bool) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ switch typeDesc.Kind() {
+ case reflect.Bool:
+ return reflect.ValueOf(b).Convert(typeDesc).Interface(), nil
+ case reflect.Ptr:
+ switch typeDesc {
+ case anyValueType:
+ // Primitives must be wrapped to a wrapperspb.BoolValue before being packed into an Any.
+ return anypb.New(wrapperspb.Bool(bool(b)))
+ case boolWrapperType:
+ // Convert the bool to a wrapperspb.BoolValue.
+ return wrapperspb.Bool(bool(b)), nil
+ case jsonValueType:
+ // Return the bool as a new structpb.Value.
+ return structpb.NewBoolValue(bool(b)), nil
+ default:
+ if typeDesc.Elem().Kind() == reflect.Bool {
+ p := bool(b)
+ return &p, nil
+ }
+ }
+ case reflect.Interface:
+ bv := b.Value()
+ if reflect.TypeOf(bv).Implements(typeDesc) {
+ return bv, nil
+ }
+ if reflect.TypeOf(b).Implements(typeDesc) {
+ return b, nil
+ }
+ }
+ return nil, fmt.Errorf("type conversion error from bool to '%v'", typeDesc)
+}
+
+// ConvertToType implements the ref.Val interface method.
+func (b Bool) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case StringType:
+ return String(strconv.FormatBool(bool(b)))
+ case BoolType:
+ return b
+ case TypeType:
+ return BoolType
+ }
+ return NewErr("type conversion error from '%v' to '%v'", BoolType, typeVal)
+}
+
+// Equal implements the ref.Val interface method.
+func (b Bool) Equal(other ref.Val) ref.Val {
+ otherBool, ok := other.(Bool)
+ if !ok {
+ return ValOrErr(other, "no such overload")
+ }
+ return Bool(b == otherBool)
+}
+
+// Negate implements the traits.Negater interface method.
+func (b Bool) Negate() ref.Val {
+ return !b
+}
+
+// Type implements the ref.Val interface method.
+func (b Bool) Type() ref.Type {
+ return BoolType
+}
+
+// Value implements the ref.Val interface method.
+func (b Bool) Value() interface{} {
+ return bool(b)
+}
+
+// IsBool returns whether the input ref.Val or ref.Type is equal to BoolType.
+func IsBool(elem interface{}) bool {
+ switch elem := elem.(type) {
+ case ref.Type:
+ return elem == BoolType
+ case ref.Val:
+ return IsBool(elem.Type())
+ }
+ return false
+}
diff --git a/vendor/github.com/google/cel-go/common/types/bytes.go b/vendor/github.com/google/cel-go/common/types/bytes.go
new file mode 100644
index 0000000000..5ef367f023
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/bytes.go
@@ -0,0 +1,135 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "bytes"
+ "encoding/base64"
+ "fmt"
+ "reflect"
+ "unicode/utf8"
+
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ wrapperspb "google.golang.org/protobuf/types/known/wrapperspb"
+)
+
+// Bytes type that implements ref.Val and supports add, compare, and size
+// operations.
+type Bytes []byte
+
+var (
+ // BytesType singleton.
+ BytesType = NewTypeValue("bytes",
+ traits.AdderType,
+ traits.ComparerType,
+ traits.SizerType)
+
+ // byteWrapperType golang reflected type for protobuf bytes wrapper type.
+ byteWrapperType = reflect.TypeOf(&wrapperspb.BytesValue{})
+)
+
+// Add implements traits.Adder interface method by concatenating byte sequences.
+func (b Bytes) Add(other ref.Val) ref.Val {
+ otherBytes, ok := other.(Bytes)
+ if !ok {
+ return ValOrErr(other, "no such overload")
+ }
+ return append(b, otherBytes...)
+}
+
+// Compare implments traits.Comparer interface method by lexicographic ordering.
+func (b Bytes) Compare(other ref.Val) ref.Val {
+ otherBytes, ok := other.(Bytes)
+ if !ok {
+ return ValOrErr(other, "no such overload")
+ }
+ return Int(bytes.Compare(b, otherBytes))
+}
+
+// ConvertToNative implements the ref.Val interface method.
+func (b Bytes) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ switch typeDesc.Kind() {
+ case reflect.Array, reflect.Slice:
+ return reflect.ValueOf(b).Convert(typeDesc).Interface(), nil
+ case reflect.Ptr:
+ switch typeDesc {
+ case anyValueType:
+ // Primitives must be wrapped before being set on an Any field.
+ return anypb.New(wrapperspb.Bytes([]byte(b)))
+ case byteWrapperType:
+ // Convert the bytes to a wrapperspb.BytesValue.
+ return wrapperspb.Bytes([]byte(b)), nil
+ case jsonValueType:
+ // CEL follows the proto3 to JSON conversion by encoding bytes to a string via base64.
+ // The encoding below matches the golang 'encoding/json' behavior during marshaling,
+ // which uses base64.StdEncoding.
+ str := base64.StdEncoding.EncodeToString([]byte(b))
+ return structpb.NewStringValue(str), nil
+ }
+ case reflect.Interface:
+ bv := b.Value()
+ if reflect.TypeOf(bv).Implements(typeDesc) {
+ return bv, nil
+ }
+ if reflect.TypeOf(b).Implements(typeDesc) {
+ return b, nil
+ }
+ }
+ return nil, fmt.Errorf("type conversion error from Bytes to '%v'", typeDesc)
+}
+
+// ConvertToType implements the ref.Val interface method.
+func (b Bytes) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case StringType:
+ if !utf8.Valid(b) {
+ return NewErr("invalid UTF-8 in bytes, cannot convert to string")
+ }
+ return String(b)
+ case BytesType:
+ return b
+ case TypeType:
+ return BytesType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", BytesType, typeVal)
+}
+
+// Equal implements the ref.Val interface method.
+func (b Bytes) Equal(other ref.Val) ref.Val {
+ otherBytes, ok := other.(Bytes)
+ if !ok {
+ return ValOrErr(other, "no such overload")
+ }
+ return Bool(bytes.Equal(b, otherBytes))
+}
+
+// Size implements the traits.Sizer interface method.
+func (b Bytes) Size() ref.Val {
+ return Int(len(b))
+}
+
+// Type implements the ref.Val interface method.
+func (b Bytes) Type() ref.Type {
+ return BytesType
+}
+
+// Value implements the ref.Val interface method.
+func (b Bytes) Value() interface{} {
+ return []byte(b)
+}
diff --git a/vendor/github.com/google/cel-go/common/types/doc.go b/vendor/github.com/google/cel-go/common/types/doc.go
new file mode 100644
index 0000000000..5f641d7043
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/doc.go
@@ -0,0 +1,17 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package types contains the types, traits, and utilities common to all
+// components of expression handling.
+package types
diff --git a/vendor/github.com/google/cel-go/common/types/double.go b/vendor/github.com/google/cel-go/common/types/double.go
new file mode 100644
index 0000000000..2a67913762
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/double.go
@@ -0,0 +1,200 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ wrapperspb "google.golang.org/protobuf/types/known/wrapperspb"
+)
+
+// Double type that implements ref.Val, comparison, and mathematical
+// operations.
+type Double float64
+
+var (
+ // DoubleType singleton.
+ DoubleType = NewTypeValue("double",
+ traits.AdderType,
+ traits.ComparerType,
+ traits.DividerType,
+ traits.MultiplierType,
+ traits.NegatorType,
+ traits.SubtractorType)
+
+ // doubleWrapperType reflected type for protobuf double wrapper type.
+ doubleWrapperType = reflect.TypeOf(&wrapperspb.DoubleValue{})
+
+ // floatWrapperType reflected type for protobuf float wrapper type.
+ floatWrapperType = reflect.TypeOf(&wrapperspb.FloatValue{})
+)
+
+// Add implements traits.Adder.Add.
+func (d Double) Add(other ref.Val) ref.Val {
+ otherDouble, ok := other.(Double)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return d + otherDouble
+}
+
+// Compare implements traits.Comparer.Compare.
+func (d Double) Compare(other ref.Val) ref.Val {
+ otherDouble, ok := other.(Double)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if d < otherDouble {
+ return IntNegOne
+ }
+ if d > otherDouble {
+ return IntOne
+ }
+ return IntZero
+}
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (d Double) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ switch typeDesc.Kind() {
+ case reflect.Float32:
+ v := float32(d)
+ return reflect.ValueOf(v).Convert(typeDesc).Interface(), nil
+ case reflect.Float64:
+ v := float64(d)
+ return reflect.ValueOf(v).Convert(typeDesc).Interface(), nil
+ case reflect.Ptr:
+ switch typeDesc {
+ case anyValueType:
+ // Primitives must be wrapped before being set on an Any field.
+ return anypb.New(wrapperspb.Double(float64(d)))
+ case doubleWrapperType:
+ // Convert to a wrapperspb.DoubleValue
+ return wrapperspb.Double(float64(d)), nil
+ case floatWrapperType:
+ // Convert to a wrapperspb.FloatValue (with truncation).
+ return wrapperspb.Float(float32(d)), nil
+ case jsonValueType:
+ // Note, there are special cases for proto3 to json conversion that
+ // expect the floating point value to be converted to a NaN,
+ // Infinity, or -Infinity string values, but the jsonpb string
+ // marshaling of the protobuf.Value will handle this conversion.
+ return structpb.NewNumberValue(float64(d)), nil
+ }
+ switch typeDesc.Elem().Kind() {
+ case reflect.Float32:
+ v := float32(d)
+ p := reflect.New(typeDesc.Elem())
+ p.Elem().Set(reflect.ValueOf(v).Convert(typeDesc.Elem()))
+ return p.Interface(), nil
+ case reflect.Float64:
+ v := float64(d)
+ p := reflect.New(typeDesc.Elem())
+ p.Elem().Set(reflect.ValueOf(v).Convert(typeDesc.Elem()))
+ return p.Interface(), nil
+ }
+ case reflect.Interface:
+ dv := d.Value()
+ if reflect.TypeOf(dv).Implements(typeDesc) {
+ return dv, nil
+ }
+ if reflect.TypeOf(d).Implements(typeDesc) {
+ return d, nil
+ }
+ }
+ return nil, fmt.Errorf("type conversion error from Double to '%v'", typeDesc)
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (d Double) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case IntType:
+ i, err := doubleToInt64Checked(float64(d))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Int(i)
+ case UintType:
+ i, err := doubleToUint64Checked(float64(d))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Uint(i)
+ case DoubleType:
+ return d
+ case StringType:
+ return String(fmt.Sprintf("%g", float64(d)))
+ case TypeType:
+ return DoubleType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", DoubleType, typeVal)
+}
+
+// Divide implements traits.Divider.Divide.
+func (d Double) Divide(other ref.Val) ref.Val {
+ otherDouble, ok := other.(Double)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return d / otherDouble
+}
+
+// Equal implements ref.Val.Equal.
+func (d Double) Equal(other ref.Val) ref.Val {
+ otherDouble, ok := other.(Double)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ // TODO: Handle NaNs properly.
+ return Bool(d == otherDouble)
+}
+
+// Multiply implements traits.Multiplier.Multiply.
+func (d Double) Multiply(other ref.Val) ref.Val {
+ otherDouble, ok := other.(Double)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return d * otherDouble
+}
+
+// Negate implements traits.Negater.Negate.
+func (d Double) Negate() ref.Val {
+ return -d
+}
+
+// Subtract implements traits.Subtractor.Subtract.
+func (d Double) Subtract(subtrahend ref.Val) ref.Val {
+ subtraDouble, ok := subtrahend.(Double)
+ if !ok {
+ return MaybeNoSuchOverloadErr(subtrahend)
+ }
+ return d - subtraDouble
+}
+
+// Type implements ref.Val.Type.
+func (d Double) Type() ref.Type {
+ return DoubleType
+}
+
+// Value implements ref.Val.Value.
+func (d Double) Value() interface{} {
+ return float64(d)
+}
diff --git a/vendor/github.com/google/cel-go/common/types/duration.go b/vendor/github.com/google/cel-go/common/types/duration.go
new file mode 100644
index 0000000000..23409b75e3
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/duration.go
@@ -0,0 +1,202 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+ "strconv"
+ "time"
+
+ "github.com/google/cel-go/common/overloads"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ dpb "google.golang.org/protobuf/types/known/durationpb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+// Duration type that implements ref.Val and supports add, compare, negate,
+// and subtract operators. This type is also a receiver which means it can
+// participate in dispatch to receiver functions.
+type Duration struct {
+ time.Duration
+}
+
+func durationOf(d time.Duration) Duration {
+ return Duration{Duration: d}
+}
+
+var (
+ // DurationType singleton.
+ DurationType = NewTypeValue("google.protobuf.Duration",
+ traits.AdderType,
+ traits.ComparerType,
+ traits.NegatorType,
+ traits.ReceiverType,
+ traits.SubtractorType)
+)
+
+// Add implements traits.Adder.Add.
+func (d Duration) Add(other ref.Val) ref.Val {
+ switch other.Type() {
+ case DurationType:
+ dur2 := other.(Duration)
+ val, err := addDurationChecked(d.Duration, dur2.Duration)
+ if err != nil {
+ return wrapErr(err)
+ }
+ return durationOf(val)
+ case TimestampType:
+ ts := other.(Timestamp).Time
+ val, err := addTimeDurationChecked(ts, d.Duration)
+ if err != nil {
+ return wrapErr(err)
+ }
+ return timestampOf(val)
+ }
+ return MaybeNoSuchOverloadErr(other)
+}
+
+// Compare implements traits.Comparer.Compare.
+func (d Duration) Compare(other ref.Val) ref.Val {
+ otherDur, ok := other.(Duration)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ d1 := d.Duration
+ d2 := otherDur.Duration
+ switch {
+ case d1 < d2:
+ return IntNegOne
+ case d1 > d2:
+ return IntOne
+ default:
+ return IntZero
+ }
+}
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (d Duration) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ // If the duration is already assignable to the desired type return it.
+ if reflect.TypeOf(d.Duration).AssignableTo(typeDesc) {
+ return d.Duration, nil
+ }
+ if reflect.TypeOf(d).AssignableTo(typeDesc) {
+ return d, nil
+ }
+ switch typeDesc {
+ case anyValueType:
+ // Pack the duration as a dpb.Duration into an Any value.
+ return anypb.New(dpb.New(d.Duration))
+ case durationValueType:
+ // Unwrap the CEL value to its underlying proto value.
+ return dpb.New(d.Duration), nil
+ case jsonValueType:
+ // CEL follows the proto3 to JSON conversion.
+ // Note, using jsonpb would wrap the result in extra double quotes.
+ v := d.ConvertToType(StringType)
+ if IsError(v) {
+ return nil, v.(*Err)
+ }
+ return structpb.NewStringValue(string(v.(String))), nil
+ }
+ return nil, fmt.Errorf("type conversion error from 'Duration' to '%v'", typeDesc)
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (d Duration) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case StringType:
+ return String(strconv.FormatFloat(d.Seconds(), 'f', -1, 64) + "s")
+ case IntType:
+ return Int(d.Duration)
+ case DurationType:
+ return d
+ case TypeType:
+ return DurationType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", DurationType, typeVal)
+}
+
+// Equal implements ref.Val.Equal.
+func (d Duration) Equal(other ref.Val) ref.Val {
+ otherDur, ok := other.(Duration)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return Bool(d.Duration == otherDur.Duration)
+}
+
+// Negate implements traits.Negater.Negate.
+func (d Duration) Negate() ref.Val {
+ val, err := negateDurationChecked(d.Duration)
+ if err != nil {
+ return wrapErr(err)
+ }
+ return durationOf(val)
+}
+
+// Receive implements traits.Receiver.Receive.
+func (d Duration) Receive(function string, overload string, args []ref.Val) ref.Val {
+ if len(args) == 0 {
+ if f, found := durationZeroArgOverloads[function]; found {
+ return f(d.Duration)
+ }
+ }
+ return NoSuchOverloadErr()
+}
+
+// Subtract implements traits.Subtractor.Subtract.
+func (d Duration) Subtract(subtrahend ref.Val) ref.Val {
+ subtraDur, ok := subtrahend.(Duration)
+ if !ok {
+ return MaybeNoSuchOverloadErr(subtrahend)
+ }
+ val, err := subtractDurationChecked(d.Duration, subtraDur.Duration)
+ if err != nil {
+ return wrapErr(err)
+ }
+ return durationOf(val)
+}
+
+// Type implements ref.Val.Type.
+func (d Duration) Type() ref.Type {
+ return DurationType
+}
+
+// Value implements ref.Val.Value.
+func (d Duration) Value() interface{} {
+ return d.Duration
+}
+
+var (
+ durationValueType = reflect.TypeOf(&dpb.Duration{})
+
+ durationZeroArgOverloads = map[string]func(time.Duration) ref.Val{
+ overloads.TimeGetHours: func(dur time.Duration) ref.Val {
+ return Int(dur.Hours())
+ },
+ overloads.TimeGetMinutes: func(dur time.Duration) ref.Val {
+ return Int(dur.Minutes())
+ },
+ overloads.TimeGetSeconds: func(dur time.Duration) ref.Val {
+ return Int(dur.Seconds())
+ },
+ overloads.TimeGetMilliseconds: func(dur time.Duration) ref.Val {
+ return Int(dur.Milliseconds())
+ }}
+)
diff --git a/vendor/github.com/google/cel-go/common/types/err.go b/vendor/github.com/google/cel-go/common/types/err.go
new file mode 100644
index 0000000000..1ae247f41c
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/err.go
@@ -0,0 +1,130 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "errors"
+ "fmt"
+ "reflect"
+
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// Err type which extends the built-in go error and implements ref.Val.
+type Err struct {
+ error
+}
+
+var (
+ // ErrType singleton.
+ ErrType = NewTypeValue("error")
+
+ // errDivideByZero is an error indicating a division by zero of an integer value.
+ errDivideByZero = errors.New("division by zero")
+ // errModulusByZero is an error indicating a modulus by zero of an integer value.
+ errModulusByZero = errors.New("modulus by zero")
+ // errIntOverflow is an error representing integer overflow.
+ errIntOverflow = errors.New("integer overflow")
+ // errUintOverflow is an error representing unsigned integer overflow.
+ errUintOverflow = errors.New("unsigned integer overflow")
+ // errDurationOverflow is an error representing duration overflow.
+ errDurationOverflow = errors.New("duration overflow")
+ // errTimestampOverflow is an error representing timestamp overflow.
+ errTimestampOverflow = errors.New("timestamp overflow")
+ celErrTimestampOverflow = &Err{error: errTimestampOverflow}
+
+ // celErrNoSuchOverload indicates that the call arguments did not match a supported method signature.
+ celErrNoSuchOverload = NewErr("no such overload")
+)
+
+// NewErr creates a new Err described by the format string and args.
+// TODO: Audit the use of this function and standardize the error messages and codes.
+func NewErr(format string, args ...interface{}) ref.Val {
+ return &Err{fmt.Errorf(format, args...)}
+}
+
+// NoSuchOverloadErr returns a new types.Err instance with a no such overload message.
+func NoSuchOverloadErr() ref.Val {
+ return celErrNoSuchOverload
+}
+
+// UnsupportedRefValConversionErr returns a types.NewErr instance with a no such conversion
+// message that indicates that the native value could not be converted to a CEL ref.Val.
+func UnsupportedRefValConversionErr(val interface{}) ref.Val {
+ return NewErr("unsupported conversion to ref.Val: (%T)%v", val, val)
+}
+
+// MaybeNoSuchOverloadErr returns the error or unknown if the input ref.Val is one of these types,
+// else a new no such overload error.
+func MaybeNoSuchOverloadErr(val ref.Val) ref.Val {
+ return ValOrErr(val, "no such overload")
+}
+
+// ValOrErr either returns the existing error or create a new one.
+// TODO: Audit the use of this function and standardize the error messages and codes.
+func ValOrErr(val ref.Val, format string, args ...interface{}) ref.Val {
+ if val == nil {
+ return NewErr(format, args...)
+ }
+ switch val.Type() {
+ case ErrType, UnknownType:
+ return val
+ default:
+ return NewErr(format, args...)
+ }
+}
+
+// wrapErr wraps an existing Go error value into a CEL Err value.
+func wrapErr(err error) ref.Val {
+ return &Err{error: err}
+}
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (e *Err) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ return nil, e.error
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (e *Err) ConvertToType(typeVal ref.Type) ref.Val {
+ // Errors are not convertible to other representations.
+ return e
+}
+
+// Equal implements ref.Val.Equal.
+func (e *Err) Equal(other ref.Val) ref.Val {
+ // An error cannot be equal to any other value, so it returns itself.
+ return e
+}
+
+// String implements fmt.Stringer.
+func (e *Err) String() string {
+ return e.error.Error()
+}
+
+// Type implements ref.Val.Type.
+func (e *Err) Type() ref.Type {
+ return ErrType
+}
+
+// Value implements ref.Val.Value.
+func (e *Err) Value() interface{} {
+ return e.error
+}
+
+// IsError returns whether the input element ref.Type or ref.Val is equal to
+// the ErrType singleton.
+func IsError(val ref.Val) bool {
+ return val.Type() == ErrType
+}
diff --git a/vendor/github.com/google/cel-go/common/types/int.go b/vendor/github.com/google/cel-go/common/types/int.go
new file mode 100644
index 0000000000..1b45c6425f
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/int.go
@@ -0,0 +1,286 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+ "strconv"
+ "time"
+
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ wrapperspb "google.golang.org/protobuf/types/known/wrapperspb"
+)
+
+// Int type that implements ref.Val as well as comparison and math operators.
+type Int int64
+
+// Int constants used for comparison results.
+const (
+ // IntZero is the zero-value for Int
+ IntZero = Int(0)
+ IntOne = Int(1)
+ IntNegOne = Int(-1)
+)
+
+var (
+ // IntType singleton.
+ IntType = NewTypeValue("int",
+ traits.AdderType,
+ traits.ComparerType,
+ traits.DividerType,
+ traits.ModderType,
+ traits.MultiplierType,
+ traits.NegatorType,
+ traits.SubtractorType)
+
+ // int32WrapperType reflected type for protobuf int32 wrapper type.
+ int32WrapperType = reflect.TypeOf(&wrapperspb.Int32Value{})
+
+ // int64WrapperType reflected type for protobuf int64 wrapper type.
+ int64WrapperType = reflect.TypeOf(&wrapperspb.Int64Value{})
+)
+
+// Add implements traits.Adder.Add.
+func (i Int) Add(other ref.Val) ref.Val {
+ otherInt, ok := other.(Int)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ val, err := addInt64Checked(int64(i), int64(otherInt))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Int(val)
+}
+
+// Compare implements traits.Comparer.Compare.
+func (i Int) Compare(other ref.Val) ref.Val {
+ otherInt, ok := other.(Int)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if i < otherInt {
+ return IntNegOne
+ }
+ if i > otherInt {
+ return IntOne
+ }
+ return IntZero
+}
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (i Int) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ switch typeDesc.Kind() {
+ case reflect.Int, reflect.Int32:
+ // Enums are also mapped as int32 derivations.
+ // Note, the code doesn't convert to the enum value directly since this is not known, but
+ // the net effect with respect to proto-assignment is handled correctly by the reflection
+ // Convert method.
+ v, err := int64ToInt32Checked(int64(i))
+ if err != nil {
+ return nil, err
+ }
+ return reflect.ValueOf(v).Convert(typeDesc).Interface(), nil
+ case reflect.Int64:
+ return reflect.ValueOf(i).Convert(typeDesc).Interface(), nil
+ case reflect.Ptr:
+ switch typeDesc {
+ case anyValueType:
+ // Primitives must be wrapped before being set on an Any field.
+ return anypb.New(wrapperspb.Int64(int64(i)))
+ case int32WrapperType:
+ // Convert the value to a wrapperspb.Int32Value, error on overflow.
+ v, err := int64ToInt32Checked(int64(i))
+ if err != nil {
+ return nil, err
+ }
+ return wrapperspb.Int32(v), nil
+ case int64WrapperType:
+ // Convert the value to a wrapperspb.Int64Value.
+ return wrapperspb.Int64(int64(i)), nil
+ case jsonValueType:
+ // The proto-to-JSON conversion rules would convert all 64-bit integer values to JSON
+ // decimal strings. Because CEL ints might come from the automatic widening of 32-bit
+ // values in protos, the JSON type is chosen dynamically based on the value.
+ //
+ // - Integers -2^53-1 < n < 2^53-1 are encoded as JSON numbers.
+ // - Integers outside this range are encoded as JSON strings.
+ //
+ // The integer to float range represents the largest interval where such a conversion
+ // can round-trip accurately. Thus, conversions from a 32-bit source can expect a JSON
+ // number as with protobuf. Those consuming JSON from a 64-bit source must be able to
+ // handle either a JSON number or a JSON decimal string. To handle these cases safely
+ // the string values must be explicitly converted to int() within a CEL expression;
+ // however, it is best to simply stay within the JSON number range when building JSON
+ // objects in CEL.
+ if i.isJSONSafe() {
+ return structpb.NewNumberValue(float64(i)), nil
+ }
+ // Proto3 to JSON conversion requires string-formatted int64 values
+ // since the conversion to floating point would result in truncation.
+ return structpb.NewStringValue(strconv.FormatInt(int64(i), 10)), nil
+ }
+ switch typeDesc.Elem().Kind() {
+ case reflect.Int32:
+ // Convert the value to a wrapperspb.Int32Value, error on overflow.
+ v, err := int64ToInt32Checked(int64(i))
+ if err != nil {
+ return nil, err
+ }
+ p := reflect.New(typeDesc.Elem())
+ p.Elem().Set(reflect.ValueOf(v).Convert(typeDesc.Elem()))
+ return p.Interface(), nil
+ case reflect.Int64:
+ v := int64(i)
+ p := reflect.New(typeDesc.Elem())
+ p.Elem().Set(reflect.ValueOf(v).Convert(typeDesc.Elem()))
+ return p.Interface(), nil
+ }
+ case reflect.Interface:
+ iv := i.Value()
+ if reflect.TypeOf(iv).Implements(typeDesc) {
+ return iv, nil
+ }
+ if reflect.TypeOf(i).Implements(typeDesc) {
+ return i, nil
+ }
+ }
+ return nil, fmt.Errorf("unsupported type conversion from 'int' to %v", typeDesc)
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (i Int) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case IntType:
+ return i
+ case UintType:
+ u, err := int64ToUint64Checked(int64(i))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Uint(u)
+ case DoubleType:
+ return Double(i)
+ case StringType:
+ return String(fmt.Sprintf("%d", int64(i)))
+ case TimestampType:
+ // The maximum positive value that can be passed to time.Unix is math.MaxInt64 minus the number
+ // of seconds between year 1 and year 1970. See comments on unixToInternal.
+ if int64(i) < minUnixTime || int64(i) > maxUnixTime {
+ return celErrTimestampOverflow
+ }
+ return timestampOf(time.Unix(int64(i), 0).UTC())
+ case TypeType:
+ return IntType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", IntType, typeVal)
+}
+
+// Divide implements traits.Divider.Divide.
+func (i Int) Divide(other ref.Val) ref.Val {
+ otherInt, ok := other.(Int)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ val, err := divideInt64Checked(int64(i), int64(otherInt))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Int(val)
+}
+
+// Equal implements ref.Val.Equal.
+func (i Int) Equal(other ref.Val) ref.Val {
+ otherInt, ok := other.(Int)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return Bool(i == otherInt)
+}
+
+// Modulo implements traits.Modder.Modulo.
+func (i Int) Modulo(other ref.Val) ref.Val {
+ otherInt, ok := other.(Int)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ val, err := moduloInt64Checked(int64(i), int64(otherInt))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Int(val)
+}
+
+// Multiply implements traits.Multiplier.Multiply.
+func (i Int) Multiply(other ref.Val) ref.Val {
+ otherInt, ok := other.(Int)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ val, err := multiplyInt64Checked(int64(i), int64(otherInt))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Int(val)
+}
+
+// Negate implements traits.Negater.Negate.
+func (i Int) Negate() ref.Val {
+ val, err := negateInt64Checked(int64(i))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Int(val)
+}
+
+// Subtract implements traits.Subtractor.Subtract.
+func (i Int) Subtract(subtrahend ref.Val) ref.Val {
+ subtraInt, ok := subtrahend.(Int)
+ if !ok {
+ return MaybeNoSuchOverloadErr(subtrahend)
+ }
+ val, err := subtractInt64Checked(int64(i), int64(subtraInt))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Int(val)
+}
+
+// Type implements ref.Val.Type.
+func (i Int) Type() ref.Type {
+ return IntType
+}
+
+// Value implements ref.Val.Value.
+func (i Int) Value() interface{} {
+ return int64(i)
+}
+
+// isJSONSafe indicates whether the int is safely representable as a floating point value in JSON.
+func (i Int) isJSONSafe() bool {
+ return i >= minIntJSON && i <= maxIntJSON
+}
+
+const (
+ // maxIntJSON is defined as the Number.MAX_SAFE_INTEGER value per EcmaScript 6.
+ maxIntJSON = 1<<53 - 1
+ // minIntJSON is defined as the Number.MIN_SAFE_INTEGER value per EcmaScript 6.
+ minIntJSON = -maxIntJSON
+)
diff --git a/vendor/github.com/google/cel-go/common/types/iterator.go b/vendor/github.com/google/cel-go/common/types/iterator.go
new file mode 100644
index 0000000000..4906627783
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/iterator.go
@@ -0,0 +1,55 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+)
+
+var (
+ // IteratorType singleton.
+ IteratorType = NewTypeValue("iterator", traits.IteratorType)
+)
+
+// baseIterator is the basis for list, map, and object iterators.
+//
+// An iterator in and of itself should not be a valid value for comparison, but must implement the
+// `ref.Val` methods in order to be well-supported within instruction arguments processed by the
+// interpreter.
+type baseIterator struct{}
+
+func (*baseIterator) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ return nil, fmt.Errorf("type conversion on iterators not supported")
+}
+
+func (*baseIterator) ConvertToType(typeVal ref.Type) ref.Val {
+ return NewErr("no such overload")
+}
+
+func (*baseIterator) Equal(other ref.Val) ref.Val {
+ return NewErr("no such overload")
+}
+
+func (*baseIterator) Type() ref.Type {
+ return IteratorType
+}
+
+func (*baseIterator) Value() interface{} {
+ return nil
+}
diff --git a/vendor/github.com/google/cel-go/common/types/json_value.go b/vendor/github.com/google/cel-go/common/types/json_value.go
new file mode 100644
index 0000000000..cd63b51944
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/json_value.go
@@ -0,0 +1,28 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "reflect"
+
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+// JSON type constants representing the reflected types of protobuf JSON values.
+var (
+ jsonValueType = reflect.TypeOf(&structpb.Value{})
+ jsonListValueType = reflect.TypeOf(&structpb.ListValue{})
+ jsonStructType = reflect.TypeOf(&structpb.Struct{})
+)
diff --git a/vendor/github.com/google/cel-go/common/types/list.go b/vendor/github.com/google/cel-go/common/types/list.go
new file mode 100644
index 0000000000..51c5d21e2c
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/list.go
@@ -0,0 +1,447 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+ "google.golang.org/protobuf/proto"
+ "google.golang.org/protobuf/reflect/protoreflect"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+var (
+ // ListType singleton.
+ ListType = NewTypeValue("list",
+ traits.AdderType,
+ traits.ContainerType,
+ traits.IndexerType,
+ traits.IterableType,
+ traits.SizerType)
+)
+
+// NewDynamicList returns a traits.Lister with heterogenous elements.
+// value should be an array of "native" types, i.e. any type that
+// NativeToValue() can convert to a ref.Val.
+func NewDynamicList(adapter ref.TypeAdapter, value interface{}) traits.Lister {
+ refValue := reflect.ValueOf(value)
+ return &baseList{
+ TypeAdapter: adapter,
+ value: value,
+ size: refValue.Len(),
+ get: func(i int) interface{} {
+ return refValue.Index(i).Interface()
+ },
+ }
+}
+
+// NewStringList returns a traits.Lister containing only strings.
+func NewStringList(adapter ref.TypeAdapter, elems []string) traits.Lister {
+ return &baseList{
+ TypeAdapter: adapter,
+ value: elems,
+ size: len(elems),
+ get: func(i int) interface{} { return elems[i] },
+ }
+}
+
+// NewRefValList returns a traits.Lister with ref.Val elements.
+//
+// This type specialization is used with list literals within CEL expressions.
+func NewRefValList(adapter ref.TypeAdapter, elems []ref.Val) traits.Lister {
+ return &baseList{
+ TypeAdapter: adapter,
+ value: elems,
+ size: len(elems),
+ get: func(i int) interface{} { return elems[i] },
+ }
+}
+
+// NewProtoList returns a traits.Lister based on a pb.List instance.
+func NewProtoList(adapter ref.TypeAdapter, list protoreflect.List) traits.Lister {
+ return &baseList{
+ TypeAdapter: adapter,
+ value: list,
+ size: list.Len(),
+ get: func(i int) interface{} { return list.Get(i).Interface() },
+ }
+}
+
+// NewJSONList returns a traits.Lister based on structpb.ListValue instance.
+func NewJSONList(adapter ref.TypeAdapter, l *structpb.ListValue) traits.Lister {
+ vals := l.GetValues()
+ return &baseList{
+ TypeAdapter: adapter,
+ value: l,
+ size: len(vals),
+ get: func(i int) interface{} { return vals[i] },
+ }
+}
+
+// baseList points to a list containing elements of any type.
+// The `value` is an array of native values, and refValue is its reflection object.
+// The `ref.TypeAdapter` enables native type to CEL type conversions.
+type baseList struct {
+ ref.TypeAdapter
+ value interface{}
+
+ // size indicates the number of elements within the list.
+ // Since objects are immutable the size of a list is static.
+ size int
+
+ // get returns a value at the specified integer index.
+ // The index is guaranteed to be checked against the list index range.
+ get func(int) interface{}
+}
+
+// Add implements the traits.Adder interface method.
+func (l *baseList) Add(other ref.Val) ref.Val {
+ otherList, ok := other.(traits.Lister)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if l.Size() == IntZero {
+ return other
+ }
+ if otherList.Size() == IntZero {
+ return l
+ }
+ return &concatList{
+ TypeAdapter: l.TypeAdapter,
+ prevList: l,
+ nextList: otherList}
+}
+
+// Contains implements the traits.Container interface method.
+func (l *baseList) Contains(elem ref.Val) ref.Val {
+ if IsUnknownOrError(elem) {
+ return elem
+ }
+ var err ref.Val
+ for i := 0; i < l.size; i++ {
+ val := l.NativeToValue(l.get(i))
+ cmp := elem.Equal(val)
+ b, ok := cmp.(Bool)
+ // When there is an error on the contain check, this is not necessarily terminal.
+ // The contains call could find the element and return True, just as though the user
+ // had written a per-element comparison in an exists() macro or logical ||, e.g.
+ // list.exists(e, e == elem)
+ if !ok && err == nil {
+ err = ValOrErr(cmp, "no such overload")
+ }
+ if b == True {
+ return True
+ }
+ }
+ if err != nil {
+ return err
+ }
+ return False
+}
+
+// ConvertToNative implements the ref.Val interface method.
+func (l *baseList) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ // If the underlying list value is assignable to the reflected type return it.
+ if reflect.TypeOf(l.value).AssignableTo(typeDesc) {
+ return l.value, nil
+ }
+ // If the list wrapper is assignable to the desired type return it.
+ if reflect.TypeOf(l).AssignableTo(typeDesc) {
+ return l, nil
+ }
+ // Attempt to convert the list to a set of well known protobuf types.
+ switch typeDesc {
+ case anyValueType:
+ json, err := l.ConvertToNative(jsonListValueType)
+ if err != nil {
+ return nil, err
+ }
+ return anypb.New(json.(proto.Message))
+ case jsonValueType, jsonListValueType:
+ jsonValues, err :=
+ l.ConvertToNative(reflect.TypeOf([]*structpb.Value{}))
+ if err != nil {
+ return nil, err
+ }
+ jsonList := &structpb.ListValue{Values: jsonValues.([]*structpb.Value)}
+ if typeDesc == jsonListValueType {
+ return jsonList, nil
+ }
+ return structpb.NewListValue(jsonList), nil
+ }
+ // Non-list conversion.
+ if typeDesc.Kind() != reflect.Slice && typeDesc.Kind() != reflect.Array {
+ return nil, fmt.Errorf("type conversion error from list to '%v'", typeDesc)
+ }
+
+ // List conversion.
+ // Allow the element ConvertToNative() function to determine whether conversion is possible.
+ otherElemType := typeDesc.Elem()
+ elemCount := l.size
+ nativeList := reflect.MakeSlice(typeDesc, elemCount, elemCount)
+ for i := 0; i < elemCount; i++ {
+ elem := l.NativeToValue(l.get(i))
+ nativeElemVal, err := elem.ConvertToNative(otherElemType)
+ if err != nil {
+ return nil, err
+ }
+ nativeList.Index(i).Set(reflect.ValueOf(nativeElemVal))
+ }
+ return nativeList.Interface(), nil
+}
+
+// ConvertToType implements the ref.Val interface method.
+func (l *baseList) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case ListType:
+ return l
+ case TypeType:
+ return ListType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", ListType, typeVal)
+}
+
+// Equal implements the ref.Val interface method.
+func (l *baseList) Equal(other ref.Val) ref.Val {
+ otherList, ok := other.(traits.Lister)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if l.Size() != otherList.Size() {
+ return False
+ }
+ var maybeErr ref.Val
+ for i := IntZero; i < l.Size().(Int); i++ {
+ thisElem := l.Get(i)
+ otherElem := otherList.Get(i)
+ elemEq := thisElem.Equal(otherElem)
+ if elemEq == False {
+ return False
+ }
+ if maybeErr == nil && IsUnknownOrError(elemEq) {
+ maybeErr = elemEq
+ }
+ }
+ if maybeErr != nil {
+ return maybeErr
+ }
+ return True
+}
+
+// Get implements the traits.Indexer interface method.
+func (l *baseList) Get(index ref.Val) ref.Val {
+ i, ok := index.(Int)
+ if !ok {
+ return ValOrErr(index, "unsupported index type '%s' in list", index.Type())
+ }
+ iv := int(i)
+ if iv < 0 || iv >= l.size {
+ return NewErr("index '%d' out of range in list size '%d'", i, l.Size())
+ }
+ elem := l.get(iv)
+ return l.NativeToValue(elem)
+}
+
+// Iterator implements the traits.Iterable interface method.
+func (l *baseList) Iterator() traits.Iterator {
+ return newListIterator(l)
+}
+
+// Size implements the traits.Sizer interface method.
+func (l *baseList) Size() ref.Val {
+ return Int(l.size)
+}
+
+// Type implements the ref.Val interface method.
+func (l *baseList) Type() ref.Type {
+ return ListType
+}
+
+// Value implements the ref.Val interface method.
+func (l *baseList) Value() interface{} {
+ return l.value
+}
+
+// concatList combines two list implementations together into a view.
+// The `ref.TypeAdapter` enables native type to CEL type conversions.
+type concatList struct {
+ ref.TypeAdapter
+ value interface{}
+ prevList traits.Lister
+ nextList traits.Lister
+}
+
+// Add implements the traits.Adder interface method.
+func (l *concatList) Add(other ref.Val) ref.Val {
+ otherList, ok := other.(traits.Lister)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if l.Size() == IntZero {
+ return other
+ }
+ if otherList.Size() == IntZero {
+ return l
+ }
+ return &concatList{
+ TypeAdapter: l.TypeAdapter,
+ prevList: l,
+ nextList: otherList}
+}
+
+// Contains implments the traits.Container interface method.
+func (l *concatList) Contains(elem ref.Val) ref.Val {
+ // The concat list relies on the IsErrorOrUnknown checks against the input element to be
+ // performed by the `prevList` and/or `nextList`.
+ prev := l.prevList.Contains(elem)
+ // Short-circuit the return if the elem was found in the prev list.
+ if prev == True {
+ return prev
+ }
+ // Return if the elem was found in the next list.
+ next := l.nextList.Contains(elem)
+ if next == True {
+ return next
+ }
+ // Handle the case where an error or unknown was encountered before checking next.
+ if IsUnknownOrError(prev) {
+ return prev
+ }
+ // Otherwise, rely on the next value as the representative result.
+ return next
+}
+
+// ConvertToNative implements the ref.Val interface method.
+func (l *concatList) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ combined := NewDynamicList(l.TypeAdapter, l.Value().([]interface{}))
+ return combined.ConvertToNative(typeDesc)
+}
+
+// ConvertToType implements the ref.Val interface method.
+func (l *concatList) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case ListType:
+ return l
+ case TypeType:
+ return ListType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", ListType, typeVal)
+}
+
+// Equal implements the ref.Val interface method.
+func (l *concatList) Equal(other ref.Val) ref.Val {
+ otherList, ok := other.(traits.Lister)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if l.Size() != otherList.Size() {
+ return False
+ }
+ var maybeErr ref.Val
+ for i := IntZero; i < l.Size().(Int); i++ {
+ thisElem := l.Get(i)
+ otherElem := otherList.Get(i)
+ elemEq := thisElem.Equal(otherElem)
+ if elemEq == False {
+ return False
+ }
+ if maybeErr == nil && IsUnknownOrError(elemEq) {
+ maybeErr = elemEq
+ }
+ }
+ if maybeErr != nil {
+ return maybeErr
+ }
+ return True
+}
+
+// Get implements the traits.Indexer interface method.
+func (l *concatList) Get(index ref.Val) ref.Val {
+ i, ok := index.(Int)
+ if !ok {
+ return MaybeNoSuchOverloadErr(index)
+ }
+ if i < l.prevList.Size().(Int) {
+ return l.prevList.Get(i)
+ }
+ offset := i - l.prevList.Size().(Int)
+ return l.nextList.Get(offset)
+}
+
+// Iterator implements the traits.Iterable interface method.
+func (l *concatList) Iterator() traits.Iterator {
+ return newListIterator(l)
+}
+
+// Size implements the traits.Sizer interface method.
+func (l *concatList) Size() ref.Val {
+ return l.prevList.Size().(Int).Add(l.nextList.Size())
+}
+
+// Type implements the ref.Val interface method.
+func (l *concatList) Type() ref.Type {
+ return ListType
+}
+
+// Value implements the ref.Val interface method.
+func (l *concatList) Value() interface{} {
+ if l.value == nil {
+ merged := make([]interface{}, l.Size().(Int))
+ prevLen := l.prevList.Size().(Int)
+ for i := Int(0); i < prevLen; i++ {
+ merged[i] = l.prevList.Get(i).Value()
+ }
+ nextLen := l.nextList.Size().(Int)
+ for j := Int(0); j < nextLen; j++ {
+ merged[prevLen+j] = l.nextList.Get(j).Value()
+ }
+ l.value = merged
+ }
+ return l.value
+}
+
+func newListIterator(listValue traits.Lister) traits.Iterator {
+ return &listIterator{
+ listValue: listValue,
+ len: listValue.Size().(Int),
+ }
+}
+
+type listIterator struct {
+ *baseIterator
+ listValue traits.Lister
+ cursor Int
+ len Int
+}
+
+// HasNext implements the traits.Iterator interface method.
+func (it *listIterator) HasNext() ref.Val {
+ return Bool(it.cursor < it.len)
+}
+
+// Next implements the traits.Iterator interface method.
+func (it *listIterator) Next() ref.Val {
+ if it.HasNext() == True {
+ index := it.cursor
+ it.cursor++
+ return it.listValue.Get(index)
+ }
+ return nil
+}
diff --git a/vendor/github.com/google/cel-go/common/types/map.go b/vendor/github.com/google/cel-go/common/types/map.go
new file mode 100644
index 0000000000..2b1453d907
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/map.go
@@ -0,0 +1,809 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+
+ "github.com/google/cel-go/common/types/pb"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+ "github.com/stoewer/go-strcase"
+ "google.golang.org/protobuf/proto"
+ "google.golang.org/protobuf/reflect/protoreflect"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+// NewDynamicMap returns a traits.Mapper value with dynamic key, value pairs.
+func NewDynamicMap(adapter ref.TypeAdapter, value interface{}) traits.Mapper {
+ refValue := reflect.ValueOf(value)
+ return &baseMap{
+ TypeAdapter: adapter,
+ mapAccessor: newReflectMapAccessor(adapter, refValue),
+ value: value,
+ size: refValue.Len(),
+ }
+}
+
+// NewJSONStruct creates a traits.Mapper implementation backed by a JSON struct that has been
+// encoded in protocol buffer form.
+//
+// The `adapter` argument provides type adaptation capabilities from proto to CEL.
+func NewJSONStruct(adapter ref.TypeAdapter, value *structpb.Struct) traits.Mapper {
+ fields := value.GetFields()
+ return &baseMap{
+ TypeAdapter: adapter,
+ mapAccessor: newJSONStructAccessor(adapter, fields),
+ value: value,
+ size: len(fields),
+ }
+}
+
+// NewRefValMap returns a specialized traits.Mapper with CEL valued keys and values.
+func NewRefValMap(adapter ref.TypeAdapter, value map[ref.Val]ref.Val) traits.Mapper {
+ return &baseMap{
+ TypeAdapter: adapter,
+ mapAccessor: newRefValMapAccessor(value),
+ value: value,
+ size: len(value),
+ }
+}
+
+// NewStringInterfaceMap returns a specialized traits.Mapper with string keys and interface values.
+func NewStringInterfaceMap(adapter ref.TypeAdapter, value map[string]interface{}) traits.Mapper {
+ return &baseMap{
+ TypeAdapter: adapter,
+ mapAccessor: newStringIfaceMapAccessor(adapter, value),
+ value: value,
+ size: len(value),
+ }
+}
+
+// NewStringStringMap returns a specialized traits.Mapper with string keys and values.
+func NewStringStringMap(adapter ref.TypeAdapter, value map[string]string) traits.Mapper {
+ return &baseMap{
+ TypeAdapter: adapter,
+ mapAccessor: newStringMapAccessor(value),
+ value: value,
+ size: len(value),
+ }
+}
+
+// NewProtoMap returns a specialized traits.Mapper for handling protobuf map values.
+func NewProtoMap(adapter ref.TypeAdapter, value *pb.Map) traits.Mapper {
+ return &protoMap{
+ TypeAdapter: adapter,
+ value: value,
+ }
+}
+
+var (
+ // MapType singleton.
+ MapType = NewTypeValue("map",
+ traits.ContainerType,
+ traits.IndexerType,
+ traits.IterableType,
+ traits.SizerType)
+)
+
+// mapAccessor is a private interface for finding values within a map and iterating over the keys.
+// This interface implements portions of the API surface area required by the traits.Mapper
+// interface.
+type mapAccessor interface {
+ // Find returns a value, if one exists, for the inpput key.
+ //
+ // If the key is not found the function returns (nil, false).
+ // If the input key is not valid for the map, or is Err or Unknown the function returns
+ // (Unknown|Err, false).
+ Find(ref.Val) (ref.Val, bool)
+
+ // Iterator returns an Iterator over the map key set.
+ Iterator() traits.Iterator
+}
+
+// baseMap is a reflection based map implementation designed to handle a variety of map-like types.
+//
+// Since CEL is side-effect free, the base map represents an immutable object.
+type baseMap struct {
+ // TypeAdapter used to convert keys and values accessed within the map.
+ ref.TypeAdapter
+
+ // mapAccessor interface implementation used to find and iterate over map keys.
+ mapAccessor
+
+ // value is the native Go value upon which the map type operators.
+ value interface{}
+
+ // size is the number of entries in the map.
+ size int
+}
+
+// Contains implements the traits.Container interface method.
+func (m *baseMap) Contains(index ref.Val) ref.Val {
+ val, found := m.Find(index)
+ // When the index is not found and val is non-nil, this is an error or unknown value.
+ if !found && val != nil && IsUnknownOrError(val) {
+ return val
+ }
+ return Bool(found)
+}
+
+// ConvertToNative implements the ref.Val interface method.
+func (m *baseMap) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ // If the map is already assignable to the desired type return it, e.g. interfaces and
+ // maps with the same key value types.
+ if reflect.TypeOf(m.value).AssignableTo(typeDesc) {
+ return m.value, nil
+ }
+ if reflect.TypeOf(m).AssignableTo(typeDesc) {
+ return m, nil
+ }
+ switch typeDesc {
+ case anyValueType:
+ json, err := m.ConvertToNative(jsonStructType)
+ if err != nil {
+ return nil, err
+ }
+ return anypb.New(json.(proto.Message))
+ case jsonValueType, jsonStructType:
+ jsonEntries, err :=
+ m.ConvertToNative(reflect.TypeOf(map[string]*structpb.Value{}))
+ if err != nil {
+ return nil, err
+ }
+ jsonMap := &structpb.Struct{Fields: jsonEntries.(map[string]*structpb.Value)}
+ if typeDesc == jsonStructType {
+ return jsonMap, nil
+ }
+ return structpb.NewStructValue(jsonMap), nil
+ }
+
+ // Unwrap pointers, but track their use.
+ isPtr := false
+ if typeDesc.Kind() == reflect.Ptr {
+ tk := typeDesc
+ typeDesc = typeDesc.Elem()
+ if typeDesc.Kind() == reflect.Ptr {
+ return nil, fmt.Errorf("unsupported type conversion to '%v'", tk)
+ }
+ isPtr = true
+ }
+ switch typeDesc.Kind() {
+ // Map conversion.
+ case reflect.Map:
+ otherKey := typeDesc.Key()
+ otherElem := typeDesc.Elem()
+ nativeMap := reflect.MakeMapWithSize(typeDesc, m.size)
+ it := m.Iterator()
+ for it.HasNext() == True {
+ key := it.Next()
+ refKeyValue, err := key.ConvertToNative(otherKey)
+ if err != nil {
+ return nil, err
+ }
+ refElemValue, err := m.Get(key).ConvertToNative(otherElem)
+ if err != nil {
+ return nil, err
+ }
+ nativeMap.SetMapIndex(reflect.ValueOf(refKeyValue), reflect.ValueOf(refElemValue))
+ }
+ return nativeMap.Interface(), nil
+ case reflect.Struct:
+ nativeStructPtr := reflect.New(typeDesc)
+ nativeStruct := nativeStructPtr.Elem()
+ it := m.Iterator()
+ for it.HasNext() == True {
+ key := it.Next()
+ // Ensure the field name being referenced is exported.
+ // Only exported (public) field names can be set by reflection, where the name
+ // must be at least one character in length and start with an upper-case letter.
+ fieldName := key.ConvertToType(StringType)
+ if IsError(fieldName) {
+ return nil, fieldName.(*Err)
+ }
+ name := string(fieldName.(String))
+ name = strcase.UpperCamelCase(name)
+ fieldRef := nativeStruct.FieldByName(name)
+ if !fieldRef.IsValid() {
+ return nil, fmt.Errorf("type conversion error, no such field '%s' in type '%v'", name, typeDesc)
+ }
+ fieldValue, err := m.Get(key).ConvertToNative(fieldRef.Type())
+ if err != nil {
+ return nil, err
+ }
+ fieldRef.Set(reflect.ValueOf(fieldValue))
+ }
+ if isPtr {
+ return nativeStructPtr.Interface(), nil
+ }
+ return nativeStruct.Interface(), nil
+ }
+ return nil, fmt.Errorf("type conversion error from map to '%v'", typeDesc)
+}
+
+// ConvertToType implements the ref.Val interface method.
+func (m *baseMap) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case MapType:
+ return m
+ case TypeType:
+ return MapType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", MapType, typeVal)
+}
+
+// Equal implements the ref.Val interface method.
+func (m *baseMap) Equal(other ref.Val) ref.Val {
+ otherMap, ok := other.(traits.Mapper)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if m.Size() != otherMap.Size() {
+ return False
+ }
+ it := m.Iterator()
+ var maybeErr ref.Val
+ for it.HasNext() == True {
+ key := it.Next()
+ thisVal, _ := m.Find(key)
+ otherVal, found := otherMap.Find(key)
+ if !found {
+ if otherVal == nil {
+ return False
+ }
+ if maybeErr == nil {
+ maybeErr = MaybeNoSuchOverloadErr(otherVal)
+ }
+ continue
+ }
+ valEq := thisVal.Equal(otherVal)
+ if valEq == False {
+ return False
+ }
+ if maybeErr == nil && IsUnknownOrError(valEq) {
+ maybeErr = valEq
+ }
+ }
+ if maybeErr != nil {
+ return maybeErr
+ }
+ return True
+}
+
+// Get implements the traits.Indexer interface method.
+func (m *baseMap) Get(key ref.Val) ref.Val {
+ v, found := m.Find(key)
+ if !found {
+ return ValOrErr(v, "no such key: %v", key)
+ }
+ return v
+}
+
+// Size implements the traits.Sizer interface method.
+func (m *baseMap) Size() ref.Val {
+ return Int(m.size)
+}
+
+// Type implements the ref.Val interface method.
+func (m *baseMap) Type() ref.Type {
+ return MapType
+}
+
+// Value implements the ref.Val interface method.
+func (m *baseMap) Value() interface{} {
+ return m.value
+}
+
+func newJSONStructAccessor(adapter ref.TypeAdapter, st map[string]*structpb.Value) mapAccessor {
+ return &jsonStructAccessor{
+ TypeAdapter: adapter,
+ st: st,
+ }
+}
+
+type jsonStructAccessor struct {
+ ref.TypeAdapter
+ st map[string]*structpb.Value
+}
+
+// Find searches the json struct field map for the input key value and returns (value, true) if
+// found.
+//
+// If the key is not found the function returns (nil, false).
+// If the input key is not a String, or is an Err or Unknown, the function returns
+// (Unknown|Err, false).
+func (a *jsonStructAccessor) Find(key ref.Val) (ref.Val, bool) {
+ strKey, ok := key.(String)
+ if !ok {
+ return ValOrErr(key, "unsupported key type: %v", key.Type()), false
+ }
+ keyVal, found := a.st[string(strKey)]
+ if !found {
+ return nil, false
+ }
+ return a.NativeToValue(keyVal), true
+}
+
+// Iterator creates a new traits.Iterator from the set of JSON struct field names.
+func (a *jsonStructAccessor) Iterator() traits.Iterator {
+ // Copy the keys to make their order stable.
+ mapKeys := make([]string, len(a.st))
+ i := 0
+ for k := range a.st {
+ mapKeys[i] = k
+ i++
+ }
+ return &stringKeyIterator{
+ mapKeys: mapKeys,
+ len: len(mapKeys),
+ }
+}
+
+func newReflectMapAccessor(adapter ref.TypeAdapter, value reflect.Value) mapAccessor {
+ keyType := value.Type().Key()
+ return &reflectMapAccessor{
+ TypeAdapter: adapter,
+ refValue: value,
+ keyType: keyType,
+ }
+}
+
+type reflectMapAccessor struct {
+ ref.TypeAdapter
+ refValue reflect.Value
+ keyType reflect.Type
+}
+
+// Find converts the input key to a native Golang type and then uses reflection to find the key,
+// returning (value, true) if present.
+//
+// If the key is not found the function returns (nil, false).
+// If the input key is not a String, or is an Err or Unknown, the function returns
+// (Unknown|Err, false).
+func (a *reflectMapAccessor) Find(key ref.Val) (ref.Val, bool) {
+ if IsUnknownOrError(key) {
+ return MaybeNoSuchOverloadErr(key), false
+ }
+ if a.refValue.Len() == 0 {
+ return nil, false
+ }
+ k, err := key.ConvertToNative(a.keyType)
+ if err != nil {
+ return NewErr("unsupported key type: %v", key.Type()), false
+ }
+ refKey := reflect.ValueOf(k)
+ val := a.refValue.MapIndex(refKey)
+ if val.IsValid() {
+ return a.NativeToValue(val.Interface()), true
+ }
+ mapIt := a.refValue.MapRange()
+ for mapIt.Next() {
+ if refKey.Kind() == mapIt.Key().Kind() {
+ return nil, false
+ }
+ }
+ return NewErr("unsupported key type: %v", key.Type()), false
+}
+
+// Iterator creates a Golang reflection based traits.Iterator.
+func (a *reflectMapAccessor) Iterator() traits.Iterator {
+ return &mapIterator{
+ TypeAdapter: a.TypeAdapter,
+ mapKeys: a.refValue.MapRange(),
+ len: a.refValue.Len(),
+ }
+}
+
+func newRefValMapAccessor(mapVal map[ref.Val]ref.Val) mapAccessor {
+ return &refValMapAccessor{mapVal: mapVal}
+}
+
+type refValMapAccessor struct {
+ mapVal map[ref.Val]ref.Val
+}
+
+// Find uses native map accesses to find the key, returning (value, true) if present.
+//
+// If the key is not found the function returns (nil, false).
+// If the input key is an Err or Unknown, the function returns (Unknown|Err, false).
+func (a *refValMapAccessor) Find(key ref.Val) (ref.Val, bool) {
+ if IsUnknownOrError(key) {
+ return key, false
+ }
+ if len(a.mapVal) == 0 {
+ return nil, false
+ }
+ keyVal, found := a.mapVal[key]
+ if found {
+ return keyVal, true
+ }
+ for k := range a.mapVal {
+ if k.Type().TypeName() == key.Type().TypeName() {
+ return nil, false
+ }
+ }
+ return NewErr("unsupported key type: %v", key.Type()), found
+}
+
+// Iterator produces a new traits.Iterator which iterates over the map keys via Golang reflection.
+func (a *refValMapAccessor) Iterator() traits.Iterator {
+ return &mapIterator{
+ TypeAdapter: DefaultTypeAdapter,
+ mapKeys: reflect.ValueOf(a.mapVal).MapRange(),
+ len: len(a.mapVal),
+ }
+}
+
+func newStringMapAccessor(strMap map[string]string) mapAccessor {
+ return &stringMapAccessor{mapVal: strMap}
+}
+
+type stringMapAccessor struct {
+ mapVal map[string]string
+}
+
+// Find uses native map accesses to find the key, returning (value, true) if present.
+//
+// If the key is not found the function returns (nil, false).
+// If the input key is not a String, or is an Err or Unknown, the function returns
+// (Unknown|Err, false).
+func (a *stringMapAccessor) Find(key ref.Val) (ref.Val, bool) {
+ strKey, ok := key.(String)
+ if !ok {
+ return ValOrErr(key, "unsupported key type: %v", key.Type()), false
+ }
+ keyVal, found := a.mapVal[string(strKey)]
+ if !found {
+ return nil, false
+ }
+ return String(keyVal), true
+}
+
+// Iterator creates a new traits.Iterator from the string key set of the map.
+func (a *stringMapAccessor) Iterator() traits.Iterator {
+ // Copy the keys to make their order stable.
+ mapKeys := make([]string, len(a.mapVal))
+ i := 0
+ for k := range a.mapVal {
+ mapKeys[i] = k
+ i++
+ }
+ return &stringKeyIterator{
+ mapKeys: mapKeys,
+ len: len(mapKeys),
+ }
+}
+
+func newStringIfaceMapAccessor(adapter ref.TypeAdapter, mapVal map[string]interface{}) mapAccessor {
+ return &stringIfaceMapAccessor{
+ TypeAdapter: adapter,
+ mapVal: mapVal,
+ }
+}
+
+type stringIfaceMapAccessor struct {
+ ref.TypeAdapter
+ mapVal map[string]interface{}
+}
+
+// Find uses native map accesses to find the key, returning (value, true) if present.
+//
+// If the key is not found the function returns (nil, false).
+// If the input key is not a String, or is an Err or Unknown, the function returns
+// (Unknown|Err, false).
+func (a *stringIfaceMapAccessor) Find(key ref.Val) (ref.Val, bool) {
+ strKey, ok := key.(String)
+ if !ok {
+ return ValOrErr(key, "unsupported key type: %v", key.Type()), false
+ }
+ keyVal, found := a.mapVal[string(strKey)]
+ if !found {
+ return nil, false
+ }
+ return a.NativeToValue(keyVal), true
+}
+
+// Iterator creates a new traits.Iterator from the string key set of the map.
+func (a *stringIfaceMapAccessor) Iterator() traits.Iterator {
+ // Copy the keys to make their order stable.
+ mapKeys := make([]string, len(a.mapVal))
+ i := 0
+ for k := range a.mapVal {
+ mapKeys[i] = k
+ i++
+ }
+ return &stringKeyIterator{
+ mapKeys: mapKeys,
+ len: len(mapKeys),
+ }
+}
+
+// protoMap is a specialized, separate implementation of the traits.Mapper interfaces tailored to
+// accessing protoreflect.Map values.
+type protoMap struct {
+ ref.TypeAdapter
+ value *pb.Map
+}
+
+// Contains returns whether the map contains the given key.
+func (m *protoMap) Contains(key ref.Val) ref.Val {
+ val, found := m.Find(key)
+ // When the index is not found and val is non-nil, this is an error or unknown value.
+ if !found && val != nil && IsUnknownOrError(val) {
+ return val
+ }
+ return Bool(found)
+}
+
+// ConvertToNative implements the ref.Val interface method.
+//
+// Note, assignment to Golang struct types is not yet supported.
+func (m *protoMap) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ // If the map is already assignable to the desired type return it, e.g. interfaces and
+ // maps with the same key value types.
+ switch typeDesc {
+ case anyValueType:
+ json, err := m.ConvertToNative(jsonStructType)
+ if err != nil {
+ return nil, err
+ }
+ return anypb.New(json.(proto.Message))
+ case jsonValueType, jsonStructType:
+ jsonEntries, err :=
+ m.ConvertToNative(reflect.TypeOf(map[string]*structpb.Value{}))
+ if err != nil {
+ return nil, err
+ }
+ jsonMap := &structpb.Struct{
+ Fields: jsonEntries.(map[string]*structpb.Value)}
+ if typeDesc == jsonStructType {
+ return jsonMap, nil
+ }
+ return structpb.NewStructValue(jsonMap), nil
+ }
+ switch typeDesc.Kind() {
+ case reflect.Struct, reflect.Ptr:
+ if reflect.TypeOf(m.value).AssignableTo(typeDesc) {
+ return m.value, nil
+ }
+ if reflect.TypeOf(m).AssignableTo(typeDesc) {
+ return m, nil
+ }
+ }
+ if typeDesc.Kind() != reflect.Map {
+ return nil, fmt.Errorf("unsupported type conversion: %v to map", typeDesc)
+ }
+
+ keyType := m.value.KeyType.ReflectType()
+ valType := m.value.ValueType.ReflectType()
+ otherKeyType := typeDesc.Key()
+ otherValType := typeDesc.Elem()
+ mapVal := reflect.MakeMapWithSize(typeDesc, m.value.Len())
+ var err error
+ m.value.Range(func(key protoreflect.MapKey, val protoreflect.Value) bool {
+ ntvKey := key.Interface()
+ ntvVal := val.Interface()
+ switch ntvVal.(type) {
+ case protoreflect.Message:
+ ntvVal = ntvVal.(protoreflect.Message).Interface()
+ }
+ if keyType == otherKeyType && valType == otherValType {
+ mapVal.SetMapIndex(reflect.ValueOf(ntvKey), reflect.ValueOf(ntvVal))
+ return true
+ }
+ celKey := m.NativeToValue(ntvKey)
+ celVal := m.NativeToValue(ntvVal)
+ ntvKey, err = celKey.ConvertToNative(otherKeyType)
+ if err != nil {
+ // early terminate the range loop.
+ return false
+ }
+ ntvVal, err = celVal.ConvertToNative(otherValType)
+ if err != nil {
+ // early terminate the range loop.
+ return false
+ }
+ mapVal.SetMapIndex(reflect.ValueOf(ntvKey), reflect.ValueOf(ntvVal))
+ return true
+ })
+ if err != nil {
+ return nil, err
+ }
+ return mapVal.Interface(), nil
+}
+
+// ConvertToType implements the ref.Val interface method.
+func (m *protoMap) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case MapType:
+ return m
+ case TypeType:
+ return MapType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", MapType, typeVal)
+}
+
+// Equal implements the ref.Val interface method.
+func (m *protoMap) Equal(other ref.Val) ref.Val {
+ otherMap, ok := other.(traits.Mapper)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if m.value.Map.Len() != int(otherMap.Size().(Int)) {
+ return False
+ }
+ var retVal ref.Val = True
+ m.value.Range(func(key protoreflect.MapKey, val protoreflect.Value) bool {
+ keyVal := m.NativeToValue(key.Interface())
+ valVal := m.NativeToValue(val)
+ otherVal, found := otherMap.Find(keyVal)
+ if !found {
+ if otherVal == nil {
+ retVal = False
+ return false
+ }
+ retVal = MaybeNoSuchOverloadErr(otherVal)
+ return false
+ }
+ valEq := valVal.Equal(otherVal)
+ if valEq != True {
+ retVal = valEq
+ return false
+ }
+ return true
+ })
+ return retVal
+}
+
+// Find returns whether the protoreflect.Map contains the input key.
+//
+// If the key is not found the function returns (nil, false).
+// If the input key is not a supported proto map key type, or is an Err or Unknown,
+// the function returns
+// (Unknown|Err, false).
+func (m *protoMap) Find(key ref.Val) (ref.Val, bool) {
+ if IsUnknownOrError(key) {
+ return key, false
+ }
+ // Convert the input key to the expected protobuf key type.
+ ntvKey, err := key.ConvertToNative(m.value.KeyType.ReflectType())
+ if err != nil {
+ return NewErr("unsupported key type: %v", key.Type()), false
+ }
+ // Use protoreflection to get the key value.
+ val := m.value.Get(protoreflect.ValueOf(ntvKey).MapKey())
+ if !val.IsValid() {
+ return nil, false
+ }
+ // Perform nominal type unwrapping from the input value.
+ switch v := val.Interface().(type) {
+ case protoreflect.List, protoreflect.Map:
+ // Maps do not support list or map values
+ return NewErr("unsupported map element type: (%T)%v", v, v), false
+ default:
+ return m.NativeToValue(v), true
+ }
+}
+
+// Get implements the traits.Indexer interface method.
+func (m *protoMap) Get(key ref.Val) ref.Val {
+ v, found := m.Find(key)
+ if !found {
+ return ValOrErr(v, "no such key: %v", key)
+ }
+ return v
+}
+
+// Iterator implements the traits.Iterable interface method.
+func (m *protoMap) Iterator() traits.Iterator {
+ // Copy the keys to make their order stable.
+ mapKeys := make([]protoreflect.MapKey, 0, m.value.Len())
+ m.value.Range(func(k protoreflect.MapKey, v protoreflect.Value) bool {
+ mapKeys = append(mapKeys, k)
+ return true
+ })
+ return &protoMapIterator{
+ TypeAdapter: m.TypeAdapter,
+ mapKeys: mapKeys,
+ len: m.value.Len(),
+ }
+}
+
+// Size returns the number of entries in the protoreflect.Map.
+func (m *protoMap) Size() ref.Val {
+ return Int(m.value.Len())
+}
+
+// Type implements the ref.Val interface method.
+func (m *protoMap) Type() ref.Type {
+ return MapType
+}
+
+// Value implements the ref.Val interface method.
+func (m *protoMap) Value() interface{} {
+ return m.value
+}
+
+type mapIterator struct {
+ *baseIterator
+ ref.TypeAdapter
+ mapKeys *reflect.MapIter
+ cursor int
+ len int
+}
+
+// HasNext implements the traits.Iterator interface method.
+func (it *mapIterator) HasNext() ref.Val {
+ return Bool(it.cursor < it.len)
+}
+
+// Next implements the traits.Iterator interface method.
+func (it *mapIterator) Next() ref.Val {
+ if it.HasNext() == True && it.mapKeys.Next() {
+ it.cursor++
+ refKey := it.mapKeys.Key()
+ return it.NativeToValue(refKey.Interface())
+ }
+ return nil
+}
+
+type protoMapIterator struct {
+ *baseIterator
+ ref.TypeAdapter
+ mapKeys []protoreflect.MapKey
+ cursor int
+ len int
+}
+
+// HasNext implements the traits.Iterator interface method.
+func (it *protoMapIterator) HasNext() ref.Val {
+ return Bool(it.cursor < it.len)
+}
+
+// Next implements the traits.Iterator interface method.
+func (it *protoMapIterator) Next() ref.Val {
+ if it.HasNext() == True {
+ index := it.cursor
+ it.cursor++
+ refKey := it.mapKeys[index]
+ return it.NativeToValue(refKey.Interface())
+ }
+ return nil
+}
+
+type stringKeyIterator struct {
+ *baseIterator
+ mapKeys []string
+ cursor int
+ len int
+}
+
+// HasNext implements the traits.Iterator interface method.
+func (it *stringKeyIterator) HasNext() ref.Val {
+ return Bool(it.cursor < it.len)
+}
+
+// Next implements the traits.Iterator interface method.
+func (it *stringKeyIterator) Next() ref.Val {
+ if it.HasNext() == True {
+ index := it.cursor
+ it.cursor++
+ return String(it.mapKeys[index])
+ }
+ return nil
+}
diff --git a/vendor/github.com/google/cel-go/common/types/null.go b/vendor/github.com/google/cel-go/common/types/null.go
new file mode 100644
index 0000000000..5a693f6e6d
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/null.go
@@ -0,0 +1,100 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+
+ "github.com/google/cel-go/common/types/ref"
+ "google.golang.org/protobuf/proto"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+// Null type implementation.
+type Null structpb.NullValue
+
+var (
+ // NullType singleton.
+ NullType = NewTypeValue("null_type")
+ // NullValue singleton.
+ NullValue = Null(structpb.NullValue_NULL_VALUE)
+
+ jsonNullType = reflect.TypeOf(structpb.NullValue_NULL_VALUE)
+)
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (n Null) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ switch typeDesc.Kind() {
+ case reflect.Int32:
+ return reflect.ValueOf(n).Convert(typeDesc).Interface(), nil
+ case reflect.Ptr:
+ switch typeDesc {
+ case anyValueType:
+ // Convert to a JSON-null before packing to an Any field since the enum value for JSON
+ // null cannot be packed directly.
+ pb, err := n.ConvertToNative(jsonValueType)
+ if err != nil {
+ return nil, err
+ }
+ return anypb.New(pb.(proto.Message))
+ case jsonValueType:
+ return structpb.NewNullValue(), nil
+ }
+ case reflect.Interface:
+ nv := n.Value()
+ if reflect.TypeOf(nv).Implements(typeDesc) {
+ return nv, nil
+ }
+ if reflect.TypeOf(n).Implements(typeDesc) {
+ return n, nil
+ }
+ }
+ // If the type conversion isn't supported return an error.
+ return nil, fmt.Errorf("type conversion error from '%v' to '%v'", NullType, typeDesc)
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (n Null) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case StringType:
+ return String("null")
+ case NullType:
+ return n
+ case TypeType:
+ return NullType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", NullType, typeVal)
+}
+
+// Equal implements ref.Val.Equal.
+func (n Null) Equal(other ref.Val) ref.Val {
+ if NullType != other.Type() {
+ return ValOrErr(other, "no such overload")
+ }
+ return True
+}
+
+// Type implements ref.Val.Type.
+func (n Null) Type() ref.Type {
+ return NullType
+}
+
+// Value implements ref.Val.Value.
+func (n Null) Value() interface{} {
+ return structpb.NullValue_NULL_VALUE
+}
diff --git a/vendor/github.com/google/cel-go/common/types/object.go b/vendor/github.com/google/cel-go/common/types/object.go
new file mode 100644
index 0000000000..d4efa066b0
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/object.go
@@ -0,0 +1,158 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+
+ "github.com/google/cel-go/common/types/pb"
+ "github.com/google/cel-go/common/types/ref"
+ "google.golang.org/protobuf/encoding/protojson"
+ "google.golang.org/protobuf/proto"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+type protoObj struct {
+ ref.TypeAdapter
+ value proto.Message
+ typeDesc *pb.TypeDescription
+ typeValue *TypeValue
+}
+
+// NewObject returns an object based on a proto.Message value which handles
+// conversion between protobuf type values and expression type values.
+// Objects support indexing and iteration.
+//
+// Note: the type value is pulled from the list of registered types within the
+// type provider. If the proto type is not registered within the type provider,
+// then this will result in an error within the type adapter / provider.
+func NewObject(adapter ref.TypeAdapter,
+ typeDesc *pb.TypeDescription,
+ typeValue *TypeValue,
+ value proto.Message) ref.Val {
+ return &protoObj{
+ TypeAdapter: adapter,
+ value: value,
+ typeDesc: typeDesc,
+ typeValue: typeValue}
+}
+
+func (o *protoObj) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ pb := o.value
+ if reflect.TypeOf(pb).AssignableTo(typeDesc) {
+ return pb, nil
+ }
+ if reflect.TypeOf(o).AssignableTo(typeDesc) {
+ return o, nil
+ }
+ switch typeDesc {
+ case anyValueType:
+ _, isAny := pb.(*anypb.Any)
+ if isAny {
+ return pb, nil
+ }
+ return anypb.New(pb)
+ case jsonValueType:
+ // Marshal the proto to JSON first, and then rehydrate as protobuf.Value as there is no
+ // support for direct conversion from proto.Message to protobuf.Value.
+ bytes, err := protojson.Marshal(pb)
+ if err != nil {
+ return nil, err
+ }
+ json := &structpb.Value{}
+ err = protojson.Unmarshal(bytes, json)
+ if err != nil {
+ return nil, err
+ }
+ return json, nil
+ default:
+ if typeDesc == o.typeDesc.ReflectType() {
+ return o.value, nil
+ }
+ if typeDesc.Kind() == reflect.Ptr {
+ val := reflect.New(typeDesc.Elem()).Interface()
+ dstPB, ok := val.(proto.Message)
+ if ok {
+ proto.Merge(dstPB, pb)
+ return dstPB, nil
+ }
+ }
+ }
+ return nil, fmt.Errorf("type conversion error from '%T' to '%v'", o.value, typeDesc)
+}
+
+func (o *protoObj) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ default:
+ if o.Type().TypeName() == typeVal.TypeName() {
+ return o
+ }
+ case TypeType:
+ return o.typeValue
+ }
+ return NewErr("type conversion error from '%s' to '%s'", o.typeDesc.Name(), typeVal)
+}
+
+func (o *protoObj) Equal(other ref.Val) ref.Val {
+ if o.typeDesc.Name() != other.Type().TypeName() {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return Bool(proto.Equal(o.value, other.Value().(proto.Message)))
+}
+
+// IsSet tests whether a field which is defined is set to a non-default value.
+func (o *protoObj) IsSet(field ref.Val) ref.Val {
+ protoFieldName, ok := field.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(field)
+ }
+ protoFieldStr := string(protoFieldName)
+ fd, found := o.typeDesc.FieldByName(protoFieldStr)
+ if !found {
+ return NewErr("no such field '%s'", field)
+ }
+ if fd.IsSet(o.value) {
+ return True
+ }
+ return False
+}
+
+func (o *protoObj) Get(index ref.Val) ref.Val {
+ protoFieldName, ok := index.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(index)
+ }
+ protoFieldStr := string(protoFieldName)
+ fd, found := o.typeDesc.FieldByName(protoFieldStr)
+ if !found {
+ return NewErr("no such field '%s'", index)
+ }
+ fv, err := fd.GetFrom(o.value)
+ if err != nil {
+ return NewErr(err.Error())
+ }
+ return o.NativeToValue(fv)
+}
+
+func (o *protoObj) Type() ref.Type {
+ return o.typeValue
+}
+
+func (o *protoObj) Value() interface{} {
+ return o.value
+}
diff --git a/vendor/github.com/google/cel-go/common/types/overflow.go b/vendor/github.com/google/cel-go/common/types/overflow.go
new file mode 100644
index 0000000000..48cc6ece64
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/overflow.go
@@ -0,0 +1,357 @@
+// Copyright 2021 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "math"
+ "time"
+)
+
+var (
+ doubleTwoTo64 = math.Ldexp(1.0, 64)
+)
+
+// addInt64Checked performs addition with overflow detection of two int64 values.
+//
+// If the operation fails the error return value will be non-nil.
+func addInt64Checked(x, y int64) (int64, error) {
+ if (y > 0 && x > math.MaxInt64-y) || (y < 0 && x < math.MinInt64-y) {
+ return 0, errIntOverflow
+ }
+ return x + y, nil
+}
+
+// subtractInt64Checked performs subtraction with overflow detection of two int64 values.
+//
+// If the operation fails the error return value will be non-nil.
+func subtractInt64Checked(x, y int64) (int64, error) {
+ if (y < 0 && x > math.MaxInt64+y) || (y > 0 && x < math.MinInt64+y) {
+ return 0, errIntOverflow
+ }
+ return x - y, nil
+}
+
+// negateInt64Checked performs negation with overflow detection of an int64.
+//
+// If the operation fails the error return value will be non-nil.
+func negateInt64Checked(x int64) (int64, error) {
+ // In twos complement, negating MinInt64 would result in a valid of MaxInt64+1.
+ if x == math.MinInt64 {
+ return 0, errIntOverflow
+ }
+ return -x, nil
+}
+
+// multiplyInt64Checked performs multiplication with overflow detection of two int64 value.
+//
+// If the operation fails the error return value will be non-nil.
+func multiplyInt64Checked(x, y int64) (int64, error) {
+ // Detecting multiplication overflow is more complicated than the others. The first two detect
+ // attempting to negate MinInt64, which would result in MaxInt64+1. The other four detect normal
+ // overflow conditions.
+ if (x == -1 && y == math.MinInt64) || (y == -1 && x == math.MinInt64) ||
+ // x is positive, y is positive
+ (x > 0 && y > 0 && x > math.MaxInt64/y) ||
+ // x is positive, y is negative
+ (x > 0 && y < 0 && y < math.MinInt64/x) ||
+ // x is negative, y is positive
+ (x < 0 && y > 0 && x < math.MinInt64/y) ||
+ // x is negative, y is negative
+ (x < 0 && y < 0 && y < math.MaxInt64/x) {
+ return 0, errIntOverflow
+ }
+ return x * y, nil
+}
+
+// divideInt64Checked performs division with overflow detection of two int64 values,
+// as well as a division by zero check.
+//
+// If the operation fails the error return value will be non-nil.
+func divideInt64Checked(x, y int64) (int64, error) {
+ // Division by zero.
+ if y == 0 {
+ return 0, errDivideByZero
+ }
+ // In twos complement, negating MinInt64 would result in a valid of MaxInt64+1.
+ if x == math.MinInt64 && y == -1 {
+ return 0, errIntOverflow
+ }
+ return x / y, nil
+}
+
+// moduloInt64Checked performs modulo with overflow detection of two int64 values
+// as well as a modulus by zero check.
+//
+// If the operation fails the error return value will be non-nil.
+func moduloInt64Checked(x, y int64) (int64, error) {
+ // Modulus by zero.
+ if y == 0 {
+ return 0, errModulusByZero
+ }
+ // In twos complement, negating MinInt64 would result in a valid of MaxInt64+1.
+ if x == math.MinInt64 && y == -1 {
+ return 0, errIntOverflow
+ }
+ return x % y, nil
+}
+
+// addUint64Checked performs addition with overflow detection of two uint64 values.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func addUint64Checked(x, y uint64) (uint64, error) {
+ if y > 0 && x > math.MaxUint64-y {
+ return 0, errUintOverflow
+ }
+ return x + y, nil
+}
+
+// subtractUint64Checked performs subtraction with overflow detection of two uint64 values.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func subtractUint64Checked(x, y uint64) (uint64, error) {
+ if y > x {
+ return 0, errUintOverflow
+ }
+ return x - y, nil
+}
+
+// multiplyUint64Checked performs multiplication with overflow detection of two uint64 values.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func multiplyUint64Checked(x, y uint64) (uint64, error) {
+ if y != 0 && x > math.MaxUint64/y {
+ return 0, errUintOverflow
+ }
+ return x * y, nil
+}
+
+// divideUint64Checked performs division with a test for division by zero.
+//
+// If the operation fails the error return value will be non-nil.
+func divideUint64Checked(x, y uint64) (uint64, error) {
+ if y == 0 {
+ return 0, errDivideByZero
+ }
+ return x / y, nil
+}
+
+// moduloUint64Checked performs modulo with a test for modulus by zero.
+//
+// If the operation fails the error return value will be non-nil.
+func moduloUint64Checked(x, y uint64) (uint64, error) {
+ if y == 0 {
+ return 0, errModulusByZero
+ }
+ return x % y, nil
+}
+
+// addDurationChecked performs addition with overflow detection of two time.Durations.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func addDurationChecked(x, y time.Duration) (time.Duration, error) {
+ val, err := addInt64Checked(int64(x), int64(y))
+ if err != nil {
+ return time.Duration(0), err
+ }
+ return time.Duration(val), nil
+}
+
+// subtractDurationChecked performs subtraction with overflow detection of two time.Durations.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func subtractDurationChecked(x, y time.Duration) (time.Duration, error) {
+ val, err := subtractInt64Checked(int64(x), int64(y))
+ if err != nil {
+ return time.Duration(0), err
+ }
+ return time.Duration(val), nil
+}
+
+// negateDurationChecked performs negation with overflow detection of a time.Duration.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func negateDurationChecked(x time.Duration) (time.Duration, error) {
+ val, err := negateInt64Checked(int64(x))
+ if err != nil {
+ return time.Duration(0), err
+ }
+ return time.Duration(val), nil
+}
+
+// addDurationChecked performs addition with overflow detection of a time.Time and time.Duration.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func addTimeDurationChecked(x time.Time, y time.Duration) (time.Time, error) {
+ // This is tricky. A time is represented as (int64, int32) where the first is seconds and second
+ // is nanoseconds. A duration is int64 representing nanoseconds. We cannot normalize time to int64
+ // as it could potentially overflow. The only way to proceed is to break time and duration into
+ // second and nanosecond components.
+
+ // First we break time into its components by truncating and subtracting.
+ sec1 := x.Truncate(time.Second).Unix() // Truncate to seconds.
+ nsec1 := x.Sub(x.Truncate(time.Second)).Nanoseconds() // Get nanoseconds by truncating and subtracting.
+
+ // Second we break duration into its components by dividing and modulo.
+ sec2 := int64(y) / int64(time.Second) // Truncate to seconds.
+ nsec2 := int64(y) % int64(time.Second) // Get remainder.
+
+ // Add seconds first, detecting any overflow.
+ sec, err := addInt64Checked(sec1, sec2)
+ if err != nil {
+ return time.Time{}, err
+ }
+ // Nanoseconds cannot overflow as time.Time normalizes them to [0, 999999999].
+ nsec := nsec1 + nsec2
+
+ // We need to normalize nanoseconds to be positive and carry extra nanoseconds to seconds.
+ // Adapted from time.Unix(int64, int64).
+ if nsec < 0 || nsec >= int64(time.Second) {
+ // Add seconds.
+ sec, err = addInt64Checked(sec, nsec/int64(time.Second))
+ if err != nil {
+ return time.Time{}, err
+ }
+
+ nsec -= (nsec / int64(time.Second)) * int64(time.Second)
+ if nsec < 0 {
+ // Subtract an extra second
+ sec, err = addInt64Checked(sec, -1)
+ if err != nil {
+ return time.Time{}, err
+ }
+ nsec += int64(time.Second)
+ }
+ }
+
+ // Check if the the number of seconds from Unix epoch is within our acceptable range.
+ if sec < minUnixTime || sec > maxUnixTime {
+ return time.Time{}, errTimestampOverflow
+ }
+
+ // Return resulting time and propagate time zone.
+ return time.Unix(sec, nsec).In(x.Location()), nil
+}
+
+// subtractTimeChecked performs subtraction with overflow detection of two time.Time.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func subtractTimeChecked(x, y time.Time) (time.Duration, error) {
+ // Similar to addTimeDurationOverflow() above.
+
+ // First we break time into its components by truncating and subtracting.
+ sec1 := x.Truncate(time.Second).Unix() // Truncate to seconds.
+ nsec1 := x.Sub(x.Truncate(time.Second)).Nanoseconds() // Get nanoseconds by truncating and subtracting.
+
+ // Second we break duration into its components by truncating and subtracting.
+ sec2 := y.Truncate(time.Second).Unix() // Truncate to seconds.
+ nsec2 := y.Sub(y.Truncate(time.Second)).Nanoseconds() // Get nanoseconds by truncating and subtracting.
+
+ // Subtract seconds first, detecting any overflow.
+ sec, err := subtractInt64Checked(sec1, sec2)
+ if err != nil {
+ return time.Duration(0), err
+ }
+
+ // Nanoseconds cannot overflow as time.Time normalizes them to [0, 999999999].
+ nsec := nsec1 - nsec2
+
+ // Scale seconds to nanoseconds detecting overflow.
+ tsec, err := multiplyInt64Checked(sec, int64(time.Second))
+ if err != nil {
+ return time.Duration(0), err
+ }
+
+ // Lastly we need to add the two nanoseconds together.
+ val, err := addInt64Checked(tsec, nsec)
+ if err != nil {
+ return time.Duration(0), err
+ }
+
+ return time.Duration(val), nil
+}
+
+// subtractTimeDurationChecked performs subtraction with overflow detection of a time.Time and
+// time.Duration.
+//
+// If the operation fails due to overflow the error return value will be non-nil.
+func subtractTimeDurationChecked(x time.Time, y time.Duration) (time.Time, error) {
+ // The easiest way to implement this is to negate y and add them.
+ // x - y = x + -y
+ val, err := negateDurationChecked(y)
+ if err != nil {
+ return time.Time{}, err
+ }
+ return addTimeDurationChecked(x, val)
+}
+
+// doubleToInt64Checked converts a double to an int64 value.
+//
+// If the conversion fails due to overflow the error return value will be non-nil.
+func doubleToInt64Checked(v float64) (int64, error) {
+ if math.IsInf(v, 0) || math.IsNaN(v) || v <= float64(math.MinInt64) || v >= float64(math.MaxInt64) {
+ return 0, errIntOverflow
+ }
+ return int64(v), nil
+}
+
+// doubleToInt64Checked converts a double to a uint64 value.
+//
+// If the conversion fails due to overflow the error return value will be non-nil.
+func doubleToUint64Checked(v float64) (uint64, error) {
+ if math.IsInf(v, 0) || math.IsNaN(v) || v < 0 || v >= doubleTwoTo64 {
+ return 0, errUintOverflow
+ }
+ return uint64(v), nil
+}
+
+// int64toUint64Checked converts an int64 to a uint64 value.
+//
+// If the conversion fails due to overflow the error return value will be non-nil.
+func int64ToUint64Checked(v int64) (uint64, error) {
+ if v < 0 {
+ return 0, errUintOverflow
+ }
+ return uint64(v), nil
+}
+
+// int64toInt32Checked converts an int64 to an int32 value.
+//
+// If the conversion fails due to overflow the error return value will be non-nil.
+func int64ToInt32Checked(v int64) (int32, error) {
+ if v < math.MinInt32 || v > math.MaxInt32 {
+ return 0, errIntOverflow
+ }
+ return int32(v), nil
+}
+
+// uint64toUint32Checked converts a uint64 to a uint32 value.
+//
+// If the conversion fails due to overflow the error return value will be non-nil.
+func uint64ToUint32Checked(v uint64) (uint32, error) {
+ if v > math.MaxUint32 {
+ return 0, errUintOverflow
+ }
+ return uint32(v), nil
+}
+
+// uint64toInt64Checked converts a uint64 to an int64 value.
+//
+// If the conversion fails due to overflow the error return value will be non-nil.
+func uint64ToInt64Checked(v uint64) (int64, error) {
+ if v > math.MaxInt64 {
+ return 0, errIntOverflow
+ }
+ return int64(v), nil
+}
diff --git a/vendor/github.com/google/cel-go/common/types/pb/BUILD.bazel b/vendor/github.com/google/cel-go/common/types/pb/BUILD.bazel
new file mode 100644
index 0000000000..b0c79a7f52
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/pb/BUILD.bazel
@@ -0,0 +1,50 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "checked.go",
+ "enum.go",
+ "file.go",
+ "pb.go",
+ "type.go",
+ ],
+ importpath = "github.com/google/cel-go/common/types/pb",
+ deps = [
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//proto:go_default_library",
+ "@org_golang_google_protobuf//reflect/protoreflect:go_default_library",
+ "@org_golang_google_protobuf//reflect/protoregistry:go_default_library",
+ "@org_golang_google_protobuf//types/dynamicpb:go_default_library",
+ "@org_golang_google_protobuf//types/known/anypb:go_default_library",
+ "@org_golang_google_protobuf//types/known/durationpb:go_default_library",
+ "@org_golang_google_protobuf//types/known/emptypb:go_default_library",
+ "@org_golang_google_protobuf//types/known/structpb:go_default_library",
+ "@org_golang_google_protobuf//types/known/timestamppb:go_default_library",
+ "@org_golang_google_protobuf//types/known/wrapperspb:go_default_library",
+ ],
+)
+
+go_test(
+ name = "go_default_test",
+ size = "small",
+ srcs = [
+ "file_test.go",
+ "pb_test.go",
+ "type_test.go",
+ ],
+ embed = [":go_default_library"],
+ deps = [
+ "//checker/decls:go_default_library",
+ "//test/proto2pb:test_all_types_go_proto",
+ "//test/proto3pb:test_all_types_go_proto",
+ "@org_golang_google_protobuf//reflect/protodesc:go_default_library",
+ "@org_golang_google_protobuf//reflect/protoreflect:go_default_library",
+ "@org_golang_google_protobuf//types/descriptorpb:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/common/types/pb/checked.go b/vendor/github.com/google/cel-go/common/types/pb/checked.go
new file mode 100644
index 0000000000..312a6a072f
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/pb/checked.go
@@ -0,0 +1,93 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package pb
+
+import (
+ "google.golang.org/protobuf/reflect/protoreflect"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+ emptypb "google.golang.org/protobuf/types/known/emptypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+var (
+ // CheckedPrimitives map from proto field descriptor type to expr.Type.
+ CheckedPrimitives = map[protoreflect.Kind]*exprpb.Type{
+ protoreflect.BoolKind: checkedBool,
+ protoreflect.BytesKind: checkedBytes,
+ protoreflect.DoubleKind: checkedDouble,
+ protoreflect.FloatKind: checkedDouble,
+ protoreflect.Int32Kind: checkedInt,
+ protoreflect.Int64Kind: checkedInt,
+ protoreflect.Sint32Kind: checkedInt,
+ protoreflect.Sint64Kind: checkedInt,
+ protoreflect.Uint32Kind: checkedUint,
+ protoreflect.Uint64Kind: checkedUint,
+ protoreflect.Fixed32Kind: checkedUint,
+ protoreflect.Fixed64Kind: checkedUint,
+ protoreflect.Sfixed32Kind: checkedInt,
+ protoreflect.Sfixed64Kind: checkedInt,
+ protoreflect.StringKind: checkedString}
+
+ // CheckedWellKnowns map from qualified proto type name to expr.Type for
+ // well-known proto types.
+ CheckedWellKnowns = map[string]*exprpb.Type{
+ // Wrapper types.
+ "google.protobuf.BoolValue": checkedWrap(checkedBool),
+ "google.protobuf.BytesValue": checkedWrap(checkedBytes),
+ "google.protobuf.DoubleValue": checkedWrap(checkedDouble),
+ "google.protobuf.FloatValue": checkedWrap(checkedDouble),
+ "google.protobuf.Int64Value": checkedWrap(checkedInt),
+ "google.protobuf.Int32Value": checkedWrap(checkedInt),
+ "google.protobuf.UInt64Value": checkedWrap(checkedUint),
+ "google.protobuf.UInt32Value": checkedWrap(checkedUint),
+ "google.protobuf.StringValue": checkedWrap(checkedString),
+ // Well-known types.
+ "google.protobuf.Any": checkedAny,
+ "google.protobuf.Duration": checkedDuration,
+ "google.protobuf.Timestamp": checkedTimestamp,
+ // Json types.
+ "google.protobuf.ListValue": checkedListDyn,
+ "google.protobuf.NullValue": checkedNull,
+ "google.protobuf.Struct": checkedMapStringDyn,
+ "google.protobuf.Value": checkedDyn,
+ }
+
+ // common types
+ checkedDyn = &exprpb.Type{TypeKind: &exprpb.Type_Dyn{Dyn: &emptypb.Empty{}}}
+ // Wrapper and primitive types.
+ checkedBool = checkedPrimitive(exprpb.Type_BOOL)
+ checkedBytes = checkedPrimitive(exprpb.Type_BYTES)
+ checkedDouble = checkedPrimitive(exprpb.Type_DOUBLE)
+ checkedInt = checkedPrimitive(exprpb.Type_INT64)
+ checkedString = checkedPrimitive(exprpb.Type_STRING)
+ checkedUint = checkedPrimitive(exprpb.Type_UINT64)
+ // Well-known type equivalents.
+ checkedAny = checkedWellKnown(exprpb.Type_ANY)
+ checkedDuration = checkedWellKnown(exprpb.Type_DURATION)
+ checkedTimestamp = checkedWellKnown(exprpb.Type_TIMESTAMP)
+ // Json-based type equivalents.
+ checkedNull = &exprpb.Type{
+ TypeKind: &exprpb.Type_Null{
+ Null: structpb.NullValue_NULL_VALUE}}
+ checkedListDyn = &exprpb.Type{
+ TypeKind: &exprpb.Type_ListType_{
+ ListType: &exprpb.Type_ListType{ElemType: checkedDyn}}}
+ checkedMapStringDyn = &exprpb.Type{
+ TypeKind: &exprpb.Type_MapType_{
+ MapType: &exprpb.Type_MapType{
+ KeyType: checkedString,
+ ValueType: checkedDyn}}}
+)
diff --git a/vendor/github.com/google/cel-go/common/types/pb/enum.go b/vendor/github.com/google/cel-go/common/types/pb/enum.go
new file mode 100644
index 0000000000..4a26b5c7c3
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/pb/enum.go
@@ -0,0 +1,44 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package pb
+
+import (
+ "google.golang.org/protobuf/reflect/protoreflect"
+)
+
+// NewEnumValueDescription produces an enum value description with the fully qualified enum value
+// name and the enum value descriptor.
+func NewEnumValueDescription(name string, desc protoreflect.EnumValueDescriptor) *EnumValueDescription {
+ return &EnumValueDescription{
+ enumValueName: name,
+ desc: desc,
+ }
+}
+
+// EnumValueDescription maps a fully-qualified enum value name to its numeric value.
+type EnumValueDescription struct {
+ enumValueName string
+ desc protoreflect.EnumValueDescriptor
+}
+
+// Name returns the fully-qualified identifier name for the enum value.
+func (ed *EnumValueDescription) Name() string {
+ return ed.enumValueName
+}
+
+// Value returns the (numeric) value of the enum.
+func (ed *EnumValueDescription) Value() int32 {
+ return int32(ed.desc.Number())
+}
diff --git a/vendor/github.com/google/cel-go/common/types/pb/file.go b/vendor/github.com/google/cel-go/common/types/pb/file.go
new file mode 100644
index 0000000000..0bcade75f9
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/pb/file.go
@@ -0,0 +1,141 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package pb
+
+import (
+ "fmt"
+
+ "google.golang.org/protobuf/reflect/protoreflect"
+)
+
+// NewFileDescription returns a FileDescription instance with a complete listing of all the message
+// types and enum values declared within any scope in the file.
+func NewFileDescription(fileDesc protoreflect.FileDescriptor, pbdb *Db) *FileDescription {
+ metadata := collectFileMetadata(fileDesc)
+ enums := make(map[string]*EnumValueDescription)
+ for name, enumVal := range metadata.enumValues {
+ enums[name] = NewEnumValueDescription(name, enumVal)
+ }
+ types := make(map[string]*TypeDescription)
+ for name, msgType := range metadata.msgTypes {
+ types[name] = NewTypeDescription(name, msgType)
+ }
+ return &FileDescription{
+ types: types,
+ enums: enums,
+ }
+}
+
+// FileDescription holds a map of all types and enum values declared within a proto file.
+type FileDescription struct {
+ types map[string]*TypeDescription
+ enums map[string]*EnumValueDescription
+}
+
+// GetEnumDescription returns an EnumDescription for a qualified enum value
+// name declared within the .proto file.
+func (fd *FileDescription) GetEnumDescription(enumName string) (*EnumValueDescription, bool) {
+ ed, found := fd.enums[sanitizeProtoName(enumName)]
+ return ed, found
+}
+
+// GetEnumNames returns the string names of all enum values in the file.
+func (fd *FileDescription) GetEnumNames() []string {
+ enumNames := make([]string, len(fd.enums))
+ i := 0
+ for _, e := range fd.enums {
+ enumNames[i] = e.Name()
+ i++
+ }
+ return enumNames
+}
+
+// GetTypeDescription returns a TypeDescription for a qualified protobuf message type name
+// declared within the .proto file.
+func (fd *FileDescription) GetTypeDescription(typeName string) (*TypeDescription, bool) {
+ td, found := fd.types[sanitizeProtoName(typeName)]
+ return td, found
+}
+
+// GetTypeNames returns the list of all type names contained within the file.
+func (fd *FileDescription) GetTypeNames() []string {
+ typeNames := make([]string, len(fd.types))
+ i := 0
+ for _, t := range fd.types {
+ typeNames[i] = t.Name()
+ i++
+ }
+ return typeNames
+}
+
+// sanitizeProtoName strips the leading '.' from the proto message name.
+func sanitizeProtoName(name string) string {
+ if name != "" && name[0] == '.' {
+ return name[1:]
+ }
+ return name
+}
+
+// fileMetadata is a flattened view of message types and enum values within a file descriptor.
+type fileMetadata struct {
+ // msgTypes maps from fully-qualified message name to descriptor.
+ msgTypes map[string]protoreflect.MessageDescriptor
+ // enumValues maps from fully-qualified enum value to enum value descriptor.
+ enumValues map[string]protoreflect.EnumValueDescriptor
+ // TODO: support enum type definitions for use in future type-check enhancements.
+}
+
+// collectFileMetadata traverses the proto file object graph to collect message types and enum
+// values and index them by their fully qualified names.
+func collectFileMetadata(fileDesc protoreflect.FileDescriptor) *fileMetadata {
+ msgTypes := make(map[string]protoreflect.MessageDescriptor)
+ enumValues := make(map[string]protoreflect.EnumValueDescriptor)
+ collectMsgTypes(fileDesc.Messages(), msgTypes, enumValues)
+ collectEnumValues(fileDesc.Enums(), enumValues)
+ return &fileMetadata{
+ msgTypes: msgTypes,
+ enumValues: enumValues,
+ }
+}
+
+// collectMsgTypes recursively collects messages, nested messages, and nested enums into a map of
+// fully qualified protobuf names to descriptors.
+func collectMsgTypes(msgTypes protoreflect.MessageDescriptors, msgTypeMap map[string]protoreflect.MessageDescriptor, enumValueMap map[string]protoreflect.EnumValueDescriptor) {
+ for i := 0; i < msgTypes.Len(); i++ {
+ msgType := msgTypes.Get(i)
+ msgTypeMap[string(msgType.FullName())] = msgType
+ nestedMsgTypes := msgType.Messages()
+ if nestedMsgTypes.Len() != 0 {
+ collectMsgTypes(nestedMsgTypes, msgTypeMap, enumValueMap)
+ }
+ nestedEnumTypes := msgType.Enums()
+ if nestedEnumTypes.Len() != 0 {
+ collectEnumValues(nestedEnumTypes, enumValueMap)
+ }
+ }
+}
+
+// collectEnumValues accumulates the enum values within an enum declaration.
+func collectEnumValues(enumTypes protoreflect.EnumDescriptors, enumValueMap map[string]protoreflect.EnumValueDescriptor) {
+ for i := 0; i < enumTypes.Len(); i++ {
+ enumType := enumTypes.Get(i)
+ enumTypeValues := enumType.Values()
+ for j := 0; j < enumTypeValues.Len(); j++ {
+ enumValue := enumTypeValues.Get(j)
+ enumValueName := fmt.Sprintf("%s.%s", string(enumType.FullName()), string(enumValue.Name()))
+ enumValueMap[enumValueName] = enumValue
+ }
+ }
+}
diff --git a/vendor/github.com/google/cel-go/common/types/pb/pb.go b/vendor/github.com/google/cel-go/common/types/pb/pb.go
new file mode 100644
index 0000000000..d02fbe0c25
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/pb/pb.go
@@ -0,0 +1,196 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package pb reflects over protocol buffer descriptors to generate objects
+// that simplify type, enum, and field lookup.
+package pb
+
+import (
+ "google.golang.org/protobuf/proto"
+ "google.golang.org/protobuf/reflect/protoreflect"
+ "google.golang.org/protobuf/reflect/protoregistry"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ durpb "google.golang.org/protobuf/types/known/durationpb"
+ emptypb "google.golang.org/protobuf/types/known/emptypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ tspb "google.golang.org/protobuf/types/known/timestamppb"
+ wrapperspb "google.golang.org/protobuf/types/known/wrapperspb"
+)
+
+// Db maps from file / message / enum name to file description.
+//
+// Each Db is isolated from each other, and while information about protobuf descriptors may be
+// fetched from the global protobuf registry, no descriptors are added to this registry, else
+// the isolation guarantees of the Db object would be violated.
+type Db struct {
+ revFileDescriptorMap map[string]*FileDescription
+ // files contains the deduped set of FileDescriptions whose types are contained in the pb.Db.
+ files []*FileDescription
+}
+
+var (
+ // DefaultDb used at evaluation time or unless overridden at check time.
+ DefaultDb = &Db{
+ revFileDescriptorMap: make(map[string]*FileDescription),
+ files: []*FileDescription{},
+ }
+)
+
+// NewDb creates a new `pb.Db` with an empty type name to file description map.
+func NewDb() *Db {
+ pbdb := &Db{
+ revFileDescriptorMap: make(map[string]*FileDescription),
+ files: []*FileDescription{},
+ }
+ // The FileDescription objects in the default db contain lazily initialized TypeDescription
+ // values which may point to the state contained in the DefaultDb irrespective of this shallow
+ // copy; however, the type graph for a field is idempotently computed, and is guaranteed to
+ // only be initialized once thanks to atomic values within the TypeDescription objects, so it
+ // is safe to share these values across instances.
+ for k, v := range DefaultDb.revFileDescriptorMap {
+ pbdb.revFileDescriptorMap[k] = v
+ }
+ pbdb.files = append(pbdb.files, DefaultDb.files...)
+ return pbdb
+}
+
+// Copy creates a copy of the current database with its own internal descriptor mapping.
+func (pbdb *Db) Copy() *Db {
+ copy := NewDb()
+ for k, v := range pbdb.revFileDescriptorMap {
+ copy.revFileDescriptorMap[k] = v
+ }
+ for _, f := range pbdb.files {
+ hasFile := false
+ for _, f2 := range copy.files {
+ if f2 == f {
+ hasFile = true
+ }
+ }
+ if !hasFile {
+ copy.files = append(copy.files, f)
+ }
+ }
+ return copy
+}
+
+// FileDescriptions returns the set of file descriptions associated with this db.
+func (pbdb *Db) FileDescriptions() []*FileDescription {
+ return pbdb.files
+}
+
+// RegisterDescriptor produces a `FileDescription` from a `FileDescriptor` and registers the
+// message and enum types into the `pb.Db`.
+func (pbdb *Db) RegisterDescriptor(fileDesc protoreflect.FileDescriptor) (*FileDescription, error) {
+ fd, found := pbdb.revFileDescriptorMap[fileDesc.Path()]
+ if found {
+ return fd, nil
+ }
+ // Make sure to search the global registry to see if a protoreflect.FileDescriptor for
+ // the file specified has been linked into the binary. If so, use the copy of the descriptor
+ // from the global cache.
+ //
+ // Note: Proto reflection relies on descriptor values being object equal rather than object
+ // equivalence. This choice means that a FieldDescriptor generated from a FileDescriptorProto
+ // will be incompatible with the FieldDescriptor in the global registry and any message created
+ // from that global registry.
+ globalFD, err := protoregistry.GlobalFiles.FindFileByPath(fileDesc.Path())
+ if err == nil {
+ fileDesc = globalFD
+ }
+ fd = NewFileDescription(fileDesc, pbdb)
+ for _, enumValName := range fd.GetEnumNames() {
+ pbdb.revFileDescriptorMap[enumValName] = fd
+ }
+ for _, msgTypeName := range fd.GetTypeNames() {
+ pbdb.revFileDescriptorMap[msgTypeName] = fd
+ }
+ pbdb.revFileDescriptorMap[fileDesc.Path()] = fd
+
+ // Return the specific file descriptor registered.
+ pbdb.files = append(pbdb.files, fd)
+ return fd, nil
+}
+
+// RegisterMessage produces a `FileDescription` from a `message` and registers the message and all
+// other definitions within the message file into the `pb.Db`.
+func (pbdb *Db) RegisterMessage(message proto.Message) (*FileDescription, error) {
+ msgDesc := message.ProtoReflect().Descriptor()
+ msgName := msgDesc.FullName()
+ typeName := sanitizeProtoName(string(msgName))
+ if fd, found := pbdb.revFileDescriptorMap[typeName]; found {
+ return fd, nil
+ }
+ return pbdb.RegisterDescriptor(msgDesc.ParentFile())
+}
+
+// DescribeEnum takes a qualified enum name and returns an `EnumDescription` if it exists in the
+// `pb.Db`.
+func (pbdb *Db) DescribeEnum(enumName string) (*EnumValueDescription, bool) {
+ enumName = sanitizeProtoName(enumName)
+ if fd, found := pbdb.revFileDescriptorMap[enumName]; found {
+ return fd.GetEnumDescription(enumName)
+ }
+ return nil, false
+}
+
+// DescribeType returns a `TypeDescription` for the `typeName` if it exists in the `pb.Db`.
+func (pbdb *Db) DescribeType(typeName string) (*TypeDescription, bool) {
+ typeName = sanitizeProtoName(typeName)
+ if fd, found := pbdb.revFileDescriptorMap[typeName]; found {
+ return fd.GetTypeDescription(typeName)
+ }
+ return nil, false
+}
+
+// CollectFileDescriptorSet builds a file descriptor set associated with the file where the input
+// message is declared.
+func CollectFileDescriptorSet(message proto.Message) map[string]protoreflect.FileDescriptor {
+ fdMap := map[string]protoreflect.FileDescriptor{}
+ parentFile := message.ProtoReflect().Descriptor().ParentFile()
+ fdMap[parentFile.Path()] = parentFile
+ // Initialize list of dependencies
+ deps := make([]protoreflect.FileImport, parentFile.Imports().Len())
+ for i := 0; i < parentFile.Imports().Len(); i++ {
+ deps[i] = parentFile.Imports().Get(i)
+ }
+ // Expand list for new dependencies
+ for i := 0; i < len(deps); i++ {
+ dep := deps[i]
+ if _, found := fdMap[dep.Path()]; found {
+ continue
+ }
+ fdMap[dep.Path()] = dep.FileDescriptor
+ for j := 0; j < dep.FileDescriptor.Imports().Len(); j++ {
+ deps = append(deps, dep.FileDescriptor.Imports().Get(j))
+ }
+ }
+ return fdMap
+}
+
+func init() {
+ // Describe well-known types to ensure they can always be resolved by the check and interpret
+ // execution phases.
+ //
+ // The following subset of message types is enough to ensure that all well-known types can
+ // resolved in the runtime, since describing the value results in describing the whole file
+ // where the message is declared.
+ DefaultDb.RegisterMessage(&anypb.Any{})
+ DefaultDb.RegisterMessage(&durpb.Duration{})
+ DefaultDb.RegisterMessage(&emptypb.Empty{})
+ DefaultDb.RegisterMessage(&tspb.Timestamp{})
+ DefaultDb.RegisterMessage(&structpb.Value{})
+ DefaultDb.RegisterMessage(&wrapperspb.BoolValue{})
+}
diff --git a/vendor/github.com/google/cel-go/common/types/pb/type.go b/vendor/github.com/google/cel-go/common/types/pb/type.go
new file mode 100644
index 0000000000..8594008b12
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/pb/type.go
@@ -0,0 +1,532 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package pb
+
+import (
+ "fmt"
+ "reflect"
+
+ "google.golang.org/protobuf/proto"
+ "google.golang.org/protobuf/reflect/protoreflect"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+ dynamicpb "google.golang.org/protobuf/types/dynamicpb"
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ dpb "google.golang.org/protobuf/types/known/durationpb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ tpb "google.golang.org/protobuf/types/known/timestamppb"
+ wrapperspb "google.golang.org/protobuf/types/known/wrapperspb"
+)
+
+// description is a private interface used to make it convenient to perform type unwrapping at
+// the TypeDescription or FieldDescription level.
+type description interface {
+ // Zero returns an empty immutable protobuf message when the description is a protobuf message
+ // type.
+ Zero() proto.Message
+}
+
+// NewTypeDescription produces a TypeDescription value for the fully-qualified proto type name
+// with a given descriptor.
+func NewTypeDescription(typeName string, desc protoreflect.MessageDescriptor) *TypeDescription {
+ msgType := dynamicpb.NewMessageType(desc)
+ msgZero := dynamicpb.NewMessage(desc)
+ fieldMap := map[string]*FieldDescription{}
+ fields := desc.Fields()
+ for i := 0; i < fields.Len(); i++ {
+ f := fields.Get(i)
+ fieldMap[string(f.Name())] = NewFieldDescription(f)
+ }
+ return &TypeDescription{
+ typeName: typeName,
+ desc: desc,
+ msgType: msgType,
+ fieldMap: fieldMap,
+ reflectType: reflectTypeOf(msgZero),
+ zeroMsg: zeroValueOf(msgZero),
+ }
+}
+
+// TypeDescription is a collection of type metadata relevant to expression
+// checking and evaluation.
+type TypeDescription struct {
+ typeName string
+ desc protoreflect.MessageDescriptor
+ msgType protoreflect.MessageType
+ fieldMap map[string]*FieldDescription
+ reflectType reflect.Type
+ zeroMsg proto.Message
+}
+
+// FieldMap returns a string field name to FieldDescription map.
+func (td *TypeDescription) FieldMap() map[string]*FieldDescription {
+ return td.fieldMap
+}
+
+// FieldByName returns (FieldDescription, true) if the field name is declared within the type.
+func (td *TypeDescription) FieldByName(name string) (*FieldDescription, bool) {
+ fd, found := td.fieldMap[name]
+ if !found {
+ return nil, false
+ }
+ return fd, true
+}
+
+// MaybeUnwrap accepts a proto message as input and unwraps it to a primitive CEL type if possible.
+//
+// This method returns the unwrapped value and 'true', else the original value and 'false'.
+func (td *TypeDescription) MaybeUnwrap(msg proto.Message) (interface{}, bool) {
+ return unwrap(td, msg)
+}
+
+// Name returns the fully-qualified name of the type.
+func (td *TypeDescription) Name() string {
+ return string(td.desc.FullName())
+}
+
+// New returns a mutable proto message
+func (td *TypeDescription) New() protoreflect.Message {
+ return td.msgType.New()
+}
+
+// ReflectType returns the Golang reflect.Type for this type.
+func (td *TypeDescription) ReflectType() reflect.Type {
+ return td.reflectType
+}
+
+// Zero returns the zero proto.Message value for this type.
+func (td *TypeDescription) Zero() proto.Message {
+ return td.zeroMsg
+}
+
+// NewFieldDescription creates a new field description from a protoreflect.FieldDescriptor.
+func NewFieldDescription(fieldDesc protoreflect.FieldDescriptor) *FieldDescription {
+ var reflectType reflect.Type
+ var zeroMsg proto.Message
+ switch fieldDesc.Kind() {
+ case protoreflect.EnumKind:
+ reflectType = reflectTypeOf(protoreflect.EnumNumber(0))
+ case protoreflect.MessageKind:
+ zeroMsg = dynamicpb.NewMessage(fieldDesc.Message())
+ reflectType = reflectTypeOf(zeroMsg)
+ default:
+ reflectType = reflectTypeOf(fieldDesc.Default().Interface())
+ if fieldDesc.IsList() {
+ parentMsg := dynamicpb.NewMessage(fieldDesc.ContainingMessage())
+ listField := parentMsg.NewField(fieldDesc).List()
+ elem := listField.NewElement().Interface()
+ switch elemType := elem.(type) {
+ case protoreflect.Message:
+ elem = elemType.Interface()
+ }
+ reflectType = reflectTypeOf(elem)
+ }
+ }
+ // Ensure the list type is appropriately reflected as a Go-native list.
+ if fieldDesc.IsList() {
+ reflectType = reflect.SliceOf(reflectType)
+ }
+ var keyType, valType *FieldDescription
+ if fieldDesc.IsMap() {
+ keyType = NewFieldDescription(fieldDesc.MapKey())
+ valType = NewFieldDescription(fieldDesc.MapValue())
+ }
+ return &FieldDescription{
+ desc: fieldDesc,
+ KeyType: keyType,
+ ValueType: valType,
+ reflectType: reflectType,
+ zeroMsg: zeroValueOf(zeroMsg),
+ }
+}
+
+// FieldDescription holds metadata related to fields declared within a type.
+type FieldDescription struct {
+ // KeyType holds the key FieldDescription for map fields.
+ KeyType *FieldDescription
+ // ValueType holds the value FieldDescription for map fields.
+ ValueType *FieldDescription
+
+ desc protoreflect.FieldDescriptor
+ reflectType reflect.Type
+ zeroMsg proto.Message
+}
+
+// CheckedType returns the type-definition used at type-check time.
+func (fd *FieldDescription) CheckedType() *exprpb.Type {
+ if fd.desc.IsMap() {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_MapType_{
+ MapType: &exprpb.Type_MapType{
+ KeyType: fd.KeyType.typeDefToType(),
+ ValueType: fd.ValueType.typeDefToType(),
+ },
+ },
+ }
+ }
+ if fd.desc.IsList() {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_ListType_{
+ ListType: &exprpb.Type_ListType{
+ ElemType: fd.typeDefToType()}}}
+ }
+ return fd.typeDefToType()
+}
+
+// Descriptor returns the protoreflect.FieldDescriptor for this type.
+func (fd *FieldDescription) Descriptor() protoreflect.FieldDescriptor {
+ return fd.desc
+}
+
+// IsSet returns whether the field is set on the target value, per the proto presence conventions
+// of proto2 or proto3 accordingly.
+//
+// This function implements the FieldType.IsSet function contract which can be used to operate on
+// more than just protobuf field accesses; however, the target here must be a protobuf.Message.
+func (fd *FieldDescription) IsSet(target interface{}) bool {
+ switch v := target.(type) {
+ case proto.Message:
+ pbRef := v.ProtoReflect()
+ pbDesc := pbRef.Descriptor()
+ if pbDesc == fd.desc.ContainingMessage() {
+ // When the target protobuf shares the same message descriptor instance as the field
+ // descriptor, use the cached field descriptor value.
+ return pbRef.Has(fd.desc)
+ }
+ // Otherwise, fallback to a dynamic lookup of the field descriptor from the target
+ // instance as an attempt to use the cached field descriptor will result in a panic.
+ return pbRef.Has(pbDesc.Fields().ByName(protoreflect.Name(fd.Name())))
+ default:
+ return false
+ }
+}
+
+// GetFrom returns the accessor method associated with the field on the proto generated struct.
+//
+// If the field is not set, the proto default value is returned instead.
+//
+// This function implements the FieldType.GetFrom function contract which can be used to operate
+// on more than just protobuf field accesses; however, the target here must be a protobuf.Message.
+func (fd *FieldDescription) GetFrom(target interface{}) (interface{}, error) {
+ v, ok := target.(proto.Message)
+ if !ok {
+ return nil, fmt.Errorf("unsupported field selection target: (%T)%v", target, target)
+ }
+ pbRef := v.ProtoReflect()
+ pbDesc := pbRef.Descriptor()
+ var fieldVal interface{}
+ if pbDesc == fd.desc.ContainingMessage() {
+ // When the target protobuf shares the same message descriptor instance as the field
+ // descriptor, use the cached field descriptor value.
+ fieldVal = pbRef.Get(fd.desc).Interface()
+ } else {
+ // Otherwise, fallback to a dynamic lookup of the field descriptor from the target
+ // instance as an attempt to use the cached field descriptor will result in a panic.
+ fieldVal = pbRef.Get(pbDesc.Fields().ByName(protoreflect.Name(fd.Name()))).Interface()
+ }
+ switch fv := fieldVal.(type) {
+ // Fast-path return for primitive types.
+ case bool, []byte, float32, float64, int32, int64, string, uint32, uint64, protoreflect.List:
+ return fv, nil
+ case protoreflect.EnumNumber:
+ return int64(fv), nil
+ case protoreflect.Map:
+ // Return a wrapper around the protobuf-reflected Map types which carries additional
+ // information about the key and value definitions of the map.
+ return &Map{Map: fv, KeyType: fd.KeyType, ValueType: fd.ValueType}, nil
+ case protoreflect.Message:
+ // Make sure to unwrap well-known protobuf types before returning.
+ unwrapped, _ := fd.MaybeUnwrapDynamic(fv)
+ return unwrapped, nil
+ default:
+ return fv, nil
+ }
+}
+
+// IsEnum returns true if the field type refers to an enum value.
+func (fd *FieldDescription) IsEnum() bool {
+ return fd.desc.Kind() == protoreflect.EnumKind
+}
+
+// IsMap returns true if the field is of map type.
+func (fd *FieldDescription) IsMap() bool {
+ return fd.desc.IsMap()
+}
+
+// IsMessage returns true if the field is of message type.
+func (fd *FieldDescription) IsMessage() bool {
+ return fd.desc.Kind() == protoreflect.MessageKind
+}
+
+// IsOneof returns true if the field is declared within a oneof block.
+func (fd *FieldDescription) IsOneof() bool {
+ return fd.desc.ContainingOneof() != nil
+}
+
+// IsList returns true if the field is a repeated value.
+//
+// This method will also return true for map values, so check whether the
+// field is also a map.
+func (fd *FieldDescription) IsList() bool {
+ return fd.desc.IsList()
+}
+
+// MaybeUnwrapDynamic takes the reflected protoreflect.Message and determines whether the
+// value can be unwrapped to a more primitive CEL type.
+//
+// This function returns the unwrapped value and 'true' on success, or the original value
+// and 'false' otherwise.
+func (fd *FieldDescription) MaybeUnwrapDynamic(msg protoreflect.Message) (interface{}, bool) {
+ return unwrapDynamic(fd, msg)
+}
+
+// Name returns the CamelCase name of the field within the proto-based struct.
+func (fd *FieldDescription) Name() string {
+ return string(fd.desc.Name())
+}
+
+// ReflectType returns the Golang reflect.Type for this field.
+func (fd *FieldDescription) ReflectType() reflect.Type {
+ return fd.reflectType
+}
+
+// String returns the fully qualified name of the field within its type as well as whether the
+// field occurs within a oneof.
+func (fd *FieldDescription) String() string {
+ return fmt.Sprintf("%v.%s `oneof=%t`", fd.desc.ContainingMessage().FullName(), fd.Name(), fd.IsOneof())
+}
+
+// Zero returns the zero value for the protobuf message represented by this field.
+//
+// If the field is not a proto.Message type, the zero value is nil.
+func (fd *FieldDescription) Zero() proto.Message {
+ return fd.zeroMsg
+}
+
+func (fd *FieldDescription) typeDefToType() *exprpb.Type {
+ if fd.desc.Kind() == protoreflect.MessageKind {
+ msgType := string(fd.desc.Message().FullName())
+ if wk, found := CheckedWellKnowns[msgType]; found {
+ return wk
+ }
+ return checkedMessageType(msgType)
+ }
+ if fd.desc.Kind() == protoreflect.EnumKind {
+ return checkedInt
+ }
+ return CheckedPrimitives[fd.desc.Kind()]
+}
+
+// Map wraps the protoreflect.Map object with a key and value FieldDescription for use in
+// retrieving individual elements within CEL value data types.
+type Map struct {
+ protoreflect.Map
+ KeyType *FieldDescription
+ ValueType *FieldDescription
+}
+
+func checkedMessageType(name string) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_MessageType{MessageType: name}}
+}
+
+func checkedPrimitive(primitive exprpb.Type_PrimitiveType) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_Primitive{Primitive: primitive}}
+}
+
+func checkedWellKnown(wellKnown exprpb.Type_WellKnownType) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_WellKnown{WellKnown: wellKnown}}
+}
+
+func checkedWrap(t *exprpb.Type) *exprpb.Type {
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_Wrapper{Wrapper: t.GetPrimitive()}}
+}
+
+// unwrap unwraps the provided proto.Message value, potentially based on the description if the
+// input message is a *dynamicpb.Message which obscures the typing information from Go.
+//
+// Returns the unwrapped value and 'true' if unwrapped, otherwise the input value and 'false'.
+func unwrap(desc description, msg proto.Message) (interface{}, bool) {
+ switch v := msg.(type) {
+ case *anypb.Any:
+ dynMsg, err := v.UnmarshalNew()
+ if err != nil {
+ return v, false
+ }
+ return unwrapDynamic(desc, dynMsg.ProtoReflect())
+ case *dynamicpb.Message:
+ return unwrapDynamic(desc, v)
+ case *dpb.Duration:
+ return v.AsDuration(), true
+ case *tpb.Timestamp:
+ return v.AsTime(), true
+ case *structpb.Value:
+ switch v.GetKind().(type) {
+ case *structpb.Value_BoolValue:
+ return v.GetBoolValue(), true
+ case *structpb.Value_ListValue:
+ return v.GetListValue(), true
+ case *structpb.Value_NullValue:
+ return structpb.NullValue_NULL_VALUE, true
+ case *structpb.Value_NumberValue:
+ return v.GetNumberValue(), true
+ case *structpb.Value_StringValue:
+ return v.GetStringValue(), true
+ case *structpb.Value_StructValue:
+ return v.GetStructValue(), true
+ default:
+ return structpb.NullValue_NULL_VALUE, true
+ }
+ case *wrapperspb.BoolValue:
+ return v.GetValue(), true
+ case *wrapperspb.BytesValue:
+ return v.GetValue(), true
+ case *wrapperspb.DoubleValue:
+ return v.GetValue(), true
+ case *wrapperspb.FloatValue:
+ return float64(v.GetValue()), true
+ case *wrapperspb.Int32Value:
+ return int64(v.GetValue()), true
+ case *wrapperspb.Int64Value:
+ return v.GetValue(), true
+ case *wrapperspb.StringValue:
+ return v.GetValue(), true
+ case *wrapperspb.UInt32Value:
+ return uint64(v.GetValue()), true
+ case *wrapperspb.UInt64Value:
+ return v.GetValue(), true
+ }
+ return msg, false
+}
+
+// unwrapDynamic unwraps a reflected protobuf Message value.
+//
+// Returns the unwrapped value and 'true' if unwrapped, otherwise the input value and 'false'.
+func unwrapDynamic(desc description, refMsg protoreflect.Message) (interface{}, bool) {
+ msg := refMsg.Interface()
+ if !refMsg.IsValid() {
+ msg = desc.Zero()
+ }
+ // In order to ensure that these wrapped types match the expectations of the CEL type system
+ // the dynamicpb.Message must be merged with an protobuf instance of the well-known type value.
+ typeName := string(refMsg.Descriptor().FullName())
+ switch typeName {
+ case "google.protobuf.Any":
+ // Note, Any values require further unwrapping; however, this unwrapping may or may not
+ // be to a well-known type. If the unwrapped value is a well-known type it will be further
+ // unwrapped before being returned to the caller. Otherwise, the dynamic protobuf object
+ // represented by the Any will be returned.
+ unwrappedAny := &anypb.Any{}
+ proto.Merge(unwrappedAny, msg)
+ dynMsg, err := unwrappedAny.UnmarshalNew()
+ if err != nil {
+ // Allow the error to move further up the stack as it should result in an type
+ // conversion error if the caller does not recover it somehow.
+ return unwrappedAny, true
+ }
+ // Attempt to unwrap the dynamic type, otherwise return the dynamic message.
+ if unwrapped, nested := unwrapDynamic(desc, dynMsg.ProtoReflect()); nested {
+ return unwrapped, true
+ }
+ return dynMsg, true
+ case "google.protobuf.BoolValue",
+ "google.protobuf.BytesValue",
+ "google.protobuf.DoubleValue",
+ "google.protobuf.FloatValue",
+ "google.protobuf.Int32Value",
+ "google.protobuf.Int64Value",
+ "google.protobuf.StringValue",
+ "google.protobuf.UInt32Value",
+ "google.protobuf.UInt64Value":
+ // The msg value is ignored when dealing with wrapper types as they have a null or value
+ // behavior, rather than the standard zero value behavior of other proto message types.
+ if !refMsg.IsValid() {
+ return structpb.NullValue_NULL_VALUE, true
+ }
+ valueField := refMsg.Descriptor().Fields().ByName("value")
+ return refMsg.Get(valueField).Interface(), true
+ case "google.protobuf.Duration":
+ unwrapped := &dpb.Duration{}
+ proto.Merge(unwrapped, msg)
+ return unwrapped.AsDuration(), true
+ case "google.protobuf.ListValue":
+ unwrapped := &structpb.ListValue{}
+ proto.Merge(unwrapped, msg)
+ return unwrapped, true
+ case "google.protobuf.NullValue":
+ return structpb.NullValue_NULL_VALUE, true
+ case "google.protobuf.Struct":
+ unwrapped := &structpb.Struct{}
+ proto.Merge(unwrapped, msg)
+ return unwrapped, true
+ case "google.protobuf.Timestamp":
+ unwrapped := &tpb.Timestamp{}
+ proto.Merge(unwrapped, msg)
+ return unwrapped.AsTime(), true
+ case "google.protobuf.Value":
+ unwrapped := &structpb.Value{}
+ proto.Merge(unwrapped, msg)
+ return unwrap(desc, unwrapped)
+ }
+ return msg, false
+}
+
+// reflectTypeOf intercepts the reflect.Type call to ensure that dynamicpb.Message types preserve
+// well-known protobuf reflected types expected by the CEL type system.
+func reflectTypeOf(val interface{}) reflect.Type {
+ switch v := val.(type) {
+ case proto.Message:
+ return reflect.TypeOf(zeroValueOf(v))
+ default:
+ return reflect.TypeOf(v)
+ }
+}
+
+// zeroValueOf will return the strongest possible proto.Message representing the default protobuf
+// message value of the input msg type.
+func zeroValueOf(msg proto.Message) proto.Message {
+ if msg == nil {
+ return nil
+ }
+ typeName := string(msg.ProtoReflect().Descriptor().FullName())
+ zeroVal, found := zeroValueMap[typeName]
+ if found {
+ return zeroVal
+ }
+ return msg
+}
+
+var (
+ zeroValueMap = map[string]proto.Message{
+ "google.protobuf.Any": &anypb.Any{},
+ "google.protobuf.Duration": &dpb.Duration{},
+ "google.protobuf.ListValue": &structpb.ListValue{},
+ "google.protobuf.Struct": &structpb.Struct{},
+ "google.protobuf.Timestamp": &tpb.Timestamp{},
+ "google.protobuf.Value": &structpb.Value{},
+ "google.protobuf.BoolValue": wrapperspb.Bool(false),
+ "google.protobuf.BytesValue": wrapperspb.Bytes([]byte{}),
+ "google.protobuf.DoubleValue": wrapperspb.Double(0.0),
+ "google.protobuf.FloatValue": wrapperspb.Float(0.0),
+ "google.protobuf.Int32Value": wrapperspb.Int32(0),
+ "google.protobuf.Int64Value": wrapperspb.Int64(0),
+ "google.protobuf.StringValue": wrapperspb.String(""),
+ "google.protobuf.UInt32Value": wrapperspb.UInt32(0),
+ "google.protobuf.UInt64Value": wrapperspb.UInt64(0),
+ }
+)
diff --git a/vendor/github.com/google/cel-go/common/types/provider.go b/vendor/github.com/google/cel-go/common/types/provider.go
new file mode 100644
index 0000000000..3ab30b763f
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/provider.go
@@ -0,0 +1,533 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+ "time"
+
+ "github.com/google/cel-go/common/types/pb"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+ "google.golang.org/protobuf/proto"
+ "google.golang.org/protobuf/reflect/protoreflect"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ dpb "google.golang.org/protobuf/types/known/durationpb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ tpb "google.golang.org/protobuf/types/known/timestamppb"
+)
+
+type protoTypeRegistry struct {
+ revTypeMap map[string]ref.Type
+ pbdb *pb.Db
+}
+
+// NewRegistry accepts a list of proto message instances and returns a type
+// provider which can create new instances of the provided message or any
+// message that proto depends upon in its FileDescriptor.
+func NewRegistry(types ...proto.Message) (ref.TypeRegistry, error) {
+ p := &protoTypeRegistry{
+ revTypeMap: make(map[string]ref.Type),
+ pbdb: pb.NewDb(),
+ }
+ err := p.RegisterType(
+ BoolType,
+ BytesType,
+ DoubleType,
+ DurationType,
+ IntType,
+ ListType,
+ MapType,
+ NullType,
+ StringType,
+ TimestampType,
+ TypeType,
+ UintType)
+ if err != nil {
+ return nil, err
+ }
+ // This block ensures that the well-known protobuf types are registered by default.
+ for _, fd := range p.pbdb.FileDescriptions() {
+ err = p.registerAllTypes(fd)
+ if err != nil {
+ return nil, err
+ }
+ }
+ for _, msgType := range types {
+ err = p.RegisterMessage(msgType)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return p, nil
+}
+
+// NewEmptyRegistry returns a registry which is completely unconfigured.
+func NewEmptyRegistry() ref.TypeRegistry {
+ return &protoTypeRegistry{
+ revTypeMap: make(map[string]ref.Type),
+ pbdb: pb.NewDb(),
+ }
+}
+
+// Copy implements the ref.TypeRegistry interface method which copies the current state of the
+// registry into its own memory space.
+func (p *protoTypeRegistry) Copy() ref.TypeRegistry {
+ copy := &protoTypeRegistry{
+ revTypeMap: make(map[string]ref.Type),
+ pbdb: p.pbdb.Copy(),
+ }
+ for k, v := range p.revTypeMap {
+ copy.revTypeMap[k] = v
+ }
+ return copy
+}
+
+func (p *protoTypeRegistry) EnumValue(enumName string) ref.Val {
+ enumVal, found := p.pbdb.DescribeEnum(enumName)
+ if !found {
+ return NewErr("unknown enum name '%s'", enumName)
+ }
+ return Int(enumVal.Value())
+}
+
+func (p *protoTypeRegistry) FindFieldType(messageType string,
+ fieldName string) (*ref.FieldType, bool) {
+ msgType, found := p.pbdb.DescribeType(messageType)
+ if !found {
+ return nil, false
+ }
+ field, found := msgType.FieldByName(fieldName)
+ if !found {
+ return nil, false
+ }
+ return &ref.FieldType{
+ Type: field.CheckedType(),
+ IsSet: field.IsSet,
+ GetFrom: field.GetFrom},
+ true
+}
+
+func (p *protoTypeRegistry) FindIdent(identName string) (ref.Val, bool) {
+ if t, found := p.revTypeMap[identName]; found {
+ return t.(ref.Val), true
+ }
+ if enumVal, found := p.pbdb.DescribeEnum(identName); found {
+ return Int(enumVal.Value()), true
+ }
+ return nil, false
+}
+
+func (p *protoTypeRegistry) FindType(typeName string) (*exprpb.Type, bool) {
+ if _, found := p.pbdb.DescribeType(typeName); !found {
+ return nil, false
+ }
+ if typeName != "" && typeName[0] == '.' {
+ typeName = typeName[1:]
+ }
+ return &exprpb.Type{
+ TypeKind: &exprpb.Type_Type{
+ Type: &exprpb.Type{
+ TypeKind: &exprpb.Type_MessageType{
+ MessageType: typeName}}}}, true
+}
+
+func (p *protoTypeRegistry) NewValue(typeName string, fields map[string]ref.Val) ref.Val {
+ td, found := p.pbdb.DescribeType(typeName)
+ if !found {
+ return NewErr("unknown type '%s'", typeName)
+ }
+ msg := td.New()
+ fieldMap := td.FieldMap()
+ for name, value := range fields {
+ field, found := fieldMap[name]
+ if !found {
+ return NewErr("no such field: %s", name)
+ }
+ err := msgSetField(msg, field, value)
+ if err != nil {
+ return &Err{err}
+ }
+ }
+ return p.NativeToValue(msg.Interface())
+}
+
+func (p *protoTypeRegistry) RegisterDescriptor(fileDesc protoreflect.FileDescriptor) error {
+ fd, err := p.pbdb.RegisterDescriptor(fileDesc)
+ if err != nil {
+ return err
+ }
+ return p.registerAllTypes(fd)
+}
+
+func (p *protoTypeRegistry) RegisterMessage(message proto.Message) error {
+ fd, err := p.pbdb.RegisterMessage(message)
+ if err != nil {
+ return err
+ }
+ return p.registerAllTypes(fd)
+}
+
+func (p *protoTypeRegistry) RegisterType(types ...ref.Type) error {
+ for _, t := range types {
+ p.revTypeMap[t.TypeName()] = t
+ }
+ // TODO: generate an error when the type name is registered more than once.
+ return nil
+}
+
+// NativeToValue converts various "native" types to ref.Val with this specific implementation
+// providing support for custom proto-based types.
+//
+// This method should be the inverse of ref.Val.ConvertToNative.
+func (p *protoTypeRegistry) NativeToValue(value interface{}) ref.Val {
+ if val, found := nativeToValue(p, value); found {
+ return val
+ }
+ switch v := value.(type) {
+ case proto.Message:
+ typeName := string(v.ProtoReflect().Descriptor().FullName())
+ td, found := p.pbdb.DescribeType(typeName)
+ if !found {
+ return NewErr("unknown type: '%s'", typeName)
+ }
+ unwrapped, isUnwrapped := td.MaybeUnwrap(v)
+ if isUnwrapped {
+ return p.NativeToValue(unwrapped)
+ }
+ typeVal, found := p.FindIdent(typeName)
+ if !found {
+ return NewErr("unknown type: '%s'", typeName)
+ }
+ return NewObject(p, td, typeVal.(*TypeValue), v)
+ case *pb.Map:
+ return NewProtoMap(p, v)
+ case protoreflect.List:
+ return NewProtoList(p, v)
+ case protoreflect.Message:
+ return p.NativeToValue(v.Interface())
+ case protoreflect.Value:
+ return p.NativeToValue(v.Interface())
+ }
+ return UnsupportedRefValConversionErr(value)
+}
+
+func (p *protoTypeRegistry) registerAllTypes(fd *pb.FileDescription) error {
+ for _, typeName := range fd.GetTypeNames() {
+ err := p.RegisterType(NewObjectTypeValue(typeName))
+ if err != nil {
+ return err
+ }
+ }
+ return nil
+}
+
+// defaultTypeAdapter converts go native types to CEL values.
+type defaultTypeAdapter struct{}
+
+var (
+ // DefaultTypeAdapter adapts canonical CEL types from their equivalent Go values.
+ DefaultTypeAdapter = &defaultTypeAdapter{}
+)
+
+// NativeToValue implements the ref.TypeAdapter interface.
+func (a *defaultTypeAdapter) NativeToValue(value interface{}) ref.Val {
+ if val, found := nativeToValue(a, value); found {
+ return val
+ }
+ return UnsupportedRefValConversionErr(value)
+}
+
+// nativeToValue returns the converted (ref.Val, true) of a conversion is found,
+// otherwise (nil, false)
+func nativeToValue(a ref.TypeAdapter, value interface{}) (ref.Val, bool) {
+ switch v := value.(type) {
+ case nil:
+ return NullValue, true
+ case *Bool:
+ if v != nil {
+ return *v, true
+ }
+ case *Bytes:
+ if v != nil {
+ return *v, true
+ }
+ case *Double:
+ if v != nil {
+ return *v, true
+ }
+ case *Int:
+ if v != nil {
+ return *v, true
+ }
+ case *String:
+ if v != nil {
+ return *v, true
+ }
+ case *Uint:
+ if v != nil {
+ return *v, true
+ }
+ case bool:
+ return Bool(v), true
+ case int:
+ return Int(v), true
+ case int32:
+ return Int(v), true
+ case int64:
+ return Int(v), true
+ case uint:
+ return Uint(v), true
+ case uint32:
+ return Uint(v), true
+ case uint64:
+ return Uint(v), true
+ case float32:
+ return Double(v), true
+ case float64:
+ return Double(v), true
+ case string:
+ return String(v), true
+ case *dpb.Duration:
+ return Duration{Duration: v.AsDuration()}, true
+ case time.Duration:
+ return Duration{Duration: v}, true
+ case *tpb.Timestamp:
+ return Timestamp{Time: v.AsTime()}, true
+ case time.Time:
+ return Timestamp{Time: v}, true
+ case *bool:
+ if v != nil {
+ return Bool(*v), true
+ }
+ case *float32:
+ if v != nil {
+ return Double(*v), true
+ }
+ case *float64:
+ if v != nil {
+ return Double(*v), true
+ }
+ case *int:
+ if v != nil {
+ return Int(*v), true
+ }
+ case *int32:
+ if v != nil {
+ return Int(*v), true
+ }
+ case *int64:
+ if v != nil {
+ return Int(*v), true
+ }
+ case *string:
+ if v != nil {
+ return String(*v), true
+ }
+ case *uint:
+ if v != nil {
+ return Uint(*v), true
+ }
+ case *uint32:
+ if v != nil {
+ return Uint(*v), true
+ }
+ case *uint64:
+ if v != nil {
+ return Uint(*v), true
+ }
+ case []byte:
+ return Bytes(v), true
+ // specializations for common lists types.
+ case []string:
+ return NewStringList(a, v), true
+ case []ref.Val:
+ return NewRefValList(a, v), true
+ // specializations for common map types.
+ case map[string]string:
+ return NewStringStringMap(a, v), true
+ case map[string]interface{}:
+ return NewStringInterfaceMap(a, v), true
+ case map[ref.Val]ref.Val:
+ return NewRefValMap(a, v), true
+ // additional specializations may be added upon request / need.
+ case *anypb.Any:
+ if v == nil {
+ return UnsupportedRefValConversionErr(v), true
+ }
+ unpackedAny, err := v.UnmarshalNew()
+ if err != nil {
+ return NewErr("anypb.UnmarshalNew() failed for type %q: %v", v.GetTypeUrl(), err), true
+ }
+ return a.NativeToValue(unpackedAny), true
+ case *structpb.NullValue, structpb.NullValue:
+ return NullValue, true
+ case *structpb.ListValue:
+ return NewJSONList(a, v), true
+ case *structpb.Struct:
+ return NewJSONStruct(a, v), true
+ case ref.Val:
+ return v, true
+ case protoreflect.EnumNumber:
+ return Int(v), true
+ case proto.Message:
+ if v == nil {
+ return UnsupportedRefValConversionErr(v), true
+ }
+ typeName := string(v.ProtoReflect().Descriptor().FullName())
+ td, found := pb.DefaultDb.DescribeType(typeName)
+ if !found {
+ return nil, false
+ }
+ val, unwrapped := td.MaybeUnwrap(v)
+ if !unwrapped {
+ return nil, false
+ }
+ return a.NativeToValue(val), true
+ // Note: dynamicpb.Message implements the proto.Message _and_ protoreflect.Message interfaces
+ // which means that this case must appear after handling a proto.Message type.
+ case protoreflect.Message:
+ return a.NativeToValue(v.Interface()), true
+ default:
+ refValue := reflect.ValueOf(v)
+ if refValue.Kind() == reflect.Ptr {
+ if refValue.IsNil() {
+ return UnsupportedRefValConversionErr(v), true
+ }
+ refValue = refValue.Elem()
+ }
+ refKind := refValue.Kind()
+ switch refKind {
+ case reflect.Array, reflect.Slice:
+ return NewDynamicList(a, v), true
+ case reflect.Map:
+ return NewDynamicMap(a, v), true
+ // type aliases of primitive types cannot be asserted as that type, but rather need
+ // to be downcast to int32 before being converted to a CEL representation.
+ case reflect.Int32:
+ intType := reflect.TypeOf(int32(0))
+ return Int(refValue.Convert(intType).Interface().(int32)), true
+ case reflect.Int64:
+ intType := reflect.TypeOf(int64(0))
+ return Int(refValue.Convert(intType).Interface().(int64)), true
+ case reflect.Uint32:
+ uintType := reflect.TypeOf(uint32(0))
+ return Uint(refValue.Convert(uintType).Interface().(uint32)), true
+ case reflect.Uint64:
+ uintType := reflect.TypeOf(uint64(0))
+ return Uint(refValue.Convert(uintType).Interface().(uint64)), true
+ case reflect.Float32:
+ doubleType := reflect.TypeOf(float32(0))
+ return Double(refValue.Convert(doubleType).Interface().(float32)), true
+ case reflect.Float64:
+ doubleType := reflect.TypeOf(float64(0))
+ return Double(refValue.Convert(doubleType).Interface().(float64)), true
+ }
+ }
+ return nil, false
+}
+
+func msgSetField(target protoreflect.Message, field *pb.FieldDescription, val ref.Val) error {
+ if field.IsList() {
+ lv := target.NewField(field.Descriptor())
+ list, ok := val.(traits.Lister)
+ if !ok {
+ return unsupportedTypeConversionError(field, val)
+ }
+ err := msgSetListField(lv.List(), field, list)
+ if err != nil {
+ return err
+ }
+ target.Set(field.Descriptor(), lv)
+ return nil
+ }
+ if field.IsMap() {
+ mv := target.NewField(field.Descriptor())
+ mp, ok := val.(traits.Mapper)
+ if !ok {
+ return unsupportedTypeConversionError(field, val)
+ }
+ err := msgSetMapField(mv.Map(), field, mp)
+ if err != nil {
+ return err
+ }
+ target.Set(field.Descriptor(), mv)
+ return nil
+ }
+ v, err := val.ConvertToNative(field.ReflectType())
+ if err != nil {
+ return fieldTypeConversionError(field, err)
+ }
+ switch v.(type) {
+ case proto.Message:
+ v = v.(proto.Message).ProtoReflect()
+ }
+ target.Set(field.Descriptor(), protoreflect.ValueOf(v))
+ return nil
+}
+
+func msgSetListField(target protoreflect.List, listField *pb.FieldDescription, listVal traits.Lister) error {
+ elemReflectType := listField.ReflectType().Elem()
+ for i := Int(0); i < listVal.Size().(Int); i++ {
+ elem := listVal.Get(i)
+ elemVal, err := elem.ConvertToNative(elemReflectType)
+ if err != nil {
+ return fieldTypeConversionError(listField, err)
+ }
+ switch ev := elemVal.(type) {
+ case proto.Message:
+ elemVal = ev.ProtoReflect()
+ }
+ target.Append(protoreflect.ValueOf(elemVal))
+ }
+ return nil
+}
+
+func msgSetMapField(target protoreflect.Map, mapField *pb.FieldDescription, mapVal traits.Mapper) error {
+ targetKeyType := mapField.KeyType.ReflectType()
+ targetValType := mapField.ValueType.ReflectType()
+ it := mapVal.Iterator()
+ for it.HasNext() == True {
+ key := it.Next()
+ val := mapVal.Get(key)
+ k, err := key.ConvertToNative(targetKeyType)
+ if err != nil {
+ return fieldTypeConversionError(mapField, err)
+ }
+ v, err := val.ConvertToNative(targetValType)
+ if err != nil {
+ return fieldTypeConversionError(mapField, err)
+ }
+ switch v.(type) {
+ case proto.Message:
+ v = v.(proto.Message).ProtoReflect()
+ }
+ target.Set(protoreflect.ValueOf(k).MapKey(), protoreflect.ValueOf(v))
+ }
+ return nil
+}
+
+func unsupportedTypeConversionError(field *pb.FieldDescription, val ref.Val) error {
+ msgName := field.Descriptor().ContainingMessage().FullName()
+ return fmt.Errorf("unsupported field type for %v.%v: %v", msgName, field.Name(), val.Type())
+}
+
+func fieldTypeConversionError(field *pb.FieldDescription, err error) error {
+ msgName := field.Descriptor().ContainingMessage().FullName()
+ return fmt.Errorf("field type conversion error for %v.%v value type: %v", msgName, field.Name(), err)
+}
diff --git a/vendor/github.com/google/cel-go/common/types/ref/BUILD.bazel b/vendor/github.com/google/cel-go/common/types/ref/BUILD.bazel
new file mode 100644
index 0000000000..1d0f468993
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/ref/BUILD.bazel
@@ -0,0 +1,20 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "provider.go",
+ "reference.go",
+ ],
+ importpath = "github.com/google/cel-go/common/types/ref",
+ deps = [
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//proto:go_default_library",
+ "@org_golang_google_protobuf//reflect/protoreflect:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/common/types/ref/provider.go b/vendor/github.com/google/cel-go/common/types/ref/provider.go
new file mode 100644
index 0000000000..91a711fa70
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/ref/provider.go
@@ -0,0 +1,103 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package ref
+
+import (
+ "google.golang.org/protobuf/proto"
+ "google.golang.org/protobuf/reflect/protoreflect"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// TypeProvider specifies functions for creating new object instances and for
+// resolving enum values by name.
+type TypeProvider interface {
+ // EnumValue returns the numeric value of the given enum value name.
+ EnumValue(enumName string) Val
+
+ // FindIdent takes a qualified identifier name and returns a Value if one
+ // exists.
+ FindIdent(identName string) (Val, bool)
+
+ // FindType looks up the Type given a qualified typeName. Returns false
+ // if not found.
+ //
+ // Used during type-checking only.
+ FindType(typeName string) (*exprpb.Type, bool)
+
+ // FieldFieldType returns the field type for a checked type value. Returns
+ // false if the field could not be found.
+ //
+ // Used during type-checking only.
+ FindFieldType(messageType string, fieldName string) (*FieldType, bool)
+
+ // NewValue creates a new type value from a qualified name and map of field
+ // name to value.
+ //
+ // Note, for each value, the Val.ConvertToNative function will be invoked
+ // to convert the Val to the field's native type. If an error occurs during
+ // conversion, the NewValue will be a types.Err.
+ NewValue(typeName string, fields map[string]Val) Val
+}
+
+// TypeAdapter converts native Go values of varying type and complexity to equivalent CEL values.
+type TypeAdapter interface {
+ // NativeToValue converts the input `value` to a CEL `ref.Val`.
+ NativeToValue(value interface{}) Val
+}
+
+// TypeRegistry allows third-parties to add custom types to CEL. Not all `TypeProvider`
+// implementations support type-customization, so these features are optional. However, a
+// `TypeRegistry` should be a `TypeProvider` and a `TypeAdapter` to ensure that types
+// which are registered can be converted to CEL representations.
+type TypeRegistry interface {
+ TypeAdapter
+ TypeProvider
+
+ // RegisterDescriptor registers the contents of a protocol buffer `FileDescriptor`.
+ RegisterDescriptor(fileDesc protoreflect.FileDescriptor) error
+
+ // RegisterMessage registers a protocol buffer message and its dependencies.
+ RegisterMessage(message proto.Message) error
+
+ // RegisterType registers a type value with the provider which ensures the
+ // provider is aware of how to map the type to an identifier.
+ //
+ // If a type is provided more than once with an alternative definition, the
+ // call will result in an error.
+ RegisterType(types ...Type) error
+
+ // Copy the TypeRegistry and return a new registry whose mutable state is isolated.
+ Copy() TypeRegistry
+}
+
+// FieldType represents a field's type value and whether that field supports
+// presence detection.
+type FieldType struct {
+ // Type of the field.
+ Type *exprpb.Type
+
+ // IsSet indicates whether the field is set on an input object.
+ IsSet FieldTester
+
+ // GetFrom retrieves the field value on the input object, if set.
+ GetFrom FieldGetter
+}
+
+// FieldTester is used to test field presence on an input object.
+type FieldTester func(target interface{}) bool
+
+// FieldGetter is used to get the field value from an input object, if set.
+type FieldGetter func(target interface{}) (interface{}, error)
diff --git a/vendor/github.com/google/cel-go/common/types/ref/reference.go b/vendor/github.com/google/cel-go/common/types/ref/reference.go
new file mode 100644
index 0000000000..e12169988d
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/ref/reference.go
@@ -0,0 +1,59 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package ref contains the reference interfaces used throughout the types
+// components.
+package ref
+
+import (
+ "reflect"
+)
+
+// Type interface indicate the name of a given type.
+type Type interface {
+ // HasTrait returns whether the type has a given trait associated with it.
+ //
+ // See common/types/traits/traits.go for a list of supported traits.
+ HasTrait(trait int) bool
+
+ // TypeName returns the qualified type name of the type.
+ //
+ // The type name is also used as the type's identifier name at type-check
+ // and interpretation time.
+ TypeName() string
+}
+
+// Val interface defines the functions supported by all expression values.
+// Val implementations may specialize the behavior of the value through the
+// addition of traits.
+type Val interface {
+ // ConvertToNative converts the Value to a native Go struct according to the
+ // reflected type description, or error if the conversion is not feasible.
+ ConvertToNative(typeDesc reflect.Type) (interface{}, error)
+
+ // ConvertToType supports type conversions between value types supported by
+ // the expression language.
+ ConvertToType(typeValue Type) Val
+
+ // Equal returns true if the `other` value has the same type and content as
+ // the implementing struct.
+ Equal(other Val) Val
+
+ // Type returns the TypeValue of the value.
+ Type() Type
+
+ // Value returns the raw value of the instance which may not be directly
+ // compatible with the expression language types.
+ Value() interface{}
+}
diff --git a/vendor/github.com/google/cel-go/common/types/string.go b/vendor/github.com/google/cel-go/common/types/string.go
new file mode 100644
index 0000000000..354d99b293
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/string.go
@@ -0,0 +1,221 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+ "regexp"
+ "strconv"
+ "strings"
+ "time"
+
+ "github.com/google/cel-go/common/overloads"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ wrapperspb "google.golang.org/protobuf/types/known/wrapperspb"
+)
+
+// String type implementation which supports addition, comparison, matching,
+// and size functions.
+type String string
+
+var (
+ // StringType singleton.
+ StringType = NewTypeValue("string",
+ traits.AdderType,
+ traits.ComparerType,
+ traits.MatcherType,
+ traits.ReceiverType,
+ traits.SizerType)
+
+ stringOneArgOverloads = map[string]func(String, ref.Val) ref.Val{
+ overloads.Contains: stringContains,
+ overloads.EndsWith: stringEndsWith,
+ overloads.StartsWith: stringStartsWith,
+ }
+
+ stringWrapperType = reflect.TypeOf(&wrapperspb.StringValue{})
+)
+
+// Add implements traits.Adder.Add.
+func (s String) Add(other ref.Val) ref.Val {
+ otherString, ok := other.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return s + otherString
+}
+
+// Compare implements traits.Comparer.Compare.
+func (s String) Compare(other ref.Val) ref.Val {
+ otherString, ok := other.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return Int(strings.Compare(s.Value().(string), otherString.Value().(string)))
+}
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (s String) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ switch typeDesc.Kind() {
+ case reflect.String:
+ if reflect.TypeOf(s).AssignableTo(typeDesc) {
+ return s, nil
+ }
+ return s.Value(), nil
+ case reflect.Ptr:
+ switch typeDesc {
+ case anyValueType:
+ // Primitives must be wrapped before being set on an Any field.
+ return anypb.New(wrapperspb.String(string(s)))
+ case jsonValueType:
+ // Convert to a protobuf representation of a JSON String.
+ return structpb.NewStringValue(string(s)), nil
+ case stringWrapperType:
+ // Convert to a wrapperspb.StringValue.
+ return wrapperspb.String(string(s)), nil
+ }
+ if typeDesc.Elem().Kind() == reflect.String {
+ p := s.Value().(string)
+ return &p, nil
+ }
+ case reflect.Interface:
+ sv := s.Value()
+ if reflect.TypeOf(sv).Implements(typeDesc) {
+ return sv, nil
+ }
+ if reflect.TypeOf(s).Implements(typeDesc) {
+ return s, nil
+ }
+ }
+ return nil, fmt.Errorf(
+ "unsupported native conversion from string to '%v'", typeDesc)
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (s String) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case IntType:
+ if n, err := strconv.ParseInt(s.Value().(string), 10, 64); err == nil {
+ return Int(n)
+ }
+ case UintType:
+ if n, err := strconv.ParseUint(s.Value().(string), 10, 64); err == nil {
+ return Uint(n)
+ }
+ case DoubleType:
+ if n, err := strconv.ParseFloat(s.Value().(string), 64); err == nil {
+ return Double(n)
+ }
+ case BoolType:
+ if b, err := strconv.ParseBool(s.Value().(string)); err == nil {
+ return Bool(b)
+ }
+ case BytesType:
+ return Bytes(s)
+ case DurationType:
+ if d, err := time.ParseDuration(s.Value().(string)); err == nil {
+ return durationOf(d)
+ }
+ case TimestampType:
+ if t, err := time.Parse(time.RFC3339, s.Value().(string)); err == nil {
+ if t.Unix() < minUnixTime || t.Unix() > maxUnixTime {
+ return celErrTimestampOverflow
+ }
+ return timestampOf(t)
+ }
+ case StringType:
+ return s
+ case TypeType:
+ return StringType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", StringType, typeVal)
+}
+
+// Equal implements ref.Val.Equal.
+func (s String) Equal(other ref.Val) ref.Val {
+ otherString, ok := other.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return Bool(s == otherString)
+}
+
+// Match implements traits.Matcher.Match.
+func (s String) Match(pattern ref.Val) ref.Val {
+ pat, ok := pattern.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(pattern)
+ }
+ matched, err := regexp.MatchString(pat.Value().(string), s.Value().(string))
+ if err != nil {
+ return &Err{err}
+ }
+ return Bool(matched)
+}
+
+// Receive implements traits.Reciever.Receive.
+func (s String) Receive(function string, overload string, args []ref.Val) ref.Val {
+ switch len(args) {
+ case 1:
+ if f, found := stringOneArgOverloads[function]; found {
+ return f(s, args[0])
+ }
+ }
+ return NoSuchOverloadErr()
+}
+
+// Size implements traits.Sizer.Size.
+func (s String) Size() ref.Val {
+ return Int(len([]rune(s.Value().(string))))
+}
+
+// Type implements ref.Val.Type.
+func (s String) Type() ref.Type {
+ return StringType
+}
+
+// Value implements ref.Val.Value.
+func (s String) Value() interface{} {
+ return string(s)
+}
+
+func stringContains(s String, sub ref.Val) ref.Val {
+ subStr, ok := sub.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(sub)
+ }
+ return Bool(strings.Contains(string(s), string(subStr)))
+}
+
+func stringEndsWith(s String, suf ref.Val) ref.Val {
+ sufStr, ok := suf.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(suf)
+ }
+ return Bool(strings.HasSuffix(string(s), string(sufStr)))
+}
+
+func stringStartsWith(s String, pre ref.Val) ref.Val {
+ preStr, ok := pre.(String)
+ if !ok {
+ return MaybeNoSuchOverloadErr(pre)
+ }
+ return Bool(strings.HasPrefix(string(s), string(preStr)))
+}
diff --git a/vendor/github.com/google/cel-go/common/types/timestamp.go b/vendor/github.com/google/cel-go/common/types/timestamp.go
new file mode 100644
index 0000000000..d27b6b80ab
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/timestamp.go
@@ -0,0 +1,318 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+ "strconv"
+ "strings"
+ "time"
+
+ "github.com/google/cel-go/common/overloads"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ tpb "google.golang.org/protobuf/types/known/timestamppb"
+)
+
+// Timestamp type implementation which supports add, compare, and subtract
+// operations. Timestamps are also capable of participating in dynamic
+// function dispatch to instance methods.
+type Timestamp struct {
+ time.Time
+}
+
+func timestampOf(t time.Time) Timestamp {
+ // Note that this function does not validate that time.Time is in our supported range.
+ return Timestamp{Time: t}
+}
+
+const (
+ // The number of seconds between year 1 and year 1970. This is borrowed from
+ // https://golang.org/src/time/time.go.
+ unixToInternal int64 = (1969*365 + 1969/4 - 1969/100 + 1969/400) * (60 * 60 * 24)
+
+ // Number of seconds between `0001-01-01T00:00:00Z` and the Unix epoch.
+ minUnixTime int64 = -62135596800
+ // Number of seconds between `9999-12-31T23:59:59.999999999Z` and the Unix epoch.
+ maxUnixTime int64 = 253402300799
+)
+
+var (
+ // TimestampType singleton.
+ TimestampType = NewTypeValue("google.protobuf.Timestamp",
+ traits.AdderType,
+ traits.ComparerType,
+ traits.ReceiverType,
+ traits.SubtractorType)
+)
+
+// Add implements traits.Adder.Add.
+func (t Timestamp) Add(other ref.Val) ref.Val {
+ switch other.Type() {
+ case DurationType:
+ return other.(Duration).Add(t)
+ }
+ return MaybeNoSuchOverloadErr(other)
+}
+
+// Compare implements traits.Comparer.Compare.
+func (t Timestamp) Compare(other ref.Val) ref.Val {
+ if TimestampType != other.Type() {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ ts1 := t.Time
+ ts2 := other.(Timestamp).Time
+ switch {
+ case ts1.Before(ts2):
+ return IntNegOne
+ case ts1.After(ts2):
+ return IntOne
+ default:
+ return IntZero
+ }
+}
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (t Timestamp) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ // If the timestamp is already assignable to the desired type return it.
+ if reflect.TypeOf(t.Time).AssignableTo(typeDesc) {
+ return t.Time, nil
+ }
+ if reflect.TypeOf(t).AssignableTo(typeDesc) {
+ return t, nil
+ }
+ switch typeDesc {
+ case anyValueType:
+ // Pack the underlying time as a tpb.Timestamp into an Any value.
+ return anypb.New(tpb.New(t.Time))
+ case jsonValueType:
+ // CEL follows the proto3 to JSON conversion which formats as an RFC 3339 encoded JSON
+ // string.
+ v := t.ConvertToType(StringType)
+ if IsError(v) {
+ return nil, v.(*Err)
+ }
+ return structpb.NewStringValue(string(v.(String))), nil
+ case timestampValueType:
+ // Unwrap the underlying tpb.Timestamp.
+ return tpb.New(t.Time), nil
+ }
+ return nil, fmt.Errorf("type conversion error from 'Timestamp' to '%v'", typeDesc)
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (t Timestamp) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case StringType:
+ return String(t.Format(time.RFC3339Nano))
+ case IntType:
+ // Return the Unix time in seconds since 1970
+ return Int(t.Unix())
+ case TimestampType:
+ return t
+ case TypeType:
+ return TimestampType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", TimestampType, typeVal)
+}
+
+// Equal implements ref.Val.Equal.
+func (t Timestamp) Equal(other ref.Val) ref.Val {
+ if TimestampType != other.Type() {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return Bool(t.Time.Equal(other.(Timestamp).Time))
+}
+
+// Receive implements traits.Reciever.Receive.
+func (t Timestamp) Receive(function string, overload string, args []ref.Val) ref.Val {
+ switch len(args) {
+ case 0:
+ if f, found := timestampZeroArgOverloads[function]; found {
+ return f(t.Time)
+ }
+ case 1:
+ if f, found := timestampOneArgOverloads[function]; found {
+ return f(t.Time, args[0])
+ }
+ }
+ return NoSuchOverloadErr()
+}
+
+// Subtract implements traits.Subtractor.Subtract.
+func (t Timestamp) Subtract(subtrahend ref.Val) ref.Val {
+ switch subtrahend.Type() {
+ case DurationType:
+ dur := subtrahend.(Duration)
+ val, err := subtractTimeDurationChecked(t.Time, dur.Duration)
+ if err != nil {
+ return wrapErr(err)
+ }
+ return timestampOf(val)
+ case TimestampType:
+ t2 := subtrahend.(Timestamp).Time
+ val, err := subtractTimeChecked(t.Time, t2)
+ if err != nil {
+ return wrapErr(err)
+ }
+ return durationOf(val)
+ }
+ return MaybeNoSuchOverloadErr(subtrahend)
+}
+
+// Type implements ref.Val.Type.
+func (t Timestamp) Type() ref.Type {
+ return TimestampType
+}
+
+// Value implements ref.Val.Value.
+func (t Timestamp) Value() interface{} {
+ return t.Time
+}
+
+var (
+ timestampValueType = reflect.TypeOf(&tpb.Timestamp{})
+
+ timestampZeroArgOverloads = map[string]func(time.Time) ref.Val{
+ overloads.TimeGetFullYear: timestampGetFullYear,
+ overloads.TimeGetMonth: timestampGetMonth,
+ overloads.TimeGetDayOfYear: timestampGetDayOfYear,
+ overloads.TimeGetDate: timestampGetDayOfMonthOneBased,
+ overloads.TimeGetDayOfMonth: timestampGetDayOfMonthZeroBased,
+ overloads.TimeGetDayOfWeek: timestampGetDayOfWeek,
+ overloads.TimeGetHours: timestampGetHours,
+ overloads.TimeGetMinutes: timestampGetMinutes,
+ overloads.TimeGetSeconds: timestampGetSeconds,
+ overloads.TimeGetMilliseconds: timestampGetMilliseconds}
+
+ timestampOneArgOverloads = map[string]func(time.Time, ref.Val) ref.Val{
+ overloads.TimeGetFullYear: timestampGetFullYearWithTz,
+ overloads.TimeGetMonth: timestampGetMonthWithTz,
+ overloads.TimeGetDayOfYear: timestampGetDayOfYearWithTz,
+ overloads.TimeGetDate: timestampGetDayOfMonthOneBasedWithTz,
+ overloads.TimeGetDayOfMonth: timestampGetDayOfMonthZeroBasedWithTz,
+ overloads.TimeGetDayOfWeek: timestampGetDayOfWeekWithTz,
+ overloads.TimeGetHours: timestampGetHoursWithTz,
+ overloads.TimeGetMinutes: timestampGetMinutesWithTz,
+ overloads.TimeGetSeconds: timestampGetSecondsWithTz,
+ overloads.TimeGetMilliseconds: timestampGetMillisecondsWithTz}
+)
+
+type timestampVisitor func(time.Time) ref.Val
+
+func timestampGetFullYear(t time.Time) ref.Val {
+ return Int(t.Year())
+}
+func timestampGetMonth(t time.Time) ref.Val {
+ // CEL spec indicates that the month should be 0-based, but the Time value
+ // for Month() is 1-based.
+ return Int(t.Month() - 1)
+}
+func timestampGetDayOfYear(t time.Time) ref.Val {
+ return Int(t.YearDay() - 1)
+}
+func timestampGetDayOfMonthZeroBased(t time.Time) ref.Val {
+ return Int(t.Day() - 1)
+}
+func timestampGetDayOfMonthOneBased(t time.Time) ref.Val {
+ return Int(t.Day())
+}
+func timestampGetDayOfWeek(t time.Time) ref.Val {
+ return Int(t.Weekday())
+}
+func timestampGetHours(t time.Time) ref.Val {
+ return Int(t.Hour())
+}
+func timestampGetMinutes(t time.Time) ref.Val {
+ return Int(t.Minute())
+}
+func timestampGetSeconds(t time.Time) ref.Val {
+ return Int(t.Second())
+}
+func timestampGetMilliseconds(t time.Time) ref.Val {
+ return Int(t.Nanosecond() / 1000000)
+}
+
+func timestampGetFullYearWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetFullYear)(t)
+}
+func timestampGetMonthWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetMonth)(t)
+}
+func timestampGetDayOfYearWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetDayOfYear)(t)
+}
+func timestampGetDayOfMonthZeroBasedWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetDayOfMonthZeroBased)(t)
+}
+func timestampGetDayOfMonthOneBasedWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetDayOfMonthOneBased)(t)
+}
+func timestampGetDayOfWeekWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetDayOfWeek)(t)
+}
+func timestampGetHoursWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetHours)(t)
+}
+func timestampGetMinutesWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetMinutes)(t)
+}
+func timestampGetSecondsWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetSeconds)(t)
+}
+func timestampGetMillisecondsWithTz(t time.Time, tz ref.Val) ref.Val {
+ return timeZone(tz, timestampGetMilliseconds)(t)
+}
+
+func timeZone(tz ref.Val, visitor timestampVisitor) timestampVisitor {
+ return func(t time.Time) ref.Val {
+ if StringType != tz.Type() {
+ return MaybeNoSuchOverloadErr(tz)
+ }
+ val := string(tz.(String))
+ ind := strings.Index(val, ":")
+ if ind == -1 {
+ loc, err := time.LoadLocation(val)
+ if err != nil {
+ return wrapErr(err)
+ }
+ return visitor(t.In(loc))
+ }
+
+ // If the input is not the name of a timezone (for example, 'US/Central'), it should be a numerical offset from UTC
+ // in the format ^(+|-)(0[0-9]|1[0-4]):[0-5][0-9]$. The numerical input is parsed in terms of hours and minutes.
+ hr, err := strconv.Atoi(string(val[0:ind]))
+ if err != nil {
+ return wrapErr(err)
+ }
+ min, err := strconv.Atoi(string(val[ind+1]))
+ if err != nil {
+ return wrapErr(err)
+ }
+ var offset int
+ if string(val[0]) == "-" {
+ offset = hr*60 - min
+ } else {
+ offset = hr*60 + min
+ }
+ secondsEastOfUTC := int((time.Duration(offset) * time.Minute).Seconds())
+ timezone := time.FixedZone("", secondsEastOfUTC)
+ return visitor(t.In(timezone))
+ }
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/BUILD.bazel b/vendor/github.com/google/cel-go/common/types/traits/BUILD.bazel
new file mode 100644
index 0000000000..86e54af61a
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/BUILD.bazel
@@ -0,0 +1,28 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "comparer.go",
+ "container.go",
+ "field_tester.go",
+ "indexer.go",
+ "iterator.go",
+ "lister.go",
+ "mapper.go",
+ "matcher.go",
+ "math.go",
+ "receiver.go",
+ "sizer.go",
+ "traits.go",
+ ],
+ importpath = "github.com/google/cel-go/common/types/traits",
+ deps = [
+ "//common/types/ref:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/common/types/traits/comparer.go b/vendor/github.com/google/cel-go/common/types/traits/comparer.go
new file mode 100644
index 0000000000..b531d9ae2b
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/comparer.go
@@ -0,0 +1,33 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import (
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// Comparer interface for ordering comparisons between values in order to
+// support '<', '<=', '>=', '>' overloads.
+type Comparer interface {
+ // Compare this value to the input other value, returning an Int:
+ //
+ // this < other -> Int(-1)
+ // this == other -> Int(0)
+ // this > other -> Int(1)
+ //
+ // If the comparison cannot be made or is not supported, an error should
+ // be returned.
+ Compare(other ref.Val) ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/container.go b/vendor/github.com/google/cel-go/common/types/traits/container.go
new file mode 100644
index 0000000000..cf5c621ae9
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/container.go
@@ -0,0 +1,23 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import "github.com/google/cel-go/common/types/ref"
+
+// Container interface which permits containment tests such as 'a in b'.
+type Container interface {
+ // Contains returns true if the value exists within the object.
+ Contains(value ref.Val) ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/field_tester.go b/vendor/github.com/google/cel-go/common/types/traits/field_tester.go
new file mode 100644
index 0000000000..816a956523
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/field_tester.go
@@ -0,0 +1,30 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import (
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// FieldTester indicates if a defined field on an object type is set to a
+// non-default value.
+//
+// For use with the `has()` macro.
+type FieldTester interface {
+ // IsSet returns true if the field is defined and set to a non-default
+ // value. The method will return false if defined and not set, and an error
+ // if the field is not defined.
+ IsSet(field ref.Val) ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/indexer.go b/vendor/github.com/google/cel-go/common/types/traits/indexer.go
new file mode 100644
index 0000000000..662c6836c3
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/indexer.go
@@ -0,0 +1,25 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import (
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// Indexer permits random access of elements by index 'a[b()]'.
+type Indexer interface {
+ // Get the value at the specified index or error.
+ Get(index ref.Val) ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/iterator.go b/vendor/github.com/google/cel-go/common/types/traits/iterator.go
new file mode 100644
index 0000000000..42dd371aa4
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/iterator.go
@@ -0,0 +1,36 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import (
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// Iterable aggregate types permit traversal over their elements.
+type Iterable interface {
+ // Iterator returns a new iterator view of the struct.
+ Iterator() Iterator
+}
+
+// Iterator permits safe traversal over the contents of an aggregate type.
+type Iterator interface {
+ ref.Val
+
+ // HasNext returns true if there are unvisited elements in the Iterator.
+ HasNext() ref.Val
+
+ // Next returns the next element.
+ Next() ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/lister.go b/vendor/github.com/google/cel-go/common/types/traits/lister.go
new file mode 100644
index 0000000000..7b05c301d5
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/lister.go
@@ -0,0 +1,27 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import "github.com/google/cel-go/common/types/ref"
+
+// Lister interface which aggregates the traits of a list.
+type Lister interface {
+ ref.Val
+ Adder
+ Container
+ Indexer
+ Iterable
+ Sizer
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/mapper.go b/vendor/github.com/google/cel-go/common/types/traits/mapper.go
new file mode 100644
index 0000000000..2f7c919a8b
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/mapper.go
@@ -0,0 +1,33 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import "github.com/google/cel-go/common/types/ref"
+
+// Mapper interface which aggregates the traits of a maps.
+type Mapper interface {
+ ref.Val
+ Container
+ Indexer
+ Iterable
+ Sizer
+
+ // Find returns a value, if one exists, for the input key.
+ //
+ // If the key is not found the function returns (nil, false).
+ // If the input key is not valid for the map, or is Err or Unknown the function returns
+ // (Unknown|Err, false).
+ Find(key ref.Val) (ref.Val, bool)
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/matcher.go b/vendor/github.com/google/cel-go/common/types/traits/matcher.go
new file mode 100644
index 0000000000..085dc94ff4
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/matcher.go
@@ -0,0 +1,23 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import "github.com/google/cel-go/common/types/ref"
+
+// Matcher interface for supporting 'matches()' overloads.
+type Matcher interface {
+ // Match returns true if the pattern matches the current value.
+ Match(pattern ref.Val) ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/math.go b/vendor/github.com/google/cel-go/common/types/traits/math.go
new file mode 100644
index 0000000000..86d5b9137e
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/math.go
@@ -0,0 +1,62 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import "github.com/google/cel-go/common/types/ref"
+
+// Adder interface to support '+' operator overloads.
+type Adder interface {
+ // Add returns a combination of the current value and other value.
+ //
+ // If the other value is an unsupported type, an error is returned.
+ Add(other ref.Val) ref.Val
+}
+
+// Divider interface to support '/' operator overloads.
+type Divider interface {
+ // Divide returns the result of dividing the current value by the input
+ // denominator.
+ //
+ // A denominator value of zero results in an error.
+ Divide(denominator ref.Val) ref.Val
+}
+
+// Modder interface to support '%' operator overloads.
+type Modder interface {
+ // Modulo returns the result of taking the modulus of the current value
+ // by the denominator.
+ //
+ // A denominator value of zero results in an error.
+ Modulo(denominator ref.Val) ref.Val
+}
+
+// Multiplier interface to support '*' operator overloads.
+type Multiplier interface {
+ // Multiply returns the result of multiplying the current and input value.
+ Multiply(other ref.Val) ref.Val
+}
+
+// Negater interface to support unary '-' and '!' operator overloads.
+type Negater interface {
+ // Negate returns the complement of the current value.
+ Negate() ref.Val
+}
+
+// Subtractor interface to support binary '-' operator overloads.
+type Subtractor interface {
+ // Subtract returns the result of subtracting the input from the current
+ // value.
+ Subtract(subtrahend ref.Val) ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/receiver.go b/vendor/github.com/google/cel-go/common/types/traits/receiver.go
new file mode 100644
index 0000000000..8f41db45e8
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/receiver.go
@@ -0,0 +1,24 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import "github.com/google/cel-go/common/types/ref"
+
+// Receiver interface for routing instance method calls within a value.
+type Receiver interface {
+ // Receive accepts a function name, overload id, and arguments and returns
+ // a value.
+ Receive(function string, overload string, args []ref.Val) ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/sizer.go b/vendor/github.com/google/cel-go/common/types/traits/sizer.go
new file mode 100644
index 0000000000..b80d25137a
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/sizer.go
@@ -0,0 +1,25 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package traits
+
+import (
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// Sizer interface for supporting 'size()' overloads.
+type Sizer interface {
+ // Size returns the number of elements or length of the value.
+ Size() ref.Val
+}
diff --git a/vendor/github.com/google/cel-go/common/types/traits/traits.go b/vendor/github.com/google/cel-go/common/types/traits/traits.go
new file mode 100644
index 0000000000..6da3e6a3e1
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/traits/traits.go
@@ -0,0 +1,64 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package traits defines interfaces that a type may implement to participate
+// in operator overloads and function dispatch.
+package traits
+
+const (
+ // AdderType types provide a '+' operator overload.
+ AdderType = 1 << iota
+
+ // ComparerType types support ordering comparisons '<', '<=', '>', '>='.
+ ComparerType
+
+ // ContainerType types support 'in' operations.
+ ContainerType
+
+ // DividerType types support '/' operations.
+ DividerType
+
+ // FieldTesterType types support the detection of field value presence.
+ FieldTesterType
+
+ // IndexerType types support index access with dynamic values.
+ IndexerType
+
+ // IterableType types can be iterated over in comprehensions.
+ IterableType
+
+ // IteratorType types support iterator semantics.
+ IteratorType
+
+ // MatcherType types support pattern matching via 'matches' method.
+ MatcherType
+
+ // ModderType types support modulus operations '%'
+ ModderType
+
+ // MultiplierType types support '*' operations.
+ MultiplierType
+
+ // NegatorType types support either negation via '!' or '-'
+ NegatorType
+
+ // ReceiverType types support dynamic dispatch to instance methods.
+ ReceiverType
+
+ // SizerType types support the size() method.
+ SizerType
+
+ // SubtractorType type support '-' operations.
+ SubtractorType
+)
diff --git a/vendor/github.com/google/cel-go/common/types/type.go b/vendor/github.com/google/cel-go/common/types/type.go
new file mode 100644
index 0000000000..a7253270a9
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/type.go
@@ -0,0 +1,104 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+)
+
+var (
+ // TypeType is the type of a TypeValue.
+ TypeType = NewTypeValue("type")
+)
+
+// TypeValue is an instance of a Value that describes a value's type.
+type TypeValue struct {
+ name string
+ traitMask int
+}
+
+// NewTypeValue returns *TypeValue which is both a ref.Type and ref.Val.
+func NewTypeValue(name string, traits ...int) *TypeValue {
+ traitMask := 0
+ for _, trait := range traits {
+ traitMask |= trait
+ }
+ return &TypeValue{
+ name: name,
+ traitMask: traitMask}
+}
+
+// NewObjectTypeValue returns a *TypeValue based on the input name, which is
+// annotated with the traits relevant to all objects.
+func NewObjectTypeValue(name string) *TypeValue {
+ return NewTypeValue(name,
+ traits.FieldTesterType,
+ traits.IndexerType)
+}
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (t *TypeValue) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ // TODO: replace the internal type representation with a proto-value.
+ return nil, fmt.Errorf("type conversion not supported for 'type'")
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (t *TypeValue) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case TypeType:
+ return TypeType
+ case StringType:
+ return String(t.TypeName())
+ }
+ return NewErr("type conversion error from '%s' to '%s'", TypeType, typeVal)
+}
+
+// Equal implements ref.Val.Equal.
+func (t *TypeValue) Equal(other ref.Val) ref.Val {
+ if TypeType != other.Type() {
+ return ValOrErr(other, "no such overload")
+ }
+ return Bool(t.TypeName() == other.(ref.Type).TypeName())
+}
+
+// HasTrait indicates whether the type supports the given trait.
+// Trait codes are defined in the traits package, e.g. see traits.AdderType.
+func (t *TypeValue) HasTrait(trait int) bool {
+ return trait&t.traitMask == trait
+}
+
+// String implements fmt.Stringer.
+func (t *TypeValue) String() string {
+ return t.name
+}
+
+// Type implements ref.Val.Type.
+func (t *TypeValue) Type() ref.Type {
+ return TypeType
+}
+
+// TypeName gives the type's name as a string.
+func (t *TypeValue) TypeName() string {
+ return t.name
+}
+
+// Value implements ref.Val.Value.
+func (t *TypeValue) Value() interface{} {
+ return t.name
+}
diff --git a/vendor/github.com/google/cel-go/common/types/uint.go b/vendor/github.com/google/cel-go/common/types/uint.go
new file mode 100644
index 0000000000..d8d0f24cc9
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/uint.go
@@ -0,0 +1,238 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "fmt"
+ "reflect"
+ "strconv"
+
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ wrapperspb "google.golang.org/protobuf/types/known/wrapperspb"
+)
+
+// Uint type implementation which supports comparison and math operators.
+type Uint uint64
+
+var (
+ // UintType singleton.
+ UintType = NewTypeValue("uint",
+ traits.AdderType,
+ traits.ComparerType,
+ traits.DividerType,
+ traits.ModderType,
+ traits.MultiplierType,
+ traits.SubtractorType)
+
+ uint32WrapperType = reflect.TypeOf(&wrapperspb.UInt32Value{})
+
+ uint64WrapperType = reflect.TypeOf(&wrapperspb.UInt64Value{})
+)
+
+// Uint constants
+const (
+ uintZero = Uint(0)
+)
+
+// Add implements traits.Adder.Add.
+func (i Uint) Add(other ref.Val) ref.Val {
+ otherUint, ok := other.(Uint)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ val, err := addUint64Checked(uint64(i), uint64(otherUint))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Uint(val)
+}
+
+// Compare implements traits.Comparer.Compare.
+func (i Uint) Compare(other ref.Val) ref.Val {
+ otherUint, ok := other.(Uint)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ if i < otherUint {
+ return IntNegOne
+ }
+ if i > otherUint {
+ return IntOne
+ }
+ return IntZero
+}
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (i Uint) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ switch typeDesc.Kind() {
+ case reflect.Uint, reflect.Uint32:
+ v, err := uint64ToUint32Checked(uint64(i))
+ if err != nil {
+ return 0, err
+ }
+ return reflect.ValueOf(v).Convert(typeDesc).Interface(), nil
+ case reflect.Uint64:
+ return reflect.ValueOf(i).Convert(typeDesc).Interface(), nil
+ case reflect.Ptr:
+ switch typeDesc {
+ case anyValueType:
+ // Primitives must be wrapped before being set on an Any field.
+ return anypb.New(wrapperspb.UInt64(uint64(i)))
+ case jsonValueType:
+ // JSON can accurately represent 32-bit uints as floating point values.
+ if i.isJSONSafe() {
+ return structpb.NewNumberValue(float64(i)), nil
+ }
+ // Proto3 to JSON conversion requires string-formatted uint64 values
+ // since the conversion to floating point would result in truncation.
+ return structpb.NewStringValue(strconv.FormatUint(uint64(i), 10)), nil
+ case uint32WrapperType:
+ // Convert the value to a wrapperspb.UInt32Value, error on overflow.
+ v, err := uint64ToUint32Checked(uint64(i))
+ if err != nil {
+ return 0, err
+ }
+ return wrapperspb.UInt32(v), nil
+ case uint64WrapperType:
+ // Convert the value to a wrapperspb.UInt64Value.
+ return wrapperspb.UInt64(uint64(i)), nil
+ }
+ switch typeDesc.Elem().Kind() {
+ case reflect.Uint32:
+ v, err := uint64ToUint32Checked(uint64(i))
+ if err != nil {
+ return 0, err
+ }
+ p := reflect.New(typeDesc.Elem())
+ p.Elem().Set(reflect.ValueOf(v).Convert(typeDesc.Elem()))
+ return p.Interface(), nil
+ case reflect.Uint64:
+ v := uint64(i)
+ p := reflect.New(typeDesc.Elem())
+ p.Elem().Set(reflect.ValueOf(v).Convert(typeDesc.Elem()))
+ return p.Interface(), nil
+ }
+ case reflect.Interface:
+ iv := i.Value()
+ if reflect.TypeOf(iv).Implements(typeDesc) {
+ return iv, nil
+ }
+ if reflect.TypeOf(i).Implements(typeDesc) {
+ return i, nil
+ }
+ }
+ return nil, fmt.Errorf("unsupported type conversion from 'uint' to %v", typeDesc)
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (i Uint) ConvertToType(typeVal ref.Type) ref.Val {
+ switch typeVal {
+ case IntType:
+ v, err := uint64ToInt64Checked(uint64(i))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Int(v)
+ case UintType:
+ return i
+ case DoubleType:
+ return Double(i)
+ case StringType:
+ return String(fmt.Sprintf("%d", uint64(i)))
+ case TypeType:
+ return UintType
+ }
+ return NewErr("type conversion error from '%s' to '%s'", UintType, typeVal)
+}
+
+// Divide implements traits.Divider.Divide.
+func (i Uint) Divide(other ref.Val) ref.Val {
+ otherUint, ok := other.(Uint)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ div, err := divideUint64Checked(uint64(i), uint64(otherUint))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Uint(div)
+}
+
+// Equal implements ref.Val.Equal.
+func (i Uint) Equal(other ref.Val) ref.Val {
+ otherUint, ok := other.(Uint)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ return Bool(i == otherUint)
+}
+
+// Modulo implements traits.Modder.Modulo.
+func (i Uint) Modulo(other ref.Val) ref.Val {
+ otherUint, ok := other.(Uint)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ mod, err := moduloUint64Checked(uint64(i), uint64(otherUint))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Uint(mod)
+}
+
+// Multiply implements traits.Multiplier.Multiply.
+func (i Uint) Multiply(other ref.Val) ref.Val {
+ otherUint, ok := other.(Uint)
+ if !ok {
+ return MaybeNoSuchOverloadErr(other)
+ }
+ val, err := multiplyUint64Checked(uint64(i), uint64(otherUint))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Uint(val)
+}
+
+// Subtract implements traits.Subtractor.Subtract.
+func (i Uint) Subtract(subtrahend ref.Val) ref.Val {
+ subtraUint, ok := subtrahend.(Uint)
+ if !ok {
+ return MaybeNoSuchOverloadErr(subtrahend)
+ }
+ val, err := subtractUint64Checked(uint64(i), uint64(subtraUint))
+ if err != nil {
+ return wrapErr(err)
+ }
+ return Uint(val)
+}
+
+// Type implements ref.Val.Type.
+func (i Uint) Type() ref.Type {
+ return UintType
+}
+
+// Value implements ref.Val.Value.
+func (i Uint) Value() interface{} {
+ return uint64(i)
+}
+
+// isJSONSafe indicates whether the uint is safely representable as a floating point value in JSON.
+func (i Uint) isJSONSafe() bool {
+ return i <= maxIntJSON
+}
diff --git a/vendor/github.com/google/cel-go/common/types/unknown.go b/vendor/github.com/google/cel-go/common/types/unknown.go
new file mode 100644
index 0000000000..a950920d60
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/unknown.go
@@ -0,0 +1,61 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "reflect"
+
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// Unknown type implementation which collects expression ids which caused the
+// current value to become unknown.
+type Unknown []int64
+
+var (
+ // UnknownType singleton.
+ UnknownType = NewTypeValue("unknown")
+)
+
+// ConvertToNative implements ref.Val.ConvertToNative.
+func (u Unknown) ConvertToNative(typeDesc reflect.Type) (interface{}, error) {
+ return u.Value(), nil
+}
+
+// ConvertToType implements ref.Val.ConvertToType.
+func (u Unknown) ConvertToType(typeVal ref.Type) ref.Val {
+ return u
+}
+
+// Equal implements ref.Val.Equal.
+func (u Unknown) Equal(other ref.Val) ref.Val {
+ return u
+}
+
+// Type implements ref.Val.Type.
+func (u Unknown) Type() ref.Type {
+ return UnknownType
+}
+
+// Value implements ref.Val.Value.
+func (u Unknown) Value() interface{} {
+ return []int64(u)
+}
+
+// IsUnknown returns whether the element ref.Type or ref.Val is equal to the
+// UnknownType singleton.
+func IsUnknown(val ref.Val) bool {
+ return val.Type() == UnknownType
+}
diff --git a/vendor/github.com/google/cel-go/common/types/util.go b/vendor/github.com/google/cel-go/common/types/util.go
new file mode 100644
index 0000000000..761c512d73
--- /dev/null
+++ b/vendor/github.com/google/cel-go/common/types/util.go
@@ -0,0 +1,38 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package types
+
+import (
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// IsUnknownOrError returns whether the input element ref.Val is an ErrType or UnknonwType.
+func IsUnknownOrError(val ref.Val) bool {
+ switch val.Type() {
+ case UnknownType, ErrType:
+ return true
+ }
+ return false
+}
+
+// IsPrimitiveType returns whether the input element ref.Val is a primitive type.
+// Note, primitive types do not include well-known types such as Duration and Timestamp.
+func IsPrimitiveType(val ref.Val) bool {
+ switch val.Type() {
+ case BoolType, BytesType, DoubleType, IntType, StringType, UintType:
+ return true
+ }
+ return false
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/BUILD.bazel b/vendor/github.com/google/cel-go/interpreter/BUILD.bazel
new file mode 100644
index 0000000000..2f4079fa04
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/BUILD.bazel
@@ -0,0 +1,70 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "activation.go",
+ "attribute_patterns.go",
+ "attributes.go",
+ "coster.go",
+ "decorators.go",
+ "dispatcher.go",
+ "evalstate.go",
+ "interpretable.go",
+ "interpreter.go",
+ "planner.go",
+ "prune.go",
+ ],
+ importpath = "github.com/google/cel-go/interpreter",
+ deps = [
+ "//common:go_default_library",
+ "//common/containers:go_default_library",
+ "//common/operators:go_default_library",
+ "//common/overloads:go_default_library",
+ "//common/types:go_default_library",
+ "//common/types/ref:go_default_library",
+ "//common/types/traits:go_default_library",
+ "//interpreter/functions:go_default_library",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//proto:go_default_library",
+ "@org_golang_google_protobuf//types/known/durationpb:go_default_library",
+ "@org_golang_google_protobuf//types/known/structpb:go_default_library",
+ "@org_golang_google_protobuf//types/known/timestamppb:go_default_library",
+ "@org_golang_google_protobuf//types/known/wrapperspb:go_default_library",
+ ],
+)
+
+go_test(
+ name = "go_default_test",
+ srcs = [
+ "activation_test.go",
+ "attribute_patterns_test.go",
+ "attributes_test.go",
+ "interpreter_test.go",
+ "prune_test.go",
+ ],
+ embed = [
+ ":go_default_library",
+ ],
+ deps = [
+ "//checker:go_default_library",
+ "//checker/decls:go_default_library",
+ "//common/containers:go_default_library",
+ "//common/debug:go_default_library",
+ "//common/operators:go_default_library",
+ "//common/types:go_default_library",
+ "//interpreter/functions:go_default_library",
+ "//parser:go_default_library",
+ "//test:go_default_library",
+ "//test/proto2pb:go_default_library",
+ "//test/proto3pb:go_default_library",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//proto:go_default_library",
+ "@org_golang_google_protobuf//types/known/anypb:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/interpreter/activation.go b/vendor/github.com/google/cel-go/interpreter/activation.go
new file mode 100644
index 0000000000..4f13151997
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/activation.go
@@ -0,0 +1,197 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "errors"
+ "fmt"
+ "sync"
+
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// Activation used to resolve identifiers by name and references by id.
+//
+// An Activation is the primary mechanism by which a caller supplies input into a CEL program.
+type Activation interface {
+ // ResolveName returns a value from the activation by qualified name, or false if the name
+ // could not be found.
+ ResolveName(name string) (interface{}, bool)
+
+ // Parent returns the parent of the current activation, may be nil.
+ // If non-nil, the parent will be searched during resolve calls.
+ Parent() Activation
+}
+
+// EmptyActivation returns a variable free activation.
+func EmptyActivation() Activation {
+ // This call cannot fail.
+ a, _ := NewActivation(map[string]interface{}{})
+ return a
+}
+
+// NewActivation returns an activation based on a map-based binding where the map keys are
+// expected to be qualified names used with ResolveName calls.
+//
+// The input `bindings` may either be of type `Activation` or `map[string]interface{}`.
+//
+// Lazy bindings may be supplied within the map-based input in either of the following forms:
+// - func() interface{}
+// - func() ref.Val
+//
+// The output of the lazy binding will overwrite the variable reference in the internal map.
+//
+// Values which are not represented as ref.Val types on input may be adapted to a ref.Val using
+// the ref.TypeAdapter configured in the environment.
+func NewActivation(bindings interface{}) (Activation, error) {
+ if bindings == nil {
+ return nil, errors.New("bindings must be non-nil")
+ }
+ a, isActivation := bindings.(Activation)
+ if isActivation {
+ return a, nil
+ }
+ m, isMap := bindings.(map[string]interface{})
+ if !isMap {
+ return nil, fmt.Errorf(
+ "activation input must be an activation or map[string]interface: got %T",
+ bindings)
+ }
+ return &mapActivation{bindings: m}, nil
+}
+
+// mapActivation which implements Activation and maps of named values.
+//
+// Named bindings may lazily supply values by providing a function which accepts no arguments and
+// produces an interface value.
+type mapActivation struct {
+ bindings map[string]interface{}
+}
+
+// Parent implements the Activation interface method.
+func (a *mapActivation) Parent() Activation {
+ return nil
+}
+
+// ResolveName implements the Activation interface method.
+func (a *mapActivation) ResolveName(name string) (interface{}, bool) {
+ obj, found := a.bindings[name]
+ if !found {
+ return nil, false
+ }
+ fn, isLazy := obj.(func() ref.Val)
+ if isLazy {
+ obj = fn()
+ a.bindings[name] = obj
+ }
+ fnRaw, isLazy := obj.(func() interface{})
+ if isLazy {
+ obj = fnRaw()
+ a.bindings[name] = obj
+ }
+ return obj, found
+}
+
+// hierarchicalActivation which implements Activation and contains a parent and
+// child activation.
+type hierarchicalActivation struct {
+ parent Activation
+ child Activation
+}
+
+// Parent implements the Activation interface method.
+func (a *hierarchicalActivation) Parent() Activation {
+ return a.parent
+}
+
+// ResolveName implements the Activation interface method.
+func (a *hierarchicalActivation) ResolveName(name string) (interface{}, bool) {
+ if object, found := a.child.ResolveName(name); found {
+ return object, found
+ }
+ return a.parent.ResolveName(name)
+}
+
+// NewHierarchicalActivation takes two activations and produces a new one which prioritizes
+// resolution in the child first and parent(s) second.
+func NewHierarchicalActivation(parent Activation, child Activation) Activation {
+ return &hierarchicalActivation{parent, child}
+}
+
+// NewPartialActivation returns an Activation which contains a list of AttributePattern values
+// representing field and index operations that should result in a 'types.Unknown' result.
+//
+// The `bindings` value may be any value type supported by the interpreter.NewActivation call,
+// but is typically either an existing Activation or map[string]interface{}.
+func NewPartialActivation(bindings interface{},
+ unknowns ...*AttributePattern) (PartialActivation, error) {
+ a, err := NewActivation(bindings)
+ if err != nil {
+ return nil, err
+ }
+ return &partActivation{Activation: a, unknowns: unknowns}, nil
+}
+
+// PartialActivation extends the Activation interface with a set of UnknownAttributePatterns.
+type PartialActivation interface {
+ Activation
+
+ // UnknownAttributePaths returns a set of AttributePattern values which match Attribute
+ // expressions for data accesses whose values are not yet known.
+ UnknownAttributePatterns() []*AttributePattern
+}
+
+// partActivation is the default implementations of the PartialActivation interface.
+type partActivation struct {
+ Activation
+ unknowns []*AttributePattern
+}
+
+// UnknownAttributePatterns implements the PartialActivation interface method.
+func (a *partActivation) UnknownAttributePatterns() []*AttributePattern {
+ return a.unknowns
+}
+
+// varActivation represents a single mutable variable binding.
+//
+// This activation type should only be used within folds as the fold loop controls the object
+// life-cycle.
+type varActivation struct {
+ parent Activation
+ name string
+ val ref.Val
+}
+
+// Parent implements the Activation interface method.
+func (v *varActivation) Parent() Activation {
+ return v.parent
+}
+
+// ResolveName implements the Activation interface method.
+func (v *varActivation) ResolveName(name string) (interface{}, bool) {
+ if name == v.name {
+ return v.val, true
+ }
+ return v.parent.ResolveName(name)
+}
+
+var (
+ // pool of var activations to reduce allocations during folds.
+ varActivationPool = &sync.Pool{
+ New: func() interface{} {
+ return &varActivation{}
+ },
+ }
+)
diff --git a/vendor/github.com/google/cel-go/interpreter/attribute_patterns.go b/vendor/github.com/google/cel-go/interpreter/attribute_patterns.go
new file mode 100644
index 0000000000..3633255d23
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/attribute_patterns.go
@@ -0,0 +1,383 @@
+// Copyright 2020 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "fmt"
+
+ "github.com/google/cel-go/common/containers"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// AttributePattern represents a top-level variable with an optional set of qualifier patterns.
+//
+// When using a CEL expression within a container, e.g. a package or namespace, the variable name
+// in the pattern must match the qualified name produced during the variable namespace resolution.
+// For example, if variable `c` appears in an expression whose container is `a.b`, the variable
+// name supplied to the pattern must be `a.b.c`
+//
+// The qualifier patterns for attribute matching must be one of the following:
+//
+// - valid map key type: string, int, uint, bool
+// - wildcard (*)
+//
+// Examples:
+//
+// 1. ns.myvar["complex-value"]
+// 2. ns.myvar["complex-value"][0]
+// 3. ns.myvar["complex-value"].*.name
+//
+// The first example is simple: match an attribute where the variable is 'ns.myvar' with a
+// field access on 'complex-value'. The second example expands the match to indicate that only
+// a specific index `0` should match. And lastly, the third example matches any indexed access
+// that later selects the 'name' field.
+type AttributePattern struct {
+ variable string
+ qualifierPatterns []*AttributeQualifierPattern
+}
+
+// NewAttributePattern produces a new mutable AttributePattern based on a variable name.
+func NewAttributePattern(variable string) *AttributePattern {
+ return &AttributePattern{
+ variable: variable,
+ qualifierPatterns: []*AttributeQualifierPattern{},
+ }
+}
+
+// QualString adds a string qualifier pattern to the AttributePattern. The string may be a valid
+// identifier, or string map key including empty string.
+func (apat *AttributePattern) QualString(pattern string) *AttributePattern {
+ apat.qualifierPatterns = append(apat.qualifierPatterns,
+ &AttributeQualifierPattern{value: pattern})
+ return apat
+}
+
+// QualInt adds an int qualifier pattern to the AttributePattern. The index may be either a map or
+// list index.
+func (apat *AttributePattern) QualInt(pattern int64) *AttributePattern {
+ apat.qualifierPatterns = append(apat.qualifierPatterns,
+ &AttributeQualifierPattern{value: pattern})
+ return apat
+}
+
+// QualUint adds an uint qualifier pattern for a map index operation to the AttributePattern.
+func (apat *AttributePattern) QualUint(pattern uint64) *AttributePattern {
+ apat.qualifierPatterns = append(apat.qualifierPatterns,
+ &AttributeQualifierPattern{value: pattern})
+ return apat
+}
+
+// QualBool adds a bool qualifier pattern for a map index operation to the AttributePattern.
+func (apat *AttributePattern) QualBool(pattern bool) *AttributePattern {
+ apat.qualifierPatterns = append(apat.qualifierPatterns,
+ &AttributeQualifierPattern{value: pattern})
+ return apat
+}
+
+// Wildcard adds a special sentinel qualifier pattern that will match any single qualifier.
+func (apat *AttributePattern) Wildcard() *AttributePattern {
+ apat.qualifierPatterns = append(apat.qualifierPatterns,
+ &AttributeQualifierPattern{wildcard: true})
+ return apat
+}
+
+// VariableMatches returns true if the fully qualified variable matches the AttributePattern
+// fully qualified variable name.
+func (apat *AttributePattern) VariableMatches(variable string) bool {
+ return apat.variable == variable
+}
+
+// QualifierPatterns returns the set of AttributeQualifierPattern values on the AttributePattern.
+func (apat *AttributePattern) QualifierPatterns() []*AttributeQualifierPattern {
+ return apat.qualifierPatterns
+}
+
+// AttributeQualifierPattern holds a wilcard or valued qualifier pattern.
+type AttributeQualifierPattern struct {
+ wildcard bool
+ value interface{}
+}
+
+// Matches returns true if the qualifier pattern is a wildcard, or the Qualifier implements the
+// qualifierValueEquator interface and its IsValueEqualTo returns true for the qualifier pattern.
+func (qpat *AttributeQualifierPattern) Matches(q Qualifier) bool {
+ if qpat.wildcard {
+ return true
+ }
+ qve, ok := q.(qualifierValueEquator)
+ return ok && qve.QualifierValueEquals(qpat.value)
+}
+
+// qualifierValueEquator defines an interface for determining if an input value, of valid map key
+// type, is equal to the value held in the Qualifier. This interface is used by the
+// AttributeQualifierPattern to determine pattern matches for non-wildcard qualifier patterns.
+//
+// Note: Attribute values are also Qualifier values; however, Attriutes are resolved before
+// qualification happens. This is an implementation detail, but one relevant to why the Attribute
+// types do not surface in the list of implementations.
+//
+// See: partialAttributeFactory.matchesUnknownPatterns for more details on how this interface is
+// used.
+type qualifierValueEquator interface {
+ // QualifierValueEquals returns true if the input value is equal to the value held in the
+ // Qualifier.
+ QualifierValueEquals(value interface{}) bool
+}
+
+// QualifierValueEquals implementation for boolean qualifiers.
+func (q *boolQualifier) QualifierValueEquals(value interface{}) bool {
+ bval, ok := value.(bool)
+ return ok && q.value == bval
+}
+
+// QualifierValueEquals implementation for field qualifiers.
+func (q *fieldQualifier) QualifierValueEquals(value interface{}) bool {
+ sval, ok := value.(string)
+ return ok && q.Name == sval
+}
+
+// QualifierValueEquals implementation for string qualifiers.
+func (q *stringQualifier) QualifierValueEquals(value interface{}) bool {
+ sval, ok := value.(string)
+ return ok && q.value == sval
+}
+
+// QualifierValueEquals implementation for int qualifiers.
+func (q *intQualifier) QualifierValueEquals(value interface{}) bool {
+ ival, ok := value.(int64)
+ return ok && q.value == ival
+}
+
+// QualifierValueEquals implementation for uint qualifiers.
+func (q *uintQualifier) QualifierValueEquals(value interface{}) bool {
+ uval, ok := value.(uint64)
+ return ok && q.value == uval
+}
+
+// NewPartialAttributeFactory returns an AttributeFactory implementation capable of performing
+// AttributePattern matches with PartialActivation inputs.
+func NewPartialAttributeFactory(container *containers.Container,
+ adapter ref.TypeAdapter,
+ provider ref.TypeProvider) AttributeFactory {
+ fac := NewAttributeFactory(container, adapter, provider)
+ return &partialAttributeFactory{
+ AttributeFactory: fac,
+ container: container,
+ adapter: adapter,
+ provider: provider,
+ }
+}
+
+type partialAttributeFactory struct {
+ AttributeFactory
+ container *containers.Container
+ adapter ref.TypeAdapter
+ provider ref.TypeProvider
+}
+
+// AbsoluteAttribute implementation of the AttributeFactory interface which wraps the
+// NamespacedAttribute resolution in an internal attributeMatcher object to dynamically match
+// unknown patterns from PartialActivation inputs if given.
+func (fac *partialAttributeFactory) AbsoluteAttribute(id int64, names ...string) NamespacedAttribute {
+ attr := fac.AttributeFactory.AbsoluteAttribute(id, names...)
+ return &attributeMatcher{fac: fac, NamespacedAttribute: attr}
+}
+
+// MaybeAttribute implementation of the AttributeFactory interface which ensure that the set of
+// 'maybe' NamespacedAttribute values are produced using the PartialAttributeFactory rather than
+// the base AttributeFactory implementation.
+func (fac *partialAttributeFactory) MaybeAttribute(id int64, name string) Attribute {
+ return &maybeAttribute{
+ id: id,
+ attrs: []NamespacedAttribute{
+ fac.AbsoluteAttribute(id, fac.container.ResolveCandidateNames(name)...),
+ },
+ adapter: fac.adapter,
+ provider: fac.provider,
+ fac: fac,
+ }
+}
+
+// matchesUnknownPatterns returns true if the variable names and qualifiers for a given
+// Attribute value match any of the ActivationPattern objects in the set of unknown activation
+// patterns on the given PartialActivation.
+//
+// For example, in the expression `a.b`, the Attribute is composed of variable `a`, with string
+// qualifier `b`. When a PartialActivation is supplied, it indicates that some or all of the data
+// provided in the input is unknown by specifying unknown AttributePatterns. An AttributePattern
+// that refers to variable `a` with a string qualifier of `c` will not match `a.b`; however, any
+// of the following patterns will match Attribute `a.b`:
+//
+// - `AttributePattern("a")`
+// - `AttributePattern("a").Wildcard()`
+// - `AttributePattern("a").QualString("b")`
+// - `AttributePattern("a").QualString("b").QualInt(0)`
+//
+// Any AttributePattern which overlaps an Attribute or vice-versa will produce an Unknown result
+// for the last pattern matched variable or qualifier in the Attribute. In the first matching
+// example, the expression id representing variable `a` would be listed in the Unknown result,
+// whereas in the other pattern examples, the qualifier `b` would be returned as the Unknown.
+func (fac *partialAttributeFactory) matchesUnknownPatterns(
+ vars PartialActivation,
+ attrID int64,
+ variableNames []string,
+ qualifiers []Qualifier) (types.Unknown, error) {
+ patterns := vars.UnknownAttributePatterns()
+ candidateIndices := map[int]struct{}{}
+ for _, variable := range variableNames {
+ for i, pat := range patterns {
+ if pat.VariableMatches(variable) {
+ candidateIndices[i] = struct{}{}
+ }
+ }
+ }
+ // Determine whether to return early if there are no candidate unknown patterns.
+ if len(candidateIndices) == 0 {
+ return nil, nil
+ }
+ // Determine whether to return early if there are no qualifiers.
+ if len(qualifiers) == 0 {
+ return types.Unknown{attrID}, nil
+ }
+ // Resolve the attribute qualifiers into a static set. This prevents more dynamic
+ // Attribute resolutions than necessary when there are multiple unknown patterns
+ // that traverse the same Attribute-based qualifier field.
+ newQuals := make([]Qualifier, len(qualifiers))
+ for i, qual := range qualifiers {
+ attr, isAttr := qual.(Attribute)
+ if isAttr {
+ val, err := attr.Resolve(vars)
+ if err != nil {
+ return nil, err
+ }
+ unk, isUnk := val.(types.Unknown)
+ if isUnk {
+ return unk, nil
+ }
+ // If this resolution behavior ever changes, new implementations of the
+ // qualifierValueEquator may be required to handle proper resolution.
+ qual, err = fac.NewQualifier(nil, qual.ID(), val)
+ if err != nil {
+ return nil, err
+ }
+ }
+ newQuals[i] = qual
+ }
+ // Determine whether any of the unknown patterns match.
+ for patIdx := range candidateIndices {
+ pat := patterns[patIdx]
+ isUnk := true
+ matchExprID := attrID
+ qualPats := pat.QualifierPatterns()
+ for i, qual := range newQuals {
+ if i >= len(qualPats) {
+ break
+ }
+ matchExprID = qual.ID()
+ qualPat := qualPats[i]
+ // Note, the AttributeQualifierPattern relies on the input Qualifier not being an
+ // Attribute, since there is no way to resolve the Attribute with the information
+ // provided to the Matches call.
+ if !qualPat.Matches(qual) {
+ isUnk = false
+ break
+ }
+ }
+ if isUnk {
+ return types.Unknown{matchExprID}, nil
+ }
+ }
+ return nil, nil
+}
+
+// attributeMatcher embeds the NamespacedAttribute interface which allows it to participate in
+// AttributePattern matching against Attribute values without having to modify the code paths that
+// identify Attributes in expressions.
+type attributeMatcher struct {
+ NamespacedAttribute
+ qualifiers []Qualifier
+ fac *partialAttributeFactory
+}
+
+// AddQualifier implements the Attribute interface method.
+func (m *attributeMatcher) AddQualifier(qual Qualifier) (Attribute, error) {
+ // Add the qualifier to the embedded NamespacedAttribute. If the input to the Resolve
+ // method is not a PartialActivation, or does not match an unknown attribute pattern, the
+ // Resolve method is directly invoked on the underlying NamespacedAttribute.
+ _, err := m.NamespacedAttribute.AddQualifier(qual)
+ if err != nil {
+ return nil, err
+ }
+ // The attributeMatcher overloads TryResolve and will attempt to match unknown patterns against
+ // the variable name and qualifier set contained within the Attribute. These values are not
+ // directly inspectable on the top-level NamespacedAttribute interface and so are tracked within
+ // the attributeMatcher.
+ m.qualifiers = append(m.qualifiers, qual)
+ return m, nil
+}
+
+// Resolve is an implementation of the Attribute interface method which uses the
+// attributeMatcher TryResolve implementation rather than the embedded NamespacedAttribute
+// Resolve implementation.
+func (m *attributeMatcher) Resolve(vars Activation) (interface{}, error) {
+ obj, found, err := m.TryResolve(vars)
+ if err != nil {
+ return nil, err
+ }
+ if !found {
+ return nil, fmt.Errorf("no such attribute: %v", m.NamespacedAttribute)
+ }
+ return obj, nil
+}
+
+// TryResolve is an implementation of the NamespacedAttribute interface method which tests
+// for matching unknown attribute patterns and returns types.Unknown if present. Otherwise,
+// the standard Resolve logic applies.
+func (m *attributeMatcher) TryResolve(vars Activation) (interface{}, bool, error) {
+ id := m.NamespacedAttribute.ID()
+ partial, isPartial := vars.(PartialActivation)
+ if isPartial {
+ unk, err := m.fac.matchesUnknownPatterns(
+ partial,
+ id,
+ m.CandidateVariableNames(),
+ m.qualifiers)
+ if err != nil {
+ return nil, true, err
+ }
+ if unk != nil {
+ return unk, true, nil
+ }
+ }
+ return m.NamespacedAttribute.TryResolve(vars)
+}
+
+// Qualify is an implementation of the Qualifier interface method.
+func (m *attributeMatcher) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ val, err := m.Resolve(vars)
+ if err != nil {
+ return nil, err
+ }
+ unk, isUnk := val.(types.Unknown)
+ if isUnk {
+ return unk, nil
+ }
+ qual, err := m.fac.NewQualifier(nil, m.ID(), val)
+ if err != nil {
+ return nil, err
+ }
+ return qual.Qualify(vars, obj)
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/attributes.go b/vendor/github.com/google/cel-go/interpreter/attributes.go
new file mode 100644
index 0000000000..e101c669ba
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/attributes.go
@@ -0,0 +1,1032 @@
+// Copyright 2019 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "errors"
+ "fmt"
+ "math"
+
+ "github.com/google/cel-go/common/containers"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// AttributeFactory provides methods creating Attribute and Qualifier values.
+type AttributeFactory interface {
+ // AbsoluteAttribute creates an attribute that refers to a top-level variable name.
+ //
+ // Checked expressions generate absolute attribute with a single name.
+ // Parse-only expressions may have more than one possible absolute identifier when the
+ // expression is created within a container, e.g. package or namespace.
+ //
+ // When there is more than one name supplied to the AbsoluteAttribute call, the names
+ // must be in CEL's namespace resolution order. The name arguments provided here are
+ // returned in the same order as they were provided by the NamespacedAttribute
+ // CandidateVariableNames method.
+ AbsoluteAttribute(id int64, names ...string) NamespacedAttribute
+
+ // ConditionalAttribute creates an attribute with two Attribute branches, where the Attribute
+ // that is resolved depends on the boolean evaluation of the input 'expr'.
+ ConditionalAttribute(id int64, expr Interpretable, t, f Attribute) Attribute
+
+ // MaybeAttribute creates an attribute that refers to either a field selection or a namespaced
+ // variable name.
+ //
+ // Only expressions which have not been type-checked may generate oneof attributes.
+ MaybeAttribute(id int64, name string) Attribute
+
+ // RelativeAttribute creates an attribute whose value is a qualification of a dynamic
+ // computation rather than a static variable reference.
+ RelativeAttribute(id int64, operand Interpretable) Attribute
+
+ // NewQualifier creates a qualifier on the target object with a given value.
+ //
+ // The 'val' may be an Attribute or any proto-supported map key type: bool, int, string, uint.
+ //
+ // The qualifier may consider the object type being qualified, if present. If absent, the
+ // qualification should be considered dynamic and the qualification should still work, though
+ // it may be sub-optimal.
+ NewQualifier(objType *exprpb.Type, qualID int64, val interface{}) (Qualifier, error)
+}
+
+// Qualifier marker interface for designating different qualifier values and where they appear
+// within field selections and index call expressions (`_[_]`).
+type Qualifier interface {
+ // ID where the qualifier appears within an expression.
+ ID() int64
+
+ // Qualify performs a qualification, e.g. field selection, on the input object and returns
+ // the value or error that results.
+ Qualify(vars Activation, obj interface{}) (interface{}, error)
+}
+
+// ConstantQualifier interface embeds the Qualifier interface and provides an option to inspect the
+// qualifier's constant value.
+//
+// Non-constant qualifiers are of Attribute type.
+type ConstantQualifier interface {
+ Qualifier
+
+ Value() ref.Val
+}
+
+// Attribute values are a variable or value with an optional set of qualifiers, such as field, key,
+// or index accesses.
+type Attribute interface {
+ Qualifier
+
+ // AddQualifier adds a qualifier on the Attribute or error if the qualification is not a valid
+ // qualifier type.
+ AddQualifier(Qualifier) (Attribute, error)
+
+ // Resolve returns the value of the Attribute given the current Activation.
+ Resolve(Activation) (interface{}, error)
+}
+
+// NamespacedAttribute values are a variable within a namespace, and an optional set of qualifiers
+// such as field, key, or index accesses.
+type NamespacedAttribute interface {
+ Attribute
+
+ // CandidateVariableNames returns the possible namespaced variable names for this Attribute in
+ // the CEL namespace resolution order.
+ CandidateVariableNames() []string
+
+ // Qualifiers returns the list of qualifiers associated with the Attribute.s
+ Qualifiers() []Qualifier
+
+ // TryResolve attempts to return the value of the attribute given the current Activation.
+ // If an error is encountered during attribute resolution, it will be returned immediately.
+ // If the attribute cannot be resolved within the Activation, the result must be: `nil`,
+ // `false`, `nil`.
+ TryResolve(Activation) (interface{}, bool, error)
+}
+
+// NewAttributeFactory returns a default AttributeFactory which is produces Attribute values
+// capable of resolving types by simple names and qualify the values using the supported qualifier
+// types: bool, int, string, and uint.
+func NewAttributeFactory(cont *containers.Container,
+ a ref.TypeAdapter,
+ p ref.TypeProvider) AttributeFactory {
+ return &attrFactory{
+ container: cont,
+ adapter: a,
+ provider: p,
+ }
+}
+
+type attrFactory struct {
+ container *containers.Container
+ adapter ref.TypeAdapter
+ provider ref.TypeProvider
+}
+
+// AbsoluteAttribute refers to a variable value and an optional qualifier path.
+//
+// The namespaceNames represent the names the variable could have based on namespace
+// resolution rules.
+func (r *attrFactory) AbsoluteAttribute(id int64, names ...string) NamespacedAttribute {
+ return &absoluteAttribute{
+ id: id,
+ namespaceNames: names,
+ qualifiers: []Qualifier{},
+ adapter: r.adapter,
+ provider: r.provider,
+ fac: r,
+ }
+}
+
+// ConditionalAttribute supports the case where an attribute selection may occur on a conditional
+// expression, e.g. (cond ? a : b).c
+func (r *attrFactory) ConditionalAttribute(id int64, expr Interpretable, t, f Attribute) Attribute {
+ return &conditionalAttribute{
+ id: id,
+ expr: expr,
+ truthy: t,
+ falsy: f,
+ adapter: r.adapter,
+ fac: r,
+ }
+}
+
+// MaybeAttribute collects variants of unchecked AbsoluteAttribute values which could either be
+// direct variable accesses or some combination of variable access with qualification.
+func (r *attrFactory) MaybeAttribute(id int64, name string) Attribute {
+ return &maybeAttribute{
+ id: id,
+ attrs: []NamespacedAttribute{
+ r.AbsoluteAttribute(id, r.container.ResolveCandidateNames(name)...),
+ },
+ adapter: r.adapter,
+ provider: r.provider,
+ fac: r,
+ }
+}
+
+// RelativeAttribute refers to an expression and an optional qualifier path.
+func (r *attrFactory) RelativeAttribute(id int64, operand Interpretable) Attribute {
+ return &relativeAttribute{
+ id: id,
+ operand: operand,
+ qualifiers: []Qualifier{},
+ adapter: r.adapter,
+ fac: r,
+ }
+}
+
+// NewQualifier is an implementation of the AttributeFactory interface.
+func (r *attrFactory) NewQualifier(objType *exprpb.Type,
+ qualID int64,
+ val interface{}) (Qualifier, error) {
+ // Before creating a new qualifier check to see if this is a protobuf message field access.
+ // If so, use the precomputed GetFrom qualification method rather than the standard
+ // stringQualifier.
+ str, isStr := val.(string)
+ if isStr && objType != nil && objType.GetMessageType() != "" {
+ ft, found := r.provider.FindFieldType(objType.GetMessageType(), str)
+ if found && ft.IsSet != nil && ft.GetFrom != nil {
+ return &fieldQualifier{
+ id: qualID,
+ Name: str,
+ FieldType: ft,
+ adapter: r.adapter,
+ }, nil
+ }
+ }
+ return newQualifier(r.adapter, qualID, val)
+}
+
+type absoluteAttribute struct {
+ id int64
+ // namespaceNames represent the names the variable could have based on declared container
+ // (package) of the expression.
+ namespaceNames []string
+ qualifiers []Qualifier
+ adapter ref.TypeAdapter
+ provider ref.TypeProvider
+ fac AttributeFactory
+}
+
+// ID implements the Attribute interface method.
+func (a *absoluteAttribute) ID() int64 {
+ return a.id
+}
+
+// Cost implements the Coster interface method.
+func (a *absoluteAttribute) Cost() (min, max int64) {
+ for _, q := range a.qualifiers {
+ minQ, maxQ := estimateCost(q)
+ min += minQ
+ max += maxQ
+ }
+ min++ // For object retrieval.
+ max++
+ return
+}
+
+// AddQualifier implements the Attribute interface method.
+func (a *absoluteAttribute) AddQualifier(qual Qualifier) (Attribute, error) {
+ a.qualifiers = append(a.qualifiers, qual)
+ return a, nil
+}
+
+// CandidateVariableNames implements the NamespaceAttribute interface method.
+func (a *absoluteAttribute) CandidateVariableNames() []string {
+ return a.namespaceNames
+}
+
+// Qualifiers returns the list of Qualifier instances associated with the namespaced attribute.
+func (a *absoluteAttribute) Qualifiers() []Qualifier {
+ return a.qualifiers
+}
+
+// Qualify is an implementation of the Qualifier interface method.
+func (a *absoluteAttribute) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ val, err := a.Resolve(vars)
+ if err != nil {
+ return nil, err
+ }
+ unk, isUnk := val.(types.Unknown)
+ if isUnk {
+ return unk, nil
+ }
+ qual, err := a.fac.NewQualifier(nil, a.id, val)
+ if err != nil {
+ return nil, err
+ }
+ return qual.Qualify(vars, obj)
+}
+
+// Resolve returns the resolved Attribute value given the Activation, or error if the Attribute
+// variable is not found, or if its Qualifiers cannot be applied successfully.
+func (a *absoluteAttribute) Resolve(vars Activation) (interface{}, error) {
+ obj, found, err := a.TryResolve(vars)
+ if err != nil {
+ return nil, err
+ }
+ if found {
+ return obj, nil
+ }
+ return nil, fmt.Errorf("no such attribute: %v", a)
+}
+
+// String implements the Stringer interface method.
+func (a *absoluteAttribute) String() string {
+ return fmt.Sprintf("id: %v, names: %v", a.id, a.namespaceNames)
+}
+
+// TryResolve iterates through the namespaced variable names until one is found within the
+// Activation or TypeProvider.
+//
+// If the variable name cannot be found as an Activation variable or in the TypeProvider as
+// a type, then the result is `nil`, `false`, `nil` per the interface requirement.
+func (a *absoluteAttribute) TryResolve(vars Activation) (interface{}, bool, error) {
+ for _, nm := range a.namespaceNames {
+ // If the variable is found, process it. Otherwise, wait until the checks to
+ // determine whether the type is unknown before returning.
+ op, found := vars.ResolveName(nm)
+ if found {
+ var err error
+ for _, qual := range a.qualifiers {
+ op, err = qual.Qualify(vars, op)
+ if err != nil {
+ return nil, true, err
+ }
+ }
+ return op, true, nil
+ }
+ // Attempt to resolve the qualified type name if the name is not a variable identifier.
+ typ, found := a.provider.FindIdent(nm)
+ if found {
+ if len(a.qualifiers) == 0 {
+ return typ, true, nil
+ }
+ return nil, true, fmt.Errorf("no such attribute: %v", typ)
+ }
+ }
+ return nil, false, nil
+}
+
+type conditionalAttribute struct {
+ id int64
+ expr Interpretable
+ truthy Attribute
+ falsy Attribute
+ adapter ref.TypeAdapter
+ fac AttributeFactory
+}
+
+// ID is an implementation of the Attribute interface method.
+func (a *conditionalAttribute) ID() int64 {
+ return a.id
+}
+
+// Cost provides the heuristic cost of a ternary operation ? : .
+// The cost is computed as cost(expr) plus the min/max costs of evaluating either
+// `t` or `f`.
+func (a *conditionalAttribute) Cost() (min, max int64) {
+ tMin, tMax := estimateCost(a.truthy)
+ fMin, fMax := estimateCost(a.falsy)
+ eMin, eMax := estimateCost(a.expr)
+ return eMin + findMin(tMin, fMin), eMax + findMax(tMax, fMax)
+}
+
+// AddQualifier appends the same qualifier to both sides of the conditional, in effect managing
+// the qualification of alternate attributes.
+func (a *conditionalAttribute) AddQualifier(qual Qualifier) (Attribute, error) {
+ _, err := a.truthy.AddQualifier(qual)
+ if err != nil {
+ return nil, err
+ }
+ _, err = a.falsy.AddQualifier(qual)
+ if err != nil {
+ return nil, err
+ }
+ return a, nil
+}
+
+// Qualify is an implementation of the Qualifier interface method.
+func (a *conditionalAttribute) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ val, err := a.Resolve(vars)
+ if err != nil {
+ return nil, err
+ }
+ unk, isUnk := val.(types.Unknown)
+ if isUnk {
+ return unk, nil
+ }
+ qual, err := a.fac.NewQualifier(nil, a.id, val)
+ if err != nil {
+ return nil, err
+ }
+ return qual.Qualify(vars, obj)
+}
+
+// Resolve evaluates the condition, and then resolves the truthy or falsy branch accordingly.
+func (a *conditionalAttribute) Resolve(vars Activation) (interface{}, error) {
+ val := a.expr.Eval(vars)
+ if types.IsError(val) {
+ return nil, val.(*types.Err)
+ }
+ if val == types.True {
+ return a.truthy.Resolve(vars)
+ }
+ if val == types.False {
+ return a.falsy.Resolve(vars)
+ }
+ if types.IsUnknown(val) {
+ return val, nil
+ }
+ return nil, types.MaybeNoSuchOverloadErr(val).(*types.Err)
+}
+
+// String is an implementation of the Stringer interface method.
+func (a *conditionalAttribute) String() string {
+ return fmt.Sprintf("id: %v, truthy attribute: %v, falsy attribute: %v", a.id, a.truthy, a.falsy)
+}
+
+type maybeAttribute struct {
+ id int64
+ attrs []NamespacedAttribute
+ adapter ref.TypeAdapter
+ provider ref.TypeProvider
+ fac AttributeFactory
+}
+
+// ID is an implementation of the Attribute interface method.
+func (a *maybeAttribute) ID() int64 {
+ return a.id
+}
+
+// Cost implements the Coster interface method. The min cost is computed as the minimal cost among
+// all the possible attributes, the max cost ditto.
+func (a *maybeAttribute) Cost() (min, max int64) {
+ min, max = math.MaxInt64, 0
+ for _, a := range a.attrs {
+ minA, maxA := estimateCost(a)
+ min = findMin(min, minA)
+ max = findMax(max, maxA)
+ }
+ return
+}
+
+func findMin(x, y int64) int64 {
+ if x < y {
+ return x
+ }
+ return y
+}
+
+func findMax(x, y int64) int64 {
+ if x > y {
+ return x
+ }
+ return y
+}
+
+// AddQualifier adds a qualifier to each possible attribute variant, and also creates
+// a new namespaced variable from the qualified value.
+//
+// The algorithm for building the maybe attribute is as follows:
+//
+// 1. Create a maybe attribute from a simple identifier when it occurs in a parsed-only expression
+//
+// mb = MaybeAttribute(, "a")
+//
+// Initializing the maybe attribute creates an absolute attribute internally which includes the
+// possible namespaced names of the attribute. In this example, let's assume we are in namespace
+// 'ns', then the maybe is either one of the following variable names:
+//
+// possible variables names -- ns.a, a
+//
+// 2. Adding a qualifier to the maybe means that the variable name could be a longer qualified
+// name, or a field selection on one of the possible variable names produced earlier:
+//
+// mb.AddQualifier("b")
+//
+// possible variables names -- ns.a.b, a.b
+// possible field selection -- ns.a['b'], a['b']
+//
+// If none of the attributes within the maybe resolves a value, the result is an error.
+func (a *maybeAttribute) AddQualifier(qual Qualifier) (Attribute, error) {
+ str := ""
+ isStr := false
+ cq, isConst := qual.(ConstantQualifier)
+ if isConst {
+ str, isStr = cq.Value().Value().(string)
+ }
+ var augmentedNames []string
+ // First add the qualifier to all existing attributes in the oneof.
+ for _, attr := range a.attrs {
+ if isStr && len(attr.Qualifiers()) == 0 {
+ candidateVars := attr.CandidateVariableNames()
+ augmentedNames = make([]string, len(candidateVars))
+ for i, name := range candidateVars {
+ augmentedNames[i] = fmt.Sprintf("%s.%s", name, str)
+ }
+ }
+ _, err := attr.AddQualifier(qual)
+ if err != nil {
+ return nil, err
+ }
+ }
+ // Next, ensure the most specific variable / type reference is searched first.
+ a.attrs = append([]NamespacedAttribute{
+ a.fac.AbsoluteAttribute(qual.ID(), augmentedNames...),
+ }, a.attrs...)
+ return a, nil
+}
+
+// Qualify is an implementation of the Qualifier interface method.
+func (a *maybeAttribute) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ val, err := a.Resolve(vars)
+ if err != nil {
+ return nil, err
+ }
+ unk, isUnk := val.(types.Unknown)
+ if isUnk {
+ return unk, nil
+ }
+ qual, err := a.fac.NewQualifier(nil, a.id, val)
+ if err != nil {
+ return nil, err
+ }
+ return qual.Qualify(vars, obj)
+}
+
+// Resolve follows the variable resolution rules to determine whether the attribute is a variable
+// or a field selection.
+func (a *maybeAttribute) Resolve(vars Activation) (interface{}, error) {
+ for _, attr := range a.attrs {
+ obj, found, err := attr.TryResolve(vars)
+ // Return an error if one is encountered.
+ if err != nil {
+ return nil, err
+ }
+ // If the object was found, return it.
+ if found {
+ return obj, nil
+ }
+ }
+ // Else, produce a no such attribute error.
+ return nil, fmt.Errorf("no such attribute: %v", a)
+}
+
+// String is an implementation of the Stringer interface method.
+func (a *maybeAttribute) String() string {
+ return fmt.Sprintf("id: %v, attributes: %v", a.id, a.attrs)
+}
+
+type relativeAttribute struct {
+ id int64
+ operand Interpretable
+ qualifiers []Qualifier
+ adapter ref.TypeAdapter
+ fac AttributeFactory
+}
+
+// ID is an implementation of the Attribute interface method.
+func (a *relativeAttribute) ID() int64 {
+ return a.id
+}
+
+// Cost implements the Coster interface method.
+func (a *relativeAttribute) Cost() (min, max int64) {
+ min, max = estimateCost(a.operand)
+ for _, qual := range a.qualifiers {
+ minQ, maxQ := estimateCost(qual)
+ min += minQ
+ max += maxQ
+ }
+ return
+}
+
+// AddQualifier implements the Attribute interface method.
+func (a *relativeAttribute) AddQualifier(qual Qualifier) (Attribute, error) {
+ a.qualifiers = append(a.qualifiers, qual)
+ return a, nil
+}
+
+// Qualify is an implementation of the Qualifier interface method.
+func (a *relativeAttribute) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ val, err := a.Resolve(vars)
+ if err != nil {
+ return nil, err
+ }
+ unk, isUnk := val.(types.Unknown)
+ if isUnk {
+ return unk, nil
+ }
+ qual, err := a.fac.NewQualifier(nil, a.id, val)
+ if err != nil {
+ return nil, err
+ }
+ return qual.Qualify(vars, obj)
+}
+
+// Resolve expression value and qualifier relative to the expression result.
+func (a *relativeAttribute) Resolve(vars Activation) (interface{}, error) {
+ // First, evaluate the operand.
+ v := a.operand.Eval(vars)
+ if types.IsError(v) {
+ return nil, v.(*types.Err)
+ }
+ if types.IsUnknown(v) {
+ return v, nil
+ }
+ // Next, qualify it. Qualification handles unkonwns as well, so there's no need to recheck.
+ var err error
+ var obj interface{} = v
+ for _, qual := range a.qualifiers {
+ obj, err = qual.Qualify(vars, obj)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return obj, nil
+}
+
+// String is an implementation of the Stringer interface method.
+func (a *relativeAttribute) String() string {
+ return fmt.Sprintf("id: %v, operand: %v", a.id, a.operand)
+}
+
+func newQualifier(adapter ref.TypeAdapter, id int64, v interface{}) (Qualifier, error) {
+ var qual Qualifier
+ switch val := v.(type) {
+ case Attribute:
+ return &attrQualifier{id: id, Attribute: val}, nil
+ case string:
+ qual = &stringQualifier{id: id, value: val, celValue: types.String(val), adapter: adapter}
+ case int:
+ qual = &intQualifier{id: id, value: int64(val), celValue: types.Int(val), adapter: adapter}
+ case int32:
+ qual = &intQualifier{id: id, value: int64(val), celValue: types.Int(val), adapter: adapter}
+ case int64:
+ qual = &intQualifier{id: id, value: val, celValue: types.Int(val), adapter: adapter}
+ case uint:
+ qual = &uintQualifier{id: id, value: uint64(val), celValue: types.Uint(val), adapter: adapter}
+ case uint32:
+ qual = &uintQualifier{id: id, value: uint64(val), celValue: types.Uint(val), adapter: adapter}
+ case uint64:
+ qual = &uintQualifier{id: id, value: val, celValue: types.Uint(val), adapter: adapter}
+ case bool:
+ qual = &boolQualifier{id: id, value: val, celValue: types.Bool(val), adapter: adapter}
+ case types.String:
+ qual = &stringQualifier{id: id, value: string(val), celValue: val, adapter: adapter}
+ case types.Int:
+ qual = &intQualifier{id: id, value: int64(val), celValue: val, adapter: adapter}
+ case types.Uint:
+ qual = &uintQualifier{id: id, value: uint64(val), celValue: val, adapter: adapter}
+ case types.Bool:
+ qual = &boolQualifier{id: id, value: bool(val), celValue: val, adapter: adapter}
+ default:
+ return nil, fmt.Errorf("invalid qualifier type: %T", v)
+ }
+ return qual, nil
+}
+
+type attrQualifier struct {
+ id int64
+ Attribute
+}
+
+func (q *attrQualifier) ID() int64 {
+ return q.id
+}
+
+// Cost returns zero for constant field qualifiers
+func (q *attrQualifier) Cost() (min, max int64) {
+ return estimateCost(q.Attribute)
+}
+
+type stringQualifier struct {
+ id int64
+ value string
+ celValue ref.Val
+ adapter ref.TypeAdapter
+}
+
+// ID is an implementation of the Qualifier interface method.
+func (q *stringQualifier) ID() int64 {
+ return q.id
+}
+
+// Qualify implements the Qualifier interface method.
+func (q *stringQualifier) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ s := q.value
+ isMap := false
+ isKey := false
+ switch o := obj.(type) {
+ case map[string]interface{}:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]string:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]int:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]int32:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]int64:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]uint:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]uint32:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]uint64:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]float32:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]float64:
+ isMap = true
+ obj, isKey = o[s]
+ case map[string]bool:
+ isMap = true
+ obj, isKey = o[s]
+ case types.Unknown:
+ return o, nil
+ default:
+ elem, err := refResolve(q.adapter, q.celValue, obj)
+ if err != nil {
+ return nil, err
+ }
+ if types.IsUnknown(elem) {
+ return elem, nil
+ }
+ return elem, nil
+ }
+ if isMap && !isKey {
+ return nil, fmt.Errorf("no such key: %v", s)
+ }
+ return obj, nil
+}
+
+// Value implements the ConstantQualifier interface
+func (q *stringQualifier) Value() ref.Val {
+ return q.celValue
+}
+
+// Cost returns zero for constant field qualifiers
+func (q *stringQualifier) Cost() (min, max int64) {
+ return 0, 0
+}
+
+type intQualifier struct {
+ id int64
+ value int64
+ celValue ref.Val
+ adapter ref.TypeAdapter
+}
+
+// ID is an implementation of the Qualifier interface method.
+func (q *intQualifier) ID() int64 {
+ return q.id
+}
+
+// Qualify implements the Qualifier interface method.
+func (q *intQualifier) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ i := q.value
+ isMap := false
+ isKey := false
+ isIndex := false
+ switch o := obj.(type) {
+ // The specialized map types supported by an int qualifier are considerably fewer than the set
+ // of specialized map types supported by string qualifiers since they are less frequently used
+ // than string-based map keys. Additional specializations may be added in the future if
+ // desired.
+ case map[int]interface{}:
+ isMap = true
+ obj, isKey = o[int(i)]
+ case map[int32]interface{}:
+ isMap = true
+ obj, isKey = o[int32(i)]
+ case map[int64]interface{}:
+ isMap = true
+ obj, isKey = o[i]
+ case []interface{}:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []string:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []int:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []int32:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []int64:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []uint:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []uint32:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []uint64:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []float32:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []float64:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case []bool:
+ isIndex = i >= 0 && i < int64(len(o))
+ if isIndex {
+ obj = o[i]
+ }
+ case types.Unknown:
+ return o, nil
+ default:
+ elem, err := refResolve(q.adapter, q.celValue, obj)
+ if err != nil {
+ return nil, err
+ }
+ if types.IsUnknown(elem) {
+ return elem, nil
+ }
+ return elem, nil
+ }
+ if isMap && !isKey {
+ return nil, fmt.Errorf("no such key: %v", i)
+ }
+ if !isMap && !isIndex {
+ return nil, fmt.Errorf("index out of bounds: %v", i)
+ }
+ return obj, nil
+}
+
+// Value implements the ConstantQualifier interface
+func (q *intQualifier) Value() ref.Val {
+ return q.celValue
+}
+
+// Cost returns zero for constant field qualifiers
+func (q *intQualifier) Cost() (min, max int64) {
+ return 0, 0
+}
+
+type uintQualifier struct {
+ id int64
+ value uint64
+ celValue ref.Val
+ adapter ref.TypeAdapter
+}
+
+// ID is an implementation of the Qualifier interface method.
+func (q *uintQualifier) ID() int64 {
+ return q.id
+}
+
+// Qualify implements the Qualifier interface method.
+func (q *uintQualifier) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ u := q.value
+ isMap := false
+ isKey := false
+ switch o := obj.(type) {
+ // The specialized map types supported by a uint qualifier are considerably fewer than the set
+ // of specialized map types supported by string qualifiers since they are less frequently used
+ // than string-based map keys. Additional specializations may be added in the future if
+ // desired.
+ case map[uint]interface{}:
+ isMap = true
+ obj, isKey = o[uint(u)]
+ case map[uint32]interface{}:
+ isMap = true
+ obj, isKey = o[uint32(u)]
+ case map[uint64]interface{}:
+ isMap = true
+ obj, isKey = o[u]
+ case types.Unknown:
+ return o, nil
+ default:
+ elem, err := refResolve(q.adapter, q.celValue, obj)
+ if err != nil {
+ return nil, err
+ }
+ if types.IsUnknown(elem) {
+ return elem, nil
+ }
+ return elem, nil
+ }
+ if isMap && !isKey {
+ return nil, fmt.Errorf("no such key: %v", u)
+ }
+ return obj, nil
+}
+
+// Value implements the ConstantQualifier interface
+func (q *uintQualifier) Value() ref.Val {
+ return q.celValue
+}
+
+// Cost returns zero for constant field qualifiers
+func (q *uintQualifier) Cost() (min, max int64) {
+ return 0, 0
+}
+
+type boolQualifier struct {
+ id int64
+ value bool
+ celValue ref.Val
+ adapter ref.TypeAdapter
+}
+
+// ID is an implementation of the Qualifier interface method.
+func (q *boolQualifier) ID() int64 {
+ return q.id
+}
+
+// Qualify implements the Qualifier interface method.
+func (q *boolQualifier) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ b := q.value
+ isKey := false
+ switch o := obj.(type) {
+ // The specialized map types supported by a bool qualifier are considerably fewer than the set
+ // of specialized map types supported by string qualifiers since they are less frequently used
+ // than string-based map keys. Additional specializations may be added in the future if
+ // desired.
+ case map[bool]interface{}:
+ obj, isKey = o[b]
+ case types.Unknown:
+ return o, nil
+ default:
+ elem, err := refResolve(q.adapter, q.celValue, obj)
+ if err != nil {
+ return nil, err
+ }
+ if types.IsUnknown(elem) {
+ return elem, nil
+ }
+ return elem, nil
+ }
+ if !isKey {
+ return nil, fmt.Errorf("no such key: %v", b)
+ }
+ return obj, nil
+}
+
+// Value implements the ConstantQualifier interface
+func (q *boolQualifier) Value() ref.Val {
+ return q.celValue
+}
+
+// Cost returns zero for constant field qualifiers
+func (q *boolQualifier) Cost() (min, max int64) {
+ return 0, 0
+}
+
+// fieldQualifier indicates that the qualification is a well-defined field with a known
+// field type. When the field type is known this can be used to improve the speed and
+// efficiency of field resolution.
+type fieldQualifier struct {
+ id int64
+ Name string
+ FieldType *ref.FieldType
+ adapter ref.TypeAdapter
+}
+
+// ID is an implementation of the Qualifier interface method.
+func (q *fieldQualifier) ID() int64 {
+ return q.id
+}
+
+// Qualify implements the Qualifier interface method.
+func (q *fieldQualifier) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ if rv, ok := obj.(ref.Val); ok {
+ obj = rv.Value()
+ }
+ return q.FieldType.GetFrom(obj)
+}
+
+// Value implements the ConstantQualifier interface
+func (q *fieldQualifier) Value() ref.Val {
+ return types.String(q.Name)
+}
+
+// Cost returns zero for constant field qualifiers
+func (q *fieldQualifier) Cost() (min, max int64) {
+ return 0, 0
+}
+
+// refResolve attempts to convert the value to a CEL value and then uses reflection methods
+// to try and resolve the qualifier.
+func refResolve(adapter ref.TypeAdapter, idx ref.Val, obj interface{}) (ref.Val, error) {
+ celVal := adapter.NativeToValue(obj)
+ mapper, isMapper := celVal.(traits.Mapper)
+ if isMapper {
+ elem, found := mapper.Find(idx)
+ if !found {
+ return nil, fmt.Errorf("no such key: %v", idx)
+ }
+ if types.IsError(elem) {
+ return nil, elem.(*types.Err)
+ }
+ return elem, nil
+ }
+ indexer, isIndexer := celVal.(traits.Indexer)
+ if isIndexer {
+ elem := indexer.Get(idx)
+ if types.IsError(elem) {
+ return nil, elem.(*types.Err)
+ }
+ return elem, nil
+ }
+ if types.IsUnknown(celVal) {
+ return celVal, nil
+ }
+ // TODO: If the types.Err value contains more than just an error message at some point in the
+ // future, then it would be reasonable to return error values as ref.Val types rather than
+ // simple go error types.
+ if types.IsError(celVal) {
+ return nil, celVal.(*types.Err)
+ }
+ return nil, errors.New("no such overload")
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/coster.go b/vendor/github.com/google/cel-go/interpreter/coster.go
new file mode 100644
index 0000000000..15cb6bc041
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/coster.go
@@ -0,0 +1,31 @@
+// Copyright 2020 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import "math"
+
+// Coster calculates the heuristic cost incurred during evaluation.
+type Coster interface {
+ Cost() (min, max int64)
+}
+
+// estimateCost returns the heuristic cost interval for the program.
+func estimateCost(i interface{}) (min, max int64) {
+ c, ok := i.(Coster)
+ if !ok {
+ return 0, math.MaxInt64
+ }
+ return c.Cost()
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/decorators.go b/vendor/github.com/google/cel-go/interpreter/decorators.go
new file mode 100644
index 0000000000..23a7f695b2
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/decorators.go
@@ -0,0 +1,201 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "github.com/google/cel-go/common/overloads"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+)
+
+// InterpretableDecorator is a functional interface for decorating or replacing
+// Interpretable expression nodes at construction time.
+type InterpretableDecorator func(Interpretable) (Interpretable, error)
+
+// evalObserver is a functional interface that accepts an expression id and an observed value.
+type evalObserver func(int64, ref.Val)
+
+// decObserveEval records evaluation state into an EvalState object.
+func decObserveEval(observer evalObserver) InterpretableDecorator {
+ return func(i Interpretable) (Interpretable, error) {
+ switch inst := i.(type) {
+ case *evalWatch, *evalWatchAttr, *evalWatchConst:
+ // these instruction are already watching, return straight-away.
+ return i, nil
+ case InterpretableAttribute:
+ return &evalWatchAttr{
+ InterpretableAttribute: inst,
+ observer: observer,
+ }, nil
+ case InterpretableConst:
+ return &evalWatchConst{
+ InterpretableConst: inst,
+ observer: observer,
+ }, nil
+ default:
+ return &evalWatch{
+ Interpretable: i,
+ observer: observer,
+ }, nil
+ }
+ }
+}
+
+// decDisableShortcircuits ensures that all branches of an expression will be evaluated, no short-circuiting.
+func decDisableShortcircuits() InterpretableDecorator {
+ return func(i Interpretable) (Interpretable, error) {
+ switch expr := i.(type) {
+ case *evalOr:
+ return &evalExhaustiveOr{
+ id: expr.id,
+ lhs: expr.lhs,
+ rhs: expr.rhs,
+ }, nil
+ case *evalAnd:
+ return &evalExhaustiveAnd{
+ id: expr.id,
+ lhs: expr.lhs,
+ rhs: expr.rhs,
+ }, nil
+ case *evalFold:
+ return &evalExhaustiveFold{
+ id: expr.id,
+ accu: expr.accu,
+ accuVar: expr.accuVar,
+ iterRange: expr.iterRange,
+ iterVar: expr.iterVar,
+ cond: expr.cond,
+ step: expr.step,
+ result: expr.result,
+ }, nil
+ case InterpretableAttribute:
+ cond, isCond := expr.Attr().(*conditionalAttribute)
+ if isCond {
+ return &evalExhaustiveConditional{
+ id: cond.id,
+ attr: cond,
+ adapter: expr.Adapter(),
+ }, nil
+ }
+ }
+ return i, nil
+ }
+}
+
+// decOptimize optimizes the program plan by looking for common evaluation patterns and
+// conditionally precomputating the result.
+// - build list and map values with constant elements.
+// - convert 'in' operations to set membership tests if possible.
+func decOptimize() InterpretableDecorator {
+ return func(i Interpretable) (Interpretable, error) {
+ switch inst := i.(type) {
+ case *evalList:
+ return maybeBuildListLiteral(i, inst)
+ case *evalMap:
+ return maybeBuildMapLiteral(i, inst)
+ case InterpretableCall:
+ if inst.OverloadID() == overloads.InList {
+ return maybeOptimizeSetMembership(i, inst)
+ }
+ if overloads.IsTypeConversionFunction(inst.Function()) {
+ return maybeOptimizeConstUnary(i, inst)
+ }
+ }
+ return i, nil
+ }
+}
+
+func maybeOptimizeConstUnary(i Interpretable, call InterpretableCall) (Interpretable, error) {
+ args := call.Args()
+ if len(args) != 1 {
+ return i, nil
+ }
+ _, isConst := args[0].(InterpretableConst)
+ if !isConst {
+ return i, nil
+ }
+ val := call.Eval(EmptyActivation())
+ if types.IsError(val) {
+ return nil, val.(*types.Err)
+ }
+ return NewConstValue(call.ID(), val), nil
+}
+
+func maybeBuildListLiteral(i Interpretable, l *evalList) (Interpretable, error) {
+ for _, elem := range l.elems {
+ _, isConst := elem.(InterpretableConst)
+ if !isConst {
+ return i, nil
+ }
+ }
+ return NewConstValue(l.ID(), l.Eval(EmptyActivation())), nil
+}
+
+func maybeBuildMapLiteral(i Interpretable, mp *evalMap) (Interpretable, error) {
+ for idx, key := range mp.keys {
+ _, isConst := key.(InterpretableConst)
+ if !isConst {
+ return i, nil
+ }
+ _, isConst = mp.vals[idx].(InterpretableConst)
+ if !isConst {
+ return i, nil
+ }
+ }
+ return NewConstValue(mp.ID(), mp.Eval(EmptyActivation())), nil
+}
+
+// maybeOptimizeSetMembership may convert an 'in' operation against a list to map key membership
+// test if the following conditions are true:
+// - the list is a constant with homogeneous element types.
+// - the elements are all of primitive type.
+func maybeOptimizeSetMembership(i Interpretable, inlist InterpretableCall) (Interpretable, error) {
+ args := inlist.Args()
+ lhs := args[0]
+ rhs := args[1]
+ l, isConst := rhs.(InterpretableConst)
+ if !isConst {
+ return i, nil
+ }
+ // When the incoming binary call is flagged with as the InList overload, the value will
+ // always be convertible to a `traits.Lister` type.
+ list := l.Value().(traits.Lister)
+ if list.Size() == types.IntZero {
+ return NewConstValue(inlist.ID(), types.False), nil
+ }
+ it := list.Iterator()
+ var typ ref.Type
+ valueSet := make(map[ref.Val]ref.Val)
+ for it.HasNext() == types.True {
+ elem := it.Next()
+ if !types.IsPrimitiveType(elem) {
+ // Note, non-primitive type are not yet supported.
+ return i, nil
+ }
+ if typ == nil {
+ typ = elem.Type()
+ } else if typ.TypeName() != elem.Type().TypeName() {
+ return i, nil
+ }
+ valueSet[elem] = types.True
+ }
+ return &evalSetMembership{
+ inst: inlist,
+ arg: lhs,
+ argTypeName: typ.TypeName(),
+ valueSet: valueSet,
+ }, nil
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/dispatcher.go b/vendor/github.com/google/cel-go/interpreter/dispatcher.go
new file mode 100644
index 0000000000..febf9d8a83
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/dispatcher.go
@@ -0,0 +1,100 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "fmt"
+
+ "github.com/google/cel-go/interpreter/functions"
+)
+
+// Dispatcher resolves function calls to their appropriate overload.
+type Dispatcher interface {
+ // Add one or more overloads, returning an error if any Overload has the same Overload#Name.
+ Add(overloads ...*functions.Overload) error
+
+ // FindOverload returns an Overload definition matching the provided name.
+ FindOverload(overload string) (*functions.Overload, bool)
+
+ // OverloadIds returns the set of all overload identifiers configured for dispatch.
+ OverloadIds() []string
+}
+
+// NewDispatcher returns an empty Dispatcher instance.
+func NewDispatcher() Dispatcher {
+ return &defaultDispatcher{
+ overloads: make(map[string]*functions.Overload)}
+}
+
+// ExtendDispatcher returns a Dispatcher which inherits the overloads of its parent, and
+// provides an isolation layer between built-ins and extension functions which is useful
+// for forward compatibility.
+func ExtendDispatcher(parent Dispatcher) Dispatcher {
+ return &defaultDispatcher{
+ parent: parent,
+ overloads: make(map[string]*functions.Overload)}
+}
+
+// overloadMap helper type for indexing overloads by function name.
+type overloadMap map[string]*functions.Overload
+
+// defaultDispatcher struct which contains an overload map.
+type defaultDispatcher struct {
+ parent Dispatcher
+ overloads overloadMap
+}
+
+// Add implements the Dispatcher.Add interface method.
+func (d *defaultDispatcher) Add(overloads ...*functions.Overload) error {
+ for _, o := range overloads {
+ // add the overload unless an overload of the same name has already been provided.
+ if _, found := d.overloads[o.Operator]; found {
+ return fmt.Errorf("overload already exists '%s'", o.Operator)
+ }
+ // index the overload by function name.
+ d.overloads[o.Operator] = o
+ }
+ return nil
+}
+
+// FindOverload implements the Dispatcher.FindOverload interface method.
+func (d *defaultDispatcher) FindOverload(overload string) (*functions.Overload, bool) {
+ o, found := d.overloads[overload]
+ // Attempt to dispatch to an overload defined in the parent.
+ if !found && d.parent != nil {
+ return d.parent.FindOverload(overload)
+ }
+ return o, found
+}
+
+// OverloadIds implements the Dispatcher interface method.
+func (d *defaultDispatcher) OverloadIds() []string {
+ i := 0
+ overloads := make([]string, len(d.overloads))
+ for name := range d.overloads {
+ overloads[i] = name
+ i++
+ }
+ if d.parent == nil {
+ return overloads
+ }
+ parentOverloads := d.parent.OverloadIds()
+ for _, pName := range parentOverloads {
+ if _, found := d.overloads[pName]; !found {
+ overloads = append(overloads, pName)
+ }
+ }
+ return overloads
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/evalstate.go b/vendor/github.com/google/cel-go/interpreter/evalstate.go
new file mode 100644
index 0000000000..cc0d3e6f94
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/evalstate.go
@@ -0,0 +1,75 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "github.com/google/cel-go/common/types/ref"
+)
+
+// EvalState tracks the values associated with expression ids during execution.
+type EvalState interface {
+ // IDs returns the list of ids with recorded values.
+ IDs() []int64
+
+ // Value returns the observed value of the given expression id if found, and a nil false
+ // result if not.
+ Value(int64) (ref.Val, bool)
+
+ // SetValue sets the observed value of the expression id.
+ SetValue(int64, ref.Val)
+
+ // Reset clears the previously recorded expression values.
+ Reset()
+}
+
+// evalState permits the mutation of evaluation state for a given expression id.
+type evalState struct {
+ values map[int64]ref.Val
+}
+
+// NewEvalState returns an EvalState instanced used to observe the intermediate
+// evaluations of an expression.
+func NewEvalState() EvalState {
+ return &evalState{
+ values: make(map[int64]ref.Val),
+ }
+}
+
+// IDs implements the EvalState interface method.
+func (s *evalState) IDs() []int64 {
+ var ids []int64
+ for k, v := range s.values {
+ if v != nil {
+ ids = append(ids, k)
+ }
+ }
+ return ids
+}
+
+// Value is an implementation of the EvalState interface method.
+func (s *evalState) Value(exprID int64) (ref.Val, bool) {
+ val, found := s.values[exprID]
+ return val, found
+}
+
+// SetValue is an implementation of the EvalState interface method.
+func (s *evalState) SetValue(exprID int64, val ref.Val) {
+ s.values[exprID] = val
+}
+
+// Reset implements the EvalState interface method.
+func (s *evalState) Reset() {
+ s.values = map[int64]ref.Val{}
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/functions/BUILD.bazel b/vendor/github.com/google/cel-go/interpreter/functions/BUILD.bazel
new file mode 100644
index 0000000000..846d11bf47
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/functions/BUILD.bazel
@@ -0,0 +1,22 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library")
+
+package(
+ default_visibility = ["//visibility:public"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "functions.go",
+ "standard.go",
+ ],
+ importpath = "github.com/google/cel-go/interpreter/functions",
+ deps = [
+ "//common/operators:go_default_library",
+ "//common/overloads:go_default_library",
+ "//common/types:go_default_library",
+ "//common/types/ref:go_default_library",
+ "//common/types/traits:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/interpreter/functions/functions.go b/vendor/github.com/google/cel-go/interpreter/functions/functions.go
new file mode 100644
index 0000000000..4ca706e96c
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/functions/functions.go
@@ -0,0 +1,58 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package functions defines the standard builtin functions supported by the
+// interpreter and as declared within the checker#StandardDeclarations.
+package functions
+
+import "github.com/google/cel-go/common/types/ref"
+
+// Overload defines a named overload of a function, indicating an operand trait
+// which must be present on the first argument to the overload as well as one
+// of either a unary, binary, or function implementation.
+//
+// The majority of operators within the expression language are unary or binary
+// and the specializations simplify the call contract for implementers of
+// types with operator overloads. Any added complexity is assumed to be handled
+// by the generic FunctionOp.
+type Overload struct {
+ // Operator name as written in an expression or defined within
+ // operators.go.
+ Operator string
+
+ // Operand trait used to dispatch the call. The zero-value indicates a
+ // global function overload or that one of the Unary / Binary / Function
+ // definitions should be used to execute the call.
+ OperandTrait int
+
+ // Unary defines the overload with a UnaryOp implementation. May be nil.
+ Unary UnaryOp
+
+ // Binary defines the overload with a BinaryOp implementation. May be nil.
+ Binary BinaryOp
+
+ // Function defines the overload with a FunctionOp implementation. May be
+ // nil.
+ Function FunctionOp
+}
+
+// UnaryOp is a function that takes a single value and produces an output.
+type UnaryOp func(value ref.Val) ref.Val
+
+// BinaryOp is a function that takes two values and produces an output.
+type BinaryOp func(lhs ref.Val, rhs ref.Val) ref.Val
+
+// FunctionOp is a function with accepts zero or more arguments and produces
+// an value (as interface{}) or error as a result.
+type FunctionOp func(values ...ref.Val) ref.Val
diff --git a/vendor/github.com/google/cel-go/interpreter/functions/standard.go b/vendor/github.com/google/cel-go/interpreter/functions/standard.go
new file mode 100644
index 0000000000..c8767bc176
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/functions/standard.go
@@ -0,0 +1,272 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package functions
+
+import (
+ "github.com/google/cel-go/common/operators"
+ "github.com/google/cel-go/common/overloads"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+)
+
+// StandardOverloads returns the definitions of the built-in overloads.
+func StandardOverloads() []*Overload {
+ return []*Overload{
+ // Logical not (!a)
+ {
+ Operator: operators.LogicalNot,
+ OperandTrait: traits.NegatorType,
+ Unary: func(value ref.Val) ref.Val {
+ if !types.IsBool(value) {
+ return types.ValOrErr(value, "no such overload")
+ }
+ return value.(traits.Negater).Negate()
+ }},
+ // Not strictly false: IsBool(a) ? a : true
+ {
+ Operator: operators.NotStrictlyFalse,
+ Unary: notStrictlyFalse},
+ // Deprecated: not strictly false, may be overridden in the environment.
+ {
+ Operator: operators.OldNotStrictlyFalse,
+ Unary: notStrictlyFalse},
+
+ // Less than operator
+ {Operator: operators.Less,
+ OperandTrait: traits.ComparerType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ cmp := lhs.(traits.Comparer).Compare(rhs)
+ if cmp == types.IntNegOne {
+ return types.True
+ }
+ if cmp == types.IntOne || cmp == types.IntZero {
+ return types.False
+ }
+ return cmp
+ }},
+
+ // Less than or equal operator
+ {Operator: operators.LessEquals,
+ OperandTrait: traits.ComparerType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ cmp := lhs.(traits.Comparer).Compare(rhs)
+ if cmp == types.IntNegOne || cmp == types.IntZero {
+ return types.True
+ }
+ if cmp == types.IntOne {
+ return types.False
+ }
+ return cmp
+ }},
+
+ // Greater than operator
+ {Operator: operators.Greater,
+ OperandTrait: traits.ComparerType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ cmp := lhs.(traits.Comparer).Compare(rhs)
+ if cmp == types.IntOne {
+ return types.True
+ }
+ if cmp == types.IntNegOne || cmp == types.IntZero {
+ return types.False
+ }
+ return cmp
+ }},
+
+ // Greater than equal operators
+ {Operator: operators.GreaterEquals,
+ OperandTrait: traits.ComparerType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ cmp := lhs.(traits.Comparer).Compare(rhs)
+ if cmp == types.IntOne || cmp == types.IntZero {
+ return types.True
+ }
+ if cmp == types.IntNegOne {
+ return types.False
+ }
+ return cmp
+ }},
+
+ // TODO: Verify overflow, NaN, underflow cases for numeric values.
+
+ // Add operator
+ {Operator: operators.Add,
+ OperandTrait: traits.AdderType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ return lhs.(traits.Adder).Add(rhs)
+ }},
+
+ // Subtract operators
+ {Operator: operators.Subtract,
+ OperandTrait: traits.SubtractorType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ return lhs.(traits.Subtractor).Subtract(rhs)
+ }},
+
+ // Multiply operator
+ {Operator: operators.Multiply,
+ OperandTrait: traits.MultiplierType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ return lhs.(traits.Multiplier).Multiply(rhs)
+ }},
+
+ // Divide operator
+ {Operator: operators.Divide,
+ OperandTrait: traits.DividerType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ return lhs.(traits.Divider).Divide(rhs)
+ }},
+
+ // Modulo operator
+ {Operator: operators.Modulo,
+ OperandTrait: traits.ModderType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ return lhs.(traits.Modder).Modulo(rhs)
+ }},
+
+ // Negate operator
+ {Operator: operators.Negate,
+ OperandTrait: traits.NegatorType,
+ Unary: func(value ref.Val) ref.Val {
+ if types.IsBool(value) {
+ return types.ValOrErr(value, "no such overload")
+ }
+ return value.(traits.Negater).Negate()
+ }},
+
+ // Index operator
+ {Operator: operators.Index,
+ OperandTrait: traits.IndexerType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ return lhs.(traits.Indexer).Get(rhs)
+ }},
+
+ // Size function
+ {Operator: overloads.Size,
+ OperandTrait: traits.SizerType,
+ Unary: func(value ref.Val) ref.Val {
+ return value.(traits.Sizer).Size()
+ }},
+
+ // In operator
+ {Operator: operators.In, Binary: inAggregate},
+ // Deprecated: in operator, may be overridden in the environment.
+ {Operator: operators.OldIn, Binary: inAggregate},
+
+ // Matches function
+ {Operator: overloads.Matches,
+ OperandTrait: traits.MatcherType,
+ Binary: func(lhs ref.Val, rhs ref.Val) ref.Val {
+ return lhs.(traits.Matcher).Match(rhs)
+ }},
+
+ // Type conversion functions
+ // TODO: verify type conversion safety of numeric values.
+
+ // Int conversions.
+ {Operator: overloads.TypeConvertInt,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.IntType)
+ }},
+
+ // Uint conversions.
+ {Operator: overloads.TypeConvertUint,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.UintType)
+ }},
+
+ // Double conversions.
+ {Operator: overloads.TypeConvertDouble,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.DoubleType)
+ }},
+
+ // Bool conversions.
+ {Operator: overloads.TypeConvertBool,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.BoolType)
+ }},
+
+ // Bytes conversions.
+ {Operator: overloads.TypeConvertBytes,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.BytesType)
+ }},
+
+ // String conversions.
+ {Operator: overloads.TypeConvertString,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.StringType)
+ }},
+
+ // Timestamp conversions.
+ {Operator: overloads.TypeConvertTimestamp,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.TimestampType)
+ }},
+
+ // Duration conversions.
+ {Operator: overloads.TypeConvertDuration,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.DurationType)
+ }},
+
+ // Type operations.
+ {Operator: overloads.TypeConvertType,
+ Unary: func(value ref.Val) ref.Val {
+ return value.ConvertToType(types.TypeType)
+ }},
+
+ // Dyn conversion (identity function).
+ {Operator: overloads.TypeConvertDyn,
+ Unary: func(value ref.Val) ref.Val {
+ return value
+ }},
+
+ {Operator: overloads.Iterator,
+ OperandTrait: traits.IterableType,
+ Unary: func(value ref.Val) ref.Val {
+ return value.(traits.Iterable).Iterator()
+ }},
+
+ {Operator: overloads.HasNext,
+ OperandTrait: traits.IteratorType,
+ Unary: func(value ref.Val) ref.Val {
+ return value.(traits.Iterator).HasNext()
+ }},
+
+ {Operator: overloads.Next,
+ OperandTrait: traits.IteratorType,
+ Unary: func(value ref.Val) ref.Val {
+ return value.(traits.Iterator).Next()
+ }},
+ }
+
+}
+
+func notStrictlyFalse(value ref.Val) ref.Val {
+ if types.IsBool(value) {
+ return value
+ }
+ return types.True
+}
+
+func inAggregate(lhs ref.Val, rhs ref.Val) ref.Val {
+ if rhs.Type().HasTrait(traits.ContainerType) {
+ return rhs.(traits.Container).Contains(lhs)
+ }
+ return types.ValOrErr(rhs, "no such overload")
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/interpretable.go b/vendor/github.com/google/cel-go/interpreter/interpretable.go
new file mode 100644
index 0000000000..28af6d44b0
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/interpretable.go
@@ -0,0 +1,1204 @@
+// Copyright 2019 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "math"
+
+ "github.com/google/cel-go/common/operators"
+ "github.com/google/cel-go/common/overloads"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+ "github.com/google/cel-go/interpreter/functions"
+)
+
+// Interpretable can accept a given Activation and produce a value along with
+// an accompanying EvalState which can be used to inspect whether additional
+// data might be necessary to complete the evaluation.
+type Interpretable interface {
+ // ID value corresponding to the expression node.
+ ID() int64
+
+ // Eval an Activation to produce an output.
+ Eval(activation Activation) ref.Val
+}
+
+// InterpretableConst interface for tracking whether the Interpretable is a constant value.
+type InterpretableConst interface {
+ Interpretable
+
+ // Value returns the constant value of the instruction.
+ Value() ref.Val
+}
+
+// InterpretableAttribute interface for tracking whether the Interpretable is an attribute.
+type InterpretableAttribute interface {
+ Interpretable
+
+ // Attr returns the Attribute value.
+ Attr() Attribute
+
+ // Adapter returns the type adapter to be used for adapting resolved Attribute values.
+ Adapter() ref.TypeAdapter
+
+ // AddQualifier proxies the Attribute.AddQualifier method.
+ //
+ // Note, this method may mutate the current attribute state. If the desire is to clone the
+ // Attribute, the Attribute should first be copied before adding the qualifier. Attributes
+ // are not copyable by default, so this is a capable that would need to be added to the
+ // AttributeFactory or specifically to the underlying Attribute implementation.
+ AddQualifier(Qualifier) (Attribute, error)
+
+ // Qualify replicates the Attribute.Qualify method to permit extension and interception
+ // of object qualification.
+ Qualify(vars Activation, obj interface{}) (interface{}, error)
+
+ // Resolve returns the value of the Attribute given the current Activation.
+ Resolve(Activation) (interface{}, error)
+}
+
+// InterpretableCall interface for inspecting Interpretable instructions related to function calls.
+type InterpretableCall interface {
+ Interpretable
+
+ // Function returns the function name as it appears in text or mangled operator name as it
+ // appears in the operators.go file.
+ Function() string
+
+ // OverloadID returns the overload id associated with the function specialization.
+ // Overload ids are stable across language boundaries and can be treated as synonymous with a
+ // unique function signature.
+ OverloadID() string
+
+ // Args returns the normalized arguments to the function overload.
+ // For receiver-style functions, the receiver target is arg 0.
+ Args() []Interpretable
+}
+
+// Core Interpretable implementations used during the program planning phase.
+
+type evalTestOnly struct {
+ id int64
+ op Interpretable
+ field types.String
+ fieldType *ref.FieldType
+}
+
+// ID implements the Interpretable interface method.
+func (test *evalTestOnly) ID() int64 {
+ return test.id
+}
+
+// Eval implements the Interpretable interface method.
+func (test *evalTestOnly) Eval(ctx Activation) ref.Val {
+ // Handle field selection on a proto in the most efficient way possible.
+ if test.fieldType != nil {
+ opAttr, ok := test.op.(InterpretableAttribute)
+ if ok {
+ opVal, err := opAttr.Resolve(ctx)
+ if err != nil {
+ return types.NewErr(err.Error())
+ }
+ refVal, ok := opVal.(ref.Val)
+ if ok {
+ opVal = refVal.Value()
+ }
+ if test.fieldType.IsSet(opVal) {
+ return types.True
+ }
+ return types.False
+ }
+ }
+
+ obj := test.op.Eval(ctx)
+ tester, ok := obj.(traits.FieldTester)
+ if ok {
+ return tester.IsSet(test.field)
+ }
+ container, ok := obj.(traits.Container)
+ if ok {
+ return container.Contains(test.field)
+ }
+ return types.ValOrErr(obj, "invalid type for field selection.")
+}
+
+// Cost provides the heuristic cost of a `has(field)` macro. The cost has at least 1 for determining
+// if the field exists, apart from the cost of accessing the field.
+func (test *evalTestOnly) Cost() (min, max int64) {
+ min, max = estimateCost(test.op)
+ min++
+ max++
+ return
+}
+
+// NewConstValue creates a new constant valued Interpretable.
+func NewConstValue(id int64, val ref.Val) InterpretableConst {
+ return &evalConst{
+ id: id,
+ val: val,
+ }
+}
+
+type evalConst struct {
+ id int64
+ val ref.Val
+}
+
+// ID implements the Interpretable interface method.
+func (cons *evalConst) ID() int64 {
+ return cons.id
+}
+
+// Eval implements the Interpretable interface method.
+func (cons *evalConst) Eval(ctx Activation) ref.Val {
+ return cons.val
+}
+
+// Cost returns zero for a constant valued Interpretable.
+func (cons *evalConst) Cost() (min, max int64) {
+ return 0, 0
+}
+
+// Value implements the InterpretableConst interface method.
+func (cons *evalConst) Value() ref.Val {
+ return cons.val
+}
+
+type evalOr struct {
+ id int64
+ lhs Interpretable
+ rhs Interpretable
+}
+
+// ID implements the Interpretable interface method.
+func (or *evalOr) ID() int64 {
+ return or.id
+}
+
+// Eval implements the Interpretable interface method.
+func (or *evalOr) Eval(ctx Activation) ref.Val {
+ // short-circuit lhs.
+ lVal := or.lhs.Eval(ctx)
+ lBool, lok := lVal.(types.Bool)
+ if lok && lBool == types.True {
+ return types.True
+ }
+ // short-circuit on rhs.
+ rVal := or.rhs.Eval(ctx)
+ rBool, rok := rVal.(types.Bool)
+ if rok && rBool == types.True {
+ return types.True
+ }
+ // return if both sides are bool false.
+ if lok && rok {
+ return types.False
+ }
+ // TODO: return both values as a set if both are unknown or error.
+ // prefer left unknown to right unknown.
+ if types.IsUnknown(lVal) {
+ return lVal
+ }
+ if types.IsUnknown(rVal) {
+ return rVal
+ }
+ // If the left-hand side is non-boolean return it as the error.
+ if types.IsError(lVal) {
+ return lVal
+ }
+ return types.ValOrErr(rVal, "no such overload")
+}
+
+// Cost implements the Coster interface method. The minimum possible cost incurs when the left-hand
+// side expr is sufficient in determining the evaluation result.
+func (or *evalOr) Cost() (min, max int64) {
+ return calShortCircuitBinaryOpsCost(or.lhs, or.rhs)
+}
+
+type evalAnd struct {
+ id int64
+ lhs Interpretable
+ rhs Interpretable
+}
+
+// ID implements the Interpretable interface method.
+func (and *evalAnd) ID() int64 {
+ return and.id
+}
+
+// Eval implements the Interpretable interface method.
+func (and *evalAnd) Eval(ctx Activation) ref.Val {
+ // short-circuit lhs.
+ lVal := and.lhs.Eval(ctx)
+ lBool, lok := lVal.(types.Bool)
+ if lok && lBool == types.False {
+ return types.False
+ }
+ // short-circuit on rhs.
+ rVal := and.rhs.Eval(ctx)
+ rBool, rok := rVal.(types.Bool)
+ if rok && rBool == types.False {
+ return types.False
+ }
+ // return if both sides are bool true.
+ if lok && rok {
+ return types.True
+ }
+ // TODO: return both values as a set if both are unknown or error.
+ // prefer left unknown to right unknown.
+ if types.IsUnknown(lVal) {
+ return lVal
+ }
+ if types.IsUnknown(rVal) {
+ return rVal
+ }
+ // If the left-hand side is non-boolean return it as the error.
+ if types.IsError(lVal) {
+ return lVal
+ }
+ return types.ValOrErr(rVal, "no such overload")
+}
+
+// Cost implements the Coster interface method. The minimum possible cost incurs when the left-hand
+// side expr is sufficient in determining the evaluation result.
+func (and *evalAnd) Cost() (min, max int64) {
+ return calShortCircuitBinaryOpsCost(and.lhs, and.rhs)
+}
+
+func calShortCircuitBinaryOpsCost(lhs, rhs Interpretable) (min, max int64) {
+ lMin, lMax := estimateCost(lhs)
+ _, rMax := estimateCost(rhs)
+ return lMin, lMax + rMax + 1
+}
+
+type evalEq struct {
+ id int64
+ lhs Interpretable
+ rhs Interpretable
+}
+
+// ID implements the Interpretable interface method.
+func (eq *evalEq) ID() int64 {
+ return eq.id
+}
+
+// Eval implements the Interpretable interface method.
+func (eq *evalEq) Eval(ctx Activation) ref.Val {
+ lVal := eq.lhs.Eval(ctx)
+ rVal := eq.rhs.Eval(ctx)
+ return lVal.Equal(rVal)
+}
+
+// Cost implements the Coster interface method.
+func (eq *evalEq) Cost() (min, max int64) {
+ return calExhaustiveBinaryOpsCost(eq.lhs, eq.rhs)
+}
+
+// Function implements the InterpretableCall interface method.
+func (*evalEq) Function() string {
+ return operators.Equals
+}
+
+// OverloadID implements the InterpretableCall interface method.
+func (*evalEq) OverloadID() string {
+ return overloads.Equals
+}
+
+// Args implements the InterpretableCall interface method.
+func (eq *evalEq) Args() []Interpretable {
+ return []Interpretable{eq.lhs, eq.rhs}
+}
+
+type evalNe struct {
+ id int64
+ lhs Interpretable
+ rhs Interpretable
+}
+
+// ID implements the Interpretable interface method.
+func (ne *evalNe) ID() int64 {
+ return ne.id
+}
+
+// Eval implements the Interpretable interface method.
+func (ne *evalNe) Eval(ctx Activation) ref.Val {
+ lVal := ne.lhs.Eval(ctx)
+ rVal := ne.rhs.Eval(ctx)
+ eqVal := lVal.Equal(rVal)
+ eqBool, ok := eqVal.(types.Bool)
+ if !ok {
+ return types.ValOrErr(eqVal, "no such overload: _!=_")
+ }
+ return !eqBool
+}
+
+// Cost implements the Coster interface method.
+func (ne *evalNe) Cost() (min, max int64) {
+ return calExhaustiveBinaryOpsCost(ne.lhs, ne.rhs)
+}
+
+// Function implements the InterpretableCall interface method.
+func (*evalNe) Function() string {
+ return operators.NotEquals
+}
+
+// OverloadID implements the InterpretableCall interface method.
+func (*evalNe) OverloadID() string {
+ return overloads.NotEquals
+}
+
+// Args implements the InterpretableCall interface method.
+func (ne *evalNe) Args() []Interpretable {
+ return []Interpretable{ne.lhs, ne.rhs}
+}
+
+type evalZeroArity struct {
+ id int64
+ function string
+ overload string
+ impl functions.FunctionOp
+}
+
+// ID implements the Interpretable interface method.
+func (zero *evalZeroArity) ID() int64 {
+ return zero.id
+}
+
+// Eval implements the Interpretable interface method.
+func (zero *evalZeroArity) Eval(ctx Activation) ref.Val {
+ return zero.impl()
+}
+
+// Cost returns 1 representing the heuristic cost of the function.
+func (zero *evalZeroArity) Cost() (min, max int64) {
+ return 1, 1
+}
+
+// Function implements the InterpretableCall interface method.
+func (zero *evalZeroArity) Function() string {
+ return zero.function
+}
+
+// OverloadID implements the InterpretableCall interface method.
+func (zero *evalZeroArity) OverloadID() string {
+ return zero.overload
+}
+
+// Args returns the argument to the unary function.
+func (zero *evalZeroArity) Args() []Interpretable {
+ return []Interpretable{}
+}
+
+type evalUnary struct {
+ id int64
+ function string
+ overload string
+ arg Interpretable
+ trait int
+ impl functions.UnaryOp
+}
+
+// ID implements the Interpretable interface method.
+func (un *evalUnary) ID() int64 {
+ return un.id
+}
+
+// Eval implements the Interpretable interface method.
+func (un *evalUnary) Eval(ctx Activation) ref.Val {
+ argVal := un.arg.Eval(ctx)
+ // Early return if the argument to the function is unknown or error.
+ if types.IsUnknownOrError(argVal) {
+ return argVal
+ }
+ // If the implementation is bound and the argument value has the right traits required to
+ // invoke it, then call the implementation.
+ if un.impl != nil && (un.trait == 0 || argVal.Type().HasTrait(un.trait)) {
+ return un.impl(argVal)
+ }
+ // Otherwise, if the argument is a ReceiverType attempt to invoke the receiver method on the
+ // operand (arg0).
+ if argVal.Type().HasTrait(traits.ReceiverType) {
+ return argVal.(traits.Receiver).Receive(un.function, un.overload, []ref.Val{})
+ }
+ return types.NewErr("no such overload: %s", un.function)
+}
+
+// Cost implements the Coster interface method.
+func (un *evalUnary) Cost() (min, max int64) {
+ min, max = estimateCost(un.arg)
+ min++ // add cost for function
+ max++
+ return
+}
+
+// Function implements the InterpretableCall interface method.
+func (un *evalUnary) Function() string {
+ return un.function
+}
+
+// OverloadID implements the InterpretableCall interface method.
+func (un *evalUnary) OverloadID() string {
+ return un.overload
+}
+
+// Args returns the argument to the unary function.
+func (un *evalUnary) Args() []Interpretable {
+ return []Interpretable{un.arg}
+}
+
+type evalBinary struct {
+ id int64
+ function string
+ overload string
+ lhs Interpretable
+ rhs Interpretable
+ trait int
+ impl functions.BinaryOp
+}
+
+// ID implements the Interpretable interface method.
+func (bin *evalBinary) ID() int64 {
+ return bin.id
+}
+
+// Eval implements the Interpretable interface method.
+func (bin *evalBinary) Eval(ctx Activation) ref.Val {
+ lVal := bin.lhs.Eval(ctx)
+ rVal := bin.rhs.Eval(ctx)
+ // Early return if any argument to the function is unknown or error.
+ if types.IsUnknownOrError(lVal) {
+ return lVal
+ }
+ if types.IsUnknownOrError(rVal) {
+ return rVal
+ }
+ // If the implementation is bound and the argument value has the right traits required to
+ // invoke it, then call the implementation.
+ if bin.impl != nil && (bin.trait == 0 || lVal.Type().HasTrait(bin.trait)) {
+ return bin.impl(lVal, rVal)
+ }
+ // Otherwise, if the argument is a ReceiverType attempt to invoke the receiver method on the
+ // operand (arg0).
+ if lVal.Type().HasTrait(traits.ReceiverType) {
+ return lVal.(traits.Receiver).Receive(bin.function, bin.overload, []ref.Val{rVal})
+ }
+ return types.NewErr("no such overload: %s", bin.function)
+}
+
+// Cost implements the Coster interface method.
+func (bin *evalBinary) Cost() (min, max int64) {
+ return calExhaustiveBinaryOpsCost(bin.lhs, bin.rhs)
+}
+
+// Function implements the InterpretableCall interface method.
+func (bin *evalBinary) Function() string {
+ return bin.function
+}
+
+// OverloadID implements the InterpretableCall interface method.
+func (bin *evalBinary) OverloadID() string {
+ return bin.overload
+}
+
+// Args returns the argument to the unary function.
+func (bin *evalBinary) Args() []Interpretable {
+ return []Interpretable{bin.lhs, bin.rhs}
+}
+
+type evalVarArgs struct {
+ id int64
+ function string
+ overload string
+ args []Interpretable
+ trait int
+ impl functions.FunctionOp
+}
+
+// ID implements the Interpretable interface method.
+func (fn *evalVarArgs) ID() int64 {
+ return fn.id
+}
+
+// Eval implements the Interpretable interface method.
+func (fn *evalVarArgs) Eval(ctx Activation) ref.Val {
+ argVals := make([]ref.Val, len(fn.args))
+ // Early return if any argument to the function is unknown or error.
+ for i, arg := range fn.args {
+ argVals[i] = arg.Eval(ctx)
+ if types.IsUnknownOrError(argVals[i]) {
+ return argVals[i]
+ }
+ }
+ // If the implementation is bound and the argument value has the right traits required to
+ // invoke it, then call the implementation.
+ arg0 := argVals[0]
+ if fn.impl != nil && (fn.trait == 0 || arg0.Type().HasTrait(fn.trait)) {
+ return fn.impl(argVals...)
+ }
+ // Otherwise, if the argument is a ReceiverType attempt to invoke the receiver method on the
+ // operand (arg0).
+ if arg0.Type().HasTrait(traits.ReceiverType) {
+ return arg0.(traits.Receiver).Receive(fn.function, fn.overload, argVals[1:])
+ }
+ return types.NewErr("no such overload: %s", fn.function)
+}
+
+// Cost implements the Coster interface method.
+func (fn *evalVarArgs) Cost() (min, max int64) {
+ min, max = sumOfCost(fn.args)
+ min++ // add cost for function
+ max++
+ return
+}
+
+// Function implements the InterpretableCall interface method.
+func (fn *evalVarArgs) Function() string {
+ return fn.function
+}
+
+// OverloadID implements the InterpretableCall interface method.
+func (fn *evalVarArgs) OverloadID() string {
+ return fn.overload
+}
+
+// Args returns the argument to the unary function.
+func (fn *evalVarArgs) Args() []Interpretable {
+ return fn.args
+}
+
+type evalList struct {
+ id int64
+ elems []Interpretable
+ adapter ref.TypeAdapter
+}
+
+// ID implements the Interpretable interface method.
+func (l *evalList) ID() int64 {
+ return l.id
+}
+
+// Eval implements the Interpretable interface method.
+func (l *evalList) Eval(ctx Activation) ref.Val {
+ elemVals := make([]ref.Val, len(l.elems))
+ // If any argument is unknown or error early terminate.
+ for i, elem := range l.elems {
+ elemVal := elem.Eval(ctx)
+ if types.IsUnknownOrError(elemVal) {
+ return elemVal
+ }
+ elemVals[i] = elemVal
+ }
+ return l.adapter.NativeToValue(elemVals)
+}
+
+// Cost implements the Coster interface method.
+func (l *evalList) Cost() (min, max int64) {
+ return sumOfCost(l.elems)
+}
+
+type evalMap struct {
+ id int64
+ keys []Interpretable
+ vals []Interpretable
+ adapter ref.TypeAdapter
+}
+
+// ID implements the Interpretable interface method.
+func (m *evalMap) ID() int64 {
+ return m.id
+}
+
+// Eval implements the Interpretable interface method.
+func (m *evalMap) Eval(ctx Activation) ref.Val {
+ entries := make(map[ref.Val]ref.Val)
+ // If any argument is unknown or error early terminate.
+ for i, key := range m.keys {
+ keyVal := key.Eval(ctx)
+ if types.IsUnknownOrError(keyVal) {
+ return keyVal
+ }
+ valVal := m.vals[i].Eval(ctx)
+ if types.IsUnknownOrError(valVal) {
+ return valVal
+ }
+ entries[keyVal] = valVal
+ }
+ return m.adapter.NativeToValue(entries)
+}
+
+// Cost implements the Coster interface method.
+func (m *evalMap) Cost() (min, max int64) {
+ kMin, kMax := sumOfCost(m.keys)
+ vMin, vMax := sumOfCost(m.vals)
+ return kMin + vMin, kMax + vMax
+}
+
+type evalObj struct {
+ id int64
+ typeName string
+ fields []string
+ vals []Interpretable
+ provider ref.TypeProvider
+}
+
+// ID implements the Interpretable interface method.
+func (o *evalObj) ID() int64 {
+ return o.id
+}
+
+// Eval implements the Interpretable interface method.
+func (o *evalObj) Eval(ctx Activation) ref.Val {
+ fieldVals := make(map[string]ref.Val)
+ // If any argument is unknown or error early terminate.
+ for i, field := range o.fields {
+ val := o.vals[i].Eval(ctx)
+ if types.IsUnknownOrError(val) {
+ return val
+ }
+ fieldVals[field] = val
+ }
+ return o.provider.NewValue(o.typeName, fieldVals)
+}
+
+// Cost implements the Coster interface method.
+func (o *evalObj) Cost() (min, max int64) {
+ return sumOfCost(o.vals)
+}
+
+func sumOfCost(interps []Interpretable) (min, max int64) {
+ min, max = 0, 0
+ for _, in := range interps {
+ minT, maxT := estimateCost(in)
+ min += minT
+ max += maxT
+ }
+ return
+}
+
+type evalFold struct {
+ id int64
+ accuVar string
+ iterVar string
+ iterRange Interpretable
+ accu Interpretable
+ cond Interpretable
+ step Interpretable
+ result Interpretable
+}
+
+// ID implements the Interpretable interface method.
+func (fold *evalFold) ID() int64 {
+ return fold.id
+}
+
+// Eval implements the Interpretable interface method.
+func (fold *evalFold) Eval(ctx Activation) ref.Val {
+ foldRange := fold.iterRange.Eval(ctx)
+ if !foldRange.Type().HasTrait(traits.IterableType) {
+ return types.ValOrErr(foldRange, "got '%T', expected iterable type", foldRange)
+ }
+ // Configure the fold activation with the accumulator initial value.
+ accuCtx := varActivationPool.Get().(*varActivation)
+ accuCtx.parent = ctx
+ accuCtx.name = fold.accuVar
+ accuCtx.val = fold.accu.Eval(ctx)
+ iterCtx := varActivationPool.Get().(*varActivation)
+ iterCtx.parent = accuCtx
+ iterCtx.name = fold.iterVar
+ it := foldRange.(traits.Iterable).Iterator()
+ for it.HasNext() == types.True {
+ // Modify the iter var in the fold activation.
+ iterCtx.val = it.Next()
+
+ // Evaluate the condition, terminate the loop if false.
+ cond := fold.cond.Eval(iterCtx)
+ condBool, ok := cond.(types.Bool)
+ if !types.IsUnknown(cond) && ok && condBool != types.True {
+ break
+ }
+
+ // Evalute the evaluation step into accu var.
+ accuCtx.val = fold.step.Eval(iterCtx)
+ }
+ // Compute the result.
+ res := fold.result.Eval(accuCtx)
+ varActivationPool.Put(iterCtx)
+ varActivationPool.Put(accuCtx)
+ return res
+}
+
+// Cost implements the Coster interface method.
+func (fold *evalFold) Cost() (min, max int64) {
+ // Compute the cost for evaluating iterRange.
+ iMin, iMax := estimateCost(fold.iterRange)
+
+ // Compute the size of iterRange. If the size depends on the input, return the maximum possible
+ // cost range.
+ foldRange := fold.iterRange.Eval(EmptyActivation())
+ if !foldRange.Type().HasTrait(traits.IterableType) {
+ return 0, math.MaxInt64
+ }
+ var rangeCnt int64
+ it := foldRange.(traits.Iterable).Iterator()
+ for it.HasNext() == types.True {
+ it.Next()
+ rangeCnt++
+ }
+ aMin, aMax := estimateCost(fold.accu)
+ cMin, cMax := estimateCost(fold.cond)
+ sMin, sMax := estimateCost(fold.step)
+ rMin, rMax := estimateCost(fold.result)
+
+ // The cond and step costs are multiplied by size(iterRange). The minimum possible cost incurs
+ // when the evaluation result can be determined by the first iteration.
+ return iMin + aMin + cMin + sMin + rMin,
+ iMax + aMax + cMax*rangeCnt + sMax*rangeCnt + rMax
+}
+
+// Optional Intepretable implementations that specialize, subsume, or extend the core evaluation
+// plan via decorators.
+
+// evalSetMembership is an Interpretable implementation which tests whether an input value
+// exists within the set of map keys used to model a set.
+type evalSetMembership struct {
+ inst Interpretable
+ arg Interpretable
+ argTypeName string
+ valueSet map[ref.Val]ref.Val
+}
+
+// ID implements the Interpretable interface method.
+func (e *evalSetMembership) ID() int64 {
+ return e.inst.ID()
+}
+
+// Eval implements the Interpretable interface method.
+func (e *evalSetMembership) Eval(ctx Activation) ref.Val {
+ val := e.arg.Eval(ctx)
+ if val.Type().TypeName() != e.argTypeName {
+ return types.ValOrErr(val, "no such overload")
+ }
+ if ret, found := e.valueSet[val]; found {
+ return ret
+ }
+ return types.False
+}
+
+// Cost implements the Coster interface method.
+func (e *evalSetMembership) Cost() (min, max int64) {
+ return estimateCost(e.arg)
+}
+
+// evalWatch is an Interpretable implementation that wraps the execution of a given
+// expression so that it may observe the computed value and send it to an observer.
+type evalWatch struct {
+ Interpretable
+ observer evalObserver
+}
+
+// Eval implements the Interpretable interface method.
+func (e *evalWatch) Eval(ctx Activation) ref.Val {
+ val := e.Interpretable.Eval(ctx)
+ e.observer(e.ID(), val)
+ return val
+}
+
+// Cost implements the Coster interface method.
+func (e *evalWatch) Cost() (min, max int64) {
+ return estimateCost(e.Interpretable)
+}
+
+// evalWatchAttr describes a watcher of an instAttr Interpretable.
+//
+// Since the watcher may be selected against at a later stage in program planning, the watcher
+// must implement the instAttr interface by proxy.
+type evalWatchAttr struct {
+ InterpretableAttribute
+ observer evalObserver
+}
+
+// AddQualifier creates a wrapper over the incoming qualifier which observes the qualification
+// result.
+func (e *evalWatchAttr) AddQualifier(q Qualifier) (Attribute, error) {
+ cq, isConst := q.(ConstantQualifier)
+ if isConst {
+ q = &evalWatchConstQual{
+ ConstantQualifier: cq,
+ observer: e.observer,
+ adapter: e.InterpretableAttribute.Adapter(),
+ }
+ } else {
+ q = &evalWatchQual{
+ Qualifier: q,
+ observer: e.observer,
+ adapter: e.InterpretableAttribute.Adapter(),
+ }
+ }
+ _, err := e.InterpretableAttribute.AddQualifier(q)
+ return e, err
+}
+
+// evalWatchConstQual observes the qualification of an object using a constant boolean, int,
+// string, or uint.
+type evalWatchConstQual struct {
+ ConstantQualifier
+ observer evalObserver
+ adapter ref.TypeAdapter
+}
+
+// Cost implements the Coster interface method.
+func (e *evalWatchConstQual) Cost() (min, max int64) {
+ return estimateCost(e.ConstantQualifier)
+}
+
+// Qualify observes the qualification of a object via a constant boolean, int, string, or uint.
+func (e *evalWatchConstQual) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ out, err := e.ConstantQualifier.Qualify(vars, obj)
+ var val ref.Val
+ if err != nil {
+ val = types.NewErr(err.Error())
+ } else {
+ val = e.adapter.NativeToValue(out)
+ }
+ e.observer(e.ID(), val)
+ return out, err
+}
+
+// QualifierValueEquals tests whether the incoming value is equal to the qualificying constant.
+func (e *evalWatchConstQual) QualifierValueEquals(value interface{}) bool {
+ qve, ok := e.ConstantQualifier.(qualifierValueEquator)
+ return ok && qve.QualifierValueEquals(value)
+}
+
+// evalWatchQual observes the qualification of an object by a value computed at runtime.
+type evalWatchQual struct {
+ Qualifier
+ observer evalObserver
+ adapter ref.TypeAdapter
+}
+
+// Cost implements the Coster interface method.
+func (e *evalWatchQual) Cost() (min, max int64) {
+ return estimateCost(e.Qualifier)
+}
+
+// Qualify observes the qualification of a object via a value computed at runtime.
+func (e *evalWatchQual) Qualify(vars Activation, obj interface{}) (interface{}, error) {
+ out, err := e.Qualifier.Qualify(vars, obj)
+ var val ref.Val
+ if err != nil {
+ val = types.NewErr(err.Error())
+ } else {
+ val = e.adapter.NativeToValue(out)
+ }
+ e.observer(e.ID(), val)
+ return out, err
+}
+
+// Cost implements the Coster interface method.
+func (e *evalWatchAttr) Cost() (min, max int64) {
+ return estimateCost(e.InterpretableAttribute)
+}
+
+// Eval implements the Interpretable interface method.
+func (e *evalWatchAttr) Eval(vars Activation) ref.Val {
+ val := e.InterpretableAttribute.Eval(vars)
+ e.observer(e.ID(), val)
+ return val
+}
+
+// evalWatchConst describes a watcher of an instConst Interpretable.
+type evalWatchConst struct {
+ InterpretableConst
+ observer evalObserver
+}
+
+// Eval implements the Interpretable interface method.
+func (e *evalWatchConst) Eval(vars Activation) ref.Val {
+ val := e.Value()
+ e.observer(e.ID(), val)
+ return val
+}
+
+// Cost implements the Coster interface method.
+func (e *evalWatchConst) Cost() (min, max int64) {
+ return estimateCost(e.InterpretableConst)
+}
+
+// evalExhaustiveOr is just like evalOr, but does not short-circuit argument evaluation.
+type evalExhaustiveOr struct {
+ id int64
+ lhs Interpretable
+ rhs Interpretable
+}
+
+// ID implements the Interpretable interface method.
+func (or *evalExhaustiveOr) ID() int64 {
+ return or.id
+}
+
+// Eval implements the Interpretable interface method.
+func (or *evalExhaustiveOr) Eval(ctx Activation) ref.Val {
+ lVal := or.lhs.Eval(ctx)
+ rVal := or.rhs.Eval(ctx)
+ lBool, lok := lVal.(types.Bool)
+ if lok && lBool == types.True {
+ return types.True
+ }
+ rBool, rok := rVal.(types.Bool)
+ if rok && rBool == types.True {
+ return types.True
+ }
+ if lok && rok {
+ return types.False
+ }
+ if types.IsUnknown(lVal) {
+ return lVal
+ }
+ if types.IsUnknown(rVal) {
+ return rVal
+ }
+ // TODO: Combine the errors into a set in the future.
+ // If the left-hand side is non-boolean return it as the error.
+ if types.IsError(lVal) {
+ return lVal
+ }
+ return types.ValOrErr(rVal, "no such overload")
+}
+
+// Cost implements the Coster interface method.
+func (or *evalExhaustiveOr) Cost() (min, max int64) {
+ return calExhaustiveBinaryOpsCost(or.lhs, or.rhs)
+}
+
+// evalExhaustiveAnd is just like evalAnd, but does not short-circuit argument evaluation.
+type evalExhaustiveAnd struct {
+ id int64
+ lhs Interpretable
+ rhs Interpretable
+}
+
+// ID implements the Interpretable interface method.
+func (and *evalExhaustiveAnd) ID() int64 {
+ return and.id
+}
+
+// Eval implements the Interpretable interface method.
+func (and *evalExhaustiveAnd) Eval(ctx Activation) ref.Val {
+ lVal := and.lhs.Eval(ctx)
+ rVal := and.rhs.Eval(ctx)
+ lBool, lok := lVal.(types.Bool)
+ if lok && lBool == types.False {
+ return types.False
+ }
+ rBool, rok := rVal.(types.Bool)
+ if rok && rBool == types.False {
+ return types.False
+ }
+ if lok && rok {
+ return types.True
+ }
+ if types.IsUnknown(lVal) {
+ return lVal
+ }
+ if types.IsUnknown(rVal) {
+ return rVal
+ }
+ // TODO: Combine the errors into a set in the future.
+ // If the left-hand side is non-boolean return it as the error.
+ if types.IsError(lVal) {
+ return lVal
+ }
+ return types.ValOrErr(rVal, "no such overload")
+}
+
+// Cost implements the Coster interface method.
+func (and *evalExhaustiveAnd) Cost() (min, max int64) {
+ return calExhaustiveBinaryOpsCost(and.lhs, and.rhs)
+}
+
+func calExhaustiveBinaryOpsCost(lhs, rhs Interpretable) (min, max int64) {
+ lMin, lMax := estimateCost(lhs)
+ rMin, rMax := estimateCost(rhs)
+ return lMin + rMin + 1, lMax + rMax + 1
+}
+
+// evalExhaustiveConditional is like evalConditional, but does not short-circuit argument
+// evaluation.
+type evalExhaustiveConditional struct {
+ id int64
+ adapter ref.TypeAdapter
+ attr *conditionalAttribute
+}
+
+// ID implements the Interpretable interface method.
+func (cond *evalExhaustiveConditional) ID() int64 {
+ return cond.id
+}
+
+// Eval implements the Interpretable interface method.
+func (cond *evalExhaustiveConditional) Eval(ctx Activation) ref.Val {
+ cVal := cond.attr.expr.Eval(ctx)
+ tVal, err := cond.attr.truthy.Resolve(ctx)
+ if err != nil {
+ return types.NewErr(err.Error())
+ }
+ fVal, err := cond.attr.falsy.Resolve(ctx)
+ if err != nil {
+ return types.NewErr(err.Error())
+ }
+ cBool, ok := cVal.(types.Bool)
+ if !ok {
+ return types.ValOrErr(cVal, "no such overload")
+ }
+ if cBool {
+ return cond.adapter.NativeToValue(tVal)
+ }
+ return cond.adapter.NativeToValue(fVal)
+}
+
+// Cost implements the Coster interface method.
+func (cond *evalExhaustiveConditional) Cost() (min, max int64) {
+ return cond.attr.Cost()
+}
+
+// evalExhaustiveFold is like evalFold, but does not short-circuit argument evaluation.
+type evalExhaustiveFold struct {
+ id int64
+ accuVar string
+ iterVar string
+ iterRange Interpretable
+ accu Interpretable
+ cond Interpretable
+ step Interpretable
+ result Interpretable
+}
+
+// ID implements the Interpretable interface method.
+func (fold *evalExhaustiveFold) ID() int64 {
+ return fold.id
+}
+
+// Eval implements the Interpretable interface method.
+func (fold *evalExhaustiveFold) Eval(ctx Activation) ref.Val {
+ foldRange := fold.iterRange.Eval(ctx)
+ if !foldRange.Type().HasTrait(traits.IterableType) {
+ return types.ValOrErr(foldRange, "got '%T', expected iterable type", foldRange)
+ }
+ // Configure the fold activation with the accumulator initial value.
+ accuCtx := varActivationPool.Get().(*varActivation)
+ accuCtx.parent = ctx
+ accuCtx.name = fold.accuVar
+ accuCtx.val = fold.accu.Eval(ctx)
+ iterCtx := varActivationPool.Get().(*varActivation)
+ iterCtx.parent = accuCtx
+ iterCtx.name = fold.iterVar
+ it := foldRange.(traits.Iterable).Iterator()
+ for it.HasNext() == types.True {
+ // Modify the iter var in the fold activation.
+ iterCtx.val = it.Next()
+
+ // Evaluate the condition, but don't terminate the loop as this is exhaustive eval!
+ fold.cond.Eval(iterCtx)
+
+ // Evalute the evaluation step into accu var.
+ accuCtx.val = fold.step.Eval(iterCtx)
+ }
+ // Compute the result.
+ res := fold.result.Eval(accuCtx)
+ varActivationPool.Put(iterCtx)
+ varActivationPool.Put(accuCtx)
+ return res
+}
+
+// Cost implements the Coster interface method.
+func (fold *evalExhaustiveFold) Cost() (min, max int64) {
+ // Compute the cost for evaluating iterRange.
+ iMin, iMax := estimateCost(fold.iterRange)
+
+ // Compute the size of iterRange. If the size depends on the input, return the maximum possible
+ // cost range.
+ foldRange := fold.iterRange.Eval(EmptyActivation())
+ if !foldRange.Type().HasTrait(traits.IterableType) {
+ return 0, math.MaxInt64
+ }
+ var rangeCnt int64
+ it := foldRange.(traits.Iterable).Iterator()
+ for it.HasNext() == types.True {
+ it.Next()
+ rangeCnt++
+ }
+
+ aMin, aMax := estimateCost(fold.accu)
+ cMin, cMax := estimateCost(fold.cond)
+ sMin, sMax := estimateCost(fold.step)
+ rMin, rMax := estimateCost(fold.result)
+
+ // The cond and step costs are multiplied by size(iterRange).
+ return iMin + aMin + cMin*rangeCnt + sMin*rangeCnt + rMin,
+ iMax + aMax + cMax*rangeCnt + sMax*rangeCnt + rMax
+}
+
+// evalAttr evaluates an Attribute value.
+type evalAttr struct {
+ adapter ref.TypeAdapter
+ attr Attribute
+}
+
+// ID of the attribute instruction.
+func (a *evalAttr) ID() int64 {
+ return a.attr.ID()
+}
+
+// AddQualifier implements the instAttr interface method.
+func (a *evalAttr) AddQualifier(qual Qualifier) (Attribute, error) {
+ attr, err := a.attr.AddQualifier(qual)
+ a.attr = attr
+ return attr, err
+}
+
+// Attr implements the instAttr interface method.
+func (a *evalAttr) Attr() Attribute {
+ return a.attr
+}
+
+// Adapter implements the instAttr interface method.
+func (a *evalAttr) Adapter() ref.TypeAdapter {
+ return a.adapter
+}
+
+// Cost implements the Coster interface method.
+func (a *evalAttr) Cost() (min, max int64) {
+ return estimateCost(a.attr)
+}
+
+// Eval implements the Interpretable interface method.
+func (a *evalAttr) Eval(ctx Activation) ref.Val {
+ v, err := a.attr.Resolve(ctx)
+ if err != nil {
+ return types.NewErr(err.Error())
+ }
+ return a.adapter.NativeToValue(v)
+}
+
+// Qualify proxies to the Attribute's Qualify method.
+func (a *evalAttr) Qualify(ctx Activation, obj interface{}) (interface{}, error) {
+ return a.attr.Qualify(ctx, obj)
+}
+
+// Resolve proxies to the Attribute's Resolve method.
+func (a *evalAttr) Resolve(ctx Activation) (interface{}, error) {
+ return a.attr.Resolve(ctx)
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/interpreter.go b/vendor/github.com/google/cel-go/interpreter/interpreter.go
new file mode 100644
index 0000000000..6ffc41efe1
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/interpreter.go
@@ -0,0 +1,137 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package interpreter provides functions to evaluate parsed expressions with
+// the option to augment the evaluation with inputs and functions supplied at
+// evaluation time.
+package interpreter
+
+import (
+ "github.com/google/cel-go/common/containers"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/interpreter/functions"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// Interpreter generates a new Interpretable from a checked or unchecked expression.
+type Interpreter interface {
+ // NewInterpretable creates an Interpretable from a checked expression and an
+ // optional list of InterpretableDecorator values.
+ NewInterpretable(checked *exprpb.CheckedExpr,
+ decorators ...InterpretableDecorator) (Interpretable, error)
+
+ // NewUncheckedInterpretable returns an Interpretable from a parsed expression
+ // and an optional list of InterpretableDecorator values.
+ NewUncheckedInterpretable(expr *exprpb.Expr,
+ decorators ...InterpretableDecorator) (Interpretable, error)
+}
+
+// TrackState decorates each expression node with an observer which records the value
+// associated with the given expression id. EvalState must be provided to the decorator.
+// This decorator is not thread-safe, and the EvalState must be reset between Eval()
+// calls.
+func TrackState(state EvalState) InterpretableDecorator {
+ observer := func(id int64, val ref.Val) {
+ state.SetValue(id, val)
+ }
+ return decObserveEval(observer)
+}
+
+// ExhaustiveEval replaces operations that short-circuit with versions that evaluate
+// expressions and couples this behavior with the TrackState() decorator to provide
+// insight into the evaluation state of the entire expression. EvalState must be
+// provided to the decorator. This decorator is not thread-safe, and the EvalState
+// must be reset between Eval() calls.
+func ExhaustiveEval(state EvalState) InterpretableDecorator {
+ ex := decDisableShortcircuits()
+ obs := TrackState(state)
+ return func(i Interpretable) (Interpretable, error) {
+ var err error
+ i, err = ex(i)
+ if err != nil {
+ return nil, err
+ }
+ return obs(i)
+ }
+}
+
+// Optimize will pre-compute operations such as list and map construction and optimize
+// call arguments to set membership tests. The set of optimizations will increase over time.
+func Optimize() InterpretableDecorator {
+ return decOptimize()
+}
+
+type exprInterpreter struct {
+ dispatcher Dispatcher
+ container *containers.Container
+ provider ref.TypeProvider
+ adapter ref.TypeAdapter
+ attrFactory AttributeFactory
+}
+
+// NewInterpreter builds an Interpreter from a Dispatcher and TypeProvider which will be used
+// throughout the Eval of all Interpretable instances gerenated from it.
+func NewInterpreter(dispatcher Dispatcher,
+ container *containers.Container,
+ provider ref.TypeProvider,
+ adapter ref.TypeAdapter,
+ attrFactory AttributeFactory) Interpreter {
+ return &exprInterpreter{
+ dispatcher: dispatcher,
+ container: container,
+ provider: provider,
+ adapter: adapter,
+ attrFactory: attrFactory}
+}
+
+// NewStandardInterpreter builds a Dispatcher and TypeProvider with support for all of the CEL
+// builtins defined in the language definition.
+func NewStandardInterpreter(container *containers.Container,
+ provider ref.TypeProvider,
+ adapter ref.TypeAdapter,
+ resolver AttributeFactory) Interpreter {
+ dispatcher := NewDispatcher()
+ dispatcher.Add(functions.StandardOverloads()...)
+ return NewInterpreter(dispatcher, container, provider, adapter, resolver)
+}
+
+// NewIntepretable implements the Interpreter interface method.
+func (i *exprInterpreter) NewInterpretable(
+ checked *exprpb.CheckedExpr,
+ decorators ...InterpretableDecorator) (Interpretable, error) {
+ p := newPlanner(
+ i.dispatcher,
+ i.provider,
+ i.adapter,
+ i.attrFactory,
+ i.container,
+ checked,
+ decorators...)
+ return p.Plan(checked.GetExpr())
+}
+
+// NewUncheckedIntepretable implements the Interpreter interface method.
+func (i *exprInterpreter) NewUncheckedInterpretable(
+ expr *exprpb.Expr,
+ decorators ...InterpretableDecorator) (Interpretable, error) {
+ p := newUncheckedPlanner(
+ i.dispatcher,
+ i.provider,
+ i.adapter,
+ i.attrFactory,
+ i.container,
+ decorators...)
+ return p.Plan(expr)
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/planner.go b/vendor/github.com/google/cel-go/interpreter/planner.go
new file mode 100644
index 0000000000..040e19c6ae
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/planner.go
@@ -0,0 +1,773 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "fmt"
+ "strings"
+
+ "github.com/google/cel-go/common/containers"
+ "github.com/google/cel-go/common/operators"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/interpreter/functions"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// interpretablePlanner creates an Interpretable evaluation plan from a proto Expr value.
+type interpretablePlanner interface {
+ // Plan generates an Interpretable value (or error) from the input proto Expr.
+ Plan(expr *exprpb.Expr) (Interpretable, error)
+}
+
+// newPlanner creates an interpretablePlanner which references a Dispatcher, TypeProvider,
+// TypeAdapter, Container, and CheckedExpr value. These pieces of data are used to resolve
+// functions, types, and namespaced identifiers at plan time rather than at runtime since
+// it only needs to be done once and may be semi-expensive to compute.
+func newPlanner(disp Dispatcher,
+ provider ref.TypeProvider,
+ adapter ref.TypeAdapter,
+ attrFactory AttributeFactory,
+ cont *containers.Container,
+ checked *exprpb.CheckedExpr,
+ decorators ...InterpretableDecorator) interpretablePlanner {
+ return &planner{
+ disp: disp,
+ provider: provider,
+ adapter: adapter,
+ attrFactory: attrFactory,
+ container: cont,
+ refMap: checked.GetReferenceMap(),
+ typeMap: checked.GetTypeMap(),
+ decorators: decorators,
+ }
+}
+
+// newUncheckedPlanner creates an interpretablePlanner which references a Dispatcher, TypeProvider,
+// TypeAdapter, and Container to resolve functions and types at plan time. Namespaces present in
+// Select expressions are resolved lazily at evaluation time.
+func newUncheckedPlanner(disp Dispatcher,
+ provider ref.TypeProvider,
+ adapter ref.TypeAdapter,
+ attrFactory AttributeFactory,
+ cont *containers.Container,
+ decorators ...InterpretableDecorator) interpretablePlanner {
+ return &planner{
+ disp: disp,
+ provider: provider,
+ adapter: adapter,
+ attrFactory: attrFactory,
+ container: cont,
+ refMap: make(map[int64]*exprpb.Reference),
+ typeMap: make(map[int64]*exprpb.Type),
+ decorators: decorators,
+ }
+}
+
+// planner is an implementatio of the interpretablePlanner interface.
+type planner struct {
+ disp Dispatcher
+ provider ref.TypeProvider
+ adapter ref.TypeAdapter
+ attrFactory AttributeFactory
+ container *containers.Container
+ refMap map[int64]*exprpb.Reference
+ typeMap map[int64]*exprpb.Type
+ decorators []InterpretableDecorator
+}
+
+// Plan implements the interpretablePlanner interface. This implementation of the Plan method also
+// applies decorators to each Interpretable generated as part of the overall plan. Decorators are
+// useful for layering functionality into the evaluation that is not natively understood by CEL,
+// such as state-tracking, expression re-write, and possibly efficient thread-safe memoization of
+// repeated expressions.
+func (p *planner) Plan(expr *exprpb.Expr) (Interpretable, error) {
+ switch expr.ExprKind.(type) {
+ case *exprpb.Expr_CallExpr:
+ return p.decorate(p.planCall(expr))
+ case *exprpb.Expr_IdentExpr:
+ return p.decorate(p.planIdent(expr))
+ case *exprpb.Expr_SelectExpr:
+ return p.decorate(p.planSelect(expr))
+ case *exprpb.Expr_ListExpr:
+ return p.decorate(p.planCreateList(expr))
+ case *exprpb.Expr_StructExpr:
+ return p.decorate(p.planCreateStruct(expr))
+ case *exprpb.Expr_ComprehensionExpr:
+ return p.decorate(p.planComprehension(expr))
+ case *exprpb.Expr_ConstExpr:
+ return p.decorate(p.planConst(expr))
+ }
+ return nil, fmt.Errorf("unsupported expr: %v", expr)
+}
+
+// decorate applies the InterpretableDecorator functions to the given Interpretable.
+// Both the Interpretable and error generated by a Plan step are accepted as arguments
+// for convenience.
+func (p *planner) decorate(i Interpretable, err error) (Interpretable, error) {
+ if err != nil {
+ return nil, err
+ }
+ for _, dec := range p.decorators {
+ i, err = dec(i)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return i, nil
+}
+
+// planIdent creates an Interpretable that resolves an identifier from an Activation.
+func (p *planner) planIdent(expr *exprpb.Expr) (Interpretable, error) {
+ // Establish whether the identifier is in the reference map.
+ if identRef, found := p.refMap[expr.GetId()]; found {
+ return p.planCheckedIdent(expr.GetId(), identRef)
+ }
+ // Create the possible attribute list for the unresolved reference.
+ ident := expr.GetIdentExpr()
+ return &evalAttr{
+ adapter: p.adapter,
+ attr: p.attrFactory.MaybeAttribute(expr.GetId(), ident.Name),
+ }, nil
+}
+
+func (p *planner) planCheckedIdent(id int64, identRef *exprpb.Reference) (Interpretable, error) {
+ // Plan a constant reference if this is the case for this simple identifier.
+ if identRef.Value != nil {
+ return p.Plan(&exprpb.Expr{Id: id,
+ ExprKind: &exprpb.Expr_ConstExpr{
+ ConstExpr: identRef.Value,
+ }})
+ }
+
+ // Check to see whether the type map indicates this is a type name. All types should be
+ // registered with the provider.
+ cType := p.typeMap[id]
+ if cType.GetType() != nil {
+ cVal, found := p.provider.FindIdent(identRef.Name)
+ if !found {
+ return nil, fmt.Errorf("reference to undefined type: %s", identRef.Name)
+ }
+ return NewConstValue(id, cVal), nil
+ }
+
+ // Otherwise, return the attribute for the resolved identifier name.
+ return &evalAttr{
+ adapter: p.adapter,
+ attr: p.attrFactory.AbsoluteAttribute(id, identRef.Name),
+ }, nil
+}
+
+// planSelect creates an Interpretable with either:
+// a) selects a field from a map or proto.
+// b) creates a field presence test for a select within a has() macro.
+// c) resolves the select expression to a namespaced identifier.
+func (p *planner) planSelect(expr *exprpb.Expr) (Interpretable, error) {
+ // If the Select id appears in the reference map from the CheckedExpr proto then it is either
+ // a namespaced identifier or enum value.
+ if identRef, found := p.refMap[expr.GetId()]; found {
+ return p.planCheckedIdent(expr.GetId(), identRef)
+ }
+
+ sel := expr.GetSelectExpr()
+ // Plan the operand evaluation.
+ op, err := p.Plan(sel.GetOperand())
+ if err != nil {
+ return nil, err
+ }
+
+ // Determine the field type if this is a proto message type.
+ var fieldType *ref.FieldType
+ opType := p.typeMap[sel.GetOperand().GetId()]
+ if opType.GetMessageType() != "" {
+ ft, found := p.provider.FindFieldType(opType.GetMessageType(), sel.Field)
+ if found && ft.IsSet != nil && ft.GetFrom != nil {
+ fieldType = ft
+ }
+ }
+
+ // If the Select was marked TestOnly, this is a presence test.
+ //
+ // Note: presence tests are defined for structured (e.g. proto) and dynamic values (map, json)
+ // as follows:
+ // - True if the object field has a non-default value, e.g. obj.str != ""
+ // - True if the dynamic value has the field defined, e.g. key in map
+ //
+ // However, presence tests are not defined for qualified identifier names with primitive types.
+ // If a string named 'a.b.c' is declared in the environment and referenced within `has(a.b.c)`,
+ // it is not clear whether has should error or follow the convention defined for structured
+ // values.
+ if sel.TestOnly {
+ // Return the test only eval expression.
+ return &evalTestOnly{
+ id: expr.Id,
+ field: types.String(sel.Field),
+ fieldType: fieldType,
+ op: op,
+ }, nil
+ }
+ // Build a qualifier.
+ qual, err := p.attrFactory.NewQualifier(
+ opType, expr.Id, sel.Field)
+ if err != nil {
+ return nil, err
+ }
+ // Lastly, create a field selection Interpretable.
+ attr, isAttr := op.(InterpretableAttribute)
+ if isAttr {
+ _, err = attr.AddQualifier(qual)
+ return attr, err
+ }
+
+ relAttr, err := p.relativeAttr(op.ID(), op)
+ if err != nil {
+ return nil, err
+ }
+ _, err = relAttr.AddQualifier(qual)
+ if err != nil {
+ return nil, err
+ }
+ return relAttr, nil
+}
+
+// planCall creates a callable Interpretable while specializing for common functions and invocation
+// patterns. Specifically, conditional operators &&, ||, ?:, and (in)equality functions result in
+// optimized Interpretable values.
+func (p *planner) planCall(expr *exprpb.Expr) (Interpretable, error) {
+ call := expr.GetCallExpr()
+ target, fnName, oName := p.resolveFunction(expr)
+ argCount := len(call.GetArgs())
+ var offset int
+ if target != nil {
+ argCount++
+ offset++
+ }
+
+ args := make([]Interpretable, argCount)
+ if target != nil {
+ arg, err := p.Plan(target)
+ if err != nil {
+ return nil, err
+ }
+ args[0] = arg
+ }
+ for i, argExpr := range call.GetArgs() {
+ arg, err := p.Plan(argExpr)
+ if err != nil {
+ return nil, err
+ }
+ args[i+offset] = arg
+ }
+
+ // Generate specialized Interpretable operators by function name if possible.
+ switch fnName {
+ case operators.LogicalAnd:
+ return p.planCallLogicalAnd(expr, args)
+ case operators.LogicalOr:
+ return p.planCallLogicalOr(expr, args)
+ case operators.Conditional:
+ return p.planCallConditional(expr, args)
+ case operators.Equals:
+ return p.planCallEqual(expr, args)
+ case operators.NotEquals:
+ return p.planCallNotEqual(expr, args)
+ case operators.Index:
+ return p.planCallIndex(expr, args)
+ }
+
+ // Otherwise, generate Interpretable calls specialized by argument count.
+ // Try to find the specific function by overload id.
+ var fnDef *functions.Overload
+ if oName != "" {
+ fnDef, _ = p.disp.FindOverload(oName)
+ }
+ // If the overload id couldn't resolve the function, try the simple function name.
+ if fnDef == nil {
+ fnDef, _ = p.disp.FindOverload(fnName)
+ }
+ switch argCount {
+ case 0:
+ return p.planCallZero(expr, fnName, oName, fnDef)
+ case 1:
+ return p.planCallUnary(expr, fnName, oName, fnDef, args)
+ case 2:
+ return p.planCallBinary(expr, fnName, oName, fnDef, args)
+ default:
+ return p.planCallVarArgs(expr, fnName, oName, fnDef, args)
+ }
+}
+
+// planCallZero generates a zero-arity callable Interpretable.
+func (p *planner) planCallZero(expr *exprpb.Expr,
+ function string,
+ overload string,
+ impl *functions.Overload) (Interpretable, error) {
+ if impl == nil || impl.Function == nil {
+ return nil, fmt.Errorf("no such overload: %s()", function)
+ }
+ return &evalZeroArity{
+ id: expr.Id,
+ function: function,
+ overload: overload,
+ impl: impl.Function,
+ }, nil
+}
+
+// planCallUnary generates a unary callable Interpretable.
+func (p *planner) planCallUnary(expr *exprpb.Expr,
+ function string,
+ overload string,
+ impl *functions.Overload,
+ args []Interpretable) (Interpretable, error) {
+ var fn functions.UnaryOp
+ var trait int
+ if impl != nil {
+ if impl.Unary == nil {
+ return nil, fmt.Errorf("no such overload: %s(arg)", function)
+ }
+ fn = impl.Unary
+ trait = impl.OperandTrait
+ }
+ return &evalUnary{
+ id: expr.Id,
+ function: function,
+ overload: overload,
+ arg: args[0],
+ trait: trait,
+ impl: fn,
+ }, nil
+}
+
+// planCallBinary generates a binary callable Interpretable.
+func (p *planner) planCallBinary(expr *exprpb.Expr,
+ function string,
+ overload string,
+ impl *functions.Overload,
+ args []Interpretable) (Interpretable, error) {
+ var fn functions.BinaryOp
+ var trait int
+ if impl != nil {
+ if impl.Binary == nil {
+ return nil, fmt.Errorf("no such overload: %s(lhs, rhs)", function)
+ }
+ fn = impl.Binary
+ trait = impl.OperandTrait
+ }
+ return &evalBinary{
+ id: expr.Id,
+ function: function,
+ overload: overload,
+ lhs: args[0],
+ rhs: args[1],
+ trait: trait,
+ impl: fn,
+ }, nil
+}
+
+// planCallVarArgs generates a variable argument callable Interpretable.
+func (p *planner) planCallVarArgs(expr *exprpb.Expr,
+ function string,
+ overload string,
+ impl *functions.Overload,
+ args []Interpretable) (Interpretable, error) {
+ var fn functions.FunctionOp
+ var trait int
+ if impl != nil {
+ if impl.Function == nil {
+ return nil, fmt.Errorf("no such overload: %s(...)", function)
+ }
+ fn = impl.Function
+ trait = impl.OperandTrait
+ }
+ return &evalVarArgs{
+ id: expr.Id,
+ function: function,
+ overload: overload,
+ args: args,
+ trait: trait,
+ impl: fn,
+ }, nil
+}
+
+// planCallEqual generates an equals (==) Interpretable.
+func (p *planner) planCallEqual(expr *exprpb.Expr,
+ args []Interpretable) (Interpretable, error) {
+ return &evalEq{
+ id: expr.Id,
+ lhs: args[0],
+ rhs: args[1],
+ }, nil
+}
+
+// planCallNotEqual generates a not equals (!=) Interpretable.
+func (p *planner) planCallNotEqual(expr *exprpb.Expr,
+ args []Interpretable) (Interpretable, error) {
+ return &evalNe{
+ id: expr.Id,
+ lhs: args[0],
+ rhs: args[1],
+ }, nil
+}
+
+// planCallLogicalAnd generates a logical and (&&) Interpretable.
+func (p *planner) planCallLogicalAnd(expr *exprpb.Expr,
+ args []Interpretable) (Interpretable, error) {
+ return &evalAnd{
+ id: expr.Id,
+ lhs: args[0],
+ rhs: args[1],
+ }, nil
+}
+
+// planCallLogicalOr generates a logical or (||) Interpretable.
+func (p *planner) planCallLogicalOr(expr *exprpb.Expr,
+ args []Interpretable) (Interpretable, error) {
+ return &evalOr{
+ id: expr.Id,
+ lhs: args[0],
+ rhs: args[1],
+ }, nil
+}
+
+// planCallConditional generates a conditional / ternary (c ? t : f) Interpretable.
+func (p *planner) planCallConditional(expr *exprpb.Expr,
+ args []Interpretable) (Interpretable, error) {
+ cond := args[0]
+
+ t := args[1]
+ var tAttr Attribute
+ truthyAttr, isTruthyAttr := t.(InterpretableAttribute)
+ if isTruthyAttr {
+ tAttr = truthyAttr.Attr()
+ } else {
+ tAttr = p.attrFactory.RelativeAttribute(t.ID(), t)
+ }
+
+ f := args[2]
+ var fAttr Attribute
+ falsyAttr, isFalsyAttr := f.(InterpretableAttribute)
+ if isFalsyAttr {
+ fAttr = falsyAttr.Attr()
+ } else {
+ fAttr = p.attrFactory.RelativeAttribute(f.ID(), f)
+ }
+
+ return &evalAttr{
+ adapter: p.adapter,
+ attr: p.attrFactory.ConditionalAttribute(expr.Id, cond, tAttr, fAttr),
+ }, nil
+}
+
+// planCallIndex either extends an attribute with the argument to the index operation, or creates
+// a relative attribute based on the return of a function call or operation.
+func (p *planner) planCallIndex(expr *exprpb.Expr,
+ args []Interpretable) (Interpretable, error) {
+ op := args[0]
+ ind := args[1]
+ opAttr, err := p.relativeAttr(op.ID(), op)
+ if err != nil {
+ return nil, err
+ }
+ opType := p.typeMap[expr.GetCallExpr().GetTarget().GetId()]
+ indConst, isIndConst := ind.(InterpretableConst)
+ if isIndConst {
+ qual, err := p.attrFactory.NewQualifier(
+ opType, expr.GetId(), indConst.Value())
+ if err != nil {
+ return nil, err
+ }
+ _, err = opAttr.AddQualifier(qual)
+ return opAttr, err
+ }
+ indAttr, isIndAttr := ind.(InterpretableAttribute)
+ if isIndAttr {
+ qual, err := p.attrFactory.NewQualifier(
+ opType, expr.GetId(), indAttr)
+ if err != nil {
+ return nil, err
+ }
+ _, err = opAttr.AddQualifier(qual)
+ return opAttr, err
+ }
+ indQual, err := p.relativeAttr(expr.GetId(), ind)
+ if err != nil {
+ return nil, err
+ }
+ _, err = opAttr.AddQualifier(indQual)
+ return opAttr, err
+}
+
+// planCreateList generates a list construction Interpretable.
+func (p *planner) planCreateList(expr *exprpb.Expr) (Interpretable, error) {
+ list := expr.GetListExpr()
+ elems := make([]Interpretable, len(list.GetElements()))
+ for i, elem := range list.GetElements() {
+ elemVal, err := p.Plan(elem)
+ if err != nil {
+ return nil, err
+ }
+ elems[i] = elemVal
+ }
+ return &evalList{
+ id: expr.Id,
+ elems: elems,
+ adapter: p.adapter,
+ }, nil
+}
+
+// planCreateStruct generates a map or object construction Interpretable.
+func (p *planner) planCreateStruct(expr *exprpb.Expr) (Interpretable, error) {
+ str := expr.GetStructExpr()
+ if len(str.MessageName) != 0 {
+ return p.planCreateObj(expr)
+ }
+ entries := str.GetEntries()
+ keys := make([]Interpretable, len(entries))
+ vals := make([]Interpretable, len(entries))
+ for i, entry := range entries {
+ keyVal, err := p.Plan(entry.GetMapKey())
+ if err != nil {
+ return nil, err
+ }
+ keys[i] = keyVal
+
+ valVal, err := p.Plan(entry.GetValue())
+ if err != nil {
+ return nil, err
+ }
+ vals[i] = valVal
+ }
+ return &evalMap{
+ id: expr.Id,
+ keys: keys,
+ vals: vals,
+ adapter: p.adapter,
+ }, nil
+}
+
+// planCreateObj generates an object construction Interpretable.
+func (p *planner) planCreateObj(expr *exprpb.Expr) (Interpretable, error) {
+ obj := expr.GetStructExpr()
+ typeName, defined := p.resolveTypeName(obj.MessageName)
+ if !defined {
+ return nil, fmt.Errorf("unknown type: %s", typeName)
+ }
+ entries := obj.GetEntries()
+ fields := make([]string, len(entries))
+ vals := make([]Interpretable, len(entries))
+ for i, entry := range entries {
+ fields[i] = entry.GetFieldKey()
+ val, err := p.Plan(entry.GetValue())
+ if err != nil {
+ return nil, err
+ }
+ vals[i] = val
+ }
+ return &evalObj{
+ id: expr.Id,
+ typeName: typeName,
+ fields: fields,
+ vals: vals,
+ provider: p.provider,
+ }, nil
+}
+
+// planComprehension generates an Interpretable fold operation.
+func (p *planner) planComprehension(expr *exprpb.Expr) (Interpretable, error) {
+ fold := expr.GetComprehensionExpr()
+ accu, err := p.Plan(fold.GetAccuInit())
+ if err != nil {
+ return nil, err
+ }
+ iterRange, err := p.Plan(fold.GetIterRange())
+ if err != nil {
+ return nil, err
+ }
+ cond, err := p.Plan(fold.GetLoopCondition())
+ if err != nil {
+ return nil, err
+ }
+ step, err := p.Plan(fold.GetLoopStep())
+ if err != nil {
+ return nil, err
+ }
+ result, err := p.Plan(fold.GetResult())
+ if err != nil {
+ return nil, err
+ }
+ return &evalFold{
+ id: expr.Id,
+ accuVar: fold.AccuVar,
+ accu: accu,
+ iterVar: fold.IterVar,
+ iterRange: iterRange,
+ cond: cond,
+ step: step,
+ result: result,
+ }, nil
+}
+
+// planConst generates a constant valued Interpretable.
+func (p *planner) planConst(expr *exprpb.Expr) (Interpretable, error) {
+ val, err := p.constValue(expr.GetConstExpr())
+ if err != nil {
+ return nil, err
+ }
+ return NewConstValue(expr.Id, val), nil
+}
+
+// constValue converts a proto Constant value to a ref.Val.
+func (p *planner) constValue(c *exprpb.Constant) (ref.Val, error) {
+ switch c.ConstantKind.(type) {
+ case *exprpb.Constant_BoolValue:
+ return p.adapter.NativeToValue(c.GetBoolValue()), nil
+ case *exprpb.Constant_BytesValue:
+ return p.adapter.NativeToValue(c.GetBytesValue()), nil
+ case *exprpb.Constant_DoubleValue:
+ return p.adapter.NativeToValue(c.GetDoubleValue()), nil
+ case *exprpb.Constant_DurationValue:
+ return p.adapter.NativeToValue(c.GetDurationValue().AsDuration()), nil
+ case *exprpb.Constant_Int64Value:
+ return p.adapter.NativeToValue(c.GetInt64Value()), nil
+ case *exprpb.Constant_NullValue:
+ return p.adapter.NativeToValue(c.GetNullValue()), nil
+ case *exprpb.Constant_StringValue:
+ return p.adapter.NativeToValue(c.GetStringValue()), nil
+ case *exprpb.Constant_TimestampValue:
+ return p.adapter.NativeToValue(c.GetTimestampValue().AsTime()), nil
+ case *exprpb.Constant_Uint64Value:
+ return p.adapter.NativeToValue(c.GetUint64Value()), nil
+ }
+ return nil, fmt.Errorf("unknown constant type: %v", c)
+}
+
+// resolveTypeName takes a qualified string constructed at parse time, applies the proto
+// namespace resolution rules to it in a scan over possible matching types in the TypeProvider.
+func (p *planner) resolveTypeName(typeName string) (string, bool) {
+ for _, qualifiedTypeName := range p.container.ResolveCandidateNames(typeName) {
+ if _, found := p.provider.FindType(qualifiedTypeName); found {
+ return qualifiedTypeName, true
+ }
+ }
+ return "", false
+}
+
+// resolveFunction determines the call target, function name, and overload name from a given Expr
+// value.
+//
+// The resolveFunction resolves ambiguities where a function may either be a receiver-style
+// invocation or a qualified global function name.
+// - The target expression may only consist of ident and select expressions.
+// - The function is declared in the environment using its fully-qualified name.
+// - The fully-qualified function name matches the string serialized target value.
+func (p *planner) resolveFunction(expr *exprpb.Expr) (*exprpb.Expr, string, string) {
+ // Note: similar logic exists within the `checker/checker.go`. If making changes here
+ // please consider the impact on checker.go and consolidate implementations or mirror code
+ // as appropriate.
+ call := expr.GetCallExpr()
+ target := call.GetTarget()
+ fnName := call.GetFunction()
+
+ // Checked expressions always have a reference map entry, and _should_ have the fully qualified
+ // function name as the fnName value.
+ oRef, hasOverload := p.refMap[expr.GetId()]
+ if hasOverload {
+ if len(oRef.GetOverloadId()) == 1 {
+ return target, fnName, oRef.GetOverloadId()[0]
+ }
+ // Note, this namespaced function name will not appear as a fully qualified name in ASTs
+ // built and stored before cel-go v0.5.0; however, this functionality did not work at all
+ // before the v0.5.0 release.
+ return target, fnName, ""
+ }
+
+ // Parse-only expressions need to handle the same logic as is normally performed at check time,
+ // but with potentially much less information. The only reliable source of information about
+ // which functions are configured is the dispatcher.
+ if target == nil {
+ // If the user has a parse-only expression, then it should have been configured as such in
+ // the interpreter dispatcher as it may have been omitted from the checker environment.
+ for _, qualifiedName := range p.container.ResolveCandidateNames(fnName) {
+ _, found := p.disp.FindOverload(qualifiedName)
+ if found {
+ return nil, qualifiedName, ""
+ }
+ }
+ // It's possible that the overload was not found, but this situation is accounted for in
+ // the planCall phase; however, the leading dot used for denoting fully-qualified
+ // namespaced identifiers must be stripped, as all declarations already use fully-qualified
+ // names. This stripping behavior is handled automatically by the ResolveCandidateNames
+ // call.
+ return target, stripLeadingDot(fnName), ""
+ }
+
+ // Handle the situation where the function target actually indicates a qualified function name.
+ qualifiedPrefix, maybeQualified := p.toQualifiedName(target)
+ if maybeQualified {
+ maybeQualifiedName := qualifiedPrefix + "." + fnName
+ for _, qualifiedName := range p.container.ResolveCandidateNames(maybeQualifiedName) {
+ _, found := p.disp.FindOverload(qualifiedName)
+ if found {
+ // Clear the target to ensure the proper arity is used for finding the
+ // implementation.
+ return nil, qualifiedName, ""
+ }
+ }
+ }
+ // In the default case, the function is exactly as it was advertised: a receiver call on with
+ // an expression-based target with the given simple function name.
+ return target, fnName, ""
+}
+
+func (p *planner) relativeAttr(id int64, eval Interpretable) (InterpretableAttribute, error) {
+ eAttr, ok := eval.(InterpretableAttribute)
+ if !ok {
+ eAttr = &evalAttr{
+ adapter: p.adapter,
+ attr: p.attrFactory.RelativeAttribute(id, eval),
+ }
+ }
+ decAttr, err := p.decorate(eAttr, nil)
+ if err != nil {
+ return nil, err
+ }
+ eAttr, ok = decAttr.(InterpretableAttribute)
+ if !ok {
+ return nil, fmt.Errorf("invalid attribute decoration: %v(%T)", decAttr, decAttr)
+ }
+ return eAttr, nil
+}
+
+// toQualifiedName converts an expression AST into a qualified name if possible, with a boolean
+// 'found' value that indicates if the conversion is successful.
+func (p *planner) toQualifiedName(operand *exprpb.Expr) (string, bool) {
+ // If the checker identified the expression as an attribute by the type-checker, then it can't
+ // possibly be part of qualified name in a namespace.
+ _, isAttr := p.refMap[operand.GetId()]
+ if isAttr {
+ return "", false
+ }
+ // Since functions cannot be both namespaced and receiver functions, if the operand is not an
+ // qualified variable name, return the (possibly) qualified name given the expressions.
+ return containers.ToQualifiedName(operand)
+}
+
+func stripLeadingDot(name string) string {
+ if strings.HasPrefix(name, ".") {
+ return name[1:]
+ }
+ return name
+}
diff --git a/vendor/github.com/google/cel-go/interpreter/prune.go b/vendor/github.com/google/cel-go/interpreter/prune.go
new file mode 100644
index 0000000000..7dab68efbb
--- /dev/null
+++ b/vendor/github.com/google/cel-go/interpreter/prune.go
@@ -0,0 +1,391 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package interpreter
+
+import (
+ "github.com/google/cel-go/common/operators"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/common/types/traits"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+type astPruner struct {
+ expr *exprpb.Expr
+ state EvalState
+ nextExprID int64
+}
+
+// TODO Consider having a separate walk of the AST that finds common
+// subexpressions. This can be called before or after constant folding to find
+// common subexpressions.
+
+// PruneAst prunes the given AST based on the given EvalState and generates a new AST.
+// Given AST is copied on write and a new AST is returned.
+// Couple of typical use cases this interface would be:
+//
+// A)
+// 1) Evaluate expr with some unknowns,
+// 2) If result is unknown:
+// a) PruneAst
+// b) Goto 1
+// Functional call results which are known would be effectively cached across
+// iterations.
+//
+// B)
+// 1) Compile the expression (maybe via a service and maybe after checking a
+// compiled expression does not exists in local cache)
+// 2) Prepare the environment and the interpreter. Activation might be empty.
+// 3) Eval the expression. This might return unknown or error or a concrete
+// value.
+// 4) PruneAst
+// 4) Maybe cache the expression
+// This is effectively constant folding the expression. How the environment is
+// prepared in step 2 is flexible. For example, If the caller caches the
+// compiled and constant folded expressions, but is not willing to constant
+// fold(and thus cache results of) some external calls, then they can prepare
+// the overloads accordingly.
+func PruneAst(expr *exprpb.Expr, state EvalState) *exprpb.Expr {
+ pruner := &astPruner{
+ expr: expr,
+ state: state,
+ nextExprID: 1}
+ newExpr, _ := pruner.prune(expr)
+ return newExpr
+}
+
+func (p *astPruner) createLiteral(id int64, val *exprpb.Constant) *exprpb.Expr {
+ return &exprpb.Expr{
+ Id: id,
+ ExprKind: &exprpb.Expr_ConstExpr{
+ ConstExpr: val,
+ },
+ }
+}
+
+func (p *astPruner) maybeCreateLiteral(id int64, val ref.Val) (*exprpb.Expr, bool) {
+ switch val.Type() {
+ case types.BoolType:
+ return p.createLiteral(id,
+ &exprpb.Constant{ConstantKind: &exprpb.Constant_BoolValue{BoolValue: val.Value().(bool)}}), true
+ case types.IntType:
+ return p.createLiteral(id,
+ &exprpb.Constant{ConstantKind: &exprpb.Constant_Int64Value{Int64Value: val.Value().(int64)}}), true
+ case types.UintType:
+ return p.createLiteral(id,
+ &exprpb.Constant{ConstantKind: &exprpb.Constant_Uint64Value{Uint64Value: val.Value().(uint64)}}), true
+ case types.StringType:
+ return p.createLiteral(id,
+ &exprpb.Constant{ConstantKind: &exprpb.Constant_StringValue{StringValue: val.Value().(string)}}), true
+ case types.DoubleType:
+ return p.createLiteral(id,
+ &exprpb.Constant{ConstantKind: &exprpb.Constant_DoubleValue{DoubleValue: val.Value().(float64)}}), true
+ case types.BytesType:
+ return p.createLiteral(id,
+ &exprpb.Constant{ConstantKind: &exprpb.Constant_BytesValue{BytesValue: val.Value().([]byte)}}), true
+ case types.NullType:
+ return p.createLiteral(id,
+ &exprpb.Constant{ConstantKind: &exprpb.Constant_NullValue{NullValue: val.Value().(structpb.NullValue)}}), true
+ }
+
+ // Attempt to build a list literal.
+ if list, isList := val.(traits.Lister); isList {
+ sz := list.Size().(types.Int)
+ elemExprs := make([]*exprpb.Expr, sz)
+ for i := types.Int(0); i < sz; i++ {
+ elem := list.Get(i)
+ if types.IsUnknownOrError(elem) {
+ return nil, false
+ }
+ elemExpr, ok := p.maybeCreateLiteral(p.nextID(), elem)
+ if !ok {
+ return nil, false
+ }
+ elemExprs[i] = elemExpr
+ }
+ return &exprpb.Expr{
+ Id: id,
+ ExprKind: &exprpb.Expr_ListExpr{
+ ListExpr: &exprpb.Expr_CreateList{
+ Elements: elemExprs,
+ },
+ },
+ }, true
+ }
+
+ // Create a map literal if possible.
+ if mp, isMap := val.(traits.Mapper); isMap {
+ it := mp.Iterator()
+ entries := make([]*exprpb.Expr_CreateStruct_Entry, mp.Size().(types.Int))
+ i := 0
+ for it.HasNext() != types.False {
+ key := it.Next()
+ val := mp.Get(key)
+ if types.IsUnknownOrError(key) || types.IsUnknownOrError(val) {
+ return nil, false
+ }
+ keyExpr, ok := p.maybeCreateLiteral(p.nextID(), key)
+ if !ok {
+ return nil, false
+ }
+ valExpr, ok := p.maybeCreateLiteral(p.nextID(), val)
+ if !ok {
+ return nil, false
+ }
+ entry := &exprpb.Expr_CreateStruct_Entry{
+ Id: p.nextID(),
+ KeyKind: &exprpb.Expr_CreateStruct_Entry_MapKey{
+ MapKey: keyExpr,
+ },
+ Value: valExpr,
+ }
+ entries[i] = entry
+ i++
+ }
+ return &exprpb.Expr{
+ Id: id,
+ ExprKind: &exprpb.Expr_StructExpr{
+ StructExpr: &exprpb.Expr_CreateStruct{
+ Entries: entries,
+ },
+ },
+ }, true
+ }
+
+ // TODO(issues/377) To construct message literals, the type provider will need to support
+ // the enumeration the fields for a given message.
+ return nil, false
+}
+
+func (p *astPruner) maybePruneAndOr(node *exprpb.Expr) (*exprpb.Expr, bool) {
+ if !p.existsWithUnknownValue(node.GetId()) {
+ return nil, false
+ }
+
+ call := node.GetCallExpr()
+ // We know result is unknown, so we have at least one unknown arg
+ // and if one side is a known value, we know we can ignore it.
+ if p.existsWithKnownValue(call.Args[0].GetId()) {
+ return call.Args[1], true
+ }
+ if p.existsWithKnownValue(call.Args[1].GetId()) {
+ return call.Args[0], true
+ }
+ return nil, false
+}
+
+func (p *astPruner) maybePruneConditional(node *exprpb.Expr) (*exprpb.Expr, bool) {
+ if !p.existsWithUnknownValue(node.GetId()) {
+ return nil, false
+ }
+
+ call := node.GetCallExpr()
+ condVal, condValueExists := p.value(call.Args[0].GetId())
+ if !condValueExists || types.IsUnknownOrError(condVal) {
+ return nil, false
+ }
+
+ if condVal.Value().(bool) {
+ return call.Args[1], true
+ }
+ return call.Args[2], true
+}
+
+func (p *astPruner) maybePruneFunction(node *exprpb.Expr) (*exprpb.Expr, bool) {
+ call := node.GetCallExpr()
+ if call.Function == operators.LogicalOr || call.Function == operators.LogicalAnd {
+ return p.maybePruneAndOr(node)
+ }
+ if call.Function == operators.Conditional {
+ return p.maybePruneConditional(node)
+ }
+
+ return nil, false
+}
+
+func (p *astPruner) prune(node *exprpb.Expr) (*exprpb.Expr, bool) {
+ if node == nil {
+ return node, false
+ }
+ val, valueExists := p.value(node.GetId())
+ if valueExists && !types.IsUnknownOrError(val) {
+ if newNode, ok := p.maybeCreateLiteral(node.GetId(), val); ok {
+ return newNode, true
+ }
+ }
+
+ // We have either an unknown/error value, or something we dont want to
+ // transform, or expression was not evaluated. If possible, drill down
+ // more.
+
+ switch node.ExprKind.(type) {
+ case *exprpb.Expr_SelectExpr:
+ if operand, pruned := p.prune(node.GetSelectExpr().Operand); pruned {
+ return &exprpb.Expr{
+ Id: node.GetId(),
+ ExprKind: &exprpb.Expr_SelectExpr{
+ SelectExpr: &exprpb.Expr_Select{
+ Operand: operand,
+ Field: node.GetSelectExpr().GetField(),
+ TestOnly: node.GetSelectExpr().GetTestOnly(),
+ },
+ },
+ }, true
+ }
+ case *exprpb.Expr_CallExpr:
+ if newExpr, pruned := p.maybePruneFunction(node); pruned {
+ newExpr, _ = p.prune(newExpr)
+ return newExpr, true
+ }
+ var prunedCall bool
+ call := node.GetCallExpr()
+ args := call.GetArgs()
+ newArgs := make([]*exprpb.Expr, len(args))
+ newCall := &exprpb.Expr_Call{
+ Function: call.GetFunction(),
+ Target: call.GetTarget(),
+ Args: newArgs,
+ }
+ for i, arg := range args {
+ newArgs[i] = arg
+ if newArg, prunedArg := p.prune(arg); prunedArg {
+ prunedCall = true
+ newArgs[i] = newArg
+ }
+ }
+ if newTarget, prunedTarget := p.prune(call.GetTarget()); prunedTarget {
+ prunedCall = true
+ newCall.Target = newTarget
+ }
+ if prunedCall {
+ return &exprpb.Expr{
+ Id: node.GetId(),
+ ExprKind: &exprpb.Expr_CallExpr{
+ CallExpr: newCall,
+ },
+ }, true
+ }
+ case *exprpb.Expr_ListExpr:
+ elems := node.GetListExpr().GetElements()
+ newElems := make([]*exprpb.Expr, len(elems))
+ var prunedList bool
+ for i, elem := range elems {
+ newElems[i] = elem
+ if newElem, prunedElem := p.prune(elem); prunedElem {
+ newElems[i] = newElem
+ prunedList = true
+ }
+ }
+ if prunedList {
+ return &exprpb.Expr{
+ Id: node.GetId(),
+ ExprKind: &exprpb.Expr_ListExpr{
+ ListExpr: &exprpb.Expr_CreateList{
+ Elements: newElems,
+ },
+ },
+ }, true
+ }
+ case *exprpb.Expr_StructExpr:
+ var prunedStruct bool
+ entries := node.GetStructExpr().GetEntries()
+ messageType := node.GetStructExpr().GetMessageName()
+ newEntries := make([]*exprpb.Expr_CreateStruct_Entry, len(entries))
+ for i, entry := range entries {
+ newEntries[i] = entry
+ newKey, prunedKey := p.prune(entry.GetMapKey())
+ newValue, prunedValue := p.prune(entry.GetValue())
+ if !prunedKey && !prunedValue {
+ continue
+ }
+ prunedStruct = true
+ newEntry := &exprpb.Expr_CreateStruct_Entry{
+ Value: newValue,
+ }
+ if messageType != "" {
+ newEntry.KeyKind = &exprpb.Expr_CreateStruct_Entry_FieldKey{
+ FieldKey: entry.GetFieldKey(),
+ }
+ } else {
+ newEntry.KeyKind = &exprpb.Expr_CreateStruct_Entry_MapKey{
+ MapKey: newKey,
+ }
+ }
+ newEntries[i] = newEntry
+ }
+ if prunedStruct {
+ return &exprpb.Expr{
+ Id: node.GetId(),
+ ExprKind: &exprpb.Expr_StructExpr{
+ StructExpr: &exprpb.Expr_CreateStruct{
+ MessageName: messageType,
+ Entries: newEntries,
+ },
+ },
+ }, true
+ }
+ case *exprpb.Expr_ComprehensionExpr:
+ compre := node.GetComprehensionExpr()
+ // Only the range of the comprehension is pruned since the state tracking only records
+ // the last iteration of the comprehension and not each step in the evaluation which
+ // means that the any residuals computed in between might be inaccurate.
+ if newRange, pruned := p.prune(compre.GetIterRange()); pruned {
+ return &exprpb.Expr{
+ Id: node.GetId(),
+ ExprKind: &exprpb.Expr_ComprehensionExpr{
+ ComprehensionExpr: &exprpb.Expr_Comprehension{
+ IterVar: compre.GetIterVar(),
+ IterRange: newRange,
+ AccuVar: compre.GetAccuVar(),
+ AccuInit: compre.GetAccuInit(),
+ LoopCondition: compre.GetLoopCondition(),
+ LoopStep: compre.GetLoopStep(),
+ Result: compre.GetResult(),
+ },
+ },
+ }, true
+ }
+ }
+ return node, false
+}
+
+func (p *astPruner) value(id int64) (ref.Val, bool) {
+ val, found := p.state.Value(id)
+ return val, (found && val != nil)
+}
+
+func (p *astPruner) existsWithUnknownValue(id int64) bool {
+ val, valueExists := p.value(id)
+ return valueExists && types.IsUnknown(val)
+}
+
+func (p *astPruner) existsWithKnownValue(id int64) bool {
+ val, valueExists := p.value(id)
+ return valueExists && !types.IsUnknown(val)
+}
+
+func (p *astPruner) nextID() int64 {
+ for {
+ _, found := p.state.Value(p.nextExprID)
+ if !found {
+ next := p.nextExprID
+ p.nextExprID++
+ return next
+ }
+ p.nextExprID++
+ }
+}
diff --git a/vendor/github.com/google/cel-go/parser/BUILD.bazel b/vendor/github.com/google/cel-go/parser/BUILD.bazel
new file mode 100644
index 0000000000..a1917b4640
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/BUILD.bazel
@@ -0,0 +1,51 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+package(
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "errors.go",
+ "helper.go",
+ "input.go",
+ "macro.go",
+ "options.go",
+ "parser.go",
+ "unescape.go",
+ "unparser.go",
+ ],
+ importpath = "github.com/google/cel-go/parser",
+ visibility = ["//visibility:public"],
+ deps = [
+ "//common:go_default_library",
+ "//common/operators:go_default_library",
+ "//common/runes:go_default_library",
+ "//parser/gen:go_default_library",
+ "@com_github_antlr//runtime/Go/antlr:go_default_library",
+ "@org_golang_google_genproto//googleapis/api/expr/v1alpha1:go_default_library",
+ "@org_golang_google_protobuf//proto:go_default_library",
+ "@org_golang_google_protobuf//types/known/structpb:go_default_library",
+ ],
+)
+
+go_test(
+ name = "go_default_test",
+ size = "small",
+ srcs = [
+ "parser_test.go",
+ "unescape_test.go",
+ "unparser_test.go",
+ ],
+ embed = [
+ ":go_default_library",
+ ],
+ deps = [
+ "//common/debug:go_default_library",
+ "//parser/gen:go_default_library",
+ "//test:go_default_library",
+ "@com_github_antlr//runtime/Go/antlr:go_default_library",
+ "@org_golang_google_protobuf//proto:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/parser/errors.go b/vendor/github.com/google/cel-go/parser/errors.go
new file mode 100644
index 0000000000..ce49bb87f8
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/errors.go
@@ -0,0 +1,30 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package parser
+
+import (
+ "fmt"
+
+ "github.com/google/cel-go/common"
+)
+
+// parseErrors is a specialization of Errors.
+type parseErrors struct {
+ *common.Errors
+}
+
+func (e *parseErrors) syntaxError(l common.Location, message string) {
+ e.ReportError(l, fmt.Sprintf("Syntax error: %s", message))
+}
diff --git a/vendor/github.com/google/cel-go/parser/gen/BUILD.bazel b/vendor/github.com/google/cel-go/parser/gen/BUILD.bazel
new file mode 100644
index 0000000000..78e0432c40
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/BUILD.bazel
@@ -0,0 +1,26 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library")
+
+package(
+ default_visibility = ["//parser:__subpackages__"],
+ licenses = ["notice"], # Apache 2.0
+)
+
+go_library(
+ name = "go_default_library",
+ srcs = [
+ "cel_base_listener.go",
+ "cel_base_visitor.go",
+ "cel_lexer.go",
+ "cel_listener.go",
+ "cel_parser.go",
+ "cel_visitor.go",
+ ],
+ data = [
+ "CEL.tokens",
+ "CELLexer.tokens",
+ ],
+ importpath = "github.com/google/cel-go/parser/gen",
+ deps = [
+ "@com_github_antlr//runtime/Go/antlr:go_default_library",
+ ],
+)
diff --git a/vendor/github.com/google/cel-go/parser/gen/CEL.g4 b/vendor/github.com/google/cel-go/parser/gen/CEL.g4
new file mode 100644
index 0000000000..7928120289
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/CEL.g4
@@ -0,0 +1,186 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+grammar CEL;
+
+// Grammar Rules
+// =============
+
+start
+ : e=expr EOF
+ ;
+
+expr
+ : e=conditionalOr (op='?' e1=conditionalOr ':' e2=expr)?
+ ;
+
+conditionalOr
+ : e=conditionalAnd (ops+='||' e1+=conditionalAnd)*
+ ;
+
+conditionalAnd
+ : e=relation (ops+='&&' e1+=relation)*
+ ;
+
+relation
+ : calc
+ | relation op=('<'|'<='|'>='|'>'|'=='|'!='|'in') relation
+ ;
+
+calc
+ : unary
+ | calc op=('*'|'/'|'%') calc
+ | calc op=('+'|'-') calc
+ ;
+
+unary
+ : member # MemberExpr
+ | (ops+='!')+ member # LogicalNot
+ | (ops+='-')+ member # Negate
+ ;
+
+member
+ : primary # PrimaryExpr
+ | member op='.' id=IDENTIFIER (open='(' args=exprList? ')')? # SelectOrCall
+ | member op='[' index=expr ']' # Index
+ | member op='{' entries=fieldInitializerList? ','? '}' # CreateMessage
+ ;
+
+primary
+ : leadingDot='.'? id=IDENTIFIER (op='(' args=exprList? ')')? # IdentOrGlobalCall
+ | '(' e=expr ')' # Nested
+ | op='[' elems=exprList? ','? ']' # CreateList
+ | op='{' entries=mapInitializerList? ','? '}' # CreateStruct
+ | literal # ConstantLiteral
+ ;
+
+exprList
+ : e+=expr (',' e+=expr)*
+ ;
+
+fieldInitializerList
+ : fields+=IDENTIFIER cols+=':' values+=expr (',' fields+=IDENTIFIER cols+=':' values+=expr)*
+ ;
+
+mapInitializerList
+ : keys+=expr cols+=':' values+=expr (',' keys+=expr cols+=':' values+=expr)*
+ ;
+
+literal
+ : sign=MINUS? tok=NUM_INT # Int
+ | tok=NUM_UINT # Uint
+ | sign=MINUS? tok=NUM_FLOAT # Double
+ | tok=STRING # String
+ | tok=BYTES # Bytes
+ | tok='true' # BoolTrue
+ | tok='false' # BoolFalse
+ | tok='null' # Null
+ ;
+
+// Lexer Rules
+// ===========
+
+EQUALS : '==';
+NOT_EQUALS : '!=';
+IN: 'in';
+LESS : '<';
+LESS_EQUALS : '<=';
+GREATER_EQUALS : '>=';
+GREATER : '>';
+LOGICAL_AND : '&&';
+LOGICAL_OR : '||';
+
+LBRACKET : '[';
+RPRACKET : ']';
+LBRACE : '{';
+RBRACE : '}';
+LPAREN : '(';
+RPAREN : ')';
+DOT : '.';
+COMMA : ',';
+MINUS : '-';
+EXCLAM : '!';
+QUESTIONMARK : '?';
+COLON : ':';
+PLUS : '+';
+STAR : '*';
+SLASH : '/';
+PERCENT : '%';
+TRUE : 'true';
+FALSE : 'false';
+NULL : 'null';
+
+fragment BACKSLASH : '\\';
+fragment LETTER : 'A'..'Z' | 'a'..'z' ;
+fragment DIGIT : '0'..'9' ;
+fragment EXPONENT : ('e' | 'E') ( '+' | '-' )? DIGIT+ ;
+fragment HEXDIGIT : ('0'..'9'|'a'..'f'|'A'..'F') ;
+fragment RAW : 'r' | 'R';
+
+fragment ESC_SEQ
+ : ESC_CHAR_SEQ
+ | ESC_BYTE_SEQ
+ | ESC_UNI_SEQ
+ | ESC_OCT_SEQ
+ ;
+
+fragment ESC_CHAR_SEQ
+ : BACKSLASH ('a'|'b'|'f'|'n'|'r'|'t'|'v'|'"'|'\''|'\\'|'?'|'`')
+ ;
+
+fragment ESC_OCT_SEQ
+ : BACKSLASH ('0'..'3') ('0'..'7') ('0'..'7')
+ ;
+
+fragment ESC_BYTE_SEQ
+ : BACKSLASH ( 'x' | 'X' ) HEXDIGIT HEXDIGIT
+ ;
+
+fragment ESC_UNI_SEQ
+ : BACKSLASH 'u' HEXDIGIT HEXDIGIT HEXDIGIT HEXDIGIT
+ | BACKSLASH 'U' HEXDIGIT HEXDIGIT HEXDIGIT HEXDIGIT HEXDIGIT HEXDIGIT HEXDIGIT HEXDIGIT
+ ;
+
+WHITESPACE : ( '\t' | ' ' | '\r' | '\n'| '\u000C' )+ -> channel(HIDDEN) ;
+COMMENT : '//' (~'\n')* -> channel(HIDDEN) ;
+
+NUM_FLOAT
+ : ( DIGIT+ ('.' DIGIT+) EXPONENT?
+ | DIGIT+ EXPONENT
+ | '.' DIGIT+ EXPONENT?
+ )
+ ;
+
+NUM_INT
+ : ( DIGIT+ | '0x' HEXDIGIT+ );
+
+NUM_UINT
+ : DIGIT+ ( 'u' | 'U' )
+ | '0x' HEXDIGIT+ ( 'u' | 'U' )
+ ;
+
+STRING
+ : '"' (ESC_SEQ | ~('\\'|'"'|'\n'|'\r'))* '"'
+ | '\'' (ESC_SEQ | ~('\\'|'\''|'\n'|'\r'))* '\''
+ | '"""' (ESC_SEQ | ~('\\'))*? '"""'
+ | '\'\'\'' (ESC_SEQ | ~('\\'))*? '\'\'\''
+ | RAW '"' ~('"'|'\n'|'\r')* '"'
+ | RAW '\'' ~('\''|'\n'|'\r')* '\''
+ | RAW '"""' .*? '"""'
+ | RAW '\'\'\'' .*? '\'\'\''
+ ;
+
+BYTES : ('b' | 'B') STRING;
+
+IDENTIFIER : (LETTER | '_') ( LETTER | DIGIT | '_')*;
diff --git a/vendor/github.com/google/cel-go/parser/gen/CEL.tokens b/vendor/github.com/google/cel-go/parser/gen/CEL.tokens
new file mode 100644
index 0000000000..c99e4c0210
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/CEL.tokens
@@ -0,0 +1,64 @@
+EQUALS=1
+NOT_EQUALS=2
+IN=3
+LESS=4
+LESS_EQUALS=5
+GREATER_EQUALS=6
+GREATER=7
+LOGICAL_AND=8
+LOGICAL_OR=9
+LBRACKET=10
+RPRACKET=11
+LBRACE=12
+RBRACE=13
+LPAREN=14
+RPAREN=15
+DOT=16
+COMMA=17
+MINUS=18
+EXCLAM=19
+QUESTIONMARK=20
+COLON=21
+PLUS=22
+STAR=23
+SLASH=24
+PERCENT=25
+TRUE=26
+FALSE=27
+NULL=28
+WHITESPACE=29
+COMMENT=30
+NUM_FLOAT=31
+NUM_INT=32
+NUM_UINT=33
+STRING=34
+BYTES=35
+IDENTIFIER=36
+'=='=1
+'!='=2
+'in'=3
+'<'=4
+'<='=5
+'>='=6
+'>'=7
+'&&'=8
+'||'=9
+'['=10
+']'=11
+'{'=12
+'}'=13
+'('=14
+')'=15
+'.'=16
+','=17
+'-'=18
+'!'=19
+'?'=20
+':'=21
+'+'=22
+'*'=23
+'/'=24
+'%'=25
+'true'=26
+'false'=27
+'null'=28
diff --git a/vendor/github.com/google/cel-go/parser/gen/CELLexer.tokens b/vendor/github.com/google/cel-go/parser/gen/CELLexer.tokens
new file mode 100644
index 0000000000..c99e4c0210
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/CELLexer.tokens
@@ -0,0 +1,64 @@
+EQUALS=1
+NOT_EQUALS=2
+IN=3
+LESS=4
+LESS_EQUALS=5
+GREATER_EQUALS=6
+GREATER=7
+LOGICAL_AND=8
+LOGICAL_OR=9
+LBRACKET=10
+RPRACKET=11
+LBRACE=12
+RBRACE=13
+LPAREN=14
+RPAREN=15
+DOT=16
+COMMA=17
+MINUS=18
+EXCLAM=19
+QUESTIONMARK=20
+COLON=21
+PLUS=22
+STAR=23
+SLASH=24
+PERCENT=25
+TRUE=26
+FALSE=27
+NULL=28
+WHITESPACE=29
+COMMENT=30
+NUM_FLOAT=31
+NUM_INT=32
+NUM_UINT=33
+STRING=34
+BYTES=35
+IDENTIFIER=36
+'=='=1
+'!='=2
+'in'=3
+'<'=4
+'<='=5
+'>='=6
+'>'=7
+'&&'=8
+'||'=9
+'['=10
+']'=11
+'{'=12
+'}'=13
+'('=14
+')'=15
+'.'=16
+','=17
+'-'=18
+'!'=19
+'?'=20
+':'=21
+'+'=22
+'*'=23
+'/'=24
+'%'=25
+'true'=26
+'false'=27
+'null'=28
diff --git a/vendor/github.com/google/cel-go/parser/gen/cel_base_listener.go b/vendor/github.com/google/cel-go/parser/gen/cel_base_listener.go
new file mode 100644
index 0000000000..94f6c58812
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/cel_base_listener.go
@@ -0,0 +1,195 @@
+// Generated from /Users/tswadell/go/src/github.com/google/cel-go/bin/../parser/gen/CEL.g4 by ANTLR 4.7.
+
+package gen // CEL
+import "github.com/antlr/antlr4/runtime/Go/antlr"
+
+// BaseCELListener is a complete listener for a parse tree produced by CELParser.
+type BaseCELListener struct{}
+
+var _ CELListener = &BaseCELListener{}
+
+// VisitTerminal is called when a terminal node is visited.
+func (s *BaseCELListener) VisitTerminal(node antlr.TerminalNode) {}
+
+// VisitErrorNode is called when an error node is visited.
+func (s *BaseCELListener) VisitErrorNode(node antlr.ErrorNode) {}
+
+// EnterEveryRule is called when any rule is entered.
+func (s *BaseCELListener) EnterEveryRule(ctx antlr.ParserRuleContext) {}
+
+// ExitEveryRule is called when any rule is exited.
+func (s *BaseCELListener) ExitEveryRule(ctx antlr.ParserRuleContext) {}
+
+// EnterStart is called when production start is entered.
+func (s *BaseCELListener) EnterStart(ctx *StartContext) {}
+
+// ExitStart is called when production start is exited.
+func (s *BaseCELListener) ExitStart(ctx *StartContext) {}
+
+// EnterExpr is called when production expr is entered.
+func (s *BaseCELListener) EnterExpr(ctx *ExprContext) {}
+
+// ExitExpr is called when production expr is exited.
+func (s *BaseCELListener) ExitExpr(ctx *ExprContext) {}
+
+// EnterConditionalOr is called when production conditionalOr is entered.
+func (s *BaseCELListener) EnterConditionalOr(ctx *ConditionalOrContext) {}
+
+// ExitConditionalOr is called when production conditionalOr is exited.
+func (s *BaseCELListener) ExitConditionalOr(ctx *ConditionalOrContext) {}
+
+// EnterConditionalAnd is called when production conditionalAnd is entered.
+func (s *BaseCELListener) EnterConditionalAnd(ctx *ConditionalAndContext) {}
+
+// ExitConditionalAnd is called when production conditionalAnd is exited.
+func (s *BaseCELListener) ExitConditionalAnd(ctx *ConditionalAndContext) {}
+
+// EnterRelation is called when production relation is entered.
+func (s *BaseCELListener) EnterRelation(ctx *RelationContext) {}
+
+// ExitRelation is called when production relation is exited.
+func (s *BaseCELListener) ExitRelation(ctx *RelationContext) {}
+
+// EnterCalc is called when production calc is entered.
+func (s *BaseCELListener) EnterCalc(ctx *CalcContext) {}
+
+// ExitCalc is called when production calc is exited.
+func (s *BaseCELListener) ExitCalc(ctx *CalcContext) {}
+
+// EnterMemberExpr is called when production MemberExpr is entered.
+func (s *BaseCELListener) EnterMemberExpr(ctx *MemberExprContext) {}
+
+// ExitMemberExpr is called when production MemberExpr is exited.
+func (s *BaseCELListener) ExitMemberExpr(ctx *MemberExprContext) {}
+
+// EnterLogicalNot is called when production LogicalNot is entered.
+func (s *BaseCELListener) EnterLogicalNot(ctx *LogicalNotContext) {}
+
+// ExitLogicalNot is called when production LogicalNot is exited.
+func (s *BaseCELListener) ExitLogicalNot(ctx *LogicalNotContext) {}
+
+// EnterNegate is called when production Negate is entered.
+func (s *BaseCELListener) EnterNegate(ctx *NegateContext) {}
+
+// ExitNegate is called when production Negate is exited.
+func (s *BaseCELListener) ExitNegate(ctx *NegateContext) {}
+
+// EnterSelectOrCall is called when production SelectOrCall is entered.
+func (s *BaseCELListener) EnterSelectOrCall(ctx *SelectOrCallContext) {}
+
+// ExitSelectOrCall is called when production SelectOrCall is exited.
+func (s *BaseCELListener) ExitSelectOrCall(ctx *SelectOrCallContext) {}
+
+// EnterPrimaryExpr is called when production PrimaryExpr is entered.
+func (s *BaseCELListener) EnterPrimaryExpr(ctx *PrimaryExprContext) {}
+
+// ExitPrimaryExpr is called when production PrimaryExpr is exited.
+func (s *BaseCELListener) ExitPrimaryExpr(ctx *PrimaryExprContext) {}
+
+// EnterIndex is called when production Index is entered.
+func (s *BaseCELListener) EnterIndex(ctx *IndexContext) {}
+
+// ExitIndex is called when production Index is exited.
+func (s *BaseCELListener) ExitIndex(ctx *IndexContext) {}
+
+// EnterCreateMessage is called when production CreateMessage is entered.
+func (s *BaseCELListener) EnterCreateMessage(ctx *CreateMessageContext) {}
+
+// ExitCreateMessage is called when production CreateMessage is exited.
+func (s *BaseCELListener) ExitCreateMessage(ctx *CreateMessageContext) {}
+
+// EnterIdentOrGlobalCall is called when production IdentOrGlobalCall is entered.
+func (s *BaseCELListener) EnterIdentOrGlobalCall(ctx *IdentOrGlobalCallContext) {}
+
+// ExitIdentOrGlobalCall is called when production IdentOrGlobalCall is exited.
+func (s *BaseCELListener) ExitIdentOrGlobalCall(ctx *IdentOrGlobalCallContext) {}
+
+// EnterNested is called when production Nested is entered.
+func (s *BaseCELListener) EnterNested(ctx *NestedContext) {}
+
+// ExitNested is called when production Nested is exited.
+func (s *BaseCELListener) ExitNested(ctx *NestedContext) {}
+
+// EnterCreateList is called when production CreateList is entered.
+func (s *BaseCELListener) EnterCreateList(ctx *CreateListContext) {}
+
+// ExitCreateList is called when production CreateList is exited.
+func (s *BaseCELListener) ExitCreateList(ctx *CreateListContext) {}
+
+// EnterCreateStruct is called when production CreateStruct is entered.
+func (s *BaseCELListener) EnterCreateStruct(ctx *CreateStructContext) {}
+
+// ExitCreateStruct is called when production CreateStruct is exited.
+func (s *BaseCELListener) ExitCreateStruct(ctx *CreateStructContext) {}
+
+// EnterConstantLiteral is called when production ConstantLiteral is entered.
+func (s *BaseCELListener) EnterConstantLiteral(ctx *ConstantLiteralContext) {}
+
+// ExitConstantLiteral is called when production ConstantLiteral is exited.
+func (s *BaseCELListener) ExitConstantLiteral(ctx *ConstantLiteralContext) {}
+
+// EnterExprList is called when production exprList is entered.
+func (s *BaseCELListener) EnterExprList(ctx *ExprListContext) {}
+
+// ExitExprList is called when production exprList is exited.
+func (s *BaseCELListener) ExitExprList(ctx *ExprListContext) {}
+
+// EnterFieldInitializerList is called when production fieldInitializerList is entered.
+func (s *BaseCELListener) EnterFieldInitializerList(ctx *FieldInitializerListContext) {}
+
+// ExitFieldInitializerList is called when production fieldInitializerList is exited.
+func (s *BaseCELListener) ExitFieldInitializerList(ctx *FieldInitializerListContext) {}
+
+// EnterMapInitializerList is called when production mapInitializerList is entered.
+func (s *BaseCELListener) EnterMapInitializerList(ctx *MapInitializerListContext) {}
+
+// ExitMapInitializerList is called when production mapInitializerList is exited.
+func (s *BaseCELListener) ExitMapInitializerList(ctx *MapInitializerListContext) {}
+
+// EnterInt is called when production Int is entered.
+func (s *BaseCELListener) EnterInt(ctx *IntContext) {}
+
+// ExitInt is called when production Int is exited.
+func (s *BaseCELListener) ExitInt(ctx *IntContext) {}
+
+// EnterUint is called when production Uint is entered.
+func (s *BaseCELListener) EnterUint(ctx *UintContext) {}
+
+// ExitUint is called when production Uint is exited.
+func (s *BaseCELListener) ExitUint(ctx *UintContext) {}
+
+// EnterDouble is called when production Double is entered.
+func (s *BaseCELListener) EnterDouble(ctx *DoubleContext) {}
+
+// ExitDouble is called when production Double is exited.
+func (s *BaseCELListener) ExitDouble(ctx *DoubleContext) {}
+
+// EnterString is called when production String is entered.
+func (s *BaseCELListener) EnterString(ctx *StringContext) {}
+
+// ExitString is called when production String is exited.
+func (s *BaseCELListener) ExitString(ctx *StringContext) {}
+
+// EnterBytes is called when production Bytes is entered.
+func (s *BaseCELListener) EnterBytes(ctx *BytesContext) {}
+
+// ExitBytes is called when production Bytes is exited.
+func (s *BaseCELListener) ExitBytes(ctx *BytesContext) {}
+
+// EnterBoolTrue is called when production BoolTrue is entered.
+func (s *BaseCELListener) EnterBoolTrue(ctx *BoolTrueContext) {}
+
+// ExitBoolTrue is called when production BoolTrue is exited.
+func (s *BaseCELListener) ExitBoolTrue(ctx *BoolTrueContext) {}
+
+// EnterBoolFalse is called when production BoolFalse is entered.
+func (s *BaseCELListener) EnterBoolFalse(ctx *BoolFalseContext) {}
+
+// ExitBoolFalse is called when production BoolFalse is exited.
+func (s *BaseCELListener) ExitBoolFalse(ctx *BoolFalseContext) {}
+
+// EnterNull is called when production Null is entered.
+func (s *BaseCELListener) EnterNull(ctx *NullContext) {}
+
+// ExitNull is called when production Null is exited.
+func (s *BaseCELListener) ExitNull(ctx *NullContext) {}
diff --git a/vendor/github.com/google/cel-go/parser/gen/cel_base_visitor.go b/vendor/github.com/google/cel-go/parser/gen/cel_base_visitor.go
new file mode 100644
index 0000000000..bb46a64d5e
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/cel_base_visitor.go
@@ -0,0 +1,124 @@
+// Generated from /Users/tswadell/go/src/github.com/google/cel-go/bin/../parser/gen/CEL.g4 by ANTLR 4.7.
+
+package gen // CEL
+import "github.com/antlr/antlr4/runtime/Go/antlr"
+
+type BaseCELVisitor struct {
+ *antlr.BaseParseTreeVisitor
+}
+
+func (v *BaseCELVisitor) VisitStart(ctx *StartContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitExpr(ctx *ExprContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitConditionalOr(ctx *ConditionalOrContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitConditionalAnd(ctx *ConditionalAndContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitRelation(ctx *RelationContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitCalc(ctx *CalcContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitMemberExpr(ctx *MemberExprContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitLogicalNot(ctx *LogicalNotContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitNegate(ctx *NegateContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitSelectOrCall(ctx *SelectOrCallContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitPrimaryExpr(ctx *PrimaryExprContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitIndex(ctx *IndexContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitCreateMessage(ctx *CreateMessageContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitIdentOrGlobalCall(ctx *IdentOrGlobalCallContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitNested(ctx *NestedContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitCreateList(ctx *CreateListContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitCreateStruct(ctx *CreateStructContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitConstantLiteral(ctx *ConstantLiteralContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitExprList(ctx *ExprListContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitFieldInitializerList(ctx *FieldInitializerListContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitMapInitializerList(ctx *MapInitializerListContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitInt(ctx *IntContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitUint(ctx *UintContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitDouble(ctx *DoubleContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitString(ctx *StringContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitBytes(ctx *BytesContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitBoolTrue(ctx *BoolTrueContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitBoolFalse(ctx *BoolFalseContext) interface{} {
+ return v.VisitChildren(ctx)
+}
+
+func (v *BaseCELVisitor) VisitNull(ctx *NullContext) interface{} {
+ return v.VisitChildren(ctx)
+}
diff --git a/vendor/github.com/google/cel-go/parser/gen/cel_lexer.go b/vendor/github.com/google/cel-go/parser/gen/cel_lexer.go
new file mode 100644
index 0000000000..b76f78a650
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/cel_lexer.go
@@ -0,0 +1,319 @@
+// Generated from /Users/tswadell/go/src/github.com/google/cel-go/bin/../parser/gen/CEL.g4 by ANTLR 4.7.
+
+package gen
+
+import (
+ "fmt"
+ "unicode"
+
+ "github.com/antlr/antlr4/runtime/Go/antlr"
+)
+
+// Suppress unused import error
+var _ = fmt.Printf
+var _ = unicode.IsLetter
+
+var serializedLexerAtn = []uint16{
+ 3, 24715, 42794, 33075, 47597, 16764, 15335, 30598, 22884, 2, 38, 425,
+ 8, 1, 4, 2, 9, 2, 4, 3, 9, 3, 4, 4, 9, 4, 4, 5, 9, 5, 4, 6, 9, 6, 4, 7,
+ 9, 7, 4, 8, 9, 8, 4, 9, 9, 9, 4, 10, 9, 10, 4, 11, 9, 11, 4, 12, 9, 12,
+ 4, 13, 9, 13, 4, 14, 9, 14, 4, 15, 9, 15, 4, 16, 9, 16, 4, 17, 9, 17, 4,
+ 18, 9, 18, 4, 19, 9, 19, 4, 20, 9, 20, 4, 21, 9, 21, 4, 22, 9, 22, 4, 23,
+ 9, 23, 4, 24, 9, 24, 4, 25, 9, 25, 4, 26, 9, 26, 4, 27, 9, 27, 4, 28, 9,
+ 28, 4, 29, 9, 29, 4, 30, 9, 30, 4, 31, 9, 31, 4, 32, 9, 32, 4, 33, 9, 33,
+ 4, 34, 9, 34, 4, 35, 9, 35, 4, 36, 9, 36, 4, 37, 9, 37, 4, 38, 9, 38, 4,
+ 39, 9, 39, 4, 40, 9, 40, 4, 41, 9, 41, 4, 42, 9, 42, 4, 43, 9, 43, 4, 44,
+ 9, 44, 4, 45, 9, 45, 4, 46, 9, 46, 4, 47, 9, 47, 4, 48, 9, 48, 3, 2, 3,
+ 2, 3, 2, 3, 3, 3, 3, 3, 3, 3, 4, 3, 4, 3, 4, 3, 5, 3, 5, 3, 6, 3, 6, 3,
+ 6, 3, 7, 3, 7, 3, 7, 3, 8, 3, 8, 3, 9, 3, 9, 3, 9, 3, 10, 3, 10, 3, 10,
+ 3, 11, 3, 11, 3, 12, 3, 12, 3, 13, 3, 13, 3, 14, 3, 14, 3, 15, 3, 15, 3,
+ 16, 3, 16, 3, 17, 3, 17, 3, 18, 3, 18, 3, 19, 3, 19, 3, 20, 3, 20, 3, 21,
+ 3, 21, 3, 22, 3, 22, 3, 23, 3, 23, 3, 24, 3, 24, 3, 25, 3, 25, 3, 26, 3,
+ 26, 3, 27, 3, 27, 3, 27, 3, 27, 3, 27, 3, 28, 3, 28, 3, 28, 3, 28, 3, 28,
+ 3, 28, 3, 29, 3, 29, 3, 29, 3, 29, 3, 29, 3, 30, 3, 30, 3, 31, 3, 31, 3,
+ 32, 3, 32, 3, 33, 3, 33, 5, 33, 179, 10, 33, 3, 33, 6, 33, 182, 10, 33,
+ 13, 33, 14, 33, 183, 3, 34, 3, 34, 3, 35, 3, 35, 3, 36, 3, 36, 3, 36, 3,
+ 36, 5, 36, 194, 10, 36, 3, 37, 3, 37, 3, 37, 3, 38, 3, 38, 3, 38, 3, 38,
+ 3, 38, 3, 39, 3, 39, 3, 39, 3, 39, 3, 39, 3, 40, 3, 40, 3, 40, 3, 40, 3,
+ 40, 3, 40, 3, 40, 3, 40, 3, 40, 3, 40, 3, 40, 3, 40, 3, 40, 3, 40, 3, 40,
+ 3, 40, 3, 40, 3, 40, 5, 40, 227, 10, 40, 3, 41, 6, 41, 230, 10, 41, 13,
+ 41, 14, 41, 231, 3, 41, 3, 41, 3, 42, 3, 42, 3, 42, 3, 42, 7, 42, 240,
+ 10, 42, 12, 42, 14, 42, 243, 11, 42, 3, 42, 3, 42, 3, 43, 6, 43, 248, 10,
+ 43, 13, 43, 14, 43, 249, 3, 43, 3, 43, 6, 43, 254, 10, 43, 13, 43, 14,
+ 43, 255, 3, 43, 5, 43, 259, 10, 43, 3, 43, 6, 43, 262, 10, 43, 13, 43,
+ 14, 43, 263, 3, 43, 3, 43, 3, 43, 3, 43, 6, 43, 270, 10, 43, 13, 43, 14,
+ 43, 271, 3, 43, 5, 43, 275, 10, 43, 5, 43, 277, 10, 43, 3, 44, 6, 44, 280,
+ 10, 44, 13, 44, 14, 44, 281, 3, 44, 3, 44, 3, 44, 3, 44, 6, 44, 288, 10,
+ 44, 13, 44, 14, 44, 289, 5, 44, 292, 10, 44, 3, 45, 6, 45, 295, 10, 45,
+ 13, 45, 14, 45, 296, 3, 45, 3, 45, 3, 45, 3, 45, 3, 45, 3, 45, 6, 45, 305,
+ 10, 45, 13, 45, 14, 45, 306, 3, 45, 3, 45, 5, 45, 311, 10, 45, 3, 46, 3,
+ 46, 3, 46, 7, 46, 316, 10, 46, 12, 46, 14, 46, 319, 11, 46, 3, 46, 3, 46,
+ 3, 46, 3, 46, 7, 46, 325, 10, 46, 12, 46, 14, 46, 328, 11, 46, 3, 46, 3,
+ 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 7, 46, 337, 10, 46, 12, 46, 14,
+ 46, 340, 11, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46,
+ 3, 46, 7, 46, 351, 10, 46, 12, 46, 14, 46, 354, 11, 46, 3, 46, 3, 46, 3,
+ 46, 3, 46, 3, 46, 3, 46, 7, 46, 362, 10, 46, 12, 46, 14, 46, 365, 11, 46,
+ 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 7, 46, 372, 10, 46, 12, 46, 14, 46,
+ 375, 11, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 7,
+ 46, 385, 10, 46, 12, 46, 14, 46, 388, 11, 46, 3, 46, 3, 46, 3, 46, 3, 46,
+ 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 3, 46, 7, 46, 400, 10, 46, 12, 46, 14,
+ 46, 403, 11, 46, 3, 46, 3, 46, 3, 46, 3, 46, 5, 46, 409, 10, 46, 3, 47,
+ 3, 47, 3, 47, 3, 48, 3, 48, 5, 48, 416, 10, 48, 3, 48, 3, 48, 3, 48, 7,
+ 48, 421, 10, 48, 12, 48, 14, 48, 424, 11, 48, 6, 338, 352, 386, 401, 2,
+ 49, 3, 3, 5, 4, 7, 5, 9, 6, 11, 7, 13, 8, 15, 9, 17, 10, 19, 11, 21, 12,
+ 23, 13, 25, 14, 27, 15, 29, 16, 31, 17, 33, 18, 35, 19, 37, 20, 39, 21,
+ 41, 22, 43, 23, 45, 24, 47, 25, 49, 26, 51, 27, 53, 28, 55, 29, 57, 30,
+ 59, 2, 61, 2, 63, 2, 65, 2, 67, 2, 69, 2, 71, 2, 73, 2, 75, 2, 77, 2, 79,
+ 2, 81, 31, 83, 32, 85, 33, 87, 34, 89, 35, 91, 36, 93, 37, 95, 38, 3, 2,
+ 18, 4, 2, 67, 92, 99, 124, 4, 2, 71, 71, 103, 103, 4, 2, 45, 45, 47, 47,
+ 5, 2, 50, 59, 67, 72, 99, 104, 4, 2, 84, 84, 116, 116, 12, 2, 36, 36, 41,
+ 41, 65, 65, 94, 94, 98, 100, 104, 104, 112, 112, 116, 116, 118, 118, 120,
+ 120, 4, 2, 90, 90, 122, 122, 5, 2, 11, 12, 14, 15, 34, 34, 3, 2, 12, 12,
+ 4, 2, 87, 87, 119, 119, 6, 2, 12, 12, 15, 15, 36, 36, 94, 94, 6, 2, 12,
+ 12, 15, 15, 41, 41, 94, 94, 3, 2, 94, 94, 5, 2, 12, 12, 15, 15, 36, 36,
+ 5, 2, 12, 12, 15, 15, 41, 41, 4, 2, 68, 68, 100, 100, 2, 458, 2, 3, 3,
+ 2, 2, 2, 2, 5, 3, 2, 2, 2, 2, 7, 3, 2, 2, 2, 2, 9, 3, 2, 2, 2, 2, 11, 3,
+ 2, 2, 2, 2, 13, 3, 2, 2, 2, 2, 15, 3, 2, 2, 2, 2, 17, 3, 2, 2, 2, 2, 19,
+ 3, 2, 2, 2, 2, 21, 3, 2, 2, 2, 2, 23, 3, 2, 2, 2, 2, 25, 3, 2, 2, 2, 2,
+ 27, 3, 2, 2, 2, 2, 29, 3, 2, 2, 2, 2, 31, 3, 2, 2, 2, 2, 33, 3, 2, 2, 2,
+ 2, 35, 3, 2, 2, 2, 2, 37, 3, 2, 2, 2, 2, 39, 3, 2, 2, 2, 2, 41, 3, 2, 2,
+ 2, 2, 43, 3, 2, 2, 2, 2, 45, 3, 2, 2, 2, 2, 47, 3, 2, 2, 2, 2, 49, 3, 2,
+ 2, 2, 2, 51, 3, 2, 2, 2, 2, 53, 3, 2, 2, 2, 2, 55, 3, 2, 2, 2, 2, 57, 3,
+ 2, 2, 2, 2, 81, 3, 2, 2, 2, 2, 83, 3, 2, 2, 2, 2, 85, 3, 2, 2, 2, 2, 87,
+ 3, 2, 2, 2, 2, 89, 3, 2, 2, 2, 2, 91, 3, 2, 2, 2, 2, 93, 3, 2, 2, 2, 2,
+ 95, 3, 2, 2, 2, 3, 97, 3, 2, 2, 2, 5, 100, 3, 2, 2, 2, 7, 103, 3, 2, 2,
+ 2, 9, 106, 3, 2, 2, 2, 11, 108, 3, 2, 2, 2, 13, 111, 3, 2, 2, 2, 15, 114,
+ 3, 2, 2, 2, 17, 116, 3, 2, 2, 2, 19, 119, 3, 2, 2, 2, 21, 122, 3, 2, 2,
+ 2, 23, 124, 3, 2, 2, 2, 25, 126, 3, 2, 2, 2, 27, 128, 3, 2, 2, 2, 29, 130,
+ 3, 2, 2, 2, 31, 132, 3, 2, 2, 2, 33, 134, 3, 2, 2, 2, 35, 136, 3, 2, 2,
+ 2, 37, 138, 3, 2, 2, 2, 39, 140, 3, 2, 2, 2, 41, 142, 3, 2, 2, 2, 43, 144,
+ 3, 2, 2, 2, 45, 146, 3, 2, 2, 2, 47, 148, 3, 2, 2, 2, 49, 150, 3, 2, 2,
+ 2, 51, 152, 3, 2, 2, 2, 53, 154, 3, 2, 2, 2, 55, 159, 3, 2, 2, 2, 57, 165,
+ 3, 2, 2, 2, 59, 170, 3, 2, 2, 2, 61, 172, 3, 2, 2, 2, 63, 174, 3, 2, 2,
+ 2, 65, 176, 3, 2, 2, 2, 67, 185, 3, 2, 2, 2, 69, 187, 3, 2, 2, 2, 71, 193,
+ 3, 2, 2, 2, 73, 195, 3, 2, 2, 2, 75, 198, 3, 2, 2, 2, 77, 203, 3, 2, 2,
+ 2, 79, 226, 3, 2, 2, 2, 81, 229, 3, 2, 2, 2, 83, 235, 3, 2, 2, 2, 85, 276,
+ 3, 2, 2, 2, 87, 291, 3, 2, 2, 2, 89, 310, 3, 2, 2, 2, 91, 408, 3, 2, 2,
+ 2, 93, 410, 3, 2, 2, 2, 95, 415, 3, 2, 2, 2, 97, 98, 7, 63, 2, 2, 98, 99,
+ 7, 63, 2, 2, 99, 4, 3, 2, 2, 2, 100, 101, 7, 35, 2, 2, 101, 102, 7, 63,
+ 2, 2, 102, 6, 3, 2, 2, 2, 103, 104, 7, 107, 2, 2, 104, 105, 7, 112, 2,
+ 2, 105, 8, 3, 2, 2, 2, 106, 107, 7, 62, 2, 2, 107, 10, 3, 2, 2, 2, 108,
+ 109, 7, 62, 2, 2, 109, 110, 7, 63, 2, 2, 110, 12, 3, 2, 2, 2, 111, 112,
+ 7, 64, 2, 2, 112, 113, 7, 63, 2, 2, 113, 14, 3, 2, 2, 2, 114, 115, 7, 64,
+ 2, 2, 115, 16, 3, 2, 2, 2, 116, 117, 7, 40, 2, 2, 117, 118, 7, 40, 2, 2,
+ 118, 18, 3, 2, 2, 2, 119, 120, 7, 126, 2, 2, 120, 121, 7, 126, 2, 2, 121,
+ 20, 3, 2, 2, 2, 122, 123, 7, 93, 2, 2, 123, 22, 3, 2, 2, 2, 124, 125, 7,
+ 95, 2, 2, 125, 24, 3, 2, 2, 2, 126, 127, 7, 125, 2, 2, 127, 26, 3, 2, 2,
+ 2, 128, 129, 7, 127, 2, 2, 129, 28, 3, 2, 2, 2, 130, 131, 7, 42, 2, 2,
+ 131, 30, 3, 2, 2, 2, 132, 133, 7, 43, 2, 2, 133, 32, 3, 2, 2, 2, 134, 135,
+ 7, 48, 2, 2, 135, 34, 3, 2, 2, 2, 136, 137, 7, 46, 2, 2, 137, 36, 3, 2,
+ 2, 2, 138, 139, 7, 47, 2, 2, 139, 38, 3, 2, 2, 2, 140, 141, 7, 35, 2, 2,
+ 141, 40, 3, 2, 2, 2, 142, 143, 7, 65, 2, 2, 143, 42, 3, 2, 2, 2, 144, 145,
+ 7, 60, 2, 2, 145, 44, 3, 2, 2, 2, 146, 147, 7, 45, 2, 2, 147, 46, 3, 2,
+ 2, 2, 148, 149, 7, 44, 2, 2, 149, 48, 3, 2, 2, 2, 150, 151, 7, 49, 2, 2,
+ 151, 50, 3, 2, 2, 2, 152, 153, 7, 39, 2, 2, 153, 52, 3, 2, 2, 2, 154, 155,
+ 7, 118, 2, 2, 155, 156, 7, 116, 2, 2, 156, 157, 7, 119, 2, 2, 157, 158,
+ 7, 103, 2, 2, 158, 54, 3, 2, 2, 2, 159, 160, 7, 104, 2, 2, 160, 161, 7,
+ 99, 2, 2, 161, 162, 7, 110, 2, 2, 162, 163, 7, 117, 2, 2, 163, 164, 7,
+ 103, 2, 2, 164, 56, 3, 2, 2, 2, 165, 166, 7, 112, 2, 2, 166, 167, 7, 119,
+ 2, 2, 167, 168, 7, 110, 2, 2, 168, 169, 7, 110, 2, 2, 169, 58, 3, 2, 2,
+ 2, 170, 171, 7, 94, 2, 2, 171, 60, 3, 2, 2, 2, 172, 173, 9, 2, 2, 2, 173,
+ 62, 3, 2, 2, 2, 174, 175, 4, 50, 59, 2, 175, 64, 3, 2, 2, 2, 176, 178,
+ 9, 3, 2, 2, 177, 179, 9, 4, 2, 2, 178, 177, 3, 2, 2, 2, 178, 179, 3, 2,
+ 2, 2, 179, 181, 3, 2, 2, 2, 180, 182, 5, 63, 32, 2, 181, 180, 3, 2, 2,
+ 2, 182, 183, 3, 2, 2, 2, 183, 181, 3, 2, 2, 2, 183, 184, 3, 2, 2, 2, 184,
+ 66, 3, 2, 2, 2, 185, 186, 9, 5, 2, 2, 186, 68, 3, 2, 2, 2, 187, 188, 9,
+ 6, 2, 2, 188, 70, 3, 2, 2, 2, 189, 194, 5, 73, 37, 2, 190, 194, 5, 77,
+ 39, 2, 191, 194, 5, 79, 40, 2, 192, 194, 5, 75, 38, 2, 193, 189, 3, 2,
+ 2, 2, 193, 190, 3, 2, 2, 2, 193, 191, 3, 2, 2, 2, 193, 192, 3, 2, 2, 2,
+ 194, 72, 3, 2, 2, 2, 195, 196, 5, 59, 30, 2, 196, 197, 9, 7, 2, 2, 197,
+ 74, 3, 2, 2, 2, 198, 199, 5, 59, 30, 2, 199, 200, 4, 50, 53, 2, 200, 201,
+ 4, 50, 57, 2, 201, 202, 4, 50, 57, 2, 202, 76, 3, 2, 2, 2, 203, 204, 5,
+ 59, 30, 2, 204, 205, 9, 8, 2, 2, 205, 206, 5, 67, 34, 2, 206, 207, 5, 67,
+ 34, 2, 207, 78, 3, 2, 2, 2, 208, 209, 5, 59, 30, 2, 209, 210, 7, 119, 2,
+ 2, 210, 211, 5, 67, 34, 2, 211, 212, 5, 67, 34, 2, 212, 213, 5, 67, 34,
+ 2, 213, 214, 5, 67, 34, 2, 214, 227, 3, 2, 2, 2, 215, 216, 5, 59, 30, 2,
+ 216, 217, 7, 87, 2, 2, 217, 218, 5, 67, 34, 2, 218, 219, 5, 67, 34, 2,
+ 219, 220, 5, 67, 34, 2, 220, 221, 5, 67, 34, 2, 221, 222, 5, 67, 34, 2,
+ 222, 223, 5, 67, 34, 2, 223, 224, 5, 67, 34, 2, 224, 225, 5, 67, 34, 2,
+ 225, 227, 3, 2, 2, 2, 226, 208, 3, 2, 2, 2, 226, 215, 3, 2, 2, 2, 227,
+ 80, 3, 2, 2, 2, 228, 230, 9, 9, 2, 2, 229, 228, 3, 2, 2, 2, 230, 231, 3,
+ 2, 2, 2, 231, 229, 3, 2, 2, 2, 231, 232, 3, 2, 2, 2, 232, 233, 3, 2, 2,
+ 2, 233, 234, 8, 41, 2, 2, 234, 82, 3, 2, 2, 2, 235, 236, 7, 49, 2, 2, 236,
+ 237, 7, 49, 2, 2, 237, 241, 3, 2, 2, 2, 238, 240, 10, 10, 2, 2, 239, 238,
+ 3, 2, 2, 2, 240, 243, 3, 2, 2, 2, 241, 239, 3, 2, 2, 2, 241, 242, 3, 2,
+ 2, 2, 242, 244, 3, 2, 2, 2, 243, 241, 3, 2, 2, 2, 244, 245, 8, 42, 2, 2,
+ 245, 84, 3, 2, 2, 2, 246, 248, 5, 63, 32, 2, 247, 246, 3, 2, 2, 2, 248,
+ 249, 3, 2, 2, 2, 249, 247, 3, 2, 2, 2, 249, 250, 3, 2, 2, 2, 250, 251,
+ 3, 2, 2, 2, 251, 253, 7, 48, 2, 2, 252, 254, 5, 63, 32, 2, 253, 252, 3,
+ 2, 2, 2, 254, 255, 3, 2, 2, 2, 255, 253, 3, 2, 2, 2, 255, 256, 3, 2, 2,
+ 2, 256, 258, 3, 2, 2, 2, 257, 259, 5, 65, 33, 2, 258, 257, 3, 2, 2, 2,
+ 258, 259, 3, 2, 2, 2, 259, 277, 3, 2, 2, 2, 260, 262, 5, 63, 32, 2, 261,
+ 260, 3, 2, 2, 2, 262, 263, 3, 2, 2, 2, 263, 261, 3, 2, 2, 2, 263, 264,
+ 3, 2, 2, 2, 264, 265, 3, 2, 2, 2, 265, 266, 5, 65, 33, 2, 266, 277, 3,
+ 2, 2, 2, 267, 269, 7, 48, 2, 2, 268, 270, 5, 63, 32, 2, 269, 268, 3, 2,
+ 2, 2, 270, 271, 3, 2, 2, 2, 271, 269, 3, 2, 2, 2, 271, 272, 3, 2, 2, 2,
+ 272, 274, 3, 2, 2, 2, 273, 275, 5, 65, 33, 2, 274, 273, 3, 2, 2, 2, 274,
+ 275, 3, 2, 2, 2, 275, 277, 3, 2, 2, 2, 276, 247, 3, 2, 2, 2, 276, 261,
+ 3, 2, 2, 2, 276, 267, 3, 2, 2, 2, 277, 86, 3, 2, 2, 2, 278, 280, 5, 63,
+ 32, 2, 279, 278, 3, 2, 2, 2, 280, 281, 3, 2, 2, 2, 281, 279, 3, 2, 2, 2,
+ 281, 282, 3, 2, 2, 2, 282, 292, 3, 2, 2, 2, 283, 284, 7, 50, 2, 2, 284,
+ 285, 7, 122, 2, 2, 285, 287, 3, 2, 2, 2, 286, 288, 5, 67, 34, 2, 287, 286,
+ 3, 2, 2, 2, 288, 289, 3, 2, 2, 2, 289, 287, 3, 2, 2, 2, 289, 290, 3, 2,
+ 2, 2, 290, 292, 3, 2, 2, 2, 291, 279, 3, 2, 2, 2, 291, 283, 3, 2, 2, 2,
+ 292, 88, 3, 2, 2, 2, 293, 295, 5, 63, 32, 2, 294, 293, 3, 2, 2, 2, 295,
+ 296, 3, 2, 2, 2, 296, 294, 3, 2, 2, 2, 296, 297, 3, 2, 2, 2, 297, 298,
+ 3, 2, 2, 2, 298, 299, 9, 11, 2, 2, 299, 311, 3, 2, 2, 2, 300, 301, 7, 50,
+ 2, 2, 301, 302, 7, 122, 2, 2, 302, 304, 3, 2, 2, 2, 303, 305, 5, 67, 34,
+ 2, 304, 303, 3, 2, 2, 2, 305, 306, 3, 2, 2, 2, 306, 304, 3, 2, 2, 2, 306,
+ 307, 3, 2, 2, 2, 307, 308, 3, 2, 2, 2, 308, 309, 9, 11, 2, 2, 309, 311,
+ 3, 2, 2, 2, 310, 294, 3, 2, 2, 2, 310, 300, 3, 2, 2, 2, 311, 90, 3, 2,
+ 2, 2, 312, 317, 7, 36, 2, 2, 313, 316, 5, 71, 36, 2, 314, 316, 10, 12,
+ 2, 2, 315, 313, 3, 2, 2, 2, 315, 314, 3, 2, 2, 2, 316, 319, 3, 2, 2, 2,
+ 317, 315, 3, 2, 2, 2, 317, 318, 3, 2, 2, 2, 318, 320, 3, 2, 2, 2, 319,
+ 317, 3, 2, 2, 2, 320, 409, 7, 36, 2, 2, 321, 326, 7, 41, 2, 2, 322, 325,
+ 5, 71, 36, 2, 323, 325, 10, 13, 2, 2, 324, 322, 3, 2, 2, 2, 324, 323, 3,
+ 2, 2, 2, 325, 328, 3, 2, 2, 2, 326, 324, 3, 2, 2, 2, 326, 327, 3, 2, 2,
+ 2, 327, 329, 3, 2, 2, 2, 328, 326, 3, 2, 2, 2, 329, 409, 7, 41, 2, 2, 330,
+ 331, 7, 36, 2, 2, 331, 332, 7, 36, 2, 2, 332, 333, 7, 36, 2, 2, 333, 338,
+ 3, 2, 2, 2, 334, 337, 5, 71, 36, 2, 335, 337, 10, 14, 2, 2, 336, 334, 3,
+ 2, 2, 2, 336, 335, 3, 2, 2, 2, 337, 340, 3, 2, 2, 2, 338, 339, 3, 2, 2,
+ 2, 338, 336, 3, 2, 2, 2, 339, 341, 3, 2, 2, 2, 340, 338, 3, 2, 2, 2, 341,
+ 342, 7, 36, 2, 2, 342, 343, 7, 36, 2, 2, 343, 409, 7, 36, 2, 2, 344, 345,
+ 7, 41, 2, 2, 345, 346, 7, 41, 2, 2, 346, 347, 7, 41, 2, 2, 347, 352, 3,
+ 2, 2, 2, 348, 351, 5, 71, 36, 2, 349, 351, 10, 14, 2, 2, 350, 348, 3, 2,
+ 2, 2, 350, 349, 3, 2, 2, 2, 351, 354, 3, 2, 2, 2, 352, 353, 3, 2, 2, 2,
+ 352, 350, 3, 2, 2, 2, 353, 355, 3, 2, 2, 2, 354, 352, 3, 2, 2, 2, 355,
+ 356, 7, 41, 2, 2, 356, 357, 7, 41, 2, 2, 357, 409, 7, 41, 2, 2, 358, 359,
+ 5, 69, 35, 2, 359, 363, 7, 36, 2, 2, 360, 362, 10, 15, 2, 2, 361, 360,
+ 3, 2, 2, 2, 362, 365, 3, 2, 2, 2, 363, 361, 3, 2, 2, 2, 363, 364, 3, 2,
+ 2, 2, 364, 366, 3, 2, 2, 2, 365, 363, 3, 2, 2, 2, 366, 367, 7, 36, 2, 2,
+ 367, 409, 3, 2, 2, 2, 368, 369, 5, 69, 35, 2, 369, 373, 7, 41, 2, 2, 370,
+ 372, 10, 16, 2, 2, 371, 370, 3, 2, 2, 2, 372, 375, 3, 2, 2, 2, 373, 371,
+ 3, 2, 2, 2, 373, 374, 3, 2, 2, 2, 374, 376, 3, 2, 2, 2, 375, 373, 3, 2,
+ 2, 2, 376, 377, 7, 41, 2, 2, 377, 409, 3, 2, 2, 2, 378, 379, 5, 69, 35,
+ 2, 379, 380, 7, 36, 2, 2, 380, 381, 7, 36, 2, 2, 381, 382, 7, 36, 2, 2,
+ 382, 386, 3, 2, 2, 2, 383, 385, 11, 2, 2, 2, 384, 383, 3, 2, 2, 2, 385,
+ 388, 3, 2, 2, 2, 386, 387, 3, 2, 2, 2, 386, 384, 3, 2, 2, 2, 387, 389,
+ 3, 2, 2, 2, 388, 386, 3, 2, 2, 2, 389, 390, 7, 36, 2, 2, 390, 391, 7, 36,
+ 2, 2, 391, 392, 7, 36, 2, 2, 392, 409, 3, 2, 2, 2, 393, 394, 5, 69, 35,
+ 2, 394, 395, 7, 41, 2, 2, 395, 396, 7, 41, 2, 2, 396, 397, 7, 41, 2, 2,
+ 397, 401, 3, 2, 2, 2, 398, 400, 11, 2, 2, 2, 399, 398, 3, 2, 2, 2, 400,
+ 403, 3, 2, 2, 2, 401, 402, 3, 2, 2, 2, 401, 399, 3, 2, 2, 2, 402, 404,
+ 3, 2, 2, 2, 403, 401, 3, 2, 2, 2, 404, 405, 7, 41, 2, 2, 405, 406, 7, 41,
+ 2, 2, 406, 407, 7, 41, 2, 2, 407, 409, 3, 2, 2, 2, 408, 312, 3, 2, 2, 2,
+ 408, 321, 3, 2, 2, 2, 408, 330, 3, 2, 2, 2, 408, 344, 3, 2, 2, 2, 408,
+ 358, 3, 2, 2, 2, 408, 368, 3, 2, 2, 2, 408, 378, 3, 2, 2, 2, 408, 393,
+ 3, 2, 2, 2, 409, 92, 3, 2, 2, 2, 410, 411, 9, 17, 2, 2, 411, 412, 5, 91,
+ 46, 2, 412, 94, 3, 2, 2, 2, 413, 416, 5, 61, 31, 2, 414, 416, 7, 97, 2,
+ 2, 415, 413, 3, 2, 2, 2, 415, 414, 3, 2, 2, 2, 416, 422, 3, 2, 2, 2, 417,
+ 421, 5, 61, 31, 2, 418, 421, 5, 63, 32, 2, 419, 421, 7, 97, 2, 2, 420,
+ 417, 3, 2, 2, 2, 420, 418, 3, 2, 2, 2, 420, 419, 3, 2, 2, 2, 421, 424,
+ 3, 2, 2, 2, 422, 420, 3, 2, 2, 2, 422, 423, 3, 2, 2, 2, 423, 96, 3, 2,
+ 2, 2, 424, 422, 3, 2, 2, 2, 38, 2, 178, 183, 193, 226, 231, 241, 249, 255,
+ 258, 263, 271, 274, 276, 281, 289, 291, 296, 306, 310, 315, 317, 324, 326,
+ 336, 338, 350, 352, 363, 373, 386, 401, 408, 415, 420, 422, 3, 2, 3, 2,
+}
+
+var lexerChannelNames = []string{
+ "DEFAULT_TOKEN_CHANNEL", "HIDDEN",
+}
+
+var lexerModeNames = []string{
+ "DEFAULT_MODE",
+}
+
+var lexerLiteralNames = []string{
+ "", "'=='", "'!='", "'in'", "'<'", "'<='", "'>='", "'>'", "'&&'", "'||'",
+ "'['", "']'", "'{'", "'}'", "'('", "')'", "'.'", "','", "'-'", "'!'", "'?'",
+ "':'", "'+'", "'*'", "'/'", "'%'", "'true'", "'false'", "'null'",
+}
+
+var lexerSymbolicNames = []string{
+ "", "EQUALS", "NOT_EQUALS", "IN", "LESS", "LESS_EQUALS", "GREATER_EQUALS",
+ "GREATER", "LOGICAL_AND", "LOGICAL_OR", "LBRACKET", "RPRACKET", "LBRACE",
+ "RBRACE", "LPAREN", "RPAREN", "DOT", "COMMA", "MINUS", "EXCLAM", "QUESTIONMARK",
+ "COLON", "PLUS", "STAR", "SLASH", "PERCENT", "TRUE", "FALSE", "NULL", "WHITESPACE",
+ "COMMENT", "NUM_FLOAT", "NUM_INT", "NUM_UINT", "STRING", "BYTES", "IDENTIFIER",
+}
+
+var lexerRuleNames = []string{
+ "EQUALS", "NOT_EQUALS", "IN", "LESS", "LESS_EQUALS", "GREATER_EQUALS",
+ "GREATER", "LOGICAL_AND", "LOGICAL_OR", "LBRACKET", "RPRACKET", "LBRACE",
+ "RBRACE", "LPAREN", "RPAREN", "DOT", "COMMA", "MINUS", "EXCLAM", "QUESTIONMARK",
+ "COLON", "PLUS", "STAR", "SLASH", "PERCENT", "TRUE", "FALSE", "NULL", "BACKSLASH",
+ "LETTER", "DIGIT", "EXPONENT", "HEXDIGIT", "RAW", "ESC_SEQ", "ESC_CHAR_SEQ",
+ "ESC_OCT_SEQ", "ESC_BYTE_SEQ", "ESC_UNI_SEQ", "WHITESPACE", "COMMENT",
+ "NUM_FLOAT", "NUM_INT", "NUM_UINT", "STRING", "BYTES", "IDENTIFIER",
+}
+
+type CELLexer struct {
+ *antlr.BaseLexer
+ channelNames []string
+ modeNames []string
+ // TODO: EOF string
+}
+
+func NewCELLexer(input antlr.CharStream) *CELLexer {
+
+ l := new(CELLexer)
+ lexerDeserializer := antlr.NewATNDeserializer(nil)
+ lexerAtn := lexerDeserializer.DeserializeFromUInt16(serializedLexerAtn)
+ lexerDecisionToDFA := make([]*antlr.DFA, len(lexerAtn.DecisionToState))
+ for index, ds := range lexerAtn.DecisionToState {
+ lexerDecisionToDFA[index] = antlr.NewDFA(ds, index)
+ }
+
+ l.BaseLexer = antlr.NewBaseLexer(input)
+ l.Interpreter = antlr.NewLexerATNSimulator(l, lexerAtn, lexerDecisionToDFA, antlr.NewPredictionContextCache())
+
+ l.channelNames = lexerChannelNames
+ l.modeNames = lexerModeNames
+ l.RuleNames = lexerRuleNames
+ l.LiteralNames = lexerLiteralNames
+ l.SymbolicNames = lexerSymbolicNames
+ l.GrammarFileName = "CEL.g4"
+ // TODO: l.EOF = antlr.TokenEOF
+
+ return l
+}
+
+// CELLexer tokens.
+const (
+ CELLexerEQUALS = 1
+ CELLexerNOT_EQUALS = 2
+ CELLexerIN = 3
+ CELLexerLESS = 4
+ CELLexerLESS_EQUALS = 5
+ CELLexerGREATER_EQUALS = 6
+ CELLexerGREATER = 7
+ CELLexerLOGICAL_AND = 8
+ CELLexerLOGICAL_OR = 9
+ CELLexerLBRACKET = 10
+ CELLexerRPRACKET = 11
+ CELLexerLBRACE = 12
+ CELLexerRBRACE = 13
+ CELLexerLPAREN = 14
+ CELLexerRPAREN = 15
+ CELLexerDOT = 16
+ CELLexerCOMMA = 17
+ CELLexerMINUS = 18
+ CELLexerEXCLAM = 19
+ CELLexerQUESTIONMARK = 20
+ CELLexerCOLON = 21
+ CELLexerPLUS = 22
+ CELLexerSTAR = 23
+ CELLexerSLASH = 24
+ CELLexerPERCENT = 25
+ CELLexerTRUE = 26
+ CELLexerFALSE = 27
+ CELLexerNULL = 28
+ CELLexerWHITESPACE = 29
+ CELLexerCOMMENT = 30
+ CELLexerNUM_FLOAT = 31
+ CELLexerNUM_INT = 32
+ CELLexerNUM_UINT = 33
+ CELLexerSTRING = 34
+ CELLexerBYTES = 35
+ CELLexerIDENTIFIER = 36
+)
diff --git a/vendor/github.com/google/cel-go/parser/gen/cel_listener.go b/vendor/github.com/google/cel-go/parser/gen/cel_listener.go
new file mode 100644
index 0000000000..9abfc11219
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/cel_listener.go
@@ -0,0 +1,183 @@
+// Generated from /Users/tswadell/go/src/github.com/google/cel-go/bin/../parser/gen/CEL.g4 by ANTLR 4.7.
+
+package gen // CEL
+import "github.com/antlr/antlr4/runtime/Go/antlr"
+
+// CELListener is a complete listener for a parse tree produced by CELParser.
+type CELListener interface {
+ antlr.ParseTreeListener
+
+ // EnterStart is called when entering the start production.
+ EnterStart(c *StartContext)
+
+ // EnterExpr is called when entering the expr production.
+ EnterExpr(c *ExprContext)
+
+ // EnterConditionalOr is called when entering the conditionalOr production.
+ EnterConditionalOr(c *ConditionalOrContext)
+
+ // EnterConditionalAnd is called when entering the conditionalAnd production.
+ EnterConditionalAnd(c *ConditionalAndContext)
+
+ // EnterRelation is called when entering the relation production.
+ EnterRelation(c *RelationContext)
+
+ // EnterCalc is called when entering the calc production.
+ EnterCalc(c *CalcContext)
+
+ // EnterMemberExpr is called when entering the MemberExpr production.
+ EnterMemberExpr(c *MemberExprContext)
+
+ // EnterLogicalNot is called when entering the LogicalNot production.
+ EnterLogicalNot(c *LogicalNotContext)
+
+ // EnterNegate is called when entering the Negate production.
+ EnterNegate(c *NegateContext)
+
+ // EnterSelectOrCall is called when entering the SelectOrCall production.
+ EnterSelectOrCall(c *SelectOrCallContext)
+
+ // EnterPrimaryExpr is called when entering the PrimaryExpr production.
+ EnterPrimaryExpr(c *PrimaryExprContext)
+
+ // EnterIndex is called when entering the Index production.
+ EnterIndex(c *IndexContext)
+
+ // EnterCreateMessage is called when entering the CreateMessage production.
+ EnterCreateMessage(c *CreateMessageContext)
+
+ // EnterIdentOrGlobalCall is called when entering the IdentOrGlobalCall production.
+ EnterIdentOrGlobalCall(c *IdentOrGlobalCallContext)
+
+ // EnterNested is called when entering the Nested production.
+ EnterNested(c *NestedContext)
+
+ // EnterCreateList is called when entering the CreateList production.
+ EnterCreateList(c *CreateListContext)
+
+ // EnterCreateStruct is called when entering the CreateStruct production.
+ EnterCreateStruct(c *CreateStructContext)
+
+ // EnterConstantLiteral is called when entering the ConstantLiteral production.
+ EnterConstantLiteral(c *ConstantLiteralContext)
+
+ // EnterExprList is called when entering the exprList production.
+ EnterExprList(c *ExprListContext)
+
+ // EnterFieldInitializerList is called when entering the fieldInitializerList production.
+ EnterFieldInitializerList(c *FieldInitializerListContext)
+
+ // EnterMapInitializerList is called when entering the mapInitializerList production.
+ EnterMapInitializerList(c *MapInitializerListContext)
+
+ // EnterInt is called when entering the Int production.
+ EnterInt(c *IntContext)
+
+ // EnterUint is called when entering the Uint production.
+ EnterUint(c *UintContext)
+
+ // EnterDouble is called when entering the Double production.
+ EnterDouble(c *DoubleContext)
+
+ // EnterString is called when entering the String production.
+ EnterString(c *StringContext)
+
+ // EnterBytes is called when entering the Bytes production.
+ EnterBytes(c *BytesContext)
+
+ // EnterBoolTrue is called when entering the BoolTrue production.
+ EnterBoolTrue(c *BoolTrueContext)
+
+ // EnterBoolFalse is called when entering the BoolFalse production.
+ EnterBoolFalse(c *BoolFalseContext)
+
+ // EnterNull is called when entering the Null production.
+ EnterNull(c *NullContext)
+
+ // ExitStart is called when exiting the start production.
+ ExitStart(c *StartContext)
+
+ // ExitExpr is called when exiting the expr production.
+ ExitExpr(c *ExprContext)
+
+ // ExitConditionalOr is called when exiting the conditionalOr production.
+ ExitConditionalOr(c *ConditionalOrContext)
+
+ // ExitConditionalAnd is called when exiting the conditionalAnd production.
+ ExitConditionalAnd(c *ConditionalAndContext)
+
+ // ExitRelation is called when exiting the relation production.
+ ExitRelation(c *RelationContext)
+
+ // ExitCalc is called when exiting the calc production.
+ ExitCalc(c *CalcContext)
+
+ // ExitMemberExpr is called when exiting the MemberExpr production.
+ ExitMemberExpr(c *MemberExprContext)
+
+ // ExitLogicalNot is called when exiting the LogicalNot production.
+ ExitLogicalNot(c *LogicalNotContext)
+
+ // ExitNegate is called when exiting the Negate production.
+ ExitNegate(c *NegateContext)
+
+ // ExitSelectOrCall is called when exiting the SelectOrCall production.
+ ExitSelectOrCall(c *SelectOrCallContext)
+
+ // ExitPrimaryExpr is called when exiting the PrimaryExpr production.
+ ExitPrimaryExpr(c *PrimaryExprContext)
+
+ // ExitIndex is called when exiting the Index production.
+ ExitIndex(c *IndexContext)
+
+ // ExitCreateMessage is called when exiting the CreateMessage production.
+ ExitCreateMessage(c *CreateMessageContext)
+
+ // ExitIdentOrGlobalCall is called when exiting the IdentOrGlobalCall production.
+ ExitIdentOrGlobalCall(c *IdentOrGlobalCallContext)
+
+ // ExitNested is called when exiting the Nested production.
+ ExitNested(c *NestedContext)
+
+ // ExitCreateList is called when exiting the CreateList production.
+ ExitCreateList(c *CreateListContext)
+
+ // ExitCreateStruct is called when exiting the CreateStruct production.
+ ExitCreateStruct(c *CreateStructContext)
+
+ // ExitConstantLiteral is called when exiting the ConstantLiteral production.
+ ExitConstantLiteral(c *ConstantLiteralContext)
+
+ // ExitExprList is called when exiting the exprList production.
+ ExitExprList(c *ExprListContext)
+
+ // ExitFieldInitializerList is called when exiting the fieldInitializerList production.
+ ExitFieldInitializerList(c *FieldInitializerListContext)
+
+ // ExitMapInitializerList is called when exiting the mapInitializerList production.
+ ExitMapInitializerList(c *MapInitializerListContext)
+
+ // ExitInt is called when exiting the Int production.
+ ExitInt(c *IntContext)
+
+ // ExitUint is called when exiting the Uint production.
+ ExitUint(c *UintContext)
+
+ // ExitDouble is called when exiting the Double production.
+ ExitDouble(c *DoubleContext)
+
+ // ExitString is called when exiting the String production.
+ ExitString(c *StringContext)
+
+ // ExitBytes is called when exiting the Bytes production.
+ ExitBytes(c *BytesContext)
+
+ // ExitBoolTrue is called when exiting the BoolTrue production.
+ ExitBoolTrue(c *BoolTrueContext)
+
+ // ExitBoolFalse is called when exiting the BoolFalse production.
+ ExitBoolFalse(c *BoolFalseContext)
+
+ // ExitNull is called when exiting the Null production.
+ ExitNull(c *NullContext)
+}
diff --git a/vendor/github.com/google/cel-go/parser/gen/cel_parser.go b/vendor/github.com/google/cel-go/parser/gen/cel_parser.go
new file mode 100644
index 0000000000..d99ed1c6a9
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/gen/cel_parser.go
@@ -0,0 +1,4097 @@
+// Generated from /Users/tswadell/go/src/github.com/google/cel-go/bin/../parser/gen/CEL.g4 by ANTLR 4.7.
+
+package gen // CEL
+import (
+ "fmt"
+ "reflect"
+ "strconv"
+
+ "github.com/antlr/antlr4/runtime/Go/antlr"
+)
+
+// Suppress unused import errors
+var _ = fmt.Printf
+var _ = reflect.Copy
+var _ = strconv.Itoa
+
+var parserATN = []uint16{
+ 3, 24715, 42794, 33075, 47597, 16764, 15335, 30598, 22884, 3, 38, 211,
+ 4, 2, 9, 2, 4, 3, 9, 3, 4, 4, 9, 4, 4, 5, 9, 5, 4, 6, 9, 6, 4, 7, 9, 7,
+ 4, 8, 9, 8, 4, 9, 9, 9, 4, 10, 9, 10, 4, 11, 9, 11, 4, 12, 9, 12, 4, 13,
+ 9, 13, 4, 14, 9, 14, 3, 2, 3, 2, 3, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+ 3, 5, 3, 38, 10, 3, 3, 4, 3, 4, 3, 4, 7, 4, 43, 10, 4, 12, 4, 14, 4, 46,
+ 11, 4, 3, 5, 3, 5, 3, 5, 7, 5, 51, 10, 5, 12, 5, 14, 5, 54, 11, 5, 3, 6,
+ 3, 6, 3, 6, 3, 6, 3, 6, 3, 6, 7, 6, 62, 10, 6, 12, 6, 14, 6, 65, 11, 6,
+ 3, 7, 3, 7, 3, 7, 3, 7, 3, 7, 3, 7, 3, 7, 3, 7, 3, 7, 7, 7, 76, 10, 7,
+ 12, 7, 14, 7, 79, 11, 7, 3, 8, 3, 8, 6, 8, 83, 10, 8, 13, 8, 14, 8, 84,
+ 3, 8, 3, 8, 6, 8, 89, 10, 8, 13, 8, 14, 8, 90, 3, 8, 5, 8, 94, 10, 8, 3,
+ 9, 3, 9, 3, 9, 3, 9, 3, 9, 3, 9, 3, 9, 3, 9, 5, 9, 104, 10, 9, 3, 9, 5,
+ 9, 107, 10, 9, 3, 9, 3, 9, 3, 9, 3, 9, 3, 9, 3, 9, 3, 9, 3, 9, 5, 9, 117,
+ 10, 9, 3, 9, 5, 9, 120, 10, 9, 3, 9, 7, 9, 123, 10, 9, 12, 9, 14, 9, 126,
+ 11, 9, 3, 10, 5, 10, 129, 10, 10, 3, 10, 3, 10, 3, 10, 5, 10, 134, 10,
+ 10, 3, 10, 5, 10, 137, 10, 10, 3, 10, 3, 10, 3, 10, 3, 10, 3, 10, 3, 10,
+ 5, 10, 145, 10, 10, 3, 10, 5, 10, 148, 10, 10, 3, 10, 3, 10, 3, 10, 5,
+ 10, 153, 10, 10, 3, 10, 5, 10, 156, 10, 10, 3, 10, 3, 10, 5, 10, 160, 10,
+ 10, 3, 11, 3, 11, 3, 11, 7, 11, 165, 10, 11, 12, 11, 14, 11, 168, 11, 11,
+ 3, 12, 3, 12, 3, 12, 3, 12, 3, 12, 3, 12, 3, 12, 7, 12, 177, 10, 12, 12,
+ 12, 14, 12, 180, 11, 12, 3, 13, 3, 13, 3, 13, 3, 13, 3, 13, 3, 13, 3, 13,
+ 3, 13, 7, 13, 190, 10, 13, 12, 13, 14, 13, 193, 11, 13, 3, 14, 5, 14, 196,
+ 10, 14, 3, 14, 3, 14, 3, 14, 5, 14, 201, 10, 14, 3, 14, 3, 14, 3, 14, 3,
+ 14, 3, 14, 3, 14, 5, 14, 209, 10, 14, 3, 14, 2, 5, 10, 12, 16, 15, 2, 4,
+ 6, 8, 10, 12, 14, 16, 18, 20, 22, 24, 26, 2, 5, 3, 2, 3, 9, 3, 2, 25, 27,
+ 4, 2, 20, 20, 24, 24, 2, 237, 2, 28, 3, 2, 2, 2, 4, 31, 3, 2, 2, 2, 6,
+ 39, 3, 2, 2, 2, 8, 47, 3, 2, 2, 2, 10, 55, 3, 2, 2, 2, 12, 66, 3, 2, 2,
+ 2, 14, 93, 3, 2, 2, 2, 16, 95, 3, 2, 2, 2, 18, 159, 3, 2, 2, 2, 20, 161,
+ 3, 2, 2, 2, 22, 169, 3, 2, 2, 2, 24, 181, 3, 2, 2, 2, 26, 208, 3, 2, 2,
+ 2, 28, 29, 5, 4, 3, 2, 29, 30, 7, 2, 2, 3, 30, 3, 3, 2, 2, 2, 31, 37, 5,
+ 6, 4, 2, 32, 33, 7, 22, 2, 2, 33, 34, 5, 6, 4, 2, 34, 35, 7, 23, 2, 2,
+ 35, 36, 5, 4, 3, 2, 36, 38, 3, 2, 2, 2, 37, 32, 3, 2, 2, 2, 37, 38, 3,
+ 2, 2, 2, 38, 5, 3, 2, 2, 2, 39, 44, 5, 8, 5, 2, 40, 41, 7, 11, 2, 2, 41,
+ 43, 5, 8, 5, 2, 42, 40, 3, 2, 2, 2, 43, 46, 3, 2, 2, 2, 44, 42, 3, 2, 2,
+ 2, 44, 45, 3, 2, 2, 2, 45, 7, 3, 2, 2, 2, 46, 44, 3, 2, 2, 2, 47, 52, 5,
+ 10, 6, 2, 48, 49, 7, 10, 2, 2, 49, 51, 5, 10, 6, 2, 50, 48, 3, 2, 2, 2,
+ 51, 54, 3, 2, 2, 2, 52, 50, 3, 2, 2, 2, 52, 53, 3, 2, 2, 2, 53, 9, 3, 2,
+ 2, 2, 54, 52, 3, 2, 2, 2, 55, 56, 8, 6, 1, 2, 56, 57, 5, 12, 7, 2, 57,
+ 63, 3, 2, 2, 2, 58, 59, 12, 3, 2, 2, 59, 60, 9, 2, 2, 2, 60, 62, 5, 10,
+ 6, 4, 61, 58, 3, 2, 2, 2, 62, 65, 3, 2, 2, 2, 63, 61, 3, 2, 2, 2, 63, 64,
+ 3, 2, 2, 2, 64, 11, 3, 2, 2, 2, 65, 63, 3, 2, 2, 2, 66, 67, 8, 7, 1, 2,
+ 67, 68, 5, 14, 8, 2, 68, 77, 3, 2, 2, 2, 69, 70, 12, 4, 2, 2, 70, 71, 9,
+ 3, 2, 2, 71, 76, 5, 12, 7, 5, 72, 73, 12, 3, 2, 2, 73, 74, 9, 4, 2, 2,
+ 74, 76, 5, 12, 7, 4, 75, 69, 3, 2, 2, 2, 75, 72, 3, 2, 2, 2, 76, 79, 3,
+ 2, 2, 2, 77, 75, 3, 2, 2, 2, 77, 78, 3, 2, 2, 2, 78, 13, 3, 2, 2, 2, 79,
+ 77, 3, 2, 2, 2, 80, 94, 5, 16, 9, 2, 81, 83, 7, 21, 2, 2, 82, 81, 3, 2,
+ 2, 2, 83, 84, 3, 2, 2, 2, 84, 82, 3, 2, 2, 2, 84, 85, 3, 2, 2, 2, 85, 86,
+ 3, 2, 2, 2, 86, 94, 5, 16, 9, 2, 87, 89, 7, 20, 2, 2, 88, 87, 3, 2, 2,
+ 2, 89, 90, 3, 2, 2, 2, 90, 88, 3, 2, 2, 2, 90, 91, 3, 2, 2, 2, 91, 92,
+ 3, 2, 2, 2, 92, 94, 5, 16, 9, 2, 93, 80, 3, 2, 2, 2, 93, 82, 3, 2, 2, 2,
+ 93, 88, 3, 2, 2, 2, 94, 15, 3, 2, 2, 2, 95, 96, 8, 9, 1, 2, 96, 97, 5,
+ 18, 10, 2, 97, 124, 3, 2, 2, 2, 98, 99, 12, 5, 2, 2, 99, 100, 7, 18, 2,
+ 2, 100, 106, 7, 38, 2, 2, 101, 103, 7, 16, 2, 2, 102, 104, 5, 20, 11, 2,
+ 103, 102, 3, 2, 2, 2, 103, 104, 3, 2, 2, 2, 104, 105, 3, 2, 2, 2, 105,
+ 107, 7, 17, 2, 2, 106, 101, 3, 2, 2, 2, 106, 107, 3, 2, 2, 2, 107, 123,
+ 3, 2, 2, 2, 108, 109, 12, 4, 2, 2, 109, 110, 7, 12, 2, 2, 110, 111, 5,
+ 4, 3, 2, 111, 112, 7, 13, 2, 2, 112, 123, 3, 2, 2, 2, 113, 114, 12, 3,
+ 2, 2, 114, 116, 7, 14, 2, 2, 115, 117, 5, 22, 12, 2, 116, 115, 3, 2, 2,
+ 2, 116, 117, 3, 2, 2, 2, 117, 119, 3, 2, 2, 2, 118, 120, 7, 19, 2, 2, 119,
+ 118, 3, 2, 2, 2, 119, 120, 3, 2, 2, 2, 120, 121, 3, 2, 2, 2, 121, 123,
+ 7, 15, 2, 2, 122, 98, 3, 2, 2, 2, 122, 108, 3, 2, 2, 2, 122, 113, 3, 2,
+ 2, 2, 123, 126, 3, 2, 2, 2, 124, 122, 3, 2, 2, 2, 124, 125, 3, 2, 2, 2,
+ 125, 17, 3, 2, 2, 2, 126, 124, 3, 2, 2, 2, 127, 129, 7, 18, 2, 2, 128,
+ 127, 3, 2, 2, 2, 128, 129, 3, 2, 2, 2, 129, 130, 3, 2, 2, 2, 130, 136,
+ 7, 38, 2, 2, 131, 133, 7, 16, 2, 2, 132, 134, 5, 20, 11, 2, 133, 132, 3,
+ 2, 2, 2, 133, 134, 3, 2, 2, 2, 134, 135, 3, 2, 2, 2, 135, 137, 7, 17, 2,
+ 2, 136, 131, 3, 2, 2, 2, 136, 137, 3, 2, 2, 2, 137, 160, 3, 2, 2, 2, 138,
+ 139, 7, 16, 2, 2, 139, 140, 5, 4, 3, 2, 140, 141, 7, 17, 2, 2, 141, 160,
+ 3, 2, 2, 2, 142, 144, 7, 12, 2, 2, 143, 145, 5, 20, 11, 2, 144, 143, 3,
+ 2, 2, 2, 144, 145, 3, 2, 2, 2, 145, 147, 3, 2, 2, 2, 146, 148, 7, 19, 2,
+ 2, 147, 146, 3, 2, 2, 2, 147, 148, 3, 2, 2, 2, 148, 149, 3, 2, 2, 2, 149,
+ 160, 7, 13, 2, 2, 150, 152, 7, 14, 2, 2, 151, 153, 5, 24, 13, 2, 152, 151,
+ 3, 2, 2, 2, 152, 153, 3, 2, 2, 2, 153, 155, 3, 2, 2, 2, 154, 156, 7, 19,
+ 2, 2, 155, 154, 3, 2, 2, 2, 155, 156, 3, 2, 2, 2, 156, 157, 3, 2, 2, 2,
+ 157, 160, 7, 15, 2, 2, 158, 160, 5, 26, 14, 2, 159, 128, 3, 2, 2, 2, 159,
+ 138, 3, 2, 2, 2, 159, 142, 3, 2, 2, 2, 159, 150, 3, 2, 2, 2, 159, 158,
+ 3, 2, 2, 2, 160, 19, 3, 2, 2, 2, 161, 166, 5, 4, 3, 2, 162, 163, 7, 19,
+ 2, 2, 163, 165, 5, 4, 3, 2, 164, 162, 3, 2, 2, 2, 165, 168, 3, 2, 2, 2,
+ 166, 164, 3, 2, 2, 2, 166, 167, 3, 2, 2, 2, 167, 21, 3, 2, 2, 2, 168, 166,
+ 3, 2, 2, 2, 169, 170, 7, 38, 2, 2, 170, 171, 7, 23, 2, 2, 171, 178, 5,
+ 4, 3, 2, 172, 173, 7, 19, 2, 2, 173, 174, 7, 38, 2, 2, 174, 175, 7, 23,
+ 2, 2, 175, 177, 5, 4, 3, 2, 176, 172, 3, 2, 2, 2, 177, 180, 3, 2, 2, 2,
+ 178, 176, 3, 2, 2, 2, 178, 179, 3, 2, 2, 2, 179, 23, 3, 2, 2, 2, 180, 178,
+ 3, 2, 2, 2, 181, 182, 5, 4, 3, 2, 182, 183, 7, 23, 2, 2, 183, 191, 5, 4,
+ 3, 2, 184, 185, 7, 19, 2, 2, 185, 186, 5, 4, 3, 2, 186, 187, 7, 23, 2,
+ 2, 187, 188, 5, 4, 3, 2, 188, 190, 3, 2, 2, 2, 189, 184, 3, 2, 2, 2, 190,
+ 193, 3, 2, 2, 2, 191, 189, 3, 2, 2, 2, 191, 192, 3, 2, 2, 2, 192, 25, 3,
+ 2, 2, 2, 193, 191, 3, 2, 2, 2, 194, 196, 7, 20, 2, 2, 195, 194, 3, 2, 2,
+ 2, 195, 196, 3, 2, 2, 2, 196, 197, 3, 2, 2, 2, 197, 209, 7, 34, 2, 2, 198,
+ 209, 7, 35, 2, 2, 199, 201, 7, 20, 2, 2, 200, 199, 3, 2, 2, 2, 200, 201,
+ 3, 2, 2, 2, 201, 202, 3, 2, 2, 2, 202, 209, 7, 33, 2, 2, 203, 209, 7, 36,
+ 2, 2, 204, 209, 7, 37, 2, 2, 205, 209, 7, 28, 2, 2, 206, 209, 7, 29, 2,
+ 2, 207, 209, 7, 30, 2, 2, 208, 195, 3, 2, 2, 2, 208, 198, 3, 2, 2, 2, 208,
+ 200, 3, 2, 2, 2, 208, 203, 3, 2, 2, 2, 208, 204, 3, 2, 2, 2, 208, 205,
+ 3, 2, 2, 2, 208, 206, 3, 2, 2, 2, 208, 207, 3, 2, 2, 2, 209, 27, 3, 2,
+ 2, 2, 31, 37, 44, 52, 63, 75, 77, 84, 90, 93, 103, 106, 116, 119, 122,
+ 124, 128, 133, 136, 144, 147, 152, 155, 159, 166, 178, 191, 195, 200, 208,
+}
+
+var literalNames = []string{
+ "", "'=='", "'!='", "'in'", "'<'", "'<='", "'>='", "'>'", "'&&'", "'||'",
+ "'['", "']'", "'{'", "'}'", "'('", "')'", "'.'", "','", "'-'", "'!'", "'?'",
+ "':'", "'+'", "'*'", "'/'", "'%'", "'true'", "'false'", "'null'",
+}
+var symbolicNames = []string{
+ "", "EQUALS", "NOT_EQUALS", "IN", "LESS", "LESS_EQUALS", "GREATER_EQUALS",
+ "GREATER", "LOGICAL_AND", "LOGICAL_OR", "LBRACKET", "RPRACKET", "LBRACE",
+ "RBRACE", "LPAREN", "RPAREN", "DOT", "COMMA", "MINUS", "EXCLAM", "QUESTIONMARK",
+ "COLON", "PLUS", "STAR", "SLASH", "PERCENT", "TRUE", "FALSE", "NULL", "WHITESPACE",
+ "COMMENT", "NUM_FLOAT", "NUM_INT", "NUM_UINT", "STRING", "BYTES", "IDENTIFIER",
+}
+
+var ruleNames = []string{
+ "start", "expr", "conditionalOr", "conditionalAnd", "relation", "calc",
+ "unary", "member", "primary", "exprList", "fieldInitializerList", "mapInitializerList",
+ "literal",
+}
+
+type CELParser struct {
+ *antlr.BaseParser
+}
+
+func NewCELParser(input antlr.TokenStream) *CELParser {
+ this := new(CELParser)
+ deserializer := antlr.NewATNDeserializer(nil)
+ deserializedATN := deserializer.DeserializeFromUInt16(parserATN)
+ decisionToDFA := make([]*antlr.DFA, len(deserializedATN.DecisionToState))
+ for index, ds := range deserializedATN.DecisionToState {
+ decisionToDFA[index] = antlr.NewDFA(ds, index)
+ }
+
+ this.BaseParser = antlr.NewBaseParser(input)
+
+ this.Interpreter = antlr.NewParserATNSimulator(this, deserializedATN, decisionToDFA, antlr.NewPredictionContextCache())
+ this.RuleNames = ruleNames
+ this.LiteralNames = literalNames
+ this.SymbolicNames = symbolicNames
+ this.GrammarFileName = "CEL.g4"
+
+ return this
+}
+
+// CELParser tokens.
+const (
+ CELParserEOF = antlr.TokenEOF
+ CELParserEQUALS = 1
+ CELParserNOT_EQUALS = 2
+ CELParserIN = 3
+ CELParserLESS = 4
+ CELParserLESS_EQUALS = 5
+ CELParserGREATER_EQUALS = 6
+ CELParserGREATER = 7
+ CELParserLOGICAL_AND = 8
+ CELParserLOGICAL_OR = 9
+ CELParserLBRACKET = 10
+ CELParserRPRACKET = 11
+ CELParserLBRACE = 12
+ CELParserRBRACE = 13
+ CELParserLPAREN = 14
+ CELParserRPAREN = 15
+ CELParserDOT = 16
+ CELParserCOMMA = 17
+ CELParserMINUS = 18
+ CELParserEXCLAM = 19
+ CELParserQUESTIONMARK = 20
+ CELParserCOLON = 21
+ CELParserPLUS = 22
+ CELParserSTAR = 23
+ CELParserSLASH = 24
+ CELParserPERCENT = 25
+ CELParserTRUE = 26
+ CELParserFALSE = 27
+ CELParserNULL = 28
+ CELParserWHITESPACE = 29
+ CELParserCOMMENT = 30
+ CELParserNUM_FLOAT = 31
+ CELParserNUM_INT = 32
+ CELParserNUM_UINT = 33
+ CELParserSTRING = 34
+ CELParserBYTES = 35
+ CELParserIDENTIFIER = 36
+)
+
+// CELParser rules.
+const (
+ CELParserRULE_start = 0
+ CELParserRULE_expr = 1
+ CELParserRULE_conditionalOr = 2
+ CELParserRULE_conditionalAnd = 3
+ CELParserRULE_relation = 4
+ CELParserRULE_calc = 5
+ CELParserRULE_unary = 6
+ CELParserRULE_member = 7
+ CELParserRULE_primary = 8
+ CELParserRULE_exprList = 9
+ CELParserRULE_fieldInitializerList = 10
+ CELParserRULE_mapInitializerList = 11
+ CELParserRULE_literal = 12
+)
+
+// IStartContext is an interface to support dynamic dispatch.
+type IStartContext interface {
+ antlr.ParserRuleContext
+
+ // GetParser returns the parser.
+ GetParser() antlr.Parser
+
+ // GetE returns the e rule contexts.
+ GetE() IExprContext
+
+ // SetE sets the e rule contexts.
+ SetE(IExprContext)
+
+ // IsStartContext differentiates from other interfaces.
+ IsStartContext()
+}
+
+type StartContext struct {
+ *antlr.BaseParserRuleContext
+ parser antlr.Parser
+ e IExprContext
+}
+
+func NewEmptyStartContext() *StartContext {
+ var p = new(StartContext)
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(nil, -1)
+ p.RuleIndex = CELParserRULE_start
+ return p
+}
+
+func (*StartContext) IsStartContext() {}
+
+func NewStartContext(parser antlr.Parser, parent antlr.ParserRuleContext, invokingState int) *StartContext {
+ var p = new(StartContext)
+
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(parent, invokingState)
+
+ p.parser = parser
+ p.RuleIndex = CELParserRULE_start
+
+ return p
+}
+
+func (s *StartContext) GetParser() antlr.Parser { return s.parser }
+
+func (s *StartContext) GetE() IExprContext { return s.e }
+
+func (s *StartContext) SetE(v IExprContext) { s.e = v }
+
+func (s *StartContext) EOF() antlr.TerminalNode {
+ return s.GetToken(CELParserEOF, 0)
+}
+
+func (s *StartContext) Expr() IExprContext {
+ var t = s.GetTypedRuleContext(reflect.TypeOf((*IExprContext)(nil)).Elem(), 0)
+
+ if t == nil {
+ return nil
+ }
+
+ return t.(IExprContext)
+}
+
+func (s *StartContext) GetRuleContext() antlr.RuleContext {
+ return s
+}
+
+func (s *StartContext) ToStringTree(ruleNames []string, recog antlr.Recognizer) string {
+ return antlr.TreesStringTree(s, ruleNames, recog)
+}
+
+func (s *StartContext) EnterRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.EnterStart(s)
+ }
+}
+
+func (s *StartContext) ExitRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.ExitStart(s)
+ }
+}
+
+func (s *StartContext) Accept(visitor antlr.ParseTreeVisitor) interface{} {
+ switch t := visitor.(type) {
+ case CELVisitor:
+ return t.VisitStart(s)
+
+ default:
+ return t.VisitChildren(s)
+ }
+}
+
+func (p *CELParser) Start() (localctx IStartContext) {
+ localctx = NewStartContext(p, p.GetParserRuleContext(), p.GetState())
+ p.EnterRule(localctx, 0, CELParserRULE_start)
+
+ defer func() {
+ p.ExitRule()
+ }()
+
+ defer func() {
+ if err := recover(); err != nil {
+ if v, ok := err.(antlr.RecognitionException); ok {
+ localctx.SetException(v)
+ p.GetErrorHandler().ReportError(p, v)
+ p.GetErrorHandler().Recover(p, v)
+ } else {
+ panic(err)
+ }
+ }
+ }()
+
+ p.EnterOuterAlt(localctx, 1)
+ {
+ p.SetState(26)
+
+ var _x = p.Expr()
+
+ localctx.(*StartContext).e = _x
+ }
+ {
+ p.SetState(27)
+ p.Match(CELParserEOF)
+ }
+
+ return localctx
+}
+
+// IExprContext is an interface to support dynamic dispatch.
+type IExprContext interface {
+ antlr.ParserRuleContext
+
+ // GetParser returns the parser.
+ GetParser() antlr.Parser
+
+ // GetOp returns the op token.
+ GetOp() antlr.Token
+
+ // SetOp sets the op token.
+ SetOp(antlr.Token)
+
+ // GetE returns the e rule contexts.
+ GetE() IConditionalOrContext
+
+ // GetE1 returns the e1 rule contexts.
+ GetE1() IConditionalOrContext
+
+ // GetE2 returns the e2 rule contexts.
+ GetE2() IExprContext
+
+ // SetE sets the e rule contexts.
+ SetE(IConditionalOrContext)
+
+ // SetE1 sets the e1 rule contexts.
+ SetE1(IConditionalOrContext)
+
+ // SetE2 sets the e2 rule contexts.
+ SetE2(IExprContext)
+
+ // IsExprContext differentiates from other interfaces.
+ IsExprContext()
+}
+
+type ExprContext struct {
+ *antlr.BaseParserRuleContext
+ parser antlr.Parser
+ e IConditionalOrContext
+ op antlr.Token
+ e1 IConditionalOrContext
+ e2 IExprContext
+}
+
+func NewEmptyExprContext() *ExprContext {
+ var p = new(ExprContext)
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(nil, -1)
+ p.RuleIndex = CELParserRULE_expr
+ return p
+}
+
+func (*ExprContext) IsExprContext() {}
+
+func NewExprContext(parser antlr.Parser, parent antlr.ParserRuleContext, invokingState int) *ExprContext {
+ var p = new(ExprContext)
+
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(parent, invokingState)
+
+ p.parser = parser
+ p.RuleIndex = CELParserRULE_expr
+
+ return p
+}
+
+func (s *ExprContext) GetParser() antlr.Parser { return s.parser }
+
+func (s *ExprContext) GetOp() antlr.Token { return s.op }
+
+func (s *ExprContext) SetOp(v antlr.Token) { s.op = v }
+
+func (s *ExprContext) GetE() IConditionalOrContext { return s.e }
+
+func (s *ExprContext) GetE1() IConditionalOrContext { return s.e1 }
+
+func (s *ExprContext) GetE2() IExprContext { return s.e2 }
+
+func (s *ExprContext) SetE(v IConditionalOrContext) { s.e = v }
+
+func (s *ExprContext) SetE1(v IConditionalOrContext) { s.e1 = v }
+
+func (s *ExprContext) SetE2(v IExprContext) { s.e2 = v }
+
+func (s *ExprContext) AllConditionalOr() []IConditionalOrContext {
+ var ts = s.GetTypedRuleContexts(reflect.TypeOf((*IConditionalOrContext)(nil)).Elem())
+ var tst = make([]IConditionalOrContext, len(ts))
+
+ for i, t := range ts {
+ if t != nil {
+ tst[i] = t.(IConditionalOrContext)
+ }
+ }
+
+ return tst
+}
+
+func (s *ExprContext) ConditionalOr(i int) IConditionalOrContext {
+ var t = s.GetTypedRuleContext(reflect.TypeOf((*IConditionalOrContext)(nil)).Elem(), i)
+
+ if t == nil {
+ return nil
+ }
+
+ return t.(IConditionalOrContext)
+}
+
+func (s *ExprContext) Expr() IExprContext {
+ var t = s.GetTypedRuleContext(reflect.TypeOf((*IExprContext)(nil)).Elem(), 0)
+
+ if t == nil {
+ return nil
+ }
+
+ return t.(IExprContext)
+}
+
+func (s *ExprContext) GetRuleContext() antlr.RuleContext {
+ return s
+}
+
+func (s *ExprContext) ToStringTree(ruleNames []string, recog antlr.Recognizer) string {
+ return antlr.TreesStringTree(s, ruleNames, recog)
+}
+
+func (s *ExprContext) EnterRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.EnterExpr(s)
+ }
+}
+
+func (s *ExprContext) ExitRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.ExitExpr(s)
+ }
+}
+
+func (s *ExprContext) Accept(visitor antlr.ParseTreeVisitor) interface{} {
+ switch t := visitor.(type) {
+ case CELVisitor:
+ return t.VisitExpr(s)
+
+ default:
+ return t.VisitChildren(s)
+ }
+}
+
+func (p *CELParser) Expr() (localctx IExprContext) {
+ localctx = NewExprContext(p, p.GetParserRuleContext(), p.GetState())
+ p.EnterRule(localctx, 2, CELParserRULE_expr)
+ var _la int
+
+ defer func() {
+ p.ExitRule()
+ }()
+
+ defer func() {
+ if err := recover(); err != nil {
+ if v, ok := err.(antlr.RecognitionException); ok {
+ localctx.SetException(v)
+ p.GetErrorHandler().ReportError(p, v)
+ p.GetErrorHandler().Recover(p, v)
+ } else {
+ panic(err)
+ }
+ }
+ }()
+
+ p.EnterOuterAlt(localctx, 1)
+ {
+ p.SetState(29)
+
+ var _x = p.ConditionalOr()
+
+ localctx.(*ExprContext).e = _x
+ }
+ p.SetState(35)
+ p.GetErrorHandler().Sync(p)
+ _la = p.GetTokenStream().LA(1)
+
+ if _la == CELParserQUESTIONMARK {
+ {
+ p.SetState(30)
+
+ var _m = p.Match(CELParserQUESTIONMARK)
+
+ localctx.(*ExprContext).op = _m
+ }
+ {
+ p.SetState(31)
+
+ var _x = p.ConditionalOr()
+
+ localctx.(*ExprContext).e1 = _x
+ }
+ {
+ p.SetState(32)
+ p.Match(CELParserCOLON)
+ }
+ {
+ p.SetState(33)
+
+ var _x = p.Expr()
+
+ localctx.(*ExprContext).e2 = _x
+ }
+
+ }
+
+ return localctx
+}
+
+// IConditionalOrContext is an interface to support dynamic dispatch.
+type IConditionalOrContext interface {
+ antlr.ParserRuleContext
+
+ // GetParser returns the parser.
+ GetParser() antlr.Parser
+
+ // GetS9 returns the s9 token.
+ GetS9() antlr.Token
+
+ // SetS9 sets the s9 token.
+ SetS9(antlr.Token)
+
+ // GetOps returns the ops token list.
+ GetOps() []antlr.Token
+
+ // SetOps sets the ops token list.
+ SetOps([]antlr.Token)
+
+ // GetE returns the e rule contexts.
+ GetE() IConditionalAndContext
+
+ // Get_conditionalAnd returns the _conditionalAnd rule contexts.
+ Get_conditionalAnd() IConditionalAndContext
+
+ // SetE sets the e rule contexts.
+ SetE(IConditionalAndContext)
+
+ // Set_conditionalAnd sets the _conditionalAnd rule contexts.
+ Set_conditionalAnd(IConditionalAndContext)
+
+ // GetE1 returns the e1 rule context list.
+ GetE1() []IConditionalAndContext
+
+ // SetE1 sets the e1 rule context list.
+ SetE1([]IConditionalAndContext)
+
+ // IsConditionalOrContext differentiates from other interfaces.
+ IsConditionalOrContext()
+}
+
+type ConditionalOrContext struct {
+ *antlr.BaseParserRuleContext
+ parser antlr.Parser
+ e IConditionalAndContext
+ s9 antlr.Token
+ ops []antlr.Token
+ _conditionalAnd IConditionalAndContext
+ e1 []IConditionalAndContext
+}
+
+func NewEmptyConditionalOrContext() *ConditionalOrContext {
+ var p = new(ConditionalOrContext)
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(nil, -1)
+ p.RuleIndex = CELParserRULE_conditionalOr
+ return p
+}
+
+func (*ConditionalOrContext) IsConditionalOrContext() {}
+
+func NewConditionalOrContext(parser antlr.Parser, parent antlr.ParserRuleContext, invokingState int) *ConditionalOrContext {
+ var p = new(ConditionalOrContext)
+
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(parent, invokingState)
+
+ p.parser = parser
+ p.RuleIndex = CELParserRULE_conditionalOr
+
+ return p
+}
+
+func (s *ConditionalOrContext) GetParser() antlr.Parser { return s.parser }
+
+func (s *ConditionalOrContext) GetS9() antlr.Token { return s.s9 }
+
+func (s *ConditionalOrContext) SetS9(v antlr.Token) { s.s9 = v }
+
+func (s *ConditionalOrContext) GetOps() []antlr.Token { return s.ops }
+
+func (s *ConditionalOrContext) SetOps(v []antlr.Token) { s.ops = v }
+
+func (s *ConditionalOrContext) GetE() IConditionalAndContext { return s.e }
+
+func (s *ConditionalOrContext) Get_conditionalAnd() IConditionalAndContext { return s._conditionalAnd }
+
+func (s *ConditionalOrContext) SetE(v IConditionalAndContext) { s.e = v }
+
+func (s *ConditionalOrContext) Set_conditionalAnd(v IConditionalAndContext) { s._conditionalAnd = v }
+
+func (s *ConditionalOrContext) GetE1() []IConditionalAndContext { return s.e1 }
+
+func (s *ConditionalOrContext) SetE1(v []IConditionalAndContext) { s.e1 = v }
+
+func (s *ConditionalOrContext) AllConditionalAnd() []IConditionalAndContext {
+ var ts = s.GetTypedRuleContexts(reflect.TypeOf((*IConditionalAndContext)(nil)).Elem())
+ var tst = make([]IConditionalAndContext, len(ts))
+
+ for i, t := range ts {
+ if t != nil {
+ tst[i] = t.(IConditionalAndContext)
+ }
+ }
+
+ return tst
+}
+
+func (s *ConditionalOrContext) ConditionalAnd(i int) IConditionalAndContext {
+ var t = s.GetTypedRuleContext(reflect.TypeOf((*IConditionalAndContext)(nil)).Elem(), i)
+
+ if t == nil {
+ return nil
+ }
+
+ return t.(IConditionalAndContext)
+}
+
+func (s *ConditionalOrContext) GetRuleContext() antlr.RuleContext {
+ return s
+}
+
+func (s *ConditionalOrContext) ToStringTree(ruleNames []string, recog antlr.Recognizer) string {
+ return antlr.TreesStringTree(s, ruleNames, recog)
+}
+
+func (s *ConditionalOrContext) EnterRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.EnterConditionalOr(s)
+ }
+}
+
+func (s *ConditionalOrContext) ExitRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.ExitConditionalOr(s)
+ }
+}
+
+func (s *ConditionalOrContext) Accept(visitor antlr.ParseTreeVisitor) interface{} {
+ switch t := visitor.(type) {
+ case CELVisitor:
+ return t.VisitConditionalOr(s)
+
+ default:
+ return t.VisitChildren(s)
+ }
+}
+
+func (p *CELParser) ConditionalOr() (localctx IConditionalOrContext) {
+ localctx = NewConditionalOrContext(p, p.GetParserRuleContext(), p.GetState())
+ p.EnterRule(localctx, 4, CELParserRULE_conditionalOr)
+ var _la int
+
+ defer func() {
+ p.ExitRule()
+ }()
+
+ defer func() {
+ if err := recover(); err != nil {
+ if v, ok := err.(antlr.RecognitionException); ok {
+ localctx.SetException(v)
+ p.GetErrorHandler().ReportError(p, v)
+ p.GetErrorHandler().Recover(p, v)
+ } else {
+ panic(err)
+ }
+ }
+ }()
+
+ p.EnterOuterAlt(localctx, 1)
+ {
+ p.SetState(37)
+
+ var _x = p.ConditionalAnd()
+
+ localctx.(*ConditionalOrContext).e = _x
+ }
+ p.SetState(42)
+ p.GetErrorHandler().Sync(p)
+ _la = p.GetTokenStream().LA(1)
+
+ for _la == CELParserLOGICAL_OR {
+ {
+ p.SetState(38)
+
+ var _m = p.Match(CELParserLOGICAL_OR)
+
+ localctx.(*ConditionalOrContext).s9 = _m
+ }
+ localctx.(*ConditionalOrContext).ops = append(localctx.(*ConditionalOrContext).ops, localctx.(*ConditionalOrContext).s9)
+ {
+ p.SetState(39)
+
+ var _x = p.ConditionalAnd()
+
+ localctx.(*ConditionalOrContext)._conditionalAnd = _x
+ }
+ localctx.(*ConditionalOrContext).e1 = append(localctx.(*ConditionalOrContext).e1, localctx.(*ConditionalOrContext)._conditionalAnd)
+
+ p.SetState(44)
+ p.GetErrorHandler().Sync(p)
+ _la = p.GetTokenStream().LA(1)
+ }
+
+ return localctx
+}
+
+// IConditionalAndContext is an interface to support dynamic dispatch.
+type IConditionalAndContext interface {
+ antlr.ParserRuleContext
+
+ // GetParser returns the parser.
+ GetParser() antlr.Parser
+
+ // GetS8 returns the s8 token.
+ GetS8() antlr.Token
+
+ // SetS8 sets the s8 token.
+ SetS8(antlr.Token)
+
+ // GetOps returns the ops token list.
+ GetOps() []antlr.Token
+
+ // SetOps sets the ops token list.
+ SetOps([]antlr.Token)
+
+ // GetE returns the e rule contexts.
+ GetE() IRelationContext
+
+ // Get_relation returns the _relation rule contexts.
+ Get_relation() IRelationContext
+
+ // SetE sets the e rule contexts.
+ SetE(IRelationContext)
+
+ // Set_relation sets the _relation rule contexts.
+ Set_relation(IRelationContext)
+
+ // GetE1 returns the e1 rule context list.
+ GetE1() []IRelationContext
+
+ // SetE1 sets the e1 rule context list.
+ SetE1([]IRelationContext)
+
+ // IsConditionalAndContext differentiates from other interfaces.
+ IsConditionalAndContext()
+}
+
+type ConditionalAndContext struct {
+ *antlr.BaseParserRuleContext
+ parser antlr.Parser
+ e IRelationContext
+ s8 antlr.Token
+ ops []antlr.Token
+ _relation IRelationContext
+ e1 []IRelationContext
+}
+
+func NewEmptyConditionalAndContext() *ConditionalAndContext {
+ var p = new(ConditionalAndContext)
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(nil, -1)
+ p.RuleIndex = CELParserRULE_conditionalAnd
+ return p
+}
+
+func (*ConditionalAndContext) IsConditionalAndContext() {}
+
+func NewConditionalAndContext(parser antlr.Parser, parent antlr.ParserRuleContext, invokingState int) *ConditionalAndContext {
+ var p = new(ConditionalAndContext)
+
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(parent, invokingState)
+
+ p.parser = parser
+ p.RuleIndex = CELParserRULE_conditionalAnd
+
+ return p
+}
+
+func (s *ConditionalAndContext) GetParser() antlr.Parser { return s.parser }
+
+func (s *ConditionalAndContext) GetS8() antlr.Token { return s.s8 }
+
+func (s *ConditionalAndContext) SetS8(v antlr.Token) { s.s8 = v }
+
+func (s *ConditionalAndContext) GetOps() []antlr.Token { return s.ops }
+
+func (s *ConditionalAndContext) SetOps(v []antlr.Token) { s.ops = v }
+
+func (s *ConditionalAndContext) GetE() IRelationContext { return s.e }
+
+func (s *ConditionalAndContext) Get_relation() IRelationContext { return s._relation }
+
+func (s *ConditionalAndContext) SetE(v IRelationContext) { s.e = v }
+
+func (s *ConditionalAndContext) Set_relation(v IRelationContext) { s._relation = v }
+
+func (s *ConditionalAndContext) GetE1() []IRelationContext { return s.e1 }
+
+func (s *ConditionalAndContext) SetE1(v []IRelationContext) { s.e1 = v }
+
+func (s *ConditionalAndContext) AllRelation() []IRelationContext {
+ var ts = s.GetTypedRuleContexts(reflect.TypeOf((*IRelationContext)(nil)).Elem())
+ var tst = make([]IRelationContext, len(ts))
+
+ for i, t := range ts {
+ if t != nil {
+ tst[i] = t.(IRelationContext)
+ }
+ }
+
+ return tst
+}
+
+func (s *ConditionalAndContext) Relation(i int) IRelationContext {
+ var t = s.GetTypedRuleContext(reflect.TypeOf((*IRelationContext)(nil)).Elem(), i)
+
+ if t == nil {
+ return nil
+ }
+
+ return t.(IRelationContext)
+}
+
+func (s *ConditionalAndContext) GetRuleContext() antlr.RuleContext {
+ return s
+}
+
+func (s *ConditionalAndContext) ToStringTree(ruleNames []string, recog antlr.Recognizer) string {
+ return antlr.TreesStringTree(s, ruleNames, recog)
+}
+
+func (s *ConditionalAndContext) EnterRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.EnterConditionalAnd(s)
+ }
+}
+
+func (s *ConditionalAndContext) ExitRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.ExitConditionalAnd(s)
+ }
+}
+
+func (s *ConditionalAndContext) Accept(visitor antlr.ParseTreeVisitor) interface{} {
+ switch t := visitor.(type) {
+ case CELVisitor:
+ return t.VisitConditionalAnd(s)
+
+ default:
+ return t.VisitChildren(s)
+ }
+}
+
+func (p *CELParser) ConditionalAnd() (localctx IConditionalAndContext) {
+ localctx = NewConditionalAndContext(p, p.GetParserRuleContext(), p.GetState())
+ p.EnterRule(localctx, 6, CELParserRULE_conditionalAnd)
+ var _la int
+
+ defer func() {
+ p.ExitRule()
+ }()
+
+ defer func() {
+ if err := recover(); err != nil {
+ if v, ok := err.(antlr.RecognitionException); ok {
+ localctx.SetException(v)
+ p.GetErrorHandler().ReportError(p, v)
+ p.GetErrorHandler().Recover(p, v)
+ } else {
+ panic(err)
+ }
+ }
+ }()
+
+ p.EnterOuterAlt(localctx, 1)
+ {
+ p.SetState(45)
+
+ var _x = p.relation(0)
+
+ localctx.(*ConditionalAndContext).e = _x
+ }
+ p.SetState(50)
+ p.GetErrorHandler().Sync(p)
+ _la = p.GetTokenStream().LA(1)
+
+ for _la == CELParserLOGICAL_AND {
+ {
+ p.SetState(46)
+
+ var _m = p.Match(CELParserLOGICAL_AND)
+
+ localctx.(*ConditionalAndContext).s8 = _m
+ }
+ localctx.(*ConditionalAndContext).ops = append(localctx.(*ConditionalAndContext).ops, localctx.(*ConditionalAndContext).s8)
+ {
+ p.SetState(47)
+
+ var _x = p.relation(0)
+
+ localctx.(*ConditionalAndContext)._relation = _x
+ }
+ localctx.(*ConditionalAndContext).e1 = append(localctx.(*ConditionalAndContext).e1, localctx.(*ConditionalAndContext)._relation)
+
+ p.SetState(52)
+ p.GetErrorHandler().Sync(p)
+ _la = p.GetTokenStream().LA(1)
+ }
+
+ return localctx
+}
+
+// IRelationContext is an interface to support dynamic dispatch.
+type IRelationContext interface {
+ antlr.ParserRuleContext
+
+ // GetParser returns the parser.
+ GetParser() antlr.Parser
+
+ // GetOp returns the op token.
+ GetOp() antlr.Token
+
+ // SetOp sets the op token.
+ SetOp(antlr.Token)
+
+ // IsRelationContext differentiates from other interfaces.
+ IsRelationContext()
+}
+
+type RelationContext struct {
+ *antlr.BaseParserRuleContext
+ parser antlr.Parser
+ op antlr.Token
+}
+
+func NewEmptyRelationContext() *RelationContext {
+ var p = new(RelationContext)
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(nil, -1)
+ p.RuleIndex = CELParserRULE_relation
+ return p
+}
+
+func (*RelationContext) IsRelationContext() {}
+
+func NewRelationContext(parser antlr.Parser, parent antlr.ParserRuleContext, invokingState int) *RelationContext {
+ var p = new(RelationContext)
+
+ p.BaseParserRuleContext = antlr.NewBaseParserRuleContext(parent, invokingState)
+
+ p.parser = parser
+ p.RuleIndex = CELParserRULE_relation
+
+ return p
+}
+
+func (s *RelationContext) GetParser() antlr.Parser { return s.parser }
+
+func (s *RelationContext) GetOp() antlr.Token { return s.op }
+
+func (s *RelationContext) SetOp(v antlr.Token) { s.op = v }
+
+func (s *RelationContext) Calc() ICalcContext {
+ var t = s.GetTypedRuleContext(reflect.TypeOf((*ICalcContext)(nil)).Elem(), 0)
+
+ if t == nil {
+ return nil
+ }
+
+ return t.(ICalcContext)
+}
+
+func (s *RelationContext) AllRelation() []IRelationContext {
+ var ts = s.GetTypedRuleContexts(reflect.TypeOf((*IRelationContext)(nil)).Elem())
+ var tst = make([]IRelationContext, len(ts))
+
+ for i, t := range ts {
+ if t != nil {
+ tst[i] = t.(IRelationContext)
+ }
+ }
+
+ return tst
+}
+
+func (s *RelationContext) Relation(i int) IRelationContext {
+ var t = s.GetTypedRuleContext(reflect.TypeOf((*IRelationContext)(nil)).Elem(), i)
+
+ if t == nil {
+ return nil
+ }
+
+ return t.(IRelationContext)
+}
+
+func (s *RelationContext) GetRuleContext() antlr.RuleContext {
+ return s
+}
+
+func (s *RelationContext) ToStringTree(ruleNames []string, recog antlr.Recognizer) string {
+ return antlr.TreesStringTree(s, ruleNames, recog)
+}
+
+func (s *RelationContext) EnterRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.EnterRelation(s)
+ }
+}
+
+func (s *RelationContext) ExitRule(listener antlr.ParseTreeListener) {
+ if listenerT, ok := listener.(CELListener); ok {
+ listenerT.ExitRelation(s)
+ }
+}
+
+func (s *RelationContext) Accept(visitor antlr.ParseTreeVisitor) interface{} {
+ switch t := visitor.(type) {
+ case CELVisitor:
+ return t.VisitRelation(s)
+
+ default:
+ return t.VisitChildren(s)
+ }
+}
+
+func (p *CELParser) Relation() (localctx IRelationContext) {
+ return p.relation(0)
+}
+
+func (p *CELParser) relation(_p int) (localctx IRelationContext) {
+ var _parentctx antlr.ParserRuleContext = p.GetParserRuleContext()
+ _parentState := p.GetState()
+ localctx = NewRelationContext(p, p.GetParserRuleContext(), _parentState)
+ var _prevctx IRelationContext = localctx
+ var _ antlr.ParserRuleContext = _prevctx // TODO: To prevent unused variable warning.
+ _startState := 8
+ p.EnterRecursionRule(localctx, 8, CELParserRULE_relation, _p)
+ var _la int
+
+ defer func() {
+ p.UnrollRecursionContexts(_parentctx)
+ }()
+
+ defer func() {
+ if err := recover(); err != nil {
+ if v, ok := err.(antlr.RecognitionException); ok {
+ localctx.SetException(v)
+ p.GetErrorHandler().ReportError(p, v)
+ p.GetErrorHandler().Recover(p, v)
+ } else {
+ panic(err)
+ }
+ }
+ }()
+
+ var _alt int
+
+ p.EnterOuterAlt(localctx, 1)
+ {
+ p.SetState(54)
+ p.calc(0)
+ }
+
+ p.GetParserRuleContext().SetStop(p.GetTokenStream().LT(-1))
+ p.SetState(61)
+ p.GetErrorHandler().Sync(p)
+ _alt = p.GetInterpreter().AdaptivePredict(p.GetTokenStream(), 3, p.GetParserRuleContext())
+
+ for _alt != 2 && _alt != antlr.ATNInvalidAltNumber {
+ if _alt == 1 {
+ if p.GetParseListeners() != nil {
+ p.TriggerExitRuleEvent()
+ }
+ _prevctx = localctx
+ localctx = NewRelationContext(p, _parentctx, _parentState)
+ p.PushNewRecursionContext(localctx, _startState, CELParserRULE_relation)
+ p.SetState(56)
+
+ if !(p.Precpred(p.GetParserRuleContext(), 1)) {
+ panic(antlr.NewFailedPredicateException(p, "p.Precpred(p.GetParserRuleContext(), 1)", ""))
+ }
+ p.SetState(57)
+
+ var _lt = p.GetTokenStream().LT(1)
+
+ localctx.(*RelationContext).op = _lt
+
+ _la = p.GetTokenStream().LA(1)
+
+ if !(((_la)&-(0x1f+1)) == 0 && ((1<= c.buf.Len() {
+ panic("cannot consume EOF")
+ }
+ c.pos++
+}
+
+// LA implements (antlr.CharStream).LA.
+func (c *charStream) LA(offset int) int {
+ if offset == 0 {
+ return 0
+ }
+ if offset < 0 {
+ offset++
+ }
+ pos := c.pos + offset - 1
+ if pos < 0 || pos >= c.buf.Len() {
+ return antlr.TokenEOF
+ }
+ return int(c.buf.Get(pos))
+}
+
+// LT mimics (*antlr.InputStream).LT.
+func (c *charStream) LT(offset int) int {
+ return c.LA(offset)
+}
+
+// Mark implements (antlr.CharStream).Mark.
+func (c *charStream) Mark() int {
+ return -1
+}
+
+// Release implements (antlr.CharStream).Release.
+func (c *charStream) Release(marker int) {}
+
+// Index implements (antlr.CharStream).Index.
+func (c *charStream) Index() int {
+ return c.pos
+}
+
+// Seek implements (antlr.CharStream).Seek.
+func (c *charStream) Seek(index int) {
+ if index <= c.pos {
+ c.pos = index
+ return
+ }
+ if index < c.buf.Len() {
+ c.pos = index
+ } else {
+ c.pos = c.buf.Len()
+ }
+}
+
+// Size implements (antlr.CharStream).Size.
+func (c *charStream) Size() int {
+ return c.buf.Len()
+}
+
+// GetSourceName implements (antlr.CharStream).GetSourceName.
+func (c *charStream) GetSourceName() string {
+ return c.src
+}
+
+// GetText implements (antlr.CharStream).GetText.
+func (c *charStream) GetText(start, stop int) string {
+ if stop >= c.buf.Len() {
+ stop = c.buf.Len() - 1
+ }
+ if start >= c.buf.Len() {
+ return ""
+ }
+ return c.buf.Slice(start, stop+1)
+}
+
+// GetTextFromTokens implements (antlr.CharStream).GetTextFromTokens.
+func (c *charStream) GetTextFromTokens(start, stop antlr.Token) string {
+ if start != nil && stop != nil {
+ return c.GetText(start.GetTokenIndex(), stop.GetTokenIndex())
+ }
+ return ""
+}
+
+// GetTextFromInterval implements (antlr.CharStream).GetTextFromInterval.
+func (c *charStream) GetTextFromInterval(i *antlr.Interval) string {
+ return c.GetText(i.Start, i.Stop)
+}
+
+// String mimics (*antlr.InputStream).String.
+func (c *charStream) String() string {
+ return c.buf.Slice(0, c.buf.Len())
+}
+
+var _ antlr.CharStream = &charStream{}
+
+func newCharStream(buf runes.Buffer, desc string) antlr.CharStream {
+ return &charStream{
+ buf: buf,
+ src: desc,
+ }
+}
diff --git a/vendor/github.com/google/cel-go/parser/macro.go b/vendor/github.com/google/cel-go/parser/macro.go
new file mode 100644
index 0000000000..baeddd94ea
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/macro.go
@@ -0,0 +1,386 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package parser
+
+import (
+ "fmt"
+
+ "github.com/google/cel-go/common"
+ "github.com/google/cel-go/common/operators"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// TODO: Consider moving macros to common.
+
+// NewGlobalMacro creates a Macro for a global function with the specified arg count.
+func NewGlobalMacro(function string, argCount int, expander MacroExpander) Macro {
+ return ¯o{
+ function: function,
+ argCount: argCount,
+ expander: expander}
+}
+
+// NewReceiverMacro creates a Macro for a receiver function matching the specified arg count.
+func NewReceiverMacro(function string, argCount int, expander MacroExpander) Macro {
+ return ¯o{
+ function: function,
+ argCount: argCount,
+ expander: expander,
+ receiverStyle: true}
+}
+
+// NewGlobalVarArgMacro creates a Macro for a global function with a variable arg count.
+func NewGlobalVarArgMacro(function string, expander MacroExpander) Macro {
+ return ¯o{
+ function: function,
+ expander: expander,
+ varArgStyle: true}
+}
+
+// NewReceiverVarArgMacro creates a Macro for a receiver function matching a variable arg
+// count.
+func NewReceiverVarArgMacro(function string, expander MacroExpander) Macro {
+ return ¯o{
+ function: function,
+ expander: expander,
+ receiverStyle: true,
+ varArgStyle: true}
+}
+
+// Macro interface for describing the function signature to match and the MacroExpander to apply.
+//
+// Note: when a Macro should apply to multiple overloads (based on arg count) of a given function,
+// a Macro should be created per arg-count.
+type Macro interface {
+ // Function name to match.
+ Function() string
+
+ // ArgCount for the function call.
+ //
+ // When the macro is a var-arg style macro, the return value will be zero, but the MacroKey
+ // will contain a `*` where the arg count would have been.
+ ArgCount() int
+
+ // IsReceiverStyle returns true if the macro matches a receiver style call.
+ IsReceiverStyle() bool
+
+ // MacroKey returns the macro signatures accepted by this macro.
+ //
+ // Format: `::`.
+ //
+ // When the macros is a var-arg style macro, the `arg-count` value is represented as a `*`.
+ MacroKey() string
+
+ // Expander returns the MacroExpander to apply when the macro key matches the parsed call
+ // signature.
+ Expander() MacroExpander
+}
+
+// Macro type which declares the function name and arg count expected for the
+// macro, as well as a macro expansion function.
+type macro struct {
+ function string
+ receiverStyle bool
+ varArgStyle bool
+ argCount int
+ expander MacroExpander
+}
+
+// Function returns the macro's function name (i.e. the function whose syntax it mimics).
+func (m *macro) Function() string {
+ return m.function
+}
+
+// ArgCount returns the number of arguments the macro expects.
+func (m *macro) ArgCount() int {
+ return m.argCount
+}
+
+// IsReceiverStyle returns whether the macro is receiver style.
+func (m *macro) IsReceiverStyle() bool {
+ return m.receiverStyle
+}
+
+// Expander implements the Macro interface method.
+func (m *macro) Expander() MacroExpander {
+ return m.expander
+}
+
+// MacroKey implements the Macro interface method.
+func (m *macro) MacroKey() string {
+ if m.varArgStyle {
+ return makeVarArgMacroKey(m.function, m.receiverStyle)
+ }
+ return makeMacroKey(m.function, m.argCount, m.receiverStyle)
+}
+
+func makeMacroKey(name string, args int, receiverStyle bool) string {
+ return fmt.Sprintf("%s:%d:%v", name, args, receiverStyle)
+}
+
+func makeVarArgMacroKey(name string, receiverStyle bool) string {
+ return fmt.Sprintf("%s:*:%v", name, receiverStyle)
+}
+
+// MacroExpander converts the target and args of a function call that matches a Macro.
+//
+// Note: when the Macros.IsReceiverStyle() is true, the target argument will be nil.
+type MacroExpander func(eh ExprHelper,
+ target *exprpb.Expr,
+ args []*exprpb.Expr) (*exprpb.Expr, *common.Error)
+
+// ExprHelper assists with the manipulation of proto-based Expr values in a manner which is
+// consistent with the source position and expression id generation code leveraged by both
+// the parser and type-checker.
+type ExprHelper interface {
+ // LiteralBool creates an Expr value for a bool literal.
+ LiteralBool(value bool) *exprpb.Expr
+
+ // LiteralBytes creates an Expr value for a byte literal.
+ LiteralBytes(value []byte) *exprpb.Expr
+
+ // LiteralDouble creates an Expr value for double literal.
+ LiteralDouble(value float64) *exprpb.Expr
+
+ // LiteralInt creates an Expr value for an int literal.
+ LiteralInt(value int64) *exprpb.Expr
+
+ // LiteralString creates am Expr value for a string literal.
+ LiteralString(value string) *exprpb.Expr
+
+ // LiteralUint creates an Expr value for a uint literal.
+ LiteralUint(value uint64) *exprpb.Expr
+
+ // NewList creates a CreateList instruction where the list is comprised of the optional set
+ // of elements provided as arguments.
+ NewList(elems ...*exprpb.Expr) *exprpb.Expr
+
+ // NewMap creates a CreateStruct instruction for a map where the map is comprised of the
+ // optional set of key, value entries.
+ NewMap(entries ...*exprpb.Expr_CreateStruct_Entry) *exprpb.Expr
+
+ // NewMapEntry creates a Map Entry for the key, value pair.
+ NewMapEntry(key *exprpb.Expr, val *exprpb.Expr) *exprpb.Expr_CreateStruct_Entry
+
+ // NewObject creates a CreateStruct instruction for an object with a given type name and
+ // optional set of field initializers.
+ NewObject(typeName string, fieldInits ...*exprpb.Expr_CreateStruct_Entry) *exprpb.Expr
+
+ // NewObjectFieldInit creates a new Object field initializer from the field name and value.
+ NewObjectFieldInit(field string, init *exprpb.Expr) *exprpb.Expr_CreateStruct_Entry
+
+ // Fold creates a fold comprehension instruction.
+ //
+ // - iterVar is the iteration variable name.
+ // - iterRange represents the expression that resolves to a list or map where the elements or
+ // keys (respectively) will be iterated over.
+ // - accuVar is the accumulation variable name, typically parser.AccumulatorName.
+ // - accuInit is the initial expression whose value will be set for the accuVar prior to
+ // folding.
+ // - condition is the expression to test to determine whether to continue folding.
+ // - step is the expression to evaluation at the conclusion of a single fold iteration.
+ // - result is the computation to evaluate at the conclusion of the fold.
+ //
+ // The accuVar should not shadow variable names that you would like to reference within the
+ // environment in the step and condition expressions. Presently, the name __result__ is commonly
+ // used by built-in macros but this may change in the future.
+ Fold(iterVar string,
+ iterRange *exprpb.Expr,
+ accuVar string,
+ accuInit *exprpb.Expr,
+ condition *exprpb.Expr,
+ step *exprpb.Expr,
+ result *exprpb.Expr) *exprpb.Expr
+
+ // Ident creates an identifier Expr value.
+ Ident(name string) *exprpb.Expr
+
+ // GlobalCall creates a function call Expr value for a global (free) function.
+ GlobalCall(function string, args ...*exprpb.Expr) *exprpb.Expr
+
+ // ReceiverCall creates a function call Expr value for a receiver-style function.
+ ReceiverCall(function string, target *exprpb.Expr, args ...*exprpb.Expr) *exprpb.Expr
+
+ // PresenceTest creates a Select TestOnly Expr value for modelling has() semantics.
+ PresenceTest(operand *exprpb.Expr, field string) *exprpb.Expr
+
+ // Select create a field traversal Expr value.
+ Select(operand *exprpb.Expr, field string) *exprpb.Expr
+
+ // OffsetLocation returns the Location of the expression identifier.
+ OffsetLocation(exprID int64) common.Location
+}
+
+var (
+ // AllMacros includes the list of all spec-supported macros.
+ AllMacros = []Macro{
+ // The macro "has(m.f)" which tests the presence of a field, avoiding the need to specify
+ // the field as a string.
+ NewGlobalMacro(operators.Has, 1, makeHas),
+
+ // The macro "range.all(var, predicate)", which is true if for all elements in range the
+ // predicate holds.
+ NewReceiverMacro(operators.All, 2, makeAll),
+
+ // The macro "range.exists(var, predicate)", which is true if for at least one element in
+ // range the predicate holds.
+ NewReceiverMacro(operators.Exists, 2, makeExists),
+
+ // The macro "range.exists_one(var, predicate)", which is true if for exactly one element
+ // in range the predicate holds.
+ NewReceiverMacro(operators.ExistsOne, 2, makeExistsOne),
+
+ // The macro "range.map(var, function)", applies the function to the vars in the range.
+ NewReceiverMacro(operators.Map, 2, makeMap),
+
+ // The macro "range.map(var, predicate, function)", applies the function to the vars in
+ // the range for which the predicate holds true. The other variables are filtered out.
+ NewReceiverMacro(operators.Map, 3, makeMap),
+
+ // The macro "range.filter(var, predicate)", filters out the variables for which the
+ // predicate is false.
+ NewReceiverMacro(operators.Filter, 2, makeFilter),
+ }
+
+ // NoMacros list.
+ NoMacros = []Macro{}
+)
+
+// AccumulatorName is the traditional variable name assigned to the fold accumulator variable.
+const AccumulatorName = "__result__"
+
+type quantifierKind int
+
+const (
+ quantifierAll quantifierKind = iota
+ quantifierExists
+ quantifierExistsOne
+)
+
+func makeAll(eh ExprHelper, target *exprpb.Expr, args []*exprpb.Expr) (*exprpb.Expr, *common.Error) {
+ return makeQuantifier(quantifierAll, eh, target, args)
+}
+
+func makeExists(eh ExprHelper, target *exprpb.Expr, args []*exprpb.Expr) (*exprpb.Expr, *common.Error) {
+ return makeQuantifier(quantifierExists, eh, target, args)
+}
+
+func makeExistsOne(eh ExprHelper, target *exprpb.Expr, args []*exprpb.Expr) (*exprpb.Expr, *common.Error) {
+ return makeQuantifier(quantifierExistsOne, eh, target, args)
+}
+
+func makeQuantifier(kind quantifierKind, eh ExprHelper, target *exprpb.Expr, args []*exprpb.Expr) (*exprpb.Expr, *common.Error) {
+ v, found := extractIdent(args[0])
+ if !found {
+ location := eh.OffsetLocation(args[0].GetId())
+ return nil, &common.Error{
+ Message: "argument must be a simple name",
+ Location: location}
+ }
+ accuIdent := func() *exprpb.Expr {
+ return eh.Ident(AccumulatorName)
+ }
+
+ var init *exprpb.Expr
+ var condition *exprpb.Expr
+ var step *exprpb.Expr
+ var result *exprpb.Expr
+ switch kind {
+ case quantifierAll:
+ init = eh.LiteralBool(true)
+ condition = eh.GlobalCall(operators.NotStrictlyFalse, accuIdent())
+ step = eh.GlobalCall(operators.LogicalAnd, accuIdent(), args[1])
+ result = accuIdent()
+ case quantifierExists:
+ init = eh.LiteralBool(false)
+ condition = eh.GlobalCall(
+ operators.NotStrictlyFalse,
+ eh.GlobalCall(operators.LogicalNot, accuIdent()))
+ step = eh.GlobalCall(operators.LogicalOr, accuIdent(), args[1])
+ result = accuIdent()
+ case quantifierExistsOne:
+ zeroExpr := eh.LiteralInt(0)
+ oneExpr := eh.LiteralInt(1)
+ init = zeroExpr
+ condition = eh.LiteralBool(true)
+ step = eh.GlobalCall(operators.Conditional, args[1],
+ eh.GlobalCall(operators.Add, accuIdent(), oneExpr), accuIdent())
+ result = eh.GlobalCall(operators.Equals, accuIdent(), oneExpr)
+ default:
+ return nil, &common.Error{Message: fmt.Sprintf("unrecognized quantifier '%v'", kind)}
+ }
+ return eh.Fold(v, target, AccumulatorName, init, condition, step, result), nil
+}
+
+func makeMap(eh ExprHelper, target *exprpb.Expr, args []*exprpb.Expr) (*exprpb.Expr, *common.Error) {
+ v, found := extractIdent(args[0])
+ if !found {
+ return nil, &common.Error{Message: "argument is not an identifier"}
+ }
+
+ var fn *exprpb.Expr
+ var filter *exprpb.Expr
+
+ if len(args) == 3 {
+ filter = args[1]
+ fn = args[2]
+ } else {
+ filter = nil
+ fn = args[1]
+ }
+
+ accuExpr := eh.Ident(AccumulatorName)
+ init := eh.NewList()
+ condition := eh.LiteralBool(true)
+ // TODO: use compiler internal method for faster, stateful add.
+ step := eh.GlobalCall(operators.Add, accuExpr, eh.NewList(fn))
+
+ if filter != nil {
+ step = eh.GlobalCall(operators.Conditional, filter, step, accuExpr)
+ }
+ return eh.Fold(v, target, AccumulatorName, init, condition, step, accuExpr), nil
+}
+
+func makeFilter(eh ExprHelper, target *exprpb.Expr, args []*exprpb.Expr) (*exprpb.Expr, *common.Error) {
+ v, found := extractIdent(args[0])
+ if !found {
+ return nil, &common.Error{Message: "argument is not an identifier"}
+ }
+
+ filter := args[1]
+ accuExpr := eh.Ident(AccumulatorName)
+ init := eh.NewList()
+ condition := eh.LiteralBool(true)
+ // TODO: use compiler internal method for faster, stateful add.
+ step := eh.GlobalCall(operators.Add, accuExpr, eh.NewList(args[0]))
+ step = eh.GlobalCall(operators.Conditional, filter, step, accuExpr)
+ return eh.Fold(v, target, AccumulatorName, init, condition, step, accuExpr), nil
+}
+
+func extractIdent(e *exprpb.Expr) (string, bool) {
+ switch e.ExprKind.(type) {
+ case *exprpb.Expr_IdentExpr:
+ return e.GetIdentExpr().GetName(), true
+ }
+ return "", false
+}
+
+func makeHas(eh ExprHelper, target *exprpb.Expr, args []*exprpb.Expr) (*exprpb.Expr, *common.Error) {
+ if s, ok := args[0].ExprKind.(*exprpb.Expr_SelectExpr); ok {
+ return eh.PresenceTest(s.SelectExpr.GetOperand(), s.SelectExpr.GetField()), nil
+ }
+ return nil, &common.Error{Message: "invalid argument to has() macro"}
+}
diff --git a/vendor/github.com/google/cel-go/parser/options.go b/vendor/github.com/google/cel-go/parser/options.go
new file mode 100644
index 0000000000..b50686a912
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/options.go
@@ -0,0 +1,104 @@
+// Copyright 2021 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package parser
+
+import "fmt"
+
+type options struct {
+ maxRecursionDepth int
+ errorRecoveryTokenLookaheadLimit int
+ errorRecoveryLimit int
+ expressionSizeCodePointLimit int
+ macros map[string]Macro
+ populateMacroCalls bool
+}
+
+// Option configures the behavior of the parser.
+type Option func(*options) error
+
+// MaxRecursionDepth limits the maximum depth the parser will attempt to parse the expression before giving up.
+func MaxRecursionDepth(limit int) Option {
+ return func(opts *options) error {
+ if limit < -1 {
+ return fmt.Errorf("max recursion depth must be greater than or equal to -1: %d", limit)
+ }
+ opts.maxRecursionDepth = limit
+ return nil
+ }
+}
+
+// ErrorRecoveryLookaheadTokenLimit limits the number of lexer tokens that may be considered during error recovery.
+//
+// Error recovery often involves looking ahead in the input to determine if there's a point at which parsing may
+// successfully resume. In some pathological cases, the parser can look through quite a large set of input which
+// in turn generates a lot of back-tracking and performance degredation.
+//
+// The limit must be > 1, and is recommended to be less than the default of 256.
+func ErrorRecoveryLookaheadTokenLimit(limit int) Option {
+ return func(opts *options) error {
+ if limit < 1 {
+ return fmt.Errorf("error recovery lookahead token limit must be at least 1: %d", limit)
+ }
+ opts.errorRecoveryTokenLookaheadLimit = limit
+ return nil
+ }
+}
+
+// ErrorRecoveryLimit limits the number of attempts the parser will perform to recover from an error.
+func ErrorRecoveryLimit(limit int) Option {
+ return func(opts *options) error {
+ if limit < -1 {
+ return fmt.Errorf("error recovery limit must be greater than or equal to -1: %d", limit)
+ }
+ opts.errorRecoveryLimit = limit
+ return nil
+ }
+}
+
+// ExpressionSizeCodePointLimit is an option which limits the maximum code point count of an
+// expression.
+func ExpressionSizeCodePointLimit(expressionSizeCodePointLimit int) Option {
+ return func(opts *options) error {
+ if expressionSizeCodePointLimit < -1 {
+ return fmt.Errorf("expression size code point limit must be greater than or equal to -1: %d", expressionSizeCodePointLimit)
+ }
+ opts.expressionSizeCodePointLimit = expressionSizeCodePointLimit
+ return nil
+ }
+}
+
+// Macros adds the given macros to the parser.
+func Macros(macros ...Macro) Option {
+ return func(opts *options) error {
+ for _, m := range macros {
+ if m != nil {
+ if opts.macros == nil {
+ opts.macros = make(map[string]Macro)
+ }
+ opts.macros[m.MacroKey()] = m
+ }
+ }
+ return nil
+ }
+}
+
+// PopulateMacroCalls ensures that the original call signatures replaced by expanded macros
+// are preserved in the `SourceInfo` of parse result.
+func PopulateMacroCalls(populateMacroCalls bool) Option {
+ return func(opts *options) error {
+ opts.populateMacroCalls = populateMacroCalls
+ return nil
+ }
+}
diff --git a/vendor/github.com/google/cel-go/parser/parser.go b/vendor/github.com/google/cel-go/parser/parser.go
new file mode 100644
index 0000000000..11dcc0eb9d
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/parser.go
@@ -0,0 +1,903 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Package parser declares an expression parser with support for macro
+// expansion.
+package parser
+
+import (
+ "fmt"
+ "strconv"
+ "strings"
+ "sync"
+
+ "github.com/antlr/antlr4/runtime/Go/antlr"
+ "github.com/google/cel-go/common"
+ "github.com/google/cel-go/common/operators"
+ "github.com/google/cel-go/common/runes"
+ "github.com/google/cel-go/parser/gen"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+// Parser encapsulates the context necessary to perform parsing for different expressions.
+type Parser struct {
+ options
+}
+
+// NewParser builds and returns a new Parser using the provided options.
+func NewParser(opts ...Option) (*Parser, error) {
+ p := &Parser{}
+ for _, opt := range opts {
+ if err := opt(&p.options); err != nil {
+ return nil, err
+ }
+ }
+ if p.maxRecursionDepth == 0 {
+ p.maxRecursionDepth = 200
+ }
+ if p.maxRecursionDepth == -1 {
+ p.maxRecursionDepth = int((^uint(0)) >> 1)
+ }
+ if p.errorRecoveryTokenLookaheadLimit == 0 {
+ p.errorRecoveryTokenLookaheadLimit = 256
+ }
+ if p.errorRecoveryLimit == 0 {
+ p.errorRecoveryLimit = 30
+ }
+ if p.errorRecoveryLimit == -1 {
+ p.errorRecoveryLimit = int((^uint(0)) >> 1)
+ }
+ if p.expressionSizeCodePointLimit == 0 {
+ p.expressionSizeCodePointLimit = 100_000
+ }
+ if p.expressionSizeCodePointLimit == -1 {
+ p.expressionSizeCodePointLimit = int((^uint(0)) >> 1)
+ }
+ // Bool is false by default, so populateMacroCalls will be false by default
+ return p, nil
+}
+
+// mustNewParser does the work of NewParser and panics if an error occurs.
+//
+// This function is only intended for internal use and is for backwards compatibility in Parse and
+// ParseWithMacros, where we know the options will result in an error.
+func mustNewParser(opts ...Option) *Parser {
+ p, err := NewParser(opts...)
+ if err != nil {
+ panic(err)
+ }
+ return p
+}
+
+// Parse parses the expression represented by source and returns the result.
+func (p *Parser) Parse(source common.Source) (*exprpb.ParsedExpr, *common.Errors) {
+ impl := parser{
+ errors: &parseErrors{common.NewErrors(source)},
+ helper: newParserHelper(source),
+ macros: p.macros,
+ maxRecursionDepth: p.maxRecursionDepth,
+ errorRecoveryLimit: p.errorRecoveryLimit,
+ errorRecoveryLookaheadTokenLimit: p.errorRecoveryTokenLookaheadLimit,
+ populateMacroCalls: p.populateMacroCalls,
+ }
+ buf, ok := source.(runes.Buffer)
+ if !ok {
+ buf = runes.NewBuffer(source.Content())
+ }
+ var e *exprpb.Expr
+ if buf.Len() > p.expressionSizeCodePointLimit {
+ e = impl.reportError(common.NoLocation,
+ "expression code point size exceeds limit: size: %d, limit %d",
+ buf.Len(), p.expressionSizeCodePointLimit)
+ } else {
+ e = impl.parse(buf, source.Description())
+ }
+ return &exprpb.ParsedExpr{
+ Expr: e,
+ SourceInfo: impl.helper.getSourceInfo(),
+ }, impl.errors.Errors
+}
+
+// reservedIds are not legal to use as variables. We exclude them post-parse, as they *are* valid
+// field names for protos, and it would complicate the grammar to distinguish the cases.
+var reservedIds = map[string]struct{}{
+ "as": {},
+ "break": {},
+ "const": {},
+ "continue": {},
+ "else": {},
+ "false": {},
+ "for": {},
+ "function": {},
+ "if": {},
+ "import": {},
+ "in": {},
+ "let": {},
+ "loop": {},
+ "package": {},
+ "namespace": {},
+ "null": {},
+ "return": {},
+ "true": {},
+ "var": {},
+ "void": {},
+ "while": {},
+}
+
+// Parse converts a source input a parsed expression.
+// This function calls ParseWithMacros with AllMacros.
+//
+// Deprecated: Use NewParser().Parse() instead.
+func Parse(source common.Source) (*exprpb.ParsedExpr, *common.Errors) {
+ return ParseWithMacros(source, AllMacros)
+}
+
+// ParseWithMacros converts a source input and macros set to a parsed expression.
+//
+// Deprecated: Use NewParser().Parse() instead.
+func ParseWithMacros(source common.Source, macros []Macro) (*exprpb.ParsedExpr, *common.Errors) {
+ return mustNewParser(Macros(macros...)).Parse(source)
+}
+
+type recursionError struct {
+ message string
+}
+
+// Error implements error.
+func (re *recursionError) Error() string {
+ return re.message
+}
+
+var _ error = &recursionError{}
+
+type recursionListener struct {
+ maxDepth int
+ ruleTypeDepth map[int]*int
+}
+
+func (rl *recursionListener) VisitTerminal(node antlr.TerminalNode) {}
+
+func (rl *recursionListener) VisitErrorNode(node antlr.ErrorNode) {}
+
+func (rl *recursionListener) EnterEveryRule(ctx antlr.ParserRuleContext) {
+ if ctx == nil {
+ return
+ }
+ ruleIndex := ctx.GetRuleIndex()
+ depth, found := rl.ruleTypeDepth[ruleIndex]
+ if !found {
+ var counter = 1
+ rl.ruleTypeDepth[ruleIndex] = &counter
+ depth = &counter
+ } else {
+ *depth++
+ }
+ if *depth >= rl.maxDepth {
+ panic(&recursionError{
+ message: fmt.Sprintf("expression recursion limit exceeded: %d", rl.maxDepth),
+ })
+ }
+}
+
+func (rl *recursionListener) ExitEveryRule(ctx antlr.ParserRuleContext) {
+ if ctx == nil {
+ return
+ }
+ ruleIndex := ctx.GetRuleIndex()
+ if depth, found := rl.ruleTypeDepth[ruleIndex]; found && *depth > 0 {
+ *depth--
+ }
+}
+
+var _ antlr.ParseTreeListener = &recursionListener{}
+
+type recoveryLimitError struct {
+ message string
+}
+
+// Error implements error.
+func (rl *recoveryLimitError) Error() string {
+ return rl.message
+}
+
+type lookaheadLimitError struct {
+ message string
+}
+
+func (ll *lookaheadLimitError) Error() string {
+ return ll.message
+}
+
+var _ error = &recoveryLimitError{}
+
+type recoveryLimitErrorStrategy struct {
+ *antlr.DefaultErrorStrategy
+ errorRecoveryLimit int
+ errorRecoveryTokenLookaheadLimit int
+ recoveryAttempts int
+}
+
+type lookaheadConsumer struct {
+ antlr.Parser
+ errorRecoveryTokenLookaheadLimit int
+ lookaheadAttempts int
+}
+
+func (lc *lookaheadConsumer) Consume() antlr.Token {
+ if lc.lookaheadAttempts >= lc.errorRecoveryTokenLookaheadLimit {
+ panic(&lookaheadLimitError{
+ message: fmt.Sprintf("error recovery token lookahead limit exceeded: %d", lc.errorRecoveryTokenLookaheadLimit),
+ })
+ }
+ lc.lookaheadAttempts++
+ return lc.Parser.Consume()
+}
+
+func (rl *recoveryLimitErrorStrategy) Recover(recognizer antlr.Parser, e antlr.RecognitionException) {
+ rl.checkAttempts(recognizer)
+ lc := &lookaheadConsumer{Parser: recognizer, errorRecoveryTokenLookaheadLimit: rl.errorRecoveryTokenLookaheadLimit}
+ rl.DefaultErrorStrategy.Recover(lc, e)
+}
+
+func (rl *recoveryLimitErrorStrategy) RecoverInline(recognizer antlr.Parser) antlr.Token {
+ rl.checkAttempts(recognizer)
+ lc := &lookaheadConsumer{Parser: recognizer, errorRecoveryTokenLookaheadLimit: rl.errorRecoveryTokenLookaheadLimit}
+ return rl.DefaultErrorStrategy.RecoverInline(lc)
+}
+
+func (rl *recoveryLimitErrorStrategy) checkAttempts(recognizer antlr.Parser) {
+ if rl.recoveryAttempts == rl.errorRecoveryLimit {
+ rl.recoveryAttempts++
+ msg := fmt.Sprintf("error recovery attempt limit exceeded: %d", rl.errorRecoveryLimit)
+ recognizer.NotifyErrorListeners(msg, nil, nil)
+ panic(&recoveryLimitError{
+ message: msg,
+ })
+ }
+ rl.recoveryAttempts++
+}
+
+var _ antlr.ErrorStrategy = &recoveryLimitErrorStrategy{}
+
+type parser struct {
+ gen.BaseCELVisitor
+ errors *parseErrors
+ helper *parserHelper
+ macros map[string]Macro
+ maxRecursionDepth int
+ errorRecoveryLimit int
+ errorRecoveryLookaheadTokenLimit int
+ populateMacroCalls bool
+}
+
+var (
+ _ gen.CELVisitor = (*parser)(nil)
+
+ lexerPool *sync.Pool = &sync.Pool{
+ New: func() interface{} {
+ l := gen.NewCELLexer(nil)
+ l.RemoveErrorListeners()
+ return l
+ },
+ }
+
+ parserPool *sync.Pool = &sync.Pool{
+ New: func() interface{} {
+ p := gen.NewCELParser(nil)
+ p.RemoveErrorListeners()
+ return p
+ },
+ }
+)
+
+func (p *parser) parse(expr runes.Buffer, desc string) *exprpb.Expr {
+ lexer := lexerPool.Get().(*gen.CELLexer)
+ prsr := parserPool.Get().(*gen.CELParser)
+
+ // Unfortunately ANTLR Go runtime is missing (*antlr.BaseParser).RemoveParseListeners, so this is
+ // good enough until that is exported.
+ prsrListener := &recursionListener{
+ maxDepth: p.maxRecursionDepth,
+ ruleTypeDepth: map[int]*int{},
+ }
+
+ defer func() {
+ // Reset the lexer and parser before putting them back in the pool.
+ lexer.RemoveErrorListeners()
+ prsr.RemoveParseListener(prsrListener)
+ prsr.RemoveErrorListeners()
+ lexer.SetInputStream(nil)
+ prsr.SetInputStream(nil)
+ lexerPool.Put(lexer)
+ parserPool.Put(prsr)
+ }()
+
+ lexer.SetInputStream(newCharStream(expr, desc))
+ prsr.SetInputStream(antlr.NewCommonTokenStream(lexer, 0))
+
+ lexer.AddErrorListener(p)
+ prsr.AddErrorListener(p)
+ prsr.AddParseListener(prsrListener)
+
+ prsr.SetErrorHandler(&recoveryLimitErrorStrategy{
+ DefaultErrorStrategy: antlr.NewDefaultErrorStrategy(),
+ errorRecoveryLimit: p.errorRecoveryLimit,
+ errorRecoveryTokenLookaheadLimit: p.errorRecoveryLookaheadTokenLimit,
+ })
+
+ defer func() {
+ if val := recover(); val != nil {
+ switch err := val.(type) {
+ case *lookaheadLimitError:
+ p.errors.ReportError(common.NoLocation, err.Error())
+ case *recursionError:
+ p.errors.ReportError(common.NoLocation, err.Error())
+ case *recoveryLimitError:
+ // do nothing, listeners already notified and error reported.
+ default:
+ panic(val)
+ }
+ }
+ }()
+
+ return p.Visit(prsr.Start()).(*exprpb.Expr)
+}
+
+// Visitor implementations.
+func (p *parser) Visit(tree antlr.ParseTree) interface{} {
+ switch tree.(type) {
+ case *gen.StartContext:
+ return p.VisitStart(tree.(*gen.StartContext))
+ case *gen.ExprContext:
+ return p.VisitExpr(tree.(*gen.ExprContext))
+ case *gen.ConditionalAndContext:
+ return p.VisitConditionalAnd(tree.(*gen.ConditionalAndContext))
+ case *gen.ConditionalOrContext:
+ return p.VisitConditionalOr(tree.(*gen.ConditionalOrContext))
+ case *gen.RelationContext:
+ return p.VisitRelation(tree.(*gen.RelationContext))
+ case *gen.CalcContext:
+ return p.VisitCalc(tree.(*gen.CalcContext))
+ case *gen.LogicalNotContext:
+ return p.VisitLogicalNot(tree.(*gen.LogicalNotContext))
+ case *gen.MemberExprContext:
+ return p.VisitMemberExpr(tree.(*gen.MemberExprContext))
+ case *gen.PrimaryExprContext:
+ return p.VisitPrimaryExpr(tree.(*gen.PrimaryExprContext))
+ case *gen.SelectOrCallContext:
+ return p.VisitSelectOrCall(tree.(*gen.SelectOrCallContext))
+ case *gen.MapInitializerListContext:
+ return p.VisitMapInitializerList(tree.(*gen.MapInitializerListContext))
+ case *gen.NegateContext:
+ return p.VisitNegate(tree.(*gen.NegateContext))
+ case *gen.IndexContext:
+ return p.VisitIndex(tree.(*gen.IndexContext))
+ case *gen.UnaryContext:
+ return p.VisitUnary(tree.(*gen.UnaryContext))
+ case *gen.CreateListContext:
+ return p.VisitCreateList(tree.(*gen.CreateListContext))
+ case *gen.CreateMessageContext:
+ return p.VisitCreateMessage(tree.(*gen.CreateMessageContext))
+ case *gen.CreateStructContext:
+ return p.VisitCreateStruct(tree.(*gen.CreateStructContext))
+ }
+
+ // Report at least one error if the parser reaches an unknown parse element.
+ // Typically, this happens if the parser has already encountered a syntax error elsewhere.
+ if len(p.errors.GetErrors()) == 0 {
+ txt := "<>"
+ if tree != nil {
+ txt = fmt.Sprintf("<<%T>>", tree)
+ }
+ return p.reportError(common.NoLocation, "unknown parse element encountered: %s", txt)
+ }
+ return p.helper.newExpr(common.NoLocation)
+
+}
+
+// Visit a parse tree produced by CELParser#start.
+func (p *parser) VisitStart(ctx *gen.StartContext) interface{} {
+ return p.Visit(ctx.Expr())
+}
+
+// Visit a parse tree produced by CELParser#expr.
+func (p *parser) VisitExpr(ctx *gen.ExprContext) interface{} {
+ result := p.Visit(ctx.GetE()).(*exprpb.Expr)
+ if ctx.GetOp() == nil {
+ return result
+ }
+ opID := p.helper.id(ctx.GetOp())
+ ifTrue := p.Visit(ctx.GetE1()).(*exprpb.Expr)
+ ifFalse := p.Visit(ctx.GetE2()).(*exprpb.Expr)
+ return p.globalCallOrMacro(opID, operators.Conditional, result, ifTrue, ifFalse)
+}
+
+// Visit a parse tree produced by CELParser#conditionalOr.
+func (p *parser) VisitConditionalOr(ctx *gen.ConditionalOrContext) interface{} {
+ result := p.Visit(ctx.GetE()).(*exprpb.Expr)
+ if ctx.GetOps() == nil {
+ return result
+ }
+ b := newBalancer(p.helper, operators.LogicalOr, result)
+ rest := ctx.GetE1()
+ for i, op := range ctx.GetOps() {
+ if i >= len(rest) {
+ return p.reportError(ctx, "unexpected character, wanted '||'")
+ }
+ next := p.Visit(rest[i]).(*exprpb.Expr)
+ opID := p.helper.id(op)
+ b.addTerm(opID, next)
+ }
+ return b.balance()
+}
+
+// Visit a parse tree produced by CELParser#conditionalAnd.
+func (p *parser) VisitConditionalAnd(ctx *gen.ConditionalAndContext) interface{} {
+ result := p.Visit(ctx.GetE()).(*exprpb.Expr)
+ if ctx.GetOps() == nil {
+ return result
+ }
+ b := newBalancer(p.helper, operators.LogicalAnd, result)
+ rest := ctx.GetE1()
+ for i, op := range ctx.GetOps() {
+ if i >= len(rest) {
+ return p.reportError(ctx, "unexpected character, wanted '&&'")
+ }
+ next := p.Visit(rest[i]).(*exprpb.Expr)
+ opID := p.helper.id(op)
+ b.addTerm(opID, next)
+ }
+ return b.balance()
+}
+
+// Visit a parse tree produced by CELParser#relation.
+func (p *parser) VisitRelation(ctx *gen.RelationContext) interface{} {
+ if ctx.Calc() != nil {
+ return p.Visit(ctx.Calc())
+ }
+ opText := ""
+ if ctx.GetOp() != nil {
+ opText = ctx.GetOp().GetText()
+ }
+ if op, found := operators.Find(opText); found {
+ lhs := p.Visit(ctx.Relation(0)).(*exprpb.Expr)
+ opID := p.helper.id(ctx.GetOp())
+ rhs := p.Visit(ctx.Relation(1)).(*exprpb.Expr)
+ return p.globalCallOrMacro(opID, op, lhs, rhs)
+ }
+ return p.reportError(ctx, "operator not found")
+}
+
+// Visit a parse tree produced by CELParser#calc.
+func (p *parser) VisitCalc(ctx *gen.CalcContext) interface{} {
+ if ctx.Unary() != nil {
+ return p.Visit(ctx.Unary())
+ }
+ opText := ""
+ if ctx.GetOp() != nil {
+ opText = ctx.GetOp().GetText()
+ }
+ if op, found := operators.Find(opText); found {
+ lhs := p.Visit(ctx.Calc(0)).(*exprpb.Expr)
+ opID := p.helper.id(ctx.GetOp())
+ rhs := p.Visit(ctx.Calc(1)).(*exprpb.Expr)
+ return p.globalCallOrMacro(opID, op, lhs, rhs)
+ }
+ return p.reportError(ctx, "operator not found")
+}
+
+func (p *parser) VisitUnary(ctx *gen.UnaryContext) interface{} {
+ return p.helper.newLiteralString(ctx, "<>")
+}
+
+// Visit a parse tree produced by CELParser#MemberExpr.
+func (p *parser) VisitMemberExpr(ctx *gen.MemberExprContext) interface{} {
+ switch ctx.Member().(type) {
+ case *gen.PrimaryExprContext:
+ return p.VisitPrimaryExpr(ctx.Member().(*gen.PrimaryExprContext))
+ case *gen.SelectOrCallContext:
+ return p.VisitSelectOrCall(ctx.Member().(*gen.SelectOrCallContext))
+ case *gen.IndexContext:
+ return p.VisitIndex(ctx.Member().(*gen.IndexContext))
+ case *gen.CreateMessageContext:
+ return p.VisitCreateMessage(ctx.Member().(*gen.CreateMessageContext))
+ }
+ return p.reportError(ctx, "unsupported simple expression")
+}
+
+// Visit a parse tree produced by CELParser#LogicalNot.
+func (p *parser) VisitLogicalNot(ctx *gen.LogicalNotContext) interface{} {
+ if len(ctx.GetOps())%2 == 0 {
+ return p.Visit(ctx.Member())
+ }
+ opID := p.helper.id(ctx.GetOps()[0])
+ target := p.Visit(ctx.Member()).(*exprpb.Expr)
+ return p.globalCallOrMacro(opID, operators.LogicalNot, target)
+}
+
+func (p *parser) VisitNegate(ctx *gen.NegateContext) interface{} {
+ if len(ctx.GetOps())%2 == 0 {
+ return p.Visit(ctx.Member())
+ }
+ opID := p.helper.id(ctx.GetOps()[0])
+ target := p.Visit(ctx.Member()).(*exprpb.Expr)
+ return p.globalCallOrMacro(opID, operators.Negate, target)
+}
+
+// Visit a parse tree produced by CELParser#SelectOrCall.
+func (p *parser) VisitSelectOrCall(ctx *gen.SelectOrCallContext) interface{} {
+ operand := p.Visit(ctx.Member()).(*exprpb.Expr)
+ // Handle the error case where no valid identifier is specified.
+ if ctx.GetId() == nil {
+ return p.helper.newExpr(ctx)
+ }
+ id := ctx.GetId().GetText()
+ if ctx.GetOpen() != nil {
+ opID := p.helper.id(ctx.GetOpen())
+ return p.receiverCallOrMacro(opID, id, operand, p.visitList(ctx.GetArgs())...)
+ }
+ return p.helper.newSelect(ctx.GetOp(), operand, id)
+}
+
+// Visit a parse tree produced by CELParser#PrimaryExpr.
+func (p *parser) VisitPrimaryExpr(ctx *gen.PrimaryExprContext) interface{} {
+ switch ctx.Primary().(type) {
+ case *gen.NestedContext:
+ return p.VisitNested(ctx.Primary().(*gen.NestedContext))
+ case *gen.IdentOrGlobalCallContext:
+ return p.VisitIdentOrGlobalCall(ctx.Primary().(*gen.IdentOrGlobalCallContext))
+ case *gen.CreateListContext:
+ return p.VisitCreateList(ctx.Primary().(*gen.CreateListContext))
+ case *gen.CreateStructContext:
+ return p.VisitCreateStruct(ctx.Primary().(*gen.CreateStructContext))
+ case *gen.ConstantLiteralContext:
+ return p.VisitConstantLiteral(ctx.Primary().(*gen.ConstantLiteralContext))
+ }
+
+ return p.reportError(ctx, "invalid primary expression")
+}
+
+// Visit a parse tree produced by CELParser#Index.
+func (p *parser) VisitIndex(ctx *gen.IndexContext) interface{} {
+ target := p.Visit(ctx.Member()).(*exprpb.Expr)
+ opID := p.helper.id(ctx.GetOp())
+ index := p.Visit(ctx.GetIndex()).(*exprpb.Expr)
+ return p.globalCallOrMacro(opID, operators.Index, target, index)
+}
+
+// Visit a parse tree produced by CELParser#CreateMessage.
+func (p *parser) VisitCreateMessage(ctx *gen.CreateMessageContext) interface{} {
+ target := p.Visit(ctx.Member()).(*exprpb.Expr)
+ objID := p.helper.id(ctx.GetOp())
+ if messageName, found := p.extractQualifiedName(target); found {
+ entries := p.VisitIFieldInitializerList(ctx.GetEntries()).([]*exprpb.Expr_CreateStruct_Entry)
+ return p.helper.newObject(objID, messageName, entries...)
+ }
+ return p.helper.newExpr(objID)
+}
+
+// Visit a parse tree of field initializers.
+func (p *parser) VisitIFieldInitializerList(ctx gen.IFieldInitializerListContext) interface{} {
+ if ctx == nil || ctx.GetFields() == nil {
+ // This is the result of a syntax error handled elswhere, return empty.
+ return []*exprpb.Expr_CreateStruct_Entry{}
+ }
+
+ result := make([]*exprpb.Expr_CreateStruct_Entry, len(ctx.GetFields()))
+ cols := ctx.GetCols()
+ vals := ctx.GetValues()
+ for i, f := range ctx.GetFields() {
+ if i >= len(cols) || i >= len(vals) {
+ // This is the result of a syntax error detected elsewhere.
+ return []*exprpb.Expr_CreateStruct_Entry{}
+ }
+ initID := p.helper.id(cols[i])
+ value := p.Visit(vals[i]).(*exprpb.Expr)
+ field := p.helper.newObjectField(initID, f.GetText(), value)
+ result[i] = field
+ }
+ return result
+}
+
+// Visit a parse tree produced by CELParser#IdentOrGlobalCall.
+func (p *parser) VisitIdentOrGlobalCall(ctx *gen.IdentOrGlobalCallContext) interface{} {
+ identName := ""
+ if ctx.GetLeadingDot() != nil {
+ identName = "."
+ }
+ // Handle the error case where no valid identifier is specified.
+ if ctx.GetId() == nil {
+ return p.helper.newExpr(ctx)
+ }
+ // Handle reserved identifiers.
+ id := ctx.GetId().GetText()
+ if _, ok := reservedIds[id]; ok {
+ return p.reportError(ctx, "reserved identifier: %s", id)
+ }
+ identName += id
+ if ctx.GetOp() != nil {
+ opID := p.helper.id(ctx.GetOp())
+ return p.globalCallOrMacro(opID, identName, p.visitList(ctx.GetArgs())...)
+ }
+ return p.helper.newIdent(ctx.GetId(), identName)
+}
+
+// Visit a parse tree produced by CELParser#Nested.
+func (p *parser) VisitNested(ctx *gen.NestedContext) interface{} {
+ return p.Visit(ctx.GetE())
+}
+
+// Visit a parse tree produced by CELParser#CreateList.
+func (p *parser) VisitCreateList(ctx *gen.CreateListContext) interface{} {
+ listID := p.helper.id(ctx.GetOp())
+ return p.helper.newList(listID, p.visitList(ctx.GetElems())...)
+}
+
+// Visit a parse tree produced by CELParser#CreateStruct.
+func (p *parser) VisitCreateStruct(ctx *gen.CreateStructContext) interface{} {
+ structID := p.helper.id(ctx.GetOp())
+ entries := []*exprpb.Expr_CreateStruct_Entry{}
+ if ctx.GetEntries() != nil {
+ entries = p.Visit(ctx.GetEntries()).([]*exprpb.Expr_CreateStruct_Entry)
+ }
+ return p.helper.newMap(structID, entries...)
+}
+
+// Visit a parse tree produced by CELParser#ConstantLiteral.
+func (p *parser) VisitConstantLiteral(ctx *gen.ConstantLiteralContext) interface{} {
+ switch ctx.Literal().(type) {
+ case *gen.IntContext:
+ return p.VisitInt(ctx.Literal().(*gen.IntContext))
+ case *gen.UintContext:
+ return p.VisitUint(ctx.Literal().(*gen.UintContext))
+ case *gen.DoubleContext:
+ return p.VisitDouble(ctx.Literal().(*gen.DoubleContext))
+ case *gen.StringContext:
+ return p.VisitString(ctx.Literal().(*gen.StringContext))
+ case *gen.BytesContext:
+ return p.VisitBytes(ctx.Literal().(*gen.BytesContext))
+ case *gen.BoolFalseContext:
+ return p.VisitBoolFalse(ctx.Literal().(*gen.BoolFalseContext))
+ case *gen.BoolTrueContext:
+ return p.VisitBoolTrue(ctx.Literal().(*gen.BoolTrueContext))
+ case *gen.NullContext:
+ return p.VisitNull(ctx.Literal().(*gen.NullContext))
+ }
+ return p.reportError(ctx, "invalid literal")
+}
+
+// Visit a parse tree produced by CELParser#mapInitializerList.
+func (p *parser) VisitMapInitializerList(ctx *gen.MapInitializerListContext) interface{} {
+ if ctx == nil || ctx.GetKeys() == nil {
+ // This is the result of a syntax error handled elswhere, return empty.
+ return []*exprpb.Expr_CreateStruct_Entry{}
+ }
+
+ result := make([]*exprpb.Expr_CreateStruct_Entry, len(ctx.GetCols()))
+ keys := ctx.GetKeys()
+ vals := ctx.GetValues()
+ for i, col := range ctx.GetCols() {
+ colID := p.helper.id(col)
+ if i >= len(keys) || i >= len(vals) {
+ // This is the result of a syntax error detected elsewhere.
+ return []*exprpb.Expr_CreateStruct_Entry{}
+ }
+ key := p.Visit(keys[i]).(*exprpb.Expr)
+ value := p.Visit(vals[i]).(*exprpb.Expr)
+ entry := p.helper.newMapEntry(colID, key, value)
+ result[i] = entry
+ }
+ return result
+}
+
+// Visit a parse tree produced by CELParser#Int.
+func (p *parser) VisitInt(ctx *gen.IntContext) interface{} {
+ text := ctx.GetTok().GetText()
+ base := 10
+ if strings.HasPrefix(text, "0x") {
+ base = 16
+ text = text[2:]
+ }
+ if ctx.GetSign() != nil {
+ text = ctx.GetSign().GetText() + text
+ }
+ i, err := strconv.ParseInt(text, base, 64)
+ if err != nil {
+ return p.reportError(ctx, "invalid int literal")
+ }
+ return p.helper.newLiteralInt(ctx, i)
+}
+
+// Visit a parse tree produced by CELParser#Uint.
+func (p *parser) VisitUint(ctx *gen.UintContext) interface{} {
+ text := ctx.GetTok().GetText()
+ // trim the 'u' designator included in the uint literal.
+ text = text[:len(text)-1]
+ base := 10
+ if strings.HasPrefix(text, "0x") {
+ base = 16
+ text = text[2:]
+ }
+ i, err := strconv.ParseUint(text, base, 64)
+ if err != nil {
+ return p.reportError(ctx, "invalid uint literal")
+ }
+ return p.helper.newLiteralUint(ctx, i)
+}
+
+// Visit a parse tree produced by CELParser#Double.
+func (p *parser) VisitDouble(ctx *gen.DoubleContext) interface{} {
+ txt := ctx.GetTok().GetText()
+ if ctx.GetSign() != nil {
+ txt = ctx.GetSign().GetText() + txt
+ }
+ f, err := strconv.ParseFloat(txt, 64)
+ if err != nil {
+ return p.reportError(ctx, "invalid double literal")
+ }
+ return p.helper.newLiteralDouble(ctx, f)
+
+}
+
+// Visit a parse tree produced by CELParser#String.
+func (p *parser) VisitString(ctx *gen.StringContext) interface{} {
+ s := p.unquote(ctx, ctx.GetText(), false)
+ return p.helper.newLiteralString(ctx, s)
+}
+
+// Visit a parse tree produced by CELParser#Bytes.
+func (p *parser) VisitBytes(ctx *gen.BytesContext) interface{} {
+ b := []byte(p.unquote(ctx, ctx.GetTok().GetText()[1:], true))
+ return p.helper.newLiteralBytes(ctx, b)
+}
+
+// Visit a parse tree produced by CELParser#BoolTrue.
+func (p *parser) VisitBoolTrue(ctx *gen.BoolTrueContext) interface{} {
+ return p.helper.newLiteralBool(ctx, true)
+}
+
+// Visit a parse tree produced by CELParser#BoolFalse.
+func (p *parser) VisitBoolFalse(ctx *gen.BoolFalseContext) interface{} {
+ return p.helper.newLiteralBool(ctx, false)
+}
+
+// Visit a parse tree produced by CELParser#Null.
+func (p *parser) VisitNull(ctx *gen.NullContext) interface{} {
+ return p.helper.newLiteral(ctx,
+ &exprpb.Constant{
+ ConstantKind: &exprpb.Constant_NullValue{
+ NullValue: structpb.NullValue_NULL_VALUE}})
+}
+
+func (p *parser) visitList(ctx gen.IExprListContext) []*exprpb.Expr {
+ if ctx == nil {
+ return []*exprpb.Expr{}
+ }
+ return p.visitSlice(ctx.GetE())
+}
+
+func (p *parser) visitSlice(expressions []gen.IExprContext) []*exprpb.Expr {
+ if expressions == nil {
+ return []*exprpb.Expr{}
+ }
+ result := make([]*exprpb.Expr, len(expressions))
+ for i, e := range expressions {
+ ex := p.Visit(e).(*exprpb.Expr)
+ result[i] = ex
+ }
+ return result
+}
+
+func (p *parser) extractQualifiedName(e *exprpb.Expr) (string, bool) {
+ if e == nil {
+ return "", false
+ }
+ switch e.ExprKind.(type) {
+ case *exprpb.Expr_IdentExpr:
+ return e.GetIdentExpr().GetName(), true
+ case *exprpb.Expr_SelectExpr:
+ s := e.GetSelectExpr()
+ if prefix, found := p.extractQualifiedName(s.Operand); found {
+ return prefix + "." + s.Field, true
+ }
+ }
+ // TODO: Add a method to Source to get location from character offset.
+ location := p.helper.getLocation(e.GetId())
+ p.reportError(location, "expected a qualified name")
+ return "", false
+}
+
+func (p *parser) unquote(ctx interface{}, value string, isBytes bool) string {
+ text, err := unescape(value, isBytes)
+ if err != nil {
+ p.reportError(ctx, "%s", err.Error())
+ return value
+ }
+ return text
+}
+
+func (p *parser) reportError(ctx interface{}, format string, args ...interface{}) *exprpb.Expr {
+ var location common.Location
+ switch ctx.(type) {
+ case common.Location:
+ location = ctx.(common.Location)
+ case antlr.Token, antlr.ParserRuleContext:
+ err := p.helper.newExpr(ctx)
+ location = p.helper.getLocation(err.GetId())
+ }
+ err := p.helper.newExpr(ctx)
+ // Provide arguments to the report error.
+ p.errors.ReportError(location, format, args...)
+ return err
+}
+
+// ANTLR Parse listener implementations
+func (p *parser) SyntaxError(recognizer antlr.Recognizer, offendingSymbol interface{}, line, column int, msg string, e antlr.RecognitionException) {
+ // TODO: Snippet
+ l := p.helper.source.NewLocation(line, column)
+ p.errors.syntaxError(l, msg)
+}
+
+func (p *parser) ReportAmbiguity(recognizer antlr.Parser, dfa *antlr.DFA, startIndex, stopIndex int, exact bool, ambigAlts *antlr.BitSet, configs antlr.ATNConfigSet) {
+ // Intentional
+}
+
+func (p *parser) ReportAttemptingFullContext(recognizer antlr.Parser, dfa *antlr.DFA, startIndex, stopIndex int, conflictingAlts *antlr.BitSet, configs antlr.ATNConfigSet) {
+ // Intentional
+}
+
+func (p *parser) ReportContextSensitivity(recognizer antlr.Parser, dfa *antlr.DFA, startIndex, stopIndex, prediction int, configs antlr.ATNConfigSet) {
+ // Intentional
+}
+
+func (p *parser) globalCallOrMacro(exprID int64, function string, args ...*exprpb.Expr) *exprpb.Expr {
+ if expr, found := p.expandMacro(exprID, function, nil, args...); found {
+ return expr
+ }
+ return p.helper.newGlobalCall(exprID, function, args...)
+}
+
+func (p *parser) receiverCallOrMacro(exprID int64, function string, target *exprpb.Expr, args ...*exprpb.Expr) *exprpb.Expr {
+ if expr, found := p.expandMacro(exprID, function, target, args...); found {
+ return expr
+ }
+ return p.helper.newReceiverCall(exprID, function, target, args...)
+}
+
+func (p *parser) expandMacro(exprID int64, function string, target *exprpb.Expr, args ...*exprpb.Expr) (*exprpb.Expr, bool) {
+ macro, found := p.macros[makeMacroKey(function, len(args), target != nil)]
+ if !found {
+ macro, found = p.macros[makeVarArgMacroKey(function, target != nil)]
+ if !found {
+ return nil, false
+ }
+ }
+ eh := exprHelperPool.Get().(*exprHelper)
+ defer exprHelperPool.Put(eh)
+ eh.parserHelper = p.helper
+ eh.id = exprID
+ expr, err := macro.Expander()(eh, target, args)
+ if err != nil {
+ if err.Location != nil {
+ return p.reportError(err.Location, err.Message), true
+ }
+ return p.reportError(p.helper.getLocation(exprID), err.Message), true
+ }
+ if p.populateMacroCalls {
+ p.helper.addMacroCall(expr.GetId(), function, target, args...)
+ }
+ return expr, true
+}
diff --git a/vendor/github.com/google/cel-go/parser/unescape.go b/vendor/github.com/google/cel-go/parser/unescape.go
new file mode 100644
index 0000000000..27c57a9f3a
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/unescape.go
@@ -0,0 +1,237 @@
+// Copyright 2018 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package parser
+
+import (
+ "fmt"
+ "strings"
+ "unicode/utf8"
+)
+
+// Unescape takes a quoted string, unquotes, and unescapes it.
+//
+// This function performs escaping compatible with GoogleSQL.
+func unescape(value string, isBytes bool) (string, error) {
+ // All strings normalize newlines to the \n representation.
+ value = newlineNormalizer.Replace(value)
+ n := len(value)
+
+ // Nothing to unescape / decode.
+ if n < 2 {
+ return value, fmt.Errorf("unable to unescape string")
+ }
+
+ // Raw string preceded by the 'r|R' prefix.
+ isRawLiteral := false
+ if value[0] == 'r' || value[0] == 'R' {
+ value = value[1:]
+ n = len(value)
+ isRawLiteral = true
+ }
+
+ // Quoted string of some form, must have same first and last char.
+ if value[0] != value[n-1] || (value[0] != '"' && value[0] != '\'') {
+ return value, fmt.Errorf("unable to unescape string")
+ }
+
+ // Normalize the multi-line CEL string representation to a standard
+ // Go quoted string.
+ if n >= 6 {
+ if strings.HasPrefix(value, "'''") {
+ if !strings.HasSuffix(value, "'''") {
+ return value, fmt.Errorf("unable to unescape string")
+ }
+ value = "\"" + value[3:n-3] + "\""
+ } else if strings.HasPrefix(value, `"""`) {
+ if !strings.HasSuffix(value, `"""`) {
+ return value, fmt.Errorf("unable to unescape string")
+ }
+ value = "\"" + value[3:n-3] + "\""
+ }
+ n = len(value)
+ }
+ value = value[1 : n-1]
+ // If there is nothing to escape, then return.
+ if isRawLiteral || !strings.ContainsRune(value, '\\') {
+ return value, nil
+ }
+
+ // Otherwise the string contains escape characters.
+ // The following logic is adapted from `strconv/quote.go`
+ var runeTmp [utf8.UTFMax]byte
+ buf := make([]byte, 0, 3*n/2)
+ for len(value) > 0 {
+ c, encode, rest, err := unescapeChar(value, isBytes)
+ if err != nil {
+ return "", err
+ }
+ value = rest
+ if c < utf8.RuneSelf || !encode {
+ buf = append(buf, byte(c))
+ } else {
+ n := utf8.EncodeRune(runeTmp[:], c)
+ buf = append(buf, runeTmp[:n]...)
+ }
+ }
+ return string(buf), nil
+}
+
+// unescapeChar takes a string input and returns the following info:
+//
+// value - the escaped unicode rune at the front of the string.
+// encode - the value should be unicode-encoded
+// tail - the remainder of the input string.
+// err - error value, if the character could not be unescaped.
+//
+// When encode is true the return value may still fit within a single byte,
+// but unicode encoding is attempted which is more expensive than when the
+// value is known to self-represent as a single byte.
+//
+// If isBytes is set, unescape as a bytes literal so octal and hex escapes
+// represent byte values, not unicode code points.
+func unescapeChar(s string, isBytes bool) (value rune, encode bool, tail string, err error) {
+ // 1. Character is not an escape sequence.
+ switch c := s[0]; {
+ case c >= utf8.RuneSelf:
+ r, size := utf8.DecodeRuneInString(s)
+ return r, true, s[size:], nil
+ case c != '\\':
+ return rune(s[0]), false, s[1:], nil
+ }
+
+ // 2. Last character is the start of an escape sequence.
+ if len(s) <= 1 {
+ err = fmt.Errorf("unable to unescape string, found '\\' as last character")
+ return
+ }
+
+ c := s[1]
+ s = s[2:]
+ // 3. Common escape sequences shared with Google SQL
+ switch c {
+ case 'a':
+ value = '\a'
+ case 'b':
+ value = '\b'
+ case 'f':
+ value = '\f'
+ case 'n':
+ value = '\n'
+ case 'r':
+ value = '\r'
+ case 't':
+ value = '\t'
+ case 'v':
+ value = '\v'
+ case '\\':
+ value = '\\'
+ case '\'':
+ value = '\''
+ case '"':
+ value = '"'
+ case '`':
+ value = '`'
+ case '?':
+ value = '?'
+
+ // 4. Unicode escape sequences, reproduced from `strconv/quote.go`
+ case 'x', 'X', 'u', 'U':
+ n := 0
+ encode = true
+ switch c {
+ case 'x', 'X':
+ n = 2
+ encode = !isBytes
+ case 'u':
+ n = 4
+ if isBytes {
+ err = fmt.Errorf("unable to unescape string")
+ return
+ }
+ case 'U':
+ n = 8
+ if isBytes {
+ err = fmt.Errorf("unable to unescape string")
+ return
+ }
+ }
+ var v rune
+ if len(s) < n {
+ err = fmt.Errorf("unable to unescape string")
+ return
+ }
+ for j := 0; j < n; j++ {
+ x, ok := unhex(s[j])
+ if !ok {
+ err = fmt.Errorf("unable to unescape string")
+ return
+ }
+ v = v<<4 | x
+ }
+ s = s[n:]
+ if !isBytes && v > utf8.MaxRune {
+ err = fmt.Errorf("unable to unescape string")
+ return
+ }
+ value = v
+
+ // 5. Octal escape sequences, must be three digits \[0-3][0-7][0-7]
+ case '0', '1', '2', '3':
+ if len(s) < 2 {
+ err = fmt.Errorf("unable to unescape octal sequence in string")
+ return
+ }
+ v := rune(c - '0')
+ for j := 0; j < 2; j++ {
+ x := s[j]
+ if x < '0' || x > '7' {
+ err = fmt.Errorf("unable to unescape octal sequence in string")
+ return
+ }
+ v = v*8 + rune(x-'0')
+ }
+ if !isBytes && v > utf8.MaxRune {
+ err = fmt.Errorf("unable to unescape string")
+ return
+ }
+ value = v
+ s = s[2:]
+ encode = !isBytes
+
+ // Unknown escape sequence.
+ default:
+ err = fmt.Errorf("unable to unescape string")
+ }
+
+ tail = s
+ return
+}
+
+func unhex(b byte) (rune, bool) {
+ c := rune(b)
+ switch {
+ case '0' <= c && c <= '9':
+ return c - '0', true
+ case 'a' <= c && c <= 'f':
+ return c - 'a' + 10, true
+ case 'A' <= c && c <= 'F':
+ return c - 'A' + 10, true
+ }
+ return 0, false
+}
+
+var (
+ newlineNormalizer = strings.NewReplacer("\r\n", "\n", "\r", "\n")
+)
diff --git a/vendor/github.com/google/cel-go/parser/unparser.go b/vendor/github.com/google/cel-go/parser/unparser.go
new file mode 100644
index 0000000000..6a610ff76a
--- /dev/null
+++ b/vendor/github.com/google/cel-go/parser/unparser.go
@@ -0,0 +1,446 @@
+// Copyright 2019 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package parser
+
+import (
+ "errors"
+ "fmt"
+ "strconv"
+ "strings"
+
+ "github.com/google/cel-go/common/operators"
+
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+)
+
+// Unparse takes an input expression and source position information and generates a human-readable
+// expression.
+//
+// Note, unparsing an AST will often generate the same expression as was originally parsed, but some
+// formatting may be lost in translation, notably:
+//
+// - All quoted literals are doubled quoted.
+// - Byte literals are represented as octal escapes (same as Google SQL).
+// - Floating point values are converted to the small number of digits needed to represent the value.
+// - Spacing around punctuation marks may be lost.
+// - Parentheses will only be applied when they affect operator precedence.
+func Unparse(expr *exprpb.Expr, info *exprpb.SourceInfo) (string, error) {
+ un := &unparser{info: info}
+ err := un.visit(expr)
+ if err != nil {
+ return "", err
+ }
+ return un.str.String(), nil
+}
+
+// unparser visits an expression to reconstruct a human-readable string from an AST.
+type unparser struct {
+ str strings.Builder
+ info *exprpb.SourceInfo
+}
+
+func (un *unparser) visit(expr *exprpb.Expr) error {
+ if expr == nil {
+ return errors.New("unsupported expression")
+ }
+ visited, err := un.visitMaybeMacroCall(expr)
+ if visited || err != nil {
+ return err
+ }
+ switch expr.ExprKind.(type) {
+ case *exprpb.Expr_CallExpr:
+ return un.visitCall(expr)
+ case *exprpb.Expr_ConstExpr:
+ return un.visitConst(expr)
+ case *exprpb.Expr_IdentExpr:
+ return un.visitIdent(expr)
+ case *exprpb.Expr_ListExpr:
+ return un.visitList(expr)
+ case *exprpb.Expr_SelectExpr:
+ return un.visitSelect(expr)
+ case *exprpb.Expr_StructExpr:
+ return un.visitStruct(expr)
+ default:
+ return fmt.Errorf("unsupported expression: %v", expr)
+ }
+}
+
+func (un *unparser) visitCall(expr *exprpb.Expr) error {
+ c := expr.GetCallExpr()
+ fun := c.GetFunction()
+ switch fun {
+ // ternary operator
+ case operators.Conditional:
+ return un.visitCallConditional(expr)
+ // index operator
+ case operators.Index:
+ return un.visitCallIndex(expr)
+ // unary operators
+ case operators.LogicalNot, operators.Negate:
+ return un.visitCallUnary(expr)
+ // binary operators
+ case operators.Add,
+ operators.Divide,
+ operators.Equals,
+ operators.Greater,
+ operators.GreaterEquals,
+ operators.In,
+ operators.Less,
+ operators.LessEquals,
+ operators.LogicalAnd,
+ operators.LogicalOr,
+ operators.Modulo,
+ operators.Multiply,
+ operators.NotEquals,
+ operators.OldIn,
+ operators.Subtract:
+ return un.visitCallBinary(expr)
+ // standard function calls.
+ default:
+ return un.visitCallFunc(expr)
+ }
+}
+
+func (un *unparser) visitCallBinary(expr *exprpb.Expr) error {
+ c := expr.GetCallExpr()
+ fun := c.GetFunction()
+ args := c.GetArgs()
+ lhs := args[0]
+ // add parens if the current operator is lower precedence than the lhs expr operator.
+ lhsParen := isComplexOperatorWithRespectTo(fun, lhs)
+ rhs := args[1]
+ // add parens if the current operator is lower precedence than the rhs expr operator,
+ // or the same precedence and the operator is left recursive.
+ rhsParen := isComplexOperatorWithRespectTo(fun, rhs)
+ if !rhsParen && isLeftRecursive(fun) {
+ rhsParen = isSamePrecedence(fun, rhs)
+ }
+ err := un.visitMaybeNested(lhs, lhsParen)
+ if err != nil {
+ return err
+ }
+ unmangled, found := operators.FindReverseBinaryOperator(fun)
+ if !found {
+ return fmt.Errorf("cannot unmangle operator: %s", fun)
+ }
+ un.str.WriteString(" ")
+ un.str.WriteString(unmangled)
+ un.str.WriteString(" ")
+ return un.visitMaybeNested(rhs, rhsParen)
+}
+
+func (un *unparser) visitCallConditional(expr *exprpb.Expr) error {
+ c := expr.GetCallExpr()
+ args := c.GetArgs()
+ // add parens if operand is a conditional itself.
+ nested := isSamePrecedence(operators.Conditional, args[0]) ||
+ isComplexOperator(args[0])
+ err := un.visitMaybeNested(args[0], nested)
+ if err != nil {
+ return err
+ }
+ un.str.WriteString(" ? ")
+ // add parens if operand is a conditional itself.
+ nested = isSamePrecedence(operators.Conditional, args[1]) ||
+ isComplexOperator(args[1])
+ err = un.visitMaybeNested(args[1], nested)
+ if err != nil {
+ return err
+ }
+ un.str.WriteString(" : ")
+ // add parens if operand is a conditional itself.
+ nested = isSamePrecedence(operators.Conditional, args[2]) ||
+ isComplexOperator(args[2])
+
+ return un.visitMaybeNested(args[2], nested)
+}
+
+func (un *unparser) visitCallFunc(expr *exprpb.Expr) error {
+ c := expr.GetCallExpr()
+ fun := c.GetFunction()
+ args := c.GetArgs()
+ if c.GetTarget() != nil {
+ nested := isBinaryOrTernaryOperator(c.GetTarget())
+ err := un.visitMaybeNested(c.GetTarget(), nested)
+ if err != nil {
+ return err
+ }
+ un.str.WriteString(".")
+ }
+ un.str.WriteString(fun)
+ un.str.WriteString("(")
+ for i, arg := range args {
+ err := un.visit(arg)
+ if err != nil {
+ return err
+ }
+ if i < len(args)-1 {
+ un.str.WriteString(", ")
+ }
+ }
+ un.str.WriteString(")")
+ return nil
+}
+
+func (un *unparser) visitCallIndex(expr *exprpb.Expr) error {
+ c := expr.GetCallExpr()
+ args := c.GetArgs()
+ nested := isBinaryOrTernaryOperator(args[0])
+ err := un.visitMaybeNested(args[0], nested)
+ if err != nil {
+ return err
+ }
+ un.str.WriteString("[")
+ err = un.visit(args[1])
+ if err != nil {
+ return err
+ }
+ un.str.WriteString("]")
+ return nil
+}
+
+func (un *unparser) visitCallUnary(expr *exprpb.Expr) error {
+ c := expr.GetCallExpr()
+ fun := c.GetFunction()
+ args := c.GetArgs()
+ unmangled, found := operators.FindReverse(fun)
+ if !found {
+ return fmt.Errorf("cannot unmangle operator: %s", fun)
+ }
+ un.str.WriteString(unmangled)
+ nested := isComplexOperator(args[0])
+ return un.visitMaybeNested(args[0], nested)
+}
+
+func (un *unparser) visitConst(expr *exprpb.Expr) error {
+ c := expr.GetConstExpr()
+ switch c.ConstantKind.(type) {
+ case *exprpb.Constant_BoolValue:
+ un.str.WriteString(strconv.FormatBool(c.GetBoolValue()))
+ case *exprpb.Constant_BytesValue:
+ // bytes constants are surrounded with b""
+ b := c.GetBytesValue()
+ un.str.WriteString(`b"`)
+ un.str.WriteString(bytesToOctets(b))
+ un.str.WriteString(`"`)
+ case *exprpb.Constant_DoubleValue:
+ // represent the float using the minimum required digits
+ d := strconv.FormatFloat(c.GetDoubleValue(), 'g', -1, 64)
+ un.str.WriteString(d)
+ case *exprpb.Constant_Int64Value:
+ i := strconv.FormatInt(c.GetInt64Value(), 10)
+ un.str.WriteString(i)
+ case *exprpb.Constant_NullValue:
+ un.str.WriteString("null")
+ case *exprpb.Constant_StringValue:
+ // strings will be double quoted with quotes escaped.
+ un.str.WriteString(strconv.Quote(c.GetStringValue()))
+ case *exprpb.Constant_Uint64Value:
+ // uint literals have a 'u' suffix.
+ ui := strconv.FormatUint(c.GetUint64Value(), 10)
+ un.str.WriteString(ui)
+ un.str.WriteString("u")
+ default:
+ return fmt.Errorf("unsupported constant: %v", expr)
+ }
+ return nil
+}
+
+func (un *unparser) visitIdent(expr *exprpb.Expr) error {
+ un.str.WriteString(expr.GetIdentExpr().GetName())
+ return nil
+}
+
+func (un *unparser) visitList(expr *exprpb.Expr) error {
+ l := expr.GetListExpr()
+ elems := l.GetElements()
+ un.str.WriteString("[")
+ for i, elem := range elems {
+ err := un.visit(elem)
+ if err != nil {
+ return err
+ }
+ if i < len(elems)-1 {
+ un.str.WriteString(", ")
+ }
+ }
+ un.str.WriteString("]")
+ return nil
+}
+
+func (un *unparser) visitSelect(expr *exprpb.Expr) error {
+ sel := expr.GetSelectExpr()
+ // handle the case when the select expression was generated by the has() macro.
+ if sel.GetTestOnly() {
+ un.str.WriteString("has(")
+ }
+ nested := !sel.GetTestOnly() && isBinaryOrTernaryOperator(sel.GetOperand())
+ err := un.visitMaybeNested(sel.GetOperand(), nested)
+ if err != nil {
+ return err
+ }
+ un.str.WriteString(".")
+ un.str.WriteString(sel.GetField())
+ if sel.GetTestOnly() {
+ un.str.WriteString(")")
+ }
+ return nil
+}
+
+func (un *unparser) visitStruct(expr *exprpb.Expr) error {
+ s := expr.GetStructExpr()
+ // If the message name is non-empty, then this should be treated as message construction.
+ if s.GetMessageName() != "" {
+ return un.visitStructMsg(expr)
+ }
+ // Otherwise, build a map.
+ return un.visitStructMap(expr)
+}
+
+func (un *unparser) visitStructMsg(expr *exprpb.Expr) error {
+ m := expr.GetStructExpr()
+ entries := m.GetEntries()
+ un.str.WriteString(m.GetMessageName())
+ un.str.WriteString("{")
+ for i, entry := range entries {
+ f := entry.GetFieldKey()
+ un.str.WriteString(f)
+ un.str.WriteString(": ")
+ v := entry.GetValue()
+ err := un.visit(v)
+ if err != nil {
+ return err
+ }
+ if i < len(entries)-1 {
+ un.str.WriteString(", ")
+ }
+ }
+ un.str.WriteString("}")
+ return nil
+}
+
+func (un *unparser) visitStructMap(expr *exprpb.Expr) error {
+ m := expr.GetStructExpr()
+ entries := m.GetEntries()
+ un.str.WriteString("{")
+ for i, entry := range entries {
+ k := entry.GetMapKey()
+ err := un.visit(k)
+ if err != nil {
+ return err
+ }
+ un.str.WriteString(": ")
+ v := entry.GetValue()
+ err = un.visit(v)
+ if err != nil {
+ return err
+ }
+ if i < len(entries)-1 {
+ un.str.WriteString(", ")
+ }
+ }
+ un.str.WriteString("}")
+ return nil
+}
+
+func (un *unparser) visitMaybeMacroCall(expr *exprpb.Expr) (bool, error) {
+ macroCalls := un.info.GetMacroCalls()
+ call, found := macroCalls[expr.GetId()]
+ if !found {
+ return false, nil
+ }
+ return true, un.visit(call)
+}
+
+func (un *unparser) visitMaybeNested(expr *exprpb.Expr, nested bool) error {
+ if nested {
+ un.str.WriteString("(")
+ }
+ err := un.visit(expr)
+ if err != nil {
+ return err
+ }
+ if nested {
+ un.str.WriteString(")")
+ }
+ return nil
+}
+
+// isLeftRecursive indicates whether the parser resolves the call in a left-recursive manner as
+// this can have an effect of how parentheses affect the order of operations in the AST.
+func isLeftRecursive(op string) bool {
+ return op != operators.LogicalAnd && op != operators.LogicalOr
+}
+
+// isSamePrecedence indicates whether the precedence of the input operator is the same as the
+// precedence of the (possible) operation represented in the input Expr.
+//
+// If the expr is not a Call, the result is false.
+func isSamePrecedence(op string, expr *exprpb.Expr) bool {
+ if expr.GetCallExpr() == nil {
+ return false
+ }
+ c := expr.GetCallExpr()
+ other := c.GetFunction()
+ return operators.Precedence(op) == operators.Precedence(other)
+}
+
+// isLowerPrecedence indicates whether the precedence of the input operator is lower precedence
+// than the (possible) operation represented in the input Expr.
+//
+// If the expr is not a Call, the result is false.
+func isLowerPrecedence(op string, expr *exprpb.Expr) bool {
+ c := expr.GetCallExpr()
+ other := c.GetFunction()
+ return operators.Precedence(op) < operators.Precedence(other)
+}
+
+// Indicates whether the expr is a complex operator, i.e., a call expression
+// with 2 or more arguments.
+func isComplexOperator(expr *exprpb.Expr) bool {
+ if expr.GetCallExpr() != nil && len(expr.GetCallExpr().GetArgs()) >= 2 {
+ return true
+ }
+ return false
+}
+
+// Indicates whether it is a complex operation compared to another.
+// expr is *not* considered complex if it is not a call expression or has
+// less than two arguments, or if it has a higher precedence than op.
+func isComplexOperatorWithRespectTo(op string, expr *exprpb.Expr) bool {
+ if expr.GetCallExpr() == nil || len(expr.GetCallExpr().GetArgs()) < 2 {
+ return false
+ }
+ return isLowerPrecedence(op, expr)
+}
+
+// Indicate whether this is a binary or ternary operator.
+func isBinaryOrTernaryOperator(expr *exprpb.Expr) bool {
+ if expr.GetCallExpr() == nil || len(expr.GetCallExpr().GetArgs()) < 2 {
+ return false
+ }
+ _, isBinaryOp := operators.FindReverseBinaryOperator(expr.GetCallExpr().GetFunction())
+ return isBinaryOp || isSamePrecedence(operators.Conditional, expr)
+}
+
+// bytesToOctets converts byte sequences to a string using a three digit octal encoded value
+// per byte.
+func bytesToOctets(byteVal []byte) string {
+ var b strings.Builder
+ for _, c := range byteVal {
+ fmt.Fprintf(&b, "\\%03o", c)
+ }
+ return b.String()
+}
diff --git a/vendor/github.com/operator-framework/api/pkg/constraints/cel.go b/vendor/github.com/operator-framework/api/pkg/constraints/cel.go
new file mode 100644
index 0000000000..1fb10b5dd2
--- /dev/null
+++ b/vendor/github.com/operator-framework/api/pkg/constraints/cel.go
@@ -0,0 +1,135 @@
+package constraints
+
+import (
+ "fmt"
+
+ "github.com/google/cel-go/cel"
+ "github.com/google/cel-go/checker/decls"
+ "github.com/google/cel-go/common/types"
+ "github.com/google/cel-go/common/types/ref"
+ "github.com/google/cel-go/interpreter/functions"
+ exprpb "google.golang.org/genproto/googleapis/api/expr/v1alpha1"
+
+ "github.com/blang/semver/v4"
+)
+
+// PropertiesKey is the key for bundle properties map (input data for CEL evaluation)
+const PropertiesKey = "properties"
+
+// Cel is a struct representing CEL expression information
+type Cel struct {
+ // The CEL expression
+ Rule string `json:"rule" yaml:"rule"`
+}
+
+// NewCelEnvironment returns a CEL environment which can be used to
+// evaluate CEL expression and an error if occurs
+func NewCelEnvironment() *CelEnvironment {
+ env, err := cel.NewEnv(cel.Declarations(
+ decls.NewVar(PropertiesKey, decls.NewListType(decls.NewMapType(decls.String, decls.Any)))),
+ cel.Lib(semverLib{}),
+ )
+ // If an error occurs here, it means the CEL enviroment is unable to load
+ // configuration for custom libraries propertly. Hence, the CEL enviroment is
+ // unusable. Panic here will cause the program to fail immediately to prevent
+ // cascading failures later on when this CEL env is in use.
+ if err != nil {
+ panic(err)
+ }
+ return &CelEnvironment{
+ env: env,
+ }
+}
+
+// CelEnvironment is a struct that encapsulates CEL custom program enviroment
+type CelEnvironment struct {
+ env *cel.Env
+}
+
+// CelProgram is a struct that encapsulates compiled CEL program
+type CelProgram struct {
+ program cel.Program
+}
+
+/*
+This section of code is for custom library for semver comparison in CEL
+The code is inspired by https://github.com/google/cel-go/blob/master/cel/cel_test.go#L46
+
+The semver_compare is written based on `Compare` function in https://github.com/blang/semver
+particularly in https://github.com/blang/semver/blob/master/semver.go#L125
+
+Example:
+`semver_compare(v1, v2)` is equivalent of `v1.Compare(v2)` in blang/semver library
+
+The result is `semver_compare` is an integer just like `Compare`. So, the CEL
+expression `semver_compare(v1, v2) == 0` is equivalent v1.Compare(v2) == 0. In
+the other words, it checks if v1 is equal to v2 in term of semver comparision.
+*/
+type semverLib struct{}
+
+func (semverLib) CompileOptions() []cel.EnvOption {
+ return []cel.EnvOption{
+ cel.Declarations(
+ decls.NewFunction("semver_compare",
+ decls.NewOverload("semver_compare",
+ []*exprpb.Type{decls.Any, decls.Any},
+ decls.Int))),
+ }
+}
+
+func (semverLib) ProgramOptions() []cel.ProgramOption {
+ return []cel.ProgramOption{
+ cel.Functions(
+ &functions.Overload{
+ Operator: "semver_compare",
+ Binary: semverCompare,
+ },
+ ),
+ }
+}
+
+func semverCompare(val1, val2 ref.Val) ref.Val {
+ v1, err := semver.ParseTolerant(fmt.Sprint(val1.Value()))
+ if err != nil {
+ return types.ValOrErr(val1, "unable to parse '%v' to semver format", val1.Value())
+ }
+
+ v2, err := semver.ParseTolerant(fmt.Sprint(val2.Value()))
+ if err != nil {
+ return types.ValOrErr(val2, "unable to parse '%v' to semver format", val2.Value())
+ }
+ return types.Int(v1.Compare(v2))
+}
+
+// Evaluate to evaluate the compiled CEL program against input data (map)
+func (e CelProgram) Evaluate(data map[string]interface{}) (bool, error) {
+ result, _, err := e.program.Eval(data)
+ if err != nil {
+ return false, err
+ }
+
+ // we should have already ensured that this will be types.Bool during compilation
+ if b, ok := result.Value().(bool); ok {
+ return b, nil
+ }
+ return false, fmt.Errorf("cel expression evalutated to %T, not bool", result.Value())
+}
+
+// Validate to validate the CEL expression string by compiling it into CEL program
+func (e *CelEnvironment) Validate(rule string) (CelProgram, error) {
+ var celProg CelProgram
+ ast, issues := e.env.Compile(rule)
+ if err := issues.Err(); err != nil {
+ return celProg, err
+ }
+
+ if ast.ResultType() != decls.Bool {
+ return celProg, fmt.Errorf("cel expressions must have type Bool")
+ }
+
+ prog, err := e.env.Program(ast)
+ if err != nil {
+ return celProg, err
+ }
+ return CelProgram{program: prog}, nil
+}
diff --git a/vendor/github.com/operator-framework/api/pkg/constraints/constraint.go b/vendor/github.com/operator-framework/api/pkg/constraints/constraint.go
new file mode 100644
index 0000000000..d59d04542d
--- /dev/null
+++ b/vendor/github.com/operator-framework/api/pkg/constraints/constraint.go
@@ -0,0 +1,86 @@
+package constraints
+
+import (
+ "bytes"
+ "encoding/json"
+ "fmt"
+)
+
+// OLMConstraintType is the schema "type" key for all constraints known to OLM
+// (except for legacy types).
+const OLMConstraintType = "olm.constraint"
+
+// Constraint holds parsed, potentially nested dependency constraints.
+type Constraint struct {
+ // Constraint message that surfaces in resolution
+ // This field is optional
+ Message string `json:"message,omitempty" yaml:"message,omitempty"`
+
+ // The cel struct that contraints CEL expression
+ Cel *Cel `json:"cel,omitempty" yaml:"cel,omitempty"`
+
+ // Package defines a constraint for a package within a version range.
+ Package *PackageConstraint `json:"package,omitempty" yaml:"package,omitempty"`
+
+ // GVK defines a constraint for a GVK.
+ GVK *GVKConstraint `json:"gvk,omitempty" yaml:"gvk,omitempty"`
+
+ // All, Any, and None are compound constraints. See this enhancement for details:
+ // https://github.com/operator-framework/enhancements/blob/master/enhancements/compound-bundle-constraints.md
+ All *CompoundConstraint `json:"all,omitempty" yaml:"all,omitempty"`
+ Any *CompoundConstraint `json:"any,omitempty" yaml:"any,omitempty"`
+ // A note on None: this constraint is not particularly useful by itself.
+ // It should be used within an All constraint alongside some other constraint type
+ // since saying "none of these GVKs/packages/etc." without an alternative doesn't make sense.
+ None *CompoundConstraint `json:"none,omitempty" yaml:"none,omitempty"`
+}
+
+// CompoundConstraint holds a list of potentially nested constraints
+// over which a boolean operation is applied.
+type CompoundConstraint struct {
+ Constraints []Constraint `json:"constraints" yaml:"constraints"`
+}
+
+// GVKConstraint defines a GVK constraint.
+type GVKConstraint struct {
+ Group string `json:"group" yaml:"group"`
+ Kind string `json:"kind" yaml:"kind"`
+ Version string `json:"version" yaml:"version"`
+}
+
+// PackageConstraint defines a package constraint.
+type PackageConstraint struct {
+ // PackageName is the name of the package.
+ PackageName string `json:"packageName" yaml:"packageName"`
+ // VersionRange required for the package.
+ VersionRange string `json:"versionRange" yaml:"versionRange"`
+}
+
+// maxConstraintSize defines the maximum raw size in bytes of an olm.constraint.
+// 64Kb seems reasonable, since this number allows for long description strings
+// and either few deep nestings or shallow nestings and long constraints lists,
+// but not both.
+// QUESTION: make this configurable?
+const maxConstraintSize = 2 << 16
+
+// ErrMaxConstraintSizeExceeded is returned when a constraint's size > maxConstraintSize.
+var ErrMaxConstraintSizeExceeded = fmt.Errorf("olm.constraint value is greater than max constraint size %d bytes", maxConstraintSize)
+
+// Parse parses an olm.constraint property's value recursively into a Constraint.
+// Unknown value schemas result in an error. Constraints that exceed the number of bytes
+// defined by maxConstraintSize result results in an error.
+func Parse(v json.RawMessage) (c Constraint, err error) {
+ // There is no way to explicitly limit nesting depth.
+ // From https://github.com/golang/go/issues/31789#issuecomment-538134396,
+ // the recommended approach is to error out if raw input size
+ // is greater than some threshold.
+ if len(v) > maxConstraintSize {
+ return c, ErrMaxConstraintSizeExceeded
+ }
+
+ d := json.NewDecoder(bytes.NewBuffer(v))
+ d.DisallowUnknownFields()
+ err = d.Decode(&c)
+
+ return
+}
diff --git a/vendor/github.com/stoewer/go-strcase/.gitignore b/vendor/github.com/stoewer/go-strcase/.gitignore
new file mode 100644
index 0000000000..db5247b944
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/.gitignore
@@ -0,0 +1,17 @@
+# Compiled Object files, Static and Dynamic libs (Shared Objects)
+*.o
+*.a
+*.so
+
+# Folders
+vendor
+doc
+
+# Temporary files
+*~
+*.swp
+
+# Editor and IDE config
+.idea
+*.iml
+.vscode
diff --git a/vendor/github.com/stoewer/go-strcase/.golangci.yml b/vendor/github.com/stoewer/go-strcase/.golangci.yml
new file mode 100644
index 0000000000..7f98d55c42
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/.golangci.yml
@@ -0,0 +1,26 @@
+run:
+ deadline: 10m
+
+linters:
+ enable:
+ - dupl
+ - goconst
+ - gocyclo
+ - godox
+ - gosec
+ - interfacer
+ - lll
+ - maligned
+ - misspell
+ - prealloc
+ - stylecheck
+ - unconvert
+ - unparam
+ - errcheck
+ - golint
+ - gofmt
+ disable: []
+ fast: false
+
+issues:
+ exclude-use-default: false
diff --git a/vendor/github.com/stoewer/go-strcase/LICENSE b/vendor/github.com/stoewer/go-strcase/LICENSE
new file mode 100644
index 0000000000..a105a3819a
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/LICENSE
@@ -0,0 +1,21 @@
+The MIT License (MIT)
+
+Copyright (c) 2017, Adrian Stoewer
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
diff --git a/vendor/github.com/stoewer/go-strcase/README.md b/vendor/github.com/stoewer/go-strcase/README.md
new file mode 100644
index 0000000000..0e8635d801
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/README.md
@@ -0,0 +1,50 @@
+[![CircleCI](https://circleci.com/gh/stoewer/go-strcase/tree/master.svg?style=svg)](https://circleci.com/gh/stoewer/go-strcase/tree/master)
+[![codecov](https://codecov.io/gh/stoewer/go-strcase/branch/master/graph/badge.svg)](https://codecov.io/gh/stoewer/go-strcase)
+[![GoDoc](https://godoc.org/github.com/stoewer/go-strcase?status.svg)](https://pkg.go.dev/github.com/stoewer/go-strcase)
+---
+
+Go strcase
+==========
+
+The package `strcase` converts between different kinds of naming formats such as camel case
+(`CamelCase`), snake case (`snake_case`) or kebab case (`kebab-case`).
+The package is designed to work only with strings consisting of standard ASCII letters.
+Unicode is currently not supported.
+
+Versioning and stability
+------------------------
+
+Although the master branch is supposed to remain always backward compatible, the repository
+contains version tags in order to support vendoring tools.
+The tag names follow semantic versioning conventions and have the following format `v1.0.0`.
+This package supports Go modules introduced with version 1.11.
+
+Example
+-------
+
+```go
+import "github.com/stoewer/go-strcase"
+
+var snake = strcase.SnakeCase("CamelCase")
+```
+
+Dependencies
+------------
+
+### Build dependencies
+
+* none
+
+### Test dependencies
+
+* `github.com/stretchr/testify`
+
+Run linters and unit tests
+--------------------------
+
+To run the static code analysis, linters and tests use the following commands:
+
+```
+golangci-lint run --config .golangci.yml ./...
+go test ./...
+```
diff --git a/vendor/github.com/stoewer/go-strcase/camel.go b/vendor/github.com/stoewer/go-strcase/camel.go
new file mode 100644
index 0000000000..5c233cc8f1
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/camel.go
@@ -0,0 +1,37 @@
+// Copyright (c) 2017, A. Stoewer
+// All rights reserved.
+
+package strcase
+
+import (
+ "strings"
+)
+
+// UpperCamelCase converts a string into camel case starting with a upper case letter.
+func UpperCamelCase(s string) string {
+ return camelCase(s, true)
+}
+
+// LowerCamelCase converts a string into camel case starting with a lower case letter.
+func LowerCamelCase(s string) string {
+ return camelCase(s, false)
+}
+
+func camelCase(s string, upper bool) string {
+ s = strings.TrimSpace(s)
+ buffer := make([]rune, 0, len(s))
+
+ stringIter(s, func(prev, curr, next rune) {
+ if !isDelimiter(curr) {
+ if isDelimiter(prev) || (upper && prev == 0) {
+ buffer = append(buffer, toUpper(curr))
+ } else if isLower(prev) {
+ buffer = append(buffer, curr)
+ } else {
+ buffer = append(buffer, toLower(curr))
+ }
+ }
+ })
+
+ return string(buffer)
+}
diff --git a/vendor/github.com/stoewer/go-strcase/doc.go b/vendor/github.com/stoewer/go-strcase/doc.go
new file mode 100644
index 0000000000..3e441ca3ef
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/doc.go
@@ -0,0 +1,8 @@
+// Copyright (c) 2017, A. Stoewer
+// All rights reserved.
+
+// Package strcase converts between different kinds of naming formats such as camel case
+// (CamelCase), snake case (snake_case) or kebab case (kebab-case). The package is designed
+// to work only with strings consisting of standard ASCII letters. Unicode is currently not
+// supported.
+package strcase
diff --git a/vendor/github.com/stoewer/go-strcase/go.mod b/vendor/github.com/stoewer/go-strcase/go.mod
new file mode 100644
index 0000000000..8a360abe14
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/go.mod
@@ -0,0 +1,5 @@
+module github.com/stoewer/go-strcase
+
+go 1.11
+
+require github.com/stretchr/testify v1.5.1
diff --git a/vendor/github.com/stoewer/go-strcase/go.sum b/vendor/github.com/stoewer/go-strcase/go.sum
new file mode 100644
index 0000000000..331fa69822
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/go.sum
@@ -0,0 +1,11 @@
+github.com/davecgh/go-spew v1.1.0 h1:ZDRjVQ15GmhC3fiQ8ni8+OwkZQO4DARzQgrnXU1Liz8=
+github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
+github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
+github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
+github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
+github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4=
+github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
+gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM=
+gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
+gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw=
+gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
diff --git a/vendor/github.com/stoewer/go-strcase/helper.go b/vendor/github.com/stoewer/go-strcase/helper.go
new file mode 100644
index 0000000000..ecad589143
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/helper.go
@@ -0,0 +1,71 @@
+// Copyright (c) 2017, A. Stoewer
+// All rights reserved.
+
+package strcase
+
+// isLower checks if a character is lower case. More precisely it evaluates if it is
+// in the range of ASCII character 'a' to 'z'.
+func isLower(ch rune) bool {
+ return ch >= 'a' && ch <= 'z'
+}
+
+// toLower converts a character in the range of ASCII characters 'A' to 'Z' to its lower
+// case counterpart. Other characters remain the same.
+func toLower(ch rune) rune {
+ if ch >= 'A' && ch <= 'Z' {
+ return ch + 32
+ }
+ return ch
+}
+
+// isLower checks if a character is upper case. More precisely it evaluates if it is
+// in the range of ASCII characters 'A' to 'Z'.
+func isUpper(ch rune) bool {
+ return ch >= 'A' && ch <= 'Z'
+}
+
+// toLower converts a character in the range of ASCII characters 'a' to 'z' to its lower
+// case counterpart. Other characters remain the same.
+func toUpper(ch rune) rune {
+ if ch >= 'a' && ch <= 'z' {
+ return ch - 32
+ }
+ return ch
+}
+
+// isSpace checks if a character is some kind of whitespace.
+func isSpace(ch rune) bool {
+ return ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r'
+}
+
+// isDelimiter checks if a character is some kind of whitespace or '_' or '-'.
+func isDelimiter(ch rune) bool {
+ return ch == '-' || ch == '_' || isSpace(ch)
+}
+
+// iterFunc is a callback that is called fro a specific position in a string. Its arguments are the
+// rune at the respective string position as well as the previous and the next rune. If curr is at the
+// first position of the string prev is zero. If curr is at the end of the string next is zero.
+type iterFunc func(prev, curr, next rune)
+
+// stringIter iterates over a string, invoking the callback for every single rune in the string.
+func stringIter(s string, callback iterFunc) {
+ var prev rune
+ var curr rune
+ for _, next := range s {
+ if curr == 0 {
+ prev = curr
+ curr = next
+ continue
+ }
+
+ callback(prev, curr, next)
+
+ prev = curr
+ curr = next
+ }
+
+ if len(s) > 0 {
+ callback(prev, curr, 0)
+ }
+}
diff --git a/vendor/github.com/stoewer/go-strcase/kebab.go b/vendor/github.com/stoewer/go-strcase/kebab.go
new file mode 100644
index 0000000000..e9a6487579
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/kebab.go
@@ -0,0 +1,14 @@
+// Copyright (c) 2017, A. Stoewer
+// All rights reserved.
+
+package strcase
+
+// KebabCase converts a string into kebab case.
+func KebabCase(s string) string {
+ return delimiterCase(s, '-', false)
+}
+
+// UpperKebabCase converts a string into kebab case with capital letters.
+func UpperKebabCase(s string) string {
+ return delimiterCase(s, '-', true)
+}
diff --git a/vendor/github.com/stoewer/go-strcase/snake.go b/vendor/github.com/stoewer/go-strcase/snake.go
new file mode 100644
index 0000000000..1b216e20cf
--- /dev/null
+++ b/vendor/github.com/stoewer/go-strcase/snake.go
@@ -0,0 +1,58 @@
+// Copyright (c) 2017, A. Stoewer
+// All rights reserved.
+
+package strcase
+
+import (
+ "strings"
+)
+
+// SnakeCase converts a string into snake case.
+func SnakeCase(s string) string {
+ return delimiterCase(s, '_', false)
+}
+
+// UpperSnakeCase converts a string into snake case with capital letters.
+func UpperSnakeCase(s string) string {
+ return delimiterCase(s, '_', true)
+}
+
+// delimiterCase converts a string into snake_case or kebab-case depending on the delimiter passed
+// as second argument. When upperCase is true the result will be UPPER_SNAKE_CASE or UPPER-KEBAB-CASE.
+func delimiterCase(s string, delimiter rune, upperCase bool) string {
+ s = strings.TrimSpace(s)
+ buffer := make([]rune, 0, len(s)+3)
+
+ adjustCase := toLower
+ if upperCase {
+ adjustCase = toUpper
+ }
+
+ var prev rune
+ var curr rune
+ for _, next := range s {
+ if isDelimiter(curr) {
+ if !isDelimiter(prev) {
+ buffer = append(buffer, delimiter)
+ }
+ } else if isUpper(curr) {
+ if isLower(prev) || (isUpper(prev) && isLower(next)) {
+ buffer = append(buffer, delimiter)
+ }
+ buffer = append(buffer, adjustCase(curr))
+ } else if curr != 0 {
+ buffer = append(buffer, adjustCase(curr))
+ }
+ prev = curr
+ curr = next
+ }
+
+ if len(s) > 0 {
+ if isUpper(curr) && isLower(prev) && prev != 0 {
+ buffer = append(buffer, delimiter)
+ }
+ buffer = append(buffer, adjustCase(curr))
+ }
+
+ return string(buffer)
+}
diff --git a/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/checked.pb.go b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/checked.pb.go
new file mode 100644
index 0000000000..af8596fd2a
--- /dev/null
+++ b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/checked.pb.go
@@ -0,0 +1,1641 @@
+// Copyright 2020 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// protoc-gen-go v1.26.0
+// protoc v3.12.2
+// source: google/api/expr/v1alpha1/checked.proto
+
+package expr
+
+import (
+ reflect "reflect"
+ sync "sync"
+
+ protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+ protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+ emptypb "google.golang.org/protobuf/types/known/emptypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+const (
+ // Verify that this generated code is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+ // Verify that runtime/protoimpl is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+// CEL primitive types.
+type Type_PrimitiveType int32
+
+const (
+ // Unspecified type.
+ Type_PRIMITIVE_TYPE_UNSPECIFIED Type_PrimitiveType = 0
+ // Boolean type.
+ Type_BOOL Type_PrimitiveType = 1
+ // Int64 type.
+ //
+ // Proto-based integer values are widened to int64.
+ Type_INT64 Type_PrimitiveType = 2
+ // Uint64 type.
+ //
+ // Proto-based unsigned integer values are widened to uint64.
+ Type_UINT64 Type_PrimitiveType = 3
+ // Double type.
+ //
+ // Proto-based float values are widened to double values.
+ Type_DOUBLE Type_PrimitiveType = 4
+ // String type.
+ Type_STRING Type_PrimitiveType = 5
+ // Bytes type.
+ Type_BYTES Type_PrimitiveType = 6
+)
+
+// Enum value maps for Type_PrimitiveType.
+var (
+ Type_PrimitiveType_name = map[int32]string{
+ 0: "PRIMITIVE_TYPE_UNSPECIFIED",
+ 1: "BOOL",
+ 2: "INT64",
+ 3: "UINT64",
+ 4: "DOUBLE",
+ 5: "STRING",
+ 6: "BYTES",
+ }
+ Type_PrimitiveType_value = map[string]int32{
+ "PRIMITIVE_TYPE_UNSPECIFIED": 0,
+ "BOOL": 1,
+ "INT64": 2,
+ "UINT64": 3,
+ "DOUBLE": 4,
+ "STRING": 5,
+ "BYTES": 6,
+ }
+)
+
+func (x Type_PrimitiveType) Enum() *Type_PrimitiveType {
+ p := new(Type_PrimitiveType)
+ *p = x
+ return p
+}
+
+func (x Type_PrimitiveType) String() string {
+ return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (Type_PrimitiveType) Descriptor() protoreflect.EnumDescriptor {
+ return file_google_api_expr_v1alpha1_checked_proto_enumTypes[0].Descriptor()
+}
+
+func (Type_PrimitiveType) Type() protoreflect.EnumType {
+ return &file_google_api_expr_v1alpha1_checked_proto_enumTypes[0]
+}
+
+func (x Type_PrimitiveType) Number() protoreflect.EnumNumber {
+ return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use Type_PrimitiveType.Descriptor instead.
+func (Type_PrimitiveType) EnumDescriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{1, 0}
+}
+
+// Well-known protobuf types treated with first-class support in CEL.
+type Type_WellKnownType int32
+
+const (
+ // Unspecified type.
+ Type_WELL_KNOWN_TYPE_UNSPECIFIED Type_WellKnownType = 0
+ // Well-known protobuf.Any type.
+ //
+ // Any types are a polymorphic message type. During type-checking they are
+ // treated like `DYN` types, but at runtime they are resolved to a specific
+ // message type specified at evaluation time.
+ Type_ANY Type_WellKnownType = 1
+ // Well-known protobuf.Timestamp type, internally referenced as `timestamp`.
+ Type_TIMESTAMP Type_WellKnownType = 2
+ // Well-known protobuf.Duration type, internally referenced as `duration`.
+ Type_DURATION Type_WellKnownType = 3
+)
+
+// Enum value maps for Type_WellKnownType.
+var (
+ Type_WellKnownType_name = map[int32]string{
+ 0: "WELL_KNOWN_TYPE_UNSPECIFIED",
+ 1: "ANY",
+ 2: "TIMESTAMP",
+ 3: "DURATION",
+ }
+ Type_WellKnownType_value = map[string]int32{
+ "WELL_KNOWN_TYPE_UNSPECIFIED": 0,
+ "ANY": 1,
+ "TIMESTAMP": 2,
+ "DURATION": 3,
+ }
+)
+
+func (x Type_WellKnownType) Enum() *Type_WellKnownType {
+ p := new(Type_WellKnownType)
+ *p = x
+ return p
+}
+
+func (x Type_WellKnownType) String() string {
+ return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (Type_WellKnownType) Descriptor() protoreflect.EnumDescriptor {
+ return file_google_api_expr_v1alpha1_checked_proto_enumTypes[1].Descriptor()
+}
+
+func (Type_WellKnownType) Type() protoreflect.EnumType {
+ return &file_google_api_expr_v1alpha1_checked_proto_enumTypes[1]
+}
+
+func (x Type_WellKnownType) Number() protoreflect.EnumNumber {
+ return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use Type_WellKnownType.Descriptor instead.
+func (Type_WellKnownType) EnumDescriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{1, 1}
+}
+
+// A CEL expression which has been successfully type checked.
+type CheckedExpr struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // A map from expression ids to resolved references.
+ //
+ // The following entries are in this table:
+ //
+ // - An Ident or Select expression is represented here if it resolves to a
+ // declaration. For instance, if `a.b.c` is represented by
+ // `select(select(id(a), b), c)`, and `a.b` resolves to a declaration,
+ // while `c` is a field selection, then the reference is attached to the
+ // nested select expression (but not to the id or or the outer select).
+ // In turn, if `a` resolves to a declaration and `b.c` are field selections,
+ // the reference is attached to the ident expression.
+ // - Every Call expression has an entry here, identifying the function being
+ // called.
+ // - Every CreateStruct expression for a message has an entry, identifying
+ // the message.
+ ReferenceMap map[int64]*Reference `protobuf:"bytes,2,rep,name=reference_map,json=referenceMap,proto3" json:"reference_map,omitempty" protobuf_key:"varint,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"`
+ // A map from expression ids to types.
+ //
+ // Every expression node which has a type different than DYN has a mapping
+ // here. If an expression has type DYN, it is omitted from this map to save
+ // space.
+ TypeMap map[int64]*Type `protobuf:"bytes,3,rep,name=type_map,json=typeMap,proto3" json:"type_map,omitempty" protobuf_key:"varint,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"`
+ // The source info derived from input that generated the parsed `expr` and
+ // any optimizations made during the type-checking pass.
+ SourceInfo *SourceInfo `protobuf:"bytes,5,opt,name=source_info,json=sourceInfo,proto3" json:"source_info,omitempty"`
+ // The checked expression. Semantically equivalent to the parsed `expr`, but
+ // may have structural differences.
+ Expr *Expr `protobuf:"bytes,4,opt,name=expr,proto3" json:"expr,omitempty"`
+}
+
+func (x *CheckedExpr) Reset() {
+ *x = CheckedExpr{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[0]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *CheckedExpr) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*CheckedExpr) ProtoMessage() {}
+
+func (x *CheckedExpr) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[0]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use CheckedExpr.ProtoReflect.Descriptor instead.
+func (*CheckedExpr) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *CheckedExpr) GetReferenceMap() map[int64]*Reference {
+ if x != nil {
+ return x.ReferenceMap
+ }
+ return nil
+}
+
+func (x *CheckedExpr) GetTypeMap() map[int64]*Type {
+ if x != nil {
+ return x.TypeMap
+ }
+ return nil
+}
+
+func (x *CheckedExpr) GetSourceInfo() *SourceInfo {
+ if x != nil {
+ return x.SourceInfo
+ }
+ return nil
+}
+
+func (x *CheckedExpr) GetExpr() *Expr {
+ if x != nil {
+ return x.Expr
+ }
+ return nil
+}
+
+// Represents a CEL type.
+type Type struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The kind of type.
+ //
+ // Types that are assignable to TypeKind:
+ // *Type_Dyn
+ // *Type_Null
+ // *Type_Primitive
+ // *Type_Wrapper
+ // *Type_WellKnown
+ // *Type_ListType_
+ // *Type_MapType_
+ // *Type_Function
+ // *Type_MessageType
+ // *Type_TypeParam
+ // *Type_Type
+ // *Type_Error
+ // *Type_AbstractType_
+ TypeKind isType_TypeKind `protobuf_oneof:"type_kind"`
+}
+
+func (x *Type) Reset() {
+ *x = Type{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[1]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Type) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Type) ProtoMessage() {}
+
+func (x *Type) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[1]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Type.ProtoReflect.Descriptor instead.
+func (*Type) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{1}
+}
+
+func (m *Type) GetTypeKind() isType_TypeKind {
+ if m != nil {
+ return m.TypeKind
+ }
+ return nil
+}
+
+func (x *Type) GetDyn() *emptypb.Empty {
+ if x, ok := x.GetTypeKind().(*Type_Dyn); ok {
+ return x.Dyn
+ }
+ return nil
+}
+
+func (x *Type) GetNull() structpb.NullValue {
+ if x, ok := x.GetTypeKind().(*Type_Null); ok {
+ return x.Null
+ }
+ return structpb.NullValue_NULL_VALUE
+}
+
+func (x *Type) GetPrimitive() Type_PrimitiveType {
+ if x, ok := x.GetTypeKind().(*Type_Primitive); ok {
+ return x.Primitive
+ }
+ return Type_PRIMITIVE_TYPE_UNSPECIFIED
+}
+
+func (x *Type) GetWrapper() Type_PrimitiveType {
+ if x, ok := x.GetTypeKind().(*Type_Wrapper); ok {
+ return x.Wrapper
+ }
+ return Type_PRIMITIVE_TYPE_UNSPECIFIED
+}
+
+func (x *Type) GetWellKnown() Type_WellKnownType {
+ if x, ok := x.GetTypeKind().(*Type_WellKnown); ok {
+ return x.WellKnown
+ }
+ return Type_WELL_KNOWN_TYPE_UNSPECIFIED
+}
+
+func (x *Type) GetListType() *Type_ListType {
+ if x, ok := x.GetTypeKind().(*Type_ListType_); ok {
+ return x.ListType
+ }
+ return nil
+}
+
+func (x *Type) GetMapType() *Type_MapType {
+ if x, ok := x.GetTypeKind().(*Type_MapType_); ok {
+ return x.MapType
+ }
+ return nil
+}
+
+func (x *Type) GetFunction() *Type_FunctionType {
+ if x, ok := x.GetTypeKind().(*Type_Function); ok {
+ return x.Function
+ }
+ return nil
+}
+
+func (x *Type) GetMessageType() string {
+ if x, ok := x.GetTypeKind().(*Type_MessageType); ok {
+ return x.MessageType
+ }
+ return ""
+}
+
+func (x *Type) GetTypeParam() string {
+ if x, ok := x.GetTypeKind().(*Type_TypeParam); ok {
+ return x.TypeParam
+ }
+ return ""
+}
+
+func (x *Type) GetType() *Type {
+ if x, ok := x.GetTypeKind().(*Type_Type); ok {
+ return x.Type
+ }
+ return nil
+}
+
+func (x *Type) GetError() *emptypb.Empty {
+ if x, ok := x.GetTypeKind().(*Type_Error); ok {
+ return x.Error
+ }
+ return nil
+}
+
+func (x *Type) GetAbstractType() *Type_AbstractType {
+ if x, ok := x.GetTypeKind().(*Type_AbstractType_); ok {
+ return x.AbstractType
+ }
+ return nil
+}
+
+type isType_TypeKind interface {
+ isType_TypeKind()
+}
+
+type Type_Dyn struct {
+ // Dynamic type.
+ Dyn *emptypb.Empty `protobuf:"bytes,1,opt,name=dyn,proto3,oneof"`
+}
+
+type Type_Null struct {
+ // Null value.
+ Null structpb.NullValue `protobuf:"varint,2,opt,name=null,proto3,enum=google.protobuf.NullValue,oneof"`
+}
+
+type Type_Primitive struct {
+ // Primitive types: `true`, `1u`, `-2.0`, `'string'`, `b'bytes'`.
+ Primitive Type_PrimitiveType `protobuf:"varint,3,opt,name=primitive,proto3,enum=google.api.expr.v1alpha1.Type_PrimitiveType,oneof"`
+}
+
+type Type_Wrapper struct {
+ // Wrapper of a primitive type, e.g. `google.protobuf.Int64Value`.
+ Wrapper Type_PrimitiveType `protobuf:"varint,4,opt,name=wrapper,proto3,enum=google.api.expr.v1alpha1.Type_PrimitiveType,oneof"`
+}
+
+type Type_WellKnown struct {
+ // Well-known protobuf type such as `google.protobuf.Timestamp`.
+ WellKnown Type_WellKnownType `protobuf:"varint,5,opt,name=well_known,json=wellKnown,proto3,enum=google.api.expr.v1alpha1.Type_WellKnownType,oneof"`
+}
+
+type Type_ListType_ struct {
+ // Parameterized list with elements of `list_type`, e.g. `list`.
+ ListType *Type_ListType `protobuf:"bytes,6,opt,name=list_type,json=listType,proto3,oneof"`
+}
+
+type Type_MapType_ struct {
+ // Parameterized map with typed keys and values.
+ MapType *Type_MapType `protobuf:"bytes,7,opt,name=map_type,json=mapType,proto3,oneof"`
+}
+
+type Type_Function struct {
+ // Function type.
+ Function *Type_FunctionType `protobuf:"bytes,8,opt,name=function,proto3,oneof"`
+}
+
+type Type_MessageType struct {
+ // Protocol buffer message type.
+ //
+ // The `message_type` string specifies the qualified message type name. For
+ // example, `google.plus.Profile`.
+ MessageType string `protobuf:"bytes,9,opt,name=message_type,json=messageType,proto3,oneof"`
+}
+
+type Type_TypeParam struct {
+ // Type param type.
+ //
+ // The `type_param` string specifies the type parameter name, e.g. `list`
+ // would be a `list_type` whose element type was a `type_param` type
+ // named `E`.
+ TypeParam string `protobuf:"bytes,10,opt,name=type_param,json=typeParam,proto3,oneof"`
+}
+
+type Type_Type struct {
+ // Type type.
+ //
+ // The `type` value specifies the target type. e.g. int is type with a
+ // target type of `Primitive.INT`.
+ Type *Type `protobuf:"bytes,11,opt,name=type,proto3,oneof"`
+}
+
+type Type_Error struct {
+ // Error type.
+ //
+ // During type-checking if an expression is an error, its type is propagated
+ // as the `ERROR` type. This permits the type-checker to discover other
+ // errors present in the expression.
+ Error *emptypb.Empty `protobuf:"bytes,12,opt,name=error,proto3,oneof"`
+}
+
+type Type_AbstractType_ struct {
+ // Abstract, application defined type.
+ AbstractType *Type_AbstractType `protobuf:"bytes,14,opt,name=abstract_type,json=abstractType,proto3,oneof"`
+}
+
+func (*Type_Dyn) isType_TypeKind() {}
+
+func (*Type_Null) isType_TypeKind() {}
+
+func (*Type_Primitive) isType_TypeKind() {}
+
+func (*Type_Wrapper) isType_TypeKind() {}
+
+func (*Type_WellKnown) isType_TypeKind() {}
+
+func (*Type_ListType_) isType_TypeKind() {}
+
+func (*Type_MapType_) isType_TypeKind() {}
+
+func (*Type_Function) isType_TypeKind() {}
+
+func (*Type_MessageType) isType_TypeKind() {}
+
+func (*Type_TypeParam) isType_TypeKind() {}
+
+func (*Type_Type) isType_TypeKind() {}
+
+func (*Type_Error) isType_TypeKind() {}
+
+func (*Type_AbstractType_) isType_TypeKind() {}
+
+// Represents a declaration of a named value or function.
+//
+// A declaration is part of the contract between the expression, the agent
+// evaluating that expression, and the caller requesting evaluation.
+type Decl struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The fully qualified name of the declaration.
+ //
+ // Declarations are organized in containers and this represents the full path
+ // to the declaration in its container, as in `google.api.expr.Decl`.
+ //
+ // Declarations used as [FunctionDecl.Overload][google.api.expr.v1alpha1.Decl.FunctionDecl.Overload] parameters may or may not
+ // have a name depending on whether the overload is function declaration or a
+ // function definition containing a result [Expr][google.api.expr.v1alpha1.Expr].
+ Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
+ // Required. The declaration kind.
+ //
+ // Types that are assignable to DeclKind:
+ // *Decl_Ident
+ // *Decl_Function
+ DeclKind isDecl_DeclKind `protobuf_oneof:"decl_kind"`
+}
+
+func (x *Decl) Reset() {
+ *x = Decl{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[2]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Decl) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Decl) ProtoMessage() {}
+
+func (x *Decl) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[2]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Decl.ProtoReflect.Descriptor instead.
+func (*Decl) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{2}
+}
+
+func (x *Decl) GetName() string {
+ if x != nil {
+ return x.Name
+ }
+ return ""
+}
+
+func (m *Decl) GetDeclKind() isDecl_DeclKind {
+ if m != nil {
+ return m.DeclKind
+ }
+ return nil
+}
+
+func (x *Decl) GetIdent() *Decl_IdentDecl {
+ if x, ok := x.GetDeclKind().(*Decl_Ident); ok {
+ return x.Ident
+ }
+ return nil
+}
+
+func (x *Decl) GetFunction() *Decl_FunctionDecl {
+ if x, ok := x.GetDeclKind().(*Decl_Function); ok {
+ return x.Function
+ }
+ return nil
+}
+
+type isDecl_DeclKind interface {
+ isDecl_DeclKind()
+}
+
+type Decl_Ident struct {
+ // Identifier declaration.
+ Ident *Decl_IdentDecl `protobuf:"bytes,2,opt,name=ident,proto3,oneof"`
+}
+
+type Decl_Function struct {
+ // Function declaration.
+ Function *Decl_FunctionDecl `protobuf:"bytes,3,opt,name=function,proto3,oneof"`
+}
+
+func (*Decl_Ident) isDecl_DeclKind() {}
+
+func (*Decl_Function) isDecl_DeclKind() {}
+
+// Describes a resolved reference to a declaration.
+type Reference struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The fully qualified name of the declaration.
+ Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
+ // For references to functions, this is a list of `Overload.overload_id`
+ // values which match according to typing rules.
+ //
+ // If the list has more than one element, overload resolution among the
+ // presented candidates must happen at runtime because of dynamic types. The
+ // type checker attempts to narrow down this list as much as possible.
+ //
+ // Empty if this is not a reference to a [Decl.FunctionDecl][google.api.expr.v1alpha1.Decl.FunctionDecl].
+ OverloadId []string `protobuf:"bytes,3,rep,name=overload_id,json=overloadId,proto3" json:"overload_id,omitempty"`
+ // For references to constants, this may contain the value of the
+ // constant if known at compile time.
+ Value *Constant `protobuf:"bytes,4,opt,name=value,proto3" json:"value,omitempty"`
+}
+
+func (x *Reference) Reset() {
+ *x = Reference{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[3]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Reference) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Reference) ProtoMessage() {}
+
+func (x *Reference) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[3]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Reference.ProtoReflect.Descriptor instead.
+func (*Reference) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{3}
+}
+
+func (x *Reference) GetName() string {
+ if x != nil {
+ return x.Name
+ }
+ return ""
+}
+
+func (x *Reference) GetOverloadId() []string {
+ if x != nil {
+ return x.OverloadId
+ }
+ return nil
+}
+
+func (x *Reference) GetValue() *Constant {
+ if x != nil {
+ return x.Value
+ }
+ return nil
+}
+
+// List type with typed elements, e.g. `list`.
+type Type_ListType struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The element type.
+ ElemType *Type `protobuf:"bytes,1,opt,name=elem_type,json=elemType,proto3" json:"elem_type,omitempty"`
+}
+
+func (x *Type_ListType) Reset() {
+ *x = Type_ListType{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[6]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Type_ListType) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Type_ListType) ProtoMessage() {}
+
+func (x *Type_ListType) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[6]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Type_ListType.ProtoReflect.Descriptor instead.
+func (*Type_ListType) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{1, 0}
+}
+
+func (x *Type_ListType) GetElemType() *Type {
+ if x != nil {
+ return x.ElemType
+ }
+ return nil
+}
+
+// Map type with parameterized key and value types, e.g. `map`.
+type Type_MapType struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The type of the key.
+ KeyType *Type `protobuf:"bytes,1,opt,name=key_type,json=keyType,proto3" json:"key_type,omitempty"`
+ // The type of the value.
+ ValueType *Type `protobuf:"bytes,2,opt,name=value_type,json=valueType,proto3" json:"value_type,omitempty"`
+}
+
+func (x *Type_MapType) Reset() {
+ *x = Type_MapType{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[7]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Type_MapType) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Type_MapType) ProtoMessage() {}
+
+func (x *Type_MapType) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[7]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Type_MapType.ProtoReflect.Descriptor instead.
+func (*Type_MapType) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{1, 1}
+}
+
+func (x *Type_MapType) GetKeyType() *Type {
+ if x != nil {
+ return x.KeyType
+ }
+ return nil
+}
+
+func (x *Type_MapType) GetValueType() *Type {
+ if x != nil {
+ return x.ValueType
+ }
+ return nil
+}
+
+// Function type with result and arg types.
+type Type_FunctionType struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Result type of the function.
+ ResultType *Type `protobuf:"bytes,1,opt,name=result_type,json=resultType,proto3" json:"result_type,omitempty"`
+ // Argument types of the function.
+ ArgTypes []*Type `protobuf:"bytes,2,rep,name=arg_types,json=argTypes,proto3" json:"arg_types,omitempty"`
+}
+
+func (x *Type_FunctionType) Reset() {
+ *x = Type_FunctionType{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[8]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Type_FunctionType) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Type_FunctionType) ProtoMessage() {}
+
+func (x *Type_FunctionType) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[8]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Type_FunctionType.ProtoReflect.Descriptor instead.
+func (*Type_FunctionType) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{1, 2}
+}
+
+func (x *Type_FunctionType) GetResultType() *Type {
+ if x != nil {
+ return x.ResultType
+ }
+ return nil
+}
+
+func (x *Type_FunctionType) GetArgTypes() []*Type {
+ if x != nil {
+ return x.ArgTypes
+ }
+ return nil
+}
+
+// Application defined abstract type.
+type Type_AbstractType struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The fully qualified name of this abstract type.
+ Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
+ // Parameter types for this abstract type.
+ ParameterTypes []*Type `protobuf:"bytes,2,rep,name=parameter_types,json=parameterTypes,proto3" json:"parameter_types,omitempty"`
+}
+
+func (x *Type_AbstractType) Reset() {
+ *x = Type_AbstractType{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[9]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Type_AbstractType) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Type_AbstractType) ProtoMessage() {}
+
+func (x *Type_AbstractType) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[9]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Type_AbstractType.ProtoReflect.Descriptor instead.
+func (*Type_AbstractType) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{1, 3}
+}
+
+func (x *Type_AbstractType) GetName() string {
+ if x != nil {
+ return x.Name
+ }
+ return ""
+}
+
+func (x *Type_AbstractType) GetParameterTypes() []*Type {
+ if x != nil {
+ return x.ParameterTypes
+ }
+ return nil
+}
+
+// Identifier declaration which specifies its type and optional `Expr` value.
+//
+// An identifier without a value is a declaration that must be provided at
+// evaluation time. An identifier with a value should resolve to a constant,
+// but may be used in conjunction with other identifiers bound at evaluation
+// time.
+type Decl_IdentDecl struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. The type of the identifier.
+ Type *Type `protobuf:"bytes,1,opt,name=type,proto3" json:"type,omitempty"`
+ // The constant value of the identifier. If not specified, the identifier
+ // must be supplied at evaluation time.
+ Value *Constant `protobuf:"bytes,2,opt,name=value,proto3" json:"value,omitempty"`
+ // Documentation string for the identifier.
+ Doc string `protobuf:"bytes,3,opt,name=doc,proto3" json:"doc,omitempty"`
+}
+
+func (x *Decl_IdentDecl) Reset() {
+ *x = Decl_IdentDecl{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[10]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Decl_IdentDecl) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Decl_IdentDecl) ProtoMessage() {}
+
+func (x *Decl_IdentDecl) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[10]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Decl_IdentDecl.ProtoReflect.Descriptor instead.
+func (*Decl_IdentDecl) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{2, 0}
+}
+
+func (x *Decl_IdentDecl) GetType() *Type {
+ if x != nil {
+ return x.Type
+ }
+ return nil
+}
+
+func (x *Decl_IdentDecl) GetValue() *Constant {
+ if x != nil {
+ return x.Value
+ }
+ return nil
+}
+
+func (x *Decl_IdentDecl) GetDoc() string {
+ if x != nil {
+ return x.Doc
+ }
+ return ""
+}
+
+// Function declaration specifies one or more overloads which indicate the
+// function's parameter types and return type, and may optionally specify a
+// function definition in terms of CEL expressions.
+//
+// Functions have no observable side-effects (there may be side-effects like
+// logging which are not observable from CEL).
+type Decl_FunctionDecl struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. List of function overloads, must contain at least one overload.
+ Overloads []*Decl_FunctionDecl_Overload `protobuf:"bytes,1,rep,name=overloads,proto3" json:"overloads,omitempty"`
+}
+
+func (x *Decl_FunctionDecl) Reset() {
+ *x = Decl_FunctionDecl{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[11]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Decl_FunctionDecl) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Decl_FunctionDecl) ProtoMessage() {}
+
+func (x *Decl_FunctionDecl) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[11]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Decl_FunctionDecl.ProtoReflect.Descriptor instead.
+func (*Decl_FunctionDecl) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{2, 1}
+}
+
+func (x *Decl_FunctionDecl) GetOverloads() []*Decl_FunctionDecl_Overload {
+ if x != nil {
+ return x.Overloads
+ }
+ return nil
+}
+
+// An overload indicates a function's parameter types and return type, and
+// may optionally include a function body described in terms of [Expr][google.api.expr.v1alpha1.Expr]
+// values.
+//
+// Functions overloads are declared in either a function or method
+// call-style. For methods, the `params[0]` is the expected type of the
+// target receiver.
+//
+// Overloads must have non-overlapping argument types after erasure of all
+// parameterized type variables (similar as type erasure in Java).
+type Decl_FunctionDecl_Overload struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. Globally unique overload name of the function which reflects
+ // the function name and argument types.
+ //
+ // This will be used by a [Reference][google.api.expr.v1alpha1.Reference] to indicate the `overload_id` that
+ // was resolved for the function `name`.
+ OverloadId string `protobuf:"bytes,1,opt,name=overload_id,json=overloadId,proto3" json:"overload_id,omitempty"`
+ // List of function parameter [Type][google.api.expr.v1alpha1.Type] values.
+ //
+ // Param types are disjoint after generic type parameters have been
+ // replaced with the type `DYN`. Since the `DYN` type is compatible with
+ // any other type, this means that if `A` is a type parameter, the
+ // function types `int` and `int` are not disjoint. Likewise,
+ // `map` is not disjoint from `map`.
+ //
+ // When the `result_type` of a function is a generic type param, the
+ // type param name also appears as the `type` of on at least one params.
+ Params []*Type `protobuf:"bytes,2,rep,name=params,proto3" json:"params,omitempty"`
+ // The type param names associated with the function declaration.
+ //
+ // For example, `function ex(K key, map map) : V` would yield
+ // the type params of `K, V`.
+ TypeParams []string `protobuf:"bytes,3,rep,name=type_params,json=typeParams,proto3" json:"type_params,omitempty"`
+ // Required. The result type of the function. For example, the operator
+ // `string.isEmpty()` would have `result_type` of `kind: BOOL`.
+ ResultType *Type `protobuf:"bytes,4,opt,name=result_type,json=resultType,proto3" json:"result_type,omitempty"`
+ // Whether the function is to be used in a method call-style `x.f(...)`
+ // of a function call-style `f(x, ...)`.
+ //
+ // For methods, the first parameter declaration, `params[0]` is the
+ // expected type of the target receiver.
+ IsInstanceFunction bool `protobuf:"varint,5,opt,name=is_instance_function,json=isInstanceFunction,proto3" json:"is_instance_function,omitempty"`
+ // Documentation string for the overload.
+ Doc string `protobuf:"bytes,6,opt,name=doc,proto3" json:"doc,omitempty"`
+}
+
+func (x *Decl_FunctionDecl_Overload) Reset() {
+ *x = Decl_FunctionDecl_Overload{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[12]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Decl_FunctionDecl_Overload) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Decl_FunctionDecl_Overload) ProtoMessage() {}
+
+func (x *Decl_FunctionDecl_Overload) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_checked_proto_msgTypes[12]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Decl_FunctionDecl_Overload.ProtoReflect.Descriptor instead.
+func (*Decl_FunctionDecl_Overload) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP(), []int{2, 1, 0}
+}
+
+func (x *Decl_FunctionDecl_Overload) GetOverloadId() string {
+ if x != nil {
+ return x.OverloadId
+ }
+ return ""
+}
+
+func (x *Decl_FunctionDecl_Overload) GetParams() []*Type {
+ if x != nil {
+ return x.Params
+ }
+ return nil
+}
+
+func (x *Decl_FunctionDecl_Overload) GetTypeParams() []string {
+ if x != nil {
+ return x.TypeParams
+ }
+ return nil
+}
+
+func (x *Decl_FunctionDecl_Overload) GetResultType() *Type {
+ if x != nil {
+ return x.ResultType
+ }
+ return nil
+}
+
+func (x *Decl_FunctionDecl_Overload) GetIsInstanceFunction() bool {
+ if x != nil {
+ return x.IsInstanceFunction
+ }
+ return false
+}
+
+func (x *Decl_FunctionDecl_Overload) GetDoc() string {
+ if x != nil {
+ return x.Doc
+ }
+ return ""
+}
+
+var File_google_api_expr_v1alpha1_checked_proto protoreflect.FileDescriptor
+
+var file_google_api_expr_v1alpha1_checked_proto_rawDesc = []byte{
+ 0x0a, 0x26, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70,
+ 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2f, 0x63, 0x68, 0x65, 0x63, 0x6b,
+ 0x65, 0x64, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x18, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68,
+ 0x61, 0x31, 0x1a, 0x25, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65,
+ 0x78, 0x70, 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2f, 0x73, 0x79, 0x6e,
+ 0x74, 0x61, 0x78, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1b, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x65, 0x6d, 0x70, 0x74, 0x79,
+ 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1c, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70,
+ 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x2e, 0x70,
+ 0x72, 0x6f, 0x74, 0x6f, 0x22, 0xf7, 0x03, 0x0a, 0x0b, 0x43, 0x68, 0x65, 0x63, 0x6b, 0x65, 0x64,
+ 0x45, 0x78, 0x70, 0x72, 0x12, 0x5c, 0x0a, 0x0d, 0x72, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63,
+ 0x65, 0x5f, 0x6d, 0x61, 0x70, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x37, 0x2e, 0x67, 0x6f,
+ 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31,
+ 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x43, 0x68, 0x65, 0x63, 0x6b, 0x65, 0x64, 0x45, 0x78,
+ 0x70, 0x72, 0x2e, 0x52, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x4d, 0x61, 0x70, 0x45,
+ 0x6e, 0x74, 0x72, 0x79, 0x52, 0x0c, 0x72, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x4d,
+ 0x61, 0x70, 0x12, 0x4d, 0x0a, 0x08, 0x74, 0x79, 0x70, 0x65, 0x5f, 0x6d, 0x61, 0x70, 0x18, 0x03,
+ 0x20, 0x03, 0x28, 0x0b, 0x32, 0x32, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e,
+ 0x43, 0x68, 0x65, 0x63, 0x6b, 0x65, 0x64, 0x45, 0x78, 0x70, 0x72, 0x2e, 0x54, 0x79, 0x70, 0x65,
+ 0x4d, 0x61, 0x70, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x07, 0x74, 0x79, 0x70, 0x65, 0x4d, 0x61,
+ 0x70, 0x12, 0x45, 0x0a, 0x0b, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x5f, 0x69, 0x6e, 0x66, 0x6f,
+ 0x18, 0x05, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e,
+ 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+ 0x31, 0x2e, 0x53, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x0a, 0x73, 0x6f,
+ 0x75, 0x72, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x12, 0x32, 0x0a, 0x04, 0x65, 0x78, 0x70, 0x72,
+ 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e,
+ 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+ 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x04, 0x65, 0x78, 0x70, 0x72, 0x1a, 0x64, 0x0a, 0x11,
+ 0x52, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x4d, 0x61, 0x70, 0x45, 0x6e, 0x74, 0x72,
+ 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x03,
+ 0x6b, 0x65, 0x79, 0x12, 0x39, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01,
+ 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e,
+ 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x52, 0x65,
+ 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02,
+ 0x38, 0x01, 0x1a, 0x5a, 0x0a, 0x0c, 0x54, 0x79, 0x70, 0x65, 0x4d, 0x61, 0x70, 0x45, 0x6e, 0x74,
+ 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52,
+ 0x03, 0x6b, 0x65, 0x79, 0x12, 0x34, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20,
+ 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69,
+ 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54,
+ 0x79, 0x70, 0x65, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0xc8,
+ 0x0b, 0x0a, 0x04, 0x54, 0x79, 0x70, 0x65, 0x12, 0x2a, 0x0a, 0x03, 0x64, 0x79, 0x6e, 0x18, 0x01,
+ 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72,
+ 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x45, 0x6d, 0x70, 0x74, 0x79, 0x48, 0x00, 0x52, 0x03,
+ 0x64, 0x79, 0x6e, 0x12, 0x30, 0x0a, 0x04, 0x6e, 0x75, 0x6c, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28,
+ 0x0e, 0x32, 0x1a, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
+ 0x62, 0x75, 0x66, 0x2e, 0x4e, 0x75, 0x6c, 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x48, 0x00, 0x52,
+ 0x04, 0x6e, 0x75, 0x6c, 0x6c, 0x12, 0x4c, 0x0a, 0x09, 0x70, 0x72, 0x69, 0x6d, 0x69, 0x74, 0x69,
+ 0x76, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x2c, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70,
+ 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x2e, 0x50, 0x72, 0x69, 0x6d, 0x69, 0x74, 0x69,
+ 0x76, 0x65, 0x54, 0x79, 0x70, 0x65, 0x48, 0x00, 0x52, 0x09, 0x70, 0x72, 0x69, 0x6d, 0x69, 0x74,
+ 0x69, 0x76, 0x65, 0x12, 0x48, 0x0a, 0x07, 0x77, 0x72, 0x61, 0x70, 0x70, 0x65, 0x72, 0x18, 0x04,
+ 0x20, 0x01, 0x28, 0x0e, 0x32, 0x2c, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e,
+ 0x54, 0x79, 0x70, 0x65, 0x2e, 0x50, 0x72, 0x69, 0x6d, 0x69, 0x74, 0x69, 0x76, 0x65, 0x54, 0x79,
+ 0x70, 0x65, 0x48, 0x00, 0x52, 0x07, 0x77, 0x72, 0x61, 0x70, 0x70, 0x65, 0x72, 0x12, 0x4d, 0x0a,
+ 0x0a, 0x77, 0x65, 0x6c, 0x6c, 0x5f, 0x6b, 0x6e, 0x6f, 0x77, 0x6e, 0x18, 0x05, 0x20, 0x01, 0x28,
+ 0x0e, 0x32, 0x2c, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65,
+ 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70,
+ 0x65, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x48,
+ 0x00, 0x52, 0x09, 0x77, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x12, 0x46, 0x0a, 0x09,
+ 0x6c, 0x69, 0x73, 0x74, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32,
+ 0x27, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70,
+ 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x2e,
+ 0x4c, 0x69, 0x73, 0x74, 0x54, 0x79, 0x70, 0x65, 0x48, 0x00, 0x52, 0x08, 0x6c, 0x69, 0x73, 0x74,
+ 0x54, 0x79, 0x70, 0x65, 0x12, 0x43, 0x0a, 0x08, 0x6d, 0x61, 0x70, 0x5f, 0x74, 0x79, 0x70, 0x65,
+ 0x18, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x26, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e,
+ 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+ 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x2e, 0x4d, 0x61, 0x70, 0x54, 0x79, 0x70, 0x65, 0x48, 0x00,
+ 0x52, 0x07, 0x6d, 0x61, 0x70, 0x54, 0x79, 0x70, 0x65, 0x12, 0x49, 0x0a, 0x08, 0x66, 0x75, 0x6e,
+ 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x08, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x67, 0x6f,
+ 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31,
+ 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x2e, 0x46, 0x75, 0x6e, 0x63,
+ 0x74, 0x69, 0x6f, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x48, 0x00, 0x52, 0x08, 0x66, 0x75, 0x6e, 0x63,
+ 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x23, 0x0a, 0x0c, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x5f,
+ 0x74, 0x79, 0x70, 0x65, 0x18, 0x09, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x0b, 0x6d, 0x65,
+ 0x73, 0x73, 0x61, 0x67, 0x65, 0x54, 0x79, 0x70, 0x65, 0x12, 0x1f, 0x0a, 0x0a, 0x74, 0x79, 0x70,
+ 0x65, 0x5f, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x18, 0x0a, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52,
+ 0x09, 0x74, 0x79, 0x70, 0x65, 0x50, 0x61, 0x72, 0x61, 0x6d, 0x12, 0x34, 0x0a, 0x04, 0x74, 0x79,
+ 0x70, 0x65, 0x18, 0x0b, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70,
+ 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x48, 0x00, 0x52, 0x04, 0x74, 0x79, 0x70, 0x65,
+ 0x12, 0x2e, 0x0a, 0x05, 0x65, 0x72, 0x72, 0x6f, 0x72, 0x18, 0x0c, 0x20, 0x01, 0x28, 0x0b, 0x32,
+ 0x16, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75,
+ 0x66, 0x2e, 0x45, 0x6d, 0x70, 0x74, 0x79, 0x48, 0x00, 0x52, 0x05, 0x65, 0x72, 0x72, 0x6f, 0x72,
+ 0x12, 0x52, 0x0a, 0x0d, 0x61, 0x62, 0x73, 0x74, 0x72, 0x61, 0x63, 0x74, 0x5f, 0x74, 0x79, 0x70,
+ 0x65, 0x18, 0x0e, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68,
+ 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x2e, 0x41, 0x62, 0x73, 0x74, 0x72, 0x61, 0x63, 0x74,
+ 0x54, 0x79, 0x70, 0x65, 0x48, 0x00, 0x52, 0x0c, 0x61, 0x62, 0x73, 0x74, 0x72, 0x61, 0x63, 0x74,
+ 0x54, 0x79, 0x70, 0x65, 0x1a, 0x47, 0x0a, 0x08, 0x4c, 0x69, 0x73, 0x74, 0x54, 0x79, 0x70, 0x65,
+ 0x12, 0x3b, 0x0a, 0x09, 0x65, 0x6c, 0x65, 0x6d, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x01, 0x20,
+ 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69,
+ 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54,
+ 0x79, 0x70, 0x65, 0x52, 0x08, 0x65, 0x6c, 0x65, 0x6d, 0x54, 0x79, 0x70, 0x65, 0x1a, 0x83, 0x01,
+ 0x0a, 0x07, 0x4d, 0x61, 0x70, 0x54, 0x79, 0x70, 0x65, 0x12, 0x39, 0x0a, 0x08, 0x6b, 0x65, 0x79,
+ 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f,
+ 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31,
+ 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x52, 0x07, 0x6b, 0x65, 0x79,
+ 0x54, 0x79, 0x70, 0x65, 0x12, 0x3d, 0x0a, 0x0a, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x5f, 0x74, 0x79,
+ 0x70, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70,
+ 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x52, 0x09, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x54,
+ 0x79, 0x70, 0x65, 0x1a, 0x8c, 0x01, 0x0a, 0x0c, 0x46, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e,
+ 0x54, 0x79, 0x70, 0x65, 0x12, 0x3f, 0x0a, 0x0b, 0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x5f, 0x74,
+ 0x79, 0x70, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67,
+ 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c,
+ 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x52, 0x0a, 0x72, 0x65, 0x73, 0x75, 0x6c,
+ 0x74, 0x54, 0x79, 0x70, 0x65, 0x12, 0x3b, 0x0a, 0x09, 0x61, 0x72, 0x67, 0x5f, 0x74, 0x79, 0x70,
+ 0x65, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70,
+ 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x52, 0x08, 0x61, 0x72, 0x67, 0x54, 0x79, 0x70,
+ 0x65, 0x73, 0x1a, 0x6b, 0x0a, 0x0c, 0x41, 0x62, 0x73, 0x74, 0x72, 0x61, 0x63, 0x74, 0x54, 0x79,
+ 0x70, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09,
+ 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x47, 0x0a, 0x0f, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65,
+ 0x74, 0x65, 0x72, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32,
+ 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70,
+ 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x52,
+ 0x0e, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x54, 0x79, 0x70, 0x65, 0x73, 0x22,
+ 0x73, 0x0a, 0x0d, 0x50, 0x72, 0x69, 0x6d, 0x69, 0x74, 0x69, 0x76, 0x65, 0x54, 0x79, 0x70, 0x65,
+ 0x12, 0x1e, 0x0a, 0x1a, 0x50, 0x52, 0x49, 0x4d, 0x49, 0x54, 0x49, 0x56, 0x45, 0x5f, 0x54, 0x59,
+ 0x50, 0x45, 0x5f, 0x55, 0x4e, 0x53, 0x50, 0x45, 0x43, 0x49, 0x46, 0x49, 0x45, 0x44, 0x10, 0x00,
+ 0x12, 0x08, 0x0a, 0x04, 0x42, 0x4f, 0x4f, 0x4c, 0x10, 0x01, 0x12, 0x09, 0x0a, 0x05, 0x49, 0x4e,
+ 0x54, 0x36, 0x34, 0x10, 0x02, 0x12, 0x0a, 0x0a, 0x06, 0x55, 0x49, 0x4e, 0x54, 0x36, 0x34, 0x10,
+ 0x03, 0x12, 0x0a, 0x0a, 0x06, 0x44, 0x4f, 0x55, 0x42, 0x4c, 0x45, 0x10, 0x04, 0x12, 0x0a, 0x0a,
+ 0x06, 0x53, 0x54, 0x52, 0x49, 0x4e, 0x47, 0x10, 0x05, 0x12, 0x09, 0x0a, 0x05, 0x42, 0x59, 0x54,
+ 0x45, 0x53, 0x10, 0x06, 0x22, 0x56, 0x0a, 0x0d, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77,
+ 0x6e, 0x54, 0x79, 0x70, 0x65, 0x12, 0x1f, 0x0a, 0x1b, 0x57, 0x45, 0x4c, 0x4c, 0x5f, 0x4b, 0x4e,
+ 0x4f, 0x57, 0x4e, 0x5f, 0x54, 0x59, 0x50, 0x45, 0x5f, 0x55, 0x4e, 0x53, 0x50, 0x45, 0x43, 0x49,
+ 0x46, 0x49, 0x45, 0x44, 0x10, 0x00, 0x12, 0x07, 0x0a, 0x03, 0x41, 0x4e, 0x59, 0x10, 0x01, 0x12,
+ 0x0d, 0x0a, 0x09, 0x54, 0x49, 0x4d, 0x45, 0x53, 0x54, 0x41, 0x4d, 0x50, 0x10, 0x02, 0x12, 0x0c,
+ 0x0a, 0x08, 0x44, 0x55, 0x52, 0x41, 0x54, 0x49, 0x4f, 0x4e, 0x10, 0x03, 0x42, 0x0b, 0x0a, 0x09,
+ 0x74, 0x79, 0x70, 0x65, 0x5f, 0x6b, 0x69, 0x6e, 0x64, 0x22, 0xb3, 0x05, 0x0a, 0x04, 0x44, 0x65,
+ 0x63, 0x6c, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09,
+ 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x40, 0x0a, 0x05, 0x69, 0x64, 0x65, 0x6e, 0x74, 0x18,
+ 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x28, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61,
+ 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31,
+ 0x2e, 0x44, 0x65, 0x63, 0x6c, 0x2e, 0x49, 0x64, 0x65, 0x6e, 0x74, 0x44, 0x65, 0x63, 0x6c, 0x48,
+ 0x00, 0x52, 0x05, 0x69, 0x64, 0x65, 0x6e, 0x74, 0x12, 0x49, 0x0a, 0x08, 0x66, 0x75, 0x6e, 0x63,
+ 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61,
+ 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x44, 0x65, 0x63, 0x6c, 0x2e, 0x46, 0x75, 0x6e, 0x63, 0x74,
+ 0x69, 0x6f, 0x6e, 0x44, 0x65, 0x63, 0x6c, 0x48, 0x00, 0x52, 0x08, 0x66, 0x75, 0x6e, 0x63, 0x74,
+ 0x69, 0x6f, 0x6e, 0x1a, 0x8b, 0x01, 0x0a, 0x09, 0x49, 0x64, 0x65, 0x6e, 0x74, 0x44, 0x65, 0x63,
+ 0x6c, 0x12, 0x32, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32,
+ 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70,
+ 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79, 0x70, 0x65, 0x52,
+ 0x04, 0x74, 0x79, 0x70, 0x65, 0x12, 0x38, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02,
+ 0x20, 0x01, 0x28, 0x0b, 0x32, 0x22, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e,
+ 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x61, 0x6e, 0x74, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x12,
+ 0x10, 0x0a, 0x03, 0x64, 0x6f, 0x63, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x64, 0x6f,
+ 0x63, 0x1a, 0xee, 0x02, 0x0a, 0x0c, 0x46, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x44, 0x65,
+ 0x63, 0x6c, 0x12, 0x52, 0x0a, 0x09, 0x6f, 0x76, 0x65, 0x72, 0x6c, 0x6f, 0x61, 0x64, 0x73, 0x18,
+ 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x34, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61,
+ 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31,
+ 0x2e, 0x44, 0x65, 0x63, 0x6c, 0x2e, 0x46, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x44, 0x65,
+ 0x63, 0x6c, 0x2e, 0x4f, 0x76, 0x65, 0x72, 0x6c, 0x6f, 0x61, 0x64, 0x52, 0x09, 0x6f, 0x76, 0x65,
+ 0x72, 0x6c, 0x6f, 0x61, 0x64, 0x73, 0x1a, 0x89, 0x02, 0x0a, 0x08, 0x4f, 0x76, 0x65, 0x72, 0x6c,
+ 0x6f, 0x61, 0x64, 0x12, 0x1f, 0x0a, 0x0b, 0x6f, 0x76, 0x65, 0x72, 0x6c, 0x6f, 0x61, 0x64, 0x5f,
+ 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x6f, 0x76, 0x65, 0x72, 0x6c, 0x6f,
+ 0x61, 0x64, 0x49, 0x64, 0x12, 0x36, 0x0a, 0x06, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x73, 0x18, 0x02,
+ 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e,
+ 0x54, 0x79, 0x70, 0x65, 0x52, 0x06, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x73, 0x12, 0x1f, 0x0a, 0x0b,
+ 0x74, 0x79, 0x70, 0x65, 0x5f, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28,
+ 0x09, 0x52, 0x0a, 0x74, 0x79, 0x70, 0x65, 0x50, 0x61, 0x72, 0x61, 0x6d, 0x73, 0x12, 0x3f, 0x0a,
+ 0x0b, 0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x04, 0x20, 0x01,
+ 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e,
+ 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x54, 0x79,
+ 0x70, 0x65, 0x52, 0x0a, 0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x54, 0x79, 0x70, 0x65, 0x12, 0x30,
+ 0x0a, 0x14, 0x69, 0x73, 0x5f, 0x69, 0x6e, 0x73, 0x74, 0x61, 0x6e, 0x63, 0x65, 0x5f, 0x66, 0x75,
+ 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x05, 0x20, 0x01, 0x28, 0x08, 0x52, 0x12, 0x69, 0x73,
+ 0x49, 0x6e, 0x73, 0x74, 0x61, 0x6e, 0x63, 0x65, 0x46, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e,
+ 0x12, 0x10, 0x0a, 0x03, 0x64, 0x6f, 0x63, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x64,
+ 0x6f, 0x63, 0x42, 0x0b, 0x0a, 0x09, 0x64, 0x65, 0x63, 0x6c, 0x5f, 0x6b, 0x69, 0x6e, 0x64, 0x22,
+ 0x7a, 0x0a, 0x09, 0x52, 0x65, 0x66, 0x65, 0x72, 0x65, 0x6e, 0x63, 0x65, 0x12, 0x12, 0x0a, 0x04,
+ 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65,
+ 0x12, 0x1f, 0x0a, 0x0b, 0x6f, 0x76, 0x65, 0x72, 0x6c, 0x6f, 0x61, 0x64, 0x5f, 0x69, 0x64, 0x18,
+ 0x03, 0x20, 0x03, 0x28, 0x09, 0x52, 0x0a, 0x6f, 0x76, 0x65, 0x72, 0x6c, 0x6f, 0x61, 0x64, 0x49,
+ 0x64, 0x12, 0x38, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b,
+ 0x32, 0x22, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78,
+ 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x43, 0x6f, 0x6e, 0x73,
+ 0x74, 0x61, 0x6e, 0x74, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x42, 0x6c, 0x0a, 0x1c, 0x63,
+ 0x6f, 0x6d, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78,
+ 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x42, 0x09, 0x44, 0x65, 0x63,
+ 0x6c, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x3c, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x67, 0x65, 0x6e, 0x70,
+ 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x61, 0x70, 0x69, 0x73, 0x2f,
+ 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70, 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+ 0x31, 0x3b, 0x65, 0x78, 0x70, 0x72, 0xf8, 0x01, 0x01, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f,
+ 0x33,
+}
+
+var (
+ file_google_api_expr_v1alpha1_checked_proto_rawDescOnce sync.Once
+ file_google_api_expr_v1alpha1_checked_proto_rawDescData = file_google_api_expr_v1alpha1_checked_proto_rawDesc
+)
+
+func file_google_api_expr_v1alpha1_checked_proto_rawDescGZIP() []byte {
+ file_google_api_expr_v1alpha1_checked_proto_rawDescOnce.Do(func() {
+ file_google_api_expr_v1alpha1_checked_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_api_expr_v1alpha1_checked_proto_rawDescData)
+ })
+ return file_google_api_expr_v1alpha1_checked_proto_rawDescData
+}
+
+var file_google_api_expr_v1alpha1_checked_proto_enumTypes = make([]protoimpl.EnumInfo, 2)
+var file_google_api_expr_v1alpha1_checked_proto_msgTypes = make([]protoimpl.MessageInfo, 13)
+var file_google_api_expr_v1alpha1_checked_proto_goTypes = []interface{}{
+ (Type_PrimitiveType)(0), // 0: google.api.expr.v1alpha1.Type.PrimitiveType
+ (Type_WellKnownType)(0), // 1: google.api.expr.v1alpha1.Type.WellKnownType
+ (*CheckedExpr)(nil), // 2: google.api.expr.v1alpha1.CheckedExpr
+ (*Type)(nil), // 3: google.api.expr.v1alpha1.Type
+ (*Decl)(nil), // 4: google.api.expr.v1alpha1.Decl
+ (*Reference)(nil), // 5: google.api.expr.v1alpha1.Reference
+ nil, // 6: google.api.expr.v1alpha1.CheckedExpr.ReferenceMapEntry
+ nil, // 7: google.api.expr.v1alpha1.CheckedExpr.TypeMapEntry
+ (*Type_ListType)(nil), // 8: google.api.expr.v1alpha1.Type.ListType
+ (*Type_MapType)(nil), // 9: google.api.expr.v1alpha1.Type.MapType
+ (*Type_FunctionType)(nil), // 10: google.api.expr.v1alpha1.Type.FunctionType
+ (*Type_AbstractType)(nil), // 11: google.api.expr.v1alpha1.Type.AbstractType
+ (*Decl_IdentDecl)(nil), // 12: google.api.expr.v1alpha1.Decl.IdentDecl
+ (*Decl_FunctionDecl)(nil), // 13: google.api.expr.v1alpha1.Decl.FunctionDecl
+ (*Decl_FunctionDecl_Overload)(nil), // 14: google.api.expr.v1alpha1.Decl.FunctionDecl.Overload
+ (*SourceInfo)(nil), // 15: google.api.expr.v1alpha1.SourceInfo
+ (*Expr)(nil), // 16: google.api.expr.v1alpha1.Expr
+ (*emptypb.Empty)(nil), // 17: google.protobuf.Empty
+ (structpb.NullValue)(0), // 18: google.protobuf.NullValue
+ (*Constant)(nil), // 19: google.api.expr.v1alpha1.Constant
+}
+var file_google_api_expr_v1alpha1_checked_proto_depIdxs = []int32{
+ 6, // 0: google.api.expr.v1alpha1.CheckedExpr.reference_map:type_name -> google.api.expr.v1alpha1.CheckedExpr.ReferenceMapEntry
+ 7, // 1: google.api.expr.v1alpha1.CheckedExpr.type_map:type_name -> google.api.expr.v1alpha1.CheckedExpr.TypeMapEntry
+ 15, // 2: google.api.expr.v1alpha1.CheckedExpr.source_info:type_name -> google.api.expr.v1alpha1.SourceInfo
+ 16, // 3: google.api.expr.v1alpha1.CheckedExpr.expr:type_name -> google.api.expr.v1alpha1.Expr
+ 17, // 4: google.api.expr.v1alpha1.Type.dyn:type_name -> google.protobuf.Empty
+ 18, // 5: google.api.expr.v1alpha1.Type.null:type_name -> google.protobuf.NullValue
+ 0, // 6: google.api.expr.v1alpha1.Type.primitive:type_name -> google.api.expr.v1alpha1.Type.PrimitiveType
+ 0, // 7: google.api.expr.v1alpha1.Type.wrapper:type_name -> google.api.expr.v1alpha1.Type.PrimitiveType
+ 1, // 8: google.api.expr.v1alpha1.Type.well_known:type_name -> google.api.expr.v1alpha1.Type.WellKnownType
+ 8, // 9: google.api.expr.v1alpha1.Type.list_type:type_name -> google.api.expr.v1alpha1.Type.ListType
+ 9, // 10: google.api.expr.v1alpha1.Type.map_type:type_name -> google.api.expr.v1alpha1.Type.MapType
+ 10, // 11: google.api.expr.v1alpha1.Type.function:type_name -> google.api.expr.v1alpha1.Type.FunctionType
+ 3, // 12: google.api.expr.v1alpha1.Type.type:type_name -> google.api.expr.v1alpha1.Type
+ 17, // 13: google.api.expr.v1alpha1.Type.error:type_name -> google.protobuf.Empty
+ 11, // 14: google.api.expr.v1alpha1.Type.abstract_type:type_name -> google.api.expr.v1alpha1.Type.AbstractType
+ 12, // 15: google.api.expr.v1alpha1.Decl.ident:type_name -> google.api.expr.v1alpha1.Decl.IdentDecl
+ 13, // 16: google.api.expr.v1alpha1.Decl.function:type_name -> google.api.expr.v1alpha1.Decl.FunctionDecl
+ 19, // 17: google.api.expr.v1alpha1.Reference.value:type_name -> google.api.expr.v1alpha1.Constant
+ 5, // 18: google.api.expr.v1alpha1.CheckedExpr.ReferenceMapEntry.value:type_name -> google.api.expr.v1alpha1.Reference
+ 3, // 19: google.api.expr.v1alpha1.CheckedExpr.TypeMapEntry.value:type_name -> google.api.expr.v1alpha1.Type
+ 3, // 20: google.api.expr.v1alpha1.Type.ListType.elem_type:type_name -> google.api.expr.v1alpha1.Type
+ 3, // 21: google.api.expr.v1alpha1.Type.MapType.key_type:type_name -> google.api.expr.v1alpha1.Type
+ 3, // 22: google.api.expr.v1alpha1.Type.MapType.value_type:type_name -> google.api.expr.v1alpha1.Type
+ 3, // 23: google.api.expr.v1alpha1.Type.FunctionType.result_type:type_name -> google.api.expr.v1alpha1.Type
+ 3, // 24: google.api.expr.v1alpha1.Type.FunctionType.arg_types:type_name -> google.api.expr.v1alpha1.Type
+ 3, // 25: google.api.expr.v1alpha1.Type.AbstractType.parameter_types:type_name -> google.api.expr.v1alpha1.Type
+ 3, // 26: google.api.expr.v1alpha1.Decl.IdentDecl.type:type_name -> google.api.expr.v1alpha1.Type
+ 19, // 27: google.api.expr.v1alpha1.Decl.IdentDecl.value:type_name -> google.api.expr.v1alpha1.Constant
+ 14, // 28: google.api.expr.v1alpha1.Decl.FunctionDecl.overloads:type_name -> google.api.expr.v1alpha1.Decl.FunctionDecl.Overload
+ 3, // 29: google.api.expr.v1alpha1.Decl.FunctionDecl.Overload.params:type_name -> google.api.expr.v1alpha1.Type
+ 3, // 30: google.api.expr.v1alpha1.Decl.FunctionDecl.Overload.result_type:type_name -> google.api.expr.v1alpha1.Type
+ 31, // [31:31] is the sub-list for method output_type
+ 31, // [31:31] is the sub-list for method input_type
+ 31, // [31:31] is the sub-list for extension type_name
+ 31, // [31:31] is the sub-list for extension extendee
+ 0, // [0:31] is the sub-list for field type_name
+}
+
+func init() { file_google_api_expr_v1alpha1_checked_proto_init() }
+func file_google_api_expr_v1alpha1_checked_proto_init() {
+ if File_google_api_expr_v1alpha1_checked_proto != nil {
+ return
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_init()
+ if !protoimpl.UnsafeEnabled {
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*CheckedExpr); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Type); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Decl); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Reference); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Type_ListType); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Type_MapType); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[8].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Type_FunctionType); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[9].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Type_AbstractType); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[10].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Decl_IdentDecl); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[11].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Decl_FunctionDecl); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[12].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Decl_FunctionDecl_Overload); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[1].OneofWrappers = []interface{}{
+ (*Type_Dyn)(nil),
+ (*Type_Null)(nil),
+ (*Type_Primitive)(nil),
+ (*Type_Wrapper)(nil),
+ (*Type_WellKnown)(nil),
+ (*Type_ListType_)(nil),
+ (*Type_MapType_)(nil),
+ (*Type_Function)(nil),
+ (*Type_MessageType)(nil),
+ (*Type_TypeParam)(nil),
+ (*Type_Type)(nil),
+ (*Type_Error)(nil),
+ (*Type_AbstractType_)(nil),
+ }
+ file_google_api_expr_v1alpha1_checked_proto_msgTypes[2].OneofWrappers = []interface{}{
+ (*Decl_Ident)(nil),
+ (*Decl_Function)(nil),
+ }
+ type x struct{}
+ out := protoimpl.TypeBuilder{
+ File: protoimpl.DescBuilder{
+ GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+ RawDescriptor: file_google_api_expr_v1alpha1_checked_proto_rawDesc,
+ NumEnums: 2,
+ NumMessages: 13,
+ NumExtensions: 0,
+ NumServices: 0,
+ },
+ GoTypes: file_google_api_expr_v1alpha1_checked_proto_goTypes,
+ DependencyIndexes: file_google_api_expr_v1alpha1_checked_proto_depIdxs,
+ EnumInfos: file_google_api_expr_v1alpha1_checked_proto_enumTypes,
+ MessageInfos: file_google_api_expr_v1alpha1_checked_proto_msgTypes,
+ }.Build()
+ File_google_api_expr_v1alpha1_checked_proto = out.File
+ file_google_api_expr_v1alpha1_checked_proto_rawDesc = nil
+ file_google_api_expr_v1alpha1_checked_proto_goTypes = nil
+ file_google_api_expr_v1alpha1_checked_proto_depIdxs = nil
+}
diff --git a/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/eval.pb.go b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/eval.pb.go
new file mode 100644
index 0000000000..e1a8bcd661
--- /dev/null
+++ b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/eval.pb.go
@@ -0,0 +1,579 @@
+// Copyright 2020 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// protoc-gen-go v1.26.0
+// protoc v3.12.2
+// source: google/api/expr/v1alpha1/eval.proto
+
+package expr
+
+import (
+ reflect "reflect"
+ sync "sync"
+
+ status "google.golang.org/genproto/googleapis/rpc/status"
+ protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+ protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+)
+
+const (
+ // Verify that this generated code is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+ // Verify that runtime/protoimpl is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+// The state of an evaluation.
+//
+// Can represent an inital, partial, or completed state of evaluation.
+type EvalState struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The unique values referenced in this message.
+ Values []*ExprValue `protobuf:"bytes,1,rep,name=values,proto3" json:"values,omitempty"`
+ // An ordered list of results.
+ //
+ // Tracks the flow of evaluation through the expression.
+ // May be sparse.
+ Results []*EvalState_Result `protobuf:"bytes,3,rep,name=results,proto3" json:"results,omitempty"`
+}
+
+func (x *EvalState) Reset() {
+ *x = EvalState{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[0]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *EvalState) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*EvalState) ProtoMessage() {}
+
+func (x *EvalState) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[0]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use EvalState.ProtoReflect.Descriptor instead.
+func (*EvalState) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_eval_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *EvalState) GetValues() []*ExprValue {
+ if x != nil {
+ return x.Values
+ }
+ return nil
+}
+
+func (x *EvalState) GetResults() []*EvalState_Result {
+ if x != nil {
+ return x.Results
+ }
+ return nil
+}
+
+// The value of an evaluated expression.
+type ExprValue struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // An expression can resolve to a value, error or unknown.
+ //
+ // Types that are assignable to Kind:
+ // *ExprValue_Value
+ // *ExprValue_Error
+ // *ExprValue_Unknown
+ Kind isExprValue_Kind `protobuf_oneof:"kind"`
+}
+
+func (x *ExprValue) Reset() {
+ *x = ExprValue{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[1]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *ExprValue) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*ExprValue) ProtoMessage() {}
+
+func (x *ExprValue) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[1]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use ExprValue.ProtoReflect.Descriptor instead.
+func (*ExprValue) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_eval_proto_rawDescGZIP(), []int{1}
+}
+
+func (m *ExprValue) GetKind() isExprValue_Kind {
+ if m != nil {
+ return m.Kind
+ }
+ return nil
+}
+
+func (x *ExprValue) GetValue() *Value {
+ if x, ok := x.GetKind().(*ExprValue_Value); ok {
+ return x.Value
+ }
+ return nil
+}
+
+func (x *ExprValue) GetError() *ErrorSet {
+ if x, ok := x.GetKind().(*ExprValue_Error); ok {
+ return x.Error
+ }
+ return nil
+}
+
+func (x *ExprValue) GetUnknown() *UnknownSet {
+ if x, ok := x.GetKind().(*ExprValue_Unknown); ok {
+ return x.Unknown
+ }
+ return nil
+}
+
+type isExprValue_Kind interface {
+ isExprValue_Kind()
+}
+
+type ExprValue_Value struct {
+ // A concrete value.
+ Value *Value `protobuf:"bytes,1,opt,name=value,proto3,oneof"`
+}
+
+type ExprValue_Error struct {
+ // The set of errors in the critical path of evalution.
+ //
+ // Only errors in the critical path are included. For example,
+ // `( || true) && ` will only result in ``,
+ // while ` || ` will result in both `` and
+ // ``.
+ //
+ // Errors cause by the presence of other errors are not included in the
+ // set. For example `.foo`, `foo()`, and ` + 1` will
+ // only result in ``.
+ //
+ // Multiple errors *might* be included when evaluation could result
+ // in different errors. For example ` + ` and
+ // `foo(, )` may result in ``, `` or both.
+ // The exact subset of errors included for this case is unspecified and
+ // depends on the implementation details of the evaluator.
+ Error *ErrorSet `protobuf:"bytes,2,opt,name=error,proto3,oneof"`
+}
+
+type ExprValue_Unknown struct {
+ // The set of unknowns in the critical path of evaluation.
+ //
+ // Unknown behaves identically to Error with regards to propagation.
+ // Specifically, only unknowns in the critical path are included, unknowns
+ // caused by the presence of other unknowns are not included, and multiple
+ // unknowns *might* be included included when evaluation could result in
+ // different unknowns. For example:
+ //
+ // ( || true) && ->
+ // || ->
+ // .foo ->
+ // foo() ->
+ // + -> or
+ //
+ // Unknown takes precidence over Error in cases where a `Value` can short
+ // circuit the result:
+ //
+ // || ->
+ // && ->
+ //
+ // Errors take precidence in all other cases:
+ //
+ // + ->
+ // foo(, ) ->
+ Unknown *UnknownSet `protobuf:"bytes,3,opt,name=unknown,proto3,oneof"`
+}
+
+func (*ExprValue_Value) isExprValue_Kind() {}
+
+func (*ExprValue_Error) isExprValue_Kind() {}
+
+func (*ExprValue_Unknown) isExprValue_Kind() {}
+
+// A set of errors.
+//
+// The errors included depend on the context. See `ExprValue.error`.
+type ErrorSet struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The errors in the set.
+ Errors []*status.Status `protobuf:"bytes,1,rep,name=errors,proto3" json:"errors,omitempty"`
+}
+
+func (x *ErrorSet) Reset() {
+ *x = ErrorSet{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[2]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *ErrorSet) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*ErrorSet) ProtoMessage() {}
+
+func (x *ErrorSet) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[2]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use ErrorSet.ProtoReflect.Descriptor instead.
+func (*ErrorSet) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_eval_proto_rawDescGZIP(), []int{2}
+}
+
+func (x *ErrorSet) GetErrors() []*status.Status {
+ if x != nil {
+ return x.Errors
+ }
+ return nil
+}
+
+// A set of expressions for which the value is unknown.
+//
+// The unknowns included depend on the context. See `ExprValue.unknown`.
+type UnknownSet struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The ids of the expressions with unknown values.
+ Exprs []int64 `protobuf:"varint,1,rep,packed,name=exprs,proto3" json:"exprs,omitempty"`
+}
+
+func (x *UnknownSet) Reset() {
+ *x = UnknownSet{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[3]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *UnknownSet) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*UnknownSet) ProtoMessage() {}
+
+func (x *UnknownSet) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[3]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use UnknownSet.ProtoReflect.Descriptor instead.
+func (*UnknownSet) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_eval_proto_rawDescGZIP(), []int{3}
+}
+
+func (x *UnknownSet) GetExprs() []int64 {
+ if x != nil {
+ return x.Exprs
+ }
+ return nil
+}
+
+// A single evalution result.
+type EvalState_Result struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The id of the expression this result if for.
+ Expr int64 `protobuf:"varint,1,opt,name=expr,proto3" json:"expr,omitempty"`
+ // The index in `values` of the resulting value.
+ Value int64 `protobuf:"varint,2,opt,name=value,proto3" json:"value,omitempty"`
+}
+
+func (x *EvalState_Result) Reset() {
+ *x = EvalState_Result{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[4]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *EvalState_Result) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*EvalState_Result) ProtoMessage() {}
+
+func (x *EvalState_Result) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_eval_proto_msgTypes[4]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use EvalState_Result.ProtoReflect.Descriptor instead.
+func (*EvalState_Result) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_eval_proto_rawDescGZIP(), []int{0, 0}
+}
+
+func (x *EvalState_Result) GetExpr() int64 {
+ if x != nil {
+ return x.Expr
+ }
+ return 0
+}
+
+func (x *EvalState_Result) GetValue() int64 {
+ if x != nil {
+ return x.Value
+ }
+ return 0
+}
+
+var File_google_api_expr_v1alpha1_eval_proto protoreflect.FileDescriptor
+
+var file_google_api_expr_v1alpha1_eval_proto_rawDesc = []byte{
+ 0x0a, 0x23, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70,
+ 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2f, 0x65, 0x76, 0x61, 0x6c, 0x2e,
+ 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x18, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x1a,
+ 0x24, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70, 0x72,
+ 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x2e,
+ 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x17, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x72, 0x70,
+ 0x63, 0x2f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0xc2,
+ 0x01, 0x0a, 0x09, 0x45, 0x76, 0x61, 0x6c, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x3b, 0x0a, 0x06,
+ 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x67,
+ 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76,
+ 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x52, 0x06, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x12, 0x44, 0x0a, 0x07, 0x72, 0x65, 0x73,
+ 0x75, 0x6c, 0x74, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x2a, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61,
+ 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x76, 0x61, 0x6c, 0x53, 0x74, 0x61, 0x74, 0x65, 0x2e,
+ 0x52, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x52, 0x07, 0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x73, 0x1a,
+ 0x32, 0x0a, 0x06, 0x52, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x12, 0x12, 0x0a, 0x04, 0x65, 0x78, 0x70,
+ 0x72, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x04, 0x65, 0x78, 0x70, 0x72, 0x12, 0x14, 0x0a,
+ 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x03, 0x52, 0x05, 0x76, 0x61,
+ 0x6c, 0x75, 0x65, 0x22, 0xca, 0x01, 0x0a, 0x09, 0x45, 0x78, 0x70, 0x72, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x12, 0x37, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b,
+ 0x32, 0x1f, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78,
+ 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x48, 0x00, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x3a, 0x0a, 0x05, 0x65, 0x72,
+ 0x72, 0x6f, 0x72, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x22, 0x2e, 0x67, 0x6f, 0x6f, 0x67,
+ 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c,
+ 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x53, 0x65, 0x74, 0x48, 0x00, 0x52,
+ 0x05, 0x65, 0x72, 0x72, 0x6f, 0x72, 0x12, 0x40, 0x0a, 0x07, 0x75, 0x6e, 0x6b, 0x6e, 0x6f, 0x77,
+ 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68,
+ 0x61, 0x31, 0x2e, 0x55, 0x6e, 0x6b, 0x6e, 0x6f, 0x77, 0x6e, 0x53, 0x65, 0x74, 0x48, 0x00, 0x52,
+ 0x07, 0x75, 0x6e, 0x6b, 0x6e, 0x6f, 0x77, 0x6e, 0x42, 0x06, 0x0a, 0x04, 0x6b, 0x69, 0x6e, 0x64,
+ 0x22, 0x36, 0x0a, 0x08, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x53, 0x65, 0x74, 0x12, 0x2a, 0x0a, 0x06,
+ 0x65, 0x72, 0x72, 0x6f, 0x72, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x12, 0x2e, 0x67,
+ 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x72, 0x70, 0x63, 0x2e, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73,
+ 0x52, 0x06, 0x65, 0x72, 0x72, 0x6f, 0x72, 0x73, 0x22, 0x22, 0x0a, 0x0a, 0x55, 0x6e, 0x6b, 0x6e,
+ 0x6f, 0x77, 0x6e, 0x53, 0x65, 0x74, 0x12, 0x14, 0x0a, 0x05, 0x65, 0x78, 0x70, 0x72, 0x73, 0x18,
+ 0x01, 0x20, 0x03, 0x28, 0x03, 0x52, 0x05, 0x65, 0x78, 0x70, 0x72, 0x73, 0x42, 0x6c, 0x0a, 0x1c,
+ 0x63, 0x6f, 0x6d, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65,
+ 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x42, 0x09, 0x45, 0x76,
+ 0x61, 0x6c, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x3c, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x67, 0x65, 0x6e,
+ 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x61, 0x70, 0x69, 0x73,
+ 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70, 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68,
+ 0x61, 0x31, 0x3b, 0x65, 0x78, 0x70, 0x72, 0xf8, 0x01, 0x01, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74,
+ 0x6f, 0x33,
+}
+
+var (
+ file_google_api_expr_v1alpha1_eval_proto_rawDescOnce sync.Once
+ file_google_api_expr_v1alpha1_eval_proto_rawDescData = file_google_api_expr_v1alpha1_eval_proto_rawDesc
+)
+
+func file_google_api_expr_v1alpha1_eval_proto_rawDescGZIP() []byte {
+ file_google_api_expr_v1alpha1_eval_proto_rawDescOnce.Do(func() {
+ file_google_api_expr_v1alpha1_eval_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_api_expr_v1alpha1_eval_proto_rawDescData)
+ })
+ return file_google_api_expr_v1alpha1_eval_proto_rawDescData
+}
+
+var file_google_api_expr_v1alpha1_eval_proto_msgTypes = make([]protoimpl.MessageInfo, 5)
+var file_google_api_expr_v1alpha1_eval_proto_goTypes = []interface{}{
+ (*EvalState)(nil), // 0: google.api.expr.v1alpha1.EvalState
+ (*ExprValue)(nil), // 1: google.api.expr.v1alpha1.ExprValue
+ (*ErrorSet)(nil), // 2: google.api.expr.v1alpha1.ErrorSet
+ (*UnknownSet)(nil), // 3: google.api.expr.v1alpha1.UnknownSet
+ (*EvalState_Result)(nil), // 4: google.api.expr.v1alpha1.EvalState.Result
+ (*Value)(nil), // 5: google.api.expr.v1alpha1.Value
+ (*status.Status)(nil), // 6: google.rpc.Status
+}
+var file_google_api_expr_v1alpha1_eval_proto_depIdxs = []int32{
+ 1, // 0: google.api.expr.v1alpha1.EvalState.values:type_name -> google.api.expr.v1alpha1.ExprValue
+ 4, // 1: google.api.expr.v1alpha1.EvalState.results:type_name -> google.api.expr.v1alpha1.EvalState.Result
+ 5, // 2: google.api.expr.v1alpha1.ExprValue.value:type_name -> google.api.expr.v1alpha1.Value
+ 2, // 3: google.api.expr.v1alpha1.ExprValue.error:type_name -> google.api.expr.v1alpha1.ErrorSet
+ 3, // 4: google.api.expr.v1alpha1.ExprValue.unknown:type_name -> google.api.expr.v1alpha1.UnknownSet
+ 6, // 5: google.api.expr.v1alpha1.ErrorSet.errors:type_name -> google.rpc.Status
+ 6, // [6:6] is the sub-list for method output_type
+ 6, // [6:6] is the sub-list for method input_type
+ 6, // [6:6] is the sub-list for extension type_name
+ 6, // [6:6] is the sub-list for extension extendee
+ 0, // [0:6] is the sub-list for field type_name
+}
+
+func init() { file_google_api_expr_v1alpha1_eval_proto_init() }
+func file_google_api_expr_v1alpha1_eval_proto_init() {
+ if File_google_api_expr_v1alpha1_eval_proto != nil {
+ return
+ }
+ file_google_api_expr_v1alpha1_value_proto_init()
+ if !protoimpl.UnsafeEnabled {
+ file_google_api_expr_v1alpha1_eval_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*EvalState); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_eval_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*ExprValue); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_eval_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*ErrorSet); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_eval_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*UnknownSet); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_eval_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*EvalState_Result); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ }
+ file_google_api_expr_v1alpha1_eval_proto_msgTypes[1].OneofWrappers = []interface{}{
+ (*ExprValue_Value)(nil),
+ (*ExprValue_Error)(nil),
+ (*ExprValue_Unknown)(nil),
+ }
+ type x struct{}
+ out := protoimpl.TypeBuilder{
+ File: protoimpl.DescBuilder{
+ GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+ RawDescriptor: file_google_api_expr_v1alpha1_eval_proto_rawDesc,
+ NumEnums: 0,
+ NumMessages: 5,
+ NumExtensions: 0,
+ NumServices: 0,
+ },
+ GoTypes: file_google_api_expr_v1alpha1_eval_proto_goTypes,
+ DependencyIndexes: file_google_api_expr_v1alpha1_eval_proto_depIdxs,
+ MessageInfos: file_google_api_expr_v1alpha1_eval_proto_msgTypes,
+ }.Build()
+ File_google_api_expr_v1alpha1_eval_proto = out.File
+ file_google_api_expr_v1alpha1_eval_proto_rawDesc = nil
+ file_google_api_expr_v1alpha1_eval_proto_goTypes = nil
+ file_google_api_expr_v1alpha1_eval_proto_depIdxs = nil
+}
diff --git a/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/explain.pb.go b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/explain.pb.go
new file mode 100644
index 0000000000..7cc7c1bff9
--- /dev/null
+++ b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/explain.pb.go
@@ -0,0 +1,275 @@
+// Copyright 2020 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// protoc-gen-go v1.26.0
+// protoc v3.12.2
+// source: google/api/expr/v1alpha1/explain.proto
+
+package expr
+
+import (
+ reflect "reflect"
+ sync "sync"
+
+ protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+ protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+)
+
+const (
+ // Verify that this generated code is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+ // Verify that runtime/protoimpl is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+// Values of intermediate expressions produced when evaluating expression.
+// Deprecated, use `EvalState` instead.
+//
+// Deprecated: Do not use.
+type Explain struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // All of the observed values.
+ //
+ // The field value_index is an index in the values list.
+ // Separating values from steps is needed to remove redundant values.
+ Values []*Value `protobuf:"bytes,1,rep,name=values,proto3" json:"values,omitempty"`
+ // List of steps.
+ //
+ // Repeated evaluations of the same expression generate new ExprStep
+ // instances. The order of such ExprStep instances matches the order of
+ // elements returned by Comprehension.iter_range.
+ ExprSteps []*Explain_ExprStep `protobuf:"bytes,2,rep,name=expr_steps,json=exprSteps,proto3" json:"expr_steps,omitempty"`
+}
+
+func (x *Explain) Reset() {
+ *x = Explain{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_explain_proto_msgTypes[0]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Explain) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Explain) ProtoMessage() {}
+
+func (x *Explain) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_explain_proto_msgTypes[0]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Explain.ProtoReflect.Descriptor instead.
+func (*Explain) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_explain_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *Explain) GetValues() []*Value {
+ if x != nil {
+ return x.Values
+ }
+ return nil
+}
+
+func (x *Explain) GetExprSteps() []*Explain_ExprStep {
+ if x != nil {
+ return x.ExprSteps
+ }
+ return nil
+}
+
+// ID and value index of one step.
+type Explain_ExprStep struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // ID of corresponding Expr node.
+ Id int64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
+ // Index of the value in the values list.
+ ValueIndex int32 `protobuf:"varint,2,opt,name=value_index,json=valueIndex,proto3" json:"value_index,omitempty"`
+}
+
+func (x *Explain_ExprStep) Reset() {
+ *x = Explain_ExprStep{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_explain_proto_msgTypes[1]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Explain_ExprStep) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Explain_ExprStep) ProtoMessage() {}
+
+func (x *Explain_ExprStep) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_explain_proto_msgTypes[1]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Explain_ExprStep.ProtoReflect.Descriptor instead.
+func (*Explain_ExprStep) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_explain_proto_rawDescGZIP(), []int{0, 0}
+}
+
+func (x *Explain_ExprStep) GetId() int64 {
+ if x != nil {
+ return x.Id
+ }
+ return 0
+}
+
+func (x *Explain_ExprStep) GetValueIndex() int32 {
+ if x != nil {
+ return x.ValueIndex
+ }
+ return 0
+}
+
+var File_google_api_expr_v1alpha1_explain_proto protoreflect.FileDescriptor
+
+var file_google_api_expr_v1alpha1_explain_proto_rawDesc = []byte{
+ 0x0a, 0x26, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70,
+ 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2f, 0x65, 0x78, 0x70, 0x6c, 0x61,
+ 0x69, 0x6e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x18, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68,
+ 0x61, 0x31, 0x1a, 0x24, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65,
+ 0x78, 0x70, 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2f, 0x76, 0x61, 0x6c,
+ 0x75, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0xce, 0x01, 0x0a, 0x07, 0x45, 0x78, 0x70,
+ 0x6c, 0x61, 0x69, 0x6e, 0x12, 0x37, 0x0a, 0x06, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x18, 0x01,
+ 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1f, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e,
+ 0x56, 0x61, 0x6c, 0x75, 0x65, 0x52, 0x06, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x12, 0x49, 0x0a,
+ 0x0a, 0x65, 0x78, 0x70, 0x72, 0x5f, 0x73, 0x74, 0x65, 0x70, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28,
+ 0x0b, 0x32, 0x2a, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65,
+ 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70,
+ 0x6c, 0x61, 0x69, 0x6e, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x53, 0x74, 0x65, 0x70, 0x52, 0x09, 0x65,
+ 0x78, 0x70, 0x72, 0x53, 0x74, 0x65, 0x70, 0x73, 0x1a, 0x3b, 0x0a, 0x08, 0x45, 0x78, 0x70, 0x72,
+ 0x53, 0x74, 0x65, 0x70, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03,
+ 0x52, 0x02, 0x69, 0x64, 0x12, 0x1f, 0x0a, 0x0b, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x5f, 0x69, 0x6e,
+ 0x64, 0x65, 0x78, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0a, 0x76, 0x61, 0x6c, 0x75, 0x65,
+ 0x49, 0x6e, 0x64, 0x65, 0x78, 0x3a, 0x02, 0x18, 0x01, 0x42, 0x6f, 0x0a, 0x1c, 0x63, 0x6f, 0x6d,
+ 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72,
+ 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x42, 0x0c, 0x45, 0x78, 0x70, 0x6c, 0x61,
+ 0x69, 0x6e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x3c, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x67, 0x65, 0x6e,
+ 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x61, 0x70, 0x69, 0x73,
+ 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70, 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68,
+ 0x61, 0x31, 0x3b, 0x65, 0x78, 0x70, 0x72, 0xf8, 0x01, 0x01, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74,
+ 0x6f, 0x33,
+}
+
+var (
+ file_google_api_expr_v1alpha1_explain_proto_rawDescOnce sync.Once
+ file_google_api_expr_v1alpha1_explain_proto_rawDescData = file_google_api_expr_v1alpha1_explain_proto_rawDesc
+)
+
+func file_google_api_expr_v1alpha1_explain_proto_rawDescGZIP() []byte {
+ file_google_api_expr_v1alpha1_explain_proto_rawDescOnce.Do(func() {
+ file_google_api_expr_v1alpha1_explain_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_api_expr_v1alpha1_explain_proto_rawDescData)
+ })
+ return file_google_api_expr_v1alpha1_explain_proto_rawDescData
+}
+
+var file_google_api_expr_v1alpha1_explain_proto_msgTypes = make([]protoimpl.MessageInfo, 2)
+var file_google_api_expr_v1alpha1_explain_proto_goTypes = []interface{}{
+ (*Explain)(nil), // 0: google.api.expr.v1alpha1.Explain
+ (*Explain_ExprStep)(nil), // 1: google.api.expr.v1alpha1.Explain.ExprStep
+ (*Value)(nil), // 2: google.api.expr.v1alpha1.Value
+}
+var file_google_api_expr_v1alpha1_explain_proto_depIdxs = []int32{
+ 2, // 0: google.api.expr.v1alpha1.Explain.values:type_name -> google.api.expr.v1alpha1.Value
+ 1, // 1: google.api.expr.v1alpha1.Explain.expr_steps:type_name -> google.api.expr.v1alpha1.Explain.ExprStep
+ 2, // [2:2] is the sub-list for method output_type
+ 2, // [2:2] is the sub-list for method input_type
+ 2, // [2:2] is the sub-list for extension type_name
+ 2, // [2:2] is the sub-list for extension extendee
+ 0, // [0:2] is the sub-list for field type_name
+}
+
+func init() { file_google_api_expr_v1alpha1_explain_proto_init() }
+func file_google_api_expr_v1alpha1_explain_proto_init() {
+ if File_google_api_expr_v1alpha1_explain_proto != nil {
+ return
+ }
+ file_google_api_expr_v1alpha1_value_proto_init()
+ if !protoimpl.UnsafeEnabled {
+ file_google_api_expr_v1alpha1_explain_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Explain); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_explain_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Explain_ExprStep); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ }
+ type x struct{}
+ out := protoimpl.TypeBuilder{
+ File: protoimpl.DescBuilder{
+ GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+ RawDescriptor: file_google_api_expr_v1alpha1_explain_proto_rawDesc,
+ NumEnums: 0,
+ NumMessages: 2,
+ NumExtensions: 0,
+ NumServices: 0,
+ },
+ GoTypes: file_google_api_expr_v1alpha1_explain_proto_goTypes,
+ DependencyIndexes: file_google_api_expr_v1alpha1_explain_proto_depIdxs,
+ MessageInfos: file_google_api_expr_v1alpha1_explain_proto_msgTypes,
+ }.Build()
+ File_google_api_expr_v1alpha1_explain_proto = out.File
+ file_google_api_expr_v1alpha1_explain_proto_rawDesc = nil
+ file_google_api_expr_v1alpha1_explain_proto_goTypes = nil
+ file_google_api_expr_v1alpha1_explain_proto_depIdxs = nil
+}
diff --git a/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/syntax.pb.go b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/syntax.pb.go
new file mode 100644
index 0000000000..95cfea0eb0
--- /dev/null
+++ b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/syntax.pb.go
@@ -0,0 +1,1684 @@
+// Copyright 2020 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// protoc-gen-go v1.26.0
+// protoc v3.12.2
+// source: google/api/expr/v1alpha1/syntax.proto
+
+package expr
+
+import (
+ reflect "reflect"
+ sync "sync"
+
+ protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+ protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+ durationpb "google.golang.org/protobuf/types/known/durationpb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+ timestamppb "google.golang.org/protobuf/types/known/timestamppb"
+)
+
+const (
+ // Verify that this generated code is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+ // Verify that runtime/protoimpl is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+// An expression together with source information as returned by the parser.
+type ParsedExpr struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The parsed expression.
+ Expr *Expr `protobuf:"bytes,2,opt,name=expr,proto3" json:"expr,omitempty"`
+ // The source info derived from input that generated the parsed `expr`.
+ SourceInfo *SourceInfo `protobuf:"bytes,3,opt,name=source_info,json=sourceInfo,proto3" json:"source_info,omitempty"`
+}
+
+func (x *ParsedExpr) Reset() {
+ *x = ParsedExpr{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[0]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *ParsedExpr) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*ParsedExpr) ProtoMessage() {}
+
+func (x *ParsedExpr) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[0]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use ParsedExpr.ProtoReflect.Descriptor instead.
+func (*ParsedExpr) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *ParsedExpr) GetExpr() *Expr {
+ if x != nil {
+ return x.Expr
+ }
+ return nil
+}
+
+func (x *ParsedExpr) GetSourceInfo() *SourceInfo {
+ if x != nil {
+ return x.SourceInfo
+ }
+ return nil
+}
+
+// An abstract representation of a common expression.
+//
+// Expressions are abstractly represented as a collection of identifiers,
+// select statements, function calls, literals, and comprehensions. All
+// operators with the exception of the '.' operator are modelled as function
+// calls. This makes it easy to represent new operators into the existing AST.
+//
+// All references within expressions must resolve to a [Decl][google.api.expr.v1alpha1.Decl] provided at
+// type-check for an expression to be valid. A reference may either be a bare
+// identifier `name` or a qualified identifier `google.api.name`. References
+// may either refer to a value or a function declaration.
+//
+// For example, the expression `google.api.name.startsWith('expr')` references
+// the declaration `google.api.name` within a [Expr.Select][google.api.expr.v1alpha1.Expr.Select] expression, and
+// the function declaration `startsWith`.
+type Expr struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. An id assigned to this node by the parser which is unique in a
+ // given expression tree. This is used to associate type information and other
+ // attributes to a node in the parse tree.
+ Id int64 `protobuf:"varint,2,opt,name=id,proto3" json:"id,omitempty"`
+ // Required. Variants of expressions.
+ //
+ // Types that are assignable to ExprKind:
+ // *Expr_ConstExpr
+ // *Expr_IdentExpr
+ // *Expr_SelectExpr
+ // *Expr_CallExpr
+ // *Expr_ListExpr
+ // *Expr_StructExpr
+ // *Expr_ComprehensionExpr
+ ExprKind isExpr_ExprKind `protobuf_oneof:"expr_kind"`
+}
+
+func (x *Expr) Reset() {
+ *x = Expr{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[1]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Expr) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Expr) ProtoMessage() {}
+
+func (x *Expr) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[1]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Expr.ProtoReflect.Descriptor instead.
+func (*Expr) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{1}
+}
+
+func (x *Expr) GetId() int64 {
+ if x != nil {
+ return x.Id
+ }
+ return 0
+}
+
+func (m *Expr) GetExprKind() isExpr_ExprKind {
+ if m != nil {
+ return m.ExprKind
+ }
+ return nil
+}
+
+func (x *Expr) GetConstExpr() *Constant {
+ if x, ok := x.GetExprKind().(*Expr_ConstExpr); ok {
+ return x.ConstExpr
+ }
+ return nil
+}
+
+func (x *Expr) GetIdentExpr() *Expr_Ident {
+ if x, ok := x.GetExprKind().(*Expr_IdentExpr); ok {
+ return x.IdentExpr
+ }
+ return nil
+}
+
+func (x *Expr) GetSelectExpr() *Expr_Select {
+ if x, ok := x.GetExprKind().(*Expr_SelectExpr); ok {
+ return x.SelectExpr
+ }
+ return nil
+}
+
+func (x *Expr) GetCallExpr() *Expr_Call {
+ if x, ok := x.GetExprKind().(*Expr_CallExpr); ok {
+ return x.CallExpr
+ }
+ return nil
+}
+
+func (x *Expr) GetListExpr() *Expr_CreateList {
+ if x, ok := x.GetExprKind().(*Expr_ListExpr); ok {
+ return x.ListExpr
+ }
+ return nil
+}
+
+func (x *Expr) GetStructExpr() *Expr_CreateStruct {
+ if x, ok := x.GetExprKind().(*Expr_StructExpr); ok {
+ return x.StructExpr
+ }
+ return nil
+}
+
+func (x *Expr) GetComprehensionExpr() *Expr_Comprehension {
+ if x, ok := x.GetExprKind().(*Expr_ComprehensionExpr); ok {
+ return x.ComprehensionExpr
+ }
+ return nil
+}
+
+type isExpr_ExprKind interface {
+ isExpr_ExprKind()
+}
+
+type Expr_ConstExpr struct {
+ // A literal expression.
+ ConstExpr *Constant `protobuf:"bytes,3,opt,name=const_expr,json=constExpr,proto3,oneof"`
+}
+
+type Expr_IdentExpr struct {
+ // An identifier expression.
+ IdentExpr *Expr_Ident `protobuf:"bytes,4,opt,name=ident_expr,json=identExpr,proto3,oneof"`
+}
+
+type Expr_SelectExpr struct {
+ // A field selection expression, e.g. `request.auth`.
+ SelectExpr *Expr_Select `protobuf:"bytes,5,opt,name=select_expr,json=selectExpr,proto3,oneof"`
+}
+
+type Expr_CallExpr struct {
+ // A call expression, including calls to predefined functions and operators.
+ CallExpr *Expr_Call `protobuf:"bytes,6,opt,name=call_expr,json=callExpr,proto3,oneof"`
+}
+
+type Expr_ListExpr struct {
+ // A list creation expression.
+ ListExpr *Expr_CreateList `protobuf:"bytes,7,opt,name=list_expr,json=listExpr,proto3,oneof"`
+}
+
+type Expr_StructExpr struct {
+ // A map or message creation expression.
+ StructExpr *Expr_CreateStruct `protobuf:"bytes,8,opt,name=struct_expr,json=structExpr,proto3,oneof"`
+}
+
+type Expr_ComprehensionExpr struct {
+ // A comprehension expression.
+ ComprehensionExpr *Expr_Comprehension `protobuf:"bytes,9,opt,name=comprehension_expr,json=comprehensionExpr,proto3,oneof"`
+}
+
+func (*Expr_ConstExpr) isExpr_ExprKind() {}
+
+func (*Expr_IdentExpr) isExpr_ExprKind() {}
+
+func (*Expr_SelectExpr) isExpr_ExprKind() {}
+
+func (*Expr_CallExpr) isExpr_ExprKind() {}
+
+func (*Expr_ListExpr) isExpr_ExprKind() {}
+
+func (*Expr_StructExpr) isExpr_ExprKind() {}
+
+func (*Expr_ComprehensionExpr) isExpr_ExprKind() {}
+
+// Represents a primitive literal.
+//
+// Named 'Constant' here for backwards compatibility.
+//
+// This is similar as the primitives supported in the well-known type
+// `google.protobuf.Value`, but richer so it can represent CEL's full range of
+// primitives.
+//
+// Lists and structs are not included as constants as these aggregate types may
+// contain [Expr][google.api.expr.v1alpha1.Expr] elements which require evaluation and are thus not constant.
+//
+// Examples of literals include: `"hello"`, `b'bytes'`, `1u`, `4.2`, `-2`,
+// `true`, `null`.
+type Constant struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. The valid constant kinds.
+ //
+ // Types that are assignable to ConstantKind:
+ // *Constant_NullValue
+ // *Constant_BoolValue
+ // *Constant_Int64Value
+ // *Constant_Uint64Value
+ // *Constant_DoubleValue
+ // *Constant_StringValue
+ // *Constant_BytesValue
+ // *Constant_DurationValue
+ // *Constant_TimestampValue
+ ConstantKind isConstant_ConstantKind `protobuf_oneof:"constant_kind"`
+}
+
+func (x *Constant) Reset() {
+ *x = Constant{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[2]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Constant) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Constant) ProtoMessage() {}
+
+func (x *Constant) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[2]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Constant.ProtoReflect.Descriptor instead.
+func (*Constant) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{2}
+}
+
+func (m *Constant) GetConstantKind() isConstant_ConstantKind {
+ if m != nil {
+ return m.ConstantKind
+ }
+ return nil
+}
+
+func (x *Constant) GetNullValue() structpb.NullValue {
+ if x, ok := x.GetConstantKind().(*Constant_NullValue); ok {
+ return x.NullValue
+ }
+ return structpb.NullValue_NULL_VALUE
+}
+
+func (x *Constant) GetBoolValue() bool {
+ if x, ok := x.GetConstantKind().(*Constant_BoolValue); ok {
+ return x.BoolValue
+ }
+ return false
+}
+
+func (x *Constant) GetInt64Value() int64 {
+ if x, ok := x.GetConstantKind().(*Constant_Int64Value); ok {
+ return x.Int64Value
+ }
+ return 0
+}
+
+func (x *Constant) GetUint64Value() uint64 {
+ if x, ok := x.GetConstantKind().(*Constant_Uint64Value); ok {
+ return x.Uint64Value
+ }
+ return 0
+}
+
+func (x *Constant) GetDoubleValue() float64 {
+ if x, ok := x.GetConstantKind().(*Constant_DoubleValue); ok {
+ return x.DoubleValue
+ }
+ return 0
+}
+
+func (x *Constant) GetStringValue() string {
+ if x, ok := x.GetConstantKind().(*Constant_StringValue); ok {
+ return x.StringValue
+ }
+ return ""
+}
+
+func (x *Constant) GetBytesValue() []byte {
+ if x, ok := x.GetConstantKind().(*Constant_BytesValue); ok {
+ return x.BytesValue
+ }
+ return nil
+}
+
+// Deprecated: Do not use.
+func (x *Constant) GetDurationValue() *durationpb.Duration {
+ if x, ok := x.GetConstantKind().(*Constant_DurationValue); ok {
+ return x.DurationValue
+ }
+ return nil
+}
+
+// Deprecated: Do not use.
+func (x *Constant) GetTimestampValue() *timestamppb.Timestamp {
+ if x, ok := x.GetConstantKind().(*Constant_TimestampValue); ok {
+ return x.TimestampValue
+ }
+ return nil
+}
+
+type isConstant_ConstantKind interface {
+ isConstant_ConstantKind()
+}
+
+type Constant_NullValue struct {
+ // null value.
+ NullValue structpb.NullValue `protobuf:"varint,1,opt,name=null_value,json=nullValue,proto3,enum=google.protobuf.NullValue,oneof"`
+}
+
+type Constant_BoolValue struct {
+ // boolean value.
+ BoolValue bool `protobuf:"varint,2,opt,name=bool_value,json=boolValue,proto3,oneof"`
+}
+
+type Constant_Int64Value struct {
+ // int64 value.
+ Int64Value int64 `protobuf:"varint,3,opt,name=int64_value,json=int64Value,proto3,oneof"`
+}
+
+type Constant_Uint64Value struct {
+ // uint64 value.
+ Uint64Value uint64 `protobuf:"varint,4,opt,name=uint64_value,json=uint64Value,proto3,oneof"`
+}
+
+type Constant_DoubleValue struct {
+ // double value.
+ DoubleValue float64 `protobuf:"fixed64,5,opt,name=double_value,json=doubleValue,proto3,oneof"`
+}
+
+type Constant_StringValue struct {
+ // string value.
+ StringValue string `protobuf:"bytes,6,opt,name=string_value,json=stringValue,proto3,oneof"`
+}
+
+type Constant_BytesValue struct {
+ // bytes value.
+ BytesValue []byte `protobuf:"bytes,7,opt,name=bytes_value,json=bytesValue,proto3,oneof"`
+}
+
+type Constant_DurationValue struct {
+ // protobuf.Duration value.
+ //
+ // Deprecated: duration is no longer considered a builtin cel type.
+ //
+ // Deprecated: Do not use.
+ DurationValue *durationpb.Duration `protobuf:"bytes,8,opt,name=duration_value,json=durationValue,proto3,oneof"`
+}
+
+type Constant_TimestampValue struct {
+ // protobuf.Timestamp value.
+ //
+ // Deprecated: timestamp is no longer considered a builtin cel type.
+ //
+ // Deprecated: Do not use.
+ TimestampValue *timestamppb.Timestamp `protobuf:"bytes,9,opt,name=timestamp_value,json=timestampValue,proto3,oneof"`
+}
+
+func (*Constant_NullValue) isConstant_ConstantKind() {}
+
+func (*Constant_BoolValue) isConstant_ConstantKind() {}
+
+func (*Constant_Int64Value) isConstant_ConstantKind() {}
+
+func (*Constant_Uint64Value) isConstant_ConstantKind() {}
+
+func (*Constant_DoubleValue) isConstant_ConstantKind() {}
+
+func (*Constant_StringValue) isConstant_ConstantKind() {}
+
+func (*Constant_BytesValue) isConstant_ConstantKind() {}
+
+func (*Constant_DurationValue) isConstant_ConstantKind() {}
+
+func (*Constant_TimestampValue) isConstant_ConstantKind() {}
+
+// Source information collected at parse time.
+type SourceInfo struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The syntax version of the source, e.g. `cel1`.
+ SyntaxVersion string `protobuf:"bytes,1,opt,name=syntax_version,json=syntaxVersion,proto3" json:"syntax_version,omitempty"`
+ // The location name. All position information attached to an expression is
+ // relative to this location.
+ //
+ // The location could be a file, UI element, or similar. For example,
+ // `acme/app/AnvilPolicy.cel`.
+ Location string `protobuf:"bytes,2,opt,name=location,proto3" json:"location,omitempty"`
+ // Monotonically increasing list of character offsets where newlines appear.
+ //
+ // The line number of a given position is the index `i` where for a given
+ // `id` the `line_offsets[i] < id_positions[id] < line_offsets[i+1]`. The
+ // column may be derivd from `id_positions[id] - line_offsets[i]`.
+ LineOffsets []int32 `protobuf:"varint,3,rep,packed,name=line_offsets,json=lineOffsets,proto3" json:"line_offsets,omitempty"`
+ // A map from the parse node id (e.g. `Expr.id`) to the character offset
+ // within source.
+ Positions map[int64]int32 `protobuf:"bytes,4,rep,name=positions,proto3" json:"positions,omitempty" protobuf_key:"varint,1,opt,name=key,proto3" protobuf_val:"varint,2,opt,name=value,proto3"`
+ // A map from the parse node id where a macro replacement was made to the
+ // call `Expr` that resulted in a macro expansion.
+ //
+ // For example, `has(value.field)` is a function call that is replaced by a
+ // `test_only` field selection in the AST. Likewise, the call
+ // `list.exists(e, e > 10)` translates to a comprehension expression. The key
+ // in the map corresponds to the expression id of the expanded macro, and the
+ // value is the call `Expr` that was replaced.
+ MacroCalls map[int64]*Expr `protobuf:"bytes,5,rep,name=macro_calls,json=macroCalls,proto3" json:"macro_calls,omitempty" protobuf_key:"varint,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"`
+}
+
+func (x *SourceInfo) Reset() {
+ *x = SourceInfo{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[3]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *SourceInfo) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SourceInfo) ProtoMessage() {}
+
+func (x *SourceInfo) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[3]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use SourceInfo.ProtoReflect.Descriptor instead.
+func (*SourceInfo) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{3}
+}
+
+func (x *SourceInfo) GetSyntaxVersion() string {
+ if x != nil {
+ return x.SyntaxVersion
+ }
+ return ""
+}
+
+func (x *SourceInfo) GetLocation() string {
+ if x != nil {
+ return x.Location
+ }
+ return ""
+}
+
+func (x *SourceInfo) GetLineOffsets() []int32 {
+ if x != nil {
+ return x.LineOffsets
+ }
+ return nil
+}
+
+func (x *SourceInfo) GetPositions() map[int64]int32 {
+ if x != nil {
+ return x.Positions
+ }
+ return nil
+}
+
+func (x *SourceInfo) GetMacroCalls() map[int64]*Expr {
+ if x != nil {
+ return x.MacroCalls
+ }
+ return nil
+}
+
+// A specific position in source.
+type SourcePosition struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The soucre location name (e.g. file name).
+ Location string `protobuf:"bytes,1,opt,name=location,proto3" json:"location,omitempty"`
+ // The character offset.
+ Offset int32 `protobuf:"varint,2,opt,name=offset,proto3" json:"offset,omitempty"`
+ // The 1-based index of the starting line in the source text
+ // where the issue occurs, or 0 if unknown.
+ Line int32 `protobuf:"varint,3,opt,name=line,proto3" json:"line,omitempty"`
+ // The 0-based index of the starting position within the line of source text
+ // where the issue occurs. Only meaningful if line is nonzero.
+ Column int32 `protobuf:"varint,4,opt,name=column,proto3" json:"column,omitempty"`
+}
+
+func (x *SourcePosition) Reset() {
+ *x = SourcePosition{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[4]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *SourcePosition) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SourcePosition) ProtoMessage() {}
+
+func (x *SourcePosition) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[4]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use SourcePosition.ProtoReflect.Descriptor instead.
+func (*SourcePosition) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{4}
+}
+
+func (x *SourcePosition) GetLocation() string {
+ if x != nil {
+ return x.Location
+ }
+ return ""
+}
+
+func (x *SourcePosition) GetOffset() int32 {
+ if x != nil {
+ return x.Offset
+ }
+ return 0
+}
+
+func (x *SourcePosition) GetLine() int32 {
+ if x != nil {
+ return x.Line
+ }
+ return 0
+}
+
+func (x *SourcePosition) GetColumn() int32 {
+ if x != nil {
+ return x.Column
+ }
+ return 0
+}
+
+// An identifier expression. e.g. `request`.
+type Expr_Ident struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. Holds a single, unqualified identifier, possibly preceded by a
+ // '.'.
+ //
+ // Qualified names are represented by the [Expr.Select][google.api.expr.v1alpha1.Expr.Select] expression.
+ Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
+}
+
+func (x *Expr_Ident) Reset() {
+ *x = Expr_Ident{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[5]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Expr_Ident) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Expr_Ident) ProtoMessage() {}
+
+func (x *Expr_Ident) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[5]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Expr_Ident.ProtoReflect.Descriptor instead.
+func (*Expr_Ident) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{1, 0}
+}
+
+func (x *Expr_Ident) GetName() string {
+ if x != nil {
+ return x.Name
+ }
+ return ""
+}
+
+// A field selection expression. e.g. `request.auth`.
+type Expr_Select struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. The target of the selection expression.
+ //
+ // For example, in the select expression `request.auth`, the `request`
+ // portion of the expression is the `operand`.
+ Operand *Expr `protobuf:"bytes,1,opt,name=operand,proto3" json:"operand,omitempty"`
+ // Required. The name of the field to select.
+ //
+ // For example, in the select expression `request.auth`, the `auth` portion
+ // of the expression would be the `field`.
+ Field string `protobuf:"bytes,2,opt,name=field,proto3" json:"field,omitempty"`
+ // Whether the select is to be interpreted as a field presence test.
+ //
+ // This results from the macro `has(request.auth)`.
+ TestOnly bool `protobuf:"varint,3,opt,name=test_only,json=testOnly,proto3" json:"test_only,omitempty"`
+}
+
+func (x *Expr_Select) Reset() {
+ *x = Expr_Select{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[6]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Expr_Select) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Expr_Select) ProtoMessage() {}
+
+func (x *Expr_Select) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[6]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Expr_Select.ProtoReflect.Descriptor instead.
+func (*Expr_Select) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{1, 1}
+}
+
+func (x *Expr_Select) GetOperand() *Expr {
+ if x != nil {
+ return x.Operand
+ }
+ return nil
+}
+
+func (x *Expr_Select) GetField() string {
+ if x != nil {
+ return x.Field
+ }
+ return ""
+}
+
+func (x *Expr_Select) GetTestOnly() bool {
+ if x != nil {
+ return x.TestOnly
+ }
+ return false
+}
+
+// A call expression, including calls to predefined functions and operators.
+//
+// For example, `value == 10`, `size(map_value)`.
+type Expr_Call struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The target of an method call-style expression. For example, `x` in
+ // `x.f()`.
+ Target *Expr `protobuf:"bytes,1,opt,name=target,proto3" json:"target,omitempty"`
+ // Required. The name of the function or method being called.
+ Function string `protobuf:"bytes,2,opt,name=function,proto3" json:"function,omitempty"`
+ // The arguments.
+ Args []*Expr `protobuf:"bytes,3,rep,name=args,proto3" json:"args,omitempty"`
+}
+
+func (x *Expr_Call) Reset() {
+ *x = Expr_Call{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[7]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Expr_Call) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Expr_Call) ProtoMessage() {}
+
+func (x *Expr_Call) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[7]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Expr_Call.ProtoReflect.Descriptor instead.
+func (*Expr_Call) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{1, 2}
+}
+
+func (x *Expr_Call) GetTarget() *Expr {
+ if x != nil {
+ return x.Target
+ }
+ return nil
+}
+
+func (x *Expr_Call) GetFunction() string {
+ if x != nil {
+ return x.Function
+ }
+ return ""
+}
+
+func (x *Expr_Call) GetArgs() []*Expr {
+ if x != nil {
+ return x.Args
+ }
+ return nil
+}
+
+// A list creation expression.
+//
+// Lists may either be homogenous, e.g. `[1, 2, 3]`, or heterogenous, e.g.
+// `dyn([1, 'hello', 2.0])`
+type Expr_CreateList struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The elements part of the list.
+ Elements []*Expr `protobuf:"bytes,1,rep,name=elements,proto3" json:"elements,omitempty"`
+}
+
+func (x *Expr_CreateList) Reset() {
+ *x = Expr_CreateList{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[8]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Expr_CreateList) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Expr_CreateList) ProtoMessage() {}
+
+func (x *Expr_CreateList) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[8]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Expr_CreateList.ProtoReflect.Descriptor instead.
+func (*Expr_CreateList) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{1, 3}
+}
+
+func (x *Expr_CreateList) GetElements() []*Expr {
+ if x != nil {
+ return x.Elements
+ }
+ return nil
+}
+
+// A map or message creation expression.
+//
+// Maps are constructed as `{'key_name': 'value'}`. Message construction is
+// similar, but prefixed with a type name and composed of field ids:
+// `types.MyType{field_id: 'value'}`.
+type Expr_CreateStruct struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The type name of the message to be created, empty when creating map
+ // literals.
+ MessageName string `protobuf:"bytes,1,opt,name=message_name,json=messageName,proto3" json:"message_name,omitempty"`
+ // The entries in the creation expression.
+ Entries []*Expr_CreateStruct_Entry `protobuf:"bytes,2,rep,name=entries,proto3" json:"entries,omitempty"`
+}
+
+func (x *Expr_CreateStruct) Reset() {
+ *x = Expr_CreateStruct{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[9]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Expr_CreateStruct) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Expr_CreateStruct) ProtoMessage() {}
+
+func (x *Expr_CreateStruct) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[9]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Expr_CreateStruct.ProtoReflect.Descriptor instead.
+func (*Expr_CreateStruct) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{1, 4}
+}
+
+func (x *Expr_CreateStruct) GetMessageName() string {
+ if x != nil {
+ return x.MessageName
+ }
+ return ""
+}
+
+func (x *Expr_CreateStruct) GetEntries() []*Expr_CreateStruct_Entry {
+ if x != nil {
+ return x.Entries
+ }
+ return nil
+}
+
+// A comprehension expression applied to a list or map.
+//
+// Comprehensions are not part of the core syntax, but enabled with macros.
+// A macro matches a specific call signature within a parsed AST and replaces
+// the call with an alternate AST block. Macro expansion happens at parse
+// time.
+//
+// The following macros are supported within CEL:
+//
+// Aggregate type macros may be applied to all elements in a list or all keys
+// in a map:
+//
+// * `all`, `exists`, `exists_one` - test a predicate expression against
+// the inputs and return `true` if the predicate is satisfied for all,
+// any, or only one value `list.all(x, x < 10)`.
+// * `filter` - test a predicate expression against the inputs and return
+// the subset of elements which satisfy the predicate:
+// `payments.filter(p, p > 1000)`.
+// * `map` - apply an expression to all elements in the input and return the
+// output aggregate type: `[1, 2, 3].map(i, i * i)`.
+//
+// The `has(m.x)` macro tests whether the property `x` is present in struct
+// `m`. The semantics of this macro depend on the type of `m`. For proto2
+// messages `has(m.x)` is defined as 'defined, but not set`. For proto3, the
+// macro tests whether the property is set to its default. For map and struct
+// types, the macro tests whether the property `x` is defined on `m`.
+type Expr_Comprehension struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The name of the iteration variable.
+ IterVar string `protobuf:"bytes,1,opt,name=iter_var,json=iterVar,proto3" json:"iter_var,omitempty"`
+ // The range over which var iterates.
+ IterRange *Expr `protobuf:"bytes,2,opt,name=iter_range,json=iterRange,proto3" json:"iter_range,omitempty"`
+ // The name of the variable used for accumulation of the result.
+ AccuVar string `protobuf:"bytes,3,opt,name=accu_var,json=accuVar,proto3" json:"accu_var,omitempty"`
+ // The initial value of the accumulator.
+ AccuInit *Expr `protobuf:"bytes,4,opt,name=accu_init,json=accuInit,proto3" json:"accu_init,omitempty"`
+ // An expression which can contain iter_var and accu_var.
+ //
+ // Returns false when the result has been computed and may be used as
+ // a hint to short-circuit the remainder of the comprehension.
+ LoopCondition *Expr `protobuf:"bytes,5,opt,name=loop_condition,json=loopCondition,proto3" json:"loop_condition,omitempty"`
+ // An expression which can contain iter_var and accu_var.
+ //
+ // Computes the next value of accu_var.
+ LoopStep *Expr `protobuf:"bytes,6,opt,name=loop_step,json=loopStep,proto3" json:"loop_step,omitempty"`
+ // An expression which can contain accu_var.
+ //
+ // Computes the result.
+ Result *Expr `protobuf:"bytes,7,opt,name=result,proto3" json:"result,omitempty"`
+}
+
+func (x *Expr_Comprehension) Reset() {
+ *x = Expr_Comprehension{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[10]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Expr_Comprehension) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Expr_Comprehension) ProtoMessage() {}
+
+func (x *Expr_Comprehension) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[10]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Expr_Comprehension.ProtoReflect.Descriptor instead.
+func (*Expr_Comprehension) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{1, 5}
+}
+
+func (x *Expr_Comprehension) GetIterVar() string {
+ if x != nil {
+ return x.IterVar
+ }
+ return ""
+}
+
+func (x *Expr_Comprehension) GetIterRange() *Expr {
+ if x != nil {
+ return x.IterRange
+ }
+ return nil
+}
+
+func (x *Expr_Comprehension) GetAccuVar() string {
+ if x != nil {
+ return x.AccuVar
+ }
+ return ""
+}
+
+func (x *Expr_Comprehension) GetAccuInit() *Expr {
+ if x != nil {
+ return x.AccuInit
+ }
+ return nil
+}
+
+func (x *Expr_Comprehension) GetLoopCondition() *Expr {
+ if x != nil {
+ return x.LoopCondition
+ }
+ return nil
+}
+
+func (x *Expr_Comprehension) GetLoopStep() *Expr {
+ if x != nil {
+ return x.LoopStep
+ }
+ return nil
+}
+
+func (x *Expr_Comprehension) GetResult() *Expr {
+ if x != nil {
+ return x.Result
+ }
+ return nil
+}
+
+// Represents an entry.
+type Expr_CreateStruct_Entry struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. An id assigned to this node by the parser which is unique
+ // in a given expression tree. This is used to associate type
+ // information and other attributes to the node.
+ Id int64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
+ // The `Entry` key kinds.
+ //
+ // Types that are assignable to KeyKind:
+ // *Expr_CreateStruct_Entry_FieldKey
+ // *Expr_CreateStruct_Entry_MapKey
+ KeyKind isExpr_CreateStruct_Entry_KeyKind `protobuf_oneof:"key_kind"`
+ // Required. The value assigned to the key.
+ Value *Expr `protobuf:"bytes,4,opt,name=value,proto3" json:"value,omitempty"`
+}
+
+func (x *Expr_CreateStruct_Entry) Reset() {
+ *x = Expr_CreateStruct_Entry{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[11]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Expr_CreateStruct_Entry) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Expr_CreateStruct_Entry) ProtoMessage() {}
+
+func (x *Expr_CreateStruct_Entry) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_syntax_proto_msgTypes[11]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Expr_CreateStruct_Entry.ProtoReflect.Descriptor instead.
+func (*Expr_CreateStruct_Entry) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP(), []int{1, 4, 0}
+}
+
+func (x *Expr_CreateStruct_Entry) GetId() int64 {
+ if x != nil {
+ return x.Id
+ }
+ return 0
+}
+
+func (m *Expr_CreateStruct_Entry) GetKeyKind() isExpr_CreateStruct_Entry_KeyKind {
+ if m != nil {
+ return m.KeyKind
+ }
+ return nil
+}
+
+func (x *Expr_CreateStruct_Entry) GetFieldKey() string {
+ if x, ok := x.GetKeyKind().(*Expr_CreateStruct_Entry_FieldKey); ok {
+ return x.FieldKey
+ }
+ return ""
+}
+
+func (x *Expr_CreateStruct_Entry) GetMapKey() *Expr {
+ if x, ok := x.GetKeyKind().(*Expr_CreateStruct_Entry_MapKey); ok {
+ return x.MapKey
+ }
+ return nil
+}
+
+func (x *Expr_CreateStruct_Entry) GetValue() *Expr {
+ if x != nil {
+ return x.Value
+ }
+ return nil
+}
+
+type isExpr_CreateStruct_Entry_KeyKind interface {
+ isExpr_CreateStruct_Entry_KeyKind()
+}
+
+type Expr_CreateStruct_Entry_FieldKey struct {
+ // The field key for a message creator statement.
+ FieldKey string `protobuf:"bytes,2,opt,name=field_key,json=fieldKey,proto3,oneof"`
+}
+
+type Expr_CreateStruct_Entry_MapKey struct {
+ // The key expression for a map creation statement.
+ MapKey *Expr `protobuf:"bytes,3,opt,name=map_key,json=mapKey,proto3,oneof"`
+}
+
+func (*Expr_CreateStruct_Entry_FieldKey) isExpr_CreateStruct_Entry_KeyKind() {}
+
+func (*Expr_CreateStruct_Entry_MapKey) isExpr_CreateStruct_Entry_KeyKind() {}
+
+var File_google_api_expr_v1alpha1_syntax_proto protoreflect.FileDescriptor
+
+var file_google_api_expr_v1alpha1_syntax_proto_rawDesc = []byte{
+ 0x0a, 0x25, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70,
+ 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2f, 0x73, 0x79, 0x6e, 0x74, 0x61,
+ 0x78, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x18, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e,
+ 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+ 0x31, 0x1a, 0x1e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62,
+ 0x75, 0x66, 0x2f, 0x64, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x2e, 0x70, 0x72, 0x6f, 0x74,
+ 0x6f, 0x1a, 0x1c, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62,
+ 0x75, 0x66, 0x2f, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a,
+ 0x1f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66,
+ 0x2f, 0x74, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
+ 0x22, 0x87, 0x01, 0x0a, 0x0a, 0x50, 0x61, 0x72, 0x73, 0x65, 0x64, 0x45, 0x78, 0x70, 0x72, 0x12,
+ 0x32, 0x0a, 0x04, 0x65, 0x78, 0x70, 0x72, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e,
+ 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e,
+ 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x04, 0x65,
+ 0x78, 0x70, 0x72, 0x12, 0x45, 0x0a, 0x0b, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x5f, 0x69, 0x6e,
+ 0x66, 0x6f, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70,
+ 0x68, 0x61, 0x31, 0x2e, 0x53, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x0a,
+ 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x22, 0xdc, 0x0c, 0x0a, 0x04, 0x45,
+ 0x78, 0x70, 0x72, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x03, 0x52,
+ 0x02, 0x69, 0x64, 0x12, 0x43, 0x0a, 0x0a, 0x63, 0x6f, 0x6e, 0x73, 0x74, 0x5f, 0x65, 0x78, 0x70,
+ 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x22, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68,
+ 0x61, 0x31, 0x2e, 0x43, 0x6f, 0x6e, 0x73, 0x74, 0x61, 0x6e, 0x74, 0x48, 0x00, 0x52, 0x09, 0x63,
+ 0x6f, 0x6e, 0x73, 0x74, 0x45, 0x78, 0x70, 0x72, 0x12, 0x45, 0x0a, 0x0a, 0x69, 0x64, 0x65, 0x6e,
+ 0x74, 0x5f, 0x65, 0x78, 0x70, 0x72, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e, 0x67,
+ 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76,
+ 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x2e, 0x49, 0x64, 0x65,
+ 0x6e, 0x74, 0x48, 0x00, 0x52, 0x09, 0x69, 0x64, 0x65, 0x6e, 0x74, 0x45, 0x78, 0x70, 0x72, 0x12,
+ 0x48, 0x0a, 0x0b, 0x73, 0x65, 0x6c, 0x65, 0x63, 0x74, 0x5f, 0x65, 0x78, 0x70, 0x72, 0x18, 0x05,
+ 0x20, 0x01, 0x28, 0x0b, 0x32, 0x25, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e,
+ 0x45, 0x78, 0x70, 0x72, 0x2e, 0x53, 0x65, 0x6c, 0x65, 0x63, 0x74, 0x48, 0x00, 0x52, 0x0a, 0x73,
+ 0x65, 0x6c, 0x65, 0x63, 0x74, 0x45, 0x78, 0x70, 0x72, 0x12, 0x42, 0x0a, 0x09, 0x63, 0x61, 0x6c,
+ 0x6c, 0x5f, 0x65, 0x78, 0x70, 0x72, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x67,
+ 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76,
+ 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x2e, 0x43, 0x61, 0x6c,
+ 0x6c, 0x48, 0x00, 0x52, 0x08, 0x63, 0x61, 0x6c, 0x6c, 0x45, 0x78, 0x70, 0x72, 0x12, 0x48, 0x0a,
+ 0x09, 0x6c, 0x69, 0x73, 0x74, 0x5f, 0x65, 0x78, 0x70, 0x72, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0b,
+ 0x32, 0x29, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78,
+ 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72,
+ 0x2e, 0x43, 0x72, 0x65, 0x61, 0x74, 0x65, 0x4c, 0x69, 0x73, 0x74, 0x48, 0x00, 0x52, 0x08, 0x6c,
+ 0x69, 0x73, 0x74, 0x45, 0x78, 0x70, 0x72, 0x12, 0x4e, 0x0a, 0x0b, 0x73, 0x74, 0x72, 0x75, 0x63,
+ 0x74, 0x5f, 0x65, 0x78, 0x70, 0x72, 0x18, 0x08, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x67,
+ 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76,
+ 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x2e, 0x43, 0x72, 0x65,
+ 0x61, 0x74, 0x65, 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x48, 0x00, 0x52, 0x0a, 0x73, 0x74, 0x72,
+ 0x75, 0x63, 0x74, 0x45, 0x78, 0x70, 0x72, 0x12, 0x5d, 0x0a, 0x12, 0x63, 0x6f, 0x6d, 0x70, 0x72,
+ 0x65, 0x68, 0x65, 0x6e, 0x73, 0x69, 0x6f, 0x6e, 0x5f, 0x65, 0x78, 0x70, 0x72, 0x18, 0x09, 0x20,
+ 0x01, 0x28, 0x0b, 0x32, 0x2c, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69,
+ 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45,
+ 0x78, 0x70, 0x72, 0x2e, 0x43, 0x6f, 0x6d, 0x70, 0x72, 0x65, 0x68, 0x65, 0x6e, 0x73, 0x69, 0x6f,
+ 0x6e, 0x48, 0x00, 0x52, 0x11, 0x63, 0x6f, 0x6d, 0x70, 0x72, 0x65, 0x68, 0x65, 0x6e, 0x73, 0x69,
+ 0x6f, 0x6e, 0x45, 0x78, 0x70, 0x72, 0x1a, 0x1b, 0x0a, 0x05, 0x49, 0x64, 0x65, 0x6e, 0x74, 0x12,
+ 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e,
+ 0x61, 0x6d, 0x65, 0x1a, 0x75, 0x0a, 0x06, 0x53, 0x65, 0x6c, 0x65, 0x63, 0x74, 0x12, 0x38, 0x0a,
+ 0x07, 0x6f, 0x70, 0x65, 0x72, 0x61, 0x6e, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e,
+ 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72,
+ 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x07,
+ 0x6f, 0x70, 0x65, 0x72, 0x61, 0x6e, 0x64, 0x12, 0x14, 0x0a, 0x05, 0x66, 0x69, 0x65, 0x6c, 0x64,
+ 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x12, 0x1b, 0x0a,
+ 0x09, 0x74, 0x65, 0x73, 0x74, 0x5f, 0x6f, 0x6e, 0x6c, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08,
+ 0x52, 0x08, 0x74, 0x65, 0x73, 0x74, 0x4f, 0x6e, 0x6c, 0x79, 0x1a, 0x8e, 0x01, 0x0a, 0x04, 0x43,
+ 0x61, 0x6c, 0x6c, 0x12, 0x36, 0x0a, 0x06, 0x74, 0x61, 0x72, 0x67, 0x65, 0x74, 0x18, 0x01, 0x20,
+ 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69,
+ 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45,
+ 0x78, 0x70, 0x72, 0x52, 0x06, 0x74, 0x61, 0x72, 0x67, 0x65, 0x74, 0x12, 0x1a, 0x0a, 0x08, 0x66,
+ 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x66,
+ 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x32, 0x0a, 0x04, 0x61, 0x72, 0x67, 0x73, 0x18,
+ 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61,
+ 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31,
+ 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x04, 0x61, 0x72, 0x67, 0x73, 0x1a, 0x48, 0x0a, 0x0a, 0x43,
+ 0x72, 0x65, 0x61, 0x74, 0x65, 0x4c, 0x69, 0x73, 0x74, 0x12, 0x3a, 0x0a, 0x08, 0x65, 0x6c, 0x65,
+ 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f,
+ 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31,
+ 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x08, 0x65, 0x6c, 0x65,
+ 0x6d, 0x65, 0x6e, 0x74, 0x73, 0x1a, 0xb4, 0x02, 0x0a, 0x0c, 0x43, 0x72, 0x65, 0x61, 0x74, 0x65,
+ 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x12, 0x21, 0x0a, 0x0c, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67,
+ 0x65, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x6d, 0x65,
+ 0x73, 0x73, 0x61, 0x67, 0x65, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x4b, 0x0a, 0x07, 0x65, 0x6e, 0x74,
+ 0x72, 0x69, 0x65, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x31, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61,
+ 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x2e, 0x43, 0x72, 0x65, 0x61, 0x74,
+ 0x65, 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x2e, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x07, 0x65,
+ 0x6e, 0x74, 0x72, 0x69, 0x65, 0x73, 0x1a, 0xb3, 0x01, 0x0a, 0x05, 0x45, 0x6e, 0x74, 0x72, 0x79,
+ 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x02, 0x69, 0x64,
+ 0x12, 0x1d, 0x0a, 0x09, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x5f, 0x6b, 0x65, 0x79, 0x18, 0x02, 0x20,
+ 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x08, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x4b, 0x65, 0x79, 0x12,
+ 0x39, 0x0a, 0x07, 0x6d, 0x61, 0x70, 0x5f, 0x6b, 0x65, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b,
+ 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78,
+ 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72,
+ 0x48, 0x00, 0x52, 0x06, 0x6d, 0x61, 0x70, 0x4b, 0x65, 0x79, 0x12, 0x34, 0x0a, 0x05, 0x76, 0x61,
+ 0x6c, 0x75, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67,
+ 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c,
+ 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65,
+ 0x42, 0x0a, 0x0a, 0x08, 0x6b, 0x65, 0x79, 0x5f, 0x6b, 0x69, 0x6e, 0x64, 0x1a, 0xfd, 0x02, 0x0a,
+ 0x0d, 0x43, 0x6f, 0x6d, 0x70, 0x72, 0x65, 0x68, 0x65, 0x6e, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x19,
+ 0x0a, 0x08, 0x69, 0x74, 0x65, 0x72, 0x5f, 0x76, 0x61, 0x72, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09,
+ 0x52, 0x07, 0x69, 0x74, 0x65, 0x72, 0x56, 0x61, 0x72, 0x12, 0x3d, 0x0a, 0x0a, 0x69, 0x74, 0x65,
+ 0x72, 0x5f, 0x72, 0x61, 0x6e, 0x67, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e,
+ 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e,
+ 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x09, 0x69,
+ 0x74, 0x65, 0x72, 0x52, 0x61, 0x6e, 0x67, 0x65, 0x12, 0x19, 0x0a, 0x08, 0x61, 0x63, 0x63, 0x75,
+ 0x5f, 0x76, 0x61, 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x61, 0x63, 0x63, 0x75,
+ 0x56, 0x61, 0x72, 0x12, 0x3b, 0x0a, 0x09, 0x61, 0x63, 0x63, 0x75, 0x5f, 0x69, 0x6e, 0x69, 0x74,
+ 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e,
+ 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+ 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x08, 0x61, 0x63, 0x63, 0x75, 0x49, 0x6e, 0x69, 0x74,
+ 0x12, 0x45, 0x0a, 0x0e, 0x6c, 0x6f, 0x6f, 0x70, 0x5f, 0x63, 0x6f, 0x6e, 0x64, 0x69, 0x74, 0x69,
+ 0x6f, 0x6e, 0x18, 0x05, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70,
+ 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x0d, 0x6c, 0x6f, 0x6f, 0x70, 0x43, 0x6f,
+ 0x6e, 0x64, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x3b, 0x0a, 0x09, 0x6c, 0x6f, 0x6f, 0x70, 0x5f,
+ 0x73, 0x74, 0x65, 0x70, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61,
+ 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x08, 0x6c, 0x6f, 0x6f, 0x70,
+ 0x53, 0x74, 0x65, 0x70, 0x12, 0x36, 0x0a, 0x06, 0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x18, 0x07,
+ 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e,
+ 0x45, 0x78, 0x70, 0x72, 0x52, 0x06, 0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x42, 0x0b, 0x0a, 0x09,
+ 0x65, 0x78, 0x70, 0x72, 0x5f, 0x6b, 0x69, 0x6e, 0x64, 0x22, 0xc1, 0x03, 0x0a, 0x08, 0x43, 0x6f,
+ 0x6e, 0x73, 0x74, 0x61, 0x6e, 0x74, 0x12, 0x3b, 0x0a, 0x0a, 0x6e, 0x75, 0x6c, 0x6c, 0x5f, 0x76,
+ 0x61, 0x6c, 0x75, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x1a, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4e, 0x75, 0x6c,
+ 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x48, 0x00, 0x52, 0x09, 0x6e, 0x75, 0x6c, 0x6c, 0x56, 0x61,
+ 0x6c, 0x75, 0x65, 0x12, 0x1f, 0x0a, 0x0a, 0x62, 0x6f, 0x6f, 0x6c, 0x5f, 0x76, 0x61, 0x6c, 0x75,
+ 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x08, 0x48, 0x00, 0x52, 0x09, 0x62, 0x6f, 0x6f, 0x6c, 0x56,
+ 0x61, 0x6c, 0x75, 0x65, 0x12, 0x21, 0x0a, 0x0b, 0x69, 0x6e, 0x74, 0x36, 0x34, 0x5f, 0x76, 0x61,
+ 0x6c, 0x75, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x03, 0x48, 0x00, 0x52, 0x0a, 0x69, 0x6e, 0x74,
+ 0x36, 0x34, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x23, 0x0a, 0x0c, 0x75, 0x69, 0x6e, 0x74, 0x36,
+ 0x34, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x04, 0x48, 0x00, 0x52,
+ 0x0b, 0x75, 0x69, 0x6e, 0x74, 0x36, 0x34, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x23, 0x0a, 0x0c,
+ 0x64, 0x6f, 0x75, 0x62, 0x6c, 0x65, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x05, 0x20, 0x01,
+ 0x28, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x64, 0x6f, 0x75, 0x62, 0x6c, 0x65, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x12, 0x23, 0x0a, 0x0c, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x5f, 0x76, 0x61, 0x6c, 0x75,
+ 0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x0b, 0x73, 0x74, 0x72, 0x69, 0x6e,
+ 0x67, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x21, 0x0a, 0x0b, 0x62, 0x79, 0x74, 0x65, 0x73, 0x5f,
+ 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0c, 0x48, 0x00, 0x52, 0x0a, 0x62,
+ 0x79, 0x74, 0x65, 0x73, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x46, 0x0a, 0x0e, 0x64, 0x75, 0x72,
+ 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x08, 0x20, 0x01, 0x28,
+ 0x0b, 0x32, 0x19, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
+ 0x62, 0x75, 0x66, 0x2e, 0x44, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x42, 0x02, 0x18, 0x01,
+ 0x48, 0x00, 0x52, 0x0d, 0x64, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x12, 0x49, 0x0a, 0x0f, 0x74, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x5f, 0x76,
+ 0x61, 0x6c, 0x75, 0x65, 0x18, 0x09, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1a, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x54, 0x69, 0x6d,
+ 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x42, 0x02, 0x18, 0x01, 0x48, 0x00, 0x52, 0x0e, 0x74, 0x69,
+ 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x42, 0x0f, 0x0a, 0x0d,
+ 0x63, 0x6f, 0x6e, 0x73, 0x74, 0x61, 0x6e, 0x74, 0x5f, 0x6b, 0x69, 0x6e, 0x64, 0x22, 0xb9, 0x03,
+ 0x0a, 0x0a, 0x53, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x12, 0x25, 0x0a, 0x0e,
+ 0x73, 0x79, 0x6e, 0x74, 0x61, 0x78, 0x5f, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x01,
+ 0x20, 0x01, 0x28, 0x09, 0x52, 0x0d, 0x73, 0x79, 0x6e, 0x74, 0x61, 0x78, 0x56, 0x65, 0x72, 0x73,
+ 0x69, 0x6f, 0x6e, 0x12, 0x1a, 0x0a, 0x08, 0x6c, 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x18,
+ 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x6c, 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12,
+ 0x21, 0x0a, 0x0c, 0x6c, 0x69, 0x6e, 0x65, 0x5f, 0x6f, 0x66, 0x66, 0x73, 0x65, 0x74, 0x73, 0x18,
+ 0x03, 0x20, 0x03, 0x28, 0x05, 0x52, 0x0b, 0x6c, 0x69, 0x6e, 0x65, 0x4f, 0x66, 0x66, 0x73, 0x65,
+ 0x74, 0x73, 0x12, 0x51, 0x0a, 0x09, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x18,
+ 0x04, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x33, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61,
+ 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31,
+ 0x2e, 0x53, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x2e, 0x50, 0x6f, 0x73, 0x69,
+ 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x09, 0x70, 0x6f, 0x73, 0x69,
+ 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x55, 0x0a, 0x0b, 0x6d, 0x61, 0x63, 0x72, 0x6f, 0x5f, 0x63,
+ 0x61, 0x6c, 0x6c, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x34, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61,
+ 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x53, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f,
+ 0x2e, 0x4d, 0x61, 0x63, 0x72, 0x6f, 0x43, 0x61, 0x6c, 0x6c, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79,
+ 0x52, 0x0a, 0x6d, 0x61, 0x63, 0x72, 0x6f, 0x43, 0x61, 0x6c, 0x6c, 0x73, 0x1a, 0x3c, 0x0a, 0x0e,
+ 0x50, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10,
+ 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x03, 0x6b, 0x65, 0x79,
+ 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52,
+ 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x1a, 0x5d, 0x0a, 0x0f, 0x4d, 0x61,
+ 0x63, 0x72, 0x6f, 0x43, 0x61, 0x6c, 0x6c, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a,
+ 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12,
+ 0x34, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e,
+ 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72,
+ 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x78, 0x70, 0x72, 0x52, 0x05,
+ 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x70, 0x0a, 0x0e, 0x53, 0x6f, 0x75,
+ 0x72, 0x63, 0x65, 0x50, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x1a, 0x0a, 0x08, 0x6c,
+ 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x6c,
+ 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x16, 0x0a, 0x06, 0x6f, 0x66, 0x66, 0x73, 0x65,
+ 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x06, 0x6f, 0x66, 0x66, 0x73, 0x65, 0x74, 0x12,
+ 0x12, 0x0a, 0x04, 0x6c, 0x69, 0x6e, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x05, 0x52, 0x04, 0x6c,
+ 0x69, 0x6e, 0x65, 0x12, 0x16, 0x0a, 0x06, 0x63, 0x6f, 0x6c, 0x75, 0x6d, 0x6e, 0x18, 0x04, 0x20,
+ 0x01, 0x28, 0x05, 0x52, 0x06, 0x63, 0x6f, 0x6c, 0x75, 0x6d, 0x6e, 0x42, 0x6e, 0x0a, 0x1c, 0x63,
+ 0x6f, 0x6d, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78,
+ 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x42, 0x0b, 0x53, 0x79, 0x6e,
+ 0x74, 0x61, 0x78, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x3c, 0x67, 0x6f, 0x6f, 0x67,
+ 0x6c, 0x65, 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x67, 0x65,
+ 0x6e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x61, 0x70, 0x69,
+ 0x73, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70, 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70,
+ 0x68, 0x61, 0x31, 0x3b, 0x65, 0x78, 0x70, 0x72, 0xf8, 0x01, 0x01, 0x62, 0x06, 0x70, 0x72, 0x6f,
+ 0x74, 0x6f, 0x33,
+}
+
+var (
+ file_google_api_expr_v1alpha1_syntax_proto_rawDescOnce sync.Once
+ file_google_api_expr_v1alpha1_syntax_proto_rawDescData = file_google_api_expr_v1alpha1_syntax_proto_rawDesc
+)
+
+func file_google_api_expr_v1alpha1_syntax_proto_rawDescGZIP() []byte {
+ file_google_api_expr_v1alpha1_syntax_proto_rawDescOnce.Do(func() {
+ file_google_api_expr_v1alpha1_syntax_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_api_expr_v1alpha1_syntax_proto_rawDescData)
+ })
+ return file_google_api_expr_v1alpha1_syntax_proto_rawDescData
+}
+
+var file_google_api_expr_v1alpha1_syntax_proto_msgTypes = make([]protoimpl.MessageInfo, 14)
+var file_google_api_expr_v1alpha1_syntax_proto_goTypes = []interface{}{
+ (*ParsedExpr)(nil), // 0: google.api.expr.v1alpha1.ParsedExpr
+ (*Expr)(nil), // 1: google.api.expr.v1alpha1.Expr
+ (*Constant)(nil), // 2: google.api.expr.v1alpha1.Constant
+ (*SourceInfo)(nil), // 3: google.api.expr.v1alpha1.SourceInfo
+ (*SourcePosition)(nil), // 4: google.api.expr.v1alpha1.SourcePosition
+ (*Expr_Ident)(nil), // 5: google.api.expr.v1alpha1.Expr.Ident
+ (*Expr_Select)(nil), // 6: google.api.expr.v1alpha1.Expr.Select
+ (*Expr_Call)(nil), // 7: google.api.expr.v1alpha1.Expr.Call
+ (*Expr_CreateList)(nil), // 8: google.api.expr.v1alpha1.Expr.CreateList
+ (*Expr_CreateStruct)(nil), // 9: google.api.expr.v1alpha1.Expr.CreateStruct
+ (*Expr_Comprehension)(nil), // 10: google.api.expr.v1alpha1.Expr.Comprehension
+ (*Expr_CreateStruct_Entry)(nil), // 11: google.api.expr.v1alpha1.Expr.CreateStruct.Entry
+ nil, // 12: google.api.expr.v1alpha1.SourceInfo.PositionsEntry
+ nil, // 13: google.api.expr.v1alpha1.SourceInfo.MacroCallsEntry
+ (structpb.NullValue)(0), // 14: google.protobuf.NullValue
+ (*durationpb.Duration)(nil), // 15: google.protobuf.Duration
+ (*timestamppb.Timestamp)(nil), // 16: google.protobuf.Timestamp
+}
+var file_google_api_expr_v1alpha1_syntax_proto_depIdxs = []int32{
+ 1, // 0: google.api.expr.v1alpha1.ParsedExpr.expr:type_name -> google.api.expr.v1alpha1.Expr
+ 3, // 1: google.api.expr.v1alpha1.ParsedExpr.source_info:type_name -> google.api.expr.v1alpha1.SourceInfo
+ 2, // 2: google.api.expr.v1alpha1.Expr.const_expr:type_name -> google.api.expr.v1alpha1.Constant
+ 5, // 3: google.api.expr.v1alpha1.Expr.ident_expr:type_name -> google.api.expr.v1alpha1.Expr.Ident
+ 6, // 4: google.api.expr.v1alpha1.Expr.select_expr:type_name -> google.api.expr.v1alpha1.Expr.Select
+ 7, // 5: google.api.expr.v1alpha1.Expr.call_expr:type_name -> google.api.expr.v1alpha1.Expr.Call
+ 8, // 6: google.api.expr.v1alpha1.Expr.list_expr:type_name -> google.api.expr.v1alpha1.Expr.CreateList
+ 9, // 7: google.api.expr.v1alpha1.Expr.struct_expr:type_name -> google.api.expr.v1alpha1.Expr.CreateStruct
+ 10, // 8: google.api.expr.v1alpha1.Expr.comprehension_expr:type_name -> google.api.expr.v1alpha1.Expr.Comprehension
+ 14, // 9: google.api.expr.v1alpha1.Constant.null_value:type_name -> google.protobuf.NullValue
+ 15, // 10: google.api.expr.v1alpha1.Constant.duration_value:type_name -> google.protobuf.Duration
+ 16, // 11: google.api.expr.v1alpha1.Constant.timestamp_value:type_name -> google.protobuf.Timestamp
+ 12, // 12: google.api.expr.v1alpha1.SourceInfo.positions:type_name -> google.api.expr.v1alpha1.SourceInfo.PositionsEntry
+ 13, // 13: google.api.expr.v1alpha1.SourceInfo.macro_calls:type_name -> google.api.expr.v1alpha1.SourceInfo.MacroCallsEntry
+ 1, // 14: google.api.expr.v1alpha1.Expr.Select.operand:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 15: google.api.expr.v1alpha1.Expr.Call.target:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 16: google.api.expr.v1alpha1.Expr.Call.args:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 17: google.api.expr.v1alpha1.Expr.CreateList.elements:type_name -> google.api.expr.v1alpha1.Expr
+ 11, // 18: google.api.expr.v1alpha1.Expr.CreateStruct.entries:type_name -> google.api.expr.v1alpha1.Expr.CreateStruct.Entry
+ 1, // 19: google.api.expr.v1alpha1.Expr.Comprehension.iter_range:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 20: google.api.expr.v1alpha1.Expr.Comprehension.accu_init:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 21: google.api.expr.v1alpha1.Expr.Comprehension.loop_condition:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 22: google.api.expr.v1alpha1.Expr.Comprehension.loop_step:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 23: google.api.expr.v1alpha1.Expr.Comprehension.result:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 24: google.api.expr.v1alpha1.Expr.CreateStruct.Entry.map_key:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 25: google.api.expr.v1alpha1.Expr.CreateStruct.Entry.value:type_name -> google.api.expr.v1alpha1.Expr
+ 1, // 26: google.api.expr.v1alpha1.SourceInfo.MacroCallsEntry.value:type_name -> google.api.expr.v1alpha1.Expr
+ 27, // [27:27] is the sub-list for method output_type
+ 27, // [27:27] is the sub-list for method input_type
+ 27, // [27:27] is the sub-list for extension type_name
+ 27, // [27:27] is the sub-list for extension extendee
+ 0, // [0:27] is the sub-list for field type_name
+}
+
+func init() { file_google_api_expr_v1alpha1_syntax_proto_init() }
+func file_google_api_expr_v1alpha1_syntax_proto_init() {
+ if File_google_api_expr_v1alpha1_syntax_proto != nil {
+ return
+ }
+ if !protoimpl.UnsafeEnabled {
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*ParsedExpr); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Expr); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Constant); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*SourceInfo); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*SourcePosition); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Expr_Ident); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Expr_Select); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Expr_Call); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[8].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Expr_CreateList); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[9].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Expr_CreateStruct); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[10].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Expr_Comprehension); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[11].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Expr_CreateStruct_Entry); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[1].OneofWrappers = []interface{}{
+ (*Expr_ConstExpr)(nil),
+ (*Expr_IdentExpr)(nil),
+ (*Expr_SelectExpr)(nil),
+ (*Expr_CallExpr)(nil),
+ (*Expr_ListExpr)(nil),
+ (*Expr_StructExpr)(nil),
+ (*Expr_ComprehensionExpr)(nil),
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[2].OneofWrappers = []interface{}{
+ (*Constant_NullValue)(nil),
+ (*Constant_BoolValue)(nil),
+ (*Constant_Int64Value)(nil),
+ (*Constant_Uint64Value)(nil),
+ (*Constant_DoubleValue)(nil),
+ (*Constant_StringValue)(nil),
+ (*Constant_BytesValue)(nil),
+ (*Constant_DurationValue)(nil),
+ (*Constant_TimestampValue)(nil),
+ }
+ file_google_api_expr_v1alpha1_syntax_proto_msgTypes[11].OneofWrappers = []interface{}{
+ (*Expr_CreateStruct_Entry_FieldKey)(nil),
+ (*Expr_CreateStruct_Entry_MapKey)(nil),
+ }
+ type x struct{}
+ out := protoimpl.TypeBuilder{
+ File: protoimpl.DescBuilder{
+ GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+ RawDescriptor: file_google_api_expr_v1alpha1_syntax_proto_rawDesc,
+ NumEnums: 0,
+ NumMessages: 14,
+ NumExtensions: 0,
+ NumServices: 0,
+ },
+ GoTypes: file_google_api_expr_v1alpha1_syntax_proto_goTypes,
+ DependencyIndexes: file_google_api_expr_v1alpha1_syntax_proto_depIdxs,
+ MessageInfos: file_google_api_expr_v1alpha1_syntax_proto_msgTypes,
+ }.Build()
+ File_google_api_expr_v1alpha1_syntax_proto = out.File
+ file_google_api_expr_v1alpha1_syntax_proto_rawDesc = nil
+ file_google_api_expr_v1alpha1_syntax_proto_goTypes = nil
+ file_google_api_expr_v1alpha1_syntax_proto_depIdxs = nil
+}
diff --git a/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/value.pb.go b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/value.pb.go
new file mode 100644
index 0000000000..808e9fe12e
--- /dev/null
+++ b/vendor/google.golang.org/genproto/googleapis/api/expr/v1alpha1/value.pb.go
@@ -0,0 +1,720 @@
+// Copyright 2020 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// protoc-gen-go v1.26.0
+// protoc v3.12.2
+// source: google/api/expr/v1alpha1/value.proto
+
+package expr
+
+import (
+ reflect "reflect"
+ sync "sync"
+
+ protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+ protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+ anypb "google.golang.org/protobuf/types/known/anypb"
+ structpb "google.golang.org/protobuf/types/known/structpb"
+)
+
+const (
+ // Verify that this generated code is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+ // Verify that runtime/protoimpl is sufficiently up-to-date.
+ _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+// Represents a CEL value.
+//
+// This is similar to `google.protobuf.Value`, but can represent CEL's full
+// range of values.
+type Value struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Required. The valid kinds of values.
+ //
+ // Types that are assignable to Kind:
+ // *Value_NullValue
+ // *Value_BoolValue
+ // *Value_Int64Value
+ // *Value_Uint64Value
+ // *Value_DoubleValue
+ // *Value_StringValue
+ // *Value_BytesValue
+ // *Value_EnumValue
+ // *Value_ObjectValue
+ // *Value_MapValue
+ // *Value_ListValue
+ // *Value_TypeValue
+ Kind isValue_Kind `protobuf_oneof:"kind"`
+}
+
+func (x *Value) Reset() {
+ *x = Value{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[0]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Value) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Value) ProtoMessage() {}
+
+func (x *Value) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[0]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Value.ProtoReflect.Descriptor instead.
+func (*Value) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_value_proto_rawDescGZIP(), []int{0}
+}
+
+func (m *Value) GetKind() isValue_Kind {
+ if m != nil {
+ return m.Kind
+ }
+ return nil
+}
+
+func (x *Value) GetNullValue() structpb.NullValue {
+ if x, ok := x.GetKind().(*Value_NullValue); ok {
+ return x.NullValue
+ }
+ return structpb.NullValue_NULL_VALUE
+}
+
+func (x *Value) GetBoolValue() bool {
+ if x, ok := x.GetKind().(*Value_BoolValue); ok {
+ return x.BoolValue
+ }
+ return false
+}
+
+func (x *Value) GetInt64Value() int64 {
+ if x, ok := x.GetKind().(*Value_Int64Value); ok {
+ return x.Int64Value
+ }
+ return 0
+}
+
+func (x *Value) GetUint64Value() uint64 {
+ if x, ok := x.GetKind().(*Value_Uint64Value); ok {
+ return x.Uint64Value
+ }
+ return 0
+}
+
+func (x *Value) GetDoubleValue() float64 {
+ if x, ok := x.GetKind().(*Value_DoubleValue); ok {
+ return x.DoubleValue
+ }
+ return 0
+}
+
+func (x *Value) GetStringValue() string {
+ if x, ok := x.GetKind().(*Value_StringValue); ok {
+ return x.StringValue
+ }
+ return ""
+}
+
+func (x *Value) GetBytesValue() []byte {
+ if x, ok := x.GetKind().(*Value_BytesValue); ok {
+ return x.BytesValue
+ }
+ return nil
+}
+
+func (x *Value) GetEnumValue() *EnumValue {
+ if x, ok := x.GetKind().(*Value_EnumValue); ok {
+ return x.EnumValue
+ }
+ return nil
+}
+
+func (x *Value) GetObjectValue() *anypb.Any {
+ if x, ok := x.GetKind().(*Value_ObjectValue); ok {
+ return x.ObjectValue
+ }
+ return nil
+}
+
+func (x *Value) GetMapValue() *MapValue {
+ if x, ok := x.GetKind().(*Value_MapValue); ok {
+ return x.MapValue
+ }
+ return nil
+}
+
+func (x *Value) GetListValue() *ListValue {
+ if x, ok := x.GetKind().(*Value_ListValue); ok {
+ return x.ListValue
+ }
+ return nil
+}
+
+func (x *Value) GetTypeValue() string {
+ if x, ok := x.GetKind().(*Value_TypeValue); ok {
+ return x.TypeValue
+ }
+ return ""
+}
+
+type isValue_Kind interface {
+ isValue_Kind()
+}
+
+type Value_NullValue struct {
+ // Null value.
+ NullValue structpb.NullValue `protobuf:"varint,1,opt,name=null_value,json=nullValue,proto3,enum=google.protobuf.NullValue,oneof"`
+}
+
+type Value_BoolValue struct {
+ // Boolean value.
+ BoolValue bool `protobuf:"varint,2,opt,name=bool_value,json=boolValue,proto3,oneof"`
+}
+
+type Value_Int64Value struct {
+ // Signed integer value.
+ Int64Value int64 `protobuf:"varint,3,opt,name=int64_value,json=int64Value,proto3,oneof"`
+}
+
+type Value_Uint64Value struct {
+ // Unsigned integer value.
+ Uint64Value uint64 `protobuf:"varint,4,opt,name=uint64_value,json=uint64Value,proto3,oneof"`
+}
+
+type Value_DoubleValue struct {
+ // Floating point value.
+ DoubleValue float64 `protobuf:"fixed64,5,opt,name=double_value,json=doubleValue,proto3,oneof"`
+}
+
+type Value_StringValue struct {
+ // UTF-8 string value.
+ StringValue string `protobuf:"bytes,6,opt,name=string_value,json=stringValue,proto3,oneof"`
+}
+
+type Value_BytesValue struct {
+ // Byte string value.
+ BytesValue []byte `protobuf:"bytes,7,opt,name=bytes_value,json=bytesValue,proto3,oneof"`
+}
+
+type Value_EnumValue struct {
+ // An enum value.
+ EnumValue *EnumValue `protobuf:"bytes,9,opt,name=enum_value,json=enumValue,proto3,oneof"`
+}
+
+type Value_ObjectValue struct {
+ // The proto message backing an object value.
+ ObjectValue *anypb.Any `protobuf:"bytes,10,opt,name=object_value,json=objectValue,proto3,oneof"`
+}
+
+type Value_MapValue struct {
+ // Map value.
+ MapValue *MapValue `protobuf:"bytes,11,opt,name=map_value,json=mapValue,proto3,oneof"`
+}
+
+type Value_ListValue struct {
+ // List value.
+ ListValue *ListValue `protobuf:"bytes,12,opt,name=list_value,json=listValue,proto3,oneof"`
+}
+
+type Value_TypeValue struct {
+ // Type value.
+ TypeValue string `protobuf:"bytes,15,opt,name=type_value,json=typeValue,proto3,oneof"`
+}
+
+func (*Value_NullValue) isValue_Kind() {}
+
+func (*Value_BoolValue) isValue_Kind() {}
+
+func (*Value_Int64Value) isValue_Kind() {}
+
+func (*Value_Uint64Value) isValue_Kind() {}
+
+func (*Value_DoubleValue) isValue_Kind() {}
+
+func (*Value_StringValue) isValue_Kind() {}
+
+func (*Value_BytesValue) isValue_Kind() {}
+
+func (*Value_EnumValue) isValue_Kind() {}
+
+func (*Value_ObjectValue) isValue_Kind() {}
+
+func (*Value_MapValue) isValue_Kind() {}
+
+func (*Value_ListValue) isValue_Kind() {}
+
+func (*Value_TypeValue) isValue_Kind() {}
+
+// An enum value.
+type EnumValue struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The fully qualified name of the enum type.
+ Type string `protobuf:"bytes,1,opt,name=type,proto3" json:"type,omitempty"`
+ // The value of the enum.
+ Value int32 `protobuf:"varint,2,opt,name=value,proto3" json:"value,omitempty"`
+}
+
+func (x *EnumValue) Reset() {
+ *x = EnumValue{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[1]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *EnumValue) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*EnumValue) ProtoMessage() {}
+
+func (x *EnumValue) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[1]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use EnumValue.ProtoReflect.Descriptor instead.
+func (*EnumValue) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_value_proto_rawDescGZIP(), []int{1}
+}
+
+func (x *EnumValue) GetType() string {
+ if x != nil {
+ return x.Type
+ }
+ return ""
+}
+
+func (x *EnumValue) GetValue() int32 {
+ if x != nil {
+ return x.Value
+ }
+ return 0
+}
+
+// A list.
+//
+// Wrapped in a message so 'not set' and empty can be differentiated, which is
+// required for use in a 'oneof'.
+type ListValue struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The ordered values in the list.
+ Values []*Value `protobuf:"bytes,1,rep,name=values,proto3" json:"values,omitempty"`
+}
+
+func (x *ListValue) Reset() {
+ *x = ListValue{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[2]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *ListValue) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*ListValue) ProtoMessage() {}
+
+func (x *ListValue) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[2]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use ListValue.ProtoReflect.Descriptor instead.
+func (*ListValue) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_value_proto_rawDescGZIP(), []int{2}
+}
+
+func (x *ListValue) GetValues() []*Value {
+ if x != nil {
+ return x.Values
+ }
+ return nil
+}
+
+// A map.
+//
+// Wrapped in a message so 'not set' and empty can be differentiated, which is
+// required for use in a 'oneof'.
+type MapValue struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The set of map entries.
+ //
+ // CEL has fewer restrictions on keys, so a protobuf map represenation
+ // cannot be used.
+ Entries []*MapValue_Entry `protobuf:"bytes,1,rep,name=entries,proto3" json:"entries,omitempty"`
+}
+
+func (x *MapValue) Reset() {
+ *x = MapValue{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[3]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *MapValue) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*MapValue) ProtoMessage() {}
+
+func (x *MapValue) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[3]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use MapValue.ProtoReflect.Descriptor instead.
+func (*MapValue) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_value_proto_rawDescGZIP(), []int{3}
+}
+
+func (x *MapValue) GetEntries() []*MapValue_Entry {
+ if x != nil {
+ return x.Entries
+ }
+ return nil
+}
+
+// An entry in the map.
+type MapValue_Entry struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The key.
+ //
+ // Must be unique with in the map.
+ // Currently only boolean, int, uint, and string values can be keys.
+ Key *Value `protobuf:"bytes,1,opt,name=key,proto3" json:"key,omitempty"`
+ // The value.
+ Value *Value `protobuf:"bytes,2,opt,name=value,proto3" json:"value,omitempty"`
+}
+
+func (x *MapValue_Entry) Reset() {
+ *x = MapValue_Entry{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[4]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *MapValue_Entry) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*MapValue_Entry) ProtoMessage() {}
+
+func (x *MapValue_Entry) ProtoReflect() protoreflect.Message {
+ mi := &file_google_api_expr_v1alpha1_value_proto_msgTypes[4]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use MapValue_Entry.ProtoReflect.Descriptor instead.
+func (*MapValue_Entry) Descriptor() ([]byte, []int) {
+ return file_google_api_expr_v1alpha1_value_proto_rawDescGZIP(), []int{3, 0}
+}
+
+func (x *MapValue_Entry) GetKey() *Value {
+ if x != nil {
+ return x.Key
+ }
+ return nil
+}
+
+func (x *MapValue_Entry) GetValue() *Value {
+ if x != nil {
+ return x.Value
+ }
+ return nil
+}
+
+var File_google_api_expr_v1alpha1_value_proto protoreflect.FileDescriptor
+
+var file_google_api_expr_v1alpha1_value_proto_rawDesc = []byte{
+ 0x0a, 0x24, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70,
+ 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2f, 0x76, 0x61, 0x6c, 0x75, 0x65,
+ 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x18, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61,
+ 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31,
+ 0x1a, 0x19, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75,
+ 0x66, 0x2f, 0x61, 0x6e, 0x79, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1c, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x73, 0x74, 0x72,
+ 0x75, 0x63, 0x74, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0xcd, 0x04, 0x0a, 0x05, 0x56, 0x61,
+ 0x6c, 0x75, 0x65, 0x12, 0x3b, 0x0a, 0x0a, 0x6e, 0x75, 0x6c, 0x6c, 0x5f, 0x76, 0x61, 0x6c, 0x75,
+ 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x1a, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4e, 0x75, 0x6c, 0x6c, 0x56, 0x61,
+ 0x6c, 0x75, 0x65, 0x48, 0x00, 0x52, 0x09, 0x6e, 0x75, 0x6c, 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65,
+ 0x12, 0x1f, 0x0a, 0x0a, 0x62, 0x6f, 0x6f, 0x6c, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02,
+ 0x20, 0x01, 0x28, 0x08, 0x48, 0x00, 0x52, 0x09, 0x62, 0x6f, 0x6f, 0x6c, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x12, 0x21, 0x0a, 0x0b, 0x69, 0x6e, 0x74, 0x36, 0x34, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65,
+ 0x18, 0x03, 0x20, 0x01, 0x28, 0x03, 0x48, 0x00, 0x52, 0x0a, 0x69, 0x6e, 0x74, 0x36, 0x34, 0x56,
+ 0x61, 0x6c, 0x75, 0x65, 0x12, 0x23, 0x0a, 0x0c, 0x75, 0x69, 0x6e, 0x74, 0x36, 0x34, 0x5f, 0x76,
+ 0x61, 0x6c, 0x75, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x04, 0x48, 0x00, 0x52, 0x0b, 0x75, 0x69,
+ 0x6e, 0x74, 0x36, 0x34, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x23, 0x0a, 0x0c, 0x64, 0x6f, 0x75,
+ 0x62, 0x6c, 0x65, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x01, 0x48,
+ 0x00, 0x52, 0x0b, 0x64, 0x6f, 0x75, 0x62, 0x6c, 0x65, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x23,
+ 0x0a, 0x0c, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x06,
+ 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x0b, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x56, 0x61,
+ 0x6c, 0x75, 0x65, 0x12, 0x21, 0x0a, 0x0b, 0x62, 0x79, 0x74, 0x65, 0x73, 0x5f, 0x76, 0x61, 0x6c,
+ 0x75, 0x65, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0c, 0x48, 0x00, 0x52, 0x0a, 0x62, 0x79, 0x74, 0x65,
+ 0x73, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x44, 0x0a, 0x0a, 0x65, 0x6e, 0x75, 0x6d, 0x5f, 0x76,
+ 0x61, 0x6c, 0x75, 0x65, 0x18, 0x09, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61,
+ 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x45, 0x6e, 0x75, 0x6d, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x48,
+ 0x00, 0x52, 0x09, 0x65, 0x6e, 0x75, 0x6d, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x39, 0x0a, 0x0c,
+ 0x6f, 0x62, 0x6a, 0x65, 0x63, 0x74, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x0a, 0x20, 0x01,
+ 0x28, 0x0b, 0x32, 0x14, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74,
+ 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x41, 0x6e, 0x79, 0x48, 0x00, 0x52, 0x0b, 0x6f, 0x62, 0x6a, 0x65,
+ 0x63, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x41, 0x0a, 0x09, 0x6d, 0x61, 0x70, 0x5f, 0x76,
+ 0x61, 0x6c, 0x75, 0x65, 0x18, 0x0b, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x22, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61,
+ 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x4d, 0x61, 0x70, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x48, 0x00,
+ 0x52, 0x08, 0x6d, 0x61, 0x70, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x44, 0x0a, 0x0a, 0x6c, 0x69,
+ 0x73, 0x74, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x0c, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x23,
+ 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72,
+ 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x56, 0x61,
+ 0x6c, 0x75, 0x65, 0x48, 0x00, 0x52, 0x09, 0x6c, 0x69, 0x73, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65,
+ 0x12, 0x1f, 0x0a, 0x0a, 0x74, 0x79, 0x70, 0x65, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x0f,
+ 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x09, 0x74, 0x79, 0x70, 0x65, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x42, 0x06, 0x0a, 0x04, 0x6b, 0x69, 0x6e, 0x64, 0x22, 0x35, 0x0a, 0x09, 0x45, 0x6e, 0x75,
+ 0x6d, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x01,
+ 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, 0x79, 0x70, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61,
+ 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65,
+ 0x22, 0x44, 0x0a, 0x09, 0x4c, 0x69, 0x73, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x37, 0x0a,
+ 0x06, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1f, 0x2e,
+ 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e,
+ 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x52, 0x06,
+ 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x22, 0xc1, 0x01, 0x0a, 0x08, 0x4d, 0x61, 0x70, 0x56, 0x61,
+ 0x6c, 0x75, 0x65, 0x12, 0x42, 0x0a, 0x07, 0x65, 0x6e, 0x74, 0x72, 0x69, 0x65, 0x73, 0x18, 0x01,
+ 0x20, 0x03, 0x28, 0x0b, 0x32, 0x28, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70,
+ 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e,
+ 0x4d, 0x61, 0x70, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x2e, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x07,
+ 0x65, 0x6e, 0x74, 0x72, 0x69, 0x65, 0x73, 0x1a, 0x71, 0x0a, 0x05, 0x45, 0x6e, 0x74, 0x72, 0x79,
+ 0x12, 0x31, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1f, 0x2e,
+ 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70, 0x72, 0x2e,
+ 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x52, 0x03,
+ 0x6b, 0x65, 0x79, 0x12, 0x35, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01,
+ 0x28, 0x0b, 0x32, 0x1f, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e,
+ 0x65, 0x78, 0x70, 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x2e, 0x56, 0x61,
+ 0x6c, 0x75, 0x65, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x42, 0x6d, 0x0a, 0x1c, 0x63, 0x6f,
+ 0x6d, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x65, 0x78, 0x70,
+ 0x72, 0x2e, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61, 0x31, 0x42, 0x0a, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x3c, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x67, 0x65, 0x6e, 0x70,
+ 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x61, 0x70, 0x69, 0x73, 0x2f,
+ 0x61, 0x70, 0x69, 0x2f, 0x65, 0x78, 0x70, 0x72, 0x2f, 0x76, 0x31, 0x61, 0x6c, 0x70, 0x68, 0x61,
+ 0x31, 0x3b, 0x65, 0x78, 0x70, 0x72, 0xf8, 0x01, 0x01, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f,
+ 0x33,
+}
+
+var (
+ file_google_api_expr_v1alpha1_value_proto_rawDescOnce sync.Once
+ file_google_api_expr_v1alpha1_value_proto_rawDescData = file_google_api_expr_v1alpha1_value_proto_rawDesc
+)
+
+func file_google_api_expr_v1alpha1_value_proto_rawDescGZIP() []byte {
+ file_google_api_expr_v1alpha1_value_proto_rawDescOnce.Do(func() {
+ file_google_api_expr_v1alpha1_value_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_api_expr_v1alpha1_value_proto_rawDescData)
+ })
+ return file_google_api_expr_v1alpha1_value_proto_rawDescData
+}
+
+var file_google_api_expr_v1alpha1_value_proto_msgTypes = make([]protoimpl.MessageInfo, 5)
+var file_google_api_expr_v1alpha1_value_proto_goTypes = []interface{}{
+ (*Value)(nil), // 0: google.api.expr.v1alpha1.Value
+ (*EnumValue)(nil), // 1: google.api.expr.v1alpha1.EnumValue
+ (*ListValue)(nil), // 2: google.api.expr.v1alpha1.ListValue
+ (*MapValue)(nil), // 3: google.api.expr.v1alpha1.MapValue
+ (*MapValue_Entry)(nil), // 4: google.api.expr.v1alpha1.MapValue.Entry
+ (structpb.NullValue)(0), // 5: google.protobuf.NullValue
+ (*anypb.Any)(nil), // 6: google.protobuf.Any
+}
+var file_google_api_expr_v1alpha1_value_proto_depIdxs = []int32{
+ 5, // 0: google.api.expr.v1alpha1.Value.null_value:type_name -> google.protobuf.NullValue
+ 1, // 1: google.api.expr.v1alpha1.Value.enum_value:type_name -> google.api.expr.v1alpha1.EnumValue
+ 6, // 2: google.api.expr.v1alpha1.Value.object_value:type_name -> google.protobuf.Any
+ 3, // 3: google.api.expr.v1alpha1.Value.map_value:type_name -> google.api.expr.v1alpha1.MapValue
+ 2, // 4: google.api.expr.v1alpha1.Value.list_value:type_name -> google.api.expr.v1alpha1.ListValue
+ 0, // 5: google.api.expr.v1alpha1.ListValue.values:type_name -> google.api.expr.v1alpha1.Value
+ 4, // 6: google.api.expr.v1alpha1.MapValue.entries:type_name -> google.api.expr.v1alpha1.MapValue.Entry
+ 0, // 7: google.api.expr.v1alpha1.MapValue.Entry.key:type_name -> google.api.expr.v1alpha1.Value
+ 0, // 8: google.api.expr.v1alpha1.MapValue.Entry.value:type_name -> google.api.expr.v1alpha1.Value
+ 9, // [9:9] is the sub-list for method output_type
+ 9, // [9:9] is the sub-list for method input_type
+ 9, // [9:9] is the sub-list for extension type_name
+ 9, // [9:9] is the sub-list for extension extendee
+ 0, // [0:9] is the sub-list for field type_name
+}
+
+func init() { file_google_api_expr_v1alpha1_value_proto_init() }
+func file_google_api_expr_v1alpha1_value_proto_init() {
+ if File_google_api_expr_v1alpha1_value_proto != nil {
+ return
+ }
+ if !protoimpl.UnsafeEnabled {
+ file_google_api_expr_v1alpha1_value_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Value); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_value_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*EnumValue); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_value_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*ListValue); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_value_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*MapValue); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_api_expr_v1alpha1_value_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*MapValue_Entry); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ }
+ file_google_api_expr_v1alpha1_value_proto_msgTypes[0].OneofWrappers = []interface{}{
+ (*Value_NullValue)(nil),
+ (*Value_BoolValue)(nil),
+ (*Value_Int64Value)(nil),
+ (*Value_Uint64Value)(nil),
+ (*Value_DoubleValue)(nil),
+ (*Value_StringValue)(nil),
+ (*Value_BytesValue)(nil),
+ (*Value_EnumValue)(nil),
+ (*Value_ObjectValue)(nil),
+ (*Value_MapValue)(nil),
+ (*Value_ListValue)(nil),
+ (*Value_TypeValue)(nil),
+ }
+ type x struct{}
+ out := protoimpl.TypeBuilder{
+ File: protoimpl.DescBuilder{
+ GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+ RawDescriptor: file_google_api_expr_v1alpha1_value_proto_rawDesc,
+ NumEnums: 0,
+ NumMessages: 5,
+ NumExtensions: 0,
+ NumServices: 0,
+ },
+ GoTypes: file_google_api_expr_v1alpha1_value_proto_goTypes,
+ DependencyIndexes: file_google_api_expr_v1alpha1_value_proto_depIdxs,
+ MessageInfos: file_google_api_expr_v1alpha1_value_proto_msgTypes,
+ }.Build()
+ File_google_api_expr_v1alpha1_value_proto = out.File
+ file_google_api_expr_v1alpha1_value_proto_rawDesc = nil
+ file_google_api_expr_v1alpha1_value_proto_goTypes = nil
+ file_google_api_expr_v1alpha1_value_proto_depIdxs = nil
+}
diff --git a/vendor/google.golang.org/protobuf/types/dynamicpb/dynamic.go b/vendor/google.golang.org/protobuf/types/dynamicpb/dynamic.go
new file mode 100644
index 0000000000..900b9d2874
--- /dev/null
+++ b/vendor/google.golang.org/protobuf/types/dynamicpb/dynamic.go
@@ -0,0 +1,713 @@
+// Copyright 2019 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 dynamicpb creates protocol buffer messages using runtime type information.
+package dynamicpb
+
+import (
+ "math"
+
+ "google.golang.org/protobuf/internal/errors"
+ pref "google.golang.org/protobuf/reflect/protoreflect"
+ "google.golang.org/protobuf/runtime/protoiface"
+ "google.golang.org/protobuf/runtime/protoimpl"
+)
+
+// enum is a dynamic protoreflect.Enum.
+type enum struct {
+ num pref.EnumNumber
+ typ pref.EnumType
+}
+
+func (e enum) Descriptor() pref.EnumDescriptor { return e.typ.Descriptor() }
+func (e enum) Type() pref.EnumType { return e.typ }
+func (e enum) Number() pref.EnumNumber { return e.num }
+
+// enumType is a dynamic protoreflect.EnumType.
+type enumType struct {
+ desc pref.EnumDescriptor
+}
+
+// NewEnumType creates a new EnumType with the provided descriptor.
+//
+// EnumTypes created by this package are equal if their descriptors are equal.
+// That is, if ed1 == ed2, then NewEnumType(ed1) == NewEnumType(ed2).
+//
+// Enum values created by the EnumType are equal if their numbers are equal.
+func NewEnumType(desc pref.EnumDescriptor) pref.EnumType {
+ return enumType{desc}
+}
+
+func (et enumType) New(n pref.EnumNumber) pref.Enum { return enum{n, et} }
+func (et enumType) Descriptor() pref.EnumDescriptor { return et.desc }
+
+// extensionType is a dynamic protoreflect.ExtensionType.
+type extensionType struct {
+ desc extensionTypeDescriptor
+}
+
+// A Message is a dynamically constructed protocol buffer message.
+//
+// Message implements the proto.Message interface, and may be used with all
+// standard proto package functions such as Marshal, Unmarshal, and so forth.
+//
+// Message also implements the protoreflect.Message interface. See the protoreflect
+// package documentation for that interface for how to get and set fields and
+// otherwise interact with the contents of a Message.
+//
+// Reflection API functions which construct messages, such as NewField,
+// return new dynamic messages of the appropriate type. Functions which take
+// messages, such as Set for a message-value field, will accept any message
+// with a compatible type.
+//
+// Operations which modify a Message are not safe for concurrent use.
+type Message struct {
+ typ messageType
+ known map[pref.FieldNumber]pref.Value
+ ext map[pref.FieldNumber]pref.FieldDescriptor
+ unknown pref.RawFields
+}
+
+var (
+ _ pref.Message = (*Message)(nil)
+ _ pref.ProtoMessage = (*Message)(nil)
+ _ protoiface.MessageV1 = (*Message)(nil)
+)
+
+// NewMessage creates a new message with the provided descriptor.
+func NewMessage(desc pref.MessageDescriptor) *Message {
+ return &Message{
+ typ: messageType{desc},
+ known: make(map[pref.FieldNumber]pref.Value),
+ ext: make(map[pref.FieldNumber]pref.FieldDescriptor),
+ }
+}
+
+// ProtoMessage implements the legacy message interface.
+func (m *Message) ProtoMessage() {}
+
+// ProtoReflect implements the protoreflect.ProtoMessage interface.
+func (m *Message) ProtoReflect() pref.Message {
+ return m
+}
+
+// String returns a string representation of a message.
+func (m *Message) String() string {
+ return protoimpl.X.MessageStringOf(m)
+}
+
+// Reset clears the message to be empty, but preserves the dynamic message type.
+func (m *Message) Reset() {
+ m.known = make(map[pref.FieldNumber]pref.Value)
+ m.ext = make(map[pref.FieldNumber]pref.FieldDescriptor)
+ m.unknown = nil
+}
+
+// Descriptor returns the message descriptor.
+func (m *Message) Descriptor() pref.MessageDescriptor {
+ return m.typ.desc
+}
+
+// Type returns the message type.
+func (m *Message) Type() pref.MessageType {
+ return m.typ
+}
+
+// New returns a newly allocated empty message with the same descriptor.
+// See protoreflect.Message for details.
+func (m *Message) New() pref.Message {
+ return m.Type().New()
+}
+
+// Interface returns the message.
+// See protoreflect.Message for details.
+func (m *Message) Interface() pref.ProtoMessage {
+ return m
+}
+
+// ProtoMethods is an internal detail of the protoreflect.Message interface.
+// Users should never call this directly.
+func (m *Message) ProtoMethods() *protoiface.Methods {
+ return nil
+}
+
+// Range visits every populated field in undefined order.
+// See protoreflect.Message for details.
+func (m *Message) Range(f func(pref.FieldDescriptor, pref.Value) bool) {
+ for num, v := range m.known {
+ fd := m.ext[num]
+ if fd == nil {
+ fd = m.Descriptor().Fields().ByNumber(num)
+ }
+ if !isSet(fd, v) {
+ continue
+ }
+ if !f(fd, v) {
+ return
+ }
+ }
+}
+
+// Has reports whether a field is populated.
+// See protoreflect.Message for details.
+func (m *Message) Has(fd pref.FieldDescriptor) bool {
+ m.checkField(fd)
+ if fd.IsExtension() && m.ext[fd.Number()] != fd {
+ return false
+ }
+ v, ok := m.known[fd.Number()]
+ if !ok {
+ return false
+ }
+ return isSet(fd, v)
+}
+
+// Clear clears a field.
+// See protoreflect.Message for details.
+func (m *Message) Clear(fd pref.FieldDescriptor) {
+ m.checkField(fd)
+ num := fd.Number()
+ delete(m.known, num)
+ delete(m.ext, num)
+}
+
+// Get returns the value of a field.
+// See protoreflect.Message for details.
+func (m *Message) Get(fd pref.FieldDescriptor) pref.Value {
+ m.checkField(fd)
+ num := fd.Number()
+ if fd.IsExtension() {
+ if fd != m.ext[num] {
+ return fd.(pref.ExtensionTypeDescriptor).Type().Zero()
+ }
+ return m.known[num]
+ }
+ if v, ok := m.known[num]; ok {
+ switch {
+ case fd.IsMap():
+ if v.Map().Len() > 0 {
+ return v
+ }
+ case fd.IsList():
+ if v.List().Len() > 0 {
+ return v
+ }
+ default:
+ return v
+ }
+ }
+ switch {
+ case fd.IsMap():
+ return pref.ValueOfMap(&dynamicMap{desc: fd})
+ case fd.IsList():
+ return pref.ValueOfList(emptyList{desc: fd})
+ case fd.Message() != nil:
+ return pref.ValueOfMessage(&Message{typ: messageType{fd.Message()}})
+ case fd.Kind() == pref.BytesKind:
+ return pref.ValueOfBytes(append([]byte(nil), fd.Default().Bytes()...))
+ default:
+ return fd.Default()
+ }
+}
+
+// Mutable returns a mutable reference to a repeated, map, or message field.
+// See protoreflect.Message for details.
+func (m *Message) Mutable(fd pref.FieldDescriptor) pref.Value {
+ m.checkField(fd)
+ if !fd.IsMap() && !fd.IsList() && fd.Message() == nil {
+ panic(errors.New("%v: getting mutable reference to non-composite type", fd.FullName()))
+ }
+ if m.known == nil {
+ panic(errors.New("%v: modification of read-only message", fd.FullName()))
+ }
+ num := fd.Number()
+ if fd.IsExtension() {
+ if fd != m.ext[num] {
+ m.ext[num] = fd
+ m.known[num] = fd.(pref.ExtensionTypeDescriptor).Type().New()
+ }
+ return m.known[num]
+ }
+ if v, ok := m.known[num]; ok {
+ return v
+ }
+ m.clearOtherOneofFields(fd)
+ m.known[num] = m.NewField(fd)
+ if fd.IsExtension() {
+ m.ext[num] = fd
+ }
+ return m.known[num]
+}
+
+// Set stores a value in a field.
+// See protoreflect.Message for details.
+func (m *Message) Set(fd pref.FieldDescriptor, v pref.Value) {
+ m.checkField(fd)
+ if m.known == nil {
+ panic(errors.New("%v: modification of read-only message", fd.FullName()))
+ }
+ if fd.IsExtension() {
+ isValid := true
+ switch {
+ case !fd.(pref.ExtensionTypeDescriptor).Type().IsValidValue(v):
+ isValid = false
+ case fd.IsList():
+ isValid = v.List().IsValid()
+ case fd.IsMap():
+ isValid = v.Map().IsValid()
+ case fd.Message() != nil:
+ isValid = v.Message().IsValid()
+ }
+ if !isValid {
+ panic(errors.New("%v: assigning invalid type %T", fd.FullName(), v.Interface()))
+ }
+ m.ext[fd.Number()] = fd
+ } else {
+ typecheck(fd, v)
+ }
+ m.clearOtherOneofFields(fd)
+ m.known[fd.Number()] = v
+}
+
+func (m *Message) clearOtherOneofFields(fd pref.FieldDescriptor) {
+ od := fd.ContainingOneof()
+ if od == nil {
+ return
+ }
+ num := fd.Number()
+ for i := 0; i < od.Fields().Len(); i++ {
+ if n := od.Fields().Get(i).Number(); n != num {
+ delete(m.known, n)
+ }
+ }
+}
+
+// NewField returns a new value for assignable to the field of a given descriptor.
+// See protoreflect.Message for details.
+func (m *Message) NewField(fd pref.FieldDescriptor) pref.Value {
+ m.checkField(fd)
+ switch {
+ case fd.IsExtension():
+ return fd.(pref.ExtensionTypeDescriptor).Type().New()
+ case fd.IsMap():
+ return pref.ValueOfMap(&dynamicMap{
+ desc: fd,
+ mapv: make(map[interface{}]pref.Value),
+ })
+ case fd.IsList():
+ return pref.ValueOfList(&dynamicList{desc: fd})
+ case fd.Message() != nil:
+ return pref.ValueOfMessage(NewMessage(fd.Message()).ProtoReflect())
+ default:
+ return fd.Default()
+ }
+}
+
+// WhichOneof reports which field in a oneof is populated, returning nil if none are populated.
+// See protoreflect.Message for details.
+func (m *Message) WhichOneof(od pref.OneofDescriptor) pref.FieldDescriptor {
+ for i := 0; i < od.Fields().Len(); i++ {
+ fd := od.Fields().Get(i)
+ if m.Has(fd) {
+ return fd
+ }
+ }
+ return nil
+}
+
+// GetUnknown returns the raw unknown fields.
+// See protoreflect.Message for details.
+func (m *Message) GetUnknown() pref.RawFields {
+ return m.unknown
+}
+
+// SetUnknown sets the raw unknown fields.
+// See protoreflect.Message for details.
+func (m *Message) SetUnknown(r pref.RawFields) {
+ if m.known == nil {
+ panic(errors.New("%v: modification of read-only message", m.typ.desc.FullName()))
+ }
+ m.unknown = r
+}
+
+// IsValid reports whether the message is valid.
+// See protoreflect.Message for details.
+func (m *Message) IsValid() bool {
+ return m.known != nil
+}
+
+func (m *Message) checkField(fd pref.FieldDescriptor) {
+ if fd.IsExtension() && fd.ContainingMessage().FullName() == m.Descriptor().FullName() {
+ if _, ok := fd.(pref.ExtensionTypeDescriptor); !ok {
+ panic(errors.New("%v: extension field descriptor does not implement ExtensionTypeDescriptor", fd.FullName()))
+ }
+ return
+ }
+ if fd.Parent() == m.Descriptor() {
+ return
+ }
+ fields := m.Descriptor().Fields()
+ index := fd.Index()
+ if index >= fields.Len() || fields.Get(index) != fd {
+ panic(errors.New("%v: field descriptor does not belong to this message", fd.FullName()))
+ }
+}
+
+type messageType struct {
+ desc pref.MessageDescriptor
+}
+
+// NewMessageType creates a new MessageType with the provided descriptor.
+//
+// MessageTypes created by this package are equal if their descriptors are equal.
+// That is, if md1 == md2, then NewMessageType(md1) == NewMessageType(md2).
+func NewMessageType(desc pref.MessageDescriptor) pref.MessageType {
+ return messageType{desc}
+}
+
+func (mt messageType) New() pref.Message { return NewMessage(mt.desc) }
+func (mt messageType) Zero() pref.Message { return &Message{typ: messageType{mt.desc}} }
+func (mt messageType) Descriptor() pref.MessageDescriptor { return mt.desc }
+func (mt messageType) Enum(i int) pref.EnumType {
+ if ed := mt.desc.Fields().Get(i).Enum(); ed != nil {
+ return NewEnumType(ed)
+ }
+ return nil
+}
+func (mt messageType) Message(i int) pref.MessageType {
+ if md := mt.desc.Fields().Get(i).Message(); md != nil {
+ return NewMessageType(md)
+ }
+ return nil
+}
+
+type emptyList struct {
+ desc pref.FieldDescriptor
+}
+
+func (x emptyList) Len() int { return 0 }
+func (x emptyList) Get(n int) pref.Value { panic(errors.New("out of range")) }
+func (x emptyList) Set(n int, v pref.Value) { panic(errors.New("modification of immutable list")) }
+func (x emptyList) Append(v pref.Value) { panic(errors.New("modification of immutable list")) }
+func (x emptyList) AppendMutable() pref.Value { panic(errors.New("modification of immutable list")) }
+func (x emptyList) Truncate(n int) { panic(errors.New("modification of immutable list")) }
+func (x emptyList) NewElement() pref.Value { return newListEntry(x.desc) }
+func (x emptyList) IsValid() bool { return false }
+
+type dynamicList struct {
+ desc pref.FieldDescriptor
+ list []pref.Value
+}
+
+func (x *dynamicList) Len() int {
+ return len(x.list)
+}
+
+func (x *dynamicList) Get(n int) pref.Value {
+ return x.list[n]
+}
+
+func (x *dynamicList) Set(n int, v pref.Value) {
+ typecheckSingular(x.desc, v)
+ x.list[n] = v
+}
+
+func (x *dynamicList) Append(v pref.Value) {
+ typecheckSingular(x.desc, v)
+ x.list = append(x.list, v)
+}
+
+func (x *dynamicList) AppendMutable() pref.Value {
+ if x.desc.Message() == nil {
+ panic(errors.New("%v: invalid AppendMutable on list with non-message type", x.desc.FullName()))
+ }
+ v := x.NewElement()
+ x.Append(v)
+ return v
+}
+
+func (x *dynamicList) Truncate(n int) {
+ // Zero truncated elements to avoid keeping data live.
+ for i := n; i < len(x.list); i++ {
+ x.list[i] = pref.Value{}
+ }
+ x.list = x.list[:n]
+}
+
+func (x *dynamicList) NewElement() pref.Value {
+ return newListEntry(x.desc)
+}
+
+func (x *dynamicList) IsValid() bool {
+ return true
+}
+
+type dynamicMap struct {
+ desc pref.FieldDescriptor
+ mapv map[interface{}]pref.Value
+}
+
+func (x *dynamicMap) Get(k pref.MapKey) pref.Value { return x.mapv[k.Interface()] }
+func (x *dynamicMap) Set(k pref.MapKey, v pref.Value) {
+ typecheckSingular(x.desc.MapKey(), k.Value())
+ typecheckSingular(x.desc.MapValue(), v)
+ x.mapv[k.Interface()] = v
+}
+func (x *dynamicMap) Has(k pref.MapKey) bool { return x.Get(k).IsValid() }
+func (x *dynamicMap) Clear(k pref.MapKey) { delete(x.mapv, k.Interface()) }
+func (x *dynamicMap) Mutable(k pref.MapKey) pref.Value {
+ if x.desc.MapValue().Message() == nil {
+ panic(errors.New("%v: invalid Mutable on map with non-message value type", x.desc.FullName()))
+ }
+ v := x.Get(k)
+ if !v.IsValid() {
+ v = x.NewValue()
+ x.Set(k, v)
+ }
+ return v
+}
+func (x *dynamicMap) Len() int { return len(x.mapv) }
+func (x *dynamicMap) NewValue() pref.Value {
+ if md := x.desc.MapValue().Message(); md != nil {
+ return pref.ValueOfMessage(NewMessage(md).ProtoReflect())
+ }
+ return x.desc.MapValue().Default()
+}
+func (x *dynamicMap) IsValid() bool {
+ return x.mapv != nil
+}
+
+func (x *dynamicMap) Range(f func(pref.MapKey, pref.Value) bool) {
+ for k, v := range x.mapv {
+ if !f(pref.ValueOf(k).MapKey(), v) {
+ return
+ }
+ }
+}
+
+func isSet(fd pref.FieldDescriptor, v pref.Value) bool {
+ switch {
+ case fd.IsMap():
+ return v.Map().Len() > 0
+ case fd.IsList():
+ return v.List().Len() > 0
+ case fd.ContainingOneof() != nil:
+ return true
+ case fd.Syntax() == pref.Proto3 && !fd.IsExtension():
+ switch fd.Kind() {
+ case pref.BoolKind:
+ return v.Bool()
+ case pref.EnumKind:
+ return v.Enum() != 0
+ case pref.Int32Kind, pref.Sint32Kind, pref.Int64Kind, pref.Sint64Kind, pref.Sfixed32Kind, pref.Sfixed64Kind:
+ return v.Int() != 0
+ case pref.Uint32Kind, pref.Uint64Kind, pref.Fixed32Kind, pref.Fixed64Kind:
+ return v.Uint() != 0
+ case pref.FloatKind, pref.DoubleKind:
+ return v.Float() != 0 || math.Signbit(v.Float())
+ case pref.StringKind:
+ return v.String() != ""
+ case pref.BytesKind:
+ return len(v.Bytes()) > 0
+ }
+ }
+ return true
+}
+
+func typecheck(fd pref.FieldDescriptor, v pref.Value) {
+ if err := typeIsValid(fd, v); err != nil {
+ panic(err)
+ }
+}
+
+func typeIsValid(fd pref.FieldDescriptor, v pref.Value) error {
+ switch {
+ case !v.IsValid():
+ return errors.New("%v: assigning invalid value", fd.FullName())
+ case fd.IsMap():
+ if mapv, ok := v.Interface().(*dynamicMap); !ok || mapv.desc != fd || !mapv.IsValid() {
+ return errors.New("%v: assigning invalid type %T", fd.FullName(), v.Interface())
+ }
+ return nil
+ case fd.IsList():
+ switch list := v.Interface().(type) {
+ case *dynamicList:
+ if list.desc == fd && list.IsValid() {
+ return nil
+ }
+ case emptyList:
+ if list.desc == fd && list.IsValid() {
+ return nil
+ }
+ }
+ return errors.New("%v: assigning invalid type %T", fd.FullName(), v.Interface())
+ default:
+ return singularTypeIsValid(fd, v)
+ }
+}
+
+func typecheckSingular(fd pref.FieldDescriptor, v pref.Value) {
+ if err := singularTypeIsValid(fd, v); err != nil {
+ panic(err)
+ }
+}
+
+func singularTypeIsValid(fd pref.FieldDescriptor, v pref.Value) error {
+ vi := v.Interface()
+ var ok bool
+ switch fd.Kind() {
+ case pref.BoolKind:
+ _, ok = vi.(bool)
+ case pref.EnumKind:
+ // We could check against the valid set of enum values, but do not.
+ _, ok = vi.(pref.EnumNumber)
+ case pref.Int32Kind, pref.Sint32Kind, pref.Sfixed32Kind:
+ _, ok = vi.(int32)
+ case pref.Uint32Kind, pref.Fixed32Kind:
+ _, ok = vi.(uint32)
+ case pref.Int64Kind, pref.Sint64Kind, pref.Sfixed64Kind:
+ _, ok = vi.(int64)
+ case pref.Uint64Kind, pref.Fixed64Kind:
+ _, ok = vi.(uint64)
+ case pref.FloatKind:
+ _, ok = vi.(float32)
+ case pref.DoubleKind:
+ _, ok = vi.(float64)
+ case pref.StringKind:
+ _, ok = vi.(string)
+ case pref.BytesKind:
+ _, ok = vi.([]byte)
+ case pref.MessageKind, pref.GroupKind:
+ var m pref.Message
+ m, ok = vi.(pref.Message)
+ if ok && m.Descriptor().FullName() != fd.Message().FullName() {
+ return errors.New("%v: assigning invalid message type %v", fd.FullName(), m.Descriptor().FullName())
+ }
+ if dm, ok := vi.(*Message); ok && dm.known == nil {
+ return errors.New("%v: assigning invalid zero-value message", fd.FullName())
+ }
+ }
+ if !ok {
+ return errors.New("%v: assigning invalid type %T", fd.FullName(), v.Interface())
+ }
+ return nil
+}
+
+func newListEntry(fd pref.FieldDescriptor) pref.Value {
+ switch fd.Kind() {
+ case pref.BoolKind:
+ return pref.ValueOfBool(false)
+ case pref.EnumKind:
+ return pref.ValueOfEnum(fd.Enum().Values().Get(0).Number())
+ case pref.Int32Kind, pref.Sint32Kind, pref.Sfixed32Kind:
+ return pref.ValueOfInt32(0)
+ case pref.Uint32Kind, pref.Fixed32Kind:
+ return pref.ValueOfUint32(0)
+ case pref.Int64Kind, pref.Sint64Kind, pref.Sfixed64Kind:
+ return pref.ValueOfInt64(0)
+ case pref.Uint64Kind, pref.Fixed64Kind:
+ return pref.ValueOfUint64(0)
+ case pref.FloatKind:
+ return pref.ValueOfFloat32(0)
+ case pref.DoubleKind:
+ return pref.ValueOfFloat64(0)
+ case pref.StringKind:
+ return pref.ValueOfString("")
+ case pref.BytesKind:
+ return pref.ValueOfBytes(nil)
+ case pref.MessageKind, pref.GroupKind:
+ return pref.ValueOfMessage(NewMessage(fd.Message()).ProtoReflect())
+ }
+ panic(errors.New("%v: unknown kind %v", fd.FullName(), fd.Kind()))
+}
+
+// NewExtensionType creates a new ExtensionType with the provided descriptor.
+//
+// Dynamic ExtensionTypes with the same descriptor compare as equal. That is,
+// if xd1 == xd2, then NewExtensionType(xd1) == NewExtensionType(xd2).
+//
+// The InterfaceOf and ValueOf methods of the extension type are defined as:
+//
+// func (xt extensionType) ValueOf(iv interface{}) protoreflect.Value {
+// return protoreflect.ValueOf(iv)
+// }
+//
+// func (xt extensionType) InterfaceOf(v protoreflect.Value) interface{} {
+// return v.Interface()
+// }
+//
+// The Go type used by the proto.GetExtension and proto.SetExtension functions
+// is determined by these methods, and is therefore equivalent to the Go type
+// used to represent a protoreflect.Value. See the protoreflect.Value
+// documentation for more details.
+func NewExtensionType(desc pref.ExtensionDescriptor) pref.ExtensionType {
+ if xt, ok := desc.(pref.ExtensionTypeDescriptor); ok {
+ desc = xt.Descriptor()
+ }
+ return extensionType{extensionTypeDescriptor{desc}}
+}
+
+func (xt extensionType) New() pref.Value {
+ switch {
+ case xt.desc.IsMap():
+ return pref.ValueOfMap(&dynamicMap{
+ desc: xt.desc,
+ mapv: make(map[interface{}]pref.Value),
+ })
+ case xt.desc.IsList():
+ return pref.ValueOfList(&dynamicList{desc: xt.desc})
+ case xt.desc.Message() != nil:
+ return pref.ValueOfMessage(NewMessage(xt.desc.Message()))
+ default:
+ return xt.desc.Default()
+ }
+}
+
+func (xt extensionType) Zero() pref.Value {
+ switch {
+ case xt.desc.IsMap():
+ return pref.ValueOfMap(&dynamicMap{desc: xt.desc})
+ case xt.desc.Cardinality() == pref.Repeated:
+ return pref.ValueOfList(emptyList{desc: xt.desc})
+ case xt.desc.Message() != nil:
+ return pref.ValueOfMessage(&Message{typ: messageType{xt.desc.Message()}})
+ default:
+ return xt.desc.Default()
+ }
+}
+
+func (xt extensionType) TypeDescriptor() pref.ExtensionTypeDescriptor {
+ return xt.desc
+}
+
+func (xt extensionType) ValueOf(iv interface{}) pref.Value {
+ v := pref.ValueOf(iv)
+ typecheck(xt.desc, v)
+ return v
+}
+
+func (xt extensionType) InterfaceOf(v pref.Value) interface{} {
+ typecheck(xt.desc, v)
+ return v.Interface()
+}
+
+func (xt extensionType) IsValidInterface(iv interface{}) bool {
+ return typeIsValid(xt.desc, pref.ValueOf(iv)) == nil
+}
+
+func (xt extensionType) IsValidValue(v pref.Value) bool {
+ return typeIsValid(xt.desc, v) == nil
+}
+
+type extensionTypeDescriptor struct {
+ pref.ExtensionDescriptor
+}
+
+func (xt extensionTypeDescriptor) Type() pref.ExtensionType {
+ return extensionType{xt}
+}
+
+func (xt extensionTypeDescriptor) Descriptor() pref.ExtensionDescriptor {
+ return xt.ExtensionDescriptor
+}
diff --git a/vendor/google.golang.org/protobuf/types/known/emptypb/empty.pb.go b/vendor/google.golang.org/protobuf/types/known/emptypb/empty.pb.go
new file mode 100644
index 0000000000..e7fcea31f6
--- /dev/null
+++ b/vendor/google.golang.org/protobuf/types/known/emptypb/empty.pb.go
@@ -0,0 +1,168 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// https://developers.google.com/protocol-buffers/
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions are
+// met:
+//
+// * Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// * Redistributions in binary form must reproduce the above
+// copyright notice, this list of conditions and the following disclaimer
+// in the documentation and/or other materials provided with the
+// distribution.
+// * Neither the name of Google Inc. nor the names of its
+// contributors may be used to endorse or promote products derived from
+// this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// source: google/protobuf/empty.proto
+
+package emptypb
+
+import (
+ protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+ protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+ reflect "reflect"
+ sync "sync"
+)
+
+// A generic empty message that you can re-use to avoid defining duplicated
+// empty messages in your APIs. A typical example is to use it as the request
+// or the response type of an API method. For instance:
+//
+// service Foo {
+// rpc Bar(google.protobuf.Empty) returns (google.protobuf.Empty);
+// }
+//
+// The JSON representation for `Empty` is empty JSON object `{}`.
+type Empty struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+}
+
+func (x *Empty) Reset() {
+ *x = Empty{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_protobuf_empty_proto_msgTypes[0]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Empty) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Empty) ProtoMessage() {}
+
+func (x *Empty) ProtoReflect() protoreflect.Message {
+ mi := &file_google_protobuf_empty_proto_msgTypes[0]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Empty.ProtoReflect.Descriptor instead.
+func (*Empty) Descriptor() ([]byte, []int) {
+ return file_google_protobuf_empty_proto_rawDescGZIP(), []int{0}
+}
+
+var File_google_protobuf_empty_proto protoreflect.FileDescriptor
+
+var file_google_protobuf_empty_proto_rawDesc = []byte{
+ 0x0a, 0x1b, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75,
+ 0x66, 0x2f, 0x65, 0x6d, 0x70, 0x74, 0x79, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67,
+ 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x22, 0x07,
+ 0x0a, 0x05, 0x45, 0x6d, 0x70, 0x74, 0x79, 0x42, 0x7d, 0x0a, 0x13, 0x63, 0x6f, 0x6d, 0x2e, 0x67,
+ 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x42, 0x0a,
+ 0x45, 0x6d, 0x70, 0x74, 0x79, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x2e, 0x67, 0x6f,
+ 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f,
+ 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x74, 0x79, 0x70, 0x65, 0x73, 0x2f, 0x6b,
+ 0x6e, 0x6f, 0x77, 0x6e, 0x2f, 0x65, 0x6d, 0x70, 0x74, 0x79, 0x70, 0x62, 0xf8, 0x01, 0x01, 0xa2,
+ 0x02, 0x03, 0x47, 0x50, 0x42, 0xaa, 0x02, 0x1e, 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x50,
+ 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77,
+ 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
+}
+
+var (
+ file_google_protobuf_empty_proto_rawDescOnce sync.Once
+ file_google_protobuf_empty_proto_rawDescData = file_google_protobuf_empty_proto_rawDesc
+)
+
+func file_google_protobuf_empty_proto_rawDescGZIP() []byte {
+ file_google_protobuf_empty_proto_rawDescOnce.Do(func() {
+ file_google_protobuf_empty_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_empty_proto_rawDescData)
+ })
+ return file_google_protobuf_empty_proto_rawDescData
+}
+
+var file_google_protobuf_empty_proto_msgTypes = make([]protoimpl.MessageInfo, 1)
+var file_google_protobuf_empty_proto_goTypes = []interface{}{
+ (*Empty)(nil), // 0: google.protobuf.Empty
+}
+var file_google_protobuf_empty_proto_depIdxs = []int32{
+ 0, // [0:0] is the sub-list for method output_type
+ 0, // [0:0] is the sub-list for method input_type
+ 0, // [0:0] is the sub-list for extension type_name
+ 0, // [0:0] is the sub-list for extension extendee
+ 0, // [0:0] is the sub-list for field type_name
+}
+
+func init() { file_google_protobuf_empty_proto_init() }
+func file_google_protobuf_empty_proto_init() {
+ if File_google_protobuf_empty_proto != nil {
+ return
+ }
+ if !protoimpl.UnsafeEnabled {
+ file_google_protobuf_empty_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Empty); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ }
+ type x struct{}
+ out := protoimpl.TypeBuilder{
+ File: protoimpl.DescBuilder{
+ GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+ RawDescriptor: file_google_protobuf_empty_proto_rawDesc,
+ NumEnums: 0,
+ NumMessages: 1,
+ NumExtensions: 0,
+ NumServices: 0,
+ },
+ GoTypes: file_google_protobuf_empty_proto_goTypes,
+ DependencyIndexes: file_google_protobuf_empty_proto_depIdxs,
+ MessageInfos: file_google_protobuf_empty_proto_msgTypes,
+ }.Build()
+ File_google_protobuf_empty_proto = out.File
+ file_google_protobuf_empty_proto_rawDesc = nil
+ file_google_protobuf_empty_proto_goTypes = nil
+ file_google_protobuf_empty_proto_depIdxs = nil
+}
diff --git a/vendor/google.golang.org/protobuf/types/known/structpb/struct.pb.go b/vendor/google.golang.org/protobuf/types/known/structpb/struct.pb.go
new file mode 100644
index 0000000000..586690522a
--- /dev/null
+++ b/vendor/google.golang.org/protobuf/types/known/structpb/struct.pb.go
@@ -0,0 +1,810 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// https://developers.google.com/protocol-buffers/
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions are
+// met:
+//
+// * Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// * Redistributions in binary form must reproduce the above
+// copyright notice, this list of conditions and the following disclaimer
+// in the documentation and/or other materials provided with the
+// distribution.
+// * Neither the name of Google Inc. nor the names of its
+// contributors may be used to endorse or promote products derived from
+// this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// source: google/protobuf/struct.proto
+
+// Package structpb contains generated types for google/protobuf/struct.proto.
+//
+// The messages (i.e., Value, Struct, and ListValue) defined in struct.proto are
+// used to represent arbitrary JSON. The Value message represents a JSON value,
+// the Struct message represents a JSON object, and the ListValue message
+// represents a JSON array. See https://json.org for more information.
+//
+// The Value, Struct, and ListValue types have generated MarshalJSON and
+// UnmarshalJSON methods such that they serialize JSON equivalent to what the
+// messages themselves represent. Use of these types with the
+// "google.golang.org/protobuf/encoding/protojson" package
+// ensures that they will be serialized as their JSON equivalent.
+//
+//
+// Conversion to and from a Go interface
+//
+// The standard Go "encoding/json" package has functionality to serialize
+// arbitrary types to a large degree. The Value.AsInterface, Struct.AsMap, and
+// ListValue.AsSlice methods can convert the protobuf message representation into
+// a form represented by interface{}, map[string]interface{}, and []interface{}.
+// This form can be used with other packages that operate on such data structures
+// and also directly with the standard json package.
+//
+// In order to convert the interface{}, map[string]interface{}, and []interface{}
+// forms back as Value, Struct, and ListValue messages, use the NewStruct,
+// NewList, and NewValue constructor functions.
+//
+//
+// Example usage
+//
+// Consider the following example JSON object:
+//
+// {
+// "firstName": "John",
+// "lastName": "Smith",
+// "isAlive": true,
+// "age": 27,
+// "address": {
+// "streetAddress": "21 2nd Street",
+// "city": "New York",
+// "state": "NY",
+// "postalCode": "10021-3100"
+// },
+// "phoneNumbers": [
+// {
+// "type": "home",
+// "number": "212 555-1234"
+// },
+// {
+// "type": "office",
+// "number": "646 555-4567"
+// }
+// ],
+// "children": [],
+// "spouse": null
+// }
+//
+// To construct a Value message representing the above JSON object:
+//
+// m, err := structpb.NewValue(map[string]interface{}{
+// "firstName": "John",
+// "lastName": "Smith",
+// "isAlive": true,
+// "age": 27,
+// "address": map[string]interface{}{
+// "streetAddress": "21 2nd Street",
+// "city": "New York",
+// "state": "NY",
+// "postalCode": "10021-3100",
+// },
+// "phoneNumbers": []interface{}{
+// map[string]interface{}{
+// "type": "home",
+// "number": "212 555-1234",
+// },
+// map[string]interface{}{
+// "type": "office",
+// "number": "646 555-4567",
+// },
+// },
+// "children": []interface{}{},
+// "spouse": nil,
+// })
+// if err != nil {
+// ... // handle error
+// }
+// ... // make use of m as a *structpb.Value
+//
+package structpb
+
+import (
+ base64 "encoding/base64"
+ protojson "google.golang.org/protobuf/encoding/protojson"
+ protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+ protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+ math "math"
+ reflect "reflect"
+ sync "sync"
+ utf8 "unicode/utf8"
+)
+
+// `NullValue` is a singleton enumeration to represent the null value for the
+// `Value` type union.
+//
+// The JSON representation for `NullValue` is JSON `null`.
+type NullValue int32
+
+const (
+ // Null value.
+ NullValue_NULL_VALUE NullValue = 0
+)
+
+// Enum value maps for NullValue.
+var (
+ NullValue_name = map[int32]string{
+ 0: "NULL_VALUE",
+ }
+ NullValue_value = map[string]int32{
+ "NULL_VALUE": 0,
+ }
+)
+
+func (x NullValue) Enum() *NullValue {
+ p := new(NullValue)
+ *p = x
+ return p
+}
+
+func (x NullValue) String() string {
+ return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (NullValue) Descriptor() protoreflect.EnumDescriptor {
+ return file_google_protobuf_struct_proto_enumTypes[0].Descriptor()
+}
+
+func (NullValue) Type() protoreflect.EnumType {
+ return &file_google_protobuf_struct_proto_enumTypes[0]
+}
+
+func (x NullValue) Number() protoreflect.EnumNumber {
+ return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use NullValue.Descriptor instead.
+func (NullValue) EnumDescriptor() ([]byte, []int) {
+ return file_google_protobuf_struct_proto_rawDescGZIP(), []int{0}
+}
+
+// `Struct` represents a structured data value, consisting of fields
+// which map to dynamically typed values. In some languages, `Struct`
+// might be supported by a native representation. For example, in
+// scripting languages like JS a struct is represented as an
+// object. The details of that representation are described together
+// with the proto support for the language.
+//
+// The JSON representation for `Struct` is JSON object.
+type Struct struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Unordered map of dynamically typed values.
+ Fields map[string]*Value `protobuf:"bytes,1,rep,name=fields,proto3" json:"fields,omitempty" protobuf_key:"bytes,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"`
+}
+
+// NewStruct constructs a Struct from a general-purpose Go map.
+// The map keys must be valid UTF-8.
+// The map values are converted using NewValue.
+func NewStruct(v map[string]interface{}) (*Struct, error) {
+ x := &Struct{Fields: make(map[string]*Value, len(v))}
+ for k, v := range v {
+ if !utf8.ValidString(k) {
+ return nil, protoimpl.X.NewError("invalid UTF-8 in string: %q", k)
+ }
+ var err error
+ x.Fields[k], err = NewValue(v)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return x, nil
+}
+
+// AsMap converts x to a general-purpose Go map.
+// The map values are converted by calling Value.AsInterface.
+func (x *Struct) AsMap() map[string]interface{} {
+ vs := make(map[string]interface{})
+ for k, v := range x.GetFields() {
+ vs[k] = v.AsInterface()
+ }
+ return vs
+}
+
+func (x *Struct) MarshalJSON() ([]byte, error) {
+ return protojson.Marshal(x)
+}
+
+func (x *Struct) UnmarshalJSON(b []byte) error {
+ return protojson.Unmarshal(b, x)
+}
+
+func (x *Struct) Reset() {
+ *x = Struct{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_protobuf_struct_proto_msgTypes[0]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Struct) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Struct) ProtoMessage() {}
+
+func (x *Struct) ProtoReflect() protoreflect.Message {
+ mi := &file_google_protobuf_struct_proto_msgTypes[0]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Struct.ProtoReflect.Descriptor instead.
+func (*Struct) Descriptor() ([]byte, []int) {
+ return file_google_protobuf_struct_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *Struct) GetFields() map[string]*Value {
+ if x != nil {
+ return x.Fields
+ }
+ return nil
+}
+
+// `Value` represents a dynamically typed value which can be either
+// null, a number, a string, a boolean, a recursive struct value, or a
+// list of values. A producer of value is expected to set one of that
+// variants, absence of any variant indicates an error.
+//
+// The JSON representation for `Value` is JSON value.
+type Value struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // The kind of value.
+ //
+ // Types that are assignable to Kind:
+ // *Value_NullValue
+ // *Value_NumberValue
+ // *Value_StringValue
+ // *Value_BoolValue
+ // *Value_StructValue
+ // *Value_ListValue
+ Kind isValue_Kind `protobuf_oneof:"kind"`
+}
+
+// NewValue constructs a Value from a general-purpose Go interface.
+//
+// ╔════════════════════════╤════════════════════════════════════════════╗
+// ║ Go type │ Conversion ║
+// ╠════════════════════════╪════════════════════════════════════════════╣
+// ║ nil │ stored as NullValue ║
+// ║ bool │ stored as BoolValue ║
+// ║ int, int32, int64 │ stored as NumberValue ║
+// ║ uint, uint32, uint64 │ stored as NumberValue ║
+// ║ float32, float64 │ stored as NumberValue ║
+// ║ string │ stored as StringValue; must be valid UTF-8 ║
+// ║ []byte │ stored as StringValue; base64-encoded ║
+// ║ map[string]interface{} │ stored as StructValue ║
+// ║ []interface{} │ stored as ListValue ║
+// ╚════════════════════════╧════════════════════════════════════════════╝
+//
+// When converting an int64 or uint64 to a NumberValue, numeric precision loss
+// is possible since they are stored as a float64.
+func NewValue(v interface{}) (*Value, error) {
+ switch v := v.(type) {
+ case nil:
+ return NewNullValue(), nil
+ case bool:
+ return NewBoolValue(v), nil
+ case int:
+ return NewNumberValue(float64(v)), nil
+ case int32:
+ return NewNumberValue(float64(v)), nil
+ case int64:
+ return NewNumberValue(float64(v)), nil
+ case uint:
+ return NewNumberValue(float64(v)), nil
+ case uint32:
+ return NewNumberValue(float64(v)), nil
+ case uint64:
+ return NewNumberValue(float64(v)), nil
+ case float32:
+ return NewNumberValue(float64(v)), nil
+ case float64:
+ return NewNumberValue(float64(v)), nil
+ case string:
+ if !utf8.ValidString(v) {
+ return nil, protoimpl.X.NewError("invalid UTF-8 in string: %q", v)
+ }
+ return NewStringValue(v), nil
+ case []byte:
+ s := base64.StdEncoding.EncodeToString(v)
+ return NewStringValue(s), nil
+ case map[string]interface{}:
+ v2, err := NewStruct(v)
+ if err != nil {
+ return nil, err
+ }
+ return NewStructValue(v2), nil
+ case []interface{}:
+ v2, err := NewList(v)
+ if err != nil {
+ return nil, err
+ }
+ return NewListValue(v2), nil
+ default:
+ return nil, protoimpl.X.NewError("invalid type: %T", v)
+ }
+}
+
+// NewNullValue constructs a new null Value.
+func NewNullValue() *Value {
+ return &Value{Kind: &Value_NullValue{NullValue: NullValue_NULL_VALUE}}
+}
+
+// NewBoolValue constructs a new boolean Value.
+func NewBoolValue(v bool) *Value {
+ return &Value{Kind: &Value_BoolValue{BoolValue: v}}
+}
+
+// NewNumberValue constructs a new number Value.
+func NewNumberValue(v float64) *Value {
+ return &Value{Kind: &Value_NumberValue{NumberValue: v}}
+}
+
+// NewStringValue constructs a new string Value.
+func NewStringValue(v string) *Value {
+ return &Value{Kind: &Value_StringValue{StringValue: v}}
+}
+
+// NewStructValue constructs a new struct Value.
+func NewStructValue(v *Struct) *Value {
+ return &Value{Kind: &Value_StructValue{StructValue: v}}
+}
+
+// NewListValue constructs a new list Value.
+func NewListValue(v *ListValue) *Value {
+ return &Value{Kind: &Value_ListValue{ListValue: v}}
+}
+
+// AsInterface converts x to a general-purpose Go interface.
+//
+// Calling Value.MarshalJSON and "encoding/json".Marshal on this output produce
+// semantically equivalent JSON (assuming no errors occur).
+//
+// Floating-point values (i.e., "NaN", "Infinity", and "-Infinity") are
+// converted as strings to remain compatible with MarshalJSON.
+func (x *Value) AsInterface() interface{} {
+ switch v := x.GetKind().(type) {
+ case *Value_NumberValue:
+ if v != nil {
+ switch {
+ case math.IsNaN(v.NumberValue):
+ return "NaN"
+ case math.IsInf(v.NumberValue, +1):
+ return "Infinity"
+ case math.IsInf(v.NumberValue, -1):
+ return "-Infinity"
+ default:
+ return v.NumberValue
+ }
+ }
+ case *Value_StringValue:
+ if v != nil {
+ return v.StringValue
+ }
+ case *Value_BoolValue:
+ if v != nil {
+ return v.BoolValue
+ }
+ case *Value_StructValue:
+ if v != nil {
+ return v.StructValue.AsMap()
+ }
+ case *Value_ListValue:
+ if v != nil {
+ return v.ListValue.AsSlice()
+ }
+ }
+ return nil
+}
+
+func (x *Value) MarshalJSON() ([]byte, error) {
+ return protojson.Marshal(x)
+}
+
+func (x *Value) UnmarshalJSON(b []byte) error {
+ return protojson.Unmarshal(b, x)
+}
+
+func (x *Value) Reset() {
+ *x = Value{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_protobuf_struct_proto_msgTypes[1]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *Value) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Value) ProtoMessage() {}
+
+func (x *Value) ProtoReflect() protoreflect.Message {
+ mi := &file_google_protobuf_struct_proto_msgTypes[1]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use Value.ProtoReflect.Descriptor instead.
+func (*Value) Descriptor() ([]byte, []int) {
+ return file_google_protobuf_struct_proto_rawDescGZIP(), []int{1}
+}
+
+func (m *Value) GetKind() isValue_Kind {
+ if m != nil {
+ return m.Kind
+ }
+ return nil
+}
+
+func (x *Value) GetNullValue() NullValue {
+ if x, ok := x.GetKind().(*Value_NullValue); ok {
+ return x.NullValue
+ }
+ return NullValue_NULL_VALUE
+}
+
+func (x *Value) GetNumberValue() float64 {
+ if x, ok := x.GetKind().(*Value_NumberValue); ok {
+ return x.NumberValue
+ }
+ return 0
+}
+
+func (x *Value) GetStringValue() string {
+ if x, ok := x.GetKind().(*Value_StringValue); ok {
+ return x.StringValue
+ }
+ return ""
+}
+
+func (x *Value) GetBoolValue() bool {
+ if x, ok := x.GetKind().(*Value_BoolValue); ok {
+ return x.BoolValue
+ }
+ return false
+}
+
+func (x *Value) GetStructValue() *Struct {
+ if x, ok := x.GetKind().(*Value_StructValue); ok {
+ return x.StructValue
+ }
+ return nil
+}
+
+func (x *Value) GetListValue() *ListValue {
+ if x, ok := x.GetKind().(*Value_ListValue); ok {
+ return x.ListValue
+ }
+ return nil
+}
+
+type isValue_Kind interface {
+ isValue_Kind()
+}
+
+type Value_NullValue struct {
+ // Represents a null value.
+ NullValue NullValue `protobuf:"varint,1,opt,name=null_value,json=nullValue,proto3,enum=google.protobuf.NullValue,oneof"`
+}
+
+type Value_NumberValue struct {
+ // Represents a double value.
+ NumberValue float64 `protobuf:"fixed64,2,opt,name=number_value,json=numberValue,proto3,oneof"`
+}
+
+type Value_StringValue struct {
+ // Represents a string value.
+ StringValue string `protobuf:"bytes,3,opt,name=string_value,json=stringValue,proto3,oneof"`
+}
+
+type Value_BoolValue struct {
+ // Represents a boolean value.
+ BoolValue bool `protobuf:"varint,4,opt,name=bool_value,json=boolValue,proto3,oneof"`
+}
+
+type Value_StructValue struct {
+ // Represents a structured value.
+ StructValue *Struct `protobuf:"bytes,5,opt,name=struct_value,json=structValue,proto3,oneof"`
+}
+
+type Value_ListValue struct {
+ // Represents a repeated `Value`.
+ ListValue *ListValue `protobuf:"bytes,6,opt,name=list_value,json=listValue,proto3,oneof"`
+}
+
+func (*Value_NullValue) isValue_Kind() {}
+
+func (*Value_NumberValue) isValue_Kind() {}
+
+func (*Value_StringValue) isValue_Kind() {}
+
+func (*Value_BoolValue) isValue_Kind() {}
+
+func (*Value_StructValue) isValue_Kind() {}
+
+func (*Value_ListValue) isValue_Kind() {}
+
+// `ListValue` is a wrapper around a repeated field of values.
+//
+// The JSON representation for `ListValue` is JSON array.
+type ListValue struct {
+ state protoimpl.MessageState
+ sizeCache protoimpl.SizeCache
+ unknownFields protoimpl.UnknownFields
+
+ // Repeated field of dynamically typed values.
+ Values []*Value `protobuf:"bytes,1,rep,name=values,proto3" json:"values,omitempty"`
+}
+
+// NewList constructs a ListValue from a general-purpose Go slice.
+// The slice elements are converted using NewValue.
+func NewList(v []interface{}) (*ListValue, error) {
+ x := &ListValue{Values: make([]*Value, len(v))}
+ for i, v := range v {
+ var err error
+ x.Values[i], err = NewValue(v)
+ if err != nil {
+ return nil, err
+ }
+ }
+ return x, nil
+}
+
+// AsSlice converts x to a general-purpose Go slice.
+// The slice elements are converted by calling Value.AsInterface.
+func (x *ListValue) AsSlice() []interface{} {
+ vs := make([]interface{}, len(x.GetValues()))
+ for i, v := range x.GetValues() {
+ vs[i] = v.AsInterface()
+ }
+ return vs
+}
+
+func (x *ListValue) MarshalJSON() ([]byte, error) {
+ return protojson.Marshal(x)
+}
+
+func (x *ListValue) UnmarshalJSON(b []byte) error {
+ return protojson.Unmarshal(b, x)
+}
+
+func (x *ListValue) Reset() {
+ *x = ListValue{}
+ if protoimpl.UnsafeEnabled {
+ mi := &file_google_protobuf_struct_proto_msgTypes[2]
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ ms.StoreMessageInfo(mi)
+ }
+}
+
+func (x *ListValue) String() string {
+ return protoimpl.X.MessageStringOf(x)
+}
+
+func (*ListValue) ProtoMessage() {}
+
+func (x *ListValue) ProtoReflect() protoreflect.Message {
+ mi := &file_google_protobuf_struct_proto_msgTypes[2]
+ if protoimpl.UnsafeEnabled && x != nil {
+ ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+ if ms.LoadMessageInfo() == nil {
+ ms.StoreMessageInfo(mi)
+ }
+ return ms
+ }
+ return mi.MessageOf(x)
+}
+
+// Deprecated: Use ListValue.ProtoReflect.Descriptor instead.
+func (*ListValue) Descriptor() ([]byte, []int) {
+ return file_google_protobuf_struct_proto_rawDescGZIP(), []int{2}
+}
+
+func (x *ListValue) GetValues() []*Value {
+ if x != nil {
+ return x.Values
+ }
+ return nil
+}
+
+var File_google_protobuf_struct_proto protoreflect.FileDescriptor
+
+var file_google_protobuf_struct_proto_rawDesc = []byte{
+ 0x0a, 0x1c, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75,
+ 0x66, 0x2f, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f,
+ 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x22,
+ 0x98, 0x01, 0x0a, 0x06, 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x12, 0x3b, 0x0a, 0x06, 0x66, 0x69,
+ 0x65, 0x6c, 0x64, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x67, 0x6f, 0x6f,
+ 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72,
+ 0x75, 0x63, 0x74, 0x2e, 0x46, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52,
+ 0x06, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x73, 0x1a, 0x51, 0x0a, 0x0b, 0x46, 0x69, 0x65, 0x6c, 0x64,
+ 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20,
+ 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x2c, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75,
+ 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65,
+ 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x52,
+ 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0xb2, 0x02, 0x0a, 0x05, 0x56,
+ 0x61, 0x6c, 0x75, 0x65, 0x12, 0x3b, 0x0a, 0x0a, 0x6e, 0x75, 0x6c, 0x6c, 0x5f, 0x76, 0x61, 0x6c,
+ 0x75, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x1a, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
+ 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x4e, 0x75, 0x6c, 0x6c, 0x56,
+ 0x61, 0x6c, 0x75, 0x65, 0x48, 0x00, 0x52, 0x09, 0x6e, 0x75, 0x6c, 0x6c, 0x56, 0x61, 0x6c, 0x75,
+ 0x65, 0x12, 0x23, 0x0a, 0x0c, 0x6e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x5f, 0x76, 0x61, 0x6c, 0x75,
+ 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x01, 0x48, 0x00, 0x52, 0x0b, 0x6e, 0x75, 0x6d, 0x62, 0x65,
+ 0x72, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x23, 0x0a, 0x0c, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67,
+ 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x0b,
+ 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x1f, 0x0a, 0x0a, 0x62,
+ 0x6f, 0x6f, 0x6c, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x48,
+ 0x00, 0x52, 0x09, 0x62, 0x6f, 0x6f, 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x3c, 0x0a, 0x0c,
+ 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x05, 0x20, 0x01,
+ 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74,
+ 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x48, 0x00, 0x52, 0x0b, 0x73,
+ 0x74, 0x72, 0x75, 0x63, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x3b, 0x0a, 0x0a, 0x6c, 0x69,
+ 0x73, 0x74, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1a,
+ 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66,
+ 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x48, 0x00, 0x52, 0x09, 0x6c, 0x69,
+ 0x73, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x42, 0x06, 0x0a, 0x04, 0x6b, 0x69, 0x6e, 0x64, 0x22,
+ 0x3b, 0x0a, 0x09, 0x4c, 0x69, 0x73, 0x74, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x2e, 0x0a, 0x06,
+ 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x67,
+ 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x56,
+ 0x61, 0x6c, 0x75, 0x65, 0x52, 0x06, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x2a, 0x1b, 0x0a, 0x09,
+ 0x4e, 0x75, 0x6c, 0x6c, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x0e, 0x0a, 0x0a, 0x4e, 0x55, 0x4c,
+ 0x4c, 0x5f, 0x56, 0x41, 0x4c, 0x55, 0x45, 0x10, 0x00, 0x42, 0x7f, 0x0a, 0x13, 0x63, 0x6f, 0x6d,
+ 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66,
+ 0x42, 0x0b, 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a,
+ 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f,
+ 0x72, 0x67, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x74, 0x79, 0x70, 0x65,
+ 0x73, 0x2f, 0x6b, 0x6e, 0x6f, 0x77, 0x6e, 0x2f, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x70, 0x62,
+ 0xf8, 0x01, 0x01, 0xa2, 0x02, 0x03, 0x47, 0x50, 0x42, 0xaa, 0x02, 0x1e, 0x47, 0x6f, 0x6f, 0x67,
+ 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c,
+ 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74,
+ 0x6f, 0x33,
+}
+
+var (
+ file_google_protobuf_struct_proto_rawDescOnce sync.Once
+ file_google_protobuf_struct_proto_rawDescData = file_google_protobuf_struct_proto_rawDesc
+)
+
+func file_google_protobuf_struct_proto_rawDescGZIP() []byte {
+ file_google_protobuf_struct_proto_rawDescOnce.Do(func() {
+ file_google_protobuf_struct_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_struct_proto_rawDescData)
+ })
+ return file_google_protobuf_struct_proto_rawDescData
+}
+
+var file_google_protobuf_struct_proto_enumTypes = make([]protoimpl.EnumInfo, 1)
+var file_google_protobuf_struct_proto_msgTypes = make([]protoimpl.MessageInfo, 4)
+var file_google_protobuf_struct_proto_goTypes = []interface{}{
+ (NullValue)(0), // 0: google.protobuf.NullValue
+ (*Struct)(nil), // 1: google.protobuf.Struct
+ (*Value)(nil), // 2: google.protobuf.Value
+ (*ListValue)(nil), // 3: google.protobuf.ListValue
+ nil, // 4: google.protobuf.Struct.FieldsEntry
+}
+var file_google_protobuf_struct_proto_depIdxs = []int32{
+ 4, // 0: google.protobuf.Struct.fields:type_name -> google.protobuf.Struct.FieldsEntry
+ 0, // 1: google.protobuf.Value.null_value:type_name -> google.protobuf.NullValue
+ 1, // 2: google.protobuf.Value.struct_value:type_name -> google.protobuf.Struct
+ 3, // 3: google.protobuf.Value.list_value:type_name -> google.protobuf.ListValue
+ 2, // 4: google.protobuf.ListValue.values:type_name -> google.protobuf.Value
+ 2, // 5: google.protobuf.Struct.FieldsEntry.value:type_name -> google.protobuf.Value
+ 6, // [6:6] is the sub-list for method output_type
+ 6, // [6:6] is the sub-list for method input_type
+ 6, // [6:6] is the sub-list for extension type_name
+ 6, // [6:6] is the sub-list for extension extendee
+ 0, // [0:6] is the sub-list for field type_name
+}
+
+func init() { file_google_protobuf_struct_proto_init() }
+func file_google_protobuf_struct_proto_init() {
+ if File_google_protobuf_struct_proto != nil {
+ return
+ }
+ if !protoimpl.UnsafeEnabled {
+ file_google_protobuf_struct_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Struct); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_protobuf_struct_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*Value); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ file_google_protobuf_struct_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+ switch v := v.(*ListValue); i {
+ case 0:
+ return &v.state
+ case 1:
+ return &v.sizeCache
+ case 2:
+ return &v.unknownFields
+ default:
+ return nil
+ }
+ }
+ }
+ file_google_protobuf_struct_proto_msgTypes[1].OneofWrappers = []interface{}{
+ (*Value_NullValue)(nil),
+ (*Value_NumberValue)(nil),
+ (*Value_StringValue)(nil),
+ (*Value_BoolValue)(nil),
+ (*Value_StructValue)(nil),
+ (*Value_ListValue)(nil),
+ }
+ type x struct{}
+ out := protoimpl.TypeBuilder{
+ File: protoimpl.DescBuilder{
+ GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+ RawDescriptor: file_google_protobuf_struct_proto_rawDesc,
+ NumEnums: 1,
+ NumMessages: 4,
+ NumExtensions: 0,
+ NumServices: 0,
+ },
+ GoTypes: file_google_protobuf_struct_proto_goTypes,
+ DependencyIndexes: file_google_protobuf_struct_proto_depIdxs,
+ EnumInfos: file_google_protobuf_struct_proto_enumTypes,
+ MessageInfos: file_google_protobuf_struct_proto_msgTypes,
+ }.Build()
+ File_google_protobuf_struct_proto = out.File
+ file_google_protobuf_struct_proto_rawDesc = nil
+ file_google_protobuf_struct_proto_goTypes = nil
+ file_google_protobuf_struct_proto_depIdxs = nil
+}
diff --git a/vendor/modules.txt b/vendor/modules.txt
index 608e592a43..b4edece474 100644
--- a/vendor/modules.txt
+++ b/vendor/modules.txt
@@ -64,6 +64,8 @@ github.com/PuerkitoBio/purell
github.com/PuerkitoBio/urlesc
# github.com/alessio/shellescape v1.4.1
github.com/alessio/shellescape
+# github.com/antlr/antlr4/runtime/Go/antlr v0.0.0-20210826220005-b48c857c3a0e
+github.com/antlr/antlr4/runtime/Go/antlr
# github.com/asaskevich/govalidator v0.0.0-20200428143746-21a406dcc535
github.com/asaskevich/govalidator
# github.com/beorn7/perks v1.0.1
@@ -287,6 +289,24 @@ github.com/golang/protobuf/ptypes/timestamp
github.com/golang/protobuf/ptypes/wrappers
# github.com/google/btree v1.0.1
github.com/google/btree
+# github.com/google/cel-go v0.9.0
+github.com/google/cel-go/cel
+github.com/google/cel-go/checker
+github.com/google/cel-go/checker/decls
+github.com/google/cel-go/common
+github.com/google/cel-go/common/containers
+github.com/google/cel-go/common/debug
+github.com/google/cel-go/common/operators
+github.com/google/cel-go/common/overloads
+github.com/google/cel-go/common/runes
+github.com/google/cel-go/common/types
+github.com/google/cel-go/common/types/pb
+github.com/google/cel-go/common/types/ref
+github.com/google/cel-go/common/types/traits
+github.com/google/cel-go/interpreter
+github.com/google/cel-go/interpreter/functions
+github.com/google/cel-go/parser
+github.com/google/cel-go/parser/gen
# github.com/google/go-cmp v0.5.6
## explicit
github.com/google/go-cmp/cmp
@@ -498,6 +518,7 @@ github.com/openshift/client-go/config/listers/config/v1
# github.com/operator-framework/api v0.10.8-0.20211210205029-40cb9fd4036a
## explicit
github.com/operator-framework/api/crds
+github.com/operator-framework/api/pkg/constraints
github.com/operator-framework/api/pkg/lib/version
github.com/operator-framework/api/pkg/manifests
github.com/operator-framework/api/pkg/operators
@@ -589,6 +610,8 @@ github.com/spf13/cobra/doc
# github.com/spf13/pflag v1.0.5
## explicit
github.com/spf13/pflag
+# github.com/stoewer/go-strcase v1.2.0
+github.com/stoewer/go-strcase
# github.com/stretchr/testify v1.7.0
## explicit
github.com/stretchr/testify/assert
@@ -834,6 +857,7 @@ google.golang.org/appengine/internal/urlfetch
google.golang.org/appengine/urlfetch
# google.golang.org/genproto v0.0.0-20210831024726-fe130286e0e2
google.golang.org/genproto/googleapis/api/annotations
+google.golang.org/genproto/googleapis/api/expr/v1alpha1
google.golang.org/genproto/googleapis/api/httpbody
google.golang.org/genproto/googleapis/rpc/status
google.golang.org/genproto/protobuf/field_mask
@@ -915,9 +939,12 @@ google.golang.org/protobuf/reflect/protoregistry
google.golang.org/protobuf/runtime/protoiface
google.golang.org/protobuf/runtime/protoimpl
google.golang.org/protobuf/types/descriptorpb
+google.golang.org/protobuf/types/dynamicpb
google.golang.org/protobuf/types/known/anypb
google.golang.org/protobuf/types/known/durationpb
+google.golang.org/protobuf/types/known/emptypb
google.golang.org/protobuf/types/known/fieldmaskpb
+google.golang.org/protobuf/types/known/structpb
google.golang.org/protobuf/types/known/timestamppb
google.golang.org/protobuf/types/known/wrapperspb
# gopkg.in/gorp.v1 v1.7.2