From 7801f9edac070199be889af778d951b5a9154f89 Mon Sep 17 00:00:00 2001 From: Azhng Date: Wed, 4 Aug 2021 10:17:22 -0400 Subject: [PATCH] sql,jobs: create SQL Stats Compaction Job and resumer This commit introduces the SQL Stats Compaction job type and a barebones implementation of the SQL Stats compaction. Release note: None --- .../settings/settings-for-tenants.txt | 1 + docs/generated/settings/settings.html | 1 + pkg/jobs/jobspb/jobs.pb.go | 1102 +++++++++++------ pkg/jobs/jobspb/jobs.proto | 13 +- pkg/jobs/jobspb/wrap.go | 12 +- pkg/sql/BUILD.bazel | 2 + pkg/sql/compact_sql_stats.go | 80 ++ pkg/sql/conn_executor.go | 3 +- .../sqlstats/persistedsqlstats/BUILD.bazel | 15 + .../persistedsqlstats/cluster_settings.go | 9 + .../persistedsqlstats/compaction_exec.go | 181 +++ .../compaction_scheduling.go | 71 ++ .../persistedsqlstats/compaction_test.go | 280 +++++ .../sqlstats/persistedsqlstats/provider.go | 19 +- pkg/ts/catalog/chart_catalog.go | 12 + pkg/util/jobutil/BUILD.bazel | 1 + 16 files changed, 1446 insertions(+), 356 deletions(-) create mode 100644 pkg/sql/compact_sql_stats.go create mode 100644 pkg/sql/sqlstats/persistedsqlstats/compaction_exec.go create mode 100644 pkg/sql/sqlstats/persistedsqlstats/compaction_scheduling.go create mode 100644 pkg/sql/sqlstats/persistedsqlstats/compaction_test.go diff --git a/docs/generated/settings/settings-for-tenants.txt b/docs/generated/settings/settings-for-tenants.txt index bd34acb62716..b66c08f823c4 100644 --- a/docs/generated/settings/settings-for-tenants.txt +++ b/docs/generated/settings/settings-for-tenants.txt @@ -135,6 +135,7 @@ sql.stats.flush.enabled boolean true if set, SQL execution statistics are period sql.stats.flush.interval duration 1h0m0s the interval at which SQL execution statistics are flushed to disk sql.stats.histogram_collection.enabled boolean true histogram collection mode sql.stats.multi_column_collection.enabled boolean true multi-column statistics collection mode +sql.stats.persisted_rows.max integer 10000 maximum number of rows of statement and transaction statistics that will be persisted in the system tables sql.stats.post_events.enabled boolean false if set, an event is logged for every CREATE STATISTICS job sql.temp_object_cleaner.cleanup_interval duration 30m0s how often to clean up orphaned temporary objects sql.trace.log_statement_execute boolean false set to true to enable logging of executed statements diff --git a/docs/generated/settings/settings.html b/docs/generated/settings/settings.html index e4e94072f5ef..45280ef771fc 100644 --- a/docs/generated/settings/settings.html +++ b/docs/generated/settings/settings.html @@ -139,6 +139,7 @@ sql.stats.flush.intervalduration1h0m0sthe interval at which SQL execution statistics are flushed to disk sql.stats.histogram_collection.enabledbooleantruehistogram collection mode sql.stats.multi_column_collection.enabledbooleantruemulti-column statistics collection mode +sql.stats.persisted_rows.maxinteger10000maximum number of rows of statement and transaction statistics that will be persisted in the system tables sql.stats.post_events.enabledbooleanfalseif set, an event is logged for every CREATE STATISTICS job sql.temp_object_cleaner.cleanup_intervalduration30m0show often to clean up orphaned temporary objects sql.trace.log_statement_executebooleanfalseset to true to enable logging of executed statements diff --git a/pkg/jobs/jobspb/jobs.pb.go b/pkg/jobs/jobspb/jobs.pb.go index a4d488b4d84e..a11773321007 100644 --- a/pkg/jobs/jobspb/jobs.pb.go +++ b/pkg/jobs/jobspb/jobs.pb.go @@ -106,10 +106,11 @@ const ( TypeSchemaChangeGC Type = 8 // We can't name this TYPE_SCHEMA_CHANGE due to how proto generates actual // names for this enum, which cause a conflict with the SCHEMA_CHANGE entry. - TypeTypeSchemaChange Type = 9 - TypeStreamIngestion Type = 10 - TypeNewSchemaChange Type = 11 - TypeMigration Type = 12 + TypeTypeSchemaChange Type = 9 + TypeStreamIngestion Type = 10 + TypeNewSchemaChange Type = 11 + TypeMigration Type = 12 + TypeSQLStatsCompaction Type = 13 ) var Type_name = map[int32]string{ @@ -126,6 +127,7 @@ var Type_name = map[int32]string{ 10: "STREAM_INGESTION", 11: "NEW_SCHEMA_CHANGE", 12: "MIGRATION", + 13: "SQL_STATS_COMPACTION", } var Type_value = map[string]int32{ @@ -142,6 +144,7 @@ var Type_value = map[string]int32{ "STREAM_INGESTION": 10, "NEW_SCHEMA_CHANGE": 11, "MIGRATION": 12, + "SQL_STATS_COMPACTION": 13, } func (Type) EnumDescriptor() ([]byte, []int) { @@ -2097,6 +2100,70 @@ func (m *MigrationProgress) XXX_DiscardUnknown() { var xxx_messageInfo_MigrationProgress proto.InternalMessageInfo +type SQLStatsCompactionDetails struct { +} + +func (m *SQLStatsCompactionDetails) Reset() { *m = SQLStatsCompactionDetails{} } +func (m *SQLStatsCompactionDetails) String() string { return proto.CompactTextString(m) } +func (*SQLStatsCompactionDetails) ProtoMessage() {} +func (*SQLStatsCompactionDetails) Descriptor() ([]byte, []int) { + return fileDescriptor_6c315f3a2536c4ef, []int{31} +} +func (m *SQLStatsCompactionDetails) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *SQLStatsCompactionDetails) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil +} +func (m *SQLStatsCompactionDetails) XXX_Merge(src proto.Message) { + xxx_messageInfo_SQLStatsCompactionDetails.Merge(m, src) +} +func (m *SQLStatsCompactionDetails) XXX_Size() int { + return m.Size() +} +func (m *SQLStatsCompactionDetails) XXX_DiscardUnknown() { + xxx_messageInfo_SQLStatsCompactionDetails.DiscardUnknown(m) +} + +var xxx_messageInfo_SQLStatsCompactionDetails proto.InternalMessageInfo + +type SQLStatsCompactionProgress struct { +} + +func (m *SQLStatsCompactionProgress) Reset() { *m = SQLStatsCompactionProgress{} } +func (m *SQLStatsCompactionProgress) String() string { return proto.CompactTextString(m) } +func (*SQLStatsCompactionProgress) ProtoMessage() {} +func (*SQLStatsCompactionProgress) Descriptor() ([]byte, []int) { + return fileDescriptor_6c315f3a2536c4ef, []int{32} +} +func (m *SQLStatsCompactionProgress) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *SQLStatsCompactionProgress) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil +} +func (m *SQLStatsCompactionProgress) XXX_Merge(src proto.Message) { + xxx_messageInfo_SQLStatsCompactionProgress.Merge(m, src) +} +func (m *SQLStatsCompactionProgress) XXX_Size() int { + return m.Size() +} +func (m *SQLStatsCompactionProgress) XXX_DiscardUnknown() { + xxx_messageInfo_SQLStatsCompactionProgress.DiscardUnknown(m) +} + +var xxx_messageInfo_SQLStatsCompactionProgress proto.InternalMessageInfo + type Payload struct { Description string `protobuf:"bytes,1,opt,name=description,proto3" json:"description,omitempty"` // If empty, the description is assumed to be the statement. @@ -2134,6 +2201,7 @@ type Payload struct { // *Payload_StreamIngestion // *Payload_NewSchemaChange // *Payload_Migration + // *Payload_SqlStatsCompaction Details isPayload_Details `protobuf_oneof:"details"` } @@ -2141,7 +2209,7 @@ func (m *Payload) Reset() { *m = Payload{} } func (m *Payload) String() string { return proto.CompactTextString(m) } func (*Payload) ProtoMessage() {} func (*Payload) Descriptor() ([]byte, []int) { - return fileDescriptor_6c315f3a2536c4ef, []int{31} + return fileDescriptor_6c315f3a2536c4ef, []int{33} } func (m *Payload) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2205,18 +2273,22 @@ type Payload_NewSchemaChange struct { type Payload_Migration struct { Migration *MigrationDetails `protobuf:"bytes,25,opt,name=migration,proto3,oneof" json:"migration,omitempty"` } +type Payload_SqlStatsCompaction struct { + SqlStatsCompaction *SQLStatsCompactionDetails `protobuf:"bytes,27,opt,name=sqlStatsCompaction,proto3,oneof" json:"sqlStatsCompaction,omitempty"` +} -func (*Payload_Backup) isPayload_Details() {} -func (*Payload_Restore) isPayload_Details() {} -func (*Payload_SchemaChange) isPayload_Details() {} -func (*Payload_Import) isPayload_Details() {} -func (*Payload_Changefeed) isPayload_Details() {} -func (*Payload_CreateStats) isPayload_Details() {} -func (*Payload_SchemaChangeGC) isPayload_Details() {} -func (*Payload_TypeSchemaChange) isPayload_Details() {} -func (*Payload_StreamIngestion) isPayload_Details() {} -func (*Payload_NewSchemaChange) isPayload_Details() {} -func (*Payload_Migration) isPayload_Details() {} +func (*Payload_Backup) isPayload_Details() {} +func (*Payload_Restore) isPayload_Details() {} +func (*Payload_SchemaChange) isPayload_Details() {} +func (*Payload_Import) isPayload_Details() {} +func (*Payload_Changefeed) isPayload_Details() {} +func (*Payload_CreateStats) isPayload_Details() {} +func (*Payload_SchemaChangeGC) isPayload_Details() {} +func (*Payload_TypeSchemaChange) isPayload_Details() {} +func (*Payload_StreamIngestion) isPayload_Details() {} +func (*Payload_NewSchemaChange) isPayload_Details() {} +func (*Payload_Migration) isPayload_Details() {} +func (*Payload_SqlStatsCompaction) isPayload_Details() {} func (m *Payload) GetDetails() isPayload_Details { if m != nil { @@ -2302,6 +2374,13 @@ func (m *Payload) GetMigration() *MigrationDetails { return nil } +func (m *Payload) GetSqlStatsCompaction() *SQLStatsCompactionDetails { + if x, ok := m.GetDetails().(*Payload_SqlStatsCompaction); ok { + return x.SqlStatsCompaction + } + return nil +} + // XXX_OneofWrappers is for the internal use of the proto package. func (*Payload) XXX_OneofWrappers() []interface{} { return []interface{}{ @@ -2316,6 +2395,7 @@ func (*Payload) XXX_OneofWrappers() []interface{} { (*Payload_StreamIngestion)(nil), (*Payload_NewSchemaChange)(nil), (*Payload_Migration)(nil), + (*Payload_SqlStatsCompaction)(nil), } } @@ -2338,6 +2418,7 @@ type Progress struct { // *Progress_StreamIngest // *Progress_NewSchemaChange // *Progress_Migration + // *Progress_SqlStatsCompaction Details isProgress_Details `protobuf_oneof:"details"` TraceID uint64 `protobuf:"varint,21,opt,name=trace_id,json=traceId,proto3" json:"trace_id,omitempty"` } @@ -2346,7 +2427,7 @@ func (m *Progress) Reset() { *m = Progress{} } func (m *Progress) String() string { return proto.CompactTextString(m) } func (*Progress) ProtoMessage() {} func (*Progress) Descriptor() ([]byte, []int) { - return fileDescriptor_6c315f3a2536c4ef, []int{32} + return fileDescriptor_6c315f3a2536c4ef, []int{34} } func (m *Progress) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2421,6 +2502,9 @@ type Progress_NewSchemaChange struct { type Progress_Migration struct { Migration *MigrationProgress `protobuf:"bytes,20,opt,name=migration,proto3,oneof" json:"migration,omitempty"` } +type Progress_SqlStatsCompaction struct { + SqlStatsCompaction *SQLStatsCompactionProgress `protobuf:"bytes,22,opt,name=sqlStatsCompaction,proto3,oneof" json:"sqlStatsCompaction,omitempty"` +} func (*Progress_FractionCompleted) isProgress_Progress() {} func (*Progress_HighWater) isProgress_Progress() {} @@ -2435,6 +2519,7 @@ func (*Progress_TypeSchemaChange) isProgress_Details() {} func (*Progress_StreamIngest) isProgress_Details() {} func (*Progress_NewSchemaChange) isProgress_Details() {} func (*Progress_Migration) isProgress_Details() {} +func (*Progress_SqlStatsCompaction) isProgress_Details() {} func (m *Progress) GetProgress() isProgress_Progress { if m != nil { @@ -2540,6 +2625,13 @@ func (m *Progress) GetMigration() *MigrationProgress { return nil } +func (m *Progress) GetSqlStatsCompaction() *SQLStatsCompactionProgress { + if x, ok := m.GetDetails().(*Progress_SqlStatsCompaction); ok { + return x.SqlStatsCompaction + } + return nil +} + // XXX_OneofWrappers is for the internal use of the proto package. func (*Progress) XXX_OneofWrappers() []interface{} { return []interface{}{ @@ -2556,6 +2648,7 @@ func (*Progress) XXX_OneofWrappers() []interface{} { (*Progress_StreamIngest)(nil), (*Progress_NewSchemaChange)(nil), (*Progress_Migration)(nil), + (*Progress_SqlStatsCompaction)(nil), } } @@ -2571,7 +2664,7 @@ func (m *Job) Reset() { *m = Job{} } func (m *Job) String() string { return proto.CompactTextString(m) } func (*Job) ProtoMessage() {} func (*Job) Descriptor() ([]byte, []int) { - return fileDescriptor_6c315f3a2536c4ef, []int{33} + return fileDescriptor_6c315f3a2536c4ef, []int{35} } func (m *Job) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -2659,6 +2752,8 @@ func init() { proto.RegisterType((*CreateStatsProgress)(nil), "cockroach.sql.jobs.jobspb.CreateStatsProgress") proto.RegisterType((*MigrationDetails)(nil), "cockroach.sql.jobs.jobspb.MigrationDetails") proto.RegisterType((*MigrationProgress)(nil), "cockroach.sql.jobs.jobspb.MigrationProgress") + proto.RegisterType((*SQLStatsCompactionDetails)(nil), "cockroach.sql.jobs.jobspb.SQLStatsCompactionDetails") + proto.RegisterType((*SQLStatsCompactionProgress)(nil), "cockroach.sql.jobs.jobspb.SQLStatsCompactionProgress") proto.RegisterType((*Payload)(nil), "cockroach.sql.jobs.jobspb.Payload") proto.RegisterType((*Progress)(nil), "cockroach.sql.jobs.jobspb.Progress") proto.RegisterType((*Job)(nil), "cockroach.sql.jobs.jobspb.Job") @@ -2667,330 +2762,335 @@ func init() { func init() { proto.RegisterFile("jobs/jobspb/jobs.proto", fileDescriptor_6c315f3a2536c4ef) } var fileDescriptor_6c315f3a2536c4ef = []byte{ - // 5156 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xc4, 0x5b, 0x4b, 0x6c, 0x23, 0x47, - 0x7a, 0x56, 0x53, 0x14, 0x1f, 0x3f, 0x1f, 0x6a, 0x96, 0x34, 0x1a, 0x9a, 0x6b, 0x0f, 0xb5, 0xb4, - 0xc7, 0x9e, 0x19, 0xdb, 0x94, 0x57, 0xb3, 0xeb, 0xb5, 0x67, 0xed, 0xb1, 0xf9, 0x92, 0x44, 0x6a, - 0xf4, 0x98, 0x26, 0x35, 0x1e, 0xdb, 0xf1, 0x76, 0x9a, 0xdd, 0x25, 0xa9, 0x23, 0xb2, 0x9b, 0xd3, - 0xd5, 0x9c, 0x19, 0x6d, 0x80, 0x60, 0xb1, 0x8b, 0x00, 0xc1, 0x9c, 0x92, 0xc3, 0xe6, 0x90, 0x64, - 0x80, 0x05, 0xd6, 0x0b, 0xe4, 0x90, 0x20, 0xc8, 0x22, 0xd8, 0x04, 0x41, 0x0e, 0x01, 0x72, 0xf1, - 0x61, 0x03, 0xec, 0x25, 0x80, 0x93, 0x83, 0x92, 0xc8, 0x97, 0x1c, 0x83, 0xe4, 0x36, 0xa7, 0xa0, - 0x1e, 0xdd, 0x6c, 0x52, 0x2f, 0x6a, 0x66, 0xbc, 0xb9, 0x48, 0x5d, 0x7f, 0x55, 0x7d, 0xf5, 0xfa, - 0xeb, 0xfb, 0xff, 0xfa, 0xab, 0x08, 0x73, 0xbf, 0x63, 0xb7, 0xc9, 0x02, 0xfd, 0xd3, 0x6b, 0xb3, - 0x7f, 0xc5, 0x9e, 0x63, 0xbb, 0x36, 0x7a, 0x41, 0xb7, 0xf5, 0x3d, 0xc7, 0xd6, 0xf4, 0xdd, 0x22, - 0xb9, 0xd7, 0x29, 0xb2, 0x1c, 0x5e, 0x2a, 0x77, 0x01, 0x3b, 0x8e, 0xed, 0xd0, 0xf2, 0xfc, 0x83, - 0xd7, 0xc8, 0xcd, 0xee, 0xd8, 0x3b, 0x36, 0xfb, 0x5c, 0xa0, 0x5f, 0x42, 0x8a, 0x18, 0x46, 0xaf, - 0xbd, 0x60, 0x68, 0xae, 0x26, 0x64, 0x59, 0x4f, 0x66, 0xda, 0x6f, 0x6e, 0xdb, 0x4e, 0x57, 0x73, - 0x3d, 0x8c, 0x97, 0xc9, 0xbd, 0xce, 0x82, 0xae, 0xb9, 0x5a, 0xc7, 0xde, 0x59, 0x30, 0x30, 0xd1, - 0x7b, 0xed, 0x05, 0xe2, 0x3a, 0x7d, 0xdd, 0xed, 0x3b, 0xd8, 0x10, 0x85, 0xf2, 0xc7, 0x14, 0x72, - 0xb1, 0xa5, 0x59, 0xae, 0x87, 0xdf, 0x77, 0xcd, 0xce, 0xc2, 0x6e, 0x47, 0x5f, 0x70, 0xcd, 0x2e, - 0x26, 0xae, 0xd6, 0xed, 0x89, 0x9c, 0x6f, 0xd2, 0xaa, 0x44, 0xdf, 0xc5, 0x5d, 0x4d, 0xdf, 0xd5, - 0xac, 0x1d, 0xec, 0x2c, 0xf0, 0x36, 0xf4, 0x5e, 0x5b, 0x14, 0x79, 0x45, 0xef, 0xf4, 0x89, 0x8b, - 0x9d, 0xfb, 0xd8, 0x21, 0xa6, 0x6d, 0x2d, 0x88, 0xa4, 0x2a, 0xd2, 0xbc, 0x54, 0xe1, 0xe7, 0x21, - 0xb8, 0x58, 0xd6, 0xf4, 0xbd, 0x7e, 0xaf, 0x66, 0xe9, 0xce, 0x7e, 0xcf, 0x35, 0x6d, 0x6b, 0x83, - 0xfd, 0x25, 0x48, 0x86, 0xc9, 0x3d, 0xbc, 0x9f, 0x95, 0xe6, 0xa5, 0x2b, 0x49, 0x85, 0x7e, 0xa2, - 0xf7, 0x21, 0xdc, 0xb5, 0x0d, 0x9c, 0x0d, 0xcd, 0x4b, 0x57, 0xd2, 0x8b, 0x57, 0x8b, 0x27, 0xce, - 0x6d, 0x71, 0x80, 0xb6, 0x66, 0x1b, 0x58, 0x61, 0xd5, 0x50, 0x1b, 0x62, 0x7b, 0x5d, 0xa2, 0x9a, - 0xd6, 0xb6, 0x9d, 0x9d, 0x9c, 0x97, 0xae, 0x24, 0x16, 0x6f, 0x9c, 0x02, 0x71, 0x42, 0xb7, 0x8a, - 0xab, 0x6b, 0xcd, 0xba, 0xb5, 0x6d, 0x97, 0x13, 0x87, 0x07, 0xf9, 0xa8, 0x48, 0x28, 0xd1, 0xbd, - 0x2e, 0xa1, 0x1f, 0xb9, 0x0d, 0xf0, 0x64, 0xb4, 0xff, 0x7d, 0xc7, 0x64, 0xfd, 0x8f, 0x2b, 0xf4, - 0x13, 0xbd, 0x01, 0x08, 0x73, 0x3c, 0x6c, 0xa8, 0x74, 0x21, 0x55, 0x3a, 0xc0, 0x10, 0x1b, 0xa0, - 0xec, 0xe7, 0x54, 0x35, 0x57, 0x5b, 0xc5, 0xfb, 0x37, 0xc2, 0xff, 0xf5, 0xd3, 0xbc, 0xc4, 0xff, - 0x16, 0x7e, 0x38, 0x09, 0xe9, 0x41, 0x57, 0x18, 0xfc, 0x0a, 0x44, 0xd8, 0x0a, 0x60, 0xd6, 0x42, - 0x7a, 0xf1, 0xad, 0xb1, 0xa6, 0x83, 0x56, 0x2d, 0x36, 0x59, 0x3d, 0x45, 0xd4, 0x47, 0x08, 0xc2, - 0x44, 0xeb, 0xb8, 0xa2, 0x23, 0xec, 0x1b, 0xfd, 0xa9, 0x04, 0xf3, 0xa3, 0x3d, 0x2a, 0xef, 0xaf, - 0xae, 0x35, 0xd7, 0x34, 0xba, 0x8c, 0xab, 0x78, 0xbf, 0x5e, 0xcd, 0x4e, 0xce, 0x4f, 0x5e, 0x49, - 0x2c, 0x6e, 0x8c, 0xdf, 0x70, 0xed, 0x0c, 0xc4, 0x9a, 0xe5, 0x3a, 0xfb, 0xca, 0x99, 0x0d, 0xe7, - 0x9a, 0x70, 0x79, 0x2c, 0xa8, 0xa0, 0x0e, 0xc5, 0xb9, 0x0e, 0xcd, 0xc2, 0xd4, 0x7d, 0xad, 0xd3, - 0xc7, 0x62, 0xb4, 0x3c, 0x71, 0x23, 0xf4, 0x8e, 0x54, 0xb8, 0x08, 0x11, 0x3e, 0x31, 0x28, 0x05, - 0xf1, 0x52, 0xad, 0xb9, 0xf8, 0x9d, 0xb7, 0x97, 0x2b, 0x6b, 0xf2, 0x84, 0x58, 0x82, 0x5f, 0x4a, - 0x30, 0xd7, 0x74, 0x1d, 0xac, 0x75, 0xeb, 0xd6, 0x0e, 0x26, 0x74, 0x4c, 0x55, 0xec, 0x6a, 0x66, - 0x87, 0xa0, 0xcb, 0x90, 0x26, 0x2c, 0x47, 0xd5, 0x0c, 0xc3, 0xc1, 0x84, 0x88, 0x06, 0x53, 0x5c, - 0x5a, 0xe2, 0x42, 0xf4, 0x2d, 0x08, 0x93, 0x9e, 0x66, 0xb1, 0x96, 0x13, 0x8b, 0x17, 0x03, 0xd3, - 0x26, 0x36, 0x72, 0xb1, 0xd9, 0xd3, 0xac, 0x72, 0xf8, 0x8b, 0x83, 0xfc, 0x84, 0xc2, 0x8a, 0xa2, - 0x32, 0x00, 0x71, 0x35, 0xc7, 0x55, 0xe9, 0x0e, 0x14, 0x4a, 0xfb, 0x52, 0xa0, 0x22, 0xdd, 0xa1, - 0xc5, 0xdd, 0x8e, 0x5e, 0x6c, 0x79, 0x3b, 0x54, 0x54, 0x8f, 0xb3, 0x6a, 0x54, 0x5a, 0xd0, 0xe0, - 0xe2, 0x48, 0xbf, 0x37, 0x1d, 0x7b, 0x87, 0xf5, 0x68, 0x09, 0x92, 0x7a, 0xdf, 0xb5, 0xef, 0x63, - 0x87, 0x37, 0x20, 0x8d, 0xdf, 0x40, 0x42, 0x54, 0x64, 0x4d, 0xfc, 0x43, 0x04, 0x52, 0x7c, 0xbf, - 0x78, 0x53, 0x32, 0xdc, 0x71, 0xe9, 0x69, 0x3a, 0x8e, 0x6e, 0x42, 0x0c, 0x5b, 0x06, 0x47, 0x08, - 0x8d, 0x8f, 0x10, 0xc5, 0x96, 0xc1, 0xea, 0xbf, 0xc0, 0x37, 0x20, 0x9d, 0xb5, 0x78, 0x39, 0x7a, - 0x78, 0x90, 0x9f, 0xdc, 0x52, 0xea, 0x7c, 0x27, 0xfe, 0x58, 0x82, 0x99, 0xbe, 0x63, 0x12, 0xb5, - 0xbd, 0xaf, 0x76, 0x6c, 0x5d, 0xeb, 0x98, 0xee, 0xbe, 0xba, 0x77, 0x3f, 0x3b, 0xc5, 0x34, 0xfa, - 0xe6, 0x99, 0xb4, 0x20, 0x86, 0x59, 0xdc, 0x72, 0x4c, 0x52, 0xde, 0xbf, 0x25, 0x10, 0x56, 0xef, - 0x33, 0xad, 0x2b, 0xcf, 0x1e, 0x1e, 0xe4, 0xe5, 0x2d, 0xa5, 0x1e, 0xcc, 0xba, 0xa3, 0xc8, 0xfd, - 0x91, 0xc2, 0xe8, 0x3d, 0xc8, 0x19, 0xb8, 0xe7, 0x60, 0x5d, 0xa3, 0x84, 0xd0, 0x66, 0xc8, 0x6a, - 0x57, 0xb3, 0xcc, 0x6d, 0x4c, 0xdc, 0x6c, 0x98, 0x29, 0x68, 0x76, 0x50, 0x82, 0x37, 0xbd, 0x26, - 0xf2, 0x91, 0xe6, 0xb3, 0x89, 0x69, 0x5b, 0xaa, 0xcd, 0xe9, 0x29, 0x1b, 0x61, 0x13, 0xb5, 0x78, - 0x7e, 0x62, 0x53, 0x32, 0xf8, 0x08, 0x05, 0x2b, 0x30, 0x1d, 0x68, 0x82, 0x11, 0x67, 0x9c, 0xe1, - 0x5f, 0x1d, 0x7b, 0xcf, 0x2b, 0x69, 0x3c, 0xcc, 0x5b, 0x7f, 0x24, 0x41, 0x8e, 0x92, 0x3f, 0xd6, - 0xe9, 0xa0, 0x7d, 0xcb, 0xa2, 0x3a, 0x58, 0xb7, 0x1d, 0x23, 0x1b, 0xa5, 0xa3, 0x2e, 0x37, 0xff, - 0xed, 0x20, 0x7f, 0x7d, 0xc7, 0x74, 0x77, 0xfb, 0xed, 0xa2, 0x6e, 0x77, 0x17, 0xfc, 0xd6, 0x8c, - 0xf6, 0xe0, 0x7b, 0xa1, 0xb7, 0xb7, 0xb3, 0xc0, 0x6c, 0x54, 0xbf, 0x6f, 0x1a, 0xc5, 0xad, 0xad, - 0x7a, 0xf5, 0xf0, 0x20, 0x9f, 0xdd, 0xf4, 0xc0, 0x7d, 0xc5, 0x50, 0x18, 0xb4, 0x92, 0xed, 0x9d, - 0x90, 0x83, 0xde, 0x81, 0xb4, 0x6e, 0x77, 0x3a, 0x58, 0x67, 0xe3, 0xdc, 0x52, 0xea, 0xd9, 0x18, - 0x53, 0x9a, 0xcc, 0xe1, 0x41, 0x3e, 0x55, 0xf1, 0x73, 0xa8, 0xfa, 0xa4, 0xf4, 0x60, 0x32, 0x57, - 0x81, 0x0b, 0xc7, 0xea, 0xc0, 0x59, 0xcc, 0x13, 0x0f, 0x32, 0x8f, 0x0c, 0x69, 0xbe, 0x28, 0xde, - 0xc6, 0x2c, 0xfc, 0xfd, 0x1c, 0xa4, 0x15, 0x4c, 0x5c, 0xdb, 0xc1, 0xde, 0x8e, 0x0a, 0xee, 0x86, - 0xf0, 0x53, 0xec, 0x86, 0x5f, 0x48, 0x30, 0x43, 0xad, 0xbc, 0x63, 0xf6, 0x5c, 0xdb, 0x51, 0x1d, - 0xfc, 0xc0, 0x31, 0x5d, 0x4c, 0xb2, 0x21, 0xa6, 0xf2, 0xa5, 0x53, 0x16, 0x74, 0xb8, 0x23, 0xc5, - 0xaa, 0x0f, 0xa2, 0x08, 0x0c, 0xae, 0xf5, 0x37, 0x7f, 0xf4, 0xef, 0xf9, 0x1b, 0x63, 0xad, 0xd9, - 0x51, 0xc7, 0xa3, 0x58, 0xaf, 0x2a, 0xc8, 0x38, 0x02, 0x8c, 0x5e, 0x84, 0x30, 0xdd, 0x35, 0xcc, - 0xd2, 0xc4, 0xcb, 0xb1, 0xc3, 0x83, 0x7c, 0x98, 0xee, 0x2b, 0x85, 0x49, 0x91, 0x0b, 0xb3, 0x62, - 0xd3, 0xf8, 0x7b, 0x98, 0xe9, 0x68, 0x94, 0x0d, 0xe9, 0xbd, 0xf1, 0x87, 0xc4, 0x67, 0xdf, 0x5b, - 0x42, 0x66, 0xde, 0xf9, 0xec, 0xa1, 0xf6, 0x91, 0x1c, 0xb4, 0x09, 0x69, 0x6a, 0xbb, 0xdb, 0x1a, - 0xc1, 0x2a, 0xed, 0x32, 0xc9, 0xca, 0xac, 0xbd, 0xd1, 0x3d, 0x41, 0xee, 0x75, 0x68, 0x99, 0x62, - 0x55, 0x14, 0x0e, 0xcc, 0x5b, 0xca, 0x08, 0xc8, 0x08, 0x5a, 0x86, 0x84, 0xab, 0xb5, 0x3b, 0x1e, - 0x1c, 0x27, 0xa1, 0x57, 0x4f, 0x80, 0x6b, 0xd1, 0x92, 0x01, 0x2c, 0x70, 0x3d, 0x01, 0x41, 0x55, - 0x00, 0x77, 0xbf, 0xe7, 0xe1, 0xa4, 0x19, 0xce, 0xe5, 0x93, 0x70, 0xf6, 0x7b, 0x41, 0x98, 0xb8, - 0x2b, 0xd2, 0x04, 0x35, 0x20, 0xc9, 0x7d, 0x3b, 0x81, 0x33, 0xcd, 0x70, 0x5e, 0x3b, 0x01, 0x87, - 0xd9, 0x4c, 0x2d, 0x80, 0x94, 0x20, 0xbe, 0x84, 0xa0, 0x12, 0x44, 0xb9, 0x4f, 0x49, 0xb2, 0x29, - 0x06, 0xf3, 0xcd, 0x93, 0xba, 0xc3, 0x4a, 0x05, 0xa6, 0xde, 0xab, 0x87, 0x16, 0x20, 0x41, 0x0d, - 0x8d, 0x63, 0x1a, 0x58, 0x35, 0xda, 0x8c, 0xe0, 0xe2, 0xe5, 0xf4, 0xe1, 0x41, 0x1e, 0x36, 0x84, - 0xb8, 0x5a, 0x56, 0xc0, 0x2b, 0x52, 0x6d, 0xa3, 0xd7, 0x21, 0xd3, 0x73, 0x70, 0x4f, 0x73, 0xb0, - 0xaa, 0xdb, 0xdd, 0x5e, 0x07, 0xbb, 0xd8, 0x60, 0x1b, 0x3a, 0xa6, 0xc8, 0x22, 0xa3, 0xe2, 0xc9, - 0xb9, 0xed, 0xd6, 0x5c, 0xea, 0x16, 0x12, 0xec, 0xd0, 0x92, 0x71, 0x56, 0x32, 0xc5, 0xa4, 0x75, - 0x21, 0x44, 0xfb, 0x30, 0x47, 0xf6, 0x89, 0x8b, 0xbb, 0x2a, 0x9b, 0x6e, 0xa2, 0x76, 0xcd, 0x1d, - 0x87, 0x92, 0x72, 0x36, 0xc3, 0x86, 0x55, 0x19, 0x5f, 0xd9, 0x9a, 0x0c, 0x87, 0x2d, 0x23, 0x59, - 0x13, 0x28, 0xdc, 0xf1, 0x99, 0x25, 0xc7, 0x64, 0xa1, 0xeb, 0x70, 0x61, 0xb0, 0x33, 0x88, 0xda, - 0xeb, 0xb7, 0x3b, 0x26, 0xd9, 0xc5, 0x46, 0x16, 0x58, 0x47, 0x67, 0x03, 0x99, 0x9b, 0x5e, 0x1e, - 0xda, 0x1f, 0xda, 0xec, 0x3a, 0x9d, 0x1d, 0x6d, 0x07, 0x67, 0x13, 0xf3, 0xd2, 0x95, 0xa9, 0xf2, - 0xca, 0x93, 0x83, 0x7c, 0x75, 0xec, 0x9d, 0x4a, 0x70, 0x77, 0xc1, 0x75, 0x30, 0x0e, 0x6c, 0xfc, - 0x8a, 0xc0, 0x0b, 0xee, 0x59, 0x4f, 0x86, 0x14, 0x80, 0x01, 0xe5, 0x67, 0x93, 0x4f, 0x6d, 0x8f, - 0x02, 0x28, 0xc8, 0x02, 0xe4, 0xe0, 0xfb, 0x5a, 0xc7, 0x34, 0x34, 0x17, 0xab, 0xa6, 0x65, 0xe0, - 0x87, 0x98, 0x64, 0x11, 0x9b, 0xfa, 0x77, 0xc7, 0x9f, 0x7a, 0xc5, 0xc7, 0xa8, 0x53, 0x08, 0xa1, - 0x69, 0x19, 0x67, 0x58, 0x8c, 0x09, 0xfa, 0x2b, 0x09, 0x90, 0xbf, 0xc9, 0xbb, 0xb6, 0x61, 0x6e, - 0x9b, 0xd8, 0x21, 0xd9, 0x19, 0xd6, 0xe0, 0x87, 0xe7, 0xe0, 0x4a, 0x81, 0xb1, 0xe6, 0x41, 0x3c, - 0x1f, 0xaa, 0xcc, 0x18, 0xa3, 0xb8, 0xb9, 0xff, 0x95, 0x20, 0x73, 0x84, 0x99, 0x51, 0x0b, 0x42, - 0xa6, 0xc1, 0x8c, 0x50, 0xaa, 0x4c, 0x8d, 0x63, 0xa8, 0x5e, 0x7d, 0x72, 0xf0, 0x4c, 0x4d, 0x87, - 0x4c, 0x03, 0xed, 0x40, 0x9c, 0x6e, 0x22, 0xcb, 0x55, 0x4d, 0x83, 0x59, 0xb3, 0x54, 0xb9, 0x71, - 0x78, 0x90, 0x8f, 0x6d, 0x32, 0xe1, 0x33, 0x37, 0x11, 0xe3, 0xe0, 0x75, 0x03, 0xe5, 0x21, 0xe1, - 0xda, 0x2a, 0x7e, 0x68, 0x12, 0xd7, 0xb4, 0x76, 0x98, 0x27, 0x17, 0x53, 0xc0, 0xb5, 0x6b, 0x42, - 0x92, 0xfb, 0xb3, 0x10, 0xa0, 0xa3, 0xe4, 0x8d, 0xfe, 0x4e, 0x82, 0x17, 0x3d, 0xf7, 0xce, 0x76, - 0xcc, 0x1d, 0xd3, 0xd2, 0x3a, 0x43, 0x7e, 0x9e, 0xc4, 0x16, 0xf2, 0x93, 0x67, 0xb1, 0x10, 0xc2, - 0xf7, 0xdb, 0x10, 0xf0, 0xa3, 0x3e, 0xe0, 0x8b, 0xd4, 0x15, 0xe1, 0x3e, 0xe0, 0x91, 0x22, 0x77, - 0x94, 0x6c, 0xff, 0x84, 0xca, 0xb9, 0x55, 0x78, 0xe9, 0x54, 0xe0, 0xf3, 0x38, 0x16, 0xb9, 0x1f, - 0x49, 0x70, 0xf1, 0x04, 0x73, 0x1d, 0xc4, 0x49, 0x71, 0x9c, 0xdb, 0x41, 0x9c, 0xc4, 0xe2, 0xf7, - 0x9e, 0xc1, 0x25, 0x08, 0x76, 0x62, 0x19, 0x5e, 0x38, 0x91, 0xf2, 0xce, 0x1a, 0x4d, 0x2c, 0x08, - 0xf4, 0xaf, 0x12, 0x4c, 0x8f, 0xec, 0x60, 0xf4, 0x71, 0x40, 0xc1, 0xeb, 0xf4, 0x44, 0xce, 0x1a, - 0x79, 0x2e, 0x5a, 0xbe, 0x77, 0x54, 0xcb, 0xd7, 0x69, 0x0b, 0xac, 0x61, 0xd6, 0xc2, 0x07, 0x4f, - 0xdd, 0x02, 0x87, 0x18, 0x68, 0x7a, 0xee, 0x1f, 0x25, 0x90, 0x47, 0xc9, 0x02, 0x6d, 0x80, 0x8c, - 0x1f, 0xba, 0x8e, 0xa6, 0x06, 0x8c, 0xba, 0x74, 0x1e, 0xa3, 0x9e, 0x66, 0xd5, 0x5b, 0xbe, 0x65, - 0xff, 0x14, 0x52, 0x0e, 0xde, 0xa1, 0x3e, 0xae, 0x6e, 0x5b, 0xdb, 0xe6, 0x8e, 0x58, 0xe9, 0xb7, - 0xc7, 0xf6, 0x5c, 0x8a, 0x0a, 0xab, 0x5e, 0x61, 0xb5, 0x95, 0xa4, 0x13, 0x48, 0xe5, 0x7e, 0x28, - 0xc1, 0xdc, 0xf1, 0x7c, 0x77, 0x8c, 0xae, 0x6d, 0x0e, 0xeb, 0xda, 0x8d, 0xa7, 0xa7, 0xd4, 0x80, - 0x86, 0x34, 0xc2, 0x31, 0x49, 0x0e, 0x15, 0xde, 0xa2, 0x6a, 0xc2, 0xea, 0xf8, 0x07, 0xdd, 0x97, - 0x00, 0x76, 0xcd, 0x9d, 0x5d, 0xf5, 0x81, 0xe6, 0x62, 0x47, 0x84, 0x94, 0xe2, 0x54, 0xf2, 0x11, - 0x15, 0x14, 0xfe, 0x04, 0x20, 0x55, 0xef, 0xf6, 0x6c, 0xc7, 0xf5, 0xbc, 0xed, 0x5b, 0x10, 0xe1, - 0x86, 0x5e, 0x4c, 0x78, 0xf1, 0x94, 0x0e, 0x0e, 0xd5, 0xe4, 0xfe, 0x99, 0xb0, 0x2c, 0x02, 0x03, - 0x6d, 0x40, 0x94, 0x3b, 0x45, 0x24, 0x7b, 0x91, 0xc1, 0x2d, 0x8c, 0x0d, 0xc7, 0xdd, 0x2b, 0xcf, - 0x27, 0x12, 0x28, 0xbe, 0x5f, 0x1c, 0x3a, 0xd6, 0x2f, 0x7e, 0x1f, 0x22, 0x3c, 0x1e, 0x28, 0x22, - 0x06, 0xf9, 0x63, 0x42, 0x0d, 0xf5, 0x8d, 0x25, 0xb3, 0x83, 0x97, 0x58, 0x31, 0xaf, 0xb7, 0xbc, - 0x12, 0x7a, 0x15, 0x62, 0x84, 0xb8, 0x2a, 0x31, 0x7f, 0xc0, 0x4f, 0x1a, 0x93, 0x3c, 0xd6, 0xd5, - 0x6c, 0xb6, 0x9a, 0xe6, 0x0f, 0xb0, 0x12, 0x25, 0xc4, 0xa5, 0x1f, 0xe8, 0x12, 0x30, 0xaf, 0x8b, - 0x68, 0xd4, 0x97, 0x62, 0x6e, 0xd3, 0xa4, 0x12, 0x90, 0x30, 0x9c, 0x3d, 0xb3, 0xa7, 0x6e, 0xef, - 0x11, 0xee, 0xab, 0x08, 0x9c, 0x3d, 0xb3, 0xb7, 0xb4, 0x4a, 0x94, 0x28, 0xcd, 0x5c, 0xda, 0x23, - 0x28, 0x07, 0xb1, 0x07, 0x5a, 0xa7, 0xc3, 0x4e, 0x36, 0x53, 0x0c, 0xc5, 0x4f, 0x0f, 0x9b, 0x9a, - 0xc8, 0xd7, 0x6b, 0x6a, 0xc4, 0x59, 0xa2, 0xa7, 0xb9, 0xbb, 0xec, 0x18, 0x1a, 0x57, 0x80, 0x8b, - 0x36, 0x35, 0x77, 0x17, 0x65, 0x21, 0xca, 0xc7, 0x45, 0xb2, 0xb1, 0xf9, 0xc9, 0x2b, 0x49, 0xc5, - 0x4b, 0xa2, 0xd7, 0x60, 0xda, 0x64, 0xa1, 0x15, 0xd5, 0x30, 0x1d, 0xac, 0xbb, 0x9d, 0x7d, 0xe6, - 0x67, 0xc5, 0x94, 0x34, 0x17, 0x57, 0x85, 0x14, 0x5d, 0x05, 0x79, 0xd4, 0x31, 0x65, 0xfe, 0x51, - 0x4c, 0x99, 0x1e, 0xf1, 0x4b, 0xa9, 0x0f, 0x2b, 0xd6, 0x3a, 0xe0, 0xf0, 0x65, 0xb9, 0x0f, 0x2b, - 0x32, 0x06, 0xce, 0xde, 0x55, 0x90, 0x85, 0x57, 0x3a, 0x28, 0x9b, 0xe2, 0xb8, 0x5c, 0x3e, 0x28, - 0x5a, 0x84, 0x99, 0x9e, 0xe6, 0x10, 0xac, 0xb6, 0xfb, 0x96, 0xd1, 0xc1, 0x2a, 0xc7, 0xca, 0xa6, - 0x59, 0xe9, 0x0c, 0xcb, 0x2a, 0xb3, 0x1c, 0xae, 0x77, 0x67, 0x9d, 0xd6, 0xe7, 0xfe, 0x1f, 0x4e, - 0xeb, 0xb9, 0x9f, 0x87, 0x60, 0x8a, 0xed, 0x32, 0x74, 0x03, 0xc2, 0x74, 0x2d, 0x45, 0x7c, 0x69, - 0xdc, 0x13, 0x13, 0xab, 0x83, 0x10, 0x84, 0x2d, 0xad, 0x8b, 0xb3, 0x88, 0xad, 0x34, 0xfb, 0x46, - 0x17, 0x21, 0x4a, 0xf0, 0x3d, 0xf5, 0xbe, 0xd6, 0xc9, 0xce, 0x30, 0x45, 0x8c, 0x10, 0x7c, 0xef, - 0x8e, 0xd6, 0x41, 0x17, 0x20, 0x62, 0x12, 0xd5, 0xc2, 0x0f, 0xb2, 0xb3, 0xdc, 0x2a, 0x99, 0x64, - 0x1d, 0x3f, 0x40, 0xdf, 0x80, 0xf8, 0x03, 0x8d, 0xa8, 0xb8, 0xdb, 0x73, 0xf7, 0xd9, 0x5c, 0xc4, - 0xa8, 0xea, 0x92, 0x1a, 0x4d, 0x33, 0xe7, 0x45, 0x73, 0x76, 0xb0, 0xab, 0xea, 0x76, 0x87, 0x64, - 0x2f, 0xd0, 0xad, 0x4a, 0x4f, 0x6b, 0x54, 0x54, 0xb1, 0x3b, 0xa4, 0x11, 0x8e, 0x85, 0xe4, 0xc9, - 0x46, 0x38, 0x36, 0x29, 0x87, 0x1b, 0xe1, 0x58, 0x58, 0x9e, 0x6a, 0x84, 0x63, 0x53, 0x72, 0xa4, - 0x11, 0x8e, 0x45, 0xe4, 0x68, 0x23, 0x1c, 0x8b, 0xca, 0xb1, 0x46, 0x38, 0x16, 0x93, 0xe3, 0x8d, - 0x70, 0x2c, 0x2e, 0x43, 0x23, 0x1c, 0x03, 0x39, 0xd1, 0x08, 0xc7, 0x12, 0x72, 0xb2, 0x11, 0x8e, - 0x25, 0xe5, 0x54, 0x23, 0x1c, 0x4b, 0xc9, 0xe9, 0x46, 0x38, 0x96, 0x96, 0xa7, 0x1b, 0xe1, 0xd8, - 0xb4, 0x2c, 0x37, 0xc2, 0x31, 0x59, 0xce, 0x34, 0xc2, 0xb1, 0x8c, 0x8c, 0x72, 0x35, 0x11, 0xd0, - 0xd4, 0xd0, 0xf7, 0x86, 0xe6, 0x69, 0xec, 0x93, 0x1c, 0xab, 0x54, 0xf8, 0x85, 0x04, 0x72, 0x13, - 0xdf, 0xeb, 0x63, 0x4b, 0xc7, 0x77, 0xb4, 0x4e, 0x65, 0xb7, 0x6f, 0xed, 0xa1, 0x57, 0x61, 0x5a, - 0xa7, 0x1f, 0x2a, 0x8f, 0xf2, 0xd1, 0x19, 0x93, 0xd8, 0x8c, 0xa5, 0x98, 0xb8, 0x49, 0xa5, 0x74, - 0xe2, 0x5e, 0x02, 0x10, 0xe5, 0x28, 0x9b, 0x84, 0x58, 0x91, 0x38, 0x2f, 0x42, 0x29, 0x64, 0x04, - 0xc6, 0xb1, 0x1f, 0x30, 0xca, 0x1a, 0x82, 0x51, 0xec, 0x07, 0x68, 0x01, 0x66, 0x2d, 0xfc, 0xd0, - 0x55, 0x47, 0x0b, 0x33, 0x7a, 0x52, 0x32, 0x34, 0xaf, 0x12, 0xac, 0x50, 0xf8, 0xe7, 0x10, 0x4c, - 0x7b, 0x9d, 0xf6, 0x38, 0x7d, 0x1b, 0x64, 0xba, 0xba, 0xa6, 0xa1, 0xba, 0x36, 0x47, 0xf2, 0xd8, - 0xfd, 0xfd, 0x53, 0xe8, 0x78, 0x04, 0x85, 0xa6, 0xeb, 0x46, 0xcb, 0x66, 0xcd, 0x71, 0xf3, 0xa6, - 0xa4, 0x48, 0x50, 0x96, 0xdb, 0x82, 0xb4, 0x57, 0x89, 0x4b, 0x50, 0x05, 0x22, 0x43, 0xed, 0xbd, - 0x3e, 0x46, 0x7b, 0xde, 0x54, 0x2b, 0xa2, 0x6a, 0xee, 0x77, 0x01, 0x1d, 0x6d, 0x3b, 0x68, 0x5a, - 0xa7, 0xb8, 0x69, 0xdd, 0x18, 0x36, 0xad, 0xef, 0x9e, 0x6f, 0x6c, 0x81, 0x6e, 0x07, 0x43, 0x54, - 0xff, 0x14, 0x82, 0x34, 0x37, 0x4c, 0xbe, 0x4d, 0xa5, 0x14, 0x45, 0x19, 0xd0, 0xb4, 0x76, 0xd4, - 0x9e, 0x10, 0xb2, 0xf1, 0x85, 0x14, 0xd9, 0xcb, 0xf0, 0x0b, 0xbf, 0x4c, 0x3d, 0x0f, 0xcd, 0x18, - 0x14, 0x0c, 0xb1, 0x82, 0x49, 0x2a, 0xf4, 0x0b, 0x5d, 0x86, 0x34, 0xf3, 0x1e, 0x07, 0xa5, 0x26, - 0x59, 0xa9, 0x14, 0x93, 0xfa, 0xc5, 0xca, 0x90, 0x22, 0x3d, 0xcd, 0x1a, 0x94, 0x0a, 0xb3, 0x49, - 0x3d, 0x23, 0xa0, 0x9e, 0xa4, 0x75, 0x82, 0x0e, 0x81, 0x83, 0x49, 0xbf, 0x8b, 0xd5, 0x9e, 0xcd, - 0x23, 0x2e, 0x93, 0x4a, 0x9c, 0x4b, 0x36, 0x6d, 0x82, 0xb6, 0x98, 0xaa, 0xb0, 0xb9, 0x50, 0x0d, - 0x3e, 0x39, 0xd9, 0x08, 0x6b, 0xe5, 0xda, 0xf8, 0xd3, 0xa9, 0x4c, 0x93, 0x61, 0x41, 0xe1, 0xaf, - 0x25, 0xb8, 0x48, 0xbd, 0x31, 0xbe, 0xd3, 0x2a, 0xec, 0xea, 0xcc, 0xd3, 0x4e, 0x0d, 0xa2, 0xcc, - 0xcd, 0xf3, 0xdd, 0xd9, 0x95, 0xc3, 0x83, 0x7c, 0x84, 0x96, 0x7e, 0x66, 0x2b, 0x17, 0xa1, 0xc0, - 0x75, 0x16, 0x49, 0x70, 0x1d, 0xcd, 0x22, 0x26, 0x3d, 0x53, 0xd3, 0x65, 0xeb, 0xe2, 0x6e, 0x9b, - 0x9e, 0x6b, 0x43, 0xcc, 0xa0, 0xcd, 0x0e, 0x65, 0xae, 0xf1, 0xbc, 0x42, 0x0e, 0xb2, 0xa3, 0x5d, - 0xf6, 0xc3, 0x94, 0xbf, 0x05, 0x73, 0xeb, 0xf8, 0xc1, 0x71, 0xa3, 0x29, 0x43, 0x94, 0x33, 0x9d, - 0xa7, 0xf2, 0x57, 0x46, 0x49, 0x27, 0x78, 0x7b, 0x58, 0x64, 0x3d, 0x6d, 0xb1, 0x0a, 0x8a, 0x57, - 0xb1, 0xf0, 0x29, 0x5c, 0x1c, 0x41, 0xf7, 0x97, 0xef, 0x43, 0x88, 0x10, 0x57, 0x73, 0x85, 0x7b, - 0x96, 0x1e, 0x07, 0xbd, 0xe9, 0x6a, 0x6e, 0x9f, 0x28, 0xa2, 0x5e, 0x41, 0x61, 0x01, 0xd6, 0x7e, - 0x17, 0x53, 0x15, 0xb9, 0x65, 0x12, 0x17, 0x7d, 0x08, 0x49, 0xa1, 0x12, 0x54, 0x53, 0xbc, 0x7e, - 0x9f, 0xa1, 0x55, 0x09, 0xc7, 0x07, 0x21, 0x85, 0xbf, 0x91, 0x60, 0xa6, 0xea, 0xd8, 0xbd, 0x1e, - 0x36, 0x84, 0xcd, 0xe1, 0x93, 0xe1, 0x99, 0x1a, 0x29, 0x60, 0x6a, 0xd6, 0x21, 0x54, 0xaf, 0x8a, - 0x63, 0xc5, 0xcd, 0x67, 0x3d, 0xad, 0xd4, 0xab, 0xe8, 0x5d, 0x3e, 0x23, 0x7d, 0xc2, 0x08, 0x34, - 0x7d, 0x24, 0xce, 0x36, 0xa4, 0xa7, 0x81, 0xa9, 0xe8, 0x93, 0xc2, 0xe7, 0x51, 0xb8, 0x10, 0x9c, - 0xe5, 0xe5, 0x8a, 0xd7, 0xf1, 0xcf, 0x20, 0xea, 0xc5, 0x5a, 0xc6, 0x20, 0xca, 0xe3, 0x20, 0x8a, - 0x62, 0x3e, 0x82, 0xf1, 0x16, 0x0f, 0x13, 0x35, 0x21, 0x63, 0x5a, 0x2e, 0x76, 0x3a, 0x58, 0xbb, - 0x4f, 0xbd, 0x0b, 0x3a, 0x67, 0x22, 0xb6, 0x3d, 0xae, 0x2d, 0x97, 0x03, 0x00, 0xdc, 0x27, 0xf8, - 0x0c, 0x66, 0x82, 0xa0, 0x5e, 0xff, 0x4f, 0x0f, 0xaa, 0xb2, 0xee, 0x0d, 0x60, 0xbd, 0xe8, 0x6f, - 0x00, 0xc8, 0x8b, 0x0c, 0xdd, 0xf5, 0x0f, 0x06, 0x3c, 0x70, 0x7e, 0xe3, 0xa9, 0x67, 0xa4, 0x3a, - 0x72, 0x48, 0x18, 0x72, 0x75, 0x99, 0x15, 0xfc, 0x9a, 0x5c, 0xdd, 0x3b, 0x10, 0xe1, 0xb1, 0x55, - 0x71, 0x59, 0x74, 0xf3, 0x69, 0x87, 0xc0, 0x63, 0xb6, 0x8a, 0x40, 0xcb, 0xfd, 0xb1, 0x04, 0xc9, - 0xe0, 0x72, 0x23, 0x13, 0x62, 0x6c, 0xfa, 0x3d, 0x4e, 0x9b, 0x7c, 0xee, 0x07, 0x68, 0xae, 0x4a, - 0x75, 0x83, 0x7a, 0x62, 0x86, 0x63, 0xf7, 0x06, 0x97, 0x85, 0x93, 0x4a, 0x8c, 0x0a, 0xa8, 0xef, - 0x98, 0xfb, 0x3d, 0x88, 0xfb, 0x93, 0x1e, 0x08, 0x89, 0x4d, 0x3e, 0xc7, 0x90, 0xd8, 0xa9, 0xed, - 0x57, 0x21, 0x35, 0x34, 0x63, 0x68, 0xce, 0xef, 0x43, 0xb8, 0x1c, 0xe1, 0x7d, 0x38, 0x13, 0xa5, - 0xf0, 0x97, 0x51, 0x98, 0x39, 0x8e, 0x6a, 0x3f, 0x06, 0x39, 0xc0, 0x5b, 0x6a, 0xc7, 0x24, 0xae, - 0xd0, 0xcd, 0xab, 0xa7, 0x9f, 0xaa, 0x03, 0xe4, 0x27, 0x54, 0x31, 0xed, 0x0c, 0x53, 0xe2, 0xa7, - 0x90, 0x36, 0x78, 0xc7, 0x45, 0xd8, 0x5b, 0x5c, 0xf9, 0x9f, 0x76, 0x1a, 0x3e, 0x86, 0x00, 0x05, - 0x7a, 0xca, 0x08, 0x64, 0x11, 0xa4, 0x43, 0xca, 0x07, 0xdf, 0xef, 0x89, 0x63, 0xd5, 0xb3, 0x93, - 0x61, 0xd2, 0x6b, 0x85, 0x62, 0xa2, 0x1d, 0x98, 0xf6, 0x1a, 0xf1, 0x4e, 0xe0, 0xf1, 0xe7, 0xd2, - 0x8c, 0x37, 0x31, 0x4d, 0x71, 0x22, 0xff, 0xb1, 0x04, 0x33, 0x5e, 0x4b, 0x7e, 0xe4, 0xd8, 0x34, - 0x18, 0x9d, 0xa5, 0xca, 0xcd, 0xc3, 0x83, 0x7c, 0x46, 0xcc, 0x8c, 0x17, 0xc0, 0x78, 0x66, 0xbd, - 0xcb, 0x18, 0x23, 0x80, 0x06, 0x75, 0x22, 0x68, 0x3e, 0x6d, 0x78, 0x6a, 0xe0, 0x44, 0x50, 0x62, - 0x7b, 0x76, 0x27, 0x82, 0x7e, 0xd6, 0x0d, 0xf4, 0xfb, 0x12, 0x64, 0xf8, 0x6d, 0x55, 0xb7, 0xef, - 0x6a, 0xfc, 0x62, 0xd8, 0x3b, 0x9a, 0x7f, 0x7c, 0x78, 0x90, 0x9f, 0x66, 0xcb, 0xbb, 0x26, 0xf2, - 0x58, 0xb3, 0xe5, 0xa7, 0x6d, 0x76, 0x80, 0x22, 0x4e, 0xb2, 0xbe, 0xc0, 0x40, 0xab, 0x90, 0xe6, - 0xf1, 0x0a, 0xef, 0x49, 0x11, 0x3b, 0xb3, 0xa7, 0xca, 0xaf, 0x3c, 0x39, 0xc8, 0xcf, 0x1f, 0xb3, - 0x4f, 0x78, 0xa8, 0xe3, 0x0e, 0x2f, 0xab, 0xa4, 0xb6, 0x83, 0x49, 0x74, 0x0b, 0xa6, 0xb9, 0xe7, - 0xe9, 0x9f, 0x70, 0x59, 0xc4, 0x62, 0xcc, 0x3b, 0x56, 0xee, 0xb5, 0xfa, 0x52, 0x11, 0x86, 0x9a, - 0x83, 0xd9, 0x63, 0x9d, 0xa6, 0x2f, 0x23, 0x30, 0x37, 0x4c, 0xab, 0xbe, 0x5b, 0xa3, 0x8e, 0xda, - 0xdb, 0x0f, 0xc6, 0xa6, 0x66, 0x0f, 0x83, 0x53, 0xa3, 0x97, 0x1a, 0xb5, 0xb8, 0x9f, 0x8d, 0x58, - 0xaf, 0xa7, 0xc0, 0x67, 0xcb, 0x3b, 0x82, 0xef, 0x99, 0xb0, 0xbb, 0xbe, 0x65, 0xe1, 0x81, 0xa7, - 0x0f, 0x9f, 0x02, 0x9e, 0xd5, 0xf7, 0x92, 0xbe, 0x6d, 0xf9, 0x95, 0x04, 0xa9, 0xa1, 0x91, 0xfd, - 0x26, 0x8d, 0xcb, 0xa6, 0xef, 0x5b, 0xf1, 0x97, 0x67, 0xef, 0x9c, 0x7f, 0x58, 0xc3, 0x2e, 0x57, - 0xee, 0x6f, 0x25, 0x48, 0x0d, 0x4d, 0xe4, 0xd7, 0x64, 0x96, 0x9e, 0x7f, 0xcf, 0xdb, 0x90, 0x1e, - 0x5e, 0xa2, 0x40, 0x1b, 0xd2, 0xf3, 0x69, 0xa3, 0xf0, 0x5d, 0x88, 0x70, 0x09, 0x42, 0x90, 0xfe, - 0xa8, 0x54, 0x6f, 0xd5, 0xd7, 0x97, 0xd5, 0xa5, 0x0d, 0x45, 0x5d, 0xae, 0xc8, 0x13, 0x28, 0x09, - 0xb1, 0x6a, 0xed, 0x56, 0x8d, 0x0a, 0x65, 0x09, 0x25, 0x20, 0xca, 0x52, 0xb5, 0xaa, 0x1c, 0x2a, - 0x94, 0x41, 0xe6, 0xd8, 0xdb, 0x98, 0x9a, 0x19, 0x7a, 0x8c, 0x40, 0x45, 0x98, 0x61, 0x2e, 0x7f, - 0x97, 0x7a, 0x56, 0x74, 0x7b, 0xab, 0x01, 0x5f, 0x3c, 0xe3, 0x67, 0xd1, 0xdd, 0xbb, 0xae, 0x75, - 0x71, 0xe1, 0x97, 0x61, 0xc8, 0x0c, 0x40, 0x3c, 0x23, 0xfb, 0x17, 0xd2, 0xe0, 0x40, 0x13, 0x39, - 0xf3, 0xda, 0xf1, 0x48, 0x7d, 0x71, 0xb6, 0x11, 0xd7, 0x7f, 0x1f, 0xd1, 0x4d, 0xf3, 0xe4, 0x20, - 0x9f, 0x19, 0xed, 0x2c, 0x79, 0xc6, 0x7b, 0x41, 0xaf, 0x8b, 0x2c, 0xf4, 0x6a, 0x5a, 0x7b, 0xea, - 0xe0, 0xfd, 0x13, 0x0f, 0xbd, 0x9a, 0xd6, 0xde, 0x96, 0x52, 0x57, 0xa2, 0x34, 0x73, 0xcb, 0x31, - 0x51, 0x03, 0xc2, 0x76, 0xcf, 0xf5, 0x4e, 0xd0, 0x6f, 0x9f, 0x6b, 0x48, 0x1b, 0x3d, 0x31, 0x1e, - 0x85, 0x61, 0xa0, 0x06, 0xbf, 0x49, 0x1f, 0x4c, 0x34, 0x23, 0xe4, 0x31, 0x29, 0x34, 0x35, 0xb4, - 0x10, 0xb9, 0x1d, 0x48, 0x06, 0x67, 0xec, 0x98, 0x0b, 0x84, 0xd2, 0x70, 0x94, 0xe3, 0xf5, 0xb1, - 0xba, 0x2e, 0x4e, 0x98, 0x81, 0x3b, 0xa5, 0xef, 0x42, 0xdc, 0x1f, 0xc7, 0x79, 0xae, 0xd6, 0x38, - 0xc7, 0xfb, 0x21, 0xbc, 0x29, 0x39, 0x52, 0xf8, 0x3c, 0x04, 0x49, 0x05, 0x13, 0xbb, 0x73, 0x1f, - 0x1b, 0xd4, 0x83, 0xf2, 0xdf, 0xfb, 0x49, 0xe3, 0xbf, 0xf7, 0x2b, 0x41, 0x7c, 0x60, 0x81, 0xce, - 0xf1, 0xe6, 0x6d, 0x50, 0x0b, 0x7d, 0x0c, 0xa9, 0xb6, 0xdd, 0xb7, 0x0c, 0xcd, 0xd9, 0x67, 0x7e, - 0x15, 0xf3, 0x40, 0xd2, 0x8b, 0xdf, 0x3e, 0xdd, 0x17, 0xf4, 0x7b, 0x5d, 0x2c, 0x8b, 0xca, 0xd4, - 0x7f, 0x52, 0x92, 0xed, 0x40, 0xaa, 0xf0, 0x3e, 0x24, 0x83, 0xb9, 0x28, 0x06, 0xe1, 0xf5, 0x8d, - 0xf5, 0x1a, 0xdf, 0x93, 0xe5, 0x52, 0x65, 0x75, 0xa9, 0x7e, 0xeb, 0x96, 0x2c, 0x51, 0x79, 0xed, - 0x6e, 0xbd, 0x25, 0x87, 0xe8, 0xee, 0x54, 0x6a, 0xcd, 0x56, 0x49, 0x69, 0x79, 0x91, 0xce, 0x02, - 0x86, 0x54, 0xb0, 0x3d, 0xca, 0x7c, 0xd4, 0xed, 0x64, 0x82, 0xa1, 0x93, 0xf7, 0x6b, 0x63, 0xf6, - 0xd8, 0xd3, 0x20, 0x27, 0x88, 0x5a, 0xf8, 0x97, 0x10, 0xa0, 0xc1, 0xc2, 0xfb, 0x64, 0x75, 0x17, - 0x40, 0xdf, 0xc5, 0xfa, 0x5e, 0xcf, 0x36, 0x2d, 0x57, 0x9c, 0x35, 0xdf, 0x19, 0x4b, 0x77, 0x7c, - 0xb2, 0xaa, 0xf8, 0xf5, 0x95, 0x00, 0x16, 0xfa, 0xc9, 0xe9, 0x91, 0xf2, 0x49, 0x16, 0x29, 0x67, - 0x3b, 0xff, 0x37, 0x1b, 0x2d, 0x2f, 0x01, 0x0c, 0x7a, 0x8c, 0xae, 0xc3, 0xd4, 0x39, 0xa2, 0x1b, - 0xbc, 0x6c, 0x50, 0xd7, 0x0b, 0xff, 0x13, 0x06, 0x54, 0x71, 0xb0, 0xe6, 0x62, 0x4a, 0xd1, 0xe4, - 0xb4, 0x10, 0x47, 0x19, 0xa6, 0xf8, 0x91, 0x3e, 0x74, 0x9e, 0x23, 0xbd, 0xd7, 0x34, 0xab, 0x8a, - 0xbe, 0x0f, 0x49, 0xdd, 0xee, 0xf4, 0xbb, 0x96, 0xca, 0xde, 0xe3, 0x88, 0xf3, 0xc7, 0x77, 0x4e, - 0x5b, 0xb1, 0x23, 0x9d, 0x2b, 0x56, 0xec, 0x0e, 0x4d, 0xfb, 0x2f, 0x57, 0x19, 0x20, 0x2b, 0x81, - 0x5e, 0x84, 0xb8, 0xcf, 0x3c, 0x4c, 0x1d, 0xe2, 0xca, 0x40, 0x80, 0x16, 0x61, 0x4a, 0x23, 0xaa, - 0xbd, 0xcd, 0x9c, 0xe9, 0xb3, 0xb6, 0xa2, 0x12, 0xd6, 0xc8, 0xc6, 0x36, 0xba, 0x06, 0x99, 0xae, - 0xf6, 0x50, 0xdd, 0x76, 0x34, 0x5d, 0x38, 0xc7, 0x1d, 0xce, 0x84, 0x92, 0x32, 0xdd, 0xd5, 0x1e, - 0x2e, 0x09, 0x79, 0xdd, 0xe8, 0x60, 0x74, 0x1d, 0x52, 0xdb, 0xf7, 0xf8, 0xd1, 0x8a, 0x5b, 0x25, - 0xfe, 0xb8, 0x69, 0xfa, 0xf0, 0x20, 0x9f, 0x58, 0xba, 0xcd, 0x26, 0x86, 0xda, 0x24, 0x25, 0xb1, - 0x7d, 0xcf, 0x4f, 0xe4, 0xfe, 0x5b, 0x82, 0xa8, 0x18, 0x11, 0xea, 0x01, 0x88, 0xe9, 0x31, 0x0d, - 0xbe, 0xa6, 0xa9, 0xf2, 0xed, 0xc3, 0x83, 0x7c, 0xbc, 0xc2, 0xa4, 0xf5, 0x2a, 0x79, 0x72, 0x90, - 0xff, 0xf0, 0x69, 0x2d, 0x8a, 0x07, 0xa2, 0xc4, 0x79, 0x23, 0x75, 0x83, 0x05, 0x72, 0x77, 0x35, - 0xa2, 0xee, 0x9a, 0xc4, 0xb5, 0x77, 0x1c, 0xad, 0x2b, 0xae, 0xe9, 0x93, 0xbb, 0x1a, 0x59, 0xf1, - 0x64, 0x28, 0x47, 0x7d, 0xb3, 0xfb, 0xfc, 0x39, 0x15, 0x7f, 0xb4, 0xe1, 0xa7, 0xd1, 0x22, 0x5c, - 0xf0, 0x2b, 0xab, 0x74, 0xa6, 0xda, 0x7d, 0x7d, 0x0f, 0x33, 0x1b, 0x44, 0xc9, 0x7d, 0xc6, 0xcf, - 0x5c, 0xd3, 0x1e, 0x96, 0x79, 0x56, 0xe1, 0x02, 0xcc, 0x04, 0x96, 0xd5, 0xf7, 0xa4, 0x31, 0xc8, - 0xfc, 0x35, 0x41, 0xe0, 0x2d, 0xf6, 0x6d, 0x98, 0x1e, 0xf9, 0xa9, 0x81, 0xe0, 0xdf, 0x60, 0x88, - 0x70, 0xf8, 0xb7, 0x09, 0xc5, 0x0a, 0x4f, 0x7a, 0x67, 0x83, 0xb4, 0x3e, 0x94, 0x2e, 0xcc, 0x40, - 0xc6, 0x6f, 0xc6, 0x6f, 0xfb, 0x57, 0x49, 0x88, 0x6e, 0x6a, 0xfb, 0x1d, 0x5b, 0x33, 0xd0, 0x3c, - 0x24, 0xbc, 0x77, 0x50, 0x5e, 0x7b, 0x71, 0x25, 0x28, 0x1a, 0x56, 0x33, 0x99, 0xdd, 0x04, 0x05, - 0xd4, 0xcc, 0x84, 0x74, 0x9f, 0x60, 0x87, 0x6a, 0x80, 0xca, 0x7e, 0x17, 0xc1, 0xcd, 0x4d, 0xb9, - 0xfc, 0xe4, 0x20, 0x7f, 0x73, 0xbc, 0xc5, 0xc3, 0x7a, 0xdf, 0x31, 0xdd, 0xfd, 0x62, 0xf3, 0xf6, - 0xad, 0x2d, 0x01, 0x45, 0xb9, 0xc2, 0x56, 0x52, 0xfd, 0x60, 0x52, 0x3c, 0x77, 0xa3, 0x0b, 0xa1, - 0x76, 0x4d, 0xdd, 0xb1, 0x89, 0x77, 0xdf, 0x22, 0xa4, 0x6b, 0x4c, 0x88, 0x5e, 0x83, 0xe9, 0x6d, - 0xd3, 0x62, 0x57, 0x86, 0x5e, 0x39, 0x7e, 0xd5, 0x92, 0xf6, 0xc4, 0xa2, 0xe0, 0x7d, 0x48, 0x07, - 0xde, 0x99, 0x51, 0x25, 0x8c, 0x30, 0x25, 0xdc, 0x38, 0x3c, 0xc8, 0xa7, 0x06, 0x9b, 0x9a, 0x2b, - 0xe2, 0xb3, 0xb8, 0x36, 0xa9, 0x41, 0x33, 0x54, 0x0d, 0x67, 0x61, 0x8a, 0xfd, 0x6a, 0x86, 0x3f, - 0xd4, 0x55, 0x78, 0x02, 0xd5, 0x20, 0x25, 0x42, 0x21, 0xfc, 0x27, 0x35, 0xe2, 0x71, 0xde, 0x7c, - 0x60, 0xe9, 0xbd, 0x1f, 0xdd, 0x14, 0x6b, 0x96, 0x6e, 0x1b, 0xd8, 0xa8, 0xd1, 0xb4, 0x22, 0x22, - 0xbf, 0x2c, 0x41, 0xd0, 0x32, 0xa4, 0xf5, 0x0e, 0xd6, 0xac, 0x7e, 0xcf, 0xc3, 0x41, 0x63, 0xe2, - 0xa4, 0x44, 0x3d, 0x01, 0xb4, 0x0e, 0x68, 0x9b, 0xbd, 0x3d, 0x0a, 0xf6, 0x8a, 0x5d, 0x2d, 0x8e, - 0x03, 0x26, 0xb3, 0xba, 0xca, 0xa0, 0x67, 0xe8, 0x15, 0x48, 0x59, 0xb6, 0xa5, 0x6b, 0x96, 0x8e, - 0x3b, 0x8c, 0x59, 0xf9, 0x6d, 0xe4, 0xb0, 0x10, 0x95, 0x21, 0xc2, 0xef, 0xad, 0xc5, 0x19, 0xf6, - 0xca, 0xb8, 0xcf, 0xd9, 0x57, 0x26, 0x14, 0x51, 0x13, 0xd5, 0x20, 0xea, 0xf0, 0x37, 0x14, 0xec, - 0x2e, 0xfb, 0xcc, 0x58, 0x52, 0xe0, 0x85, 0xc6, 0xca, 0x84, 0xe2, 0xd5, 0x45, 0x2d, 0xef, 0x29, - 0x29, 0xb7, 0xa3, 0xe2, 0x35, 0x60, 0x71, 0xcc, 0x13, 0xc2, 0x00, 0x70, 0x08, 0x85, 0x0e, 0xd0, - 0x64, 0x77, 0x51, 0xec, 0x96, 0xfb, 0xf4, 0x01, 0x0e, 0xbd, 0xa6, 0xa0, 0x03, 0xe4, 0x35, 0xd1, - 0x3a, 0x75, 0x04, 0x3c, 0xdb, 0xce, 0xee, 0xbf, 0x13, 0x8b, 0x6f, 0x9c, 0xc7, 0xff, 0x5d, 0x99, - 0x50, 0x02, 0x08, 0xe8, 0x36, 0x24, 0xf4, 0x01, 0x45, 0x65, 0xa7, 0x19, 0xe0, 0x9b, 0xe7, 0xb2, - 0x53, 0x2b, 0xd4, 0x36, 0x0d, 0xa4, 0xe8, 0x13, 0x48, 0x93, 0xa1, 0xf3, 0x52, 0xf6, 0x02, 0x43, - 0x7d, 0xeb, 0xbc, 0xf1, 0xda, 0x95, 0x09, 0x65, 0x04, 0x09, 0xfd, 0x36, 0xc8, 0xee, 0xc8, 0xad, - 0x0e, 0xbb, 0xc0, 0x3e, 0xfd, 0xa9, 0xe6, 0x09, 0x77, 0x57, 0x2b, 0x13, 0xca, 0x11, 0x34, 0xf4, - 0x19, 0x4c, 0x93, 0xe1, 0x9f, 0x9d, 0x64, 0x2f, 0xb2, 0x06, 0xbe, 0x75, 0xea, 0xcd, 0xc4, 0x71, - 0x3f, 0xb0, 0x59, 0x99, 0x50, 0x46, 0xb1, 0x28, 0xbc, 0x35, 0x7c, 0x39, 0xc4, 0x9e, 0x47, 0x9c, - 0x0e, 0x7f, 0xfc, 0x65, 0x15, 0x85, 0x1f, 0xc1, 0x42, 0xab, 0x10, 0xef, 0x7a, 0x9c, 0x9f, 0x7d, - 0xe1, 0xcc, 0x23, 0xc6, 0xa8, 0x19, 0x5a, 0x99, 0x50, 0x06, 0xf5, 0xcb, 0x71, 0x88, 0x8a, 0x4b, - 0x44, 0xff, 0x86, 0x9f, 0xdf, 0xed, 0xf3, 0x5b, 0xfd, 0x9c, 0xfc, 0x8d, 0xc2, 0x4f, 0xe3, 0x10, - 0xf3, 0x9d, 0xd4, 0x05, 0x40, 0xbe, 0xfb, 0x30, 0x78, 0xc1, 0x4c, 0xcd, 0x4a, 0x68, 0x65, 0x42, - 0xc9, 0x78, 0x79, 0x83, 0x47, 0xcc, 0x37, 0x87, 0x9e, 0x37, 0x8d, 0xf3, 0x33, 0x21, 0xda, 0x41, - 0xff, 0xfd, 0x13, 0xa5, 0x7b, 0xf1, 0xc8, 0xd5, 0xa7, 0x7b, 0x1e, 0x7d, 0x4e, 0x7b, 0x62, 0x41, - 0xf7, 0x97, 0x21, 0xed, 0xf4, 0x2d, 0x76, 0x77, 0x28, 0xce, 0xfc, 0xdc, 0x67, 0x4a, 0x09, 0xa9, - 0x38, 0xb6, 0x57, 0x46, 0x18, 0xe8, 0xea, 0x99, 0x0c, 0xe4, 0x8d, 0x7d, 0x45, 0xf2, 0x29, 0x68, - 0x69, 0x94, 0x82, 0xae, 0x9d, 0x4d, 0x41, 0x01, 0x18, 0x9f, 0x83, 0xb6, 0x8e, 0xe5, 0xa0, 0x85, - 0x31, 0x37, 0x51, 0x00, 0x71, 0x98, 0x84, 0x2a, 0x23, 0x24, 0x74, 0xf5, 0x4c, 0x12, 0x0a, 0x8e, - 0x51, 0xb0, 0xd0, 0xc6, 0x31, 0x2c, 0xf4, 0xe6, 0xb9, 0x8e, 0x23, 0x2b, 0xd2, 0x10, 0x0d, 0x29, - 0xc7, 0xd1, 0x50, 0x71, 0x3c, 0x1a, 0x0a, 0x40, 0x0e, 0xf1, 0xd0, 0xa7, 0x47, 0x78, 0x48, 0x3e, - 0x7b, 0x23, 0x1f, 0x1b, 0xe8, 0x59, 0x91, 0x8e, 0x10, 0x91, 0x76, 0x0c, 0x11, 0x65, 0x18, 0xfc, - 0xf5, 0x73, 0x10, 0x51, 0xa0, 0x81, 0xa3, 0x4c, 0x74, 0x17, 0x92, 0x41, 0xf6, 0x60, 0x2f, 0x7e, - 0x4e, 0xe7, 0xb9, 0x13, 0x7e, 0x2f, 0xc7, 0x74, 0x20, 0x90, 0x85, 0xbe, 0x7f, 0x94, 0x84, 0x66, - 0xce, 0x04, 0x3f, 0xe1, 0x4e, 0x7b, 0x45, 0x3a, 0xca, 0x42, 0xb7, 0x82, 0x2c, 0x34, 0x7b, 0xa6, - 0x8d, 0x3a, 0xe2, 0xa5, 0xae, 0x48, 0x01, 0x1a, 0x42, 0xaf, 0x42, 0xcc, 0x75, 0x34, 0x9d, 0x5d, - 0x4b, 0x5c, 0x60, 0x77, 0x4f, 0x2c, 0x28, 0xd4, 0xa2, 0x32, 0x16, 0x3c, 0x62, 0x1f, 0x46, 0x19, - 0x20, 0xe6, 0x3d, 0xad, 0x08, 0x50, 0x57, 0xe1, 0x67, 0x12, 0x4c, 0x36, 0xec, 0x36, 0x7a, 0x29, - 0x10, 0xa9, 0x4c, 0x89, 0xf3, 0xec, 0x54, 0xc3, 0x6e, 0x8b, 0x90, 0xe3, 0x07, 0x83, 0xda, 0xe2, - 0xe0, 0xf7, 0xf2, 0x29, 0x5d, 0xf6, 0x03, 0xbd, 0x7e, 0x25, 0xf4, 0x1e, 0x44, 0x7b, 0xdc, 0xb1, - 0x16, 0x4c, 0x56, 0x38, 0xad, 0x3e, 0x2f, 0xa9, 0x78, 0x55, 0xae, 0x5d, 0x0d, 0xfe, 0x50, 0x76, - 0xcd, 0x36, 0x30, 0x4a, 0x03, 0x6c, 0x6a, 0x84, 0xf4, 0x76, 0x1d, 0x8d, 0x60, 0x79, 0x02, 0x45, - 0x61, 0x72, 0x75, 0xad, 0x29, 0x4b, 0xd7, 0xee, 0x06, 0xc3, 0x8c, 0x55, 0xa5, 0x54, 0x5f, 0xaf, - 0xaf, 0x2f, 0xab, 0xeb, 0xa5, 0xb5, 0x5a, 0x53, 0x9e, 0x40, 0x59, 0x98, 0xfd, 0xa8, 0x54, 0x6f, - 0x89, 0xb8, 0xa3, 0x5a, 0x5f, 0x6f, 0xd5, 0x94, 0x3b, 0xa5, 0x5b, 0xb2, 0x84, 0xe6, 0x00, 0x29, - 0x1b, 0x95, 0xd5, 0x66, 0xb5, 0xac, 0x56, 0x36, 0xd6, 0x36, 0x4b, 0x95, 0x56, 0x7d, 0x63, 0x5d, - 0x0e, 0xa1, 0x18, 0x84, 0xab, 0x1b, 0xeb, 0x35, 0x19, 0xae, 0xfd, 0x24, 0x0c, 0x61, 0x16, 0x21, - 0x79, 0x05, 0x12, 0x5b, 0xeb, 0xcd, 0xcd, 0x5a, 0xa5, 0xbe, 0x54, 0xaf, 0x55, 0xe5, 0x89, 0xdc, - 0xcc, 0xa3, 0xc7, 0xf3, 0xd3, 0x34, 0x6b, 0xcb, 0x22, 0x3d, 0xac, 0x33, 0x6e, 0x45, 0x39, 0x88, - 0x94, 0x4b, 0x95, 0xd5, 0xad, 0x4d, 0x59, 0xca, 0xa5, 0x1f, 0x3d, 0x9e, 0x07, 0x5a, 0x80, 0xf3, - 0x22, 0x7a, 0x91, 0x47, 0x50, 0x36, 0x94, 0x9a, 0x1c, 0xca, 0x4d, 0x3f, 0x7a, 0x3c, 0x9f, 0x60, - 0x81, 0x19, 0xc1, 0x6d, 0xaf, 0x41, 0xaa, 0x59, 0x59, 0xa9, 0xad, 0x95, 0xd4, 0xca, 0x4a, 0x69, - 0x7d, 0xb9, 0x26, 0x4f, 0xe6, 0x66, 0x1f, 0x3d, 0x9e, 0x97, 0x47, 0xf7, 0x07, 0x6d, 0xa2, 0xbe, - 0xb6, 0xb9, 0xa1, 0xb4, 0xe4, 0xf0, 0xa0, 0x09, 0x4e, 0x4b, 0xa8, 0x00, 0xc0, 0x6b, 0x2f, 0xd5, - 0x6a, 0x55, 0x79, 0x2a, 0x87, 0x1e, 0x3d, 0x9e, 0x4f, 0xd3, 0xfc, 0x01, 0xdb, 0xa0, 0xcb, 0x90, - 0xac, 0x28, 0xb5, 0x52, 0xab, 0xa6, 0x36, 0x5b, 0xa5, 0x56, 0x53, 0x8e, 0x0c, 0x46, 0x12, 0x60, - 0x10, 0x54, 0x84, 0x4c, 0x69, 0xab, 0xb5, 0xa1, 0x0e, 0x95, 0x8d, 0xe6, 0x2e, 0x3e, 0x7a, 0x3c, - 0x3f, 0x43, 0xcb, 0x96, 0xfa, 0xae, 0x1d, 0x2c, 0xff, 0x06, 0xc8, 0x43, 0xfd, 0x57, 0x97, 0x2b, - 0x72, 0x2c, 0x37, 0xf7, 0xe8, 0xf1, 0x3c, 0x1a, 0x1d, 0xc2, 0x72, 0x05, 0x7d, 0x1b, 0xe6, 0x5a, - 0x1f, 0x6f, 0xd6, 0xaa, 0xb5, 0x66, 0x45, 0x1d, 0x1e, 0x76, 0x3c, 0x97, 0x7d, 0xf4, 0x78, 0x7e, - 0x96, 0xd6, 0x39, 0x32, 0xf4, 0x37, 0x41, 0x6e, 0xb6, 0x94, 0x5a, 0x69, 0x4d, 0xad, 0xaf, 0x2f, - 0xd7, 0x9a, 0x6c, 0xb1, 0x60, 0xd0, 0xa5, 0x91, 0xbd, 0x4e, 0x87, 0xb0, 0x5e, 0xfb, 0x68, 0x04, - 0x3f, 0x31, 0x28, 0x3f, 0xb2, 0x7d, 0xd1, 0x3c, 0xc4, 0xd7, 0xea, 0xcb, 0x4a, 0x89, 0xe1, 0x26, - 0x73, 0x99, 0x47, 0x8f, 0xe7, 0x53, 0xb4, 0x9c, 0xbf, 0x19, 0x73, 0xb1, 0x3f, 0xf8, 0xd9, 0xa5, - 0x89, 0x3f, 0xff, 0xfc, 0xd2, 0x44, 0xf9, 0xca, 0x17, 0xff, 0x79, 0x69, 0xe2, 0x8b, 0xc3, 0x4b, - 0xd2, 0xaf, 0x0f, 0x2f, 0x49, 0x5f, 0x1e, 0x5e, 0x92, 0xfe, 0xe3, 0xf0, 0x92, 0xf4, 0x87, 0x5f, - 0x5d, 0x9a, 0xf8, 0xf5, 0x57, 0x97, 0x26, 0xbe, 0xfc, 0xea, 0xd2, 0xc4, 0x27, 0x11, 0xae, 0xd7, - 0xed, 0x08, 0x3b, 0x07, 0x5e, 0xff, 0xbf, 0x00, 0x00, 0x00, 0xff, 0xff, 0x18, 0x6e, 0x84, 0x74, - 0x58, 0x40, 0x00, 0x00, + // 5239 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xc4, 0x5b, 0x4d, 0x6c, 0x23, 0x47, + 0x76, 0x56, 0x53, 0x14, 0x7f, 0x9e, 0x44, 0xaa, 0x59, 0xd2, 0x68, 0x68, 0x7a, 0x3c, 0xd4, 0x72, + 0x3d, 0xf6, 0xcc, 0xd8, 0xa6, 0xbc, 0x1a, 0xdb, 0x6b, 0xcf, 0xda, 0x63, 0xf3, 0x4f, 0x12, 0xa9, + 0xdf, 0x69, 0x52, 0xe3, 0xb1, 0x1d, 0x6f, 0xa7, 0xd9, 0x5d, 0x92, 0x3a, 0x22, 0xbb, 0x39, 0x5d, + 0xcd, 0x99, 0xd1, 0x06, 0x08, 0x16, 0xbb, 0x08, 0x90, 0xcc, 0x29, 0x39, 0x24, 0x87, 0x24, 0x03, + 0x04, 0x58, 0x2f, 0x90, 0x43, 0x82, 0x20, 0x8b, 0xc5, 0x26, 0x08, 0x72, 0x08, 0x90, 0x8b, 0x81, + 0x24, 0xc0, 0x5e, 0x02, 0x38, 0x39, 0x28, 0x89, 0x7c, 0xc9, 0x31, 0x48, 0x6e, 0x73, 0x0a, 0xea, + 0xa7, 0x9b, 0x4d, 0x8a, 0x92, 0xa8, 0x99, 0xf1, 0xe6, 0x22, 0x75, 0xbd, 0xaa, 0xfa, 0xea, 0xef, + 0xd5, 0xf7, 0x5e, 0xbd, 0x2a, 0xc2, 0xdc, 0x6f, 0xd8, 0x4d, 0xb2, 0x40, 0xff, 0x74, 0x9a, 0xec, + 0x5f, 0xbe, 0xe3, 0xd8, 0xae, 0x8d, 0x5e, 0xd0, 0x6d, 0x7d, 0xdf, 0xb1, 0x35, 0x7d, 0x2f, 0x4f, + 0xee, 0xb5, 0xf2, 0x2c, 0x87, 0x97, 0xca, 0x5c, 0xc0, 0x8e, 0x63, 0x3b, 0xb4, 0x3c, 0xff, 0xe0, + 0x35, 0x32, 0xb3, 0xbb, 0xf6, 0xae, 0xcd, 0x3e, 0x17, 0xe8, 0x97, 0x90, 0x22, 0x86, 0xd1, 0x69, + 0x2e, 0x18, 0x9a, 0xab, 0x09, 0x59, 0xda, 0x93, 0x99, 0xf6, 0x1b, 0x3b, 0xb6, 0xd3, 0xd6, 0x5c, + 0x0f, 0xe3, 0xdb, 0xe4, 0x5e, 0x6b, 0x41, 0xd7, 0x5c, 0xad, 0x65, 0xef, 0x2e, 0x18, 0x98, 0xe8, + 0x9d, 0xe6, 0x02, 0x71, 0x9d, 0xae, 0xee, 0x76, 0x1d, 0x6c, 0x88, 0x42, 0xd9, 0x21, 0x85, 0x5c, + 0x6c, 0x69, 0x96, 0xeb, 0xe1, 0x77, 0x5d, 0xb3, 0xb5, 0xb0, 0xd7, 0xd2, 0x17, 0x5c, 0xb3, 0x8d, + 0x89, 0xab, 0xb5, 0x3b, 0x22, 0xe7, 0x5b, 0xb4, 0x2a, 0xd1, 0xf7, 0x70, 0x5b, 0xd3, 0xf7, 0x34, + 0x6b, 0x17, 0x3b, 0x0b, 0xbc, 0x0d, 0xbd, 0xd3, 0x14, 0x45, 0x5e, 0xd6, 0x5b, 0x5d, 0xe2, 0x62, + 0xe7, 0x3e, 0x76, 0x88, 0x69, 0x5b, 0x0b, 0x22, 0xa9, 0x8a, 0x34, 0x2f, 0x95, 0xfb, 0x69, 0x08, + 0x2e, 0x16, 0x35, 0x7d, 0xbf, 0xdb, 0xa9, 0x58, 0xba, 0x73, 0xd0, 0x71, 0x4d, 0xdb, 0xda, 0x64, + 0x7f, 0x09, 0x92, 0x61, 0x7c, 0x1f, 0x1f, 0xa4, 0xa5, 0x79, 0xe9, 0xea, 0x94, 0x42, 0x3f, 0xd1, + 0x07, 0x10, 0x6e, 0xdb, 0x06, 0x4e, 0x87, 0xe6, 0xa5, 0xab, 0xc9, 0xc5, 0x6b, 0xf9, 0x13, 0xe7, + 0x36, 0xdf, 0x43, 0x5b, 0xb7, 0x0d, 0xac, 0xb0, 0x6a, 0xa8, 0x09, 0xb1, 0xfd, 0x36, 0x51, 0x4d, + 0x6b, 0xc7, 0x4e, 0x8f, 0xcf, 0x4b, 0x57, 0x27, 0x17, 0x6f, 0x9e, 0x02, 0x71, 0x42, 0xb7, 0xf2, + 0xab, 0xeb, 0xf5, 0xaa, 0xb5, 0x63, 0x17, 0x27, 0x8f, 0x0e, 0xb3, 0x51, 0x91, 0x50, 0xa2, 0xfb, + 0x6d, 0x42, 0x3f, 0x32, 0x9b, 0xe0, 0xc9, 0x68, 0xff, 0xbb, 0x8e, 0xc9, 0xfa, 0x1f, 0x57, 0xe8, + 0x27, 0x7a, 0x1d, 0x10, 0xe6, 0x78, 0xd8, 0x50, 0xe9, 0x42, 0xaa, 0x74, 0x80, 0x21, 0x36, 0x40, + 0xd9, 0xcf, 0x29, 0x6b, 0xae, 0xb6, 0x8a, 0x0f, 0x6e, 0x86, 0xff, 0xeb, 0x4f, 0xb3, 0x12, 0xff, + 0x9b, 0xfb, 0xe1, 0x38, 0x24, 0x7b, 0x5d, 0x61, 0xf0, 0x2b, 0x10, 0x61, 0x2b, 0x80, 0x59, 0x0b, + 0xc9, 0xc5, 0x37, 0x47, 0x9a, 0x0e, 0x5a, 0x35, 0x5f, 0x67, 0xf5, 0x14, 0x51, 0x1f, 0x21, 0x08, + 0x13, 0xad, 0xe5, 0x8a, 0x8e, 0xb0, 0x6f, 0xf4, 0xc7, 0x12, 0xcc, 0x0f, 0xf6, 0xa8, 0x78, 0xb0, + 0xba, 0x5e, 0x5f, 0xd7, 0xe8, 0x32, 0xae, 0xe2, 0x83, 0x6a, 0x39, 0x3d, 0x3e, 0x3f, 0x7e, 0x75, + 0x72, 0x71, 0x73, 0xf4, 0x86, 0x2b, 0x67, 0x20, 0x56, 0x2c, 0xd7, 0x39, 0x50, 0xce, 0x6c, 0x38, + 0x53, 0x87, 0x2b, 0x23, 0x41, 0x05, 0x75, 0x28, 0xce, 0x75, 0x68, 0x16, 0x26, 0xee, 0x6b, 0xad, + 0x2e, 0x16, 0xa3, 0xe5, 0x89, 0x9b, 0xa1, 0x77, 0xa5, 0xdc, 0x45, 0x88, 0xf0, 0x89, 0x41, 0x09, + 0x88, 0x17, 0x2a, 0xf5, 0xc5, 0xb7, 0xdf, 0x59, 0x2e, 0xad, 0xcb, 0x63, 0x62, 0x09, 0x7e, 0x21, + 0xc1, 0x5c, 0xdd, 0x75, 0xb0, 0xd6, 0xae, 0x5a, 0xbb, 0x98, 0xd0, 0x31, 0x95, 0xb1, 0xab, 0x99, + 0x2d, 0x82, 0xae, 0x40, 0x92, 0xb0, 0x1c, 0x55, 0x33, 0x0c, 0x07, 0x13, 0x22, 0x1a, 0x4c, 0x70, + 0x69, 0x81, 0x0b, 0xd1, 0x77, 0x20, 0x4c, 0x3a, 0x9a, 0xc5, 0x5a, 0x9e, 0x5c, 0xbc, 0x18, 0x98, + 0x36, 0xb1, 0x91, 0xf3, 0xf5, 0x8e, 0x66, 0x15, 0xc3, 0x5f, 0x1e, 0x66, 0xc7, 0x14, 0x56, 0x14, + 0x15, 0x01, 0x88, 0xab, 0x39, 0xae, 0x4a, 0x77, 0xa0, 0x50, 0xda, 0x97, 0x02, 0x15, 0xe9, 0x0e, + 0xcd, 0xef, 0xb5, 0xf4, 0x7c, 0xc3, 0xdb, 0xa1, 0xa2, 0x7a, 0x9c, 0x55, 0xa3, 0xd2, 0x9c, 0x06, + 0x17, 0x07, 0xfa, 0xbd, 0xe5, 0xd8, 0xbb, 0xac, 0x47, 0x4b, 0x30, 0xa5, 0x77, 0x5d, 0xfb, 0x3e, + 0x76, 0x78, 0x03, 0xd2, 0xe8, 0x0d, 0x4c, 0x8a, 0x8a, 0xac, 0x89, 0xbf, 0x8b, 0x40, 0x82, 0xef, + 0x17, 0x6f, 0x4a, 0xfa, 0x3b, 0x2e, 0x3d, 0x4d, 0xc7, 0xd1, 0x2d, 0x88, 0x61, 0xcb, 0xe0, 0x08, + 0xa1, 0xd1, 0x11, 0xa2, 0xd8, 0x32, 0x58, 0xfd, 0x17, 0xf8, 0x06, 0xa4, 0xb3, 0x16, 0x2f, 0x46, + 0x8f, 0x0e, 0xb3, 0xe3, 0xdb, 0x4a, 0x95, 0xef, 0xc4, 0x1f, 0x4b, 0x30, 0xd3, 0x75, 0x4c, 0xa2, + 0x36, 0x0f, 0xd4, 0x96, 0xad, 0x6b, 0x2d, 0xd3, 0x3d, 0x50, 0xf7, 0xef, 0xa7, 0x27, 0x98, 0x46, + 0xdf, 0x3a, 0x93, 0x16, 0xc4, 0x30, 0xf3, 0xdb, 0x8e, 0x49, 0x8a, 0x07, 0x6b, 0x02, 0x61, 0xf5, + 0x3e, 0xd3, 0xba, 0xe2, 0xec, 0xd1, 0x61, 0x56, 0xde, 0x56, 0xaa, 0xc1, 0xac, 0x3b, 0x8a, 0xdc, + 0x1d, 0x28, 0x8c, 0xde, 0x87, 0x8c, 0x81, 0x3b, 0x0e, 0xd6, 0x35, 0x4a, 0x08, 0x4d, 0x86, 0xac, + 0xb6, 0x35, 0xcb, 0xdc, 0xc1, 0xc4, 0x4d, 0x87, 0x99, 0x82, 0xa6, 0x7b, 0x25, 0x78, 0xd3, 0xeb, + 0x22, 0x1f, 0x69, 0x3e, 0x9b, 0x98, 0xb6, 0xa5, 0xda, 0x9c, 0x9e, 0xd2, 0x11, 0x36, 0x51, 0x8b, + 0xe7, 0x27, 0x36, 0x25, 0x85, 0x8f, 0x51, 0xb0, 0x02, 0xd3, 0x81, 0x26, 0x18, 0x71, 0xc6, 0x19, + 0xfe, 0xb5, 0x91, 0xf7, 0xbc, 0x92, 0xc4, 0xfd, 0xbc, 0xf5, 0xfb, 0x12, 0x64, 0x28, 0xf9, 0x63, + 0x9d, 0x0e, 0xda, 0xb7, 0x2c, 0xaa, 0x83, 0x75, 0xdb, 0x31, 0xd2, 0x51, 0x3a, 0xea, 0x62, 0xfd, + 0xdf, 0x0e, 0xb3, 0x37, 0x76, 0x4d, 0x77, 0xaf, 0xdb, 0xcc, 0xeb, 0x76, 0x7b, 0xc1, 0x6f, 0xcd, + 0x68, 0xf6, 0xbe, 0x17, 0x3a, 0xfb, 0xbb, 0x0b, 0xcc, 0x46, 0x75, 0xbb, 0xa6, 0x91, 0xdf, 0xde, + 0xae, 0x96, 0x8f, 0x0e, 0xb3, 0xe9, 0x2d, 0x0f, 0xdc, 0x57, 0x0c, 0x85, 0x41, 0x2b, 0xe9, 0xce, + 0x09, 0x39, 0xe8, 0x5d, 0x48, 0xea, 0x76, 0xab, 0x85, 0x75, 0x36, 0xce, 0x6d, 0xa5, 0x9a, 0x8e, + 0x31, 0xa5, 0x49, 0x1d, 0x1d, 0x66, 0x13, 0x25, 0x3f, 0x87, 0xaa, 0x4f, 0x42, 0x0f, 0x26, 0x33, + 0x25, 0xb8, 0x30, 0x54, 0x07, 0xce, 0x62, 0x9e, 0x78, 0x90, 0x79, 0x64, 0x48, 0xf2, 0x45, 0xf1, + 0x36, 0x66, 0xee, 0x6f, 0xe7, 0x20, 0xa9, 0x60, 0xe2, 0xda, 0x0e, 0xf6, 0x76, 0x54, 0x70, 0x37, + 0x84, 0x9f, 0x62, 0x37, 0xfc, 0x4c, 0x82, 0x19, 0x6a, 0xe5, 0x1d, 0xb3, 0xe3, 0xda, 0x8e, 0xea, + 0xe0, 0x07, 0x8e, 0xe9, 0x62, 0x92, 0x0e, 0x31, 0x95, 0x2f, 0x9c, 0xb2, 0xa0, 0xfd, 0x1d, 0xc9, + 0x97, 0x7d, 0x10, 0x45, 0x60, 0x70, 0xad, 0xbf, 0xf5, 0xa3, 0x7f, 0xcf, 0xde, 0x1c, 0x69, 0xcd, + 0x8e, 0x3b, 0x1e, 0xf9, 0x6a, 0x59, 0x41, 0xc6, 0x31, 0x60, 0x74, 0x09, 0xc2, 0x74, 0xd7, 0x30, + 0x4b, 0x13, 0x2f, 0xc6, 0x8e, 0x0e, 0xb3, 0x61, 0xba, 0xaf, 0x14, 0x26, 0x45, 0x2e, 0xcc, 0x8a, + 0x4d, 0xe3, 0xef, 0x61, 0xa6, 0xa3, 0x51, 0x36, 0xa4, 0xf7, 0x47, 0x1f, 0x12, 0x9f, 0x7d, 0x6f, + 0x09, 0x99, 0x79, 0xe7, 0xb3, 0x87, 0x9a, 0xc7, 0x72, 0xd0, 0x16, 0x24, 0xa9, 0xed, 0x6e, 0x6a, + 0x04, 0xab, 0xb4, 0xcb, 0x24, 0x2d, 0xb3, 0xf6, 0x06, 0xf7, 0x04, 0xb9, 0xd7, 0xa2, 0x65, 0xf2, + 0x65, 0x51, 0x38, 0x30, 0x6f, 0x09, 0x23, 0x20, 0x23, 0x68, 0x19, 0x26, 0x5d, 0xad, 0xd9, 0xf2, + 0xe0, 0x38, 0x09, 0xbd, 0x72, 0x02, 0x5c, 0x83, 0x96, 0x0c, 0x60, 0x81, 0xeb, 0x09, 0x08, 0x2a, + 0x03, 0xb8, 0x07, 0x1d, 0x0f, 0x27, 0xc9, 0x70, 0xae, 0x9c, 0x84, 0x73, 0xd0, 0x09, 0xc2, 0xc4, + 0x5d, 0x91, 0x26, 0xa8, 0x06, 0x53, 0xdc, 0xb7, 0x13, 0x38, 0xd3, 0x0c, 0xe7, 0xd5, 0x13, 0x70, + 0x98, 0xcd, 0xd4, 0x02, 0x48, 0x93, 0xc4, 0x97, 0x10, 0x54, 0x80, 0x28, 0xf7, 0x29, 0x49, 0x3a, + 0xc1, 0x60, 0xbe, 0x75, 0x52, 0x77, 0x58, 0xa9, 0xc0, 0xd4, 0x7b, 0xf5, 0xd0, 0x02, 0x4c, 0x52, + 0x43, 0xe3, 0x98, 0x06, 0x56, 0x8d, 0x26, 0x23, 0xb8, 0x78, 0x31, 0x79, 0x74, 0x98, 0x85, 0x4d, + 0x21, 0x2e, 0x17, 0x15, 0xf0, 0x8a, 0x94, 0x9b, 0xe8, 0x35, 0x48, 0x75, 0x1c, 0xdc, 0xd1, 0x1c, + 0xac, 0xea, 0x76, 0xbb, 0xd3, 0xc2, 0x2e, 0x36, 0xd8, 0x86, 0x8e, 0x29, 0xb2, 0xc8, 0x28, 0x79, + 0x72, 0x6e, 0xbb, 0x35, 0x97, 0xba, 0x85, 0x04, 0x3b, 0xb4, 0x64, 0x9c, 0x95, 0x4c, 0x30, 0x69, + 0x55, 0x08, 0xd1, 0x01, 0xcc, 0x91, 0x03, 0xe2, 0xe2, 0xb6, 0xca, 0xa6, 0x9b, 0xa8, 0x6d, 0x73, + 0xd7, 0xa1, 0xa4, 0x9c, 0x4e, 0xb1, 0x61, 0x95, 0x46, 0x57, 0xb6, 0x3a, 0xc3, 0x61, 0xcb, 0x48, + 0xd6, 0x05, 0x0a, 0x77, 0x7c, 0x66, 0xc9, 0x90, 0x2c, 0x74, 0x03, 0x2e, 0xf4, 0x76, 0x06, 0x51, + 0x3b, 0xdd, 0x66, 0xcb, 0x24, 0x7b, 0xd8, 0x48, 0x03, 0xeb, 0xe8, 0x6c, 0x20, 0x73, 0xcb, 0xcb, + 0x43, 0x07, 0x7d, 0x9b, 0x5d, 0xa7, 0xb3, 0xa3, 0xed, 0xe2, 0xf4, 0xe4, 0xbc, 0x74, 0x75, 0xa2, + 0xb8, 0xf2, 0xe4, 0x30, 0x5b, 0x1e, 0x79, 0xa7, 0x12, 0xdc, 0x5e, 0x70, 0x1d, 0x8c, 0x03, 0x1b, + 0xbf, 0x24, 0xf0, 0x82, 0x7b, 0xd6, 0x93, 0x21, 0x05, 0xa0, 0x47, 0xf9, 0xe9, 0xa9, 0xa7, 0xb6, + 0x47, 0x01, 0x14, 0x64, 0x01, 0x72, 0xf0, 0x7d, 0xad, 0x65, 0x1a, 0x9a, 0x8b, 0x55, 0xd3, 0x32, + 0xf0, 0x43, 0x4c, 0xd2, 0x88, 0x4d, 0xfd, 0x7b, 0xa3, 0x4f, 0xbd, 0xe2, 0x63, 0x54, 0x29, 0x84, + 0xd0, 0xb4, 0x94, 0xd3, 0x2f, 0xc6, 0x04, 0xfd, 0xa5, 0x04, 0xc8, 0xdf, 0xe4, 0x6d, 0xdb, 0x30, + 0x77, 0x4c, 0xec, 0x90, 0xf4, 0x0c, 0x6b, 0xf0, 0xa3, 0x73, 0x70, 0xa5, 0xc0, 0x58, 0xf7, 0x20, + 0x9e, 0x0f, 0x55, 0xa6, 0x8c, 0x41, 0xdc, 0xcc, 0xff, 0x4a, 0x90, 0x3a, 0xc6, 0xcc, 0xa8, 0x01, + 0x21, 0xd3, 0x60, 0x46, 0x28, 0x51, 0xa4, 0xc6, 0x31, 0x54, 0x2d, 0x3f, 0x39, 0x7c, 0xa6, 0xa6, + 0x43, 0xa6, 0x81, 0x76, 0x21, 0x4e, 0x37, 0x91, 0xe5, 0xaa, 0xa6, 0xc1, 0xac, 0x59, 0xa2, 0x58, + 0x3b, 0x3a, 0xcc, 0xc6, 0xb6, 0x98, 0xf0, 0x99, 0x9b, 0x88, 0x71, 0xf0, 0xaa, 0x81, 0xb2, 0x30, + 0xe9, 0xda, 0x2a, 0x7e, 0x68, 0x12, 0xd7, 0xb4, 0x76, 0x99, 0x27, 0x17, 0x53, 0xc0, 0xb5, 0x2b, + 0x42, 0x92, 0xf9, 0x93, 0x10, 0xa0, 0xe3, 0xe4, 0x8d, 0xfe, 0x46, 0x82, 0x4b, 0x9e, 0x7b, 0x67, + 0x3b, 0xe6, 0xae, 0x69, 0x69, 0xad, 0x3e, 0x3f, 0x4f, 0x62, 0x0b, 0xf9, 0xe9, 0xb3, 0x58, 0x08, + 0xe1, 0xfb, 0x6d, 0x0a, 0xf8, 0x41, 0x1f, 0xf0, 0x12, 0x75, 0x45, 0xb8, 0x0f, 0x78, 0xac, 0xc8, + 0x1d, 0x25, 0xdd, 0x3d, 0xa1, 0x72, 0x66, 0x15, 0x5e, 0x3a, 0x15, 0xf8, 0x3c, 0x8e, 0x45, 0xe6, + 0x47, 0x12, 0x5c, 0x3c, 0xc1, 0x5c, 0x07, 0x71, 0x12, 0x1c, 0xe7, 0x76, 0x10, 0x67, 0x72, 0xf1, + 0x7b, 0xcf, 0xe0, 0x12, 0x04, 0x3b, 0xb1, 0x0c, 0x2f, 0x9c, 0x48, 0x79, 0x67, 0x8d, 0x26, 0x16, + 0x04, 0xfa, 0x57, 0x09, 0xa6, 0x07, 0x76, 0x30, 0xfa, 0x24, 0xa0, 0xe0, 0x55, 0x7a, 0x22, 0x67, + 0x8d, 0x3c, 0x17, 0x2d, 0xdf, 0x3f, 0xae, 0xe5, 0x1b, 0xb4, 0x05, 0xd6, 0x30, 0x6b, 0xe1, 0xc3, + 0xa7, 0x6e, 0x81, 0x43, 0xf4, 0x34, 0x3d, 0xf3, 0xf7, 0x12, 0xc8, 0x83, 0x64, 0x81, 0x36, 0x41, + 0xc6, 0x0f, 0x5d, 0x47, 0x53, 0x03, 0x46, 0x5d, 0x3a, 0x8f, 0x51, 0x4f, 0xb2, 0xea, 0x0d, 0xdf, + 0xb2, 0x7f, 0x06, 0x09, 0x07, 0xef, 0x52, 0x1f, 0x57, 0xb7, 0xad, 0x1d, 0x73, 0x57, 0xac, 0xf4, + 0x3b, 0x23, 0x7b, 0x2e, 0x79, 0x85, 0x55, 0x2f, 0xb1, 0xda, 0xca, 0x94, 0x13, 0x48, 0x65, 0x7e, + 0x28, 0xc1, 0xdc, 0x70, 0xbe, 0x1b, 0xa2, 0x6b, 0x5b, 0xfd, 0xba, 0x76, 0xf3, 0xe9, 0x29, 0x35, + 0xa0, 0x21, 0xb5, 0x70, 0x4c, 0x92, 0x43, 0xb9, 0x37, 0xa9, 0x9a, 0xb0, 0x3a, 0xfe, 0x41, 0xf7, + 0x25, 0x80, 0x3d, 0x73, 0x77, 0x4f, 0x7d, 0xa0, 0xb9, 0xd8, 0x11, 0x21, 0xa5, 0x38, 0x95, 0x7c, + 0x4c, 0x05, 0xb9, 0x3f, 0x02, 0x48, 0x54, 0xdb, 0x1d, 0xdb, 0x71, 0x3d, 0x6f, 0x7b, 0x0d, 0x22, + 0xdc, 0xd0, 0x8b, 0x09, 0xcf, 0x9f, 0xd2, 0xc1, 0xbe, 0x9a, 0xdc, 0x3f, 0x13, 0x96, 0x45, 0x60, + 0xa0, 0x4d, 0x88, 0x72, 0xa7, 0x88, 0xa4, 0x2f, 0x32, 0xb8, 0x85, 0x91, 0xe1, 0xb8, 0x7b, 0xe5, + 0xf9, 0x44, 0x02, 0xc5, 0xf7, 0x8b, 0x43, 0x43, 0xfd, 0xe2, 0x0f, 0x20, 0xc2, 0xe3, 0x81, 0x22, + 0x62, 0x90, 0x1d, 0x12, 0x6a, 0xa8, 0x6e, 0x2e, 0x99, 0x2d, 0xbc, 0xc4, 0x8a, 0x79, 0xbd, 0xe5, + 0x95, 0xd0, 0x2b, 0x10, 0x23, 0xc4, 0x55, 0x89, 0xf9, 0x03, 0x7e, 0xd2, 0x18, 0xe7, 0xb1, 0xae, + 0x7a, 0xbd, 0x51, 0x37, 0x7f, 0x80, 0x95, 0x28, 0x21, 0x2e, 0xfd, 0x40, 0x97, 0x81, 0x79, 0x5d, + 0x44, 0xa3, 0xbe, 0x14, 0x73, 0x9b, 0xc6, 0x95, 0x80, 0x84, 0xe1, 0xec, 0x9b, 0x1d, 0x75, 0x67, + 0x9f, 0x70, 0x5f, 0x45, 0xe0, 0xec, 0x9b, 0x9d, 0xa5, 0x55, 0xa2, 0x44, 0x69, 0xe6, 0xd2, 0x3e, + 0x41, 0x19, 0x88, 0x3d, 0xd0, 0x5a, 0x2d, 0x76, 0xb2, 0x99, 0x60, 0x28, 0x7e, 0xba, 0xdf, 0xd4, + 0x44, 0xbe, 0x59, 0x53, 0x23, 0xce, 0x12, 0x1d, 0xcd, 0xdd, 0x63, 0xc7, 0xd0, 0xb8, 0x02, 0x5c, + 0xb4, 0xa5, 0xb9, 0x7b, 0x28, 0x0d, 0x51, 0x3e, 0x2e, 0x92, 0x8e, 0xcd, 0x8f, 0x5f, 0x9d, 0x52, + 0xbc, 0x24, 0x7a, 0x15, 0xa6, 0x4d, 0x16, 0x5a, 0x51, 0x0d, 0xd3, 0xc1, 0xba, 0xdb, 0x3a, 0x60, + 0x7e, 0x56, 0x4c, 0x49, 0x72, 0x71, 0x59, 0x48, 0xd1, 0x35, 0x90, 0x07, 0x1d, 0x53, 0xe6, 0x1f, + 0xc5, 0x94, 0xe9, 0x01, 0xbf, 0x94, 0xfa, 0xb0, 0x62, 0xad, 0x03, 0x0e, 0x5f, 0x9a, 0xfb, 0xb0, + 0x22, 0xa3, 0xe7, 0xec, 0x5d, 0x03, 0x59, 0x78, 0xa5, 0xbd, 0xb2, 0x09, 0x8e, 0xcb, 0xe5, 0xbd, + 0xa2, 0x79, 0x98, 0xe9, 0x68, 0x0e, 0xc1, 0x6a, 0xb3, 0x6b, 0x19, 0x2d, 0xac, 0x72, 0xac, 0x74, + 0x92, 0x95, 0x4e, 0xb1, 0xac, 0x22, 0xcb, 0xe1, 0x7a, 0x77, 0xd6, 0x69, 0x7d, 0xee, 0xff, 0xe1, + 0xb4, 0x9e, 0xf9, 0x69, 0x08, 0x26, 0xd8, 0x2e, 0x43, 0x37, 0x21, 0x4c, 0xd7, 0x52, 0xc4, 0x97, + 0x46, 0x3d, 0x31, 0xb1, 0x3a, 0x08, 0x41, 0xd8, 0xd2, 0xda, 0x38, 0x8d, 0xd8, 0x4a, 0xb3, 0x6f, + 0x74, 0x11, 0xa2, 0x04, 0xdf, 0x53, 0xef, 0x6b, 0xad, 0xf4, 0x0c, 0x53, 0xc4, 0x08, 0xc1, 0xf7, + 0xee, 0x68, 0x2d, 0x74, 0x01, 0x22, 0x26, 0x51, 0x2d, 0xfc, 0x20, 0x3d, 0xcb, 0xad, 0x92, 0x49, + 0x36, 0xf0, 0x03, 0xf4, 0x22, 0xc4, 0x1f, 0x68, 0x44, 0xc5, 0xed, 0x8e, 0x7b, 0xc0, 0xe6, 0x22, + 0x46, 0x55, 0x97, 0x54, 0x68, 0x9a, 0x39, 0x2f, 0x9a, 0xb3, 0x8b, 0x5d, 0x55, 0xb7, 0x5b, 0x24, + 0x7d, 0x81, 0x6e, 0x55, 0x7a, 0x5a, 0xa3, 0xa2, 0x92, 0xdd, 0x22, 0xb5, 0x70, 0x2c, 0x24, 0x8f, + 0xd7, 0xc2, 0xb1, 0x71, 0x39, 0x5c, 0x0b, 0xc7, 0xc2, 0xf2, 0x44, 0x2d, 0x1c, 0x9b, 0x90, 0x23, + 0xb5, 0x70, 0x2c, 0x22, 0x47, 0x6b, 0xe1, 0x58, 0x54, 0x8e, 0xd5, 0xc2, 0xb1, 0x98, 0x1c, 0xaf, + 0x85, 0x63, 0x71, 0x19, 0x6a, 0xe1, 0x18, 0xc8, 0x93, 0xb5, 0x70, 0x6c, 0x52, 0x9e, 0xaa, 0x85, + 0x63, 0x53, 0x72, 0xa2, 0x16, 0x8e, 0x25, 0xe4, 0x64, 0x2d, 0x1c, 0x4b, 0xca, 0xd3, 0xb5, 0x70, + 0x6c, 0x5a, 0x96, 0x6b, 0xe1, 0x98, 0x2c, 0xa7, 0x6a, 0xe1, 0x58, 0x4a, 0x46, 0x99, 0x8a, 0x08, + 0x68, 0x6a, 0xe8, 0x7b, 0x7d, 0xf3, 0x34, 0xf2, 0x49, 0x8e, 0x55, 0xca, 0xfd, 0x4c, 0x02, 0xb9, + 0x8e, 0xef, 0x75, 0xb1, 0xa5, 0xe3, 0x3b, 0x5a, 0xab, 0xb4, 0xd7, 0xb5, 0xf6, 0xd1, 0x2b, 0x30, + 0xad, 0xd3, 0x0f, 0x95, 0x47, 0xf9, 0xe8, 0x8c, 0x49, 0x6c, 0xc6, 0x12, 0x4c, 0x5c, 0xa7, 0x52, + 0x3a, 0x71, 0x2f, 0x01, 0x88, 0x72, 0x94, 0x4d, 0x42, 0xac, 0x48, 0x9c, 0x17, 0xa1, 0x14, 0x32, + 0x00, 0xe3, 0xd8, 0x0f, 0x18, 0x65, 0xf5, 0xc1, 0x28, 0xf6, 0x03, 0xb4, 0x00, 0xb3, 0x16, 0x7e, + 0xe8, 0xaa, 0x83, 0x85, 0x19, 0x3d, 0x29, 0x29, 0x9a, 0x57, 0x0a, 0x56, 0xc8, 0xfd, 0x73, 0x08, + 0xa6, 0xbd, 0x4e, 0x7b, 0x9c, 0xbe, 0x03, 0x32, 0x5d, 0x5d, 0xd3, 0x50, 0x5d, 0x9b, 0x23, 0x79, + 0xec, 0xfe, 0xc1, 0x29, 0x74, 0x3c, 0x80, 0x42, 0xd3, 0x55, 0xa3, 0x61, 0xb3, 0xe6, 0xb8, 0x79, + 0x53, 0x12, 0x24, 0x28, 0xcb, 0x6c, 0x43, 0xd2, 0xab, 0xc4, 0x25, 0xa8, 0x04, 0x91, 0xbe, 0xf6, + 0x5e, 0x1b, 0xa1, 0x3d, 0x6f, 0xaa, 0x15, 0x51, 0x35, 0xf3, 0x9b, 0x80, 0x8e, 0xb7, 0x1d, 0x34, + 0xad, 0x13, 0xdc, 0xb4, 0x6e, 0xf6, 0x9b, 0xd6, 0xf7, 0xce, 0x37, 0xb6, 0x40, 0xb7, 0x83, 0x21, + 0xaa, 0x7f, 0x08, 0x41, 0x92, 0x1b, 0x26, 0xdf, 0xa6, 0x52, 0x8a, 0xa2, 0x0c, 0x68, 0x5a, 0xbb, + 0x6a, 0x47, 0x08, 0xd9, 0xf8, 0x42, 0x8a, 0xec, 0x65, 0xf8, 0x85, 0xbf, 0x4d, 0x3d, 0x0f, 0xcd, + 0xe8, 0x15, 0x0c, 0xb1, 0x82, 0x53, 0x54, 0xe8, 0x17, 0xba, 0x02, 0x49, 0xe6, 0x3d, 0xf6, 0x4a, + 0x8d, 0xb3, 0x52, 0x09, 0x26, 0xf5, 0x8b, 0x15, 0x21, 0x41, 0x3a, 0x9a, 0xd5, 0x2b, 0x15, 0x66, + 0x93, 0x7a, 0x46, 0x40, 0x7d, 0x8a, 0xd6, 0x09, 0x3a, 0x04, 0x0e, 0x26, 0xdd, 0x36, 0x56, 0x3b, + 0x36, 0x8f, 0xb8, 0x8c, 0x2b, 0x71, 0x2e, 0xd9, 0xb2, 0x09, 0xda, 0x66, 0xaa, 0xc2, 0xe6, 0x42, + 0x35, 0xf8, 0xe4, 0xa4, 0x23, 0xac, 0x95, 0xeb, 0xa3, 0x4f, 0xa7, 0x32, 0x4d, 0xfa, 0x05, 0xb9, + 0xbf, 0x92, 0xe0, 0x22, 0xf5, 0xc6, 0xf8, 0x4e, 0x2b, 0xb1, 0xab, 0x33, 0x4f, 0x3b, 0x35, 0x88, + 0x32, 0x37, 0xcf, 0x77, 0x67, 0x57, 0x8e, 0x0e, 0xb3, 0x11, 0x5a, 0xfa, 0x99, 0xad, 0x5c, 0x84, + 0x02, 0x57, 0x59, 0x24, 0xc1, 0x75, 0x34, 0x8b, 0x98, 0xf4, 0x4c, 0x4d, 0x97, 0xad, 0x8d, 0xdb, + 0x4d, 0x7a, 0xae, 0x0d, 0x31, 0x83, 0x36, 0xdb, 0x97, 0xb9, 0xce, 0xf3, 0x72, 0x19, 0x48, 0x0f, + 0x76, 0xd9, 0x0f, 0x53, 0xfe, 0x1a, 0xcc, 0x6d, 0xe0, 0x07, 0xc3, 0x46, 0x53, 0x84, 0x28, 0x67, + 0x3a, 0x4f, 0xe5, 0xaf, 0x0e, 0x92, 0x4e, 0xf0, 0xf6, 0x30, 0xcf, 0x7a, 0xda, 0x60, 0x15, 0x14, + 0xaf, 0x62, 0xee, 0x33, 0xb8, 0x38, 0x80, 0xee, 0x2f, 0xdf, 0x47, 0x10, 0x21, 0xae, 0xe6, 0x0a, + 0xf7, 0x2c, 0x39, 0x0a, 0x7a, 0xdd, 0xd5, 0xdc, 0x2e, 0x51, 0x44, 0xbd, 0x9c, 0xc2, 0x02, 0xac, + 0xdd, 0x36, 0xa6, 0x2a, 0xb2, 0x66, 0x12, 0x17, 0x7d, 0x04, 0x53, 0x42, 0x25, 0xa8, 0xa6, 0x78, + 0xfd, 0x3e, 0x43, 0xab, 0x26, 0x1d, 0x1f, 0x84, 0xe4, 0x7e, 0x2e, 0xc1, 0x4c, 0xd9, 0xb1, 0x3b, + 0x1d, 0x6c, 0x08, 0x9b, 0xc3, 0x27, 0xc3, 0x33, 0x35, 0x52, 0xc0, 0xd4, 0x6c, 0x40, 0xa8, 0x5a, + 0x16, 0xc7, 0x8a, 0x5b, 0xcf, 0x7a, 0x5a, 0xa9, 0x96, 0xd1, 0x7b, 0x7c, 0x46, 0xba, 0x84, 0x11, + 0x68, 0xf2, 0x58, 0x9c, 0xad, 0x4f, 0x4f, 0x03, 0x53, 0xd1, 0x25, 0xb9, 0x2f, 0xa2, 0x70, 0x21, + 0x38, 0xcb, 0xcb, 0x25, 0xaf, 0xe3, 0x9f, 0x43, 0xd4, 0x8b, 0xb5, 0x8c, 0x40, 0x94, 0xc3, 0x20, + 0xf2, 0x62, 0x3e, 0x82, 0xf1, 0x16, 0x0f, 0x13, 0xd5, 0x21, 0x65, 0x5a, 0x2e, 0x76, 0x5a, 0x58, + 0xbb, 0x4f, 0xbd, 0x0b, 0x3a, 0x67, 0x22, 0xb6, 0x3d, 0xaa, 0x2d, 0x97, 0x03, 0x00, 0xdc, 0x27, + 0xf8, 0x1c, 0x66, 0x82, 0xa0, 0x5e, 0xff, 0x4f, 0x0f, 0xaa, 0xb2, 0xee, 0xf5, 0x60, 0xbd, 0xe8, + 0x6f, 0x00, 0xc8, 0x8b, 0x0c, 0xdd, 0xf5, 0x0f, 0x06, 0x3c, 0x70, 0x7e, 0xf3, 0xa9, 0x67, 0xa4, + 0x3c, 0x70, 0x48, 0xe8, 0x73, 0x75, 0x99, 0x15, 0xfc, 0x86, 0x5c, 0xdd, 0x3b, 0x10, 0xe1, 0xb1, + 0x55, 0x71, 0x59, 0x74, 0xeb, 0x69, 0x87, 0xc0, 0x63, 0xb6, 0x8a, 0x40, 0xcb, 0xfc, 0xa1, 0x04, + 0x53, 0xc1, 0xe5, 0x46, 0x26, 0xc4, 0xd8, 0xf4, 0x7b, 0x9c, 0x36, 0xfe, 0xdc, 0x0f, 0xd0, 0x5c, + 0x95, 0xaa, 0x06, 0xf5, 0xc4, 0x0c, 0xc7, 0xee, 0xf4, 0x2e, 0x0b, 0xc7, 0x95, 0x18, 0x15, 0x50, + 0xdf, 0x31, 0xf3, 0x5b, 0x10, 0xf7, 0x27, 0x3d, 0x10, 0x12, 0x1b, 0x7f, 0x8e, 0x21, 0xb1, 0x53, + 0xdb, 0x2f, 0x43, 0xa2, 0x6f, 0xc6, 0xd0, 0x9c, 0xdf, 0x87, 0x70, 0x31, 0xc2, 0xfb, 0x70, 0x26, + 0x4a, 0xee, 0x2f, 0xa2, 0x30, 0x33, 0x8c, 0x6a, 0x3f, 0x01, 0x39, 0xc0, 0x5b, 0x6a, 0xcb, 0x24, + 0xae, 0xd0, 0xcd, 0x6b, 0xa7, 0x9f, 0xaa, 0x03, 0xe4, 0x27, 0x54, 0x31, 0xe9, 0xf4, 0x53, 0xe2, + 0x67, 0x90, 0x34, 0x78, 0xc7, 0x45, 0xd8, 0x5b, 0x5c, 0xf9, 0x9f, 0x76, 0x1a, 0x1e, 0x42, 0x80, + 0x02, 0x3d, 0x61, 0x04, 0xb2, 0x08, 0xd2, 0x21, 0xe1, 0x83, 0x1f, 0x74, 0xc4, 0xb1, 0xea, 0xd9, + 0xc9, 0x70, 0xca, 0x6b, 0x85, 0x62, 0xa2, 0x5d, 0x98, 0xf6, 0x1a, 0xf1, 0x4e, 0xe0, 0xf1, 0xe7, + 0xd2, 0x8c, 0x37, 0x31, 0x75, 0x71, 0x22, 0xff, 0xb1, 0x04, 0x33, 0x5e, 0x4b, 0x7e, 0xe4, 0xd8, + 0x34, 0x18, 0x9d, 0x25, 0x8a, 0xf5, 0xa3, 0xc3, 0x6c, 0x4a, 0xcc, 0x8c, 0x17, 0xc0, 0x78, 0x66, + 0xbd, 0x4b, 0x19, 0x03, 0x80, 0x06, 0x75, 0x22, 0x68, 0x3e, 0x6d, 0x78, 0xa2, 0xe7, 0x44, 0x50, + 0x62, 0x7b, 0x76, 0x27, 0x82, 0x7e, 0x56, 0x0d, 0xf4, 0xdb, 0x12, 0xa4, 0xf8, 0x6d, 0x55, 0xbb, + 0xeb, 0x6a, 0xfc, 0x62, 0xd8, 0x3b, 0x9a, 0x7f, 0x72, 0x74, 0x98, 0x9d, 0x66, 0xcb, 0xbb, 0x2e, + 0xf2, 0x58, 0xb3, 0xc5, 0xa7, 0x6d, 0xb6, 0x87, 0x22, 0x4e, 0xb2, 0xbe, 0xc0, 0x40, 0xab, 0x90, + 0xe4, 0xf1, 0x0a, 0xef, 0x49, 0x11, 0x3b, 0xb3, 0x27, 0x8a, 0x2f, 0x3f, 0x39, 0xcc, 0xce, 0x0f, + 0xd9, 0x27, 0x3c, 0xd4, 0x71, 0x87, 0x97, 0x55, 0x12, 0x3b, 0xc1, 0x24, 0x5a, 0x83, 0x69, 0xee, + 0x79, 0xfa, 0x27, 0x5c, 0x16, 0xb1, 0x18, 0xf1, 0x8e, 0x95, 0x7b, 0xad, 0xbe, 0x54, 0x84, 0xa1, + 0xe6, 0x60, 0x76, 0xa8, 0xd3, 0xf4, 0x55, 0x04, 0xe6, 0xfa, 0x69, 0xd5, 0x77, 0x6b, 0xd4, 0x41, + 0x7b, 0xfb, 0xe1, 0xc8, 0xd4, 0xec, 0x61, 0x70, 0x6a, 0xf4, 0x52, 0x83, 0x16, 0xf7, 0xf3, 0x01, + 0xeb, 0xf5, 0x14, 0xf8, 0x6c, 0x79, 0x07, 0xf0, 0x3d, 0x13, 0x76, 0xd7, 0xb7, 0x2c, 0x3c, 0xf0, + 0xf4, 0xd1, 0x53, 0xc0, 0xb3, 0xfa, 0x5e, 0xd2, 0xb7, 0x2d, 0xff, 0x24, 0x41, 0xa2, 0x6f, 0x64, + 0xbf, 0x4a, 0xe3, 0xb2, 0xe5, 0xfb, 0x56, 0xfc, 0xe5, 0xd9, 0xbb, 0xe7, 0x1f, 0x56, 0xbf, 0xcb, + 0x95, 0xf9, 0x6b, 0x09, 0x12, 0x7d, 0x13, 0xf9, 0x0d, 0x99, 0xa5, 0xe7, 0xdf, 0xf3, 0x26, 0x24, + 0xfb, 0x97, 0x28, 0xd0, 0x86, 0xf4, 0x7c, 0xda, 0xc8, 0x7d, 0x17, 0x22, 0x5c, 0x82, 0x10, 0x24, + 0x3f, 0x2e, 0x54, 0x1b, 0xd5, 0x8d, 0x65, 0x75, 0x69, 0x53, 0x51, 0x97, 0x4b, 0xf2, 0x18, 0x9a, + 0x82, 0x58, 0xb9, 0xb2, 0x56, 0xa1, 0x42, 0x59, 0x42, 0x93, 0x10, 0x65, 0xa9, 0x4a, 0x59, 0x0e, + 0xe5, 0x8a, 0x20, 0x73, 0xec, 0x1d, 0x4c, 0xcd, 0x0c, 0x3d, 0x46, 0xa0, 0x3c, 0xcc, 0x30, 0x97, + 0xbf, 0x4d, 0x3d, 0x2b, 0xba, 0xbd, 0xd5, 0x80, 0x2f, 0x9e, 0xf2, 0xb3, 0xe8, 0xee, 0xdd, 0xd0, + 0xda, 0x38, 0xf7, 0x8b, 0x30, 0xa4, 0x7a, 0x20, 0x9e, 0x91, 0xfd, 0x73, 0xa9, 0x77, 0xa0, 0x89, + 0x9c, 0x79, 0xed, 0x78, 0xac, 0xbe, 0x38, 0xdb, 0x88, 0xeb, 0xbf, 0x8f, 0xe9, 0xa6, 0x79, 0x72, + 0x98, 0x4d, 0x0d, 0x76, 0x96, 0x3c, 0xe3, 0xbd, 0xa0, 0xd7, 0x45, 0x16, 0x7a, 0x35, 0xad, 0x7d, + 0xb5, 0xf7, 0xfe, 0x89, 0x87, 0x5e, 0x4d, 0x6b, 0x7f, 0x5b, 0xa9, 0x2a, 0x51, 0x9a, 0xb9, 0xed, + 0x98, 0xa8, 0x06, 0x61, 0xbb, 0xe3, 0x7a, 0x27, 0xe8, 0x77, 0xce, 0x35, 0xa4, 0xcd, 0x8e, 0x18, + 0x8f, 0xc2, 0x30, 0x50, 0x8d, 0xdf, 0xa4, 0xf7, 0x26, 0x9a, 0x11, 0xf2, 0x88, 0x14, 0x9a, 0xe8, + 0x5b, 0x88, 0xcc, 0x2e, 0x4c, 0x05, 0x67, 0x6c, 0xc8, 0x05, 0x42, 0xa1, 0x3f, 0xca, 0xf1, 0xda, + 0x48, 0x5d, 0x17, 0x27, 0xcc, 0xc0, 0x9d, 0xd2, 0x77, 0x21, 0xee, 0x8f, 0xe3, 0x3c, 0x57, 0x6b, + 0x9c, 0xe3, 0xfd, 0x10, 0xde, 0x84, 0x1c, 0xc9, 0x7d, 0x11, 0x82, 0x29, 0x05, 0x13, 0xbb, 0x75, + 0x1f, 0x1b, 0xd4, 0x83, 0xf2, 0xdf, 0xfb, 0x49, 0xa3, 0xbf, 0xf7, 0x2b, 0x40, 0xbc, 0x67, 0x81, + 0xce, 0xf1, 0xe6, 0xad, 0x57, 0x0b, 0x7d, 0x02, 0x89, 0xa6, 0xdd, 0xb5, 0x0c, 0xcd, 0x39, 0x60, + 0x7e, 0x15, 0xf3, 0x40, 0x92, 0x8b, 0x6f, 0x9d, 0xee, 0x0b, 0xfa, 0xbd, 0xce, 0x17, 0x45, 0x65, + 0xea, 0x3f, 0x29, 0x53, 0xcd, 0x40, 0x2a, 0xf7, 0x01, 0x4c, 0x05, 0x73, 0x51, 0x0c, 0xc2, 0x1b, + 0x9b, 0x1b, 0x15, 0xbe, 0x27, 0x8b, 0x85, 0xd2, 0xea, 0x52, 0x75, 0x6d, 0x4d, 0x96, 0xa8, 0xbc, + 0x72, 0xb7, 0xda, 0x90, 0x43, 0x74, 0x77, 0x2a, 0x95, 0x7a, 0xa3, 0xa0, 0x34, 0xbc, 0x48, 0x67, + 0x0e, 0x43, 0x22, 0xd8, 0x1e, 0x65, 0x3e, 0xea, 0x76, 0x32, 0x41, 0xdf, 0xc9, 0xfb, 0xd5, 0x11, + 0x7b, 0xec, 0x69, 0x90, 0x13, 0x44, 0xcd, 0xfd, 0x4b, 0x08, 0x50, 0x6f, 0xe1, 0x7d, 0xb2, 0xba, + 0x0b, 0xa0, 0xef, 0x61, 0x7d, 0xbf, 0x63, 0x9b, 0x96, 0x2b, 0xce, 0x9a, 0xef, 0x8e, 0xa4, 0x3b, + 0x3e, 0x59, 0x95, 0xfc, 0xfa, 0x4a, 0x00, 0x0b, 0xfd, 0xc1, 0xe9, 0x91, 0xf2, 0x71, 0x16, 0x29, + 0x67, 0x3b, 0xff, 0x57, 0x1b, 0x2d, 0x2f, 0x00, 0xf4, 0x7a, 0x8c, 0x6e, 0xc0, 0xc4, 0x39, 0xa2, + 0x1b, 0xbc, 0x6c, 0x50, 0xd7, 0x73, 0xff, 0x13, 0x06, 0x54, 0x72, 0xb0, 0xe6, 0x62, 0x4a, 0xd1, + 0xe4, 0xb4, 0x10, 0x47, 0x11, 0x26, 0xf8, 0x91, 0x3e, 0x74, 0x9e, 0x23, 0xbd, 0xd7, 0x34, 0xab, + 0x8a, 0xbe, 0x0f, 0x53, 0xba, 0xdd, 0xea, 0xb6, 0x2d, 0x95, 0xbd, 0xc7, 0x11, 0xe7, 0x8f, 0xb7, + 0x4f, 0x5b, 0xb1, 0x63, 0x9d, 0xcb, 0x97, 0xec, 0x16, 0x4d, 0xfb, 0x2f, 0x57, 0x19, 0x20, 0x2b, + 0x81, 0x2e, 0x41, 0xdc, 0x67, 0x1e, 0xa6, 0x0e, 0x71, 0xa5, 0x27, 0x40, 0x8b, 0x30, 0xa1, 0x11, + 0xd5, 0xde, 0x61, 0xce, 0xf4, 0x59, 0x5b, 0x51, 0x09, 0x6b, 0x64, 0x73, 0x07, 0x5d, 0x87, 0x54, + 0x5b, 0x7b, 0xa8, 0xee, 0x38, 0x9a, 0x2e, 0x9c, 0xe3, 0x16, 0x67, 0x42, 0x49, 0x99, 0x6e, 0x6b, + 0x0f, 0x97, 0x84, 0xbc, 0x6a, 0xb4, 0x30, 0xba, 0x01, 0x89, 0x9d, 0x7b, 0xfc, 0x68, 0xc5, 0xad, + 0x12, 0x7f, 0xdc, 0x34, 0x7d, 0x74, 0x98, 0x9d, 0x5c, 0xba, 0xcd, 0x26, 0x86, 0xda, 0x24, 0x65, + 0x72, 0xe7, 0x9e, 0x9f, 0xc8, 0xfc, 0xb7, 0x04, 0x51, 0x31, 0x22, 0xd4, 0x01, 0x10, 0xd3, 0x63, + 0x1a, 0x7c, 0x4d, 0x13, 0xc5, 0xdb, 0x47, 0x87, 0xd9, 0x78, 0x89, 0x49, 0xab, 0x65, 0xf2, 0xe4, + 0x30, 0xfb, 0xd1, 0xd3, 0x5a, 0x14, 0x0f, 0x44, 0x89, 0xf3, 0x46, 0xaa, 0x06, 0x0b, 0xe4, 0xee, + 0x69, 0x44, 0xdd, 0x33, 0x89, 0x6b, 0xef, 0x3a, 0x5a, 0x5b, 0x5c, 0xd3, 0x4f, 0xed, 0x69, 0x64, + 0xc5, 0x93, 0xa1, 0x0c, 0xf5, 0xcd, 0xee, 0xf3, 0xe7, 0x54, 0xfc, 0xd1, 0x86, 0x9f, 0x46, 0x8b, + 0x70, 0xc1, 0xaf, 0xac, 0xd2, 0x99, 0x6a, 0x76, 0xf5, 0x7d, 0xcc, 0x6c, 0x10, 0x25, 0xf7, 0x19, + 0x3f, 0x73, 0x5d, 0x7b, 0x58, 0xe4, 0x59, 0xb9, 0x0b, 0x30, 0x13, 0x58, 0x56, 0xdf, 0x93, 0xc6, + 0x20, 0xf3, 0xd7, 0x04, 0x81, 0xb7, 0xd8, 0xb7, 0x61, 0x7a, 0xe0, 0xa7, 0x06, 0x82, 0x7f, 0x83, + 0x21, 0xc2, 0xfe, 0xdf, 0x26, 0xe4, 0x4b, 0x3c, 0xe9, 0x9d, 0x0d, 0x92, 0x7a, 0x5f, 0x3a, 0x37, + 0x03, 0x29, 0xbf, 0x19, 0xbf, 0xed, 0x17, 0xe1, 0x85, 0xfa, 0xed, 0x35, 0xd6, 0x9f, 0x92, 0xdd, + 0xee, 0xf0, 0x45, 0xf5, 0xe2, 0xbc, 0x97, 0x20, 0x73, 0x3c, 0xd3, 0xaf, 0xfa, 0xf3, 0x04, 0x44, + 0xb7, 0xb4, 0x83, 0x96, 0xad, 0x19, 0x68, 0x1e, 0x26, 0xbd, 0x27, 0x54, 0x5e, 0x57, 0xe3, 0x4a, + 0x50, 0xd4, 0xaf, 0xa1, 0x32, 0xbb, 0x44, 0x0a, 0x68, 0xa8, 0x09, 0xc9, 0x2e, 0xc1, 0x0e, 0x55, + 0x1e, 0x95, 0xfd, 0xa4, 0x82, 0x5b, 0xaa, 0x62, 0xf1, 0xc9, 0x61, 0xf6, 0xd6, 0x68, 0xeb, 0x8e, + 0xf5, 0xae, 0x63, 0xba, 0x07, 0xf9, 0xfa, 0xed, 0xb5, 0x6d, 0x01, 0x45, 0x69, 0xc6, 0x56, 0x12, + 0xdd, 0x60, 0x52, 0xbc, 0x94, 0xa3, 0x6b, 0xa8, 0xb6, 0x4d, 0xdd, 0xb1, 0x89, 0x77, 0x55, 0x23, + 0xa4, 0xeb, 0x4c, 0x88, 0x5e, 0x85, 0xe9, 0x1d, 0xd3, 0x62, 0xb7, 0x8d, 0x5e, 0x39, 0x7e, 0x4b, + 0x93, 0xf4, 0xc4, 0xa2, 0xe0, 0x7d, 0x48, 0x06, 0x9e, 0xa8, 0x51, 0xfd, 0x8d, 0x30, 0xfd, 0xdd, + 0x3c, 0x3a, 0xcc, 0x26, 0x7a, 0x7c, 0xc0, 0x75, 0xf8, 0x59, 0xbc, 0xa2, 0x44, 0xaf, 0x19, 0xaa, + 0xc1, 0xb3, 0x30, 0xc1, 0x7e, 0x70, 0xc3, 0xdf, 0xf8, 0x2a, 0x3c, 0x81, 0x2a, 0x90, 0x10, 0x51, + 0x14, 0xfe, 0x6b, 0x1c, 0xf1, 0xae, 0x6f, 0x3e, 0xa0, 0x35, 0xde, 0xef, 0x75, 0xf2, 0x15, 0x4b, + 0xb7, 0x0d, 0x6c, 0x54, 0x68, 0x5a, 0x11, 0x41, 0x63, 0x96, 0x20, 0x68, 0x19, 0x92, 0x7a, 0x0b, + 0x6b, 0x56, 0xb7, 0xe3, 0xe1, 0xa0, 0x11, 0x71, 0x12, 0xa2, 0x9e, 0x00, 0xda, 0x00, 0xb4, 0xc3, + 0x9e, 0x2d, 0x05, 0x7b, 0xc5, 0x6e, 0x25, 0x47, 0x01, 0x93, 0x59, 0x5d, 0xa5, 0xd7, 0x33, 0xf4, + 0x32, 0x24, 0x2c, 0xdb, 0xd2, 0x35, 0x4b, 0xc7, 0x2d, 0x46, 0xca, 0xfc, 0x22, 0xb3, 0x5f, 0x88, + 0x8a, 0x10, 0xe1, 0x57, 0xde, 0xe2, 0xf8, 0x7b, 0x75, 0xd4, 0x97, 0xf0, 0x2b, 0x63, 0x8a, 0xa8, + 0x89, 0x2a, 0x10, 0x75, 0xf8, 0xf3, 0x0b, 0x76, 0x0d, 0x7e, 0x66, 0x18, 0x2a, 0xf0, 0xb8, 0x63, + 0x65, 0x4c, 0xf1, 0xea, 0xa2, 0x86, 0xf7, 0x0a, 0x95, 0x9b, 0x60, 0xf1, 0x90, 0x30, 0x3f, 0xe2, + 0xe1, 0xa2, 0x07, 0xd8, 0x87, 0x42, 0x07, 0x68, 0xb2, 0x6b, 0x2c, 0x76, 0x41, 0x7e, 0xfa, 0x00, + 0xfb, 0x1e, 0x62, 0xd0, 0x01, 0xf2, 0x9a, 0x68, 0x83, 0xfa, 0x10, 0x9e, 0x5b, 0xc0, 0xae, 0xce, + 0x27, 0x17, 0x5f, 0x3f, 0x8f, 0xeb, 0xbc, 0x32, 0xa6, 0x04, 0x10, 0xd0, 0x6d, 0x98, 0xd4, 0x7b, + 0xec, 0x96, 0x9e, 0x66, 0x80, 0x6f, 0x9c, 0xcb, 0xc4, 0xad, 0x50, 0xb3, 0xd6, 0x93, 0xa2, 0x4f, + 0x21, 0x49, 0xfa, 0x8e, 0x5a, 0xe9, 0x0b, 0x0c, 0xf5, 0xcd, 0xf3, 0x86, 0x7a, 0x57, 0xc6, 0x94, + 0x01, 0x24, 0xf4, 0xeb, 0x20, 0xbb, 0x03, 0x17, 0x42, 0xec, 0xee, 0xfb, 0xf4, 0x57, 0x9e, 0x27, + 0x5c, 0x7b, 0xad, 0x8c, 0x29, 0xc7, 0xd0, 0xd0, 0xe7, 0x30, 0x4d, 0xfa, 0x7f, 0xb1, 0x92, 0xbe, + 0xc8, 0x1a, 0xf8, 0xce, 0xa9, 0x97, 0x1a, 0xc3, 0x7e, 0x9b, 0xb3, 0x32, 0xa6, 0x0c, 0x62, 0x51, + 0x78, 0xab, 0xff, 0x5e, 0x89, 0xbd, 0xac, 0x38, 0x1d, 0x7e, 0xf8, 0x3d, 0x17, 0x85, 0x1f, 0xc0, + 0x42, 0xab, 0x10, 0x6f, 0x7b, 0xe6, 0x22, 0xfd, 0xc2, 0x99, 0xa7, 0x93, 0x41, 0x0b, 0xb6, 0x32, + 0xa6, 0xf4, 0xea, 0xa3, 0x1d, 0x40, 0xe4, 0x5e, 0x6b, 0xc0, 0x92, 0xa4, 0x5f, 0x64, 0xa8, 0xa7, + 0xb9, 0xf4, 0x27, 0xda, 0xa6, 0x95, 0x31, 0x65, 0x08, 0x62, 0x31, 0x0e, 0x51, 0x71, 0xcf, 0xe9, + 0x3f, 0x42, 0xe0, 0xcf, 0x0f, 0xf8, 0xc3, 0x83, 0x8c, 0xfc, 0x62, 0xee, 0x77, 0x01, 0x62, 0xbe, + 0x1f, 0xbd, 0x00, 0xc8, 0xf7, 0x70, 0x7a, 0x8f, 0xac, 0xa9, 0xf9, 0x0a, 0xad, 0x8c, 0x29, 0x29, + 0x2f, 0xaf, 0xf7, 0xce, 0xfa, 0x56, 0xdf, 0x0b, 0xac, 0x51, 0x7e, 0xc9, 0x44, 0x27, 0xc2, 0x7f, + 0xa2, 0x45, 0xcd, 0x8a, 0x78, 0x87, 0xeb, 0x9b, 0x15, 0x1e, 0x20, 0x4f, 0x7a, 0x62, 0x61, 0x56, + 0xae, 0x40, 0xd2, 0xe9, 0x5a, 0xec, 0x7a, 0x53, 0x84, 0x25, 0xb8, 0x5b, 0x97, 0x10, 0x52, 0x11, + 0x59, 0x28, 0x0d, 0x30, 0xdd, 0xb5, 0x33, 0x99, 0xce, 0x1b, 0xfb, 0x8a, 0xe4, 0x53, 0xdd, 0xd2, + 0x20, 0xd5, 0x5d, 0x3f, 0x9b, 0xea, 0x02, 0x30, 0x3e, 0xd7, 0x6d, 0x0f, 0xe5, 0xba, 0x85, 0x11, + 0x37, 0x6b, 0x00, 0xb1, 0x9f, 0xec, 0x4a, 0x03, 0x64, 0x77, 0xed, 0x4c, 0xb2, 0x0b, 0x8e, 0x51, + 0xb0, 0xdd, 0xe6, 0x10, 0xb6, 0x7b, 0xe3, 0x5c, 0x27, 0xa6, 0x15, 0xa9, 0x8f, 0xee, 0x94, 0x61, + 0x74, 0x97, 0x1f, 0x8d, 0xee, 0x02, 0x90, 0x7d, 0x7c, 0xf7, 0xd9, 0x31, 0xbe, 0x93, 0xcf, 0x26, + 0x8c, 0xa1, 0xb1, 0xa8, 0x15, 0xe9, 0x18, 0xe1, 0x69, 0x43, 0x08, 0x2f, 0xc5, 0xe0, 0x6f, 0x9c, + 0x83, 0xf0, 0x02, 0x0d, 0x1c, 0x67, 0xbc, 0xbb, 0x30, 0x15, 0x64, 0x29, 0xf6, 0x28, 0xe9, 0x74, + 0x3e, 0x3d, 0xe1, 0x27, 0x7d, 0x4c, 0x07, 0x02, 0x59, 0xe8, 0xfb, 0xc7, 0xc9, 0x6e, 0xe6, 0x4c, + 0xf0, 0x13, 0xae, 0xdd, 0x57, 0xa4, 0xe3, 0x6c, 0xb7, 0x16, 0x64, 0xbb, 0xd9, 0x33, 0x6d, 0xe1, + 0x31, 0x47, 0x7a, 0x45, 0x0a, 0xd2, 0xdd, 0xee, 0x50, 0xba, 0xe3, 0xd6, 0xe5, 0xed, 0x73, 0xd1, + 0x5d, 0x00, 0x7f, 0x08, 0x24, 0x7a, 0x05, 0x62, 0xae, 0xa3, 0xe9, 0xec, 0x8a, 0xe6, 0x02, 0xbb, + 0x87, 0x63, 0x01, 0xb2, 0x06, 0x95, 0xb1, 0x40, 0x1a, 0xfb, 0x30, 0x8a, 0x00, 0x31, 0xef, 0x99, + 0x49, 0x80, 0x23, 0x73, 0x3f, 0x91, 0x60, 0xbc, 0x66, 0x37, 0xd1, 0x4b, 0x81, 0xa8, 0x6d, 0x42, + 0x9c, 0xed, 0x27, 0x6a, 0x76, 0x53, 0x84, 0x5f, 0x3f, 0xec, 0xd5, 0x16, 0x87, 0xe0, 0x6f, 0x9f, + 0x32, 0x08, 0x3f, 0xe8, 0xed, 0x57, 0x42, 0xef, 0x43, 0xb4, 0xc3, 0x4f, 0x0a, 0x82, 0x32, 0x73, + 0xa7, 0xd5, 0xe7, 0x25, 0x15, 0xaf, 0xca, 0xf5, 0x6b, 0xc1, 0x1f, 0x0d, 0xaf, 0xdb, 0x06, 0x46, + 0x49, 0x80, 0x2d, 0x8d, 0x90, 0xce, 0x9e, 0xa3, 0x11, 0x2c, 0x8f, 0xa1, 0x28, 0x8c, 0xaf, 0xae, + 0xd7, 0x65, 0xe9, 0xfa, 0xdd, 0x60, 0xc8, 0xb5, 0xac, 0x14, 0xaa, 0x1b, 0xd5, 0x8d, 0x65, 0x75, + 0xa3, 0xb0, 0x5e, 0xa9, 0xcb, 0x63, 0x28, 0x0d, 0xb3, 0x1f, 0x17, 0xaa, 0x0d, 0x11, 0x83, 0x55, + 0xab, 0x1b, 0x8d, 0x8a, 0x72, 0xa7, 0xb0, 0x26, 0x4b, 0x68, 0x0e, 0x90, 0xb2, 0x59, 0x5a, 0xad, + 0x97, 0x8b, 0x6a, 0x69, 0x73, 0x7d, 0xab, 0x50, 0x6a, 0x54, 0x37, 0x37, 0xe4, 0x10, 0x8a, 0x41, + 0xb8, 0xbc, 0xb9, 0x51, 0x91, 0xe1, 0xfa, 0x3f, 0x86, 0x21, 0xcc, 0xa2, 0x45, 0x2f, 0xc3, 0xe4, + 0xf6, 0x46, 0x7d, 0xab, 0x52, 0xaa, 0x2e, 0x55, 0x2b, 0x65, 0x79, 0x2c, 0x33, 0xf3, 0xe8, 0xf1, + 0xfc, 0x34, 0xcd, 0xda, 0xb6, 0x48, 0x07, 0xeb, 0x8c, 0xc4, 0x51, 0x06, 0x22, 0xc5, 0x42, 0x69, + 0x75, 0x7b, 0x4b, 0x96, 0x32, 0xc9, 0x47, 0x8f, 0xe7, 0x81, 0x16, 0xe0, 0x04, 0x8c, 0x2e, 0xf1, + 0x68, 0xd2, 0xa6, 0x52, 0x91, 0x43, 0x99, 0xe9, 0x47, 0x8f, 0xe7, 0x27, 0x59, 0x90, 0x4a, 0x90, + 0xe8, 0xab, 0x90, 0xa8, 0x97, 0x56, 0x2a, 0xeb, 0x05, 0xb5, 0xb4, 0x52, 0xd8, 0x58, 0xae, 0xc8, + 0xe3, 0x99, 0xd9, 0x47, 0x8f, 0xe7, 0xe5, 0xc1, 0x8d, 0x48, 0x9b, 0xa8, 0xae, 0x6f, 0x6d, 0x2a, + 0x0d, 0x39, 0xdc, 0x6b, 0x82, 0xf3, 0x1f, 0xca, 0x01, 0xf0, 0xda, 0x4b, 0x95, 0x4a, 0x59, 0x9e, + 0xc8, 0xa0, 0x47, 0x8f, 0xe7, 0x93, 0x34, 0xbf, 0x47, 0x6b, 0xe8, 0x0a, 0x4c, 0x95, 0x94, 0x4a, + 0xa1, 0x51, 0x51, 0xeb, 0x8d, 0x42, 0xa3, 0x2e, 0x47, 0x7a, 0x23, 0x09, 0x50, 0x15, 0xca, 0x43, + 0xaa, 0xb0, 0xdd, 0xd8, 0x54, 0xfb, 0xca, 0x46, 0x33, 0x17, 0x1f, 0x3d, 0x9e, 0x9f, 0xa1, 0x65, + 0x0b, 0x5d, 0xd7, 0x0e, 0x96, 0x7f, 0x1d, 0xe4, 0xbe, 0xfe, 0xab, 0xcb, 0x25, 0x39, 0x96, 0x99, + 0x7b, 0xf4, 0x78, 0x1e, 0x0d, 0x0e, 0x61, 0xb9, 0x84, 0xde, 0x82, 0xb9, 0xc6, 0x27, 0x5b, 0x95, + 0x72, 0xa5, 0x5e, 0x52, 0xfb, 0x87, 0x1d, 0xcf, 0xa4, 0x1f, 0x3d, 0x9e, 0x9f, 0xa5, 0x75, 0x8e, + 0x0d, 0xfd, 0x0d, 0x90, 0xeb, 0x0d, 0xa5, 0x52, 0x58, 0x57, 0xab, 0x1b, 0xcb, 0x95, 0x3a, 0x5b, + 0x2c, 0xe8, 0x75, 0x69, 0x80, 0x54, 0xe8, 0x10, 0x36, 0x2a, 0x1f, 0x0f, 0xe0, 0x4f, 0xf6, 0xca, + 0x0f, 0xf0, 0x04, 0x9a, 0x87, 0xf8, 0x7a, 0x75, 0x59, 0x29, 0x30, 0xdc, 0xa9, 0x4c, 0xea, 0xd1, + 0xe3, 0xf9, 0x04, 0x2d, 0xe7, 0xef, 0x7a, 0xf4, 0x16, 0xcc, 0xd6, 0x6f, 0xaf, 0xf1, 0xc9, 0x08, + 0x6a, 0x4c, 0x22, 0x93, 0x79, 0xf4, 0x78, 0x7e, 0x8e, 0x75, 0xe2, 0xd8, 0x5e, 0xce, 0xc4, 0x7e, + 0xe7, 0x27, 0x97, 0xc7, 0xfe, 0xec, 0x8b, 0xcb, 0x63, 0xc5, 0xab, 0x5f, 0xfe, 0xe7, 0xe5, 0xb1, + 0x2f, 0x8f, 0x2e, 0x4b, 0xbf, 0x3c, 0xba, 0x2c, 0x7d, 0x75, 0x74, 0x59, 0xfa, 0x8f, 0xa3, 0xcb, + 0xd2, 0xef, 0x7d, 0x7d, 0x79, 0xec, 0x97, 0x5f, 0x5f, 0x1e, 0xfb, 0xea, 0xeb, 0xcb, 0x63, 0x9f, + 0x46, 0xf8, 0x6e, 0x68, 0x46, 0xd8, 0x71, 0xf8, 0xc6, 0xff, 0x05, 0x00, 0x00, 0xff, 0xff, 0x43, + 0xa5, 0x10, 0x62, 0x9a, 0x41, 0x00, 0x00, } func (this *BackupEncryptionOptions) Equal(that interface{}) bool { @@ -5712,6 +5812,52 @@ func (m *MigrationProgress) MarshalToSizedBuffer(dAtA []byte) (int, error) { return len(dAtA) - i, nil } +func (m *SQLStatsCompactionDetails) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *SQLStatsCompactionDetails) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *SQLStatsCompactionDetails) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + +func (m *SQLStatsCompactionProgress) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *SQLStatsCompactionProgress) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *SQLStatsCompactionProgress) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + func (m *Payload) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) @@ -6103,6 +6249,29 @@ func (m *Payload_Migration) MarshalToSizedBuffer(dAtA []byte) (int, error) { } return len(dAtA) - i, nil } +func (m *Payload_SqlStatsCompaction) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *Payload_SqlStatsCompaction) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + if m.SqlStatsCompaction != nil { + { + size, err := m.SqlStatsCompaction.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintJobs(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1 + i-- + dAtA[i] = 0xda + } + return len(dAtA) - i, nil +} func (m *Progress) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) @@ -6123,13 +6292,6 @@ func (m *Progress) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l - if m.TraceID != 0 { - i = encodeVarintJobs(dAtA, i, uint64(m.TraceID)) - i-- - dAtA[i] = 0x1 - i-- - dAtA[i] = 0xa8 - } if m.Details != nil { { size := m.Details.Size() @@ -6139,6 +6301,13 @@ func (m *Progress) MarshalToSizedBuffer(dAtA []byte) (int, error) { } } } + if m.TraceID != 0 { + i = encodeVarintJobs(dAtA, i, uint64(m.TraceID)) + i-- + dAtA[i] = 0x1 + i-- + dAtA[i] = 0xa8 + } if len(m.RunningStatus) > 0 { i -= len(m.RunningStatus) copy(dAtA[i:], m.RunningStatus) @@ -6438,6 +6607,29 @@ func (m *Progress_Migration) MarshalToSizedBuffer(dAtA []byte) (int, error) { } return len(dAtA) - i, nil } +func (m *Progress_SqlStatsCompaction) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *Progress_SqlStatsCompaction) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + if m.SqlStatsCompaction != nil { + { + size, err := m.SqlStatsCompaction.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintJobs(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1 + i-- + dAtA[i] = 0xb2 + } + return len(dAtA) - i, nil +} func (m *Job) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) @@ -7554,6 +7746,24 @@ func (m *MigrationProgress) Size() (n int) { return n } +func (m *SQLStatsCompactionDetails) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *SQLStatsCompactionProgress) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + func (m *Payload) Size() (n int) { if m == nil { return 0 @@ -7748,6 +7958,18 @@ func (m *Payload_Migration) Size() (n int) { } return n } +func (m *Payload_SqlStatsCompaction) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.SqlStatsCompaction != nil { + l = m.SqlStatsCompaction.Size() + n += 2 + l + sovJobs(uint64(l)) + } + return n +} func (m *Progress) Size() (n int) { if m == nil { return 0 @@ -7926,6 +8148,18 @@ func (m *Progress_Migration) Size() (n int) { } return n } +func (m *Progress_SqlStatsCompaction) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.SqlStatsCompaction != nil { + l = m.SqlStatsCompaction.Size() + n += 2 + l + sovJobs(uint64(l)) + } + return n +} func (m *Job) Size() (n int) { if m == nil { return 0 @@ -15478,6 +15712,106 @@ func (m *MigrationProgress) Unmarshal(dAtA []byte) error { } return nil } +func (m *SQLStatsCompactionDetails) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowJobs + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: SQLStatsCompactionDetails: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: SQLStatsCompactionDetails: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + default: + iNdEx = preIndex + skippy, err := skipJobs(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthJobs + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *SQLStatsCompactionProgress) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowJobs + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: SQLStatsCompactionProgress: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: SQLStatsCompactionProgress: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + default: + iNdEx = preIndex + skippy, err := skipJobs(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthJobs + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} func (m *Payload) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 @@ -16258,6 +16592,41 @@ func (m *Payload) Unmarshal(dAtA []byte) error { } m.Details = &Payload_Migration{v} iNdEx = postIndex + case 27: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field SqlStatsCompaction", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowJobs + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthJobs + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthJobs + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + v := &SQLStatsCompactionDetails{} + if err := v.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + m.Details = &Payload_SqlStatsCompaction{v} + iNdEx = postIndex default: iNdEx = preIndex skippy, err := skipJobs(dAtA[iNdEx:]) @@ -16809,6 +17178,41 @@ func (m *Progress) Unmarshal(dAtA []byte) error { break } } + case 22: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field SqlStatsCompaction", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowJobs + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthJobs + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthJobs + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + v := &SQLStatsCompactionProgress{} + if err := v.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + m.Details = &Progress_SqlStatsCompaction{v} + iNdEx = postIndex default: iNdEx = preIndex skippy, err := skipJobs(dAtA[iNdEx:]) diff --git a/pkg/jobs/jobspb/jobs.proto b/pkg/jobs/jobspb/jobs.proto index 341a1b548c1c..03f5eb6623c0 100644 --- a/pkg/jobs/jobspb/jobs.proto +++ b/pkg/jobs/jobspb/jobs.proto @@ -663,6 +663,14 @@ message MigrationProgress { } +message SQLStatsCompactionDetails { + +} + +message SQLStatsCompactionProgress { + +} + message Payload { string description = 1; // If empty, the description is assumed to be the statement. @@ -706,10 +714,11 @@ message Payload { StreamIngestionDetails streamIngestion = 23; NewSchemaChangeDetails newSchemaChange = 24; MigrationDetails migration = 25; + SQLStatsCompactionDetails sqlStatsCompaction = 27; } reserved 26; - // NEXT ID: 27. + // NEXT ID: 28. } message Progress { @@ -732,6 +741,7 @@ message Progress { StreamIngestionProgress streamIngest = 18; NewSchemaChangeProgress newSchemaChange = 19; MigrationProgress migration = 20; + SQLStatsCompactionProgress sqlStatsCompaction = 22; } uint64 trace_id = 21 [(gogoproto.customname) = "TraceID"]; @@ -756,6 +766,7 @@ enum Type { STREAM_INGESTION = 10 [(gogoproto.enumvalue_customname) = "TypeStreamIngestion"]; NEW_SCHEMA_CHANGE = 11 [(gogoproto.enumvalue_customname) = "TypeNewSchemaChange"]; MIGRATION = 12 [(gogoproto.enumvalue_customname) = "TypeMigration"]; + SQL_STATS_COMPACTION = 13 [(gogoproto.enumvalue_customname) = "TypeSQLStatsCompaction"]; } message Job { diff --git a/pkg/jobs/jobspb/wrap.go b/pkg/jobs/jobspb/wrap.go index 03e8b8592986..26deda8ed0e2 100644 --- a/pkg/jobs/jobspb/wrap.go +++ b/pkg/jobs/jobspb/wrap.go @@ -92,6 +92,8 @@ func DetailsType(d isPayload_Details) Type { return TypeNewSchemaChange case *Payload_Migration: return TypeMigration + case *Payload_SqlStatsCompaction: + return TypeSQLStatsCompaction default: panic(errors.AssertionFailedf("Payload.Type called on a payload with an unknown details type: %T", d)) } @@ -128,6 +130,8 @@ func WrapProgressDetails(details ProgressDetails) interface { return &Progress_NewSchemaChange{NewSchemaChange: &d} case MigrationProgress: return &Progress_Migration{Migration: &d} + case SQLStatsCompactionProgress: + return &Progress_SqlStatsCompaction{SqlStatsCompaction: &d} default: panic(errors.AssertionFailedf("WrapProgressDetails: unknown details type %T", d)) } @@ -159,6 +163,8 @@ func (p *Payload) UnwrapDetails() Details { return *d.NewSchemaChange case *Payload_Migration: return *d.Migration + case *Payload_SqlStatsCompaction: + return *d.SqlStatsCompaction default: return nil } @@ -190,6 +196,8 @@ func (p *Progress) UnwrapDetails() ProgressDetails { return *d.NewSchemaChange case *Progress_Migration: return *d.Migration + case *Progress_SqlStatsCompaction: + return *d.SqlStatsCompaction default: return nil } @@ -234,6 +242,8 @@ func WrapPayloadDetails(details Details) interface { return &Payload_NewSchemaChange{NewSchemaChange: &d} case MigrationDetails: return &Payload_Migration{Migration: &d} + case SQLStatsCompactionDetails: + return &Payload_SqlStatsCompaction{SqlStatsCompaction: &d} default: panic(errors.AssertionFailedf("jobs.WrapPayloadDetails: unknown details type %T", d)) } @@ -269,7 +279,7 @@ const ( func (Type) SafeValue() {} // NumJobTypes is the number of jobs types. -const NumJobTypes = 13 +const NumJobTypes = 14 // MarshalJSONPB redacts sensitive sink URI parameters from ChangefeedDetails. func (p ChangefeedDetails) MarshalJSONPB(x *jsonpb.Marshaler) ([]byte, error) { diff --git a/pkg/sql/BUILD.bazel b/pkg/sql/BUILD.bazel index c5eb99b5a6d8..17699051b20a 100644 --- a/pkg/sql/BUILD.bazel +++ b/pkg/sql/BUILD.bazel @@ -33,6 +33,7 @@ go_library( "comment_on_database.go", "comment_on_index.go", "comment_on_table.go", + "compact_sql_stats.go", "conn_executor.go", "conn_executor_exec.go", "conn_executor_prepare.go", @@ -379,6 +380,7 @@ go_library( "//pkg/util/hlc", "//pkg/util/humanizeutil", "//pkg/util/iterutil", + "//pkg/util/jobutil", "//pkg/util/json", "//pkg/util/log", "//pkg/util/log/eventpb", diff --git a/pkg/sql/compact_sql_stats.go b/pkg/sql/compact_sql_stats.go new file mode 100644 index 000000000000..9ac5e74b7065 --- /dev/null +++ b/pkg/sql/compact_sql_stats.go @@ -0,0 +1,80 @@ +// Copyright 2021 The Cockroach Authors. +// +// Use of this software is governed by the Business Source License +// included in the file licenses/BSL.txt. +// +// As of the Change Date specified in that file, in accordance with +// the Business Source License, use of this software will be governed +// by the Apache License, Version 2.0, included in the file +// licenses/APL.txt. + +package sql + +import ( + "context" + + "github.com/cockroachdb/cockroach/pkg/jobs" + "github.com/cockroachdb/cockroach/pkg/jobs/jobspb" + "github.com/cockroachdb/cockroach/pkg/kv" + "github.com/cockroachdb/cockroach/pkg/settings/cluster" + "github.com/cockroachdb/cockroach/pkg/sql/sqlstats/persistedsqlstats" + "github.com/cockroachdb/cockroach/pkg/util/log" + "github.com/cockroachdb/errors" +) + +type sqlStatsCompactionResumer struct { + *jobs.Job + compactionExecutor *persistedsqlstats.StatsCompactor +} + +var _ jobs.Resumer = &sqlStatsCompactionResumer{} + +// Resume implements the jobs.Resumer interface. +func (r *sqlStatsCompactionResumer) Resume(ctx context.Context, execCtx interface{}) error { + log.Infof(ctx, "starting sql stats compaction job") + p := execCtx.(JobExecContext) + ie := p.ExecCfg().InternalExecutor + db := p.ExecCfg().DB + + // We check for concurrently running SQL Stats compaction jobs. We only allow + // one job to be running at the same time. + if err := persistedsqlstats.CheckExistingCompactionJob(ctx, r.Job, ie, nil /* txn */); err != nil { + if errors.Is(err, persistedsqlstats.ErrConcurrentSQLStatsCompaction) { + log.Infof(ctx, "exiting due to a running sql stats compaction job") + return nil + } + return err + } + + r.compactionExecutor.Init(ie, db) + err := r.compactionExecutor.DeleteOldestEntries(ctx) + + return db.Txn(ctx, func(ctx context.Context, txn *kv.Txn) error { + if err != nil { + if jobErr := r.Job.FractionProgressed(ctx, txn, func(ctx context.Context, _ jobspb.ProgressDetails) float32 { + return 0 + }); jobErr != nil { + err = errors.CombineErrors(err, jobErr) + return err + } + } + + return nil + }) +} + +// OnFailOrCancel implements the jobs.Resumer interface. +func (r *sqlStatsCompactionResumer) OnFailOrCancel(ctx context.Context, execCtx interface{}) error { + return nil +} + +func init() { + jobs.RegisterConstructor(jobspb.TypeSQLStatsCompaction, func(job *jobs.Job, settings *cluster.Settings) jobs.Resumer { + return &sqlStatsCompactionResumer{ + Job: job, + compactionExecutor: &persistedsqlstats.StatsCompactor{ + Settings: settings, + }, + } + }) +} diff --git a/pkg/sql/conn_executor.go b/pkg/sql/conn_executor.go index 06e53561dda3..501d4b728ecb 100644 --- a/pkg/sql/conn_executor.go +++ b/pkg/sql/conn_executor.go @@ -257,7 +257,7 @@ type Server struct { // sqlStats tracks per-application statistics for all applications on each // node. Newly collected statistics flow into sqlStats. - sqlStats sqlstats.Provider + sqlStats *persistedsqlstats.PersistedSQLStats // sqlStatsController is the control-plane interface for sqlStats. sqlStatsController *sslocal.Controller @@ -353,6 +353,7 @@ func NewServer(cfg *ExecutorConfig, pool *mon.BytesMonitor) *Server { InternalExecutor: &sqlStatsInternalExecutor, KvDB: cfg.DB, SQLIDContainer: cfg.NodeID, + JobRegistry: s.cfg.JobRegistry, Knobs: cfg.SQLStatsTestingKnobs, FlushCounter: metrics.StatsMetrics.SQLStatsFlushStarted, FailureCounter: metrics.StatsMetrics.SQLStatsFlushFailure, diff --git a/pkg/sql/sqlstats/persistedsqlstats/BUILD.bazel b/pkg/sql/sqlstats/persistedsqlstats/BUILD.bazel index a887dfcbc6b2..1af7475b739c 100644 --- a/pkg/sql/sqlstats/persistedsqlstats/BUILD.bazel +++ b/pkg/sql/sqlstats/persistedsqlstats/BUILD.bazel @@ -4,6 +4,8 @@ go_library( name = "persistedsqlstats", srcs = [ "cluster_settings.go", + "compaction_exec.go", + "compaction_scheduling.go", "flush.go", "provider.go", "test_utils.go", @@ -13,8 +15,11 @@ go_library( visibility = ["//visibility:public"], deps = [ "//pkg/base", + "//pkg/jobs", + "//pkg/jobs/jobspb", "//pkg/kv", "//pkg/roachpb:with-mocks", + "//pkg/scheduledjobs", "//pkg/security", "//pkg/settings", "//pkg/settings/cluster", @@ -26,6 +31,7 @@ go_library( "//pkg/sql/sqlstats/sslocal", "//pkg/sql/sqlstats/ssmemstorage", "//pkg/sql/sqlutil", + "//pkg/util/jobutil", "//pkg/util/log", "//pkg/util/metric", "//pkg/util/stop", @@ -37,21 +43,30 @@ go_library( go_test( name = "persistedsqlstats_test", srcs = [ + "compaction_test.go", "flush_test.go", "main_test.go", ], deps = [ ":persistedsqlstats", "//pkg/base", + "//pkg/jobs", + "//pkg/jobs/jobspb", + "//pkg/kv/kvserver", + "//pkg/kv/kvserver/kvserverbase", "//pkg/roachpb:with-mocks", "//pkg/security", "//pkg/security/securitytest", "//pkg/server", "//pkg/sql", + "//pkg/sql/catalog/descpb", "//pkg/sql/sqlstats", + "//pkg/sql/sqlutil", + "//pkg/testutils", "//pkg/testutils/serverutils", "//pkg/testutils/sqlutils", "//pkg/testutils/testcluster", + "//pkg/util/encoding", "//pkg/util/leaktest", "//pkg/util/log", "//pkg/util/stop", diff --git a/pkg/sql/sqlstats/persistedsqlstats/cluster_settings.go b/pkg/sql/sqlstats/persistedsqlstats/cluster_settings.go index 85199ee611cb..07e46d96839f 100644 --- a/pkg/sql/sqlstats/persistedsqlstats/cluster_settings.go +++ b/pkg/sql/sqlstats/persistedsqlstats/cluster_settings.go @@ -50,3 +50,12 @@ var SQLStatsFlushJitter = settings.RegisterFloatSetting( return nil }, ) + +// SQLStatsMaxPersistedRows specifies maximum number of rows that will be +// retained in system.statement_statistics and system.transaction_statistics. +var SQLStatsMaxPersistedRows = settings.RegisterIntSetting( + "sql.stats.persisted_rows.max", + "maximum number of rows of statement and transaction"+ + " statistics that will be persisted in the system tables", + 10000, /* defaultValue */ +).WithPublic() diff --git a/pkg/sql/sqlstats/persistedsqlstats/compaction_exec.go b/pkg/sql/sqlstats/persistedsqlstats/compaction_exec.go new file mode 100644 index 000000000000..23d0d95b24b6 --- /dev/null +++ b/pkg/sql/sqlstats/persistedsqlstats/compaction_exec.go @@ -0,0 +1,181 @@ +// Copyright 2021 The Cockroach Authors. +// +// Use of this software is governed by the Business Source License +// included in the file licenses/BSL.txt. +// +// As of the Change Date specified in that file, in accordance with +// the Business Source License, use of this software will be governed +// by the Apache License, Version 2.0, included in the file +// licenses/APL.txt. + +package persistedsqlstats + +import ( + "context" + "fmt" + + "github.com/cockroachdb/cockroach/pkg/kv" + "github.com/cockroachdb/cockroach/pkg/scheduledjobs" + "github.com/cockroachdb/cockroach/pkg/security" + "github.com/cockroachdb/cockroach/pkg/settings/cluster" + "github.com/cockroachdb/cockroach/pkg/sql/sem/tree" + "github.com/cockroachdb/cockroach/pkg/sql/sessiondata" + "github.com/cockroachdb/cockroach/pkg/sql/sqlutil" + "github.com/cockroachdb/errors" +) + +// StatsCompactor is responsible for compacting older SQL Stats. It is +// executed by sql.sqlStatsCompactionResumer. +type StatsCompactor struct { + Settings *cluster.Settings + + initialized bool + db *kv.DB + ie sqlutil.InternalExecutor + + TestingKnobs *StatsCompactorTestingKnobs +} + +// StatsCompactorTestingKnobs can be used to tune the behavior of +// StatsCompactor in unit tests. +type StatsCompactorTestingKnobs struct { + // DisableFollowerRead disables the use of follower read used in + // StatsCompactor. This is used because follower can cause problems in + // in unit tests where we immediately start running follower read SQL queries + // on system tables that are yet to be created. This is not a scenario that is + // possible in real life. + DisableFollowerRead bool + + // JobSchedulerEnv overrides the environment to use for scheduled jobs. + JobsSchedulerEnv scheduledjobs.JobSchedulerEnv +} + +// Init initializes the StatsCompactor. This method needs to be called before +// the DeleteOldestEntries method. +func (c *StatsCompactor) Init(internalEx sqlutil.InternalExecutor, db *kv.DB) { + c.db = db + c.ie = internalEx + c.initialized = true +} + +// DeleteOldestEntries removes the oldest statement and transaction statistics +// that exceeded the limit defined by `sql.stats.persisted_rows.max` +// (persistedsqlstats.SQLStatsMaxPersistedRows). +func (c *StatsCompactor) DeleteOldestEntries(ctx context.Context) error { + if !c.initialized { + return errors.AssertionFailedf("CompactExecutor has not being initialized") + } + + stmtStatsEntryCount, txnStatsEntryCount, err := c.getExistingStmtAndTxnStatsEntries(ctx) + if err != nil { + return err + } + + err = c.deleteOldestEntries(ctx, stmtStatsEntryCount, txnStatsEntryCount) + if err != nil { + return err + } + + return nil +} + +func (c *StatsCompactor) getExistingStmtAndTxnStatsEntries( + ctx context.Context, +) (stmtStatsEntryCount, txnStatsEntryCount int64, err error) { + stmt := "SELECT count(*) FROM system.statement_statistics AS OF SYSTEM TIME follower_read_timestamp()" + if c.TestingKnobs != nil && c.TestingKnobs.DisableFollowerRead { + stmt = "SELECT count(*) FROM system.statement_statistics" + } + row, err := c.ie.QueryRowEx(ctx, + "scan-sql-stmt-stats-entries", + nil, + sessiondata.InternalExecutorOverride{User: security.NodeUserName()}, + stmt) + if err != nil { + return 0 /* stmtStatsEntryCount */, 0 /* txnStatsEntryCount */, err + } + + if row.Len() != 1 { + return 0 /* stmtStatsEntryCount */, 0 /* txnStatsEntryCount */, errors.AssertionFailedf("unexpected number of column returned") + } + stmtStatsEntryCount = int64(tree.MustBeDInt(row[0])) + + stmt = "SELECT count(*) FROM system.transaction_statistics AS OF SYSTEM TIME follower_read_timestamp()" + if c.TestingKnobs != nil && c.TestingKnobs.DisableFollowerRead { + stmt = "SELECT count(*) FROM system.transaction_statistics" + } + row, err = c.ie.QueryRowEx(ctx, + "scan-sql-txn-stats-entries", + nil, + sessiondata.InternalExecutorOverride{User: security.NodeUserName()}, + stmt) + if err != nil { + return 0 /* stmtStatsEntryCount */, 0 /* txnStatsEntryCount */, err + } + + if row.Len() != 1 { + return 0 /* stmtStatsEntryCount */, 0 /* txnStatsEntryCount */, errors.AssertionFailedf("unexpected number of column returned") + } + txnStatsEntryCount = int64(tree.MustBeDInt(row[0])) + + return stmtStatsEntryCount, txnStatsEntryCount, nil +} + +func (c *StatsCompactor) deleteOldestEntries( + ctx context.Context, curStmtStatsEntries, curTxnStatsEntries int64, +) error { + maxStatsEntry := SQLStatsMaxPersistedRows.Get(&c.Settings.SV) + + // [1]: table name + // [2]: primary key + // [3]: number of entries to remove + stmt := ` +DELETE FROM %[1]s +WHERE (%[2]s) IN ( + SELECT %[2]s + FROM %[1]s + ORDER BY aggregated_ts ASC + LIMIT %[3]d +) +` + + err := c.db.Txn(ctx, func(ctx context.Context, txn *kv.Txn) error { + if entriesToRemove := curStmtStatsEntries - maxStatsEntry; entriesToRemove > 0 { + _, err := c.ie.ExecEx(ctx, + "delete-old-stmt-stats", + txn, + sessiondata.InternalExecutorOverride{User: security.NodeUserName()}, + fmt.Sprintf(stmt, + "system.statement_statistics", + "aggregated_ts, fingerprint_id, plan_hash, app_name, node_id", + entriesToRemove)) + + if err != nil { + return err + } + } + + if entriesToRemove := curTxnStatsEntries - maxStatsEntry; entriesToRemove > 0 { + _, err := c.ie.ExecEx(ctx, + "delete-old-txn-stats", + txn, + sessiondata.InternalExecutorOverride{User: security.NodeUserName()}, + fmt.Sprintf(stmt, + "system.transaction_statistics", + "aggregated_ts, fingerprint_id, app_name, node_id", + entriesToRemove)) + + if err != nil { + return err + } + } + + return nil + }) + + if err != nil { + return err + } + + return nil +} diff --git a/pkg/sql/sqlstats/persistedsqlstats/compaction_scheduling.go b/pkg/sql/sqlstats/persistedsqlstats/compaction_scheduling.go new file mode 100644 index 000000000000..10bfe75e017b --- /dev/null +++ b/pkg/sql/sqlstats/persistedsqlstats/compaction_scheduling.go @@ -0,0 +1,71 @@ +// Copyright 2021 The Cockroach Authors. +// +// Use of this software is governed by the Business Source License +// included in the file licenses/BSL.txt. +// +// As of the Change Date specified in that file, in accordance with +// the Business Source License, use of this software will be governed +// by the Apache License, Version 2.0, included in the file +// licenses/APL.txt. + +package persistedsqlstats + +import ( + "context" + + "github.com/cockroachdb/cockroach/pkg/jobs" + "github.com/cockroachdb/cockroach/pkg/jobs/jobspb" + "github.com/cockroachdb/cockroach/pkg/kv" + "github.com/cockroachdb/cockroach/pkg/security" + "github.com/cockroachdb/cockroach/pkg/sql/sqlutil" + "github.com/cockroachdb/cockroach/pkg/util/jobutil" +) + +// CreateCompactionJob creates a system.jobs record if there is no other +// SQL Stats compaction job running. This is invoked either through the +// crdb_internal.sql_stats_compact() builtin or the scheduled job Executor. +func CreateCompactionJob( + ctx context.Context, + createdByInfo *jobs.CreatedByInfo, + txn *kv.Txn, + ie sqlutil.InternalExecutor, + jobRegistry *jobs.Registry, +) (jobspb.JobID, error) { + if err := CheckExistingCompactionJob(ctx, nil /* job */, ie, txn); err != nil { + return jobspb.InvalidJobID, err + } + record := jobs.Record{ + Description: "SQL Stats compaction", + Username: security.NodeUserName(), + Details: jobspb.SQLStatsCompactionDetails{}, + Progress: jobspb.SQLStatsCompactionProgress{}, + CreatedBy: createdByInfo, + } + + jobID := jobRegistry.MakeJobID() + if _, err := jobRegistry.CreateAdoptableJobWithTxn(ctx, record, jobID, txn); err != nil { + return jobspb.InvalidJobID, err + } + return jobID, nil +} + +// CheckExistingCompactionJob checks for existing SQL Stats Compaction job +// that are either PAUSED, CANCELED, or RUNNING. If so, it returns a +// ErrConcurrentSQLStatsCompaction. +func CheckExistingCompactionJob( + ctx context.Context, job *jobs.Job, ie sqlutil.InternalExecutor, txn *kv.Txn, +) error { + exists, err := jobutil.RunningJobExists(ctx, job, ie, txn, func(payload *jobspb.Payload) bool { + return payload.Type() == jobspb.TypeSQLStatsCompaction + }) + + if err != nil { + return err + } + + if exists { + return ErrConcurrentSQLStatsCompaction + } + + return nil +} diff --git a/pkg/sql/sqlstats/persistedsqlstats/compaction_test.go b/pkg/sql/sqlstats/persistedsqlstats/compaction_test.go new file mode 100644 index 000000000000..814aa00c2e3a --- /dev/null +++ b/pkg/sql/sqlstats/persistedsqlstats/compaction_test.go @@ -0,0 +1,280 @@ +// Copyright 2021 The Cockroach Authors. +// +// Use of this software is governed by the Business Source License +// included in the file licenses/BSL.txt. +// +// As of the Change Date specified in that file, in accordance with +// the Business Source License, use of this software will be governed +// by the Apache License, Version 2.0, included in the file +// licenses/APL.txt. + +package persistedsqlstats_test + +import ( + "context" + gosql "database/sql" + "errors" + "fmt" + "net/url" + "testing" + + "github.com/cockroachdb/cockroach/pkg/base" + "github.com/cockroachdb/cockroach/pkg/jobs" + "github.com/cockroachdb/cockroach/pkg/jobs/jobspb" + "github.com/cockroachdb/cockroach/pkg/kv/kvserver" + "github.com/cockroachdb/cockroach/pkg/kv/kvserver/kvserverbase" + "github.com/cockroachdb/cockroach/pkg/roachpb" + "github.com/cockroachdb/cockroach/pkg/security" + "github.com/cockroachdb/cockroach/pkg/sql" + "github.com/cockroachdb/cockroach/pkg/sql/catalog/descpb" + "github.com/cockroachdb/cockroach/pkg/sql/sqlstats/persistedsqlstats" + "github.com/cockroachdb/cockroach/pkg/sql/sqlutil" + "github.com/cockroachdb/cockroach/pkg/testutils" + "github.com/cockroachdb/cockroach/pkg/testutils/serverutils" + "github.com/cockroachdb/cockroach/pkg/testutils/sqlutils" + "github.com/cockroachdb/cockroach/pkg/util/encoding" + "github.com/cockroachdb/cockroach/pkg/util/leaktest" + "github.com/cockroachdb/cockroach/pkg/util/log" + "github.com/stretchr/testify/require" +) + +func TestSQLStatsCompactor(t *testing.T) { + defer leaktest.AfterTest(t)() + defer log.Scope(t).Close(t) + + testCluster := serverutils.StartNewTestCluster(t, 3 /* numNodes */, base.TestClusterArgs{ + ServerArgs: base.TestServerArgs{}, + }) + + ctx := context.Background() + defer testCluster.Stopper().Stop(ctx) + + firstServer := testCluster.Server(0 /* idx */) + firstPgURL, firstServerConnCleanup := sqlutils.PGUrl( + t, firstServer.ServingSQLAddr(), "CreateConnections" /* prefix */, url.User(security.RootUser)) + defer firstServerConnCleanup() + + pgFirstSQLConn, err := gosql.Open("postgres", firstPgURL.String()) + require.NoError(t, err) + firstSQLConn := sqlutils.MakeSQLRunner(pgFirstSQLConn) + + defer func() { + err := pgFirstSQLConn.Close() + require.NoError(t, err) + }() + + maxPersistedRowLimit := 5 + firstServerSQLStats := firstServer.SQLServer().(*sql.Server).GetSQLStatsProvider().(*persistedsqlstats.PersistedSQLStats) + firstSQLConn.Exec(t, fmt.Sprintf("SET CLUSTER SETTING sql.stats.persisted_rows.max = %d", maxPersistedRowLimit)) + + stmt := "SELECT 1" + for i := 0; i < 10; i++ { + firstSQLConn.Exec(t, stmt) + // Mutate the stmt to create different fingerprint. + stmt = fmt.Sprintf("%s, 1", stmt) + } + + firstServerSQLStats.Flush(ctx) + + compactionExecutor := &persistedsqlstats.StatsCompactor{ + Settings: firstServer.ClusterSettings(), + TestingKnobs: &persistedsqlstats.StatsCompactorTestingKnobs{ + DisableFollowerRead: true, + }, + } + compactionExecutor.Init(firstServer.InternalExecutor().(sqlutil.InternalExecutor), firstServer.DB()) + + // Initial compaction should remove the all the oldest entries. + expectedDeletedStmtFingerprints, expectedDeletedTxnFingerprints := getTopSortedFingerprints(t, firstSQLConn, maxPersistedRowLimit) + + err = compactionExecutor.DeleteOldestEntries(ctx) + require.NoError(t, err) + + actualStmtFingerprints, actualTxnFingerprints := getTopSortedFingerprints(t, firstSQLConn, 0 /* limit */) + require.Equal(t, maxPersistedRowLimit, len(actualStmtFingerprints)) + require.Equal(t, maxPersistedRowLimit, len(actualTxnFingerprints)) + + for fingerprintID := range actualStmtFingerprints { + for _, deletedFingerprintID := range expectedDeletedStmtFingerprints { + require.NotEqual(t, deletedFingerprintID, fingerprintID) + } + } + + for fingerprintID := range actualTxnFingerprints { + for _, deletedFingerprintID := range expectedDeletedTxnFingerprints { + require.NotEqual(t, deletedFingerprintID, fingerprintID) + } + } + + // Calling it again should be a noop. + err = compactionExecutor.DeleteOldestEntries(ctx) + require.NoError(t, err) + stmtStatsCnt, txnStatsCnt := getPersistedStatsEntry(t, firstSQLConn) + require.Equal(t, maxPersistedRowLimit, stmtStatsCnt) + require.Equal(t, maxPersistedRowLimit, txnStatsCnt) +} + +func TestAtMostOneSQLStatsCompactionJob(t *testing.T) { + defer leaktest.AfterTest(t)() + defer log.Scope(t).Close(t) + + var serverArgs base.TestServerArgs + var allowRequest chan struct{} + + params := base.TestClusterArgs{ServerArgs: serverArgs} + params.ServerArgs.Knobs.JobsTestingKnobs = jobs.NewTestingKnobsWithShortIntervals() + + params.ServerArgs.Knobs.Store = &kvserver.StoreTestingKnobs{ + TestingRequestFilter: createStatsRequestFilter(t, &allowRequest), + } + + ctx := context.Background() + tc := serverutils.StartNewTestCluster(t, 3 /* numNodes */, params) + defer tc.Stopper().Stop(ctx) + conn := tc.ServerConn(0 /* idx */) + server := tc.Server(0 /* idx */) + + allowRequest = make(chan struct{}) + + jobID, err := launchSQLStatsCompactionJob(server) + require.NoError(t, err) + + // We wait until the job appears in the system.jobs table. + testutils.SucceedsSoon(t, func() error { + server.JobRegistry().(*jobs.Registry).TestingNudgeAdoptionQueue() + var cnt uint64 + row := conn.QueryRow(`SELECT count(*) FROM system.jobs where id = $1`, jobID) + require.NoError(t, row.Scan(&cnt)) + if cnt == 0 { + return errors.New("retry") + } + return nil + }) + + allowRequest <- struct{}{} + + // Launching a second job should fail here since we are still blocking the + // the first job's execution through allowRequest. (Since we need to send + // struct{}{} twice into the channel to fully unblock it.) + _, err = launchSQLStatsCompactionJob(server) + expected := persistedsqlstats.ErrConcurrentSQLStatsCompaction.Error() + if !testutils.IsError(err, expected) { + t.Fatalf("expected '%s' error, but got %+v", expected, err) + } + + allowRequest <- struct{}{} + close(allowRequest) + + // We wait until the first job finishes. + testutils.SucceedsSoon(t, func() error { + var cnt uint64 + row := conn.QueryRow(`SELECT id FROM system.jobs where id = $1 AND status = 'succeeded'`, jobID) + return row.Scan(&cnt) + }) + + // Launching the job now should succeed. + jobID, err = launchSQLStatsCompactionJob(server) + require.NoError(t, err) + + // Wait until the second job to finish for sanity check. + testutils.SucceedsSoon(t, func() error { + server.JobRegistry().(*jobs.Registry).TestingNudgeAdoptionQueue() + var cnt uint64 + row := conn.QueryRow(`SELECT id FROM system.jobs where id = $1 AND status = 'succeeded'`, jobID) + return row.Scan(&cnt) + }) +} + +func launchSQLStatsCompactionJob(server serverutils.TestServerInterface) (jobspb.JobID, error) { + return persistedsqlstats.CreateCompactionJob( + context.Background(), nil /* createdByInfo */, nil, /* txn */ + server.InternalExecutor().(sqlutil.InternalExecutor), + server.JobRegistry().(*jobs.Registry)) +} + +func getPersistedStatsEntry( + t *testing.T, sqlConn *sqlutils.SQLRunner, +) (stmtStatsCnt, txnStatsCnt int) { + stmt := "SELECT count(*) FROM %s" + + row := sqlConn.QueryRow(t, fmt.Sprintf(stmt, "system.statement_statistics")) + row.Scan(&stmtStatsCnt) + + row = sqlConn.QueryRow(t, fmt.Sprintf(stmt, "system.transaction_statistics")) + row.Scan(&txnStatsCnt) + + return stmtStatsCnt, txnStatsCnt +} + +func getTopSortedFingerprints( + t *testing.T, sqlDb *sqlutils.SQLRunner, limit int, +) (stmtFingerprints, txnFingerprints []uint64) { + query := ` +SELECT fingerprint_id +FROM %s +ORDER BY aggregated_ts` + + if limit > 0 { + query = fmt.Sprintf("%s LIMIT %d", query, limit) + } + + stmtFingerprints = make([]uint64, 0) + txnFingerprints = make([]uint64, 0) + + fingerprintIDBuffer := make([]byte, 0, 8) + rows := sqlDb.Query(t, fmt.Sprintf(query, "system.statement_statistics")) + for rows.Next() { + fingerprintIDBuffer = fingerprintIDBuffer[:0] + require.NoError(t, rows.Scan(&fingerprintIDBuffer)) + _, fingerprintID, err := encoding.DecodeUint64Ascending(fingerprintIDBuffer) + require.NoError(t, err) + stmtFingerprints = append(stmtFingerprints, fingerprintID) + } + require.NoError(t, rows.Close()) + + rows = sqlDb.Query(t, fmt.Sprintf(query, "system.transaction_statistics")) + for rows.Next() { + fingerprintIDBuffer = fingerprintIDBuffer[:0] + require.NoError(t, rows.Scan(&fingerprintIDBuffer)) + _, fingerprintID, err := encoding.DecodeUint64Ascending(fingerprintIDBuffer) + require.NoError(t, err) + txnFingerprints = append(txnFingerprints, fingerprintID) + } + require.NoError(t, rows.Close()) + + return stmtFingerprints, txnFingerprints +} + +func createStatsRequestFilter( + t *testing.T, allowToProgress *chan struct{}, +) kvserverbase.ReplicaRequestFilter { + // Start a test server here so we can get the descriptor ID for the system + // table. This allows us to not hardcode the descriptor ID. + s, sqlConn, _ := serverutils.StartServer(t, base.TestServerArgs{}) + defer func() { + s.Stopper().Stop(context.Background()) + err := sqlConn.Close() + require.NoError(t, err) + }() + sqlDB := sqlutils.MakeSQLRunner(sqlConn) + + stmtStatsTableID, txnStatsTableID := getStatsTablesIDs(t, sqlDB) + return func(_ context.Context, ba roachpb.BatchRequest) *roachpb.Error { + if req, ok := ba.GetArg(roachpb.Scan); ok { + _, tableID, _ := encoding.DecodeUvarintAscending(req.(*roachpb.ScanRequest).Key) + if descpb.ID(tableID) == stmtStatsTableID || descpb.ID(tableID) == txnStatsTableID { + <-*allowToProgress + <-*allowToProgress + } + } + return nil + } +} + +func getStatsTablesIDs( + t *testing.T, sqlDB *sqlutils.SQLRunner, +) (stmtStatsTableID, txnStatsTableID descpb.ID) { + stmt := "select 'system.statement_statistics'::regclass::oid, 'system.transaction_statistics'::regclass::oid" + sqlDB.QueryRow(t, stmt).Scan(&stmtStatsTableID, &txnStatsTableID) + return stmtStatsTableID, txnStatsTableID +} diff --git a/pkg/sql/sqlstats/persistedsqlstats/provider.go b/pkg/sql/sqlstats/persistedsqlstats/provider.go index 00b3ce5ff069..3810330fb8f4 100644 --- a/pkg/sql/sqlstats/persistedsqlstats/provider.go +++ b/pkg/sql/sqlstats/persistedsqlstats/provider.go @@ -19,6 +19,7 @@ import ( "time" "github.com/cockroachdb/cockroach/pkg/base" + "github.com/cockroachdb/cockroach/pkg/jobs" "github.com/cockroachdb/cockroach/pkg/kv" "github.com/cockroachdb/cockroach/pkg/settings/cluster" "github.com/cockroachdb/cockroach/pkg/sql/sqlstats" @@ -27,6 +28,7 @@ import ( "github.com/cockroachdb/cockroach/pkg/util/metric" "github.com/cockroachdb/cockroach/pkg/util/stop" "github.com/cockroachdb/cockroach/pkg/util/timeutil" + "github.com/cockroachdb/errors" ) // TODO(azhng): currently we do not have the ability to compute a hash for @@ -35,16 +37,25 @@ import ( // update this. const dummyPlanHash = int64(0) +// ErrConcurrentSQLStatsCompaction is reported when two sql stats compaction +// jobs are issued concurrently. This is a sentinel error. +var ErrConcurrentSQLStatsCompaction = errors.New("another sql stats compaction job is already running") + // Config is a configuration struct for the persisted SQL stats subsystem. type Config struct { Settings *cluster.Settings InternalExecutor sqlutil.InternalExecutor KvDB *kv.DB SQLIDContainer *base.SQLIDContainer - Knobs *TestingKnobs - FlushCounter *metric.Counter - FlushDuration *metric.Histogram - FailureCounter *metric.Counter + JobRegistry *jobs.Registry + + // Metrics. + FlushCounter *metric.Counter + FlushDuration *metric.Histogram + FailureCounter *metric.Counter + + // Testing knobs. + Knobs *TestingKnobs } // PersistedSQLStats is a sqlstats.Provider that wraps a node-local in-memory diff --git a/pkg/ts/catalog/chart_catalog.go b/pkg/ts/catalog/chart_catalog.go index be9ed1bb3f84..ecb5654439ab 100644 --- a/pkg/ts/catalog/chart_catalog.go +++ b/pkg/ts/catalog/chart_catalog.go @@ -2523,6 +2523,7 @@ var charts = []sectionDescription{ "jobs.typedesc_schema_change.currently_running", "jobs.stream_ingestion.currently_running", "jobs.migration.currently_running", + "jobs.sql_stats_compaction.currently_running", }, }, { @@ -2667,6 +2668,17 @@ var charts = []sectionDescription{ "jobs.migration.resume_retry_error", }, }, + { + Title: "SQL Stats Compaction", + Metrics: []string{ + "jobs.sql_stats_compaction.fail_or_cancel_completed", + "jobs.sql_stats_compaction.fail_or_cancel_failed", + "jobs.sql_stats_compaction.fail_or_cancel_retry_error", + "jobs.sql_stats_compaction.resume_completed", + "jobs.sql_stats_compaction.resume_failed", + "jobs.sql_stats_compaction.resume_retry_error", + }, + }, }, }, { diff --git a/pkg/util/jobutil/BUILD.bazel b/pkg/util/jobutil/BUILD.bazel index 34e2a69c3c98..dc2a697ad714 100644 --- a/pkg/util/jobutil/BUILD.bazel +++ b/pkg/util/jobutil/BUILD.bazel @@ -8,6 +8,7 @@ go_library( deps = [ "//pkg/jobs", "//pkg/jobs/jobspb", + "//pkg/kv", "//pkg/sql/sem/tree", "//pkg/sql/sqlutil", "@com_github_cockroachdb_errors//:errors",