From 4509a001dffff626d2d8708fd2eb1c6317b201f3 Mon Sep 17 00:00:00 2001 From: Ying Li Date: Tue, 11 Jul 2017 12:22:34 -0700 Subject: [PATCH] Re-vendor swarmkit. This includes the following fixes: - https://github.com/docker/swarmkit/pull/2266 (support for templating Node.Hostname in docker executor) - https://github.com/docker/swarmkit/pull/2281 (change restore action on objects to be update, not delete/create) - https://github.com/docker/swarmkit/pull/2285 (extend watch queue with timeout and size limit) - https://github.com/docker/swarmkit/pull/2253 (version-aware failure tracking in the scheduler) - https://github.com/docker/swarmkit/pull/2275 (update containerd and port executor to container client library) - https://github.com/docker/swarmkit/pull/2292 (rename some generic resources) - https://github.com/docker/swarmkit/pull/2300 (limit the size of the external CA response) - https://github.com/docker/swarmkit/pull/2301 (delete global tasks when the node running them is deleted) Minor cleanups, dependency bumps, and vendoring: - https://github.com/docker/swarmkit/pull/2271 - https://github.com/docker/swarmkit/pull/2279 - https://github.com/docker/swarmkit/pull/2283 - https://github.com/docker/swarmkit/pull/2282 - https://github.com/docker/swarmkit/pull/2274 - https://github.com/docker/swarmkit/pull/2296 (dependency bump of etcd, go-winio) Signed-off-by: Ying Li --- .../cluster/executor/container/container.go | 2 +- vendor.conf | 2 +- .../docker/swarmkit/agent/storage.go | 8 +- .../swarmkit/api/genericresource/helpers.go | 22 +- .../genericresource/resource_management.go | 36 +- .../swarmkit/api/genericresource/string.go | 18 +- .../swarmkit/api/genericresource/validate.go | 22 +- .../docker/swarmkit/api/types.pb.go | 811 +++++++++--------- .../docker/swarmkit/api/types.proto | 18 +- .../github.com/docker/swarmkit/ca/config.go | 42 +- .../github.com/docker/swarmkit/ca/external.go | 18 +- .../swarmkit/manager/controlapi/service.go | 8 +- .../swarmkit/manager/dispatcher/dispatcher.go | 10 +- .../manager/orchestrator/global/global.go | 41 +- .../swarmkit/manager/scheduler/nodeinfo.go | 70 +- .../swarmkit/manager/scheduler/scheduler.go | 6 +- .../swarmkit/manager/state/store/clusters.go | 18 +- .../swarmkit/manager/state/store/configs.go | 18 +- .../manager/state/store/extensions.go | 26 +- .../swarmkit/manager/state/store/networks.go | 18 +- .../swarmkit/manager/state/store/nodes.go | 18 +- .../swarmkit/manager/state/store/object.go | 43 + .../swarmkit/manager/state/store/resources.go | 26 +- .../swarmkit/manager/state/store/secrets.go | 18 +- .../swarmkit/manager/state/store/services.go | 18 +- .../swarmkit/manager/state/store/tasks.go | 18 +- .../github.com/docker/swarmkit/node/node.go | 42 +- .../docker/swarmkit/template/context.go | 32 +- .../docker/swarmkit/template/expand.go | 15 +- .../docker/swarmkit/template/getter.go | 20 +- vendor/github.com/docker/swarmkit/vendor.conf | 12 +- .../docker/swarmkit/watch/queue/queue.go | 158 ++++ .../github.com/docker/swarmkit/watch/sinks.go | 95 ++ .../github.com/docker/swarmkit/watch/watch.go | 160 +++- 34 files changed, 1155 insertions(+), 734 deletions(-) create mode 100644 vendor/github.com/docker/swarmkit/watch/queue/queue.go create mode 100644 vendor/github.com/docker/swarmkit/watch/sinks.go diff --git a/daemon/cluster/executor/container/container.go b/daemon/cluster/executor/container/container.go index 501da3286c..f27980cb1a 100644 --- a/daemon/cluster/executor/container/container.go +++ b/daemon/cluster/executor/container/container.go @@ -77,7 +77,7 @@ func (c *containerConfig) setTask(t *api.Task) error { c.task = t if t.Spec.GetContainer() != nil { - preparedSpec, err := template.ExpandContainerSpec(t) + preparedSpec, err := template.ExpandContainerSpec(nil, t) if err != nil { return err } diff --git a/vendor.conf b/vendor.conf index 98db7a9774..edc1d83aaf 100644 --- a/vendor.conf +++ b/vendor.conf @@ -106,7 +106,7 @@ github.com/stevvooe/continuity cd7a8e21e2b6f84799f5dd4b65faf49c8d3ee02d github.com/tonistiigi/fsutil 0ac4c11b053b9c5c7c47558f81f96c7100ce50fb # cluster -github.com/docker/swarmkit 79381d0840be27f8b3f5c667b348a4467d866eeb +github.com/docker/swarmkit a3d96fe13e30e46c3d4cfc3f316ebdd8446a079d github.com/gogo/protobuf v0.4 github.com/cloudflare/cfssl 7fb22c8cba7ecaf98e4082d22d65800cf45e042a github.com/google/certificate-transparency d90e65c3a07988180c5b1ece71791c0b6506826e diff --git a/vendor/github.com/docker/swarmkit/agent/storage.go b/vendor/github.com/docker/swarmkit/agent/storage.go index f488de7638..a49ad81fa4 100644 --- a/vendor/github.com/docker/swarmkit/agent/storage.go +++ b/vendor/github.com/docker/swarmkit/agent/storage.go @@ -35,7 +35,7 @@ func GetTask(tx *bolt.Tx, id string) (*api.Task, error) { var t api.Task if err := withTaskBucket(tx, id, func(bkt *bolt.Bucket) error { - p := bkt.Get([]byte("data")) + p := bkt.Get(bucketKeyData) if p == nil { return errTaskUnknown } @@ -136,7 +136,7 @@ func PutTaskStatus(tx *bolt.Tx, id string, status *api.TaskStatus) error { if err != nil { return err } - return bkt.Put([]byte("status"), p) + return bkt.Put(bucketKeyStatus, p) }) } @@ -154,9 +154,9 @@ func DeleteTask(tx *bolt.Tx, id string) error { func SetTaskAssignment(tx *bolt.Tx, id string, assigned bool) error { return withTaskBucket(tx, id, func(bkt *bolt.Bucket) error { if assigned { - return bkt.Put([]byte("assigned"), []byte{0xFF}) + return bkt.Put(bucketKeyAssigned, []byte{0xFF}) } - return bkt.Delete([]byte("assigned")) + return bkt.Delete(bucketKeyAssigned) }) } diff --git a/vendor/github.com/docker/swarmkit/api/genericresource/helpers.go b/vendor/github.com/docker/swarmkit/api/genericresource/helpers.go index f9c22ac6cc..350ab730c1 100644 --- a/vendor/github.com/docker/swarmkit/api/genericresource/helpers.go +++ b/vendor/github.com/docker/swarmkit/api/genericresource/helpers.go @@ -18,8 +18,8 @@ func NewSet(key string, vals ...string) []*api.GenericResource { // NewString creates a String resource func NewString(key, val string) *api.GenericResource { return &api.GenericResource{ - Resource: &api.GenericResource_Str{ - Str: &api.GenericString{ + Resource: &api.GenericResource_NamedResourceSpec{ + NamedResourceSpec: &api.NamedGenericResource{ Kind: key, Value: val, }, @@ -30,8 +30,8 @@ func NewString(key, val string) *api.GenericResource { // NewDiscrete creates a Discrete resource func NewDiscrete(key string, val int64) *api.GenericResource { return &api.GenericResource{ - Resource: &api.GenericResource_Discrete{ - Discrete: &api.GenericDiscrete{ + Resource: &api.GenericResource_DiscreteResourceSpec{ + DiscreteResourceSpec: &api.DiscreteGenericResource{ Kind: key, Value: val, }, @@ -86,21 +86,21 @@ loop: // Returns true if the element is to be removed from the list func remove(na, r *api.GenericResource) bool { switch tr := r.Resource.(type) { - case *api.GenericResource_Discrete: - if na.GetDiscrete() == nil { + case *api.GenericResource_DiscreteResourceSpec: + if na.GetDiscreteResourceSpec() == nil { return false // Type change, ignore } - na.GetDiscrete().Value -= tr.Discrete.Value - if na.GetDiscrete().Value <= 0 { + na.GetDiscreteResourceSpec().Value -= tr.DiscreteResourceSpec.Value + if na.GetDiscreteResourceSpec().Value <= 0 { return true } - case *api.GenericResource_Str: - if na.GetStr() == nil { + case *api.GenericResource_NamedResourceSpec: + if na.GetNamedResourceSpec() == nil { return false // Type change, ignore } - if tr.Str.Value != na.GetStr().Value { + if tr.NamedResourceSpec.Value != na.GetNamedResourceSpec().Value { return false // not the right item, ignore } diff --git a/vendor/github.com/docker/swarmkit/api/genericresource/resource_management.go b/vendor/github.com/docker/swarmkit/api/genericresource/resource_management.go index 217c52051a..a89a118d62 100644 --- a/vendor/github.com/docker/swarmkit/api/genericresource/resource_management.go +++ b/vendor/github.com/docker/swarmkit/api/genericresource/resource_management.go @@ -12,7 +12,7 @@ func Claim(nodeAvailableResources, taskAssigned *[]*api.GenericResource, var resSelected []*api.GenericResource for _, res := range taskReservations { - tr := res.GetDiscrete() + tr := res.GetDiscreteResourceSpec() if tr == nil { return fmt.Errorf("task should only hold Discrete type") } @@ -39,7 +39,7 @@ func ClaimResources(nodeAvailableResources, taskAssigned *[]*api.GenericResource } func selectNodeResources(nodeRes []*api.GenericResource, - tr *api.GenericDiscrete) ([]*api.GenericResource, error) { + tr *api.DiscreteGenericResource) ([]*api.GenericResource, error) { var nrs []*api.GenericResource for _, res := range nodeRes { @@ -48,13 +48,13 @@ func selectNodeResources(nodeRes []*api.GenericResource, } switch nr := res.Resource.(type) { - case *api.GenericResource_Discrete: - if nr.Discrete.Value >= tr.Value && tr.Value != 0 { + case *api.GenericResource_DiscreteResourceSpec: + if nr.DiscreteResourceSpec.Value >= tr.Value && tr.Value != 0 { nrs = append(nrs, NewDiscrete(tr.Kind, tr.Value)) } return nrs, nil - case *api.GenericResource_Str: + case *api.GenericResource_NamedResourceSpec: nrs = append(nrs, res.Copy()) if int64(len(nrs)) == tr.Value { @@ -90,8 +90,8 @@ func reclaimResources(nodeAvailableResources *[]*api.GenericResource, taskAssign for _, res := range taskAssigned { switch tr := res.Resource.(type) { - case *api.GenericResource_Discrete: - nrs := GetResource(tr.Discrete.Kind, *nodeAvailableResources) + case *api.GenericResource_DiscreteResourceSpec: + nrs := GetResource(tr.DiscreteResourceSpec.Kind, *nodeAvailableResources) // If the resource went down to 0 it's no longer in the // available list @@ -103,13 +103,13 @@ func reclaimResources(nodeAvailableResources *[]*api.GenericResource, taskAssign continue // Type change } - nr := nrs[0].GetDiscrete() + nr := nrs[0].GetDiscreteResourceSpec() if nr == nil { continue // Type change } - nr.Value += tr.Discrete.Value - case *api.GenericResource_Str: + nr.Value += tr.DiscreteResourceSpec.Value + case *api.GenericResource_NamedResourceSpec: *nodeAvailableResources = append(*nodeAvailableResources, res.Copy()) } } @@ -157,8 +157,8 @@ func sanitize(nodeRes []*api.GenericResource, nodeAvailableResources *[]*api.Gen // Returns false if the element isn't in nodeRes and "sane" and the element(s) that should be replacing it func sanitizeResource(nodeRes []*api.GenericResource, res *api.GenericResource) (ok bool, nrs []*api.GenericResource) { switch na := res.Resource.(type) { - case *api.GenericResource_Discrete: - nrs := GetResource(na.Discrete.Kind, nodeRes) + case *api.GenericResource_DiscreteResourceSpec: + nrs := GetResource(na.DiscreteResourceSpec.Kind, nodeRes) // Type change or removed: reset if len(nrs) != 1 { @@ -166,17 +166,17 @@ func sanitizeResource(nodeRes []*api.GenericResource, res *api.GenericResource) } // Type change: reset - nr := nrs[0].GetDiscrete() + nr := nrs[0].GetDiscreteResourceSpec() if nr == nil { return false, nrs } // Amount change: reset - if na.Discrete.Value > nr.Value { + if na.DiscreteResourceSpec.Value > nr.Value { return false, nrs } - case *api.GenericResource_Str: - nrs := GetResource(na.Str.Kind, nodeRes) + case *api.GenericResource_NamedResourceSpec: + nrs := GetResource(na.NamedResourceSpec.Kind, nodeRes) // Type change if len(nrs) == 0 { @@ -185,11 +185,11 @@ func sanitizeResource(nodeRes []*api.GenericResource, res *api.GenericResource) for _, nr := range nrs { // Type change: reset - if nr.GetDiscrete() != nil { + if nr.GetDiscreteResourceSpec() != nil { return false, nrs } - if na.Str.Value == nr.GetStr().Value { + if na.NamedResourceSpec.Value == nr.GetNamedResourceSpec().Value { return true, nil } } diff --git a/vendor/github.com/docker/swarmkit/api/genericresource/string.go b/vendor/github.com/docker/swarmkit/api/genericresource/string.go index a353853135..5e388bebb0 100644 --- a/vendor/github.com/docker/swarmkit/api/genericresource/string.go +++ b/vendor/github.com/docker/swarmkit/api/genericresource/string.go @@ -7,17 +7,17 @@ import ( "github.com/docker/swarmkit/api" ) -func discreteToString(d *api.GenericResource_Discrete) string { - return strconv.FormatInt(d.Discrete.Value, 10) +func discreteToString(d *api.GenericResource_DiscreteResourceSpec) string { + return strconv.FormatInt(d.DiscreteResourceSpec.Value, 10) } // Kind returns the kind key as a string func Kind(res *api.GenericResource) string { switch r := res.Resource.(type) { - case *api.GenericResource_Discrete: - return r.Discrete.Kind - case *api.GenericResource_Str: - return r.Str.Kind + case *api.GenericResource_DiscreteResourceSpec: + return r.DiscreteResourceSpec.Kind + case *api.GenericResource_NamedResourceSpec: + return r.NamedResourceSpec.Kind } return "" @@ -26,10 +26,10 @@ func Kind(res *api.GenericResource) string { // Value returns the value key as a string func Value(res *api.GenericResource) string { switch res := res.Resource.(type) { - case *api.GenericResource_Discrete: + case *api.GenericResource_DiscreteResourceSpec: return discreteToString(res) - case *api.GenericResource_Str: - return res.Str.Value + case *api.GenericResource_NamedResourceSpec: + return res.NamedResourceSpec.Value } return "" diff --git a/vendor/github.com/docker/swarmkit/api/genericresource/validate.go b/vendor/github.com/docker/swarmkit/api/genericresource/validate.go index 98953e107d..eee3706c74 100644 --- a/vendor/github.com/docker/swarmkit/api/genericresource/validate.go +++ b/vendor/github.com/docker/swarmkit/api/genericresource/validate.go @@ -9,7 +9,7 @@ import ( // for generic resources func ValidateTask(resources *api.Resources) error { for _, v := range resources.Generic { - if v.GetDiscrete() != nil { + if v.GetDiscreteResourceSpec() != nil { continue } @@ -21,7 +21,7 @@ func ValidateTask(resources *api.Resources) error { // HasEnough returns true if node can satisfy the task's GenericResource request func HasEnough(nodeRes []*api.GenericResource, taskRes *api.GenericResource) (bool, error) { - t := taskRes.GetDiscrete() + t := taskRes.GetDiscreteResourceSpec() if t == nil { return false, fmt.Errorf("task should only hold Discrete type") } @@ -36,11 +36,11 @@ func HasEnough(nodeRes []*api.GenericResource, taskRes *api.GenericResource) (bo } switch nr := nrs[0].Resource.(type) { - case *api.GenericResource_Discrete: - if t.Value > nr.Discrete.Value { + case *api.GenericResource_DiscreteResourceSpec: + if t.Value > nr.DiscreteResourceSpec.Value { return false, nil } - case *api.GenericResource_Str: + case *api.GenericResource_NamedResourceSpec: if t.Value > int64(len(nrs)) { return false, nil } @@ -57,22 +57,22 @@ func HasResource(res *api.GenericResource, resources []*api.GenericResource) boo } switch rtype := r.Resource.(type) { - case *api.GenericResource_Discrete: - if res.GetDiscrete() == nil { + case *api.GenericResource_DiscreteResourceSpec: + if res.GetDiscreteResourceSpec() == nil { return false } - if res.GetDiscrete().Value < rtype.Discrete.Value { + if res.GetDiscreteResourceSpec().Value < rtype.DiscreteResourceSpec.Value { return false } return true - case *api.GenericResource_Str: - if res.GetStr() == nil { + case *api.GenericResource_NamedResourceSpec: + if res.GetNamedResourceSpec() == nil { return false } - if res.GetStr().Value != rtype.Str.Value { + if res.GetNamedResourceSpec().Value != rtype.NamedResourceSpec.Value { continue } diff --git a/vendor/github.com/docker/swarmkit/api/types.pb.go b/vendor/github.com/docker/swarmkit/api/types.pb.go index 2befc03577..d41e761304 100644 --- a/vendor/github.com/docker/swarmkit/api/types.pb.go +++ b/vendor/github.com/docker/swarmkit/api/types.pb.go @@ -23,8 +23,8 @@ Version IndexEntry Annotations - GenericString - GenericDiscrete + NamedGenericResource + DiscreteGenericResource GenericResource Resources ResourceRequirements @@ -781,28 +781,38 @@ func (m *Annotations) Reset() { *m = Annotations{} } func (*Annotations) ProtoMessage() {} func (*Annotations) Descriptor() ([]byte, []int) { return fileDescriptorTypes, []int{2} } -type GenericString struct { +// NamedGenericResource represents a "user defined" resource which is defined +// as a string. +// "Kind" is used to describe the Kind of a resource (e.g: "GPU", "FPGA", "SSD", ...) +// Value is used to identify the resource (GPU="UUID-1", FPGA="/dev/sdb5", ...) +type NamedGenericResource struct { Kind string `protobuf:"bytes,1,opt,name=kind,proto3" json:"kind,omitempty"` Value string `protobuf:"bytes,2,opt,name=value,proto3" json:"value,omitempty"` } -func (m *GenericString) Reset() { *m = GenericString{} } -func (*GenericString) ProtoMessage() {} -func (*GenericString) Descriptor() ([]byte, []int) { return fileDescriptorTypes, []int{3} } +func (m *NamedGenericResource) Reset() { *m = NamedGenericResource{} } +func (*NamedGenericResource) ProtoMessage() {} +func (*NamedGenericResource) Descriptor() ([]byte, []int) { return fileDescriptorTypes, []int{3} } -type GenericDiscrete struct { +// DiscreteGenericResource represents a "user defined" resource which is defined +// as an integer +// "Kind" is used to describe the Kind of a resource (e.g: "GPU", "FPGA", "SSD", ...) +// Value is used to count the resource (SSD=5, HDD=3, ...) +type DiscreteGenericResource struct { Kind string `protobuf:"bytes,1,opt,name=kind,proto3" json:"kind,omitempty"` Value int64 `protobuf:"varint,2,opt,name=value,proto3" json:"value,omitempty"` } -func (m *GenericDiscrete) Reset() { *m = GenericDiscrete{} } -func (*GenericDiscrete) ProtoMessage() {} -func (*GenericDiscrete) Descriptor() ([]byte, []int) { return fileDescriptorTypes, []int{4} } +func (m *DiscreteGenericResource) Reset() { *m = DiscreteGenericResource{} } +func (*DiscreteGenericResource) ProtoMessage() {} +func (*DiscreteGenericResource) Descriptor() ([]byte, []int) { return fileDescriptorTypes, []int{4} } +// GenericResource represents a "user defined" resource which can +// be either an integer (e.g: SSD=3) or a string (e.g: SSD=sda1) type GenericResource struct { // Types that are valid to be assigned to Resource: - // *GenericResource_Str - // *GenericResource_Discrete + // *GenericResource_NamedResourceSpec + // *GenericResource_DiscreteResourceSpec Resource isGenericResource_Resource `protobuf_oneof:"resource"` } @@ -816,15 +826,15 @@ type isGenericResource_Resource interface { Size() int } -type GenericResource_Str struct { - Str *GenericString `protobuf:"bytes,1,opt,name=str,oneof"` +type GenericResource_NamedResourceSpec struct { + NamedResourceSpec *NamedGenericResource `protobuf:"bytes,1,opt,name=named_resource_spec,json=namedResourceSpec,oneof"` } -type GenericResource_Discrete struct { - Discrete *GenericDiscrete `protobuf:"bytes,2,opt,name=discrete,oneof"` +type GenericResource_DiscreteResourceSpec struct { + DiscreteResourceSpec *DiscreteGenericResource `protobuf:"bytes,2,opt,name=discrete_resource_spec,json=discreteResourceSpec,oneof"` } -func (*GenericResource_Str) isGenericResource_Resource() {} -func (*GenericResource_Discrete) isGenericResource_Resource() {} +func (*GenericResource_NamedResourceSpec) isGenericResource_Resource() {} +func (*GenericResource_DiscreteResourceSpec) isGenericResource_Resource() {} func (m *GenericResource) GetResource() isGenericResource_Resource { if m != nil { @@ -833,16 +843,16 @@ func (m *GenericResource) GetResource() isGenericResource_Resource { return nil } -func (m *GenericResource) GetStr() *GenericString { - if x, ok := m.GetResource().(*GenericResource_Str); ok { - return x.Str +func (m *GenericResource) GetNamedResourceSpec() *NamedGenericResource { + if x, ok := m.GetResource().(*GenericResource_NamedResourceSpec); ok { + return x.NamedResourceSpec } return nil } -func (m *GenericResource) GetDiscrete() *GenericDiscrete { - if x, ok := m.GetResource().(*GenericResource_Discrete); ok { - return x.Discrete +func (m *GenericResource) GetDiscreteResourceSpec() *DiscreteGenericResource { + if x, ok := m.GetResource().(*GenericResource_DiscreteResourceSpec); ok { + return x.DiscreteResourceSpec } return nil } @@ -850,8 +860,8 @@ func (m *GenericResource) GetDiscrete() *GenericDiscrete { // XXX_OneofFuncs is for the internal use of the proto package. func (*GenericResource) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) { return _GenericResource_OneofMarshaler, _GenericResource_OneofUnmarshaler, _GenericResource_OneofSizer, []interface{}{ - (*GenericResource_Str)(nil), - (*GenericResource_Discrete)(nil), + (*GenericResource_NamedResourceSpec)(nil), + (*GenericResource_DiscreteResourceSpec)(nil), } } @@ -859,14 +869,14 @@ func _GenericResource_OneofMarshaler(msg proto.Message, b *proto.Buffer) error { m := msg.(*GenericResource) // resource switch x := m.Resource.(type) { - case *GenericResource_Str: + case *GenericResource_NamedResourceSpec: _ = b.EncodeVarint(1<<3 | proto.WireBytes) - if err := b.EncodeMessage(x.Str); err != nil { + if err := b.EncodeMessage(x.NamedResourceSpec); err != nil { return err } - case *GenericResource_Discrete: + case *GenericResource_DiscreteResourceSpec: _ = b.EncodeVarint(2<<3 | proto.WireBytes) - if err := b.EncodeMessage(x.Discrete); err != nil { + if err := b.EncodeMessage(x.DiscreteResourceSpec); err != nil { return err } case nil: @@ -879,21 +889,21 @@ func _GenericResource_OneofMarshaler(msg proto.Message, b *proto.Buffer) error { func _GenericResource_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) { m := msg.(*GenericResource) switch tag { - case 1: // resource.str + case 1: // resource.named_resource_spec if wire != proto.WireBytes { return true, proto.ErrInternalBadWireType } - msg := new(GenericString) + msg := new(NamedGenericResource) err := b.DecodeMessage(msg) - m.Resource = &GenericResource_Str{msg} + m.Resource = &GenericResource_NamedResourceSpec{msg} return true, err - case 2: // resource.discrete + case 2: // resource.discrete_resource_spec if wire != proto.WireBytes { return true, proto.ErrInternalBadWireType } - msg := new(GenericDiscrete) + msg := new(DiscreteGenericResource) err := b.DecodeMessage(msg) - m.Resource = &GenericResource_Discrete{msg} + m.Resource = &GenericResource_DiscreteResourceSpec{msg} return true, err default: return false, nil @@ -904,13 +914,13 @@ func _GenericResource_OneofSizer(msg proto.Message) (n int) { m := msg.(*GenericResource) // resource switch x := m.Resource.(type) { - case *GenericResource_Str: - s := proto.Size(x.Str) + case *GenericResource_NamedResourceSpec: + s := proto.Size(x.NamedResourceSpec) n += proto.SizeVarint(1<<3 | proto.WireBytes) n += proto.SizeVarint(uint64(s)) n += s - case *GenericResource_Discrete: - s := proto.Size(x.Discrete) + case *GenericResource_DiscreteResourceSpec: + s := proto.Size(x.DiscreteResourceSpec) n += proto.SizeVarint(2<<3 | proto.WireBytes) n += proto.SizeVarint(uint64(s)) n += s @@ -2242,8 +2252,8 @@ func init() { proto.RegisterType((*Version)(nil), "docker.swarmkit.v1.Version") proto.RegisterType((*IndexEntry)(nil), "docker.swarmkit.v1.IndexEntry") proto.RegisterType((*Annotations)(nil), "docker.swarmkit.v1.Annotations") - proto.RegisterType((*GenericString)(nil), "docker.swarmkit.v1.GenericString") - proto.RegisterType((*GenericDiscrete)(nil), "docker.swarmkit.v1.GenericDiscrete") + proto.RegisterType((*NamedGenericResource)(nil), "docker.swarmkit.v1.NamedGenericResource") + proto.RegisterType((*DiscreteGenericResource)(nil), "docker.swarmkit.v1.DiscreteGenericResource") proto.RegisterType((*GenericResource)(nil), "docker.swarmkit.v1.GenericResource") proto.RegisterType((*Resources)(nil), "docker.swarmkit.v1.Resources") proto.RegisterType((*ResourceRequirements)(nil), "docker.swarmkit.v1.ResourceRequirements") @@ -2379,33 +2389,33 @@ func (m *Annotations) CopyFrom(src interface{}) { } -func (m *GenericString) Copy() *GenericString { +func (m *NamedGenericResource) Copy() *NamedGenericResource { if m == nil { return nil } - o := &GenericString{} + o := &NamedGenericResource{} o.CopyFrom(m) return o } -func (m *GenericString) CopyFrom(src interface{}) { +func (m *NamedGenericResource) CopyFrom(src interface{}) { - o := src.(*GenericString) + o := src.(*NamedGenericResource) *m = *o } -func (m *GenericDiscrete) Copy() *GenericDiscrete { +func (m *DiscreteGenericResource) Copy() *DiscreteGenericResource { if m == nil { return nil } - o := &GenericDiscrete{} + o := &DiscreteGenericResource{} o.CopyFrom(m) return o } -func (m *GenericDiscrete) CopyFrom(src interface{}) { +func (m *DiscreteGenericResource) CopyFrom(src interface{}) { - o := src.(*GenericDiscrete) + o := src.(*DiscreteGenericResource) *m = *o } @@ -2424,17 +2434,17 @@ func (m *GenericResource) CopyFrom(src interface{}) { *m = *o if o.Resource != nil { switch o.Resource.(type) { - case *GenericResource_Str: - v := GenericResource_Str{ - Str: &GenericString{}, + case *GenericResource_NamedResourceSpec: + v := GenericResource_NamedResourceSpec{ + NamedResourceSpec: &NamedGenericResource{}, } - github_com_docker_swarmkit_api_deepcopy.Copy(v.Str, o.GetStr()) + github_com_docker_swarmkit_api_deepcopy.Copy(v.NamedResourceSpec, o.GetNamedResourceSpec()) m.Resource = &v - case *GenericResource_Discrete: - v := GenericResource_Discrete{ - Discrete: &GenericDiscrete{}, + case *GenericResource_DiscreteResourceSpec: + v := GenericResource_DiscreteResourceSpec{ + DiscreteResourceSpec: &DiscreteGenericResource{}, } - github_com_docker_swarmkit_api_deepcopy.Copy(v.Discrete, o.GetDiscrete()) + github_com_docker_swarmkit_api_deepcopy.Copy(v.DiscreteResourceSpec, o.GetDiscreteResourceSpec()) m.Resource = &v } } @@ -3762,7 +3772,7 @@ func (m *Annotations) MarshalTo(dAtA []byte) (int, error) { return i, nil } -func (m *GenericString) Marshal() (dAtA []byte, err error) { +func (m *NamedGenericResource) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) n, err := m.MarshalTo(dAtA) @@ -3772,7 +3782,7 @@ func (m *GenericString) Marshal() (dAtA []byte, err error) { return dAtA[:n], nil } -func (m *GenericString) MarshalTo(dAtA []byte) (int, error) { +func (m *NamedGenericResource) MarshalTo(dAtA []byte) (int, error) { var i int _ = i var l int @@ -3792,7 +3802,7 @@ func (m *GenericString) MarshalTo(dAtA []byte) (int, error) { return i, nil } -func (m *GenericDiscrete) Marshal() (dAtA []byte, err error) { +func (m *DiscreteGenericResource) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) n, err := m.MarshalTo(dAtA) @@ -3802,7 +3812,7 @@ func (m *GenericDiscrete) Marshal() (dAtA []byte, err error) { return dAtA[:n], nil } -func (m *GenericDiscrete) MarshalTo(dAtA []byte) (int, error) { +func (m *DiscreteGenericResource) MarshalTo(dAtA []byte) (int, error) { var i int _ = i var l int @@ -3846,13 +3856,13 @@ func (m *GenericResource) MarshalTo(dAtA []byte) (int, error) { return i, nil } -func (m *GenericResource_Str) MarshalTo(dAtA []byte) (int, error) { +func (m *GenericResource_NamedResourceSpec) MarshalTo(dAtA []byte) (int, error) { i := 0 - if m.Str != nil { + if m.NamedResourceSpec != nil { dAtA[i] = 0xa i++ - i = encodeVarintTypes(dAtA, i, uint64(m.Str.Size())) - n2, err := m.Str.MarshalTo(dAtA[i:]) + i = encodeVarintTypes(dAtA, i, uint64(m.NamedResourceSpec.Size())) + n2, err := m.NamedResourceSpec.MarshalTo(dAtA[i:]) if err != nil { return 0, err } @@ -3860,13 +3870,13 @@ func (m *GenericResource_Str) MarshalTo(dAtA []byte) (int, error) { } return i, nil } -func (m *GenericResource_Discrete) MarshalTo(dAtA []byte) (int, error) { +func (m *GenericResource_DiscreteResourceSpec) MarshalTo(dAtA []byte) (int, error) { i := 0 - if m.Discrete != nil { + if m.DiscreteResourceSpec != nil { dAtA[i] = 0x12 i++ - i = encodeVarintTypes(dAtA, i, uint64(m.Discrete.Size())) - n3, err := m.Discrete.MarshalTo(dAtA[i:]) + i = encodeVarintTypes(dAtA, i, uint64(m.DiscreteResourceSpec.Size())) + n3, err := m.DiscreteResourceSpec.MarshalTo(dAtA[i:]) if err != nil { return 0, err } @@ -6303,7 +6313,7 @@ func (m *Annotations) Size() (n int) { return n } -func (m *GenericString) Size() (n int) { +func (m *NamedGenericResource) Size() (n int) { var l int _ = l l = len(m.Kind) @@ -6317,7 +6327,7 @@ func (m *GenericString) Size() (n int) { return n } -func (m *GenericDiscrete) Size() (n int) { +func (m *DiscreteGenericResource) Size() (n int) { var l int _ = l l = len(m.Kind) @@ -6339,20 +6349,20 @@ func (m *GenericResource) Size() (n int) { return n } -func (m *GenericResource_Str) Size() (n int) { +func (m *GenericResource_NamedResourceSpec) Size() (n int) { var l int _ = l - if m.Str != nil { - l = m.Str.Size() + if m.NamedResourceSpec != nil { + l = m.NamedResourceSpec.Size() n += 1 + l + sovTypes(uint64(l)) } return n } -func (m *GenericResource_Discrete) Size() (n int) { +func (m *GenericResource_DiscreteResourceSpec) Size() (n int) { var l int _ = l - if m.Discrete != nil { - l = m.Discrete.Size() + if m.DiscreteResourceSpec != nil { + l = m.DiscreteResourceSpec.Size() n += 1 + l + sovTypes(uint64(l)) } return n @@ -7458,22 +7468,22 @@ func (this *Annotations) String() string { }, "") return s } -func (this *GenericString) String() string { +func (this *NamedGenericResource) String() string { if this == nil { return "nil" } - s := strings.Join([]string{`&GenericString{`, + s := strings.Join([]string{`&NamedGenericResource{`, `Kind:` + fmt.Sprintf("%v", this.Kind) + `,`, `Value:` + fmt.Sprintf("%v", this.Value) + `,`, `}`, }, "") return s } -func (this *GenericDiscrete) String() string { +func (this *DiscreteGenericResource) String() string { if this == nil { return "nil" } - s := strings.Join([]string{`&GenericDiscrete{`, + s := strings.Join([]string{`&DiscreteGenericResource{`, `Kind:` + fmt.Sprintf("%v", this.Kind) + `,`, `Value:` + fmt.Sprintf("%v", this.Value) + `,`, `}`, @@ -7490,22 +7500,22 @@ func (this *GenericResource) String() string { }, "") return s } -func (this *GenericResource_Str) String() string { +func (this *GenericResource_NamedResourceSpec) String() string { if this == nil { return "nil" } - s := strings.Join([]string{`&GenericResource_Str{`, - `Str:` + strings.Replace(fmt.Sprintf("%v", this.Str), "GenericString", "GenericString", 1) + `,`, + s := strings.Join([]string{`&GenericResource_NamedResourceSpec{`, + `NamedResourceSpec:` + strings.Replace(fmt.Sprintf("%v", this.NamedResourceSpec), "NamedGenericResource", "NamedGenericResource", 1) + `,`, `}`, }, "") return s } -func (this *GenericResource_Discrete) String() string { +func (this *GenericResource_DiscreteResourceSpec) String() string { if this == nil { return "nil" } - s := strings.Join([]string{`&GenericResource_Discrete{`, - `Discrete:` + strings.Replace(fmt.Sprintf("%v", this.Discrete), "GenericDiscrete", "GenericDiscrete", 1) + `,`, + s := strings.Join([]string{`&GenericResource_DiscreteResourceSpec{`, + `DiscreteResourceSpec:` + strings.Replace(fmt.Sprintf("%v", this.DiscreteResourceSpec), "DiscreteGenericResource", "DiscreteGenericResource", 1) + `,`, `}`, }, "") return s @@ -8713,7 +8723,7 @@ func (m *Annotations) Unmarshal(dAtA []byte) error { } return nil } -func (m *GenericString) Unmarshal(dAtA []byte) error { +func (m *NamedGenericResource) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -8736,10 +8746,10 @@ func (m *GenericString) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: GenericString: wiretype end group for non-group") + return fmt.Errorf("proto: NamedGenericResource: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: GenericString: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: NamedGenericResource: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: @@ -8821,7 +8831,7 @@ func (m *GenericString) Unmarshal(dAtA []byte) error { } return nil } -func (m *GenericDiscrete) Unmarshal(dAtA []byte) error { +func (m *DiscreteGenericResource) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -8844,10 +8854,10 @@ func (m *GenericDiscrete) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: GenericDiscrete: wiretype end group for non-group") + return fmt.Errorf("proto: DiscreteGenericResource: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: GenericDiscrete: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: DiscreteGenericResource: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: @@ -8950,7 +8960,7 @@ func (m *GenericResource) Unmarshal(dAtA []byte) error { switch fieldNum { case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Str", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field NamedResourceSpec", wireType) } var msglen int for shift := uint(0); ; shift += 7 { @@ -8974,15 +8984,15 @@ func (m *GenericResource) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - v := &GenericString{} + v := &NamedGenericResource{} if err := v.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { return err } - m.Resource = &GenericResource_Str{v} + m.Resource = &GenericResource_NamedResourceSpec{v} iNdEx = postIndex case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Discrete", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field DiscreteResourceSpec", wireType) } var msglen int for shift := uint(0); ; shift += 7 { @@ -9006,11 +9016,11 @@ func (m *GenericResource) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - v := &GenericDiscrete{} + v := &DiscreteGenericResource{} if err := v.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { return err } - m.Resource = &GenericResource_Discrete{v} + m.Resource = &GenericResource_DiscreteResourceSpec{v} iNdEx = postIndex default: iNdEx = preIndex @@ -17051,306 +17061,307 @@ var ( func init() { proto.RegisterFile("types.proto", fileDescriptorTypes) } var fileDescriptorTypes = []byte{ - // 4808 bytes of a gzipped FileDescriptorProto + // 4822 bytes of a gzipped FileDescriptorProto 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xac, 0x7a, 0x4d, 0x6c, 0x24, 0x49, - 0x56, 0xbf, 0xeb, 0xd3, 0x55, 0xaf, 0xca, 0x76, 0x76, 0xb4, 0xb7, 0xd7, 0x5d, 0xd3, 0x63, 0xd7, - 0xe4, 0x4c, 0xef, 0x7c, 0xec, 0xfc, 0x6b, 0xba, 0xdd, 0x33, 0xa3, 0xee, 0xe9, 0xff, 0x7c, 0xd4, - 0x97, 0xdb, 0xb5, 0x6d, 0x57, 0x95, 0xa2, 0xca, 0xdd, 0x3b, 0x07, 0x48, 0xa5, 0x33, 0xc3, 0xe5, - 0x1c, 0x67, 0x65, 0x14, 0x99, 0x59, 0x76, 0x17, 0x0b, 0xa2, 0xc5, 0x01, 0x90, 0x4f, 0x70, 0x62, - 0x25, 0x64, 0x2e, 0x70, 0x42, 0x48, 0x1c, 0x40, 0x42, 0x70, 0x61, 0x90, 0x38, 0xcc, 0x8d, 0x05, - 0x24, 0xb4, 0x02, 0xc9, 0x30, 0x3e, 0x70, 0x43, 0x70, 0x59, 0x71, 0x01, 0x09, 0xc5, 0x47, 0x66, - 0x65, 0xb9, 0xd3, 0x76, 0x0f, 0xb3, 0x17, 0x3b, 0xe3, 0xbd, 0xdf, 0x7b, 0xf1, 0xe2, 0x45, 0xc4, + 0x56, 0xbf, 0xeb, 0xd3, 0x55, 0xaf, 0xca, 0x76, 0x3a, 0xda, 0xdb, 0xe3, 0xae, 0xed, 0xb1, 0x6b, + 0x72, 0xa6, 0x77, 0x66, 0x67, 0xe7, 0x5f, 0xd3, 0x1f, 0xbb, 0xab, 0x9e, 0x99, 0xff, 0x7c, 0xd4, + 0x97, 0xdb, 0xb5, 0x6d, 0x57, 0x95, 0xa2, 0xca, 0xdd, 0x3b, 0x48, 0x90, 0x4a, 0x67, 0x86, 0xcb, + 0x39, 0xce, 0xca, 0x28, 0x32, 0xb3, 0xec, 0x2e, 0x16, 0x44, 0x8b, 0x03, 0x20, 0x9f, 0xe0, 0xb6, + 0x12, 0x32, 0x17, 0x38, 0x21, 0x24, 0x0e, 0x20, 0x21, 0xb8, 0x30, 0x48, 0x1c, 0xe6, 0xc6, 0x02, + 0x12, 0x5a, 0x81, 0x64, 0x18, 0x1f, 0xb8, 0x21, 0xb8, 0xac, 0xb8, 0x80, 0x84, 0xe2, 0x23, 0xb3, + 0xb2, 0xaa, 0xd3, 0x76, 0x0f, 0xb3, 0x17, 0x3b, 0xe3, 0xbd, 0xdf, 0x7b, 0xf1, 0xe2, 0x45, 0xc4, 0x8b, 0xf7, 0x22, 0x0a, 0x0a, 0xfe, 0x64, 0x44, 0xbc, 0xca, 0xc8, 0xa5, 0x3e, 0x45, 0xc8, 0xa4, - 0xc6, 0x01, 0x71, 0x2b, 0xde, 0x91, 0xee, 0x0e, 0x0f, 0x2c, 0xbf, 0x72, 0x78, 0xb7, 0xb4, 0x36, - 0xa0, 0x74, 0x60, 0x93, 0xf7, 0x38, 0x62, 0x77, 0xbc, 0xf7, 0x9e, 0x6f, 0x0d, 0x89, 0xe7, 0xeb, - 0xc3, 0x91, 0x10, 0x2a, 0xad, 0x9e, 0x07, 0x98, 0x63, 0x57, 0xf7, 0x2d, 0xea, 0x48, 0xfe, 0xf2, - 0x80, 0x0e, 0x28, 0xff, 0x7c, 0x8f, 0x7d, 0x09, 0xaa, 0xba, 0x06, 0xf3, 0x4f, 0x88, 0xeb, 0x59, - 0xd4, 0x41, 0xcb, 0x90, 0xb1, 0x1c, 0x93, 0x3c, 0x5b, 0x49, 0x94, 0x13, 0x6f, 0xa5, 0xb1, 0x68, - 0xa8, 0x77, 0x00, 0x5a, 0xec, 0xa3, 0xe9, 0xf8, 0xee, 0x04, 0x29, 0x90, 0x3a, 0x20, 0x13, 0x8e, - 0xc8, 0x63, 0xf6, 0xc9, 0x28, 0x87, 0xba, 0xbd, 0x92, 0x14, 0x94, 0x43, 0xdd, 0x56, 0xbf, 0x4e, - 0x40, 0xa1, 0xea, 0x38, 0xd4, 0xe7, 0xbd, 0x7b, 0x08, 0x41, 0xda, 0xd1, 0x87, 0x44, 0x0a, 0xf1, - 0x6f, 0x54, 0x87, 0xac, 0xad, 0xef, 0x12, 0xdb, 0x5b, 0x49, 0x96, 0x53, 0x6f, 0x15, 0xd6, 0xbf, - 0x5f, 0x79, 0x71, 0xc8, 0x95, 0x88, 0x92, 0xca, 0x16, 0x47, 0x73, 0x23, 0xb0, 0x14, 0x45, 0x9f, - 0xc0, 0xbc, 0xe5, 0x98, 0x96, 0x41, 0xbc, 0x95, 0x34, 0xd7, 0xb2, 0x1a, 0xa7, 0x65, 0x6a, 0x7d, - 0x2d, 0xfd, 0xd5, 0xe9, 0xda, 0x1c, 0x0e, 0x84, 0x4a, 0x0f, 0xa0, 0x10, 0x51, 0x1b, 0x33, 0xb6, - 0x65, 0xc8, 0x1c, 0xea, 0xf6, 0x98, 0xc8, 0xd1, 0x89, 0xc6, 0x47, 0xc9, 0xfb, 0x09, 0xf5, 0x01, - 0x2c, 0x3c, 0x22, 0x0e, 0x71, 0x2d, 0xa3, 0xe7, 0xbb, 0x96, 0x33, 0x60, 0x83, 0x3c, 0xb0, 0x1c, - 0x33, 0x18, 0x24, 0xfb, 0x8e, 0x17, 0x57, 0x1f, 0xc2, 0x92, 0x14, 0x6d, 0x58, 0x9e, 0xe1, 0x12, - 0x9f, 0x5c, 0x2d, 0x9c, 0x0a, 0x84, 0x7f, 0x37, 0x11, 0x4a, 0x63, 0xe2, 0xd1, 0xb1, 0x6b, 0x10, - 0xf4, 0x01, 0xa4, 0x3c, 0xdf, 0xe5, 0xc2, 0x85, 0xf5, 0xd7, 0xe2, 0x5c, 0x30, 0x63, 0xea, 0xe6, - 0x1c, 0x66, 0x78, 0x54, 0x85, 0x9c, 0x29, 0x0d, 0xe0, 0x7d, 0x14, 0xd6, 0x5f, 0xbf, 0x44, 0x36, - 0xb0, 0x75, 0x73, 0x0e, 0x87, 0x62, 0x35, 0x80, 0x9c, 0x2b, 0xad, 0x50, 0x7f, 0x9c, 0x80, 0x7c, - 0x60, 0x92, 0x87, 0xde, 0x86, 0xbc, 0xa3, 0x3b, 0x54, 0x33, 0x46, 0x63, 0x8f, 0x5b, 0x96, 0xaa, - 0x15, 0xcf, 0x4e, 0xd7, 0x72, 0x6d, 0xdd, 0xa1, 0xf5, 0xee, 0x8e, 0x87, 0x73, 0x8c, 0x5d, 0x1f, - 0x8d, 0x3d, 0xf4, 0x1a, 0x14, 0x87, 0x64, 0x48, 0xdd, 0x89, 0xb6, 0x3b, 0xf1, 0x89, 0x27, 0xc7, - 0x5b, 0x10, 0xb4, 0x1a, 0x23, 0xa1, 0x8f, 0x61, 0x7e, 0x20, 0xcc, 0x58, 0x49, 0xf1, 0x89, 0xbe, - 0xcc, 0xd2, 0xc0, 0x08, 0x1c, 0xc8, 0xa8, 0xbf, 0x9d, 0x80, 0xe5, 0x90, 0x4a, 0x7e, 0x69, 0x6c, - 0xb9, 0x64, 0x48, 0x1c, 0xdf, 0x43, 0x1f, 0x40, 0xd6, 0xb6, 0x86, 0x96, 0xef, 0x49, 0xe7, 0xbd, - 0x1a, 0xa7, 0x36, 0x1c, 0x14, 0x96, 0x60, 0x54, 0x85, 0xa2, 0x4b, 0x3c, 0xe2, 0x1e, 0x8a, 0xb5, - 0x29, 0xbd, 0x77, 0x85, 0xf0, 0x8c, 0x88, 0xba, 0x01, 0xb9, 0xae, 0xad, 0xfb, 0x7b, 0xd4, 0x1d, - 0x22, 0x15, 0x8a, 0xba, 0x6b, 0xec, 0x5b, 0x3e, 0x31, 0xfc, 0xb1, 0x1b, 0xec, 0x93, 0x19, 0x1a, - 0xba, 0x01, 0x49, 0x2a, 0x3a, 0xca, 0xd7, 0xb2, 0x67, 0xa7, 0x6b, 0xc9, 0x4e, 0x0f, 0x27, 0xa9, - 0xa7, 0x3e, 0x84, 0x6b, 0x5d, 0x7b, 0x3c, 0xb0, 0x9c, 0x06, 0xf1, 0x0c, 0xd7, 0x1a, 0x31, 0xed, - 0x6c, 0x39, 0xb1, 0x68, 0x12, 0x2c, 0x27, 0xf6, 0x1d, 0x6e, 0xc2, 0xe4, 0x74, 0x13, 0xaa, 0xbf, - 0x99, 0x84, 0x6b, 0x4d, 0x67, 0x60, 0x39, 0x24, 0x2a, 0x7d, 0x1b, 0x16, 0x09, 0x27, 0x6a, 0x87, - 0x22, 0x30, 0x48, 0x3d, 0x0b, 0x82, 0x1a, 0x44, 0x8b, 0xd6, 0xb9, 0x1d, 0x7c, 0x37, 0x6e, 0xf8, - 0x2f, 0x68, 0x8f, 0xdd, 0xc7, 0x4d, 0x98, 0x1f, 0xf1, 0x41, 0x78, 0x72, 0x7a, 0x6f, 0xc7, 0xe9, - 0x7a, 0x61, 0x9c, 0xc1, 0x76, 0x96, 0xb2, 0xdf, 0x66, 0x3b, 0xff, 0x71, 0x12, 0x96, 0xda, 0xd4, - 0x9c, 0xf1, 0x43, 0x09, 0x72, 0xfb, 0xd4, 0xf3, 0x23, 0xa1, 0x2b, 0x6c, 0xa3, 0xfb, 0x90, 0x1b, - 0xc9, 0xe9, 0x93, 0xb3, 0x7f, 0x2b, 0xde, 0x64, 0x81, 0xc1, 0x21, 0x1a, 0x3d, 0x84, 0x7c, 0xb0, - 0x65, 0xd8, 0x68, 0x5f, 0x62, 0xe1, 0x4c, 0xf1, 0xe8, 0x63, 0xc8, 0x8a, 0x49, 0x58, 0x49, 0x73, - 0xc9, 0xdb, 0x2f, 0xe5, 0x73, 0x2c, 0x85, 0xd0, 0x23, 0xc8, 0xf9, 0xb6, 0xa7, 0x59, 0xce, 0x1e, - 0x5d, 0xc9, 0x70, 0x05, 0x6b, 0x71, 0x0a, 0x98, 0x23, 0xfa, 0x5b, 0xbd, 0x96, 0xb3, 0x47, 0x6b, - 0x85, 0xb3, 0xd3, 0xb5, 0x79, 0xd9, 0xc0, 0xf3, 0xbe, 0xed, 0xb1, 0x0f, 0xf5, 0x77, 0x12, 0x50, - 0x88, 0xa0, 0xd0, 0xab, 0x00, 0xbe, 0x3b, 0xf6, 0x7c, 0xcd, 0xa5, 0xd4, 0xe7, 0xce, 0x2a, 0xe2, - 0x3c, 0xa7, 0x60, 0x4a, 0x7d, 0x54, 0x81, 0xeb, 0x06, 0x71, 0x7d, 0xcd, 0xf2, 0xbc, 0x31, 0x71, - 0x35, 0x6f, 0xbc, 0xfb, 0x05, 0x31, 0x7c, 0xee, 0xb8, 0x22, 0xbe, 0xc6, 0x58, 0x2d, 0xce, 0xe9, - 0x09, 0x06, 0xba, 0x07, 0x37, 0xa2, 0xf8, 0xd1, 0x78, 0xd7, 0xb6, 0x0c, 0x8d, 0x4d, 0x66, 0x8a, - 0x8b, 0x5c, 0x9f, 0x8a, 0x74, 0x39, 0xef, 0x31, 0x99, 0xa8, 0x3f, 0x4d, 0x80, 0x82, 0xf5, 0x3d, - 0x7f, 0x9b, 0x0c, 0x77, 0x89, 0xdb, 0xf3, 0x75, 0x7f, 0xec, 0xa1, 0x1b, 0x90, 0xb5, 0x89, 0x6e, - 0x12, 0x11, 0x1d, 0x73, 0x58, 0xb6, 0xd0, 0x0e, 0xdb, 0xc1, 0xba, 0xb1, 0xaf, 0xef, 0x5a, 0xb6, - 0xe5, 0x4f, 0xb8, 0x29, 0x8b, 0xf1, 0x4b, 0xf8, 0xbc, 0xce, 0x0a, 0x8e, 0x08, 0xe2, 0x19, 0x35, - 0x68, 0x05, 0xe6, 0x87, 0xc4, 0xf3, 0xf4, 0x01, 0xe1, 0x96, 0xe6, 0x71, 0xd0, 0x54, 0x1f, 0x42, - 0x31, 0x2a, 0x87, 0x0a, 0x30, 0xbf, 0xd3, 0x7e, 0xdc, 0xee, 0x3c, 0x6d, 0x2b, 0x73, 0x68, 0x09, - 0x0a, 0x3b, 0x6d, 0xdc, 0xac, 0xd6, 0x37, 0xab, 0xb5, 0xad, 0xa6, 0x92, 0x40, 0x0b, 0x90, 0x9f, - 0x36, 0x93, 0xea, 0x9f, 0x26, 0x00, 0x98, 0xbb, 0xe5, 0xa0, 0x3e, 0x82, 0x8c, 0xe7, 0xeb, 0xbe, - 0x58, 0x95, 0x8b, 0xeb, 0x6f, 0x5c, 0x34, 0x87, 0xd2, 0x5e, 0xf6, 0x8f, 0x60, 0x21, 0x12, 0xb5, - 0x30, 0x39, 0x63, 0x21, 0x0b, 0x10, 0xba, 0x69, 0xba, 0xd2, 0x70, 0xfe, 0xad, 0x3e, 0x84, 0x0c, - 0x97, 0x9e, 0x35, 0x37, 0x07, 0xe9, 0x06, 0xfb, 0x4a, 0xa0, 0x3c, 0x64, 0x70, 0xb3, 0xda, 0xf8, - 0x5c, 0x49, 0x22, 0x05, 0x8a, 0x8d, 0x56, 0xaf, 0xde, 0x69, 0xb7, 0x9b, 0xf5, 0x7e, 0xb3, 0xa1, - 0xa4, 0xd4, 0xdb, 0x90, 0x69, 0x0d, 0x99, 0xe6, 0x5b, 0x6c, 0xc9, 0xef, 0x11, 0x97, 0x38, 0x46, - 0xb0, 0x93, 0xa6, 0x04, 0xf5, 0x27, 0x79, 0xc8, 0x6c, 0xd3, 0xb1, 0xe3, 0xa3, 0xf5, 0x48, 0xd8, - 0x5a, 0x8c, 0x3f, 0xcb, 0x39, 0xb0, 0xd2, 0x9f, 0x8c, 0x88, 0x0c, 0x6b, 0x37, 0x20, 0x2b, 0x36, - 0x87, 0x1c, 0x8e, 0x6c, 0x31, 0xba, 0xaf, 0xbb, 0x03, 0xe2, 0xcb, 0xf1, 0xc8, 0x16, 0x7a, 0x8b, - 0x9d, 0x58, 0xba, 0x49, 0x1d, 0x7b, 0xc2, 0xf7, 0x50, 0x4e, 0x1c, 0x4b, 0x98, 0xe8, 0x66, 0xc7, - 0xb1, 0x27, 0x38, 0xe4, 0xa2, 0x4d, 0x28, 0xee, 0x5a, 0x8e, 0xa9, 0xd1, 0x91, 0x08, 0xf2, 0x99, - 0x8b, 0x77, 0x9c, 0xb0, 0xaa, 0x66, 0x39, 0x66, 0x47, 0x80, 0x71, 0x61, 0x77, 0xda, 0x40, 0x6d, - 0x58, 0x3c, 0xa4, 0xf6, 0x78, 0x48, 0x42, 0x5d, 0x59, 0xae, 0xeb, 0xcd, 0x8b, 0x75, 0x3d, 0xe1, - 0xf8, 0x40, 0xdb, 0xc2, 0x61, 0xb4, 0x89, 0x1e, 0xc3, 0x82, 0x3f, 0x1c, 0xed, 0x79, 0xa1, 0xba, - 0x79, 0xae, 0xee, 0x7b, 0x97, 0x38, 0x8c, 0xc1, 0x03, 0x6d, 0x45, 0x3f, 0xd2, 0x2a, 0xfd, 0x7a, - 0x0a, 0x0a, 0x11, 0xcb, 0x51, 0x0f, 0x0a, 0x23, 0x97, 0x8e, 0xf4, 0x01, 0x3f, 0xa8, 0xe4, 0x5c, - 0xdc, 0x7d, 0xa9, 0x51, 0x57, 0xba, 0x53, 0x41, 0x1c, 0xd5, 0xa2, 0x9e, 0x24, 0xa1, 0x10, 0x61, - 0xa2, 0x77, 0x20, 0x87, 0xbb, 0xb8, 0xf5, 0xa4, 0xda, 0x6f, 0x2a, 0x73, 0xa5, 0x5b, 0xc7, 0x27, - 0xe5, 0x15, 0xae, 0x2d, 0xaa, 0xa0, 0xeb, 0x5a, 0x87, 0x6c, 0xe9, 0xbd, 0x05, 0xf3, 0x01, 0x34, - 0x51, 0x7a, 0xe5, 0xf8, 0xa4, 0xfc, 0xdd, 0xf3, 0xd0, 0x08, 0x12, 0xf7, 0x36, 0xab, 0xb8, 0xd9, - 0x50, 0x92, 0xf1, 0x48, 0xdc, 0xdb, 0xd7, 0x5d, 0x62, 0xa2, 0xef, 0x41, 0x56, 0x02, 0x53, 0xa5, - 0xd2, 0xf1, 0x49, 0xf9, 0xc6, 0x79, 0xe0, 0x14, 0x87, 0x7b, 0x5b, 0xd5, 0x27, 0x4d, 0x25, 0x1d, - 0x8f, 0xc3, 0x3d, 0x5b, 0x3f, 0x24, 0xe8, 0x0d, 0xc8, 0x08, 0x58, 0xa6, 0x74, 0xf3, 0xf8, 0xa4, - 0xfc, 0x9d, 0x17, 0xd4, 0x31, 0x54, 0x69, 0xe5, 0xb7, 0xfe, 0x60, 0x75, 0xee, 0x2f, 0xff, 0x70, - 0x55, 0x39, 0xcf, 0x2e, 0xfd, 0x77, 0x02, 0x16, 0x66, 0xa6, 0x1c, 0xa9, 0x90, 0x75, 0xa8, 0x41, - 0x47, 0xe2, 0xfc, 0xca, 0xd5, 0xe0, 0xec, 0x74, 0x2d, 0xdb, 0xa6, 0x75, 0x3a, 0x9a, 0x60, 0xc9, - 0x41, 0x8f, 0xcf, 0x9d, 0xc0, 0xf7, 0x5e, 0x72, 0x3d, 0xc5, 0x9e, 0xc1, 0x9f, 0xc2, 0x82, 0xe9, - 0x5a, 0x87, 0xc4, 0xd5, 0x0c, 0xea, 0xec, 0x59, 0x03, 0x79, 0x36, 0x95, 0xe2, 0x74, 0x36, 0x38, - 0x10, 0x17, 0x85, 0x40, 0x9d, 0xe3, 0xbf, 0xc5, 0xe9, 0x5b, 0x7a, 0x02, 0xc5, 0xe8, 0x0a, 0x65, - 0xc7, 0x89, 0x67, 0xfd, 0x32, 0x91, 0xf9, 0x20, 0xcf, 0x1e, 0x71, 0x9e, 0x51, 0x44, 0x36, 0xf8, - 0x26, 0xa4, 0x87, 0xd4, 0x14, 0x7a, 0x16, 0x6a, 0xd7, 0x59, 0x12, 0xf0, 0x4f, 0xa7, 0x6b, 0x05, - 0xea, 0x55, 0x36, 0x2c, 0x9b, 0x6c, 0x53, 0x93, 0x60, 0x0e, 0x50, 0x0f, 0x21, 0xcd, 0x42, 0x05, - 0x7a, 0x05, 0xd2, 0xb5, 0x56, 0xbb, 0xa1, 0xcc, 0x95, 0xae, 0x1d, 0x9f, 0x94, 0x17, 0xb8, 0x4b, - 0x18, 0x83, 0xad, 0x5d, 0xb4, 0x06, 0xd9, 0x27, 0x9d, 0xad, 0x9d, 0x6d, 0xb6, 0xbc, 0xae, 0x1f, - 0x9f, 0x94, 0x97, 0x42, 0xb6, 0x70, 0x1a, 0x7a, 0x15, 0x32, 0xfd, 0xed, 0xee, 0x46, 0x4f, 0x49, - 0x96, 0xd0, 0xf1, 0x49, 0x79, 0x31, 0xe4, 0x73, 0x9b, 0x4b, 0xd7, 0xe4, 0xac, 0xe6, 0x43, 0xba, - 0xfa, 0xb3, 0x24, 0x2c, 0x60, 0x56, 0x9b, 0xb9, 0x7e, 0x97, 0xda, 0x96, 0x31, 0x41, 0x5d, 0xc8, - 0x1b, 0xd4, 0x31, 0xad, 0xc8, 0x9e, 0x5a, 0xbf, 0xe0, 0xd4, 0x9f, 0x4a, 0x05, 0xad, 0x7a, 0x20, - 0x89, 0xa7, 0x4a, 0xd0, 0x7b, 0x90, 0x31, 0x89, 0xad, 0x4f, 0x64, 0xfa, 0x71, 0xb3, 0x22, 0xaa, - 0xbf, 0x4a, 0x50, 0xfd, 0x55, 0x1a, 0xb2, 0xfa, 0xc3, 0x02, 0xc7, 0xd3, 0x6c, 0xfd, 0x99, 0xa6, - 0xfb, 0x3e, 0x19, 0x8e, 0x7c, 0x91, 0x7b, 0xa4, 0x71, 0x61, 0xa8, 0x3f, 0xab, 0x4a, 0x12, 0xba, - 0x0b, 0xd9, 0x23, 0xcb, 0x31, 0xe9, 0x91, 0x4c, 0x2f, 0x2e, 0x51, 0x2a, 0x81, 0xea, 0x31, 0x3b, - 0x75, 0xcf, 0x99, 0xc9, 0xfc, 0xdd, 0xee, 0xb4, 0x9b, 0x81, 0xbf, 0x25, 0xbf, 0xe3, 0xb4, 0xa9, - 0xc3, 0xf6, 0x0a, 0x74, 0xda, 0xda, 0x46, 0xb5, 0xb5, 0xb5, 0x83, 0x99, 0xcf, 0x97, 0x8f, 0x4f, - 0xca, 0x4a, 0x08, 0xd9, 0xd0, 0x2d, 0x9b, 0xe5, 0xbb, 0x37, 0x21, 0x55, 0x6d, 0x7f, 0xae, 0x24, - 0x4b, 0xca, 0xf1, 0x49, 0xb9, 0x18, 0xb2, 0xab, 0xce, 0x64, 0xba, 0x8d, 0xce, 0xf7, 0xab, 0xfe, - 0x6d, 0x0a, 0x8a, 0x3b, 0x23, 0x53, 0xf7, 0x89, 0x58, 0x93, 0xa8, 0x0c, 0x85, 0x91, 0xee, 0xea, - 0xb6, 0x4d, 0x6c, 0xcb, 0x1b, 0xca, 0xba, 0x36, 0x4a, 0x42, 0x0f, 0x5e, 0xd6, 0x8d, 0xb5, 0x1c, - 0x5b, 0x67, 0x3f, 0xfe, 0x97, 0xb5, 0x44, 0xe0, 0xd0, 0x1d, 0x58, 0xdc, 0x13, 0xd6, 0x6a, 0xba, - 0xc1, 0x27, 0x36, 0xc5, 0x27, 0xb6, 0x12, 0x37, 0xb1, 0x51, 0xb3, 0x2a, 0x72, 0x90, 0x55, 0x2e, - 0x85, 0x17, 0xf6, 0xa2, 0x4d, 0x74, 0x0f, 0xe6, 0x87, 0xd4, 0xb1, 0x7c, 0xea, 0x5e, 0x3d, 0x0b, - 0x01, 0x12, 0xbd, 0x03, 0xd7, 0xd8, 0xe4, 0x06, 0xf6, 0x70, 0x36, 0x3f, 0xb1, 0x92, 0x78, 0x69, - 0xa8, 0x3f, 0x93, 0x1d, 0x62, 0x46, 0x46, 0x35, 0xc8, 0x50, 0x97, 0xa5, 0x44, 0x59, 0x6e, 0xee, - 0xbb, 0x57, 0x9a, 0x2b, 0x1a, 0x1d, 0x26, 0x83, 0x85, 0xa8, 0xfa, 0x21, 0x2c, 0xcc, 0x0c, 0x82, - 0x65, 0x02, 0xdd, 0xea, 0x4e, 0xaf, 0xa9, 0xcc, 0xa1, 0x22, 0xe4, 0xea, 0x9d, 0x76, 0xbf, 0xd5, - 0xde, 0x61, 0xa9, 0x4c, 0x11, 0x72, 0xb8, 0xb3, 0xb5, 0x55, 0xab, 0xd6, 0x1f, 0x2b, 0x49, 0xb5, - 0x02, 0x85, 0x88, 0x36, 0xb4, 0x08, 0xd0, 0xeb, 0x77, 0xba, 0xda, 0x46, 0x0b, 0xf7, 0xfa, 0x22, - 0x11, 0xea, 0xf5, 0xab, 0xb8, 0x2f, 0x09, 0x09, 0xf5, 0x3f, 0x92, 0xc1, 0x8c, 0xca, 0xdc, 0xa7, - 0x36, 0x9b, 0xfb, 0x5c, 0x62, 0xbc, 0xcc, 0x7e, 0xa6, 0x8d, 0x30, 0x07, 0x7a, 0x00, 0xc0, 0x17, - 0x0e, 0x31, 0x35, 0xdd, 0x97, 0x13, 0x5f, 0x7a, 0xc1, 0xc9, 0xfd, 0xe0, 0x7a, 0x05, 0xe7, 0x25, - 0xba, 0xea, 0xa3, 0x8f, 0xa1, 0x68, 0xd0, 0xe1, 0xc8, 0x26, 0x52, 0x38, 0x75, 0xa5, 0x70, 0x21, - 0xc4, 0x57, 0xfd, 0x68, 0xf6, 0x95, 0x9e, 0xcd, 0x0f, 0x7f, 0x23, 0x11, 0x78, 0x26, 0x26, 0xe1, - 0x2a, 0x42, 0x6e, 0xa7, 0xdb, 0xa8, 0xf6, 0x5b, 0xed, 0x47, 0x4a, 0x02, 0x01, 0x64, 0xb9, 0xab, - 0x1b, 0x4a, 0x92, 0x25, 0x8a, 0xf5, 0xce, 0x76, 0x77, 0xab, 0xc9, 0x53, 0x2e, 0xb4, 0x0c, 0x4a, - 0xe0, 0x6c, 0x8d, 0x3b, 0xb2, 0xd9, 0x50, 0xd2, 0xe8, 0x3a, 0x2c, 0x85, 0x54, 0x29, 0x99, 0x41, - 0x37, 0x00, 0x85, 0xc4, 0xa9, 0x8a, 0xac, 0xfa, 0xab, 0xb0, 0x54, 0xa7, 0x8e, 0xaf, 0x5b, 0x4e, - 0x98, 0x44, 0xaf, 0xb3, 0x41, 0x4b, 0x92, 0x66, 0xc9, 0x5b, 0x8a, 0xda, 0xd2, 0xd9, 0xe9, 0x5a, - 0x21, 0x84, 0xb6, 0x1a, 0x6c, 0xa4, 0x41, 0xc3, 0x64, 0xfb, 0x77, 0x64, 0x99, 0xdc, 0xb9, 0x99, - 0xda, 0xfc, 0xd9, 0xe9, 0x5a, 0xaa, 0xdb, 0x6a, 0x60, 0x46, 0x43, 0xaf, 0x40, 0x9e, 0x3c, 0xb3, - 0x7c, 0xcd, 0x60, 0x31, 0x9c, 0x39, 0x30, 0x83, 0x73, 0x8c, 0x50, 0x67, 0x21, 0xbb, 0x06, 0xd0, - 0xa5, 0xae, 0x2f, 0x7b, 0x7e, 0x1f, 0x32, 0x23, 0xea, 0xf2, 0xf2, 0xfc, 0xc2, 0xeb, 0x1d, 0x06, - 0x17, 0x0b, 0x15, 0x0b, 0xb0, 0xfa, 0x57, 0x49, 0x80, 0xbe, 0xee, 0x1d, 0x48, 0x25, 0xf7, 0x21, - 0x1f, 0x5e, 0x95, 0xc9, 0x3a, 0xff, 0xd2, 0xd9, 0x0e, 0xc1, 0xe8, 0x5e, 0xb0, 0xd8, 0x44, 0x79, - 0x10, 0x5b, 0xa7, 0x05, 0x1d, 0xc5, 0x65, 0xd8, 0xb3, 0x35, 0x00, 0x3b, 0x12, 0x89, 0xeb, 0xca, - 0x99, 0x67, 0x9f, 0xa8, 0xce, 0x8f, 0x05, 0xe1, 0x34, 0x99, 0x60, 0xc6, 0xde, 0x6c, 0x9c, 0x9b, - 0x91, 0xcd, 0x39, 0x3c, 0x95, 0x43, 0x9f, 0x42, 0x81, 0x8d, 0x5b, 0xf3, 0x38, 0x4f, 0xe6, 0x96, - 0x17, 0xba, 0x4a, 0x68, 0xc0, 0x30, 0x0a, 0xbf, 0x6b, 0x0a, 0x2c, 0xba, 0x63, 0x87, 0x0d, 0x5b, - 0xea, 0x50, 0xff, 0x24, 0x09, 0xdf, 0x6d, 0x13, 0xff, 0x88, 0xba, 0x07, 0x55, 0xdf, 0xd7, 0x8d, - 0xfd, 0x21, 0x71, 0xa4, 0x93, 0x23, 0x99, 0x75, 0x62, 0x26, 0xb3, 0x5e, 0x81, 0x79, 0xdd, 0xb6, - 0x74, 0x8f, 0x88, 0x74, 0x24, 0x8f, 0x83, 0x26, 0xcb, 0xff, 0x59, 0x35, 0x41, 0x3c, 0x8f, 0x88, - 0x02, 0x3f, 0x8f, 0xa7, 0x04, 0xf4, 0x23, 0xb8, 0x21, 0x13, 0x0f, 0x3d, 0xec, 0x8a, 0x65, 0xb6, - 0xc1, 0x9d, 0x5e, 0x33, 0xb6, 0xbc, 0x89, 0x37, 0x4e, 0x66, 0x26, 0x53, 0x72, 0x67, 0xe4, 0xcb, - 0x3c, 0x67, 0xd9, 0x8c, 0x61, 0x95, 0x1e, 0xc1, 0xcd, 0x0b, 0x45, 0xbe, 0xd1, 0x05, 0xc2, 0x3f, - 0x24, 0x01, 0x5a, 0xdd, 0xea, 0xb6, 0x74, 0x52, 0x03, 0xb2, 0x7b, 0xfa, 0xd0, 0xb2, 0x27, 0x97, - 0xc5, 0xa9, 0x29, 0xbe, 0x52, 0x15, 0xee, 0xd8, 0xe0, 0x32, 0x58, 0xca, 0xf2, 0xe2, 0x66, 0xbc, - 0xeb, 0x10, 0x3f, 0x2c, 0x6e, 0x78, 0x8b, 0x99, 0xe1, 0xea, 0x4e, 0xb8, 0xc0, 0x44, 0x83, 0x4d, - 0xc0, 0x40, 0xf7, 0xc9, 0x91, 0x3e, 0x09, 0x82, 0x8b, 0x6c, 0xa2, 0x4d, 0x7e, 0x4d, 0x47, 0xdc, - 0x43, 0x62, 0xae, 0x64, 0xb8, 0x53, 0xaf, 0xb2, 0x07, 0x4b, 0xb8, 0xf0, 0x5d, 0x28, 0x5d, 0x7a, - 0xc8, 0x13, 0x9b, 0x29, 0xeb, 0x1b, 0xf9, 0xe8, 0x0e, 0x2c, 0xcc, 0x8c, 0xf3, 0x85, 0xaa, 0xb2, - 0xd5, 0x7d, 0xf2, 0xbe, 0x92, 0x96, 0x5f, 0x1f, 0x2a, 0x59, 0xf5, 0x8f, 0x52, 0x22, 0x1c, 0x48, - 0xaf, 0xc6, 0x5f, 0x24, 0xe7, 0xf8, 0x26, 0x36, 0xa8, 0x2d, 0xb7, 0xe9, 0x9b, 0x97, 0x47, 0x09, - 0x56, 0xa5, 0x70, 0x38, 0x0e, 0x05, 0xd1, 0x1a, 0x14, 0xc4, 0x2a, 0xd6, 0xd8, 0xb6, 0xe0, 0x6e, - 0x5d, 0xc0, 0x20, 0x48, 0x4c, 0x12, 0xdd, 0x86, 0x45, 0x7e, 0x0b, 0xe1, 0xed, 0x13, 0x53, 0x60, - 0xd2, 0x1c, 0xb3, 0x10, 0x52, 0x39, 0x6c, 0x1b, 0x8a, 0x92, 0xa0, 0xf1, 0x0c, 0x35, 0xc3, 0x0d, - 0x7a, 0xe7, 0x2a, 0x83, 0x84, 0x08, 0x4f, 0x5c, 0x0b, 0xa3, 0x69, 0x43, 0x6d, 0x40, 0x2e, 0x30, - 0x16, 0xad, 0x40, 0xaa, 0x5f, 0xef, 0x2a, 0x73, 0xa5, 0xa5, 0xe3, 0x93, 0x72, 0x21, 0x20, 0xf7, - 0xeb, 0x5d, 0xc6, 0xd9, 0x69, 0x74, 0x95, 0xc4, 0x2c, 0x67, 0xa7, 0xd1, 0x2d, 0xa5, 0x59, 0xa6, - 0xa4, 0xee, 0x41, 0x21, 0xd2, 0x03, 0x7a, 0x1d, 0xe6, 0x5b, 0xed, 0x47, 0xb8, 0xd9, 0xeb, 0x29, - 0x73, 0xa5, 0x1b, 0xc7, 0x27, 0x65, 0x14, 0xe1, 0xb6, 0x9c, 0x01, 0x9b, 0x1f, 0xf4, 0x2a, 0xa4, - 0x37, 0x3b, 0xec, 0x04, 0x16, 0x29, 0x71, 0x04, 0xb1, 0x49, 0x3d, 0xbf, 0x74, 0x5d, 0xa6, 0x60, - 0x51, 0xc5, 0xea, 0xef, 0x25, 0x20, 0x2b, 0x36, 0x53, 0xec, 0x44, 0x55, 0x61, 0x3e, 0xa8, 0x57, - 0x45, 0xb9, 0xf2, 0xe6, 0xc5, 0xa5, 0x45, 0x45, 0x56, 0x02, 0x62, 0xf9, 0x05, 0x72, 0xa5, 0x8f, - 0xa0, 0x18, 0x65, 0x7c, 0xa3, 0xc5, 0xf7, 0x23, 0x28, 0xb0, 0xf5, 0x1d, 0x94, 0x18, 0xeb, 0x90, - 0x15, 0x01, 0x21, 0x3c, 0x11, 0x2e, 0xae, 0x73, 0x24, 0x12, 0xdd, 0x87, 0x79, 0x51, 0x1b, 0x05, - 0xd7, 0x94, 0xab, 0x97, 0xef, 0x22, 0x1c, 0xc0, 0xd5, 0x4f, 0x21, 0xdd, 0x25, 0xc4, 0x65, 0xbe, - 0x77, 0xa8, 0x49, 0xa6, 0x87, 0xa8, 0x2c, 0xeb, 0x4c, 0xd2, 0x6a, 0xb0, 0xb2, 0xce, 0x24, 0x2d, - 0x33, 0xbc, 0x88, 0x49, 0x46, 0x2e, 0x62, 0xfa, 0x50, 0x7c, 0x4a, 0xac, 0xc1, 0xbe, 0x4f, 0x4c, - 0xae, 0xe8, 0x5d, 0x48, 0x8f, 0x48, 0x68, 0xfc, 0x4a, 0xec, 0x02, 0x23, 0xc4, 0xc5, 0x1c, 0xc5, - 0xe2, 0xc8, 0x11, 0x97, 0x96, 0x77, 0xeb, 0xb2, 0xa5, 0xfe, 0x7d, 0x12, 0x16, 0x5b, 0x9e, 0x37, - 0xd6, 0x1d, 0x23, 0xc8, 0xaf, 0x3e, 0x99, 0xcd, 0xaf, 0xde, 0x8a, 0x1d, 0xe1, 0x8c, 0xc8, 0xec, - 0xfd, 0x92, 0x3c, 0xe3, 0x92, 0xe1, 0x19, 0xa7, 0xfe, 0x7b, 0x22, 0xb8, 0x44, 0xba, 0x1d, 0xd9, - 0xee, 0xa5, 0x95, 0xe3, 0x93, 0xf2, 0x72, 0x54, 0x13, 0xd9, 0x71, 0x0e, 0x1c, 0x7a, 0xe4, 0xa0, - 0xd7, 0x20, 0x83, 0x9b, 0xed, 0xe6, 0x53, 0x25, 0x21, 0x96, 0xe7, 0x0c, 0x08, 0x13, 0x87, 0x1c, - 0x31, 0x4d, 0xdd, 0x66, 0xbb, 0xc1, 0xf2, 0xa1, 0x64, 0x8c, 0xa6, 0x2e, 0x71, 0x4c, 0xcb, 0x19, - 0xa0, 0xd7, 0x21, 0xdb, 0xea, 0xf5, 0x76, 0x78, 0x99, 0xff, 0xdd, 0xe3, 0x93, 0xf2, 0xf5, 0x19, - 0x14, 0xbf, 0x40, 0x34, 0x19, 0x88, 0x15, 0x23, 0x2c, 0x53, 0x8a, 0x01, 0xb1, 0x2c, 0x57, 0x80, - 0x70, 0xa7, 0x5f, 0xed, 0xb3, 0x0a, 0xff, 0x45, 0x10, 0xa6, 0xec, 0xaf, 0xdc, 0x6e, 0xff, 0x9c, - 0x04, 0xa5, 0x6a, 0x18, 0x64, 0xe4, 0x33, 0xbe, 0xac, 0xff, 0xfa, 0x90, 0x1b, 0xb1, 0x2f, 0x8b, - 0x04, 0xb9, 0xcc, 0xfd, 0xd8, 0x07, 0xaf, 0x73, 0x72, 0x15, 0x4c, 0x6d, 0x52, 0x35, 0x87, 0x96, - 0xe7, 0x59, 0xd4, 0x11, 0x34, 0x1c, 0x6a, 0x2a, 0xfd, 0x67, 0x02, 0xae, 0xc7, 0x20, 0xd0, 0x1d, - 0x48, 0xbb, 0xd4, 0x0e, 0xe6, 0xf0, 0xd6, 0x45, 0xf7, 0x83, 0x4c, 0x14, 0x73, 0x24, 0x5a, 0x05, - 0xd0, 0xc7, 0x3e, 0xd5, 0x79, 0xff, 0x7c, 0xf6, 0x72, 0x38, 0x42, 0x41, 0x4f, 0x21, 0xeb, 0x11, - 0xc3, 0x25, 0x41, 0xc6, 0xfb, 0xe9, 0xff, 0xd5, 0xfa, 0x4a, 0x8f, 0xab, 0xc1, 0x52, 0x5d, 0xa9, - 0x02, 0x59, 0x41, 0x61, 0xcb, 0xde, 0xd4, 0x7d, 0x5d, 0xde, 0x1e, 0xf3, 0x6f, 0xb6, 0x9a, 0x74, - 0x7b, 0x10, 0xac, 0x26, 0xdd, 0x1e, 0xa8, 0x7f, 0x93, 0x04, 0x68, 0x3e, 0xf3, 0x89, 0xeb, 0xe8, - 0x76, 0xbd, 0x8a, 0x9a, 0x91, 0xe8, 0x2f, 0x46, 0xfb, 0x76, 0xec, 0x95, 0x78, 0x28, 0x51, 0xa9, - 0x57, 0x63, 0xe2, 0xff, 0x4d, 0x48, 0x8d, 0x5d, 0xf9, 0x86, 0x29, 0xb2, 0xd5, 0x1d, 0xbc, 0x85, - 0x19, 0x0d, 0x35, 0xa7, 0x61, 0x2b, 0x75, 0xf1, 0x4b, 0x65, 0xa4, 0x83, 0xd8, 0xd0, 0xc5, 0x76, - 0xbe, 0xa1, 0x6b, 0x06, 0x91, 0x27, 0x47, 0x51, 0xec, 0xfc, 0x7a, 0xb5, 0x4e, 0x5c, 0x1f, 0x67, - 0x0d, 0x9d, 0xfd, 0xff, 0x56, 0xf1, 0xed, 0x5d, 0x80, 0xe9, 0xd0, 0xd0, 0x2a, 0x64, 0xea, 0x1b, - 0xbd, 0xde, 0x96, 0x32, 0x27, 0x02, 0xf8, 0x94, 0xc5, 0xc9, 0xea, 0x5f, 0x24, 0x21, 0x57, 0xaf, - 0xca, 0x63, 0xb5, 0x0e, 0x0a, 0x8f, 0x4a, 0xfc, 0xce, 0x9d, 0x3c, 0x1b, 0x59, 0xee, 0x44, 0x06, - 0x96, 0x4b, 0x4a, 0xcf, 0x45, 0x26, 0xc2, 0xac, 0x6e, 0x72, 0x01, 0x84, 0xa1, 0x48, 0xa4, 0x13, - 0x34, 0x43, 0x0f, 0x62, 0xfc, 0xea, 0xe5, 0xce, 0x12, 0x45, 0xc4, 0xb4, 0xed, 0xe1, 0x42, 0xa0, - 0xa4, 0xae, 0x7b, 0xe8, 0x01, 0x2c, 0x79, 0xd6, 0xc0, 0xb1, 0x9c, 0x81, 0x16, 0x38, 0x8f, 0x3f, - 0x00, 0xd4, 0xae, 0x9d, 0x9d, 0xae, 0x2d, 0xf4, 0x04, 0x4b, 0xfa, 0x70, 0x41, 0x22, 0xeb, 0xdc, - 0x95, 0xe8, 0x43, 0x58, 0x8c, 0x88, 0x32, 0x2f, 0x0a, 0xb7, 0x2b, 0x67, 0xa7, 0x6b, 0xc5, 0x50, - 0xf2, 0x31, 0x99, 0xe0, 0x62, 0x28, 0xf8, 0x98, 0xf0, 0x5b, 0x92, 0x3d, 0xea, 0x1a, 0x44, 0x73, - 0xf9, 0x9e, 0xe6, 0x27, 0x78, 0x1a, 0x17, 0x38, 0x4d, 0x6c, 0x73, 0xf5, 0x09, 0x5c, 0xef, 0xb8, - 0xc6, 0x3e, 0xf1, 0x7c, 0xe1, 0x0a, 0xe9, 0xc5, 0x4f, 0xe1, 0x96, 0xaf, 0x7b, 0x07, 0xda, 0xbe, - 0xe5, 0xf9, 0xd4, 0x9d, 0x68, 0x2e, 0xf1, 0x89, 0xc3, 0xf8, 0x1a, 0x7f, 0x35, 0x94, 0xd7, 0x58, - 0x37, 0x19, 0x66, 0x53, 0x40, 0x70, 0x80, 0xd8, 0x62, 0x00, 0xb5, 0x05, 0x45, 0x56, 0x4c, 0x34, - 0xc8, 0x9e, 0x3e, 0xb6, 0x7d, 0x36, 0x7a, 0xb0, 0xe9, 0x40, 0x7b, 0xe9, 0x63, 0x2a, 0x6f, 0xd3, - 0x81, 0xf8, 0x54, 0x7f, 0x08, 0x4a, 0xc3, 0xf2, 0x46, 0xba, 0x6f, 0xec, 0x07, 0xf7, 0x73, 0xa8, - 0x01, 0xca, 0x3e, 0xd1, 0x5d, 0x7f, 0x97, 0xe8, 0xbe, 0x36, 0x22, 0xae, 0x45, 0xcd, 0xab, 0x67, - 0x79, 0x29, 0x14, 0xe9, 0x72, 0x09, 0xf5, 0xbf, 0x12, 0x00, 0x58, 0xdf, 0x0b, 0x32, 0xb2, 0xef, - 0xc3, 0x35, 0xcf, 0xd1, 0x47, 0xde, 0x3e, 0xf5, 0x35, 0xcb, 0xf1, 0x89, 0x7b, 0xa8, 0xdb, 0xf2, - 0x9a, 0x45, 0x09, 0x18, 0x2d, 0x49, 0x47, 0xef, 0x02, 0x3a, 0x20, 0x64, 0xa4, 0x51, 0xdb, 0xd4, - 0x02, 0xa6, 0x78, 0xd3, 0x4c, 0x63, 0x85, 0x71, 0x3a, 0xb6, 0xd9, 0x0b, 0xe8, 0xa8, 0x06, 0xab, - 0x6c, 0xf8, 0xc4, 0xf1, 0x5d, 0x8b, 0x78, 0xda, 0x1e, 0x75, 0x35, 0xcf, 0xa6, 0x47, 0xda, 0x1e, - 0xb5, 0x6d, 0x7a, 0x44, 0xdc, 0xe0, 0x06, 0xab, 0x64, 0xd3, 0x41, 0x53, 0x80, 0x36, 0xa8, 0xdb, - 0xb3, 0xe9, 0xd1, 0x46, 0x80, 0x60, 0x69, 0xdb, 0x74, 0xcc, 0xbe, 0x65, 0x1c, 0x04, 0x69, 0x5b, - 0x48, 0xed, 0x5b, 0xc6, 0x01, 0x7a, 0x1d, 0x16, 0x88, 0x4d, 0xf8, 0x45, 0x86, 0x40, 0x65, 0x38, - 0xaa, 0x18, 0x10, 0x19, 0x48, 0xfd, 0x0c, 0x94, 0xa6, 0x63, 0xb8, 0x93, 0x51, 0x64, 0xce, 0xdf, - 0x05, 0xc4, 0x82, 0xa4, 0x66, 0x53, 0xe3, 0x40, 0x1b, 0xea, 0x8e, 0x3e, 0x60, 0x76, 0x89, 0xa7, - 0x26, 0x85, 0x71, 0xb6, 0xa8, 0x71, 0xb0, 0x2d, 0xe9, 0xea, 0x03, 0x80, 0xde, 0xc8, 0x25, 0xba, - 0xd9, 0x61, 0xd9, 0x04, 0x73, 0x1d, 0x6f, 0x69, 0xa6, 0x7c, 0xaa, 0xa3, 0xae, 0xdc, 0xea, 0x8a, - 0x60, 0x34, 0x42, 0xba, 0xfa, 0x0b, 0x70, 0xbd, 0x6b, 0xeb, 0x06, 0x7f, 0xb6, 0xee, 0x86, 0x6f, - 0x27, 0xe8, 0x3e, 0x64, 0x05, 0x54, 0xce, 0x64, 0xec, 0x76, 0x9b, 0xf6, 0xb9, 0x39, 0x87, 0x25, - 0xbe, 0x56, 0x04, 0x98, 0xea, 0x51, 0xff, 0x2c, 0x01, 0xf9, 0x50, 0x3f, 0x2a, 0x03, 0x2b, 0xe5, - 0xd9, 0xf2, 0xb6, 0x1c, 0x59, 0x7b, 0xe7, 0x71, 0x94, 0x84, 0x5a, 0x50, 0x18, 0x85, 0xd2, 0x97, - 0xe6, 0x73, 0x31, 0x56, 0xe3, 0xa8, 0x2c, 0xfa, 0x08, 0xf2, 0xc1, 0xdb, 0x68, 0x10, 0x61, 0x2f, - 0x7f, 0x4a, 0x9d, 0xc2, 0xd5, 0x4f, 0x00, 0x7e, 0x40, 0x2d, 0xa7, 0x4f, 0x0f, 0x88, 0xc3, 0xdf, - 0xfa, 0x58, 0x4d, 0x48, 0x02, 0x2f, 0xca, 0x16, 0x2f, 0xc8, 0xc5, 0x14, 0x84, 0x4f, 0x5e, 0xa2, - 0xa9, 0xfe, 0x75, 0x12, 0xb2, 0x98, 0x52, 0xbf, 0x5e, 0x45, 0x65, 0xc8, 0xca, 0x38, 0xc1, 0xcf, - 0x9f, 0x5a, 0xfe, 0xec, 0x74, 0x2d, 0x23, 0x02, 0x44, 0xc6, 0xe0, 0x91, 0x21, 0x12, 0xc1, 0x93, - 0x17, 0x45, 0x70, 0x74, 0x07, 0x8a, 0x12, 0xa4, 0xed, 0xeb, 0xde, 0xbe, 0x28, 0xd0, 0x6a, 0x8b, - 0x67, 0xa7, 0x6b, 0x20, 0x90, 0x9b, 0xba, 0xb7, 0x8f, 0x41, 0xa0, 0xd9, 0x37, 0x6a, 0x42, 0xe1, - 0x0b, 0x6a, 0x39, 0x9a, 0xcf, 0x07, 0x21, 0xaf, 0xfc, 0x62, 0xe7, 0x71, 0x3a, 0x54, 0xf9, 0xf0, - 0x0d, 0x5f, 0x4c, 0x07, 0xdf, 0x84, 0x05, 0x97, 0x52, 0x5f, 0x84, 0x2d, 0x8b, 0x3a, 0xf2, 0x36, - 0xa1, 0x1c, 0x7b, 0xc9, 0x4c, 0xa9, 0x8f, 0x25, 0x0e, 0x17, 0xdd, 0x48, 0x0b, 0xdd, 0x81, 0x65, - 0x5b, 0xf7, 0x7c, 0x8d, 0xc7, 0x3b, 0x73, 0xaa, 0x2d, 0xcb, 0xb7, 0x1a, 0x62, 0xbc, 0x0d, 0xce, - 0x0a, 0x24, 0xd4, 0x7f, 0x4c, 0x40, 0x81, 0x0d, 0xc6, 0xda, 0xb3, 0x0c, 0x96, 0xe4, 0x7d, 0xf3, - 0xdc, 0xe3, 0x26, 0xa4, 0x0c, 0xcf, 0x95, 0x4e, 0xe5, 0x87, 0x6f, 0xbd, 0x87, 0x31, 0xa3, 0xa1, - 0xcf, 0x20, 0x2b, 0x6f, 0x35, 0x44, 0xda, 0xa1, 0x5e, 0x9d, 0x8e, 0x4a, 0xdf, 0x48, 0x39, 0xbe, - 0x96, 0xa7, 0xd6, 0x89, 0x43, 0x00, 0x47, 0x49, 0xe8, 0x06, 0x24, 0x0d, 0xe1, 0x2e, 0xf9, 0xcb, - 0x8a, 0x7a, 0x1b, 0x27, 0x0d, 0x47, 0xfd, 0xbb, 0x04, 0x2c, 0x4c, 0x37, 0x3c, 0x5b, 0x01, 0xb7, - 0x20, 0xef, 0x8d, 0x77, 0xbd, 0x89, 0xe7, 0x93, 0x61, 0xf0, 0x8e, 0x19, 0x12, 0x50, 0x0b, 0xf2, - 0xba, 0x3d, 0xa0, 0xae, 0xe5, 0xef, 0x0f, 0x65, 0x25, 0x1a, 0x9f, 0x2a, 0x44, 0x75, 0x56, 0xaa, - 0x81, 0x08, 0x9e, 0x4a, 0x07, 0xe7, 0xbe, 0x78, 0xec, 0xe6, 0xe7, 0xfe, 0x6b, 0x50, 0xb4, 0xf5, - 0x21, 0xbf, 0xe6, 0xf1, 0xad, 0xa1, 0x18, 0x47, 0x1a, 0x17, 0x24, 0xad, 0x6f, 0x0d, 0x89, 0xaa, - 0x42, 0x3e, 0x54, 0x86, 0x96, 0xa0, 0x50, 0x6d, 0xf6, 0xb4, 0xbb, 0xeb, 0xf7, 0xb5, 0x47, 0xf5, - 0x6d, 0x65, 0x4e, 0xe6, 0xa6, 0x7f, 0x9e, 0x80, 0x05, 0x19, 0x8e, 0x64, 0xbe, 0xff, 0x3a, 0xcc, - 0xbb, 0xfa, 0x9e, 0x1f, 0x54, 0x24, 0x69, 0xb1, 0xaa, 0x59, 0x84, 0x67, 0x15, 0x09, 0x63, 0xc5, - 0x57, 0x24, 0x91, 0x97, 0xf5, 0xd4, 0xa5, 0x2f, 0xeb, 0xe9, 0x9f, 0xcb, 0xcb, 0xba, 0xfa, 0x6b, - 0x00, 0x1b, 0x96, 0x4d, 0xfa, 0xe2, 0xae, 0x29, 0xae, 0xbe, 0x64, 0x39, 0x9c, 0xbc, 0x71, 0x0c, - 0x72, 0xb8, 0x56, 0x03, 0x33, 0x1a, 0x63, 0x0d, 0x2c, 0x53, 0x6e, 0x46, 0xce, 0x7a, 0xc4, 0x58, - 0x03, 0xcb, 0x0c, 0xdf, 0x92, 0xd2, 0x57, 0xbd, 0x25, 0x9d, 0x24, 0x60, 0x49, 0xe6, 0xae, 0x61, - 0xf8, 0x7d, 0x1b, 0xf2, 0x22, 0x8d, 0x9d, 0x16, 0x74, 0xfc, 0x35, 0x59, 0xe0, 0x5a, 0x0d, 0x9c, - 0x13, 0xec, 0x96, 0x89, 0xd6, 0xa0, 0x20, 0xa1, 0x91, 0x5f, 0xe1, 0x80, 0x20, 0xb5, 0x99, 0xf9, - 0xef, 0x43, 0x7a, 0xcf, 0xb2, 0x89, 0x5c, 0xe8, 0xb1, 0x01, 0x60, 0xea, 0x80, 0xcd, 0x39, 0xcc, - 0xd1, 0xb5, 0x5c, 0x70, 0x19, 0xc7, 0xed, 0x93, 0x65, 0x67, 0xd4, 0x3e, 0x51, 0x81, 0x9e, 0xb3, - 0x4f, 0xe0, 0x98, 0x7d, 0x82, 0x2d, 0xec, 0x93, 0xd0, 0xa8, 0x7d, 0x82, 0xf4, 0x73, 0xb1, 0x6f, - 0x0b, 0x6e, 0xd4, 0x6c, 0xdd, 0x38, 0xb0, 0x2d, 0xcf, 0x27, 0x66, 0x34, 0x62, 0xac, 0x43, 0x76, - 0x26, 0xe9, 0xbc, 0xec, 0x72, 0x56, 0x22, 0xd5, 0x7f, 0x4b, 0x40, 0x71, 0x93, 0xe8, 0xb6, 0xbf, - 0x3f, 0xbd, 0x1a, 0xf2, 0x89, 0xe7, 0xcb, 0xc3, 0x8a, 0x7f, 0xa3, 0x0f, 0x20, 0x17, 0xe6, 0x24, - 0x57, 0xbe, 0x92, 0x85, 0x50, 0x74, 0x0f, 0xe6, 0xd9, 0x1e, 0xa3, 0xe3, 0xa0, 0xd8, 0xb9, 0xec, - 0x01, 0x46, 0x22, 0xd9, 0x21, 0xe3, 0x12, 0x9e, 0x84, 0xf0, 0xa5, 0x94, 0xc1, 0x41, 0x13, 0xfd, - 0x7f, 0x28, 0xf2, 0xf7, 0x83, 0x20, 0xe7, 0xca, 0x5c, 0xa5, 0xb3, 0x20, 0x9e, 0x00, 0x45, 0xbe, - 0xf5, 0x3f, 0x09, 0x58, 0xde, 0xd6, 0x27, 0xbb, 0x44, 0x86, 0x0d, 0x62, 0x62, 0x62, 0x50, 0xd7, - 0x44, 0xdd, 0x68, 0xb8, 0xb9, 0xe4, 0x45, 0x31, 0x4e, 0x38, 0x3e, 0xea, 0x04, 0x05, 0x58, 0x32, - 0x52, 0x80, 0x2d, 0x43, 0xc6, 0xa1, 0x8e, 0x41, 0x64, 0x2c, 0x12, 0x0d, 0xd5, 0x8a, 0x86, 0x9a, - 0x52, 0xf8, 0xd8, 0xc7, 0x9f, 0xea, 0xda, 0xd4, 0x0f, 0x7b, 0x43, 0x9f, 0x41, 0xa9, 0xd7, 0xac, - 0xe3, 0x66, 0xbf, 0xd6, 0xf9, 0xa1, 0xd6, 0xab, 0x6e, 0xf5, 0xaa, 0xeb, 0x77, 0xb4, 0x6e, 0x67, - 0xeb, 0xf3, 0xbb, 0xf7, 0xee, 0x7c, 0xa0, 0x24, 0x4a, 0xe5, 0xe3, 0x93, 0xf2, 0xad, 0x76, 0xb5, - 0xbe, 0x25, 0x76, 0xcc, 0x2e, 0x7d, 0xd6, 0xd3, 0x6d, 0x4f, 0x5f, 0xbf, 0xd3, 0xa5, 0xf6, 0x84, - 0x61, 0xd8, 0xb2, 0x2e, 0x46, 0xcf, 0xab, 0xe8, 0x31, 0x9c, 0xb8, 0xf0, 0x18, 0x9e, 0x9e, 0xe6, - 0xc9, 0x0b, 0x4e, 0xf3, 0x0d, 0x58, 0x36, 0x5c, 0xea, 0x79, 0x1a, 0xcb, 0xfe, 0x89, 0x79, 0xae, - 0xbe, 0xf8, 0xce, 0xd9, 0xe9, 0xda, 0xb5, 0x3a, 0xe3, 0xf7, 0x38, 0x5b, 0xaa, 0xbf, 0x66, 0x44, - 0x48, 0xbc, 0x27, 0xf5, 0xf7, 0x53, 0x2c, 0x91, 0xb2, 0x0e, 0x2d, 0x9b, 0x0c, 0x88, 0x87, 0x9e, - 0xc0, 0x92, 0xe1, 0x12, 0x93, 0xa5, 0xf5, 0xba, 0xad, 0x79, 0x23, 0x62, 0xc8, 0x45, 0xfd, 0xff, - 0x62, 0x73, 0x9a, 0x50, 0xb0, 0x52, 0x0f, 0xa5, 0x7a, 0x23, 0x62, 0xe0, 0x45, 0x63, 0xa6, 0x8d, - 0xbe, 0x80, 0x25, 0x8f, 0xd8, 0x96, 0x33, 0x7e, 0xa6, 0x19, 0xd4, 0xf1, 0xc9, 0xb3, 0xe0, 0xdd, - 0xea, 0x2a, 0xbd, 0xbd, 0xe6, 0x16, 0x93, 0xaa, 0x0b, 0xa1, 0x1a, 0x3a, 0x3b, 0x5d, 0x5b, 0x9c, - 0xa5, 0xe1, 0x45, 0xa9, 0x59, 0xb6, 0x4b, 0x6d, 0x58, 0x9c, 0xb5, 0x06, 0x2d, 0xcb, 0xbd, 0xcf, - 0x43, 0x48, 0xb0, 0xb7, 0xd1, 0x2d, 0xc8, 0xb9, 0x64, 0x60, 0x79, 0xbe, 0x2b, 0xdc, 0xcc, 0x38, - 0x21, 0x85, 0xed, 0x7c, 0xf1, 0x53, 0x9c, 0xd2, 0xaf, 0xc0, 0xb9, 0x1e, 0xd9, 0x66, 0x31, 0x2d, - 0x4f, 0xdf, 0x95, 0x2a, 0x73, 0x38, 0x68, 0xb2, 0x35, 0x38, 0xf6, 0xc2, 0x44, 0x8d, 0x7f, 0x33, - 0x1a, 0xcf, 0x28, 0xe4, 0x0f, 0x93, 0x78, 0xce, 0x10, 0xfc, 0xc2, 0x31, 0x1d, 0xf9, 0x85, 0xe3, - 0x32, 0x64, 0x6c, 0x72, 0x48, 0x6c, 0x71, 0x96, 0x63, 0xd1, 0x78, 0xe7, 0x67, 0x29, 0xc8, 0x87, - 0x6f, 0x34, 0xec, 0x24, 0x68, 0x37, 0x9f, 0x06, 0x6b, 0x35, 0xa4, 0xb7, 0xc9, 0x11, 0x7a, 0x6d, - 0x7a, 0xa7, 0xf4, 0x99, 0x78, 0x94, 0x0e, 0xd9, 0xc1, 0x7d, 0xd2, 0x1b, 0x90, 0xab, 0xf6, 0x7a, - 0xad, 0x47, 0xed, 0x66, 0x43, 0xf9, 0x32, 0x51, 0xfa, 0xce, 0xf1, 0x49, 0xf9, 0x5a, 0x08, 0xaa, - 0x7a, 0x62, 0x29, 0x71, 0x54, 0xbd, 0xde, 0xec, 0xf6, 0x9b, 0x0d, 0xe5, 0x79, 0xf2, 0x3c, 0x8a, - 0xdf, 0x91, 0xf0, 0x9f, 0x96, 0xe4, 0xbb, 0xb8, 0xd9, 0xad, 0x62, 0xd6, 0xe1, 0x97, 0x49, 0x71, - 0xd5, 0x35, 0xed, 0xd1, 0x25, 0x23, 0x9d, 0xff, 0xae, 0x78, 0x35, 0xf8, 0x89, 0xd5, 0xf3, 0x94, - 0xf8, 0xf9, 0xc1, 0xf4, 0xc1, 0x89, 0xe8, 0xe6, 0x84, 0xf5, 0xc6, 0x5f, 0xfa, 0xb8, 0x9a, 0xd4, - 0xb9, 0xde, 0x7a, 0x2c, 0x92, 0x30, 0x2d, 0x2a, 0xcc, 0xe3, 0x9d, 0x76, 0x9b, 0x81, 0x9e, 0xa7, - 0xcf, 0x8d, 0x0e, 0x8f, 0x1d, 0x56, 0xff, 0xa2, 0xdb, 0x90, 0x0b, 0x1e, 0x02, 0x95, 0x2f, 0xd3, - 0xe7, 0x0c, 0xaa, 0x07, 0xaf, 0x98, 0xbc, 0xc3, 0xcd, 0x9d, 0x3e, 0xff, 0x05, 0xd8, 0xf3, 0xcc, - 0xf9, 0x0e, 0xf7, 0xc7, 0xbe, 0x49, 0x8f, 0x1c, 0xb6, 0x03, 0xe5, 0xad, 0xda, 0x97, 0x19, 0x71, - 0x05, 0x11, 0x62, 0xe4, 0x95, 0xda, 0x1b, 0x90, 0xc3, 0xcd, 0x1f, 0x88, 0x1f, 0x8b, 0x3d, 0xcf, - 0x9e, 0xd3, 0x83, 0xc9, 0x17, 0xc4, 0x90, 0xbd, 0x75, 0x70, 0x77, 0xb3, 0xca, 0x5d, 0x7e, 0x1e, - 0xd5, 0x71, 0x47, 0xfb, 0xba, 0x43, 0xcc, 0xe9, 0x6f, 0x30, 0x42, 0xd6, 0x3b, 0xbf, 0x08, 0xb9, - 0x20, 0xcf, 0x44, 0xab, 0x90, 0x7d, 0xda, 0xc1, 0x8f, 0x9b, 0x58, 0x99, 0x13, 0x3e, 0x0c, 0x38, - 0x4f, 0x45, 0x85, 0x50, 0x86, 0xf9, 0xed, 0x6a, 0xbb, 0xfa, 0xa8, 0x89, 0x83, 0x0b, 0xef, 0x00, - 0x20, 0x93, 0xa5, 0x92, 0x22, 0x3b, 0x08, 0x75, 0xd6, 0x56, 0xbe, 0xfa, 0x7a, 0x75, 0xee, 0xa7, - 0x5f, 0xaf, 0xce, 0x3d, 0x3f, 0x5b, 0x4d, 0x7c, 0x75, 0xb6, 0x9a, 0xf8, 0xc9, 0xd9, 0x6a, 0xe2, - 0x5f, 0xcf, 0x56, 0x13, 0xbb, 0x59, 0x1e, 0xd2, 0xef, 0xfd, 0x6f, 0x00, 0x00, 0x00, 0xff, 0xff, - 0xdb, 0x9d, 0xe2, 0x3d, 0xd2, 0x2f, 0x00, 0x00, + 0xc6, 0x11, 0x71, 0x2b, 0xde, 0x89, 0xee, 0x0e, 0x8f, 0x2c, 0xbf, 0x72, 0x7c, 0xaf, 0xb4, 0x39, + 0xa0, 0x74, 0x60, 0x93, 0x77, 0x39, 0x62, 0x7f, 0x7c, 0xf0, 0xae, 0x6f, 0x0d, 0x89, 0xe7, 0xeb, + 0xc3, 0x91, 0x10, 0x2a, 0x6d, 0xcc, 0x03, 0xcc, 0xb1, 0xab, 0xfb, 0x16, 0x75, 0x24, 0x7f, 0x6d, + 0x40, 0x07, 0x94, 0x7f, 0xbe, 0xcb, 0xbe, 0x04, 0x55, 0xdd, 0x84, 0xc5, 0x27, 0xc4, 0xf5, 0x2c, + 0xea, 0xa0, 0x35, 0xc8, 0x58, 0x8e, 0x49, 0x9e, 0xad, 0x27, 0xca, 0x89, 0xb7, 0xd2, 0x58, 0x34, + 0xd4, 0xbb, 0x00, 0x2d, 0xf6, 0xd1, 0x74, 0x7c, 0x77, 0x82, 0x14, 0x48, 0x1d, 0x91, 0x09, 0x47, + 0xe4, 0x31, 0xfb, 0x64, 0x94, 0x63, 0xdd, 0x5e, 0x4f, 0x0a, 0xca, 0xb1, 0x6e, 0xab, 0x5f, 0x26, + 0xa0, 0x50, 0x75, 0x1c, 0xea, 0xf3, 0xde, 0x3d, 0x84, 0x20, 0xed, 0xe8, 0x43, 0x22, 0x85, 0xf8, + 0x37, 0xaa, 0x43, 0xd6, 0xd6, 0xf7, 0x89, 0xed, 0xad, 0x27, 0xcb, 0xa9, 0xb7, 0x0a, 0xf7, 0xbf, + 0x53, 0x79, 0x71, 0xc8, 0x95, 0x88, 0x92, 0xca, 0x0e, 0x47, 0x73, 0x23, 0xb0, 0x14, 0x45, 0x1f, + 0xc1, 0xa2, 0xe5, 0x98, 0x96, 0x41, 0xbc, 0xf5, 0x34, 0xd7, 0xb2, 0x11, 0xa7, 0x65, 0x6a, 0x7d, + 0x2d, 0xfd, 0xc5, 0xf9, 0xe6, 0x02, 0x0e, 0x84, 0x4a, 0xef, 0x41, 0x21, 0xa2, 0x36, 0x66, 0x6c, + 0x6b, 0x90, 0x39, 0xd6, 0xed, 0x31, 0x91, 0xa3, 0x13, 0x8d, 0xf7, 0x93, 0x0f, 0x13, 0xea, 0x27, + 0xb0, 0xd6, 0xd6, 0x87, 0xc4, 0x7c, 0x44, 0x1c, 0xe2, 0x5a, 0x06, 0x26, 0x1e, 0x1d, 0xbb, 0x06, + 0x61, 0x63, 0x3d, 0xb2, 0x1c, 0x33, 0x18, 0x2b, 0xfb, 0x8e, 0xd7, 0xa2, 0xd6, 0xe1, 0x95, 0x86, + 0xe5, 0x19, 0x2e, 0xf1, 0xc9, 0x57, 0x56, 0x92, 0x0a, 0x94, 0x9c, 0x27, 0x60, 0x65, 0x5e, 0xfa, + 0x17, 0xe0, 0x06, 0x73, 0xb1, 0xa9, 0xb9, 0x92, 0xa2, 0x79, 0x23, 0x62, 0x70, 0x65, 0x85, 0xfb, + 0x6f, 0xc5, 0x79, 0x28, 0x6e, 0x24, 0xdb, 0x0b, 0x78, 0x95, 0xab, 0x09, 0x08, 0xbd, 0x11, 0x31, + 0x90, 0x01, 0x37, 0x4d, 0x69, 0xf4, 0x9c, 0xfa, 0x24, 0x57, 0x1f, 0x3b, 0x8d, 0x97, 0x0c, 0x73, + 0x7b, 0x01, 0xaf, 0x05, 0xca, 0xa2, 0x9d, 0xd4, 0x00, 0x72, 0x81, 0x6e, 0xf5, 0xc7, 0x09, 0xc8, + 0x07, 0x4c, 0x0f, 0x7d, 0x1b, 0xf2, 0x8e, 0xee, 0x50, 0xcd, 0x18, 0x8d, 0x3d, 0x3e, 0xa0, 0x54, + 0xad, 0x78, 0x71, 0xbe, 0x99, 0x6b, 0xeb, 0x0e, 0xad, 0x77, 0xf7, 0x3c, 0x9c, 0x63, 0xec, 0xfa, + 0x68, 0xec, 0xa1, 0xd7, 0xa0, 0x38, 0x24, 0x43, 0xea, 0x4e, 0xb4, 0xfd, 0x89, 0x4f, 0x3c, 0xe9, + 0xb6, 0x82, 0xa0, 0xd5, 0x18, 0x09, 0x7d, 0x08, 0x8b, 0x03, 0x61, 0xd2, 0x7a, 0x8a, 0x2f, 0x9f, + 0xd7, 0xe3, 0xac, 0x9f, 0xb3, 0x1a, 0x07, 0x32, 0xea, 0xef, 0x24, 0x60, 0x2d, 0xa4, 0x92, 0x5f, + 0x1e, 0x5b, 0x2e, 0x19, 0x12, 0xc7, 0xf7, 0xd0, 0xf7, 0x20, 0x6b, 0x5b, 0x43, 0xcb, 0xf7, 0xa4, + 0xcf, 0x5f, 0x8d, 0x53, 0x1b, 0x0e, 0x0a, 0x4b, 0x30, 0xaa, 0x42, 0xd1, 0x25, 0x1e, 0x71, 0x8f, + 0xc5, 0x8a, 0x97, 0x1e, 0xbd, 0x46, 0x78, 0x46, 0x44, 0xdd, 0x82, 0x5c, 0xd7, 0xd6, 0xfd, 0x03, + 0xea, 0x0e, 0x91, 0x0a, 0x45, 0xdd, 0x35, 0x0e, 0x2d, 0x9f, 0x18, 0xfe, 0xd8, 0x0d, 0x76, 0xdf, + 0x0c, 0x0d, 0xdd, 0x84, 0x24, 0x15, 0x1d, 0xe5, 0x6b, 0xd9, 0x8b, 0xf3, 0xcd, 0x64, 0xa7, 0x87, + 0x93, 0xd4, 0x53, 0x3f, 0x80, 0xd5, 0xae, 0x3d, 0x1e, 0x58, 0x4e, 0x83, 0x78, 0x86, 0x6b, 0x8d, + 0x98, 0x76, 0xb6, 0x2a, 0x59, 0x8c, 0x0a, 0x56, 0x25, 0xfb, 0x0e, 0xb7, 0x76, 0x72, 0xba, 0xb5, + 0xd5, 0xdf, 0x4a, 0xc2, 0x6a, 0xd3, 0x19, 0x58, 0x0e, 0x89, 0x4a, 0xdf, 0x81, 0x65, 0xc2, 0x89, + 0xda, 0xb1, 0x08, 0x37, 0x52, 0xcf, 0x92, 0xa0, 0x06, 0x31, 0xa8, 0x35, 0x17, 0x17, 0xee, 0xc5, + 0x0d, 0xff, 0x05, 0xed, 0xb1, 0xd1, 0xa1, 0x09, 0x8b, 0x23, 0x3e, 0x08, 0x4f, 0x4e, 0xef, 0x9d, + 0x38, 0x5d, 0x2f, 0x8c, 0x33, 0x08, 0x12, 0x52, 0xf6, 0xeb, 0x04, 0x89, 0x3f, 0x4e, 0xc2, 0x4a, + 0x9b, 0x9a, 0x33, 0x7e, 0x28, 0x41, 0xee, 0x90, 0x7a, 0x7e, 0x24, 0x20, 0x86, 0x6d, 0xf4, 0x10, + 0x72, 0x23, 0x39, 0x7d, 0x72, 0xf6, 0x6f, 0xc7, 0x9b, 0x2c, 0x30, 0x38, 0x44, 0xa3, 0x0f, 0x20, + 0x1f, 0x6c, 0x19, 0x36, 0xda, 0x97, 0x58, 0x38, 0x53, 0x3c, 0xfa, 0x10, 0xb2, 0x62, 0x12, 0xd6, + 0xd3, 0x5c, 0xf2, 0xce, 0x4b, 0xf9, 0x1c, 0x4b, 0x21, 0xf4, 0x08, 0x72, 0xbe, 0xed, 0x69, 0x96, + 0x73, 0x40, 0xd7, 0x33, 0x5c, 0xc1, 0x66, 0x6c, 0x90, 0xa1, 0x26, 0xe9, 0xef, 0xf4, 0x5a, 0xce, + 0x01, 0xad, 0x15, 0x2e, 0xce, 0x37, 0x17, 0x65, 0x03, 0x2f, 0xfa, 0xb6, 0xc7, 0x3e, 0xd4, 0xdf, + 0x4d, 0x40, 0x21, 0x82, 0x42, 0xaf, 0x02, 0xf8, 0xee, 0xd8, 0xf3, 0x35, 0x97, 0x52, 0x9f, 0x3b, + 0xab, 0x88, 0xf3, 0x9c, 0x82, 0x29, 0xf5, 0x51, 0x05, 0x6e, 0x18, 0xc4, 0xf5, 0x35, 0xcb, 0xf3, + 0xc6, 0xc4, 0xd5, 0xbc, 0xf1, 0xfe, 0x67, 0xc4, 0xf0, 0xb9, 0xe3, 0x8a, 0x78, 0x95, 0xb1, 0x5a, + 0x9c, 0xd3, 0x13, 0x0c, 0xf4, 0x00, 0x6e, 0x46, 0xf1, 0xa3, 0xf1, 0xbe, 0x6d, 0x19, 0x1a, 0x9b, + 0xcc, 0x14, 0x17, 0xb9, 0x31, 0x15, 0xe9, 0x72, 0xde, 0x63, 0x32, 0x51, 0x7f, 0x9a, 0x00, 0x05, + 0xeb, 0x07, 0xfe, 0x2e, 0x19, 0xee, 0x13, 0xb7, 0xe7, 0xeb, 0xfe, 0xd8, 0x43, 0x37, 0x21, 0x6b, + 0x13, 0xdd, 0x24, 0x2e, 0x37, 0x2a, 0x87, 0x65, 0x0b, 0xed, 0xb1, 0x1d, 0xac, 0x1b, 0x87, 0xfa, + 0xbe, 0x65, 0x5b, 0xfe, 0x84, 0x9b, 0xb2, 0x1c, 0xbf, 0x84, 0xe7, 0x75, 0x56, 0x70, 0x44, 0x10, + 0xcf, 0xa8, 0x41, 0xeb, 0xb0, 0x38, 0x24, 0x9e, 0xa7, 0x0f, 0x08, 0xb7, 0x34, 0x8f, 0x83, 0xa6, + 0xfa, 0x01, 0x14, 0xa3, 0x72, 0xa8, 0x00, 0x8b, 0x7b, 0xed, 0xc7, 0xed, 0xce, 0xd3, 0xb6, 0xb2, + 0x80, 0x56, 0xa0, 0xb0, 0xd7, 0xc6, 0xcd, 0x6a, 0x7d, 0xbb, 0x5a, 0xdb, 0x69, 0x2a, 0x09, 0xb4, + 0x04, 0xf9, 0x69, 0x33, 0xa9, 0xfe, 0x69, 0x02, 0x80, 0xb9, 0x5b, 0x0e, 0xea, 0x7d, 0xc8, 0x78, + 0xbe, 0xee, 0x8b, 0x55, 0xb9, 0x7c, 0xff, 0x8d, 0xcb, 0xe6, 0x50, 0xda, 0xcb, 0xfe, 0x11, 0x2c, + 0x44, 0xa2, 0x16, 0x26, 0x67, 0x2c, 0x64, 0x01, 0x42, 0x37, 0x4d, 0x57, 0x1a, 0xce, 0xbf, 0xd5, + 0x0f, 0x20, 0xc3, 0xa5, 0x67, 0xcd, 0xcd, 0x41, 0xba, 0xc1, 0xbe, 0x12, 0x28, 0x0f, 0x19, 0xdc, + 0xac, 0x36, 0x3e, 0x55, 0x92, 0x48, 0x81, 0x62, 0xa3, 0xd5, 0xab, 0x77, 0xda, 0xed, 0x66, 0xbd, + 0xdf, 0x6c, 0x28, 0x29, 0xf5, 0x0e, 0x64, 0x5a, 0x43, 0xa6, 0xf9, 0x36, 0x5b, 0xf2, 0x07, 0xc4, + 0x25, 0x8e, 0x11, 0xec, 0xa4, 0x29, 0x41, 0xfd, 0x49, 0x1e, 0x32, 0xbb, 0x74, 0xec, 0xf8, 0xe8, + 0x7e, 0x24, 0x6c, 0x2d, 0xc7, 0x67, 0x08, 0x1c, 0x58, 0xe9, 0x4f, 0x46, 0x44, 0x86, 0xb5, 0x9b, + 0x90, 0x15, 0x9b, 0x43, 0x0e, 0x47, 0xb6, 0x18, 0xdd, 0xd7, 0xdd, 0x01, 0xf1, 0xe5, 0x78, 0x64, + 0x0b, 0xbd, 0xc5, 0x4e, 0x2c, 0xdd, 0xa4, 0x8e, 0x3d, 0xe1, 0x7b, 0x28, 0x27, 0x8e, 0x25, 0x4c, + 0x74, 0xb3, 0xe3, 0xd8, 0x13, 0x1c, 0x72, 0xd1, 0x36, 0x14, 0xf7, 0x2d, 0xc7, 0xd4, 0xe8, 0x48, + 0x04, 0xf9, 0xcc, 0xe5, 0x3b, 0x4e, 0x58, 0x55, 0xb3, 0x1c, 0xb3, 0x23, 0xc0, 0xb8, 0xb0, 0x3f, + 0x6d, 0xa0, 0x36, 0x2c, 0x1f, 0x53, 0x7b, 0x3c, 0x24, 0xa1, 0xae, 0x2c, 0xd7, 0xf5, 0xe6, 0xe5, + 0xba, 0x9e, 0x70, 0x7c, 0xa0, 0x6d, 0xe9, 0x38, 0xda, 0x44, 0x8f, 0x61, 0xc9, 0x1f, 0x8e, 0x0e, + 0xbc, 0x50, 0xdd, 0x22, 0x57, 0xf7, 0xad, 0x2b, 0x1c, 0xc6, 0xe0, 0x81, 0xb6, 0xa2, 0x1f, 0x69, + 0x95, 0x7e, 0x23, 0x05, 0x85, 0x88, 0xe5, 0xa8, 0x07, 0x85, 0x91, 0x4b, 0x47, 0xfa, 0x80, 0x1f, + 0x54, 0x72, 0x2e, 0xee, 0xbd, 0xd4, 0xa8, 0x2b, 0xdd, 0xa9, 0x20, 0x8e, 0x6a, 0x51, 0xcf, 0x92, + 0x50, 0x88, 0x30, 0xd1, 0xdb, 0x90, 0xc3, 0x5d, 0xdc, 0x7a, 0x52, 0xed, 0x37, 0x95, 0x85, 0xd2, + 0xed, 0xd3, 0xb3, 0xf2, 0x3a, 0xd7, 0x16, 0x55, 0xd0, 0x75, 0xad, 0x63, 0xb6, 0xf4, 0xde, 0x82, + 0xc5, 0x00, 0x9a, 0x28, 0x7d, 0xf3, 0xf4, 0xac, 0xfc, 0xca, 0x3c, 0x34, 0x82, 0xc4, 0xbd, 0xed, + 0x2a, 0x6e, 0x36, 0x94, 0x64, 0x3c, 0x12, 0xf7, 0x0e, 0x75, 0x97, 0x98, 0xe8, 0x5b, 0x90, 0x95, + 0xc0, 0x54, 0xa9, 0x74, 0x7a, 0x56, 0xbe, 0x39, 0x0f, 0x9c, 0xe2, 0x70, 0x6f, 0xa7, 0xfa, 0xa4, + 0xa9, 0xa4, 0xe3, 0x71, 0xb8, 0x67, 0xeb, 0xc7, 0x04, 0xbd, 0x01, 0x19, 0x01, 0xcb, 0x94, 0x6e, + 0x9d, 0x9e, 0x95, 0xbf, 0xf1, 0x82, 0x3a, 0x86, 0x2a, 0xad, 0xff, 0xf6, 0x1f, 0x6c, 0x2c, 0xfc, + 0xe5, 0x1f, 0x6e, 0x28, 0xf3, 0xec, 0xd2, 0x7f, 0x27, 0x60, 0x69, 0x66, 0xca, 0x91, 0x0a, 0x59, + 0x87, 0x1a, 0x74, 0x24, 0xce, 0xaf, 0x5c, 0x0d, 0x2e, 0xce, 0x37, 0xb3, 0x6d, 0x5a, 0xa7, 0xa3, + 0x09, 0x96, 0x1c, 0xf4, 0x78, 0xee, 0x04, 0x7e, 0xf0, 0x92, 0xeb, 0x29, 0xf6, 0x0c, 0xfe, 0x18, + 0x96, 0x4c, 0xd7, 0x3a, 0x26, 0xae, 0x66, 0x50, 0xe7, 0xc0, 0x1a, 0xc8, 0xb3, 0xa9, 0x14, 0x9b, + 0x26, 0x72, 0x20, 0x2e, 0x0a, 0x81, 0x3a, 0xc7, 0x7f, 0x8d, 0xd3, 0xb7, 0xf4, 0x04, 0x8a, 0xd1, + 0x15, 0xca, 0x8e, 0x13, 0xcf, 0xfa, 0x15, 0x22, 0xf3, 0x41, 0x9e, 0x3d, 0xe2, 0x3c, 0xa3, 0x88, + 0x6c, 0xf0, 0x4d, 0x48, 0x0f, 0xa9, 0x29, 0xf4, 0x2c, 0xd5, 0x6e, 0xb0, 0x24, 0xe0, 0x9f, 0xce, + 0x37, 0x0b, 0xd4, 0xab, 0x6c, 0x59, 0x36, 0xd9, 0xa5, 0x26, 0xc1, 0x1c, 0xa0, 0x1e, 0x43, 0x9a, + 0x85, 0x0a, 0xf4, 0x4d, 0x48, 0xd7, 0x5a, 0xed, 0x86, 0xb2, 0x50, 0x5a, 0x3d, 0x3d, 0x2b, 0x2f, + 0x71, 0x97, 0x30, 0x06, 0x5b, 0xbb, 0x68, 0x13, 0xb2, 0x4f, 0x3a, 0x3b, 0x7b, 0xbb, 0x6c, 0x79, + 0xdd, 0x38, 0x3d, 0x2b, 0xaf, 0x84, 0x6c, 0xe1, 0x34, 0xf4, 0x2a, 0x64, 0xfa, 0xbb, 0xdd, 0xad, + 0x9e, 0x92, 0x2c, 0xa1, 0xd3, 0xb3, 0xf2, 0x72, 0xc8, 0xe7, 0x36, 0x97, 0x56, 0xe5, 0xac, 0xe6, + 0x43, 0xba, 0xfa, 0xb3, 0x24, 0x2c, 0x61, 0x56, 0xf1, 0xb9, 0x7e, 0x97, 0xda, 0x96, 0x31, 0x41, + 0x5d, 0xc8, 0x1b, 0xd4, 0x31, 0xad, 0xc8, 0x9e, 0xba, 0x7f, 0xc9, 0xa9, 0x3f, 0x95, 0x0a, 0x5a, + 0xf5, 0x40, 0x12, 0x4f, 0x95, 0xa0, 0x77, 0x21, 0x63, 0x12, 0x5b, 0x9f, 0xc8, 0xf4, 0xe3, 0x56, + 0x45, 0xd4, 0x94, 0x95, 0xa0, 0xa6, 0xac, 0x34, 0x64, 0x4d, 0x89, 0x05, 0x8e, 0xa7, 0xd9, 0xfa, + 0x33, 0x4d, 0xf7, 0x7d, 0x32, 0x1c, 0xf9, 0x22, 0xf7, 0x48, 0xe3, 0xc2, 0x50, 0x7f, 0x56, 0x95, + 0x24, 0x74, 0x0f, 0xb2, 0x27, 0x96, 0x63, 0xd2, 0x13, 0x99, 0x5e, 0x5c, 0xa1, 0x54, 0x02, 0xd5, + 0x53, 0x76, 0xea, 0xce, 0x99, 0xc9, 0xfc, 0xdd, 0xee, 0xb4, 0x9b, 0x81, 0xbf, 0x25, 0xbf, 0xe3, + 0xb4, 0xa9, 0xc3, 0xf6, 0x0a, 0x74, 0xda, 0xda, 0x56, 0xb5, 0xb5, 0xb3, 0x87, 0x99, 0xcf, 0xd7, + 0x4e, 0xcf, 0xca, 0x4a, 0x08, 0xd9, 0xd2, 0x2d, 0x9b, 0xe5, 0xbb, 0xb7, 0x20, 0x55, 0x6d, 0x7f, + 0xaa, 0x24, 0x4b, 0xca, 0xe9, 0x59, 0xb9, 0x18, 0xb2, 0xab, 0xce, 0x64, 0xba, 0x8d, 0xe6, 0xfb, + 0x55, 0xff, 0x36, 0x05, 0xc5, 0xbd, 0x91, 0xa9, 0xfb, 0x44, 0xac, 0x49, 0x54, 0x86, 0xc2, 0x48, + 0x77, 0x75, 0xdb, 0x26, 0xb6, 0xe5, 0x0d, 0x65, 0xb5, 0x1c, 0x25, 0xa1, 0xf7, 0x5e, 0xd6, 0x8d, + 0xb5, 0x1c, 0x5b, 0x67, 0x3f, 0xfe, 0x97, 0xcd, 0x44, 0xe0, 0xd0, 0x3d, 0x58, 0x3e, 0x10, 0xd6, + 0x6a, 0xba, 0xc1, 0x27, 0x36, 0xc5, 0x27, 0xb6, 0x12, 0x37, 0xb1, 0x51, 0xb3, 0x2a, 0x72, 0x90, + 0x55, 0x2e, 0x85, 0x97, 0x0e, 0xa2, 0x4d, 0xf4, 0x00, 0x16, 0x87, 0xd4, 0xb1, 0x7c, 0xea, 0x5e, + 0x3f, 0x0b, 0x01, 0x12, 0xbd, 0x0d, 0xab, 0x6c, 0x72, 0x03, 0x7b, 0x38, 0x9b, 0x9f, 0x58, 0x49, + 0xbc, 0x32, 0xd4, 0x9f, 0xc9, 0x0e, 0x31, 0x23, 0xa3, 0x1a, 0x64, 0xa8, 0xcb, 0x52, 0xa2, 0x2c, + 0x37, 0xf7, 0x9d, 0x6b, 0xcd, 0x15, 0x8d, 0x0e, 0x93, 0xc1, 0x42, 0x54, 0xfd, 0x3e, 0x2c, 0xcd, + 0x0c, 0x82, 0x65, 0x02, 0xdd, 0xea, 0x5e, 0xaf, 0xa9, 0x2c, 0xa0, 0x22, 0xe4, 0xea, 0x9d, 0x76, + 0xbf, 0xd5, 0xde, 0x63, 0xa9, 0x4c, 0x11, 0x72, 0xb8, 0xb3, 0xb3, 0x53, 0xab, 0xd6, 0x1f, 0x2b, + 0x49, 0xb5, 0x02, 0x85, 0x88, 0x36, 0xb4, 0x0c, 0xd0, 0xeb, 0x77, 0xba, 0xda, 0x56, 0x0b, 0xf7, + 0xfa, 0x22, 0x11, 0xea, 0xf5, 0xab, 0xb8, 0x2f, 0x09, 0x09, 0xf5, 0x3f, 0x92, 0xc1, 0x8c, 0xca, + 0xdc, 0xa7, 0x36, 0x9b, 0xfb, 0x5c, 0x61, 0xbc, 0xcc, 0x7e, 0xa6, 0x8d, 0x30, 0x07, 0x7a, 0x0f, + 0x80, 0x2f, 0x1c, 0x62, 0x6a, 0xba, 0x2f, 0x27, 0xbe, 0xf4, 0x82, 0x93, 0xfb, 0xc1, 0xa5, 0x0d, + 0xce, 0x4b, 0x74, 0xd5, 0x47, 0x1f, 0x42, 0xd1, 0xa0, 0xc3, 0x91, 0x4d, 0xa4, 0x70, 0xea, 0x5a, + 0xe1, 0x42, 0x88, 0xaf, 0xfa, 0xd1, 0xec, 0x2b, 0x3d, 0x9b, 0x1f, 0xfe, 0x66, 0x22, 0xf0, 0x4c, + 0x4c, 0xc2, 0x55, 0x84, 0xdc, 0x5e, 0xb7, 0x51, 0xed, 0xb7, 0xda, 0x8f, 0x94, 0x04, 0x02, 0xc8, + 0x72, 0x57, 0x37, 0x94, 0x24, 0x4b, 0x14, 0xeb, 0x9d, 0xdd, 0xee, 0x4e, 0x93, 0xa7, 0x5c, 0x68, + 0x0d, 0x94, 0xc0, 0xd9, 0x1a, 0x77, 0x64, 0xb3, 0xa1, 0xa4, 0xd1, 0x0d, 0x58, 0x09, 0xa9, 0x52, + 0x32, 0x83, 0x6e, 0x02, 0x0a, 0x89, 0x53, 0x15, 0x59, 0xf5, 0xd7, 0x60, 0xa5, 0x4e, 0x1d, 0x5f, + 0xb7, 0x9c, 0x30, 0x89, 0xbe, 0xcf, 0x06, 0x2d, 0x49, 0x9a, 0x25, 0x2f, 0x3b, 0x6a, 0x2b, 0x17, + 0xe7, 0x9b, 0x85, 0x10, 0xda, 0x6a, 0xb0, 0x91, 0x06, 0x0d, 0x93, 0xed, 0xdf, 0x91, 0x65, 0x72, + 0xe7, 0x66, 0x6a, 0x8b, 0x17, 0xe7, 0x9b, 0xa9, 0x6e, 0xab, 0x81, 0x19, 0x0d, 0x7d, 0x13, 0xf2, + 0xe4, 0x99, 0xe5, 0x6b, 0x06, 0x8b, 0xe1, 0xcc, 0x81, 0x19, 0x9c, 0x63, 0x84, 0x3a, 0x0b, 0xd9, + 0x35, 0x80, 0x2e, 0x75, 0x7d, 0xd9, 0xf3, 0x77, 0x21, 0x33, 0xa2, 0x2e, 0x2f, 0xcf, 0x2f, 0xbd, + 0x34, 0x62, 0x70, 0xb1, 0x50, 0xb1, 0x00, 0xab, 0x7f, 0x95, 0x04, 0xe8, 0xeb, 0xde, 0x91, 0x54, + 0xf2, 0x10, 0xf2, 0xe1, 0x05, 0x9c, 0xac, 0xf3, 0xaf, 0x9c, 0xed, 0x10, 0x8c, 0x1e, 0x04, 0x8b, + 0x4d, 0x94, 0x07, 0xb1, 0x75, 0x5a, 0xd0, 0x51, 0x5c, 0x86, 0x3d, 0x5b, 0x03, 0xb0, 0x23, 0x91, + 0xb8, 0xae, 0x9c, 0x79, 0xf6, 0x89, 0xea, 0xfc, 0x58, 0x10, 0x4e, 0x93, 0x09, 0x66, 0xec, 0xcd, + 0xc6, 0xdc, 0x8c, 0x6c, 0x2f, 0xe0, 0xa9, 0x1c, 0xfa, 0x18, 0x0a, 0x6c, 0xdc, 0x9a, 0xc7, 0x79, + 0x32, 0xb7, 0xbc, 0xd4, 0x55, 0x42, 0x03, 0x86, 0x51, 0xf8, 0x5d, 0x53, 0x60, 0xd9, 0x1d, 0x3b, + 0x6c, 0xd8, 0x52, 0x87, 0xfa, 0x27, 0x49, 0x78, 0xa5, 0x4d, 0xfc, 0x13, 0xea, 0x1e, 0x55, 0x7d, + 0x5f, 0x37, 0x0e, 0x87, 0xc4, 0x91, 0x4e, 0x8e, 0x64, 0xd6, 0x89, 0x99, 0xcc, 0x7a, 0x1d, 0x16, + 0x75, 0xdb, 0xd2, 0x3d, 0x22, 0xd2, 0x91, 0x3c, 0x0e, 0x9a, 0x2c, 0xff, 0x67, 0xd5, 0x04, 0xf1, + 0x3c, 0x22, 0x0a, 0xfc, 0x3c, 0x9e, 0x12, 0xd0, 0x8f, 0xe0, 0xa6, 0x4c, 0x3c, 0xf4, 0xb0, 0x2b, + 0x96, 0xd9, 0x06, 0x37, 0x85, 0xcd, 0xd8, 0xf2, 0x26, 0xde, 0x38, 0x99, 0x99, 0x4c, 0xc9, 0x9d, + 0x91, 0x2f, 0xf3, 0x9c, 0x35, 0x33, 0x86, 0x55, 0x7a, 0x04, 0xb7, 0x2e, 0x15, 0xf9, 0x4a, 0x17, + 0x08, 0xff, 0x90, 0x04, 0x68, 0x75, 0xab, 0xbb, 0xd2, 0x49, 0x0d, 0xc8, 0x1e, 0xe8, 0x43, 0xcb, + 0x9e, 0x5c, 0x15, 0xa7, 0xa6, 0xf8, 0x4a, 0x55, 0xb8, 0x63, 0x8b, 0xcb, 0x60, 0x29, 0xcb, 0x8b, + 0x9b, 0xf1, 0xbe, 0x43, 0xfc, 0xb0, 0xb8, 0xe1, 0x2d, 0x66, 0x86, 0xab, 0x3b, 0xe1, 0x02, 0x13, + 0x0d, 0x36, 0x01, 0x03, 0xdd, 0x27, 0x27, 0xfa, 0x24, 0x08, 0x2e, 0xb2, 0x89, 0xb6, 0xf9, 0x35, + 0x1d, 0x71, 0x8f, 0x89, 0xb9, 0x9e, 0xe1, 0x4e, 0xbd, 0xce, 0x1e, 0x2c, 0xe1, 0xc2, 0x77, 0xa1, + 0x74, 0xe9, 0x03, 0x9e, 0xd8, 0x4c, 0x59, 0x5f, 0xc9, 0x47, 0x77, 0x61, 0x69, 0x66, 0x9c, 0x2f, + 0x54, 0x95, 0xad, 0xee, 0x93, 0xef, 0x2a, 0x69, 0xf9, 0xf5, 0x7d, 0x25, 0xab, 0xfe, 0x51, 0x4a, + 0x84, 0x03, 0xe9, 0xd5, 0xf8, 0xeb, 0xe9, 0x1c, 0xdf, 0xc4, 0x06, 0xb5, 0xe5, 0x36, 0x7d, 0xf3, + 0xea, 0x28, 0xc1, 0xaa, 0x14, 0x0e, 0xc7, 0xa1, 0x20, 0xda, 0x84, 0x82, 0x58, 0xc5, 0x1a, 0xdb, + 0x16, 0xdc, 0xad, 0x4b, 0x18, 0x04, 0x89, 0x49, 0xa2, 0x3b, 0xb0, 0xcc, 0x6f, 0x21, 0xbc, 0x43, + 0x62, 0x0a, 0x4c, 0x9a, 0x63, 0x96, 0x42, 0x2a, 0x87, 0xed, 0x42, 0x51, 0x12, 0x34, 0x9e, 0xa1, + 0x66, 0xb8, 0x41, 0x6f, 0x5f, 0x67, 0x90, 0x10, 0xe1, 0x89, 0x6b, 0x61, 0x34, 0x6d, 0xa8, 0x0d, + 0xc8, 0x05, 0xc6, 0xa2, 0x75, 0x48, 0xf5, 0xeb, 0x5d, 0x65, 0xa1, 0xb4, 0x72, 0x7a, 0x56, 0x2e, + 0x04, 0xe4, 0x7e, 0xbd, 0xcb, 0x38, 0x7b, 0x8d, 0xae, 0x92, 0x98, 0xe5, 0xec, 0x35, 0xba, 0xa5, + 0x34, 0xcb, 0x94, 0xd4, 0x03, 0x28, 0x44, 0x7a, 0x40, 0xaf, 0xc3, 0x62, 0xab, 0xfd, 0x08, 0x37, + 0x7b, 0x3d, 0x65, 0xa1, 0x74, 0xf3, 0xf4, 0xac, 0x8c, 0x22, 0xdc, 0x96, 0x33, 0x60, 0xf3, 0x83, + 0x5e, 0x85, 0xf4, 0x76, 0x87, 0x9d, 0xc0, 0x22, 0x25, 0x8e, 0x20, 0xb6, 0xa9, 0xe7, 0x97, 0x6e, + 0xc8, 0x14, 0x2c, 0xaa, 0x58, 0xfd, 0xbd, 0x04, 0x64, 0xc5, 0x66, 0x8a, 0x9d, 0xa8, 0x2a, 0x2c, + 0x06, 0xf5, 0xaa, 0x28, 0x57, 0xde, 0xbc, 0xbc, 0xb4, 0xa8, 0xc8, 0x4a, 0x40, 0x2c, 0xbf, 0x40, + 0xae, 0xf4, 0x3e, 0x14, 0xa3, 0x8c, 0xaf, 0xb4, 0xf8, 0x7e, 0x04, 0x05, 0xb6, 0xbe, 0x83, 0x12, + 0xe3, 0x3e, 0x64, 0x45, 0x40, 0x08, 0x4f, 0x84, 0xcb, 0xeb, 0x1c, 0x89, 0x44, 0x0f, 0x61, 0x51, + 0xd4, 0x46, 0xc1, 0x35, 0xe5, 0xc6, 0xd5, 0xbb, 0x08, 0x07, 0x70, 0xf5, 0x63, 0x48, 0x77, 0x09, + 0x71, 0x99, 0xef, 0x1d, 0x6a, 0x92, 0xe9, 0x21, 0x2a, 0xcb, 0x3a, 0x93, 0xb4, 0x1a, 0xac, 0xac, + 0x33, 0x49, 0xcb, 0x0c, 0x2f, 0x62, 0x92, 0x91, 0x8b, 0x98, 0x3e, 0x14, 0x9f, 0x12, 0x6b, 0x70, + 0xe8, 0x13, 0x93, 0x2b, 0x7a, 0x07, 0xd2, 0x23, 0x12, 0x1a, 0xbf, 0x1e, 0xbb, 0xc0, 0x08, 0x71, + 0x31, 0x47, 0xb1, 0x38, 0x72, 0xc2, 0xa5, 0xe5, 0xdd, 0xba, 0x6c, 0xa9, 0x7f, 0x9f, 0x84, 0xe5, + 0x96, 0xe7, 0x8d, 0x75, 0xc7, 0x08, 0xf2, 0xab, 0x8f, 0x66, 0xf3, 0xab, 0xd8, 0x47, 0x88, 0x59, + 0x91, 0xd9, 0xfb, 0x25, 0x79, 0xc6, 0x25, 0xc3, 0x33, 0x4e, 0xfd, 0xf7, 0x44, 0x70, 0x89, 0x74, + 0x27, 0xb2, 0xdd, 0x4b, 0xeb, 0xa7, 0x67, 0xe5, 0xb5, 0xa8, 0x26, 0xb2, 0xe7, 0x1c, 0x39, 0xf4, + 0xc4, 0x41, 0xaf, 0x41, 0x06, 0x37, 0xdb, 0xcd, 0xa7, 0x4a, 0x42, 0x2c, 0xcf, 0x19, 0x10, 0x26, + 0x0e, 0x39, 0x61, 0x9a, 0xba, 0xcd, 0x76, 0x83, 0xe5, 0x43, 0xc9, 0x18, 0x4d, 0x5d, 0xe2, 0x98, + 0x96, 0x33, 0x40, 0xaf, 0x43, 0xb6, 0xd5, 0xeb, 0xed, 0xf1, 0x32, 0xff, 0x95, 0xd3, 0xb3, 0xf2, + 0x8d, 0x19, 0x14, 0xbf, 0x40, 0x34, 0x19, 0x88, 0x15, 0x23, 0x2c, 0x53, 0x8a, 0x01, 0xb1, 0x2c, + 0x57, 0x80, 0x70, 0xa7, 0x5f, 0xed, 0xb3, 0x0a, 0xff, 0x45, 0x10, 0xa6, 0xec, 0xaf, 0xdc, 0x6e, + 0xff, 0x9c, 0x04, 0xa5, 0x6a, 0x18, 0x64, 0xe4, 0x33, 0xbe, 0xac, 0xff, 0xfa, 0x90, 0x1b, 0xb1, + 0x2f, 0x8b, 0x04, 0xb9, 0xcc, 0xc3, 0xd8, 0x67, 0xb4, 0x39, 0xb9, 0x0a, 0xa6, 0x36, 0xa9, 0x9a, + 0x43, 0xcb, 0xf3, 0x2c, 0xea, 0x08, 0x1a, 0x0e, 0x35, 0x95, 0xfe, 0x33, 0x01, 0x37, 0x62, 0x10, + 0xe8, 0x2e, 0xa4, 0x5d, 0x6a, 0x07, 0x73, 0x78, 0xfb, 0xb2, 0xfb, 0x41, 0x26, 0x8a, 0x39, 0x12, + 0x6d, 0x00, 0xe8, 0x63, 0x9f, 0xea, 0xbc, 0x7f, 0x3e, 0x7b, 0x39, 0x1c, 0xa1, 0xa0, 0xa7, 0x90, + 0xf5, 0x88, 0xe1, 0x92, 0x20, 0xe3, 0xfd, 0xf8, 0xff, 0x6a, 0x7d, 0xa5, 0xc7, 0xd5, 0x60, 0xa9, + 0xae, 0x54, 0x81, 0xac, 0xa0, 0xb0, 0x65, 0x6f, 0xea, 0xbe, 0x2e, 0x6f, 0x8f, 0xf9, 0x37, 0x5b, + 0x4d, 0xba, 0x3d, 0x08, 0x56, 0x93, 0x6e, 0x0f, 0xd4, 0xbf, 0x49, 0x02, 0x34, 0x9f, 0xf9, 0xc4, + 0x75, 0x74, 0xbb, 0x5e, 0x45, 0xcd, 0x48, 0xf4, 0x17, 0xa3, 0xfd, 0x76, 0xec, 0x95, 0x78, 0x28, + 0x51, 0xa9, 0x57, 0x63, 0xe2, 0xff, 0x2d, 0x48, 0x8d, 0x5d, 0xf9, 0x32, 0x2a, 0xb2, 0xd5, 0x3d, + 0xbc, 0x83, 0x19, 0x0d, 0x35, 0xa7, 0x61, 0x2b, 0x75, 0xf9, 0xfb, 0x67, 0xa4, 0x83, 0xd8, 0xd0, + 0xc5, 0x76, 0xbe, 0xa1, 0x6b, 0x06, 0x91, 0x27, 0x47, 0x51, 0xec, 0xfc, 0x7a, 0xb5, 0x4e, 0x5c, + 0x1f, 0x67, 0x0d, 0x9d, 0xfd, 0xff, 0x5a, 0xf1, 0xed, 0x1d, 0x80, 0xe9, 0xd0, 0xd0, 0x06, 0x64, + 0xea, 0x5b, 0xbd, 0xde, 0x8e, 0xb2, 0x20, 0x02, 0xf8, 0x94, 0xc5, 0xc9, 0xea, 0x5f, 0x24, 0x21, + 0x57, 0xaf, 0xca, 0x63, 0xb5, 0x0e, 0x0a, 0x8f, 0x4a, 0xfc, 0xce, 0x9d, 0x3c, 0x1b, 0x59, 0xee, + 0x44, 0x06, 0x96, 0x2b, 0x4a, 0xcf, 0x65, 0x26, 0xc2, 0xac, 0x6e, 0x72, 0x01, 0x84, 0xa1, 0x48, + 0xa4, 0x13, 0x34, 0x43, 0x0f, 0x62, 0xfc, 0xc6, 0xd5, 0xce, 0x12, 0x45, 0xc4, 0xb4, 0xed, 0xe1, + 0x42, 0xa0, 0xa4, 0xae, 0x7b, 0xe8, 0x3d, 0x58, 0xf1, 0xac, 0x81, 0x63, 0x39, 0x03, 0x2d, 0x70, + 0x1e, 0x7f, 0x00, 0xa8, 0xad, 0x5e, 0x9c, 0x6f, 0x2e, 0xf5, 0x04, 0x4b, 0xfa, 0x70, 0x49, 0x22, + 0xeb, 0xdc, 0x95, 0xe8, 0xfb, 0xb0, 0x1c, 0x11, 0x65, 0x5e, 0x14, 0x6e, 0x57, 0x2e, 0xce, 0x37, + 0x8b, 0xa1, 0xe4, 0x63, 0x32, 0xc1, 0xc5, 0x50, 0xf0, 0x31, 0xe1, 0xb7, 0x24, 0x07, 0xd4, 0x35, + 0x88, 0xe6, 0xf2, 0x3d, 0xcd, 0x4f, 0xf0, 0x34, 0x2e, 0x70, 0x9a, 0xd8, 0xe6, 0xea, 0x13, 0xb8, + 0xd1, 0x71, 0x8d, 0x43, 0xe2, 0xf9, 0xc2, 0x15, 0xd2, 0x8b, 0x1f, 0xc3, 0x6d, 0x5f, 0xf7, 0x8e, + 0xb4, 0x43, 0xcb, 0xf3, 0xa9, 0x3b, 0xd1, 0x5c, 0xe2, 0x13, 0x87, 0xf1, 0x35, 0xfe, 0x6a, 0x28, + 0xaf, 0xb1, 0x6e, 0x31, 0xcc, 0xb6, 0x80, 0xe0, 0x00, 0xb1, 0xc3, 0x00, 0x6a, 0x0b, 0x8a, 0xac, + 0x98, 0x68, 0x90, 0x03, 0x7d, 0x6c, 0xfb, 0x6c, 0xf4, 0x60, 0xd3, 0x81, 0xf6, 0xd2, 0xc7, 0x54, + 0xde, 0xa6, 0x03, 0xf1, 0xa9, 0xfe, 0x10, 0x94, 0x86, 0xe5, 0x8d, 0x74, 0xdf, 0x38, 0x0c, 0xee, + 0xe7, 0x50, 0x03, 0x94, 0x43, 0xa2, 0xbb, 0xfe, 0x3e, 0xd1, 0x7d, 0x6d, 0x44, 0x5c, 0x8b, 0x9a, + 0xd7, 0xcf, 0xf2, 0x4a, 0x28, 0xd2, 0xe5, 0x12, 0xea, 0x7f, 0x25, 0x00, 0xb0, 0x7e, 0x10, 0x64, + 0x64, 0xdf, 0x81, 0x55, 0xcf, 0xd1, 0x47, 0xde, 0x21, 0xf5, 0x35, 0xcb, 0xf1, 0x89, 0x7b, 0xac, + 0xdb, 0xf2, 0x9a, 0x45, 0x09, 0x18, 0x2d, 0x49, 0x47, 0xef, 0x00, 0x3a, 0x22, 0x64, 0xa4, 0x51, + 0xdb, 0xd4, 0x02, 0xa6, 0x78, 0xd3, 0x4c, 0x63, 0x85, 0x71, 0x3a, 0xb6, 0xd9, 0x0b, 0xe8, 0xa8, + 0x06, 0x1b, 0x6c, 0xf8, 0xc4, 0xf1, 0x5d, 0x8b, 0x78, 0xda, 0x01, 0x75, 0x35, 0xcf, 0xa6, 0x27, + 0xda, 0x01, 0xb5, 0x6d, 0x7a, 0x42, 0xdc, 0xe0, 0x06, 0xab, 0x64, 0xd3, 0x41, 0x53, 0x80, 0xb6, + 0xa8, 0xdb, 0xb3, 0xe9, 0xc9, 0x56, 0x80, 0x60, 0x69, 0xdb, 0x74, 0xcc, 0xbe, 0x65, 0x1c, 0x05, + 0x69, 0x5b, 0x48, 0xed, 0x5b, 0xc6, 0x11, 0x7a, 0x1d, 0x96, 0x88, 0x4d, 0xf8, 0x45, 0x86, 0x40, + 0x65, 0x38, 0xaa, 0x18, 0x10, 0x19, 0x48, 0xfd, 0x04, 0x94, 0xa6, 0x63, 0xb8, 0x93, 0x51, 0x64, + 0xce, 0xdf, 0x01, 0xc4, 0x82, 0xa4, 0x66, 0x53, 0xe3, 0x48, 0x1b, 0xea, 0x8e, 0x3e, 0x60, 0x76, + 0x89, 0xa7, 0x26, 0x85, 0x71, 0x76, 0xa8, 0x71, 0xb4, 0x2b, 0xe9, 0xea, 0x7b, 0x00, 0xbd, 0x91, + 0x4b, 0x74, 0xb3, 0xc3, 0xb2, 0x09, 0xe6, 0x3a, 0xde, 0xd2, 0x4c, 0xf9, 0x54, 0x47, 0x5d, 0xb9, + 0xd5, 0x15, 0xc1, 0x68, 0x84, 0x74, 0xf5, 0x17, 0xe1, 0x46, 0xd7, 0xd6, 0x0d, 0xfe, 0x6c, 0xdd, + 0x0d, 0xdf, 0x4e, 0xd0, 0x43, 0xc8, 0x0a, 0xa8, 0x9c, 0xc9, 0xd8, 0xed, 0x36, 0xed, 0x73, 0x7b, + 0x01, 0x4b, 0x7c, 0xad, 0x08, 0x30, 0xd5, 0xa3, 0xfe, 0x59, 0x02, 0xf2, 0xa1, 0x7e, 0x54, 0x06, + 0x56, 0xca, 0xb3, 0xe5, 0x6d, 0x39, 0xb2, 0xf6, 0xce, 0xe3, 0x28, 0x09, 0xb5, 0xa0, 0x30, 0x0a, + 0xa5, 0xaf, 0xcc, 0xe7, 0x62, 0xac, 0xc6, 0x51, 0x59, 0xf4, 0x3e, 0xe4, 0x83, 0xb7, 0xd1, 0x20, + 0xc2, 0x5e, 0xfd, 0x94, 0x3a, 0x85, 0xab, 0x1f, 0x01, 0xfc, 0x80, 0x5a, 0x4e, 0x9f, 0x1e, 0x11, + 0x87, 0xbf, 0xf5, 0xb1, 0x9a, 0x90, 0x04, 0x5e, 0x94, 0x2d, 0x5e, 0x90, 0x8b, 0x29, 0x08, 0x9f, + 0xbc, 0x44, 0x53, 0xfd, 0xeb, 0x24, 0x64, 0x31, 0xa5, 0x7e, 0xbd, 0x8a, 0xca, 0x90, 0x95, 0x71, + 0x82, 0x9f, 0x3f, 0xb5, 0xfc, 0xc5, 0xf9, 0x66, 0x46, 0x04, 0x88, 0x8c, 0xc1, 0x23, 0x43, 0x24, + 0x82, 0x27, 0x2f, 0x8b, 0xe0, 0xe8, 0x2e, 0x14, 0x25, 0x48, 0x3b, 0xd4, 0xbd, 0x43, 0x51, 0xa0, + 0xd5, 0x96, 0x2f, 0xce, 0x37, 0x41, 0x20, 0xb7, 0x75, 0xef, 0x10, 0x83, 0x40, 0xb3, 0x6f, 0xd4, + 0x84, 0xc2, 0x67, 0xd4, 0x72, 0x34, 0x9f, 0x0f, 0x42, 0x5e, 0xf9, 0xc5, 0xce, 0xe3, 0x74, 0xa8, + 0xf2, 0xe1, 0x1b, 0x3e, 0x9b, 0x0e, 0xbe, 0x09, 0x4b, 0x2e, 0xa5, 0xbe, 0x08, 0x5b, 0x16, 0x75, + 0xe4, 0x6d, 0x42, 0x39, 0xf6, 0x92, 0x99, 0x52, 0x1f, 0x4b, 0x1c, 0x2e, 0xba, 0x91, 0x16, 0xba, + 0x0b, 0x6b, 0xb6, 0xee, 0xf9, 0x1a, 0x8f, 0x77, 0xe6, 0x54, 0x5b, 0x96, 0x6f, 0x35, 0xc4, 0x78, + 0x5b, 0x9c, 0x15, 0x48, 0xa8, 0xff, 0x98, 0x80, 0x02, 0x1b, 0x8c, 0x75, 0x60, 0x19, 0x2c, 0xc9, + 0xfb, 0xea, 0xb9, 0xc7, 0x2d, 0x48, 0x19, 0x9e, 0x2b, 0x9d, 0xca, 0x0f, 0xdf, 0x7a, 0x0f, 0x63, + 0x46, 0x43, 0x9f, 0x40, 0x56, 0xde, 0x6a, 0x88, 0xb4, 0x43, 0xbd, 0x3e, 0x1d, 0x95, 0xbe, 0x91, + 0x72, 0x7c, 0x2d, 0x4f, 0xad, 0x13, 0x87, 0x00, 0x8e, 0x92, 0xd0, 0x4d, 0x48, 0x1a, 0xc2, 0x5d, + 0xf2, 0x97, 0x15, 0xf5, 0x36, 0x4e, 0x1a, 0x8e, 0xfa, 0x77, 0x09, 0x58, 0x9a, 0x6e, 0x78, 0xb6, + 0x02, 0x6e, 0x43, 0xde, 0x1b, 0xef, 0x7b, 0x13, 0xcf, 0x27, 0xc3, 0xe0, 0x1d, 0x33, 0x24, 0xa0, + 0x16, 0xe4, 0x75, 0x7b, 0x40, 0x5d, 0xcb, 0x3f, 0x1c, 0xca, 0x4a, 0x34, 0x3e, 0x55, 0x88, 0xea, + 0xac, 0x54, 0x03, 0x11, 0x3c, 0x95, 0x0e, 0xce, 0x7d, 0xf1, 0xd8, 0xcd, 0xcf, 0xfd, 0xd7, 0xa0, + 0x68, 0xeb, 0x43, 0x7e, 0xcd, 0xe3, 0x5b, 0x43, 0x31, 0x8e, 0x34, 0x2e, 0x48, 0x5a, 0xdf, 0x1a, + 0x12, 0x55, 0x85, 0x7c, 0xa8, 0x0c, 0xad, 0x40, 0xa1, 0xda, 0xec, 0x69, 0xf7, 0xee, 0x3f, 0xd4, + 0x1e, 0xd5, 0x77, 0x95, 0x05, 0x99, 0x9b, 0xfe, 0x79, 0x02, 0x96, 0x64, 0x38, 0x92, 0xf9, 0xfe, + 0xeb, 0xb0, 0xe8, 0xea, 0x07, 0x7e, 0x50, 0x91, 0xa4, 0xc5, 0xaa, 0x66, 0x11, 0x9e, 0x55, 0x24, + 0x8c, 0x15, 0x5f, 0x91, 0x44, 0x5e, 0xd6, 0x53, 0x57, 0xbe, 0xac, 0xa7, 0x7f, 0x2e, 0x2f, 0xeb, + 0xea, 0xaf, 0x03, 0x6c, 0x59, 0x36, 0xe9, 0x8b, 0xbb, 0xa6, 0xb8, 0xfa, 0x92, 0xe5, 0x70, 0xf2, + 0xc6, 0x31, 0xc8, 0xe1, 0x5a, 0x0d, 0xcc, 0x68, 0x8c, 0x35, 0xb0, 0x4c, 0xb9, 0x19, 0x39, 0xeb, + 0x11, 0x63, 0x0d, 0x2c, 0x33, 0x7c, 0x4b, 0x4a, 0x5f, 0xf7, 0x96, 0x74, 0x96, 0x80, 0x15, 0x99, + 0xbb, 0x86, 0xe1, 0xf7, 0xdb, 0x90, 0x17, 0x69, 0xec, 0xb4, 0xa0, 0xe3, 0xaf, 0xc9, 0x02, 0xd7, + 0x6a, 0xe0, 0x9c, 0x60, 0xb7, 0x4c, 0xb4, 0x09, 0x05, 0x09, 0x8d, 0xfc, 0x0a, 0x07, 0x04, 0xa9, + 0xcd, 0xcc, 0xff, 0x2e, 0xa4, 0x0f, 0x2c, 0x9b, 0xc8, 0x85, 0x1e, 0x1b, 0x00, 0xa6, 0x0e, 0xd8, + 0x5e, 0xc0, 0x1c, 0x5d, 0xcb, 0x05, 0x97, 0x71, 0xdc, 0x3e, 0x59, 0x76, 0x46, 0xed, 0x13, 0x15, + 0xe8, 0x9c, 0x7d, 0x02, 0xc7, 0xec, 0x13, 0x6c, 0x61, 0x9f, 0x84, 0x46, 0xed, 0x13, 0xa4, 0x9f, + 0x8b, 0x7d, 0x3b, 0x70, 0xb3, 0x66, 0xeb, 0xc6, 0x91, 0x6d, 0x79, 0x3e, 0x31, 0xa3, 0x11, 0xe3, + 0x3e, 0x64, 0x67, 0x92, 0xce, 0xab, 0x2e, 0x67, 0x25, 0x52, 0xfd, 0xb7, 0x04, 0x14, 0xb7, 0x89, + 0x6e, 0xfb, 0x87, 0xd3, 0xab, 0x21, 0x9f, 0x78, 0xbe, 0x3c, 0xac, 0xf8, 0x37, 0xfa, 0x1e, 0xe4, + 0xc2, 0x9c, 0xe4, 0xda, 0x57, 0xb2, 0x10, 0x8a, 0x1e, 0xc0, 0x22, 0xdb, 0x63, 0x74, 0x1c, 0x14, + 0x3b, 0x57, 0x3d, 0xc0, 0x48, 0x24, 0x3b, 0x64, 0x5c, 0xc2, 0x93, 0x10, 0xbe, 0x94, 0x32, 0x38, + 0x68, 0xa2, 0xff, 0x0f, 0x45, 0xfe, 0x7e, 0x10, 0xe4, 0x5c, 0x99, 0xeb, 0x74, 0x16, 0xc4, 0x13, + 0xa0, 0xc8, 0xb7, 0xfe, 0x27, 0x01, 0x6b, 0xbb, 0xfa, 0x64, 0x9f, 0xc8, 0xb0, 0x41, 0x4c, 0x4c, + 0x0c, 0xea, 0x9a, 0xa8, 0x1b, 0x0d, 0x37, 0x57, 0xbc, 0x28, 0xc6, 0x09, 0xc7, 0x47, 0x9d, 0xa0, + 0x00, 0x4b, 0x46, 0x0a, 0xb0, 0x35, 0xc8, 0x38, 0xd4, 0x31, 0x88, 0x8c, 0x45, 0xa2, 0xa1, 0x5a, + 0xd1, 0x50, 0x53, 0x0a, 0x1f, 0xfb, 0xf8, 0x53, 0x5d, 0x9b, 0xfa, 0x61, 0x6f, 0xe8, 0x13, 0x28, + 0xf5, 0x9a, 0x75, 0xdc, 0xec, 0xd7, 0x3a, 0x3f, 0xd4, 0x7a, 0xd5, 0x9d, 0x5e, 0xf5, 0xfe, 0x5d, + 0xad, 0xdb, 0xd9, 0xf9, 0xf4, 0xde, 0x83, 0xbb, 0xdf, 0x53, 0x12, 0xa5, 0xf2, 0xe9, 0x59, 0xf9, + 0x76, 0xbb, 0x5a, 0xdf, 0x11, 0x3b, 0x66, 0x9f, 0x3e, 0xeb, 0xe9, 0xb6, 0xa7, 0xdf, 0xbf, 0xdb, + 0xa5, 0xf6, 0x84, 0x61, 0xd8, 0xb2, 0x2e, 0x46, 0xcf, 0xab, 0xe8, 0x31, 0x9c, 0xb8, 0xf4, 0x18, + 0x9e, 0x9e, 0xe6, 0xc9, 0x4b, 0x4e, 0xf3, 0x2d, 0x58, 0x33, 0x5c, 0xea, 0x79, 0x1a, 0xcb, 0xfe, + 0x89, 0x39, 0x57, 0x5f, 0x7c, 0xe3, 0xe2, 0x7c, 0x73, 0xb5, 0xce, 0xf8, 0x3d, 0xce, 0x96, 0xea, + 0x57, 0x8d, 0x08, 0x89, 0xf7, 0xa4, 0xfe, 0x7e, 0x8a, 0x25, 0x52, 0xd6, 0xb1, 0x65, 0x93, 0x01, + 0xf1, 0xd0, 0x13, 0x58, 0x31, 0x5c, 0x62, 0xb2, 0xb4, 0x5e, 0xb7, 0xa3, 0xbf, 0xe6, 0xfc, 0x7f, + 0xb1, 0x39, 0x4d, 0x28, 0x58, 0xa9, 0x87, 0x52, 0xbd, 0x11, 0x31, 0xf0, 0xb2, 0x31, 0xd3, 0x46, + 0x9f, 0xc1, 0x8a, 0x47, 0x6c, 0xcb, 0x19, 0x3f, 0xd3, 0x0c, 0xea, 0xf8, 0xe4, 0x59, 0xf0, 0x6e, + 0x75, 0x9d, 0xde, 0x5e, 0x73, 0x87, 0x49, 0xd5, 0x85, 0x50, 0x0d, 0x5d, 0x9c, 0x6f, 0x2e, 0xcf, + 0xd2, 0xf0, 0xb2, 0xd4, 0x2c, 0xdb, 0xa5, 0x36, 0x2c, 0xcf, 0x5a, 0x83, 0xd6, 0xe4, 0xde, 0xe7, + 0x21, 0x24, 0xd8, 0xdb, 0xe8, 0x36, 0xe4, 0x5c, 0x32, 0xb0, 0x3c, 0xdf, 0x15, 0x6e, 0x66, 0x9c, + 0x90, 0xc2, 0x76, 0xbe, 0xf8, 0x29, 0x4e, 0xe9, 0x57, 0x61, 0xae, 0x47, 0xb6, 0x59, 0x4c, 0xcb, + 0xd3, 0xf7, 0xa5, 0xca, 0x1c, 0x0e, 0x9a, 0x6c, 0x0d, 0x8e, 0xbd, 0x30, 0x51, 0xe3, 0xdf, 0x8c, + 0xc6, 0x33, 0x0a, 0xf9, 0xc3, 0x24, 0x9e, 0x33, 0x04, 0xbf, 0x70, 0x4c, 0x47, 0x7e, 0xe1, 0xb8, + 0x06, 0x19, 0x9b, 0x1c, 0x13, 0x5b, 0x9c, 0xe5, 0x58, 0x34, 0xde, 0xfe, 0x59, 0x0a, 0xf2, 0xe1, + 0x1b, 0x0d, 0x3b, 0x09, 0xda, 0xcd, 0xa7, 0xc1, 0x5a, 0x0d, 0xe9, 0x6d, 0x72, 0x82, 0x5e, 0x9b, + 0xde, 0x29, 0x7d, 0x22, 0x1e, 0xa5, 0x43, 0x76, 0x70, 0x9f, 0xf4, 0x06, 0xe4, 0xaa, 0xbd, 0x5e, + 0xeb, 0x51, 0xbb, 0xd9, 0x50, 0x3e, 0x4f, 0x94, 0xbe, 0x71, 0x7a, 0x56, 0x5e, 0x0d, 0x41, 0x55, + 0x4f, 0x2c, 0x25, 0x8e, 0xaa, 0xd7, 0x9b, 0xdd, 0x7e, 0xb3, 0xa1, 0x3c, 0x4f, 0xce, 0xa3, 0xf8, + 0x1d, 0x09, 0xff, 0x69, 0x49, 0xbe, 0x8b, 0x9b, 0xdd, 0x2a, 0x66, 0x1d, 0x7e, 0x9e, 0x14, 0x57, + 0x5d, 0xd3, 0x1e, 0x5d, 0x32, 0xd2, 0x5d, 0xd6, 0xe7, 0x46, 0xf0, 0x13, 0xab, 0xe7, 0x29, 0xf1, + 0xf3, 0x83, 0xe9, 0x83, 0x13, 0xd1, 0xcd, 0x09, 0xeb, 0x8d, 0xbf, 0xf4, 0x71, 0x35, 0xa9, 0xb9, + 0xde, 0x7a, 0x2c, 0x92, 0x30, 0x2d, 0x2a, 0x2c, 0xe2, 0xbd, 0x76, 0x9b, 0x81, 0x9e, 0xa7, 0xe7, + 0x46, 0x87, 0xc7, 0x0e, 0xab, 0x7f, 0xd1, 0x1d, 0xc8, 0x05, 0x0f, 0x81, 0xca, 0xe7, 0xe9, 0x39, + 0x83, 0xea, 0xc1, 0x2b, 0x26, 0xef, 0x70, 0x7b, 0xaf, 0xcf, 0x7f, 0x01, 0xf6, 0x3c, 0x33, 0xdf, + 0xe1, 0xe1, 0xd8, 0x37, 0xe9, 0x89, 0xc3, 0x76, 0xa0, 0xbc, 0x55, 0xfb, 0x3c, 0x23, 0xae, 0x20, + 0x42, 0x8c, 0xbc, 0x52, 0x7b, 0x03, 0x72, 0xb8, 0xf9, 0x03, 0xf1, 0x63, 0xb1, 0xe7, 0xd9, 0x39, + 0x3d, 0x98, 0x7c, 0x46, 0x0c, 0xd9, 0x5b, 0x07, 0x77, 0xb7, 0xab, 0xdc, 0xe5, 0xf3, 0xa8, 0x8e, + 0x3b, 0x3a, 0xd4, 0x1d, 0x62, 0x4e, 0x7f, 0x83, 0x11, 0xb2, 0xde, 0xfe, 0x25, 0xc8, 0x05, 0x79, + 0x26, 0xda, 0x80, 0xec, 0xd3, 0x0e, 0x7e, 0xdc, 0xc4, 0xca, 0x82, 0xf0, 0x61, 0xc0, 0x79, 0x2a, + 0x2a, 0x84, 0x32, 0x2c, 0xee, 0x56, 0xdb, 0xd5, 0x47, 0x4d, 0x1c, 0x5c, 0x78, 0x07, 0x00, 0x99, + 0x2c, 0x95, 0x14, 0xd9, 0x41, 0xa8, 0xb3, 0xb6, 0xfe, 0xc5, 0x97, 0x1b, 0x0b, 0x3f, 0xfd, 0x72, + 0x63, 0xe1, 0xf9, 0xc5, 0x46, 0xe2, 0x8b, 0x8b, 0x8d, 0xc4, 0x4f, 0x2e, 0x36, 0x12, 0xff, 0x7a, + 0xb1, 0x91, 0xd8, 0xcf, 0xf2, 0x90, 0xfe, 0xe0, 0x7f, 0x03, 0x00, 0x00, 0xff, 0xff, 0x48, 0x1c, + 0x30, 0x25, 0x28, 0x30, 0x00, 0x00, } diff --git a/vendor/github.com/docker/swarmkit/api/types.proto b/vendor/github.com/docker/swarmkit/api/types.proto index 201bc3587f..a9fb07a57b 100644 --- a/vendor/github.com/docker/swarmkit/api/types.proto +++ b/vendor/github.com/docker/swarmkit/api/types.proto @@ -30,20 +30,30 @@ message Annotations { repeated IndexEntry indices = 4 [(gogoproto.nullable) = false]; } -message GenericString { +// NamedGenericResource represents a "user defined" resource which is defined +// as a string. +// "Kind" is used to describe the Kind of a resource (e.g: "GPU", "FPGA", "SSD", ...) +// Value is used to identify the resource (GPU="UUID-1", FPGA="/dev/sdb5", ...) +message NamedGenericResource { string kind = 1; string value = 2; } -message GenericDiscrete { +// DiscreteGenericResource represents a "user defined" resource which is defined +// as an integer +// "Kind" is used to describe the Kind of a resource (e.g: "GPU", "FPGA", "SSD", ...) +// Value is used to count the resource (SSD=5, HDD=3, ...) +message DiscreteGenericResource { string kind = 1; int64 value = 2; } +// GenericResource represents a "user defined" resource which can +// be either an integer (e.g: SSD=3) or a string (e.g: SSD=sda1) message GenericResource { oneof resource { - GenericString str = 1; - GenericDiscrete discrete = 2; + NamedGenericResource named_resource_spec = 1; + DiscreteGenericResource discrete_resource_spec = 2; } } diff --git a/vendor/github.com/docker/swarmkit/ca/config.go b/vendor/github.com/docker/swarmkit/ca/config.go index 9dd84ecb36..cfaccd00b9 100644 --- a/vendor/github.com/docker/swarmkit/ca/config.go +++ b/vendor/github.com/docker/swarmkit/ca/config.go @@ -14,6 +14,7 @@ import ( "github.com/Sirupsen/logrus" cfconfig "github.com/cloudflare/cfssl/config" + events "github.com/docker/go-events" "github.com/docker/swarmkit/api" "github.com/docker/swarmkit/connectionbroker" "github.com/docker/swarmkit/identity" @@ -123,11 +124,11 @@ func validateRootCAAndTLSCert(rootCA *RootCA, externalCARootPool *x509.CertPool, } // NewSecurityConfig initializes and returns a new SecurityConfig. -func NewSecurityConfig(rootCA *RootCA, krw *KeyReadWriter, tlsKeyPair *tls.Certificate, issuerInfo *IssuerInfo) (*SecurityConfig, error) { +func NewSecurityConfig(rootCA *RootCA, krw *KeyReadWriter, tlsKeyPair *tls.Certificate, issuerInfo *IssuerInfo) (*SecurityConfig, func() error, error) { // Create the Server TLS Credentials for this node. These will not be used by workers. serverTLSCreds, err := rootCA.NewServerTLSCredentials(tlsKeyPair) if err != nil { - return nil, err + return nil, nil, err } // Create a TLSConfig to be used when this node connects as a client to another remote node. @@ -135,7 +136,7 @@ func NewSecurityConfig(rootCA *RootCA, krw *KeyReadWriter, tlsKeyPair *tls.Certi // and managers always connect to remote managers. clientTLSCreds, err := rootCA.NewClientTLSCredentials(tlsKeyPair, ManagerRole) if err != nil { - return nil, err + return nil, nil, err } // Make a new TLS config for the external CA client without a @@ -146,18 +147,21 @@ func NewSecurityConfig(rootCA *RootCA, krw *KeyReadWriter, tlsKeyPair *tls.Certi MinVersion: tls.VersionTLS12, } + q := watch.NewQueue() + return &SecurityConfig{ rootCA: rootCA, keyReadWriter: krw, certificate: tlsKeyPair, issuerInfo: issuerInfo, + queue: q, externalCA: NewExternalCA(rootCA, externalCATLSConfig), ClientTLSCreds: clientTLSCreds, ServerTLSCreds: serverTLSCreds, externalCAClientRootPool: rootCA.Pool, - }, nil + }, q.Close, nil } // RootCA returns the root CA. @@ -200,11 +204,9 @@ func (s *SecurityConfig) UpdateRootCA(rootCA *RootCA, externalCARootPool *x509.C return s.updateTLSCredentials(s.certificate, s.issuerInfo) } -// SetWatch allows you to set a watch on the security config, in order to be notified of any changes -func (s *SecurityConfig) SetWatch(q *watch.Queue) { - s.mu.Lock() - defer s.mu.Unlock() - s.queue = q +// Watch allows you to set a watch on the security config, in order to be notified of any changes +func (s *SecurityConfig) Watch() (chan events.Event, func()) { + return s.queue.Watch() } // IssuerInfo returns the issuer subject and issuer public key @@ -382,7 +384,7 @@ func DownloadRootCA(ctx context.Context, paths CertPaths, token string, connBrok // LoadSecurityConfig loads TLS credentials from disk, or returns an error if // these credentials do not exist or are unusable. -func LoadSecurityConfig(ctx context.Context, rootCA RootCA, krw *KeyReadWriter, allowExpired bool) (*SecurityConfig, error) { +func LoadSecurityConfig(ctx context.Context, rootCA RootCA, krw *KeyReadWriter, allowExpired bool) (*SecurityConfig, func() error, error) { ctx = log.WithModule(ctx, "tls") // At this point we've successfully loaded the CA details from disk, or @@ -392,13 +394,13 @@ func LoadSecurityConfig(ctx context.Context, rootCA RootCA, krw *KeyReadWriter, // Read both the Cert and Key from disk cert, key, err := krw.Read() if err != nil { - return nil, err + return nil, nil, err } // Check to see if this certificate was signed by our CA, and isn't expired _, chains, err := ValidateCertChain(rootCA.Pool, cert, allowExpired) if err != nil { - return nil, err + return nil, nil, err } // ValidateChain, if successful, will always return at least 1 chain containing // at least 2 certificates: the leaf and the root. @@ -408,10 +410,10 @@ func LoadSecurityConfig(ctx context.Context, rootCA RootCA, krw *KeyReadWriter, // credentials keyPair, err := tls.X509KeyPair(cert, key) if err != nil { - return nil, err + return nil, nil, err } - secConfig, err := NewSecurityConfig(&rootCA, krw, &keyPair, &IssuerInfo{ + secConfig, cleanup, err := NewSecurityConfig(&rootCA, krw, &keyPair, &IssuerInfo{ Subject: issuer.RawSubject, PublicKey: issuer.RawSubjectPublicKeyInfo, }) @@ -421,7 +423,7 @@ func LoadSecurityConfig(ctx context.Context, rootCA RootCA, krw *KeyReadWriter, "node.role": secConfig.ClientTLSCreds.Role(), }).Debug("loaded node credentials") } - return secConfig, err + return secConfig, cleanup, err } // CertificateRequestConfig contains the information needed to request a @@ -450,7 +452,7 @@ type CertificateRequestConfig struct { // CreateSecurityConfig creates a new key and cert for this node, either locally // or via a remote CA. -func (rootCA RootCA) CreateSecurityConfig(ctx context.Context, krw *KeyReadWriter, config CertificateRequestConfig) (*SecurityConfig, error) { +func (rootCA RootCA) CreateSecurityConfig(ctx context.Context, krw *KeyReadWriter, config CertificateRequestConfig) (*SecurityConfig, func() error, error) { ctx = log.WithModule(ctx, "tls") // Create a new random ID for this certificate @@ -467,7 +469,7 @@ func (rootCA RootCA) CreateSecurityConfig(ctx context.Context, krw *KeyReadWrite tlsKeyPair, issuerInfo, err = rootCA.RequestAndSaveNewCertificates(ctx, krw, config) if err != nil { log.G(ctx).WithError(err).Error("failed to request and save new certificate") - return nil, err + return nil, nil, err } case nil: log.G(ctx).WithFields(logrus.Fields{ @@ -479,17 +481,17 @@ func (rootCA RootCA) CreateSecurityConfig(ctx context.Context, krw *KeyReadWrite "node.id": cn, "node.role": proposedRole, }).WithError(err).Errorf("failed to issue and save new certificate") - return nil, err + return nil, nil, err } - secConfig, err := NewSecurityConfig(&rootCA, krw, tlsKeyPair, issuerInfo) + secConfig, cleanup, err := NewSecurityConfig(&rootCA, krw, tlsKeyPair, issuerInfo) if err == nil { log.G(ctx).WithFields(logrus.Fields{ "node.id": secConfig.ClientTLSCreds.NodeID(), "node.role": secConfig.ClientTLSCreds.Role(), }).Debugf("new node credentials generated: %s", krw.Target()) } - return secConfig, err + return secConfig, cleanup, err } // TODO(cyli): currently we have to only update if it's a worker role - if we have a single root CA update path for diff --git a/vendor/github.com/docker/swarmkit/ca/external.go b/vendor/github.com/docker/swarmkit/ca/external.go index d6a9421e0d..ef76e2fbe5 100644 --- a/vendor/github.com/docker/swarmkit/ca/external.go +++ b/vendor/github.com/docker/swarmkit/ca/external.go @@ -8,6 +8,7 @@ import ( "encoding/hex" "encoding/json" "encoding/pem" + "io" "io/ioutil" "net/http" "sync" @@ -24,8 +25,18 @@ import ( "golang.org/x/net/context/ctxhttp" ) -// ExternalCrossSignProfile is the profile that we will be sending cross-signing CSR sign requests with -const ExternalCrossSignProfile = "CA" +const ( + // ExternalCrossSignProfile is the profile that we will be sending cross-signing CSR sign requests with + ExternalCrossSignProfile = "CA" + + // CertificateMaxSize is the maximum expected size of a certificate. + // While there is no specced upper limit to the size of an x509 certificate in PEM format, + // one with a ridiculous RSA key size (16384) and 26 256-character DNS SAN fields is about 14k. + // While there is no upper limit on the length of certificate chains, long chains are impractical. + // To be conservative, and to also account for external CA certificate responses in JSON format + // from CFSSL, we'll set the max to be 256KiB. + CertificateMaxSize int64 = 256 << 10 +) // ErrNoExternalCAURLs is an error used it indicate that an ExternalCA is // configured with no URLs to which it can proxy certificate signing requests. @@ -191,7 +202,8 @@ func makeExternalSignRequest(ctx context.Context, client *http.Client, url strin } defer resp.Body.Close() - body, err := ioutil.ReadAll(resp.Body) + b := io.LimitReader(resp.Body, CertificateMaxSize) + body, err := ioutil.ReadAll(b) if err != nil { return nil, recoverableErr{err: errors.Wrap(err, "unable to read CSR response body")} } diff --git a/vendor/github.com/docker/swarmkit/manager/controlapi/service.go b/vendor/github.com/docker/swarmkit/manager/controlapi/service.go index d556b6c0e7..0a0a9ffa2a 100644 --- a/vendor/github.com/docker/swarmkit/manager/controlapi/service.go +++ b/vendor/github.com/docker/swarmkit/manager/controlapi/service.go @@ -128,7 +128,13 @@ func validateContainerSpec(taskSpec api.TaskSpec) error { // Building a empty/dummy Task to validate the templating and // the resulting container spec as well. This is a *best effort* // validation. - container, err := template.ExpandContainerSpec(&api.Task{ + container, err := template.ExpandContainerSpec(&api.NodeDescription{ + Hostname: "nodeHostname", + Platform: &api.Platform{ + OS: "os", + Architecture: "architecture", + }, + }, &api.Task{ Spec: taskSpec, ServiceID: "serviceid", Slot: 1, diff --git a/vendor/github.com/docker/swarmkit/manager/dispatcher/dispatcher.go b/vendor/github.com/docker/swarmkit/manager/dispatcher/dispatcher.go index 33275f4c16..47899cc48a 100644 --- a/vendor/github.com/docker/swarmkit/manager/dispatcher/dispatcher.go +++ b/vendor/github.com/docker/swarmkit/manager/dispatcher/dispatcher.go @@ -475,7 +475,7 @@ func (d *Dispatcher) register(ctx context.Context, nodeID string, description *a addr, err := nodeIPFromContext(ctx) if err != nil { - log.G(ctx).Debug(err.Error()) + log.G(ctx).WithError(err).Debug("failed to get remote node IP") } if err := d.markNodeReady(dctx, nodeID, description, addr); err != nil { @@ -483,7 +483,7 @@ func (d *Dispatcher) register(ctx context.Context, nodeID string, description *a } expireFunc := func() { - log.G(ctx).Debugf("heartbeat expiration") + log.G(ctx).Debug("heartbeat expiration") if err := d.markNodeNotReady(nodeID, api.NodeStatus_DOWN, "heartbeat failure"); err != nil { log.G(ctx).WithError(err).Errorf("failed deregistering node after heartbeat expiration") } @@ -703,7 +703,7 @@ func (d *Dispatcher) Tasks(r *api.TasksRequest, stream api.Dispatcher_TasksServe if nodeInfo.ForwardedBy != nil { fields["forwarder.id"] = nodeInfo.ForwardedBy.NodeID } - log.G(stream.Context()).WithFields(fields).Debugf("") + log.G(stream.Context()).WithFields(fields).Debug("") if _, err = d.nodes.GetWithSession(nodeID, r.SessionID); err != nil { return err @@ -827,7 +827,7 @@ func (d *Dispatcher) Assignments(r *api.AssignmentsRequest, stream api.Dispatche fields["forwarder.id"] = nodeInfo.ForwardedBy.NodeID } log := log.G(stream.Context()).WithFields(fields) - log.Debugf("") + log.Debug("") if _, err = d.nodes.GetWithSession(nodeID, r.SessionID); err != nil { return err @@ -1118,7 +1118,7 @@ func (d *Dispatcher) Session(r *api.SessionRequest, stream api.Dispatcher_Sessio // get the node IP addr addr, err := nodeIPFromContext(stream.Context()) if err != nil { - log.G(ctx).Debugf(err.Error()) + log.G(ctx).WithError(err).Debug("failed to get remote node IP") } // update the node description if err := d.markNodeReady(dctx, nodeID, r.Description, addr); err != nil { diff --git a/vendor/github.com/docker/swarmkit/manager/orchestrator/global/global.go b/vendor/github.com/docker/swarmkit/manager/orchestrator/global/global.go index f5e6b3afc0..b89a105fec 100644 --- a/vendor/github.com/docker/swarmkit/manager/orchestrator/global/global.go +++ b/vendor/github.com/docker/swarmkit/manager/orchestrator/global/global.go @@ -159,13 +159,13 @@ func (g *Orchestrator) Run(ctx context.Context) error { switch v.Node.Status.State { // NodeStatus_DISCONNECTED is a transient state, no need to make any change case api.NodeStatus_DOWN: - g.removeTasksFromNode(ctx, v.Node) + g.foreachTaskFromNode(ctx, v.Node, g.shutdownTask) case api.NodeStatus_READY: // node could come back to READY from DOWN or DISCONNECT g.reconcileOneNode(ctx, v.Node) } case api.EventDeleteNode: - g.removeTasksFromNode(ctx, v.Node) + g.foreachTaskFromNode(ctx, v.Node, g.deleteTask) delete(g.nodes, v.Node.ID) case api.EventUpdateTask: g.handleTaskChange(ctx, v.Task) @@ -201,7 +201,7 @@ func (g *Orchestrator) FixTask(ctx context.Context, batch *store.Batch, t *api.T } // if the node no longer valid, remove the task if t.NodeID == "" || orchestrator.InvalidNode(node) { - g.removeTask(ctx, batch, t) + g.shutdownTask(ctx, batch, t) return } @@ -236,7 +236,7 @@ func (g *Orchestrator) Stop() { g.restarts.CancelAll() } -func (g *Orchestrator) removeTasksFromNode(ctx context.Context, node *api.Node) { +func (g *Orchestrator) foreachTaskFromNode(ctx context.Context, node *api.Node, cb func(context.Context, *store.Batch, *api.Task)) { var ( tasks []*api.Task err error @@ -245,7 +245,7 @@ func (g *Orchestrator) removeTasksFromNode(ctx context.Context, node *api.Node) tasks, err = store.FindTasks(tx, store.ByNodeID(node.ID)) }) if err != nil { - log.G(ctx).WithError(err).Errorf("global orchestrator: removeTasksFromNode failed finding tasks") + log.G(ctx).WithError(err).Errorf("global orchestrator: foreachTaskFromNode failed finding tasks") return } @@ -253,13 +253,13 @@ func (g *Orchestrator) removeTasksFromNode(ctx context.Context, node *api.Node) for _, t := range tasks { // Global orchestrator only removes tasks from globalServices if _, exists := g.globalServices[t.ServiceID]; exists { - g.removeTask(ctx, batch, t) + cb(ctx, batch, t) } } return nil }) if err != nil { - log.G(ctx).WithError(err).Errorf("global orchestrator: removeTasksFromNode failed batching tasks") + log.G(ctx).WithError(err).Errorf("global orchestrator: foreachTaskFromNode failed batching tasks") } } @@ -314,7 +314,7 @@ func (g *Orchestrator) reconcileServices(ctx context.Context, serviceIDs []strin // if restart policy considers this node has finished its task // it should remove all running tasks if _, exists := nodeCompleted[serviceID][nodeID]; exists || !meetsConstraints { - g.removeTasks(ctx, batch, ntasks) + g.shutdownTasks(ctx, batch, ntasks) continue } @@ -340,7 +340,7 @@ func (g *Orchestrator) reconcileServices(ctx context.Context, serviceIDs []strin // These must be associated with nodes that are drained, or // nodes that no longer exist. for _, ntasks := range nodeTasks[serviceID] { - g.removeTasks(ctx, batch, ntasks) + g.shutdownTasks(ctx, batch, ntasks) } } return nil @@ -382,7 +382,7 @@ func (g *Orchestrator) updateService(service *api.Service) { func (g *Orchestrator) reconcileOneNode(ctx context.Context, node *api.Node) { if node.Spec.Availability == api.NodeAvailabilityDrain { log.G(ctx).Debugf("global orchestrator: node %s in drain state, removing tasks from it", node.ID) - g.removeTasksFromNode(ctx, node) + g.foreachTaskFromNode(ctx, node, g.shutdownTask) return } @@ -447,7 +447,7 @@ func (g *Orchestrator) reconcileServicesOneNode(ctx context.Context, serviceIDs // if restart policy considers this node has finished its task // it should remove all running tasks if completed[serviceID] { - g.removeTasks(ctx, batch, tasks[serviceID]) + g.shutdownTasks(ctx, batch, tasks[serviceID]) continue } @@ -491,7 +491,7 @@ func (g *Orchestrator) reconcileServicesOneNode(ctx context.Context, serviceIDs } else { dirtyTasks = append(dirtyTasks, cleanTasks[1:]...) } - g.removeTasks(ctx, batch, dirtyTasks) + g.shutdownTasks(ctx, batch, dirtyTasks) } } return nil @@ -542,7 +542,7 @@ func (g *Orchestrator) tickTasks(ctx context.Context) { g.restartTasks = make(map[string]struct{}) } -func (g *Orchestrator) removeTask(ctx context.Context, batch *store.Batch, t *api.Task) { +func (g *Orchestrator) shutdownTask(ctx context.Context, batch *store.Batch, t *api.Task) { // set existing task DesiredState to TaskStateShutdown // TODO(aaronl): optimistic update? err := batch.Update(func(tx store.Tx) error { @@ -554,7 +554,7 @@ func (g *Orchestrator) removeTask(ctx context.Context, batch *store.Batch, t *ap return nil }) if err != nil { - log.G(ctx).WithError(err).Errorf("global orchestrator: removeTask failed to remove %s", t.ID) + log.G(ctx).WithError(err).Errorf("global orchestrator: shutdownTask failed to shut down %s", t.ID) } } @@ -572,9 +572,18 @@ func (g *Orchestrator) addTask(ctx context.Context, batch *store.Batch, service } } -func (g *Orchestrator) removeTasks(ctx context.Context, batch *store.Batch, tasks []*api.Task) { +func (g *Orchestrator) shutdownTasks(ctx context.Context, batch *store.Batch, tasks []*api.Task) { for _, t := range tasks { - g.removeTask(ctx, batch, t) + g.shutdownTask(ctx, batch, t) + } +} + +func (g *Orchestrator) deleteTask(ctx context.Context, batch *store.Batch, t *api.Task) { + err := batch.Update(func(tx store.Tx) error { + return store.DeleteTask(tx, t.ID) + }) + if err != nil { + log.G(ctx).WithError(err).Errorf("global orchestrator: deleteTask failed to delete %s", t.ID) } } diff --git a/vendor/github.com/docker/swarmkit/manager/scheduler/nodeinfo.go b/vendor/github.com/docker/swarmkit/manager/scheduler/nodeinfo.go index a375ed9f5d..78fa630ca3 100644 --- a/vendor/github.com/docker/swarmkit/manager/scheduler/nodeinfo.go +++ b/vendor/github.com/docker/swarmkit/manager/scheduler/nodeinfo.go @@ -15,6 +15,15 @@ type hostPortSpec struct { publishedPort uint32 } +// versionedService defines a tuple that contains a service ID and a spec +// version, so that failures can be tracked per spec version. Note that if the +// task predates spec versioning, specVersion will contain the zero value, and +// this will still work correctly. +type versionedService struct { + serviceID string + specVersion api.Version +} + // NodeInfo contains a node and some additional metadata. type NodeInfo struct { *api.Node @@ -24,12 +33,14 @@ type NodeInfo struct { AvailableResources *api.Resources usedHostPorts map[hostPortSpec]struct{} - // recentFailures is a map from service ID to the timestamps of the - // most recent failures the node has experienced from replicas of that - // service. - // TODO(aaronl): When spec versioning is supported, this should track - // the version of the spec that failed. - recentFailures map[string][]time.Time + // recentFailures is a map from service ID/version to the timestamps of + // the most recent failures the node has experienced from replicas of + // that service. + recentFailures map[versionedService][]time.Time + + // lastCleanup is the last time recentFailures was cleaned up. This is + // done periodically to avoid recentFailures growing without any limit. + lastCleanup time.Time } func newNodeInfo(n *api.Node, tasks map[string]*api.Task, availableResources api.Resources) NodeInfo { @@ -39,7 +50,8 @@ func newNodeInfo(n *api.Node, tasks map[string]*api.Task, availableResources api ActiveTasksCountByService: make(map[string]int), AvailableResources: availableResources.Copy(), usedHostPorts: make(map[hostPortSpec]struct{}), - recentFailures: make(map[string][]time.Time), + recentFailures: make(map[versionedService][]time.Time), + lastCleanup: time.Now(), } for _, t := range tasks { @@ -148,30 +160,58 @@ func taskReservations(spec api.TaskSpec) (reservations api.Resources) { return } +func (nodeInfo *NodeInfo) cleanupFailures(now time.Time) { +entriesLoop: + for key, failuresEntry := range nodeInfo.recentFailures { + for _, timestamp := range failuresEntry { + if now.Sub(timestamp) < monitorFailures { + continue entriesLoop + } + } + delete(nodeInfo.recentFailures, key) + } + nodeInfo.lastCleanup = now +} + // taskFailed records a task failure from a given service. -func (nodeInfo *NodeInfo) taskFailed(ctx context.Context, serviceID string) { +func (nodeInfo *NodeInfo) taskFailed(ctx context.Context, t *api.Task) { expired := 0 now := time.Now() - for _, timestamp := range nodeInfo.recentFailures[serviceID] { + + if now.Sub(nodeInfo.lastCleanup) >= monitorFailures { + nodeInfo.cleanupFailures(now) + } + + versionedService := versionedService{serviceID: t.ServiceID} + if t.SpecVersion != nil { + versionedService.specVersion = *t.SpecVersion + } + + for _, timestamp := range nodeInfo.recentFailures[versionedService] { if now.Sub(timestamp) < monitorFailures { break } expired++ } - if len(nodeInfo.recentFailures[serviceID])-expired == maxFailures-1 { - log.G(ctx).Warnf("underweighting node %s for service %s because it experienced %d failures or rejections within %s", nodeInfo.ID, serviceID, maxFailures, monitorFailures.String()) + if len(nodeInfo.recentFailures[versionedService])-expired == maxFailures-1 { + log.G(ctx).Warnf("underweighting node %s for service %s because it experienced %d failures or rejections within %s", nodeInfo.ID, t.ServiceID, maxFailures, monitorFailures.String()) } - nodeInfo.recentFailures[serviceID] = append(nodeInfo.recentFailures[serviceID][expired:], now) + nodeInfo.recentFailures[versionedService] = append(nodeInfo.recentFailures[versionedService][expired:], now) } // countRecentFailures returns the number of times the service has failed on // this node within the lookback window monitorFailures. -func (nodeInfo *NodeInfo) countRecentFailures(now time.Time, serviceID string) int { - recentFailureCount := len(nodeInfo.recentFailures[serviceID]) +func (nodeInfo *NodeInfo) countRecentFailures(now time.Time, t *api.Task) int { + versionedService := versionedService{serviceID: t.ServiceID} + if t.SpecVersion != nil { + versionedService.specVersion = *t.SpecVersion + } + + recentFailureCount := len(nodeInfo.recentFailures[versionedService]) for i := recentFailureCount - 1; i >= 0; i-- { - if now.Sub(nodeInfo.recentFailures[serviceID][i]) > monitorFailures { + if now.Sub(nodeInfo.recentFailures[versionedService][i]) > monitorFailures { recentFailureCount -= i + 1 break } diff --git a/vendor/github.com/docker/swarmkit/manager/scheduler/scheduler.go b/vendor/github.com/docker/swarmkit/manager/scheduler/scheduler.go index 07d9b0458c..73349e391f 100644 --- a/vendor/github.com/docker/swarmkit/manager/scheduler/scheduler.go +++ b/vendor/github.com/docker/swarmkit/manager/scheduler/scheduler.go @@ -261,7 +261,7 @@ func (s *Scheduler) updateTask(ctx context.Context, t *api.Task) bool { if _, wasPreassigned := s.preassignedTasks[t.ID]; !wasPreassigned { nodeInfo, err := s.nodeSet.nodeInfo(t.NodeID) if err == nil { - nodeInfo.taskFailed(ctx, t.ServiceID) + nodeInfo.taskFailed(ctx, t) s.nodeSet.updateNode(nodeInfo) } } @@ -543,8 +543,8 @@ func (s *Scheduler) scheduleTaskGroup(ctx context.Context, taskGroup map[string] nodeLess := func(a *NodeInfo, b *NodeInfo) bool { // If either node has at least maxFailures recent failures, // that's the deciding factor. - recentFailuresA := a.countRecentFailures(now, t.ServiceID) - recentFailuresB := b.countRecentFailures(now, t.ServiceID) + recentFailuresA := a.countRecentFailures(now, t) + recentFailuresB := b.countRecentFailures(now, t) if recentFailuresA >= maxFailures || recentFailuresB >= maxFailures { if recentFailuresA > recentFailuresB { diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/clusters.go b/vendor/github.com/docker/swarmkit/manager/state/store/clusters.go index a495dacc92..495fc04037 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/clusters.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/clusters.go @@ -43,21 +43,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - clusters, err := FindClusters(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Clusters)) + for i, x := range snapshot.Clusters { + toStoreObj[i] = x } - for _, n := range clusters { - if err := DeleteCluster(tx, n.ID); err != nil { - return err - } - } - for _, n := range snapshot.Clusters { - if err := CreateCluster(tx, n); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableCluster, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/configs.go b/vendor/github.com/docker/swarmkit/manager/state/store/configs.go index 2bd44ae1bd..d02e04ba9b 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/configs.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/configs.go @@ -37,21 +37,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - configs, err := FindConfigs(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Configs)) + for i, x := range snapshot.Configs { + toStoreObj[i] = x } - for _, s := range configs { - if err := DeleteConfig(tx, s.ID); err != nil { - return err - } - } - for _, s := range snapshot.Configs { - if err := CreateConfig(tx, s); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableConfig, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/extensions.go b/vendor/github.com/docker/swarmkit/manager/state/store/extensions.go index 627d87d531..8dac4baac7 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/extensions.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/extensions.go @@ -38,21 +38,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - extensions, err := FindExtensions(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Extensions)) + for i, x := range snapshot.Extensions { + toStoreObj[i] = extensionEntry{x} } - for _, e := range extensions { - if err := DeleteExtension(tx, e.ID); err != nil { - return err - } - } - for _, e := range snapshot.Extensions { - if err := CreateExtension(tx, e); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableExtension, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { @@ -80,6 +70,14 @@ func (e extensionEntry) CopyStoreObject() api.StoreObject { return extensionEntry{Extension: e.Extension.Copy()} } +// ensure that when update events are emitted, we unwrap extensionEntry +func (e extensionEntry) EventUpdate(oldObject api.StoreObject) api.Event { + if oldObject != nil { + return api.EventUpdateExtension{Extension: e.Extension, OldExtension: oldObject.(extensionEntry).Extension} + } + return api.EventUpdateExtension{Extension: e.Extension} +} + // CreateExtension adds a new extension to the store. // Returns ErrExist if the ID is already taken. func CreateExtension(tx Tx, e *api.Extension) error { diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/networks.go b/vendor/github.com/docker/swarmkit/manager/state/store/networks.go index df549d429c..3042def1bf 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/networks.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/networks.go @@ -37,21 +37,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - networks, err := FindNetworks(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Networks)) + for i, x := range snapshot.Networks { + toStoreObj[i] = x } - for _, n := range networks { - if err := DeleteNetwork(tx, n.ID); err != nil { - return err - } - } - for _, n := range snapshot.Networks { - if err := CreateNetwork(tx, n); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableNetwork, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/nodes.go b/vendor/github.com/docker/swarmkit/manager/state/store/nodes.go index 0661a16053..fa6ae85bd7 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/nodes.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/nodes.go @@ -47,21 +47,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - nodes, err := FindNodes(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Nodes)) + for i, x := range snapshot.Nodes { + toStoreObj[i] = x } - for _, n := range nodes { - if err := DeleteNode(tx, n.ID); err != nil { - return err - } - } - for _, n := range snapshot.Nodes { - if err := CreateNode(tx, n); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableNode, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/object.go b/vendor/github.com/docker/swarmkit/manager/state/store/object.go index 5f495fdfab..89029afb9f 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/object.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/object.go @@ -13,3 +13,46 @@ type ObjectStoreConfig struct { Restore func(Tx, *api.StoreSnapshot) error ApplyStoreAction func(Tx, api.StoreAction) error } + +// RestoreTable takes a list of new objects of a particular type (e.g. clusters, +// nodes, etc., which conform to the StoreObject interface) and replaces the +// existing objects in the store of that type with the new objects. +func RestoreTable(tx Tx, table string, newObjects []api.StoreObject) error { + checkType := func(by By) error { + return nil + } + var oldObjects []api.StoreObject + appendResult := func(o api.StoreObject) { + oldObjects = append(oldObjects, o) + } + + err := tx.find(table, All, checkType, appendResult) + if err != nil { + return nil + } + + updated := make(map[string]struct{}) + + for _, o := range newObjects { + objectID := o.GetID() + if existing := tx.lookup(table, indexID, objectID); existing != nil { + if err := tx.update(table, o); err != nil { + return err + } + updated[objectID] = struct{}{} + } else { + if err := tx.create(table, o); err != nil { + return err + } + } + } + for _, o := range oldObjects { + objectID := o.GetID() + if _, ok := updated[objectID]; !ok { + if err := tx.delete(table, objectID); err != nil { + return err + } + } + } + return nil +} diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/resources.go b/vendor/github.com/docker/swarmkit/manager/state/store/resources.go index 4e1ec7154b..1f2c3904f1 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/resources.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/resources.go @@ -40,21 +40,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - resources, err := FindResources(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Resources)) + for i, x := range snapshot.Resources { + toStoreObj[i] = resourceEntry{x} } - for _, r := range resources { - if err := DeleteResource(tx, r.ID); err != nil { - return err - } - } - for _, r := range snapshot.Resources { - if err := CreateResource(tx, r); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableResource, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { @@ -82,6 +72,14 @@ func (r resourceEntry) CopyStoreObject() api.StoreObject { return resourceEntry{Resource: r.Resource.Copy()} } +// ensure that when update events are emitted, we unwrap resourceEntry +func (r resourceEntry) EventUpdate(oldObject api.StoreObject) api.Event { + if oldObject != nil { + return api.EventUpdateResource{Resource: r.Resource, OldResource: oldObject.(resourceEntry).Resource} + } + return api.EventUpdateResource{Resource: r.Resource} +} + func confirmExtension(tx Tx, r *api.Resource) error { // There must be an extension corresponding to the Kind field. extensions, err := FindExtensions(tx, ByName(r.Kind)) diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/secrets.go b/vendor/github.com/docker/swarmkit/manager/state/store/secrets.go index 203c94c974..bf5653fd72 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/secrets.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/secrets.go @@ -37,21 +37,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - secrets, err := FindSecrets(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Secrets)) + for i, x := range snapshot.Secrets { + toStoreObj[i] = x } - for _, s := range secrets { - if err := DeleteSecret(tx, s.ID); err != nil { - return err - } - } - for _, s := range snapshot.Secrets { - if err := CreateSecret(tx, s); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableSecret, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/services.go b/vendor/github.com/docker/swarmkit/manager/state/store/services.go index 884bc3533d..1adbb87fe4 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/services.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/services.go @@ -58,21 +58,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - services, err := FindServices(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Services)) + for i, x := range snapshot.Services { + toStoreObj[i] = x } - for _, s := range services { - if err := DeleteService(tx, s.ID); err != nil { - return err - } - } - for _, s := range snapshot.Services { - if err := CreateService(tx, s); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableService, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { diff --git a/vendor/github.com/docker/swarmkit/manager/state/store/tasks.go b/vendor/github.com/docker/swarmkit/manager/state/store/tasks.go index b8d8a731c9..bf31d764fb 100644 --- a/vendor/github.com/docker/swarmkit/manager/state/store/tasks.go +++ b/vendor/github.com/docker/swarmkit/manager/state/store/tasks.go @@ -82,21 +82,11 @@ func init() { return err }, Restore: func(tx Tx, snapshot *api.StoreSnapshot) error { - tasks, err := FindTasks(tx, All) - if err != nil { - return err + toStoreObj := make([]api.StoreObject, len(snapshot.Tasks)) + for i, x := range snapshot.Tasks { + toStoreObj[i] = x } - for _, t := range tasks { - if err := DeleteTask(tx, t.ID); err != nil { - return err - } - } - for _, t := range snapshot.Tasks { - if err := CreateTask(tx, t); err != nil { - return err - } - } - return nil + return RestoreTable(tx, tableTask, toStoreObj) }, ApplyStoreAction: func(tx Tx, sa api.StoreAction) error { switch v := sa.Target.(type) { diff --git a/vendor/github.com/docker/swarmkit/node/node.go b/vendor/github.com/docker/swarmkit/node/node.go index 29badd06ed..77fe5b3d75 100644 --- a/vendor/github.com/docker/swarmkit/node/node.go +++ b/vendor/github.com/docker/swarmkit/node/node.go @@ -28,7 +28,6 @@ import ( "github.com/docker/swarmkit/manager" "github.com/docker/swarmkit/manager/encryption" "github.com/docker/swarmkit/remotes" - "github.com/docker/swarmkit/watch" "github.com/docker/swarmkit/xnet" grpc_prometheus "github.com/grpc-ecosystem/go-grpc-prometheus" "github.com/pkg/errors" @@ -276,10 +275,11 @@ func (n *Node) run(ctx context.Context) (err error) { }(ctx) paths := ca.NewConfigPaths(filepath.Join(n.config.StateDir, certDirectory)) - securityConfig, err := n.loadSecurityConfig(ctx, paths) + securityConfig, secConfigCancel, err := n.loadSecurityConfig(ctx, paths) if err != nil { return err } + defer secConfigCancel() renewer := ca.NewTLSRenewer(securityConfig, n.connBroker, paths.RootCA) @@ -509,11 +509,8 @@ waitPeer: default: } - secChangeQueue := watch.NewQueue() - defer secChangeQueue.Close() - secChangesCh, secChangesCancel := secChangeQueue.Watch() + secChangesCh, secChangesCancel := securityConfig.Watch() defer secChangesCancel() - securityConfig.SetWatch(secChangeQueue) rootCA := securityConfig.RootCA() issuer := securityConfig.IssuerInfo() @@ -668,28 +665,31 @@ func (n *Node) Remotes() []api.Peer { return remotes } -func (n *Node) loadSecurityConfig(ctx context.Context, paths *ca.SecurityConfigPaths) (*ca.SecurityConfig, error) { - var securityConfig *ca.SecurityConfig +func (n *Node) loadSecurityConfig(ctx context.Context, paths *ca.SecurityConfigPaths) (*ca.SecurityConfig, func() error, error) { + var ( + securityConfig *ca.SecurityConfig + cancel func() error + ) krw := ca.NewKeyReadWriter(paths.Node, n.unlockKey, &manager.RaftDEKData{}) if err := krw.Migrate(); err != nil { - return nil, err + return nil, nil, err } // Check if we already have a valid certificates on disk. rootCA, err := ca.GetLocalRootCA(paths.RootCA) if err != nil && err != ca.ErrNoLocalRootCA { - return nil, err + return nil, nil, err } if err == nil { // if forcing a new cluster, we allow the certificates to be expired - a new set will be generated - securityConfig, err = ca.LoadSecurityConfig(ctx, rootCA, krw, n.config.ForceNewCluster) + securityConfig, cancel, err = ca.LoadSecurityConfig(ctx, rootCA, krw, n.config.ForceNewCluster) if err != nil { _, isInvalidKEK := errors.Cause(err).(ca.ErrInvalidKEK) if isInvalidKEK { - return nil, ErrInvalidUnlockKey + return nil, nil, ErrInvalidUnlockKey } else if !os.IsNotExist(err) { - return nil, errors.Wrapf(err, "error while loading TLS certificate in %s", paths.Node.Cert) + return nil, nil, errors.Wrapf(err, "error while loading TLS certificate in %s", paths.Node.Cert) } } } @@ -704,16 +704,16 @@ func (n *Node) loadSecurityConfig(ctx context.Context, paths *ca.SecurityConfigP krw = ca.NewKeyReadWriter(paths.Node, n.unlockKey, &manager.RaftDEKData{}) rootCA, err = ca.CreateRootCA(ca.DefaultRootCN) if err != nil { - return nil, err + return nil, nil, err } if err := ca.SaveRootCA(rootCA, paths.RootCA); err != nil { - return nil, err + return nil, nil, err } log.G(ctx).Debug("generated CA key and certificate") } else if err == ca.ErrNoLocalRootCA { // from previous error loading the root CA from disk rootCA, err = ca.DownloadRootCA(ctx, paths.RootCA, n.config.JoinToken, n.connBroker) if err != nil { - return nil, err + return nil, nil, err } log.G(ctx).Debug("downloaded CA certificate") } @@ -724,25 +724,25 @@ func (n *Node) loadSecurityConfig(ctx context.Context, paths *ca.SecurityConfigP // - We wait for CreateSecurityConfig to finish since we need a certificate to operate. // Attempt to load certificate from disk - securityConfig, err = ca.LoadSecurityConfig(ctx, rootCA, krw, n.config.ForceNewCluster) + securityConfig, cancel, err = ca.LoadSecurityConfig(ctx, rootCA, krw, n.config.ForceNewCluster) if err == nil { log.G(ctx).WithFields(logrus.Fields{ "node.id": securityConfig.ClientTLSCreds.NodeID(), }).Debugf("loaded TLS certificate") } else { if _, ok := errors.Cause(err).(ca.ErrInvalidKEK); ok { - return nil, ErrInvalidUnlockKey + return nil, nil, ErrInvalidUnlockKey } log.G(ctx).WithError(err).Debugf("no node credentials found in: %s", krw.Target()) - securityConfig, err = rootCA.CreateSecurityConfig(ctx, krw, ca.CertificateRequestConfig{ + securityConfig, cancel, err = rootCA.CreateSecurityConfig(ctx, krw, ca.CertificateRequestConfig{ Token: n.config.JoinToken, Availability: n.config.Availability, ConnBroker: n.connBroker, }) if err != nil { - return nil, err + return nil, nil, err } } } @@ -753,7 +753,7 @@ func (n *Node) loadSecurityConfig(ctx context.Context, paths *ca.SecurityConfigP n.roleCond.Broadcast() n.Unlock() - return securityConfig, nil + return securityConfig, cancel, nil } func (n *Node) initManagerConnection(ctx context.Context, ready chan<- struct{}) error { diff --git a/vendor/github.com/docker/swarmkit/template/context.go b/vendor/github.com/docker/swarmkit/template/context.go index d26e155be4..e3badef532 100644 --- a/vendor/github.com/docker/swarmkit/template/context.go +++ b/vendor/github.com/docker/swarmkit/template/context.go @@ -14,6 +14,12 @@ import ( "github.com/pkg/errors" ) +// Platform holds information about the underlying platform of the node +type Platform struct { + Architecture string + OS string +} + // Context defines the strict set of values that can be injected into a // template expression in SwarmKit data structure. // NOTE: Be very careful adding any fields to this structure with types @@ -27,7 +33,9 @@ type Context struct { } Node struct { - ID string + ID string + Hostname string + Platform Platform } Task struct { @@ -41,16 +49,25 @@ type Context struct { } } -// NewContextFromTask returns a new template context from the data available in -// task. The provided context can then be used to populate runtime values in a +// NewContext returns a new template context from the data available in the +// task and the node where it is scheduled to run. +// The provided context can then be used to populate runtime values in a // ContainerSpec. -func NewContextFromTask(t *api.Task) (ctx Context) { +func NewContext(n *api.NodeDescription, t *api.Task) (ctx Context) { ctx.Service.ID = t.ServiceID ctx.Service.Name = t.ServiceAnnotations.Name ctx.Service.Labels = t.ServiceAnnotations.Labels ctx.Node.ID = t.NodeID + // Add node information to context only if we have them available + if n != nil { + ctx.Node.Hostname = n.Hostname + ctx.Node.Platform = Platform{ + Architecture: n.Platform.Architecture, + OS: n.Platform.OS, + } + } ctx.Task.ID = t.ID ctx.Task.Name = naming.Task(t) @@ -157,12 +174,13 @@ func (ctx PayloadContext) envGetter(variable string) (string, error) { } // NewPayloadContextFromTask returns a new template context from the data -// available in the task. This context also provides access to the configs +// available in the task and the node where it is scheduled to run. +// This context also provides access to the configs // and secrets that the task has access to. The provided context can then // be used to populate runtime values in a templated config or secret. -func NewPayloadContextFromTask(t *api.Task, dependencies exec.DependencyGetter) (ctx PayloadContext) { +func NewPayloadContextFromTask(node *api.NodeDescription, t *api.Task, dependencies exec.DependencyGetter) (ctx PayloadContext) { return PayloadContext{ - Context: NewContextFromTask(t), + Context: NewContext(node, t), t: t, restrictedSecrets: secrets.Restrict(dependencies.Secrets(), t), restrictedConfigs: configs.Restrict(dependencies.Configs(), t), diff --git a/vendor/github.com/docker/swarmkit/template/expand.go b/vendor/github.com/docker/swarmkit/template/expand.go index e45c36252d..45ca97114e 100644 --- a/vendor/github.com/docker/swarmkit/template/expand.go +++ b/vendor/github.com/docker/swarmkit/template/expand.go @@ -10,18 +10,19 @@ import ( ) // ExpandContainerSpec expands templated fields in the runtime using the task -// state. Templating is all evaluated on the agent-side, before execution. +// state and the node where it is scheduled to run. +// Templating is all evaluated on the agent-side, before execution. // // Note that these are projected only on runtime values, since active task // values are typically manipulated in the manager. -func ExpandContainerSpec(t *api.Task) (*api.ContainerSpec, error) { +func ExpandContainerSpec(n *api.NodeDescription, t *api.Task) (*api.ContainerSpec, error) { container := t.Spec.GetContainer() if container == nil { return nil, errors.Errorf("task missing ContainerSpec to expand") } container = container.Copy() - ctx := NewContextFromTask(t) + ctx := NewContext(n, t) var err error container.Env, err = expandEnv(ctx, container.Env) @@ -128,12 +129,12 @@ func expandPayload(ctx PayloadContext, payload []byte) ([]byte, error) { // ExpandSecretSpec expands the template inside the secret payload, if any. // Templating is evaluated on the agent-side. -func ExpandSecretSpec(s *api.Secret, t *api.Task, dependencies exec.DependencyGetter) (*api.SecretSpec, error) { +func ExpandSecretSpec(s *api.Secret, node *api.NodeDescription, t *api.Task, dependencies exec.DependencyGetter) (*api.SecretSpec, error) { if s.Spec.Templating == nil { return &s.Spec, nil } if s.Spec.Templating.Name == "golang" { - ctx := NewPayloadContextFromTask(t, dependencies) + ctx := NewPayloadContextFromTask(node, t, dependencies) secretSpec := s.Spec.Copy() var err error @@ -145,12 +146,12 @@ func ExpandSecretSpec(s *api.Secret, t *api.Task, dependencies exec.DependencyGe // ExpandConfigSpec expands the template inside the config payload, if any. // Templating is evaluated on the agent-side. -func ExpandConfigSpec(c *api.Config, t *api.Task, dependencies exec.DependencyGetter) (*api.ConfigSpec, error) { +func ExpandConfigSpec(c *api.Config, node *api.NodeDescription, t *api.Task, dependencies exec.DependencyGetter) (*api.ConfigSpec, error) { if c.Spec.Templating == nil { return &c.Spec, nil } if c.Spec.Templating.Name == "golang" { - ctx := NewPayloadContextFromTask(t, dependencies) + ctx := NewPayloadContextFromTask(node, t, dependencies) configSpec := c.Spec.Copy() var err error diff --git a/vendor/github.com/docker/swarmkit/template/getter.go b/vendor/github.com/docker/swarmkit/template/getter.go index f06c438c25..05e5de72eb 100644 --- a/vendor/github.com/docker/swarmkit/template/getter.go +++ b/vendor/github.com/docker/swarmkit/template/getter.go @@ -9,11 +9,12 @@ import ( type templatedSecretGetter struct { dependencies exec.DependencyGetter t *api.Task + node *api.NodeDescription } // NewTemplatedSecretGetter returns a SecretGetter that evaluates templates. -func NewTemplatedSecretGetter(dependencies exec.DependencyGetter, t *api.Task) exec.SecretGetter { - return templatedSecretGetter{dependencies: dependencies, t: t} +func NewTemplatedSecretGetter(dependencies exec.DependencyGetter, t *api.Task, node *api.NodeDescription) exec.SecretGetter { + return templatedSecretGetter{dependencies: dependencies, t: t, node: node} } func (t templatedSecretGetter) Get(secretID string) (*api.Secret, error) { @@ -31,7 +32,7 @@ func (t templatedSecretGetter) Get(secretID string) (*api.Secret, error) { return secret, err } - newSpec, err := ExpandSecretSpec(secret, t.t, t.dependencies) + newSpec, err := ExpandSecretSpec(secret, t.node, t.t, t.dependencies) if err != nil { return secret, errors.Wrapf(err, "failed to expand templated secret %s", secretID) } @@ -44,11 +45,12 @@ func (t templatedSecretGetter) Get(secretID string) (*api.Secret, error) { type templatedConfigGetter struct { dependencies exec.DependencyGetter t *api.Task + node *api.NodeDescription } // NewTemplatedConfigGetter returns a ConfigGetter that evaluates templates. -func NewTemplatedConfigGetter(dependencies exec.DependencyGetter, t *api.Task) exec.ConfigGetter { - return templatedConfigGetter{dependencies: dependencies, t: t} +func NewTemplatedConfigGetter(dependencies exec.DependencyGetter, t *api.Task, node *api.NodeDescription) exec.ConfigGetter { + return templatedConfigGetter{dependencies: dependencies, t: t, node: node} } func (t templatedConfigGetter) Get(configID string) (*api.Config, error) { @@ -66,7 +68,7 @@ func (t templatedConfigGetter) Get(configID string) (*api.Config, error) { return config, err } - newSpec, err := ExpandConfigSpec(config, t.t, t.dependencies) + newSpec, err := ExpandConfigSpec(config, t.node, t.t, t.dependencies) if err != nil { return config, errors.Wrapf(err, "failed to expand templated config %s", configID) } @@ -82,10 +84,10 @@ type templatedDependencyGetter struct { } // NewTemplatedDependencyGetter returns a DependencyGetter that evaluates templates. -func NewTemplatedDependencyGetter(dependencies exec.DependencyGetter, t *api.Task) exec.DependencyGetter { +func NewTemplatedDependencyGetter(dependencies exec.DependencyGetter, t *api.Task, node *api.NodeDescription) exec.DependencyGetter { return templatedDependencyGetter{ - secrets: NewTemplatedSecretGetter(dependencies, t), - configs: NewTemplatedConfigGetter(dependencies, t), + secrets: NewTemplatedSecretGetter(dependencies, t, node), + configs: NewTemplatedConfigGetter(dependencies, t, node), } } diff --git a/vendor/github.com/docker/swarmkit/vendor.conf b/vendor/github.com/docker/swarmkit/vendor.conf index 4f5d293b8b..73692eeee3 100644 --- a/vendor/github.com/docker/swarmkit/vendor.conf +++ b/vendor/github.com/docker/swarmkit/vendor.conf @@ -10,7 +10,7 @@ github.com/grpc-ecosystem/go-grpc-prometheus 6b7015e65d366bf3f19b2b2a000a831940f github.com/docker/go-metrics d466d4f6fd960e01820085bd7e1a24426ee7ef18 # etcd/raft -github.com/coreos/etcd ea5389a79f40206170582c1ea076191b8622cb8e https://github.com/aaronlehmann/etcd # for https://github.com/coreos/etcd/pull/7830 +github.com/coreos/etcd v3.2.1 github.com/coreos/go-systemd v12 github.com/coreos/pkg v3 github.com/prometheus/client_golang 52437c81da6b127a9925d17eb3a382a2e5fd395e @@ -28,18 +28,16 @@ github.com/docker/libnetwork 37e20af882e13dd01ade3658b7aabdae3412118b github.com/docker/libtrust 9cbd2a1374f46905c68a4eb3694a130610adc62a github.com/opencontainers/runc b6b70e53451794e8333e9b602cc096b47a20bd0f github.com/opencontainers/go-digest a6d0ee40d4207ea02364bd3b9e8e77b9159ba1eb -github.com/opencontainers/image-spec f03dbe35d449c54915d235f1a3cf8f585a24babe +github.com/opencontainers/image-spec 372ad780f63454fbbbbcc7cf80e5b90245c13e13 # containerd executor -github.com/containerd/containerd 7fc91b05917e93d474fab9465547d44eacd10ce3 -github.com/containerd/continuity f4ad4294c92f596c9241947c416d1297f9faf3ea +github.com/containerd/containerd 76697ac8cbf357a19beb58e4805a81fe48cf7974 github.com/containerd/fifo 69b99525e472735860a5269b75af1970142b3062 github.com/opencontainers/runtime-spec v1.0.0-rc5 -github.com/nightlyone/lockfile 1d49c987357a327b5b03aa84cbddd582c328615d golang.org/x/sync 450f422ab23cf9881c94e2db30cac0eb1b7cf80c github.com/davecgh/go-spew 5215b55f46b2b919f50a1df0eaa5886afe4e3b3d -github.com/Microsoft/go-winio f778f05015353be65d242f3fedc18695756153bb +github.com/Microsoft/go-winio v0.4.2 github.com/Sirupsen/logrus v0.11.0 github.com/beorn7/perks 4c0e84591b9aa9e6dcfdf3e020114cd81f89d5f9 github.com/boltdb/bolt e72f08ddb5a52992c0a44c7dda9316c7333938b2 @@ -52,7 +50,7 @@ github.com/hashicorp/golang-lru a0d98a5f288019575c6d1f4bb1573fef2d1fcdc4 github.com/inconshreveable/mousetrap 76626ae9c91c4f2a10f34cad8ce83ea42c93bb75 github.com/phayes/permbits f7e3ac5e859d0b919c5068d581cc4c5d4f4f9bc5 github.com/pivotal-golang/clock 3fd3c1944c59d9742e1cd333672181cd1a6f9fa0 -github.com/pkg/errors 01fa4104b9c248c8945d14d9f128454d5b28d595 +github.com/pkg/errors 645ef00459ed84a119197bfb8d8205042c6df63d github.com/pmezard/go-difflib 792786c7400a136282c1664665ae0a8db921c6c2 github.com/rcrowley/go-metrics 51425a2415d21afadfd55cd93432c0bc69e9598d github.com/spf13/cobra 8e91712f174ced10270cf66615e0a9127e7c4de5 diff --git a/vendor/github.com/docker/swarmkit/watch/queue/queue.go b/vendor/github.com/docker/swarmkit/watch/queue/queue.go new file mode 100644 index 0000000000..10bdb92080 --- /dev/null +++ b/vendor/github.com/docker/swarmkit/watch/queue/queue.go @@ -0,0 +1,158 @@ +package queue + +import ( + "container/list" + "fmt" + "sync" + + "github.com/Sirupsen/logrus" + "github.com/docker/go-events" +) + +// ErrQueueFull is returned by a Write operation when that Write causes the +// queue to reach its size limit. +var ErrQueueFull = fmt.Errorf("queue closed due to size limit") + +// LimitQueue accepts all messages into a queue for asynchronous consumption by +// a sink until an upper limit of messages is reached. When that limit is +// reached, the entire Queue is Closed. It is thread safe but the +// sink must be reliable or events will be dropped. +// If a size of 0 is provided, the LimitQueue is considered limitless. +type LimitQueue struct { + dst events.Sink + events *list.List + limit uint64 + cond *sync.Cond + mu sync.Mutex + closed bool + full chan struct{} + fullClosed bool +} + +// NewLimitQueue returns a queue to the provided Sink dst. +func NewLimitQueue(dst events.Sink, limit uint64) *LimitQueue { + eq := LimitQueue{ + dst: dst, + events: list.New(), + limit: limit, + full: make(chan struct{}), + } + + eq.cond = sync.NewCond(&eq.mu) + go eq.run() + return &eq +} + +// Write accepts the events into the queue, only failing if the queue has +// been closed or has reached its size limit. +func (eq *LimitQueue) Write(event events.Event) error { + eq.mu.Lock() + defer eq.mu.Unlock() + + if eq.closed { + return events.ErrSinkClosed + } + + if eq.limit > 0 && uint64(eq.events.Len()) >= eq.limit { + // If the limit has been reached, don't write the event to the queue, + // and close the Full channel. This notifies listeners that the queue + // is now full, but the sink is still permitted to consume events. It's + // the responsibility of the listener to decide whether they want to + // live with dropped events or whether they want to Close() the + // LimitQueue + if !eq.fullClosed { + eq.fullClosed = true + close(eq.full) + } + return ErrQueueFull + } + + eq.events.PushBack(event) + eq.cond.Signal() // signal waiters + + return nil +} + +// Full returns a channel that is closed when the queue becomes full for the +// first time. +func (eq *LimitQueue) Full() chan struct{} { + return eq.full +} + +// Close shuts down the event queue, flushing all events +func (eq *LimitQueue) Close() error { + eq.mu.Lock() + defer eq.mu.Unlock() + + if eq.closed { + return nil + } + + // set the closed flag + eq.closed = true + eq.cond.Signal() // signal flushes queue + eq.cond.Wait() // wait for signal from last flush + return eq.dst.Close() +} + +// run is the main goroutine to flush events to the target sink. +func (eq *LimitQueue) run() { + for { + event := eq.next() + + if event == nil { + return // nil block means event queue is closed. + } + + if err := eq.dst.Write(event); err != nil { + // TODO(aaronl): Dropping events could be bad depending + // on the application. We should have a way of + // communicating this condition. However, logging + // at a log level above debug may not be appropriate. + // Eventually, go-events should not use logrus at all, + // and should bubble up conditions like this through + // error values. + logrus.WithFields(logrus.Fields{ + "event": event, + "sink": eq.dst, + }).WithError(err).Debug("eventqueue: dropped event") + } + } +} + +// Len returns the number of items that are currently stored in the queue and +// not consumed by its sink. +func (eq *LimitQueue) Len() int { + eq.mu.Lock() + defer eq.mu.Unlock() + return eq.events.Len() +} + +func (eq *LimitQueue) String() string { + eq.mu.Lock() + defer eq.mu.Unlock() + return fmt.Sprintf("%v", eq.events) +} + +// next encompasses the critical section of the run loop. When the queue is +// empty, it will block on the condition. If new data arrives, it will wake +// and return a block. When closed, a nil slice will be returned. +func (eq *LimitQueue) next() events.Event { + eq.mu.Lock() + defer eq.mu.Unlock() + + for eq.events.Len() < 1 { + if eq.closed { + eq.cond.Broadcast() + return nil + } + + eq.cond.Wait() + } + + front := eq.events.Front() + block := front.Value.(events.Event) + eq.events.Remove(front) + + return block +} diff --git a/vendor/github.com/docker/swarmkit/watch/sinks.go b/vendor/github.com/docker/swarmkit/watch/sinks.go new file mode 100644 index 0000000000..b22b4842c3 --- /dev/null +++ b/vendor/github.com/docker/swarmkit/watch/sinks.go @@ -0,0 +1,95 @@ +package watch + +import ( + "fmt" + "time" + + events "github.com/docker/go-events" +) + +// ErrSinkTimeout is returned from the Write method when a sink times out. +var ErrSinkTimeout = fmt.Errorf("timeout exceeded, tearing down sink") + +// timeoutSink is a sink that wraps another sink with a timeout. If the +// embedded sink fails to complete a Write operation within the specified +// timeout, the Write operation of the timeoutSink fails. +type timeoutSink struct { + timeout time.Duration + sink events.Sink +} + +func (s timeoutSink) Write(event events.Event) error { + errChan := make(chan error) + go func(c chan<- error) { + c <- s.sink.Write(event) + }(errChan) + + timer := time.NewTimer(s.timeout) + select { + case err := <-errChan: + timer.Stop() + return err + case <-timer.C: + s.sink.Close() + return ErrSinkTimeout + } +} + +func (s timeoutSink) Close() error { + return s.sink.Close() +} + +// dropErrClosed is a sink that suppresses ErrSinkClosed from Write, to avoid +// debug log messages that may be confusing. It is possible that the queue +// will try to write an event to its destination channel while the queue is +// being removed from the broadcaster. Since the channel is closed before the +// queue, there is a narrow window when this is possible. In some event-based +// dropping events when a sink is removed from a broadcaster is a problem, but +// for the usage in this watch package that's the expected behavior. +type dropErrClosed struct { + sink events.Sink +} + +func (s dropErrClosed) Write(event events.Event) error { + err := s.sink.Write(event) + if err == events.ErrSinkClosed { + return nil + } + return err +} + +func (s dropErrClosed) Close() error { + return s.sink.Close() +} + +// dropErrClosedChanGen is a ChannelSinkGenerator for dropErrClosed sinks wrapping +// unbuffered channels. +type dropErrClosedChanGen struct{} + +func (s *dropErrClosedChanGen) NewChannelSink() (events.Sink, *events.Channel) { + ch := events.NewChannel(0) + return dropErrClosed{sink: ch}, ch +} + +// TimeoutDropErrChanGen is a ChannelSinkGenerator that creates a channel, +// wrapped by the dropErrClosed sink and a timeout. +type TimeoutDropErrChanGen struct { + timeout time.Duration +} + +// NewChannelSink creates a new sink chain of timeoutSink->dropErrClosed->Channel +func (s *TimeoutDropErrChanGen) NewChannelSink() (events.Sink, *events.Channel) { + ch := events.NewChannel(0) + return timeoutSink{ + timeout: s.timeout, + sink: dropErrClosed{ + sink: ch, + }, + }, ch +} + +// NewTimeoutDropErrSinkGen returns a generator of timeoutSinks wrapping dropErrClosed +// sinks, wrapping unbuffered channel sinks. +func NewTimeoutDropErrSinkGen(timeout time.Duration) ChannelSinkGenerator { + return &TimeoutDropErrChanGen{timeout: timeout} +} diff --git a/vendor/github.com/docker/swarmkit/watch/watch.go b/vendor/github.com/docker/swarmkit/watch/watch.go index a468237015..ed5b834452 100644 --- a/vendor/github.com/docker/swarmkit/watch/watch.go +++ b/vendor/github.com/docker/swarmkit/watch/watch.go @@ -1,48 +1,81 @@ package watch import ( + "context" + "fmt" "sync" + "time" "github.com/docker/go-events" + "github.com/docker/swarmkit/watch/queue" ) -// dropErrClosed is a sink that suppresses ErrSinkClosed from Write, to avoid -// debug log messages that may be confusing. It is possible that the queue -// will try to write an event to its destination channel while the queue is -// being removed from the broadcaster. Since the channel is closed before the -// queue, there is a narrow window when this is possible. In some event-based -// dropping events when a sink is removed from a broadcaster is a problem, but -// for the usage in this watch package that's the expected behavior. -type dropErrClosed struct { - sink events.Sink -} - -func (s dropErrClosed) Write(event events.Event) error { - err := s.sink.Write(event) - if err == events.ErrSinkClosed { - return nil - } - return err -} - -func (s dropErrClosed) Close() error { - return s.sink.Close() +// ChannelSinkGenerator is a constructor of sinks that eventually lead to a +// channel. +type ChannelSinkGenerator interface { + NewChannelSink() (events.Sink, *events.Channel) } // Queue is the structure used to publish events and watch for them. type Queue struct { + sinkGen ChannelSinkGenerator + // limit is the max number of items to be held in memory for a watcher + limit uint64 mu sync.Mutex broadcast *events.Broadcaster - cancelFuncs map[*events.Channel]func() + cancelFuncs map[events.Sink]func() + + // closeOutChan indicates whether the watchers' channels should be closed + // when a watcher queue reaches its limit or when the Close method of the + // sink is called. + closeOutChan bool } // NewQueue creates a new publish/subscribe queue which supports watchers. // The channels that it will create for subscriptions will have the buffer // size specified by buffer. -func NewQueue() *Queue { - return &Queue{ - broadcast: events.NewBroadcaster(), - cancelFuncs: make(map[*events.Channel]func()), +func NewQueue(options ...func(*Queue) error) *Queue { + // Create a queue with the default values + q := &Queue{ + sinkGen: &dropErrClosedChanGen{}, + broadcast: events.NewBroadcaster(), + cancelFuncs: make(map[events.Sink]func()), + limit: 0, + closeOutChan: false, + } + + for _, option := range options { + err := option(q) + if err != nil { + panic(fmt.Sprintf("Failed to apply options to queue: %s", err)) + } + } + + return q +} + +// WithTimeout returns a functional option for a queue that sets a write timeout +func WithTimeout(timeout time.Duration) func(*Queue) error { + return func(q *Queue) error { + q.sinkGen = NewTimeoutDropErrSinkGen(timeout) + return nil + } +} + +// WithCloseOutChan returns a functional option for a queue whose watcher +// channel is closed when no more events are expected to be sent to the watcher. +func WithCloseOutChan() func(*Queue) error { + return func(q *Queue) error { + q.closeOutChan = true + return nil + } +} + +// WithLimit returns a functional option for a queue with a max size limit. +func WithLimit(limit uint64) func(*Queue) error { + return func(q *Queue) error { + q.limit = limit + return nil } } @@ -52,13 +85,21 @@ func (q *Queue) Watch() (eventq chan events.Event, cancel func()) { return q.CallbackWatch(nil) } +// WatchContext returns a channel where all items published to the queue will +// be received. The channel will be closed when the provided context is +// cancelled. +func (q *Queue) WatchContext(ctx context.Context) (eventq chan events.Event) { + return q.CallbackWatchContext(ctx, nil) +} + // CallbackWatch returns a channel which will receive all events published to // the queue from this point that pass the check in the provided callback // function. The returned cancel function will stop the flow of events and // close the channel. func (q *Queue) CallbackWatch(matcher events.Matcher) (eventq chan events.Event, cancel func()) { - ch := events.NewChannel(0) - sink := events.Sink(events.NewQueue(dropErrClosed{sink: ch})) + chanSink, ch := q.sinkGen.NewChannelSink() + lq := queue.NewLimitQueue(chanSink, q.limit) + sink := events.Sink(lq) if matcher != nil { sink = events.NewFilter(sink, matcher) @@ -72,19 +113,68 @@ func (q *Queue) CallbackWatch(matcher events.Matcher) (eventq chan events.Event, sink.Close() } - q.mu.Lock() - q.cancelFuncs[ch] = cancelFunc - q.mu.Unlock() - return ch.C, func() { + externalCancelFunc := func() { q.mu.Lock() - cancelFunc := q.cancelFuncs[ch] - delete(q.cancelFuncs, ch) + cancelFunc := q.cancelFuncs[sink] + delete(q.cancelFuncs, sink) q.mu.Unlock() if cancelFunc != nil { cancelFunc() } } + + q.mu.Lock() + q.cancelFuncs[sink] = cancelFunc + q.mu.Unlock() + + // If the output channel shouldn't be closed and the queue is limitless, + // there's no need for an additional goroutine. + if !q.closeOutChan && q.limit == 0 { + return ch.C, externalCancelFunc + } + + outChan := make(chan events.Event) + go func() { + for { + select { + case <-ch.Done(): + // Close the output channel if the ChannelSink is Done for any + // reason. This can happen if the cancelFunc is called + // externally or if it has been closed by a wrapper sink, such + // as the TimeoutSink. + if q.closeOutChan { + close(outChan) + } + externalCancelFunc() + return + case <-lq.Full(): + // Close the output channel and tear down the Queue if the + // LimitQueue becomes full. + if q.closeOutChan { + close(outChan) + } + externalCancelFunc() + return + case event := <-ch.C: + outChan <- event + } + } + }() + + return outChan, externalCancelFunc +} + +// CallbackWatchContext returns a channel where all items published to the queue will +// be received. The channel will be closed when the provided context is +// cancelled. +func (q *Queue) CallbackWatchContext(ctx context.Context, matcher events.Matcher) (eventq chan events.Event) { + c, cancel := q.CallbackWatch(matcher) + go func() { + <-ctx.Done() + cancel() + }() + return c } // Publish adds an item to the queue. @@ -100,7 +190,7 @@ func (q *Queue) Close() error { for _, cancelFunc := range q.cancelFuncs { cancelFunc() } - q.cancelFuncs = make(map[*events.Channel]func()) + q.cancelFuncs = make(map[events.Sink]func()) q.mu.Unlock() return q.broadcast.Close()