Commit Diff


commit - /dev/null
commit + c0fbba878a5f41c852d4e4b03127be7590fbbf35
blob - /dev/null
blob + 63dd8bd3b4ca6a2fd88690b01ba818bfdba8c2be (mode 644)
--- /dev/null
+++ README.md
@@ -0,0 +1,23 @@
+# dishy
+
+Package dishy provides an interface to manage a Starlink Dishy device over the network.
+
+## gRPC Code Generation
+
+A starlink device supports gRPC [server reflection][reflection].
+This is used to eventually generate code to interact with its gRPC service.
+Regenerating the code requires:
+
+- [grpcurl][grpcurl]
+- [protoc][protoc]
+- connectivity to a Starlink Dishy's gRPC service listening on the default address (192.168.100.1:9200).
+
+To regenerate the code:
+
+	go generate
+
+This calls protoc.sh. For more information on protoc.sh, see the inline documentation in the script.
+
+[grpcurl]: https://pkg.go.dev/github.com/fullstorydev/grpcurl
+[protoc]: https://grpc.io/docs/protoc-installation/
+[reflection]: https://grpc.github.io/grpc/cpp/md_doc_server-reflection.html
blob - /dev/null
blob + 5788340e22b05d662638bb8a941dffbe8e5afb40 (mode 644)
--- /dev/null
+++ device/command.pb.go
@@ -0,0 +1,227 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// 	protoc-gen-go v1.28.1
+// 	protoc        v3.21.6
+// source: spacex/api/device/command.proto
+
+package device
+
+import (
+	protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+	protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+	reflect "reflect"
+	sync "sync"
+)
+
+const (
+	// Verify that this generated code is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+	// Verify that runtime/protoimpl is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+type Capability int32
+
+const (
+	Capability_READ    Capability = 0
+	Capability_WRITE   Capability = 1
+	Capability_DEBUG   Capability = 2
+	Capability_ADMIN   Capability = 3
+	Capability_SETUP   Capability = 4
+	Capability_SET_SKU Capability = 5
+	Capability_REFRESH Capability = 6
+)
+
+// Enum value maps for Capability.
+var (
+	Capability_name = map[int32]string{
+		0: "READ",
+		1: "WRITE",
+		2: "DEBUG",
+		3: "ADMIN",
+		4: "SETUP",
+		5: "SET_SKU",
+		6: "REFRESH",
+	}
+	Capability_value = map[string]int32{
+		"READ":    0,
+		"WRITE":   1,
+		"DEBUG":   2,
+		"ADMIN":   3,
+		"SETUP":   4,
+		"SET_SKU": 5,
+		"REFRESH": 6,
+	}
+)
+
+func (x Capability) Enum() *Capability {
+	p := new(Capability)
+	*p = x
+	return p
+}
+
+func (x Capability) String() string {
+	return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (Capability) Descriptor() protoreflect.EnumDescriptor {
+	return file_spacex_api_device_command_proto_enumTypes[0].Descriptor()
+}
+
+func (Capability) Type() protoreflect.EnumType {
+	return &file_spacex_api_device_command_proto_enumTypes[0]
+}
+
+func (x Capability) Number() protoreflect.EnumNumber {
+	return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use Capability.Descriptor instead.
+func (Capability) EnumDescriptor() ([]byte, []int) {
+	return file_spacex_api_device_command_proto_rawDescGZIP(), []int{0}
+}
+
+type PublicKey struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Key          string       `protobuf:"bytes,1,opt,name=key,proto3" json:"key,omitempty"`
+	Capabilities []Capability `protobuf:"varint,2,rep,packed,name=capabilities,proto3,enum=SpaceX.API.Device.Capability" json:"capabilities,omitempty"`
+}
+
+func (x *PublicKey) Reset() {
+	*x = PublicKey{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_command_proto_msgTypes[0]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *PublicKey) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*PublicKey) ProtoMessage() {}
+
+func (x *PublicKey) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_command_proto_msgTypes[0]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use PublicKey.ProtoReflect.Descriptor instead.
+func (*PublicKey) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_command_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *PublicKey) GetKey() string {
+	if x != nil {
+		return x.Key
+	}
+	return ""
+}
+
+func (x *PublicKey) GetCapabilities() []Capability {
+	if x != nil {
+		return x.Capabilities
+	}
+	return nil
+}
+
+var File_spacex_api_device_command_proto protoreflect.FileDescriptor
+
+var file_spacex_api_device_command_proto_rawDesc = []byte{
+	0x0a, 0x1f, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x61, 0x6e, 0x64, 0x2e, 0x70, 0x72, 0x6f, 0x74,
+	0x6f, 0x12, 0x11, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x22, 0x60, 0x0a, 0x09, 0x50, 0x75, 0x62, 0x6c, 0x69, 0x63, 0x4b, 0x65,
+	0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03,
+	0x6b, 0x65, 0x79, 0x12, 0x41, 0x0a, 0x0c, 0x63, 0x61, 0x70, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74,
+	0x69, 0x65, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0e, 0x32, 0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63,
+	0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x43, 0x61,
+	0x70, 0x61, 0x62, 0x69, 0x6c, 0x69, 0x74, 0x79, 0x52, 0x0c, 0x63, 0x61, 0x70, 0x61, 0x62, 0x69,
+	0x6c, 0x69, 0x74, 0x69, 0x65, 0x73, 0x2a, 0x5c, 0x0a, 0x0a, 0x43, 0x61, 0x70, 0x61, 0x62, 0x69,
+	0x6c, 0x69, 0x74, 0x79, 0x12, 0x08, 0x0a, 0x04, 0x52, 0x45, 0x41, 0x44, 0x10, 0x00, 0x12, 0x09,
+	0x0a, 0x05, 0x57, 0x52, 0x49, 0x54, 0x45, 0x10, 0x01, 0x12, 0x09, 0x0a, 0x05, 0x44, 0x45, 0x42,
+	0x55, 0x47, 0x10, 0x02, 0x12, 0x09, 0x0a, 0x05, 0x41, 0x44, 0x4d, 0x49, 0x4e, 0x10, 0x03, 0x12,
+	0x09, 0x0a, 0x05, 0x53, 0x45, 0x54, 0x55, 0x50, 0x10, 0x04, 0x12, 0x0b, 0x0a, 0x07, 0x53, 0x45,
+	0x54, 0x5f, 0x53, 0x4b, 0x55, 0x10, 0x05, 0x12, 0x0b, 0x0a, 0x07, 0x52, 0x45, 0x46, 0x52, 0x45,
+	0x53, 0x48, 0x10, 0x06, 0x42, 0x17, 0x5a, 0x15, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2e, 0x63,
+	0x6f, 0x6d, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x62, 0x06, 0x70,
+	0x72, 0x6f, 0x74, 0x6f, 0x33,
+}
+
+var (
+	file_spacex_api_device_command_proto_rawDescOnce sync.Once
+	file_spacex_api_device_command_proto_rawDescData = file_spacex_api_device_command_proto_rawDesc
+)
+
+func file_spacex_api_device_command_proto_rawDescGZIP() []byte {
+	file_spacex_api_device_command_proto_rawDescOnce.Do(func() {
+		file_spacex_api_device_command_proto_rawDescData = protoimpl.X.CompressGZIP(file_spacex_api_device_command_proto_rawDescData)
+	})
+	return file_spacex_api_device_command_proto_rawDescData
+}
+
+var file_spacex_api_device_command_proto_enumTypes = make([]protoimpl.EnumInfo, 1)
+var file_spacex_api_device_command_proto_msgTypes = make([]protoimpl.MessageInfo, 1)
+var file_spacex_api_device_command_proto_goTypes = []interface{}{
+	(Capability)(0),   // 0: SpaceX.API.Device.Capability
+	(*PublicKey)(nil), // 1: SpaceX.API.Device.PublicKey
+}
+var file_spacex_api_device_command_proto_depIdxs = []int32{
+	0, // 0: SpaceX.API.Device.PublicKey.capabilities:type_name -> SpaceX.API.Device.Capability
+	1, // [1:1] is the sub-list for method output_type
+	1, // [1:1] is the sub-list for method input_type
+	1, // [1:1] is the sub-list for extension type_name
+	1, // [1:1] is the sub-list for extension extendee
+	0, // [0:1] is the sub-list for field type_name
+}
+
+func init() { file_spacex_api_device_command_proto_init() }
+func file_spacex_api_device_command_proto_init() {
+	if File_spacex_api_device_command_proto != nil {
+		return
+	}
+	if !protoimpl.UnsafeEnabled {
+		file_spacex_api_device_command_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*PublicKey); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+	}
+	type x struct{}
+	out := protoimpl.TypeBuilder{
+		File: protoimpl.DescBuilder{
+			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+			RawDescriptor: file_spacex_api_device_command_proto_rawDesc,
+			NumEnums:      1,
+			NumMessages:   1,
+			NumExtensions: 0,
+			NumServices:   0,
+		},
+		GoTypes:           file_spacex_api_device_command_proto_goTypes,
+		DependencyIndexes: file_spacex_api_device_command_proto_depIdxs,
+		EnumInfos:         file_spacex_api_device_command_proto_enumTypes,
+		MessageInfos:      file_spacex_api_device_command_proto_msgTypes,
+	}.Build()
+	File_spacex_api_device_command_proto = out.File
+	file_spacex_api_device_command_proto_rawDesc = nil
+	file_spacex_api_device_command_proto_goTypes = nil
+	file_spacex_api_device_command_proto_depIdxs = nil
+}
blob - /dev/null
blob + d22feeb981c1a4e49c2b326964d964127318d198 (mode 644)
--- /dev/null
+++ device/common.pb.go
@@ -0,0 +1,1257 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// 	protoc-gen-go v1.28.1
+// 	protoc        v3.21.6
+// source: spacex/api/device/common.proto
+
+package device
+
+import (
+	protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+	protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+	reflect "reflect"
+	sync "sync"
+)
+
+const (
+	// Verify that this generated code is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+	// Verify that runtime/protoimpl is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+type EthernetNetworkInterface_Duplex int32
+
+const (
+	EthernetNetworkInterface_UNKNOWN EthernetNetworkInterface_Duplex = 0
+	EthernetNetworkInterface_HALF    EthernetNetworkInterface_Duplex = 1
+	EthernetNetworkInterface_FULL    EthernetNetworkInterface_Duplex = 2
+)
+
+// Enum value maps for EthernetNetworkInterface_Duplex.
+var (
+	EthernetNetworkInterface_Duplex_name = map[int32]string{
+		0: "UNKNOWN",
+		1: "HALF",
+		2: "FULL",
+	}
+	EthernetNetworkInterface_Duplex_value = map[string]int32{
+		"UNKNOWN": 0,
+		"HALF":    1,
+		"FULL":    2,
+	}
+)
+
+func (x EthernetNetworkInterface_Duplex) Enum() *EthernetNetworkInterface_Duplex {
+	p := new(EthernetNetworkInterface_Duplex)
+	*p = x
+	return p
+}
+
+func (x EthernetNetworkInterface_Duplex) String() string {
+	return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (EthernetNetworkInterface_Duplex) Descriptor() protoreflect.EnumDescriptor {
+	return file_spacex_api_device_common_proto_enumTypes[0].Descriptor()
+}
+
+func (EthernetNetworkInterface_Duplex) Type() protoreflect.EnumType {
+	return &file_spacex_api_device_common_proto_enumTypes[0]
+}
+
+func (x EthernetNetworkInterface_Duplex) Number() protoreflect.EnumNumber {
+	return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use EthernetNetworkInterface_Duplex.Descriptor instead.
+func (EthernetNetworkInterface_Duplex) EnumDescriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{11, 0}
+}
+
+type DeviceInfo struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Id              string `protobuf:"bytes,1,opt,name=id,proto3" json:"id,omitempty"`
+	HardwareVersion string `protobuf:"bytes,2,opt,name=hardware_version,json=hardwareVersion,proto3" json:"hardware_version,omitempty"`
+	SoftwareVersion string `protobuf:"bytes,3,opt,name=software_version,json=softwareVersion,proto3" json:"software_version,omitempty"`
+	CountryCode     string `protobuf:"bytes,4,opt,name=country_code,json=countryCode,proto3" json:"country_code,omitempty"`
+}
+
+func (x *DeviceInfo) Reset() {
+	*x = DeviceInfo{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[0]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DeviceInfo) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DeviceInfo) ProtoMessage() {}
+
+func (x *DeviceInfo) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[0]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DeviceInfo.ProtoReflect.Descriptor instead.
+func (*DeviceInfo) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *DeviceInfo) GetId() string {
+	if x != nil {
+		return x.Id
+	}
+	return ""
+}
+
+func (x *DeviceInfo) GetHardwareVersion() string {
+	if x != nil {
+		return x.HardwareVersion
+	}
+	return ""
+}
+
+func (x *DeviceInfo) GetSoftwareVersion() string {
+	if x != nil {
+		return x.SoftwareVersion
+	}
+	return ""
+}
+
+func (x *DeviceInfo) GetCountryCode() string {
+	if x != nil {
+		return x.CountryCode
+	}
+	return ""
+}
+
+type DeviceState struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	UptimeS uint64 `protobuf:"varint,1,opt,name=uptime_s,json=uptimeS,proto3" json:"uptime_s,omitempty"`
+}
+
+func (x *DeviceState) Reset() {
+	*x = DeviceState{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[1]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DeviceState) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DeviceState) ProtoMessage() {}
+
+func (x *DeviceState) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[1]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DeviceState.ProtoReflect.Descriptor instead.
+func (*DeviceState) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{1}
+}
+
+func (x *DeviceState) GetUptimeS() uint64 {
+	if x != nil {
+		return x.UptimeS
+	}
+	return 0
+}
+
+type SignedData struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Data      []byte `protobuf:"bytes,1,opt,name=data,proto3" json:"data,omitempty"`
+	Signature []byte `protobuf:"bytes,2,opt,name=signature,proto3" json:"signature,omitempty"`
+}
+
+func (x *SignedData) Reset() {
+	*x = SignedData{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[2]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *SignedData) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SignedData) ProtoMessage() {}
+
+func (x *SignedData) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[2]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use SignedData.ProtoReflect.Descriptor instead.
+func (*SignedData) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{2}
+}
+
+func (x *SignedData) GetData() []byte {
+	if x != nil {
+		return x.Data
+	}
+	return nil
+}
+
+func (x *SignedData) GetSignature() []byte {
+	if x != nil {
+		return x.Signature
+	}
+	return nil
+}
+
+type GetNextIdRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *GetNextIdRequest) Reset() {
+	*x = GetNextIdRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[3]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetNextIdRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetNextIdRequest) ProtoMessage() {}
+
+func (x *GetNextIdRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[3]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetNextIdRequest.ProtoReflect.Descriptor instead.
+func (*GetNextIdRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{3}
+}
+
+type GetNextIdResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Id      uint64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
+	EpochId uint64 `protobuf:"varint,2,opt,name=epoch_id,json=epochId,proto3" json:"epoch_id,omitempty"`
+}
+
+func (x *GetNextIdResponse) Reset() {
+	*x = GetNextIdResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[4]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetNextIdResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetNextIdResponse) ProtoMessage() {}
+
+func (x *GetNextIdResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[4]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetNextIdResponse.ProtoReflect.Descriptor instead.
+func (*GetNextIdResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{4}
+}
+
+func (x *GetNextIdResponse) GetId() uint64 {
+	if x != nil {
+		return x.Id
+	}
+	return 0
+}
+
+func (x *GetNextIdResponse) GetEpochId() uint64 {
+	if x != nil {
+		return x.EpochId
+	}
+	return 0
+}
+
+type PingTarget struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Service  string `protobuf:"bytes,1,opt,name=service,proto3" json:"service,omitempty"`
+	Location string `protobuf:"bytes,2,opt,name=location,proto3" json:"location,omitempty"`
+	Address  string `protobuf:"bytes,3,opt,name=address,proto3" json:"address,omitempty"`
+}
+
+func (x *PingTarget) Reset() {
+	*x = PingTarget{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[5]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *PingTarget) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*PingTarget) ProtoMessage() {}
+
+func (x *PingTarget) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[5]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use PingTarget.ProtoReflect.Descriptor instead.
+func (*PingTarget) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{5}
+}
+
+func (x *PingTarget) GetService() string {
+	if x != nil {
+		return x.Service
+	}
+	return ""
+}
+
+func (x *PingTarget) GetLocation() string {
+	if x != nil {
+		return x.Location
+	}
+	return ""
+}
+
+func (x *PingTarget) GetAddress() string {
+	if x != nil {
+		return x.Address
+	}
+	return ""
+}
+
+type PingResult struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Target    *PingTarget `protobuf:"bytes,3,opt,name=target,proto3" json:"target,omitempty"`
+	DropRate  float32     `protobuf:"fixed32,1,opt,name=dropRate,proto3" json:"dropRate,omitempty"`
+	LatencyMs float32     `protobuf:"fixed32,2,opt,name=latencyMs,proto3" json:"latencyMs,omitempty"`
+}
+
+func (x *PingResult) Reset() {
+	*x = PingResult{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[6]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *PingResult) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*PingResult) ProtoMessage() {}
+
+func (x *PingResult) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[6]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use PingResult.ProtoReflect.Descriptor instead.
+func (*PingResult) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{6}
+}
+
+func (x *PingResult) GetTarget() *PingTarget {
+	if x != nil {
+		return x.Target
+	}
+	return nil
+}
+
+func (x *PingResult) GetDropRate() float32 {
+	if x != nil {
+		return x.DropRate
+	}
+	return 0
+}
+
+func (x *PingResult) GetLatencyMs() float32 {
+	if x != nil {
+		return x.LatencyMs
+	}
+	return 0
+}
+
+type BondingChallenge struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	DishId string `protobuf:"bytes,1,opt,name=dish_id,json=dishId,proto3" json:"dish_id,omitempty"`
+	WifiId string `protobuf:"bytes,2,opt,name=wifi_id,json=wifiId,proto3" json:"wifi_id,omitempty"`
+	Nonce  []byte `protobuf:"bytes,3,opt,name=nonce,proto3" json:"nonce,omitempty"`
+}
+
+func (x *BondingChallenge) Reset() {
+	*x = BondingChallenge{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[7]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *BondingChallenge) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*BondingChallenge) ProtoMessage() {}
+
+func (x *BondingChallenge) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[7]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use BondingChallenge.ProtoReflect.Descriptor instead.
+func (*BondingChallenge) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{7}
+}
+
+func (x *BondingChallenge) GetDishId() string {
+	if x != nil {
+		return x.DishId
+	}
+	return ""
+}
+
+func (x *BondingChallenge) GetWifiId() string {
+	if x != nil {
+		return x.WifiId
+	}
+	return ""
+}
+
+func (x *BondingChallenge) GetNonce() []byte {
+	if x != nil {
+		return x.Nonce
+	}
+	return nil
+}
+
+type AuthenticateRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Challenge *SignedData `protobuf:"bytes,1,opt,name=challenge,proto3" json:"challenge,omitempty"`
+}
+
+func (x *AuthenticateRequest) Reset() {
+	*x = AuthenticateRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[8]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *AuthenticateRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*AuthenticateRequest) ProtoMessage() {}
+
+func (x *AuthenticateRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[8]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use AuthenticateRequest.ProtoReflect.Descriptor instead.
+func (*AuthenticateRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{8}
+}
+
+func (x *AuthenticateRequest) GetChallenge() *SignedData {
+	if x != nil {
+		return x.Challenge
+	}
+	return nil
+}
+
+type ChallengeResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Signature        []byte `protobuf:"bytes,1,opt,name=signature,proto3" json:"signature,omitempty"`
+	CertificateChain []byte `protobuf:"bytes,2,opt,name=certificate_chain,json=certificateChain,proto3" json:"certificate_chain,omitempty"`
+}
+
+func (x *ChallengeResponse) Reset() {
+	*x = ChallengeResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[9]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *ChallengeResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*ChallengeResponse) ProtoMessage() {}
+
+func (x *ChallengeResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[9]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use ChallengeResponse.ProtoReflect.Descriptor instead.
+func (*ChallengeResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{9}
+}
+
+func (x *ChallengeResponse) GetSignature() []byte {
+	if x != nil {
+		return x.Signature
+	}
+	return nil
+}
+
+func (x *ChallengeResponse) GetCertificateChain() []byte {
+	if x != nil {
+		return x.CertificateChain
+	}
+	return nil
+}
+
+type NetworkInterface struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Name    string                    `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
+	RxStats *NetworkInterface_RxStats `protobuf:"bytes,2,opt,name=rx_stats,json=rxStats,proto3" json:"rx_stats,omitempty"`
+	TxStats *NetworkInterface_TxStats `protobuf:"bytes,3,opt,name=tx_stats,json=txStats,proto3" json:"tx_stats,omitempty"`
+	// Types that are assignable to Interface:
+	//
+	//	*NetworkInterface_Ethernet
+	Interface isNetworkInterface_Interface `protobuf_oneof:"interface"`
+}
+
+func (x *NetworkInterface) Reset() {
+	*x = NetworkInterface{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[10]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *NetworkInterface) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*NetworkInterface) ProtoMessage() {}
+
+func (x *NetworkInterface) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[10]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use NetworkInterface.ProtoReflect.Descriptor instead.
+func (*NetworkInterface) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{10}
+}
+
+func (x *NetworkInterface) GetName() string {
+	if x != nil {
+		return x.Name
+	}
+	return ""
+}
+
+func (x *NetworkInterface) GetRxStats() *NetworkInterface_RxStats {
+	if x != nil {
+		return x.RxStats
+	}
+	return nil
+}
+
+func (x *NetworkInterface) GetTxStats() *NetworkInterface_TxStats {
+	if x != nil {
+		return x.TxStats
+	}
+	return nil
+}
+
+func (m *NetworkInterface) GetInterface() isNetworkInterface_Interface {
+	if m != nil {
+		return m.Interface
+	}
+	return nil
+}
+
+func (x *NetworkInterface) GetEthernet() *EthernetNetworkInterface {
+	if x, ok := x.GetInterface().(*NetworkInterface_Ethernet); ok {
+		return x.Ethernet
+	}
+	return nil
+}
+
+type isNetworkInterface_Interface interface {
+	isNetworkInterface_Interface()
+}
+
+type NetworkInterface_Ethernet struct {
+	Ethernet *EthernetNetworkInterface `protobuf:"bytes,1000,opt,name=ethernet,proto3,oneof"`
+}
+
+func (*NetworkInterface_Ethernet) isNetworkInterface_Interface() {}
+
+type EthernetNetworkInterface struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	LinkDetected      bool                            `protobuf:"varint,1,opt,name=link_detected,json=linkDetected,proto3" json:"link_detected,omitempty"`
+	SpeedMbps         uint32                          `protobuf:"varint,2,opt,name=speed_mbps,json=speedMbps,proto3" json:"speed_mbps,omitempty"`
+	AutonegotiationOn bool                            `protobuf:"varint,3,opt,name=autonegotiation_on,json=autonegotiationOn,proto3" json:"autonegotiation_on,omitempty"`
+	Duplex            EthernetNetworkInterface_Duplex `protobuf:"varint,4,opt,name=duplex,proto3,enum=SpaceX.API.Device.EthernetNetworkInterface_Duplex" json:"duplex,omitempty"`
+}
+
+func (x *EthernetNetworkInterface) Reset() {
+	*x = EthernetNetworkInterface{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[11]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *EthernetNetworkInterface) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*EthernetNetworkInterface) ProtoMessage() {}
+
+func (x *EthernetNetworkInterface) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[11]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use EthernetNetworkInterface.ProtoReflect.Descriptor instead.
+func (*EthernetNetworkInterface) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{11}
+}
+
+func (x *EthernetNetworkInterface) GetLinkDetected() bool {
+	if x != nil {
+		return x.LinkDetected
+	}
+	return false
+}
+
+func (x *EthernetNetworkInterface) GetSpeedMbps() uint32 {
+	if x != nil {
+		return x.SpeedMbps
+	}
+	return 0
+}
+
+func (x *EthernetNetworkInterface) GetAutonegotiationOn() bool {
+	if x != nil {
+		return x.AutonegotiationOn
+	}
+	return false
+}
+
+func (x *EthernetNetworkInterface) GetDuplex() EthernetNetworkInterface_Duplex {
+	if x != nil {
+		return x.Duplex
+	}
+	return EthernetNetworkInterface_UNKNOWN
+}
+
+type NetworkInterface_RxStats struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Bytes       uint64 `protobuf:"varint,1,opt,name=bytes,proto3" json:"bytes,omitempty"`
+	Packets     uint64 `protobuf:"varint,2,opt,name=packets,proto3" json:"packets,omitempty"`
+	FrameErrors uint64 `protobuf:"varint,3,opt,name=frame_errors,json=frameErrors,proto3" json:"frame_errors,omitempty"`
+}
+
+func (x *NetworkInterface_RxStats) Reset() {
+	*x = NetworkInterface_RxStats{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[12]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *NetworkInterface_RxStats) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*NetworkInterface_RxStats) ProtoMessage() {}
+
+func (x *NetworkInterface_RxStats) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[12]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use NetworkInterface_RxStats.ProtoReflect.Descriptor instead.
+func (*NetworkInterface_RxStats) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{10, 0}
+}
+
+func (x *NetworkInterface_RxStats) GetBytes() uint64 {
+	if x != nil {
+		return x.Bytes
+	}
+	return 0
+}
+
+func (x *NetworkInterface_RxStats) GetPackets() uint64 {
+	if x != nil {
+		return x.Packets
+	}
+	return 0
+}
+
+func (x *NetworkInterface_RxStats) GetFrameErrors() uint64 {
+	if x != nil {
+		return x.FrameErrors
+	}
+	return 0
+}
+
+type NetworkInterface_TxStats struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Bytes   uint64 `protobuf:"varint,1,opt,name=bytes,proto3" json:"bytes,omitempty"`
+	Packets uint64 `protobuf:"varint,2,opt,name=packets,proto3" json:"packets,omitempty"`
+}
+
+func (x *NetworkInterface_TxStats) Reset() {
+	*x = NetworkInterface_TxStats{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_common_proto_msgTypes[13]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *NetworkInterface_TxStats) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*NetworkInterface_TxStats) ProtoMessage() {}
+
+func (x *NetworkInterface_TxStats) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_common_proto_msgTypes[13]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use NetworkInterface_TxStats.ProtoReflect.Descriptor instead.
+func (*NetworkInterface_TxStats) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_common_proto_rawDescGZIP(), []int{10, 1}
+}
+
+func (x *NetworkInterface_TxStats) GetBytes() uint64 {
+	if x != nil {
+		return x.Bytes
+	}
+	return 0
+}
+
+func (x *NetworkInterface_TxStats) GetPackets() uint64 {
+	if x != nil {
+		return x.Packets
+	}
+	return 0
+}
+
+var File_spacex_api_device_common_proto protoreflect.FileDescriptor
+
+var file_spacex_api_device_common_proto_rawDesc = []byte{
+	0x0a, 0x1e, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x6f, 0x6e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
+	0x12, 0x11, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x22, 0x95, 0x01, 0x0a, 0x0a, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e,
+	0x66, 0x6f, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x02,
+	0x69, 0x64, 0x12, 0x29, 0x0a, 0x10, 0x68, 0x61, 0x72, 0x64, 0x77, 0x61, 0x72, 0x65, 0x5f, 0x76,
+	0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0f, 0x68, 0x61,
+	0x72, 0x64, 0x77, 0x61, 0x72, 0x65, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x29, 0x0a,
+	0x10, 0x73, 0x6f, 0x66, 0x74, 0x77, 0x61, 0x72, 0x65, 0x5f, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f,
+	0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0f, 0x73, 0x6f, 0x66, 0x74, 0x77, 0x61, 0x72,
+	0x65, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x21, 0x0a, 0x0c, 0x63, 0x6f, 0x75, 0x6e,
+	0x74, 0x72, 0x79, 0x5f, 0x63, 0x6f, 0x64, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b,
+	0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x43, 0x6f, 0x64, 0x65, 0x22, 0x28, 0x0a, 0x0b, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x19, 0x0a, 0x08, 0x75, 0x70,
+	0x74, 0x69, 0x6d, 0x65, 0x5f, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x07, 0x75, 0x70,
+	0x74, 0x69, 0x6d, 0x65, 0x53, 0x22, 0x3e, 0x0a, 0x0a, 0x53, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x44,
+	0x61, 0x74, 0x61, 0x12, 0x12, 0x0a, 0x04, 0x64, 0x61, 0x74, 0x61, 0x18, 0x01, 0x20, 0x01, 0x28,
+	0x0c, 0x52, 0x04, 0x64, 0x61, 0x74, 0x61, 0x12, 0x1c, 0x0a, 0x09, 0x73, 0x69, 0x67, 0x6e, 0x61,
+	0x74, 0x75, 0x72, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09, 0x73, 0x69, 0x67, 0x6e,
+	0x61, 0x74, 0x75, 0x72, 0x65, 0x22, 0x12, 0x0a, 0x10, 0x47, 0x65, 0x74, 0x4e, 0x65, 0x78, 0x74,
+	0x49, 0x64, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x3e, 0x0a, 0x11, 0x47, 0x65, 0x74,
+	0x4e, 0x65, 0x78, 0x74, 0x49, 0x64, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x0e,
+	0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x02, 0x69, 0x64, 0x12, 0x19,
+	0x0a, 0x08, 0x65, 0x70, 0x6f, 0x63, 0x68, 0x5f, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04,
+	0x52, 0x07, 0x65, 0x70, 0x6f, 0x63, 0x68, 0x49, 0x64, 0x22, 0x5c, 0x0a, 0x0a, 0x50, 0x69, 0x6e,
+	0x67, 0x54, 0x61, 0x72, 0x67, 0x65, 0x74, 0x12, 0x18, 0x0a, 0x07, 0x73, 0x65, 0x72, 0x76, 0x69,
+	0x63, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x73, 0x65, 0x72, 0x76, 0x69, 0x63,
+	0x65, 0x12, 0x1a, 0x0a, 0x08, 0x6c, 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20,
+	0x01, 0x28, 0x09, 0x52, 0x08, 0x6c, 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x18, 0x0a,
+	0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07,
+	0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x22, 0x7d, 0x0a, 0x0a, 0x50, 0x69, 0x6e, 0x67, 0x52,
+	0x65, 0x73, 0x75, 0x6c, 0x74, 0x12, 0x35, 0x0a, 0x06, 0x74, 0x61, 0x72, 0x67, 0x65, 0x74, 0x18,
+	0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41,
+	0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x50, 0x69, 0x6e, 0x67, 0x54, 0x61,
+	0x72, 0x67, 0x65, 0x74, 0x52, 0x06, 0x74, 0x61, 0x72, 0x67, 0x65, 0x74, 0x12, 0x1a, 0x0a, 0x08,
+	0x64, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x02, 0x52, 0x08,
+	0x64, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74, 0x65, 0x12, 0x1c, 0x0a, 0x09, 0x6c, 0x61, 0x74, 0x65,
+	0x6e, 0x63, 0x79, 0x4d, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x02, 0x52, 0x09, 0x6c, 0x61, 0x74,
+	0x65, 0x6e, 0x63, 0x79, 0x4d, 0x73, 0x22, 0x5a, 0x0a, 0x10, 0x42, 0x6f, 0x6e, 0x64, 0x69, 0x6e,
+	0x67, 0x43, 0x68, 0x61, 0x6c, 0x6c, 0x65, 0x6e, 0x67, 0x65, 0x12, 0x17, 0x0a, 0x07, 0x64, 0x69,
+	0x73, 0x68, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x64, 0x69, 0x73,
+	0x68, 0x49, 0x64, 0x12, 0x17, 0x0a, 0x07, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x69, 0x64, 0x18, 0x02,
+	0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x77, 0x69, 0x66, 0x69, 0x49, 0x64, 0x12, 0x14, 0x0a, 0x05,
+	0x6e, 0x6f, 0x6e, 0x63, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x05, 0x6e, 0x6f, 0x6e,
+	0x63, 0x65, 0x22, 0x52, 0x0a, 0x13, 0x41, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61,
+	0x74, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x3b, 0x0a, 0x09, 0x63, 0x68, 0x61,
+	0x6c, 0x6c, 0x65, 0x6e, 0x67, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53,
+	0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x2e, 0x53, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x44, 0x61, 0x74, 0x61, 0x52, 0x09, 0x63, 0x68, 0x61,
+	0x6c, 0x6c, 0x65, 0x6e, 0x67, 0x65, 0x22, 0x5e, 0x0a, 0x11, 0x43, 0x68, 0x61, 0x6c, 0x6c, 0x65,
+	0x6e, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x1c, 0x0a, 0x09, 0x73,
+	0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09,
+	0x73, 0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x12, 0x2b, 0x0a, 0x11, 0x63, 0x65, 0x72,
+	0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x5f, 0x63, 0x68, 0x61, 0x69, 0x6e, 0x18, 0x02,
+	0x20, 0x01, 0x28, 0x0c, 0x52, 0x10, 0x63, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+	0x65, 0x43, 0x68, 0x61, 0x69, 0x6e, 0x22, 0xa8, 0x03, 0x0a, 0x10, 0x4e, 0x65, 0x74, 0x77, 0x6f,
+	0x72, 0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x6e,
+	0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12,
+	0x46, 0x0a, 0x08, 0x72, 0x78, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28,
+	0x0b, 0x32, 0x2b, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x4e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x49, 0x6e, 0x74,
+	0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x2e, 0x52, 0x78, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x07,
+	0x72, 0x78, 0x53, 0x74, 0x61, 0x74, 0x73, 0x12, 0x46, 0x0a, 0x08, 0x74, 0x78, 0x5f, 0x73, 0x74,
+	0x61, 0x74, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x53, 0x70, 0x61, 0x63,
+	0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x4e, 0x65,
+	0x74, 0x77, 0x6f, 0x72, 0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x2e, 0x54,
+	0x78, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x07, 0x74, 0x78, 0x53, 0x74, 0x61, 0x74, 0x73, 0x12,
+	0x4a, 0x0a, 0x08, 0x65, 0x74, 0x68, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x18, 0xe8, 0x07, 0x20, 0x01,
+	0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e,
+	0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x45, 0x74, 0x68, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x4e,
+	0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x48,
+	0x00, 0x52, 0x08, 0x65, 0x74, 0x68, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x1a, 0x5c, 0x0a, 0x07, 0x52,
+	0x78, 0x53, 0x74, 0x61, 0x74, 0x73, 0x12, 0x14, 0x0a, 0x05, 0x62, 0x79, 0x74, 0x65, 0x73, 0x18,
+	0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x05, 0x62, 0x79, 0x74, 0x65, 0x73, 0x12, 0x18, 0x0a, 0x07,
+	0x70, 0x61, 0x63, 0x6b, 0x65, 0x74, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04, 0x52, 0x07, 0x70,
+	0x61, 0x63, 0x6b, 0x65, 0x74, 0x73, 0x12, 0x21, 0x0a, 0x0c, 0x66, 0x72, 0x61, 0x6d, 0x65, 0x5f,
+	0x65, 0x72, 0x72, 0x6f, 0x72, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x04, 0x52, 0x0b, 0x66, 0x72,
+	0x61, 0x6d, 0x65, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x73, 0x1a, 0x39, 0x0a, 0x07, 0x54, 0x78, 0x53,
+	0x74, 0x61, 0x74, 0x73, 0x12, 0x14, 0x0a, 0x05, 0x62, 0x79, 0x74, 0x65, 0x73, 0x18, 0x01, 0x20,
+	0x01, 0x28, 0x04, 0x52, 0x05, 0x62, 0x79, 0x74, 0x65, 0x73, 0x12, 0x18, 0x0a, 0x07, 0x70, 0x61,
+	0x63, 0x6b, 0x65, 0x74, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04, 0x52, 0x07, 0x70, 0x61, 0x63,
+	0x6b, 0x65, 0x74, 0x73, 0x42, 0x0b, 0x0a, 0x09, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63,
+	0x65, 0x22, 0x84, 0x02, 0x0a, 0x18, 0x45, 0x74, 0x68, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x4e, 0x65,
+	0x74, 0x77, 0x6f, 0x72, 0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x12, 0x23,
+	0x0a, 0x0d, 0x6c, 0x69, 0x6e, 0x6b, 0x5f, 0x64, 0x65, 0x74, 0x65, 0x63, 0x74, 0x65, 0x64, 0x18,
+	0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0c, 0x6c, 0x69, 0x6e, 0x6b, 0x44, 0x65, 0x74, 0x65, 0x63,
+	0x74, 0x65, 0x64, 0x12, 0x1d, 0x0a, 0x0a, 0x73, 0x70, 0x65, 0x65, 0x64, 0x5f, 0x6d, 0x62, 0x70,
+	0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x09, 0x73, 0x70, 0x65, 0x65, 0x64, 0x4d, 0x62,
+	0x70, 0x73, 0x12, 0x2d, 0x0a, 0x12, 0x61, 0x75, 0x74, 0x6f, 0x6e, 0x65, 0x67, 0x6f, 0x74, 0x69,
+	0x61, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x11,
+	0x61, 0x75, 0x74, 0x6f, 0x6e, 0x65, 0x67, 0x6f, 0x74, 0x69, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x4f,
+	0x6e, 0x12, 0x4a, 0x0a, 0x06, 0x64, 0x75, 0x70, 0x6c, 0x65, 0x78, 0x18, 0x04, 0x20, 0x01, 0x28,
+	0x0e, 0x32, 0x32, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x45, 0x74, 0x68, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x4e, 0x65,
+	0x74, 0x77, 0x6f, 0x72, 0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x2e, 0x44,
+	0x75, 0x70, 0x6c, 0x65, 0x78, 0x52, 0x06, 0x64, 0x75, 0x70, 0x6c, 0x65, 0x78, 0x22, 0x29, 0x0a,
+	0x06, 0x44, 0x75, 0x70, 0x6c, 0x65, 0x78, 0x12, 0x0b, 0x0a, 0x07, 0x55, 0x4e, 0x4b, 0x4e, 0x4f,
+	0x57, 0x4e, 0x10, 0x00, 0x12, 0x08, 0x0a, 0x04, 0x48, 0x41, 0x4c, 0x46, 0x10, 0x01, 0x12, 0x08,
+	0x0a, 0x04, 0x46, 0x55, 0x4c, 0x4c, 0x10, 0x02, 0x42, 0x17, 0x5a, 0x15, 0x73, 0x70, 0x61, 0x63,
+	0x65, 0x78, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
+}
+
+var (
+	file_spacex_api_device_common_proto_rawDescOnce sync.Once
+	file_spacex_api_device_common_proto_rawDescData = file_spacex_api_device_common_proto_rawDesc
+)
+
+func file_spacex_api_device_common_proto_rawDescGZIP() []byte {
+	file_spacex_api_device_common_proto_rawDescOnce.Do(func() {
+		file_spacex_api_device_common_proto_rawDescData = protoimpl.X.CompressGZIP(file_spacex_api_device_common_proto_rawDescData)
+	})
+	return file_spacex_api_device_common_proto_rawDescData
+}
+
+var file_spacex_api_device_common_proto_enumTypes = make([]protoimpl.EnumInfo, 1)
+var file_spacex_api_device_common_proto_msgTypes = make([]protoimpl.MessageInfo, 14)
+var file_spacex_api_device_common_proto_goTypes = []interface{}{
+	(EthernetNetworkInterface_Duplex)(0), // 0: SpaceX.API.Device.EthernetNetworkInterface.Duplex
+	(*DeviceInfo)(nil),                   // 1: SpaceX.API.Device.DeviceInfo
+	(*DeviceState)(nil),                  // 2: SpaceX.API.Device.DeviceState
+	(*SignedData)(nil),                   // 3: SpaceX.API.Device.SignedData
+	(*GetNextIdRequest)(nil),             // 4: SpaceX.API.Device.GetNextIdRequest
+	(*GetNextIdResponse)(nil),            // 5: SpaceX.API.Device.GetNextIdResponse
+	(*PingTarget)(nil),                   // 6: SpaceX.API.Device.PingTarget
+	(*PingResult)(nil),                   // 7: SpaceX.API.Device.PingResult
+	(*BondingChallenge)(nil),             // 8: SpaceX.API.Device.BondingChallenge
+	(*AuthenticateRequest)(nil),          // 9: SpaceX.API.Device.AuthenticateRequest
+	(*ChallengeResponse)(nil),            // 10: SpaceX.API.Device.ChallengeResponse
+	(*NetworkInterface)(nil),             // 11: SpaceX.API.Device.NetworkInterface
+	(*EthernetNetworkInterface)(nil),     // 12: SpaceX.API.Device.EthernetNetworkInterface
+	(*NetworkInterface_RxStats)(nil),     // 13: SpaceX.API.Device.NetworkInterface.RxStats
+	(*NetworkInterface_TxStats)(nil),     // 14: SpaceX.API.Device.NetworkInterface.TxStats
+}
+var file_spacex_api_device_common_proto_depIdxs = []int32{
+	6,  // 0: SpaceX.API.Device.PingResult.target:type_name -> SpaceX.API.Device.PingTarget
+	3,  // 1: SpaceX.API.Device.AuthenticateRequest.challenge:type_name -> SpaceX.API.Device.SignedData
+	13, // 2: SpaceX.API.Device.NetworkInterface.rx_stats:type_name -> SpaceX.API.Device.NetworkInterface.RxStats
+	14, // 3: SpaceX.API.Device.NetworkInterface.tx_stats:type_name -> SpaceX.API.Device.NetworkInterface.TxStats
+	12, // 4: SpaceX.API.Device.NetworkInterface.ethernet:type_name -> SpaceX.API.Device.EthernetNetworkInterface
+	0,  // 5: SpaceX.API.Device.EthernetNetworkInterface.duplex:type_name -> SpaceX.API.Device.EthernetNetworkInterface.Duplex
+	6,  // [6:6] is the sub-list for method output_type
+	6,  // [6:6] is the sub-list for method input_type
+	6,  // [6:6] is the sub-list for extension type_name
+	6,  // [6:6] is the sub-list for extension extendee
+	0,  // [0:6] is the sub-list for field type_name
+}
+
+func init() { file_spacex_api_device_common_proto_init() }
+func file_spacex_api_device_common_proto_init() {
+	if File_spacex_api_device_common_proto != nil {
+		return
+	}
+	if !protoimpl.UnsafeEnabled {
+		file_spacex_api_device_common_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DeviceInfo); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DeviceState); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*SignedData); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetNextIdRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetNextIdResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*PingTarget); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*PingResult); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*BondingChallenge); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[8].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*AuthenticateRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[9].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*ChallengeResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[10].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*NetworkInterface); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[11].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*EthernetNetworkInterface); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[12].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*NetworkInterface_RxStats); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_common_proto_msgTypes[13].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*NetworkInterface_TxStats); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+	}
+	file_spacex_api_device_common_proto_msgTypes[10].OneofWrappers = []interface{}{
+		(*NetworkInterface_Ethernet)(nil),
+	}
+	type x struct{}
+	out := protoimpl.TypeBuilder{
+		File: protoimpl.DescBuilder{
+			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+			RawDescriptor: file_spacex_api_device_common_proto_rawDesc,
+			NumEnums:      1,
+			NumMessages:   14,
+			NumExtensions: 0,
+			NumServices:   0,
+		},
+		GoTypes:           file_spacex_api_device_common_proto_goTypes,
+		DependencyIndexes: file_spacex_api_device_common_proto_depIdxs,
+		EnumInfos:         file_spacex_api_device_common_proto_enumTypes,
+		MessageInfos:      file_spacex_api_device_common_proto_msgTypes,
+	}.Build()
+	File_spacex_api_device_common_proto = out.File
+	file_spacex_api_device_common_proto_rawDesc = nil
+	file_spacex_api_device_common_proto_goTypes = nil
+	file_spacex_api_device_common_proto_depIdxs = nil
+}
blob - /dev/null
blob + 44c322e88b68755c9bc1ddbbb58d8e29a3ec4d6f (mode 644)
--- /dev/null
+++ device/device.pb.go
@@ -0,0 +1,3083 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// 	protoc-gen-go v1.28.1
+// 	protoc        v3.21.6
+// source: spacex/api/device/device.proto
+
+package device
+
+import (
+	protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+	protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+	status "olowe.co/dishy/status"
+	reflect "reflect"
+	sync "sync"
+)
+
+const (
+	// Verify that this generated code is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+	// Verify that runtime/protoimpl is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+type ToDevice struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	// Types that are assignable to Message:
+	//
+	//	*ToDevice_Request
+	Message isToDevice_Message `protobuf_oneof:"message"`
+}
+
+func (x *ToDevice) Reset() {
+	*x = ToDevice{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[0]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *ToDevice) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*ToDevice) ProtoMessage() {}
+
+func (x *ToDevice) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[0]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use ToDevice.ProtoReflect.Descriptor instead.
+func (*ToDevice) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{0}
+}
+
+func (m *ToDevice) GetMessage() isToDevice_Message {
+	if m != nil {
+		return m.Message
+	}
+	return nil
+}
+
+func (x *ToDevice) GetRequest() *Request {
+	if x, ok := x.GetMessage().(*ToDevice_Request); ok {
+		return x.Request
+	}
+	return nil
+}
+
+type isToDevice_Message interface {
+	isToDevice_Message()
+}
+
+type ToDevice_Request struct {
+	Request *Request `protobuf:"bytes,1,opt,name=request,proto3,oneof"`
+}
+
+func (*ToDevice_Request) isToDevice_Message() {}
+
+type FromDevice struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	// Types that are assignable to Message:
+	//
+	//	*FromDevice_Response
+	//	*FromDevice_Event
+	Message isFromDevice_Message `protobuf_oneof:"message"`
+}
+
+func (x *FromDevice) Reset() {
+	*x = FromDevice{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[1]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *FromDevice) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*FromDevice) ProtoMessage() {}
+
+func (x *FromDevice) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[1]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use FromDevice.ProtoReflect.Descriptor instead.
+func (*FromDevice) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{1}
+}
+
+func (m *FromDevice) GetMessage() isFromDevice_Message {
+	if m != nil {
+		return m.Message
+	}
+	return nil
+}
+
+func (x *FromDevice) GetResponse() *Response {
+	if x, ok := x.GetMessage().(*FromDevice_Response); ok {
+		return x.Response
+	}
+	return nil
+}
+
+func (x *FromDevice) GetEvent() *Event {
+	if x, ok := x.GetMessage().(*FromDevice_Event); ok {
+		return x.Event
+	}
+	return nil
+}
+
+type isFromDevice_Message interface {
+	isFromDevice_Message()
+}
+
+type FromDevice_Response struct {
+	Response *Response `protobuf:"bytes,1,opt,name=response,proto3,oneof"`
+}
+
+type FromDevice_Event struct {
+	Event *Event `protobuf:"bytes,2,opt,name=event,proto3,oneof"`
+}
+
+func (*FromDevice_Response) isFromDevice_Message() {}
+
+func (*FromDevice_Event) isFromDevice_Message() {}
+
+type Request struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Id       uint64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
+	EpochId  uint64 `protobuf:"varint,14,opt,name=epoch_id,json=epochId,proto3" json:"epoch_id,omitempty"`
+	TargetId string `protobuf:"bytes,13,opt,name=target_id,json=targetId,proto3" json:"target_id,omitempty"`
+	// Types that are assignable to Request:
+	//
+	//	*Request_SignedRequest
+	//	*Request_GetNextId
+	//	*Request_Authenticate
+	//	*Request_FactoryReset
+	//	*Request_GetDeviceInfo
+	//	*Request_GetHistory
+	//	*Request_GetLog
+	//	*Request_GetNetworkInterfaces
+	//	*Request_GetPing
+	//	*Request_PingHost
+	//	*Request_GetStatus
+	//	*Request_Reboot
+	//	*Request_SetSku
+	//	*Request_SetTrustedKeys
+	//	*Request_SpeedTest
+	//	*Request_Update
+	//	*Request_DishStow
+	//	*Request_TransceiverIfLoopbackTest
+	//	*Request_TransceiverGetStatus
+	//	*Request_WifiGetClients
+	//	*Request_WifiGetPingMetrics
+	//	*Request_WifiSetConfig
+	//	*Request_WifiSetup
+	Request isRequest_Request `protobuf_oneof:"request"`
+}
+
+func (x *Request) Reset() {
+	*x = Request{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[2]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *Request) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Request) ProtoMessage() {}
+
+func (x *Request) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[2]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use Request.ProtoReflect.Descriptor instead.
+func (*Request) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{2}
+}
+
+func (x *Request) GetId() uint64 {
+	if x != nil {
+		return x.Id
+	}
+	return 0
+}
+
+func (x *Request) GetEpochId() uint64 {
+	if x != nil {
+		return x.EpochId
+	}
+	return 0
+}
+
+func (x *Request) GetTargetId() string {
+	if x != nil {
+		return x.TargetId
+	}
+	return ""
+}
+
+func (m *Request) GetRequest() isRequest_Request {
+	if m != nil {
+		return m.Request
+	}
+	return nil
+}
+
+func (x *Request) GetSignedRequest() *SignedData {
+	if x, ok := x.GetRequest().(*Request_SignedRequest); ok {
+		return x.SignedRequest
+	}
+	return nil
+}
+
+func (x *Request) GetGetNextId() *GetNextIdRequest {
+	if x, ok := x.GetRequest().(*Request_GetNextId); ok {
+		return x.GetNextId
+	}
+	return nil
+}
+
+func (x *Request) GetAuthenticate() *AuthenticateRequest {
+	if x, ok := x.GetRequest().(*Request_Authenticate); ok {
+		return x.Authenticate
+	}
+	return nil
+}
+
+func (x *Request) GetFactoryReset() *FactoryResetRequest {
+	if x, ok := x.GetRequest().(*Request_FactoryReset); ok {
+		return x.FactoryReset
+	}
+	return nil
+}
+
+func (x *Request) GetGetDeviceInfo() *GetDeviceInfoRequest {
+	if x, ok := x.GetRequest().(*Request_GetDeviceInfo); ok {
+		return x.GetDeviceInfo
+	}
+	return nil
+}
+
+func (x *Request) GetGetHistory() *GetHistoryRequest {
+	if x, ok := x.GetRequest().(*Request_GetHistory); ok {
+		return x.GetHistory
+	}
+	return nil
+}
+
+func (x *Request) GetGetLog() *GetLogRequest {
+	if x, ok := x.GetRequest().(*Request_GetLog); ok {
+		return x.GetLog
+	}
+	return nil
+}
+
+func (x *Request) GetGetNetworkInterfaces() *GetNetworkInterfacesRequest {
+	if x, ok := x.GetRequest().(*Request_GetNetworkInterfaces); ok {
+		return x.GetNetworkInterfaces
+	}
+	return nil
+}
+
+func (x *Request) GetGetPing() *GetPingRequest {
+	if x, ok := x.GetRequest().(*Request_GetPing); ok {
+		return x.GetPing
+	}
+	return nil
+}
+
+func (x *Request) GetPingHost() *PingHostRequest {
+	if x, ok := x.GetRequest().(*Request_PingHost); ok {
+		return x.PingHost
+	}
+	return nil
+}
+
+func (x *Request) GetGetStatus() *GetStatusRequest {
+	if x, ok := x.GetRequest().(*Request_GetStatus); ok {
+		return x.GetStatus
+	}
+	return nil
+}
+
+func (x *Request) GetReboot() *RebootRequest {
+	if x, ok := x.GetRequest().(*Request_Reboot); ok {
+		return x.Reboot
+	}
+	return nil
+}
+
+func (x *Request) GetSetSku() *SetSkuRequest {
+	if x, ok := x.GetRequest().(*Request_SetSku); ok {
+		return x.SetSku
+	}
+	return nil
+}
+
+func (x *Request) GetSetTrustedKeys() *SetTrustedKeysRequest {
+	if x, ok := x.GetRequest().(*Request_SetTrustedKeys); ok {
+		return x.SetTrustedKeys
+	}
+	return nil
+}
+
+func (x *Request) GetSpeedTest() *SpeedTestRequest {
+	if x, ok := x.GetRequest().(*Request_SpeedTest); ok {
+		return x.SpeedTest
+	}
+	return nil
+}
+
+func (x *Request) GetUpdate() *UpdateRequest {
+	if x, ok := x.GetRequest().(*Request_Update); ok {
+		return x.Update
+	}
+	return nil
+}
+
+func (x *Request) GetDishStow() *DishStowRequest {
+	if x, ok := x.GetRequest().(*Request_DishStow); ok {
+		return x.DishStow
+	}
+	return nil
+}
+
+func (x *Request) GetTransceiverIfLoopbackTest() *TransceiverIFLoopbackTestRequest {
+	if x, ok := x.GetRequest().(*Request_TransceiverIfLoopbackTest); ok {
+		return x.TransceiverIfLoopbackTest
+	}
+	return nil
+}
+
+func (x *Request) GetTransceiverGetStatus() *TransceiverGetStatusRequest {
+	if x, ok := x.GetRequest().(*Request_TransceiverGetStatus); ok {
+		return x.TransceiverGetStatus
+	}
+	return nil
+}
+
+func (x *Request) GetWifiGetClients() *WifiGetClientsRequest {
+	if x, ok := x.GetRequest().(*Request_WifiGetClients); ok {
+		return x.WifiGetClients
+	}
+	return nil
+}
+
+func (x *Request) GetWifiGetPingMetrics() *WifiGetPingMetricsRequest {
+	if x, ok := x.GetRequest().(*Request_WifiGetPingMetrics); ok {
+		return x.WifiGetPingMetrics
+	}
+	return nil
+}
+
+func (x *Request) GetWifiSetConfig() *WifiSetConfigRequest {
+	if x, ok := x.GetRequest().(*Request_WifiSetConfig); ok {
+		return x.WifiSetConfig
+	}
+	return nil
+}
+
+func (x *Request) GetWifiSetup() *WifiSetupRequest {
+	if x, ok := x.GetRequest().(*Request_WifiSetup); ok {
+		return x.WifiSetup
+	}
+	return nil
+}
+
+type isRequest_Request interface {
+	isRequest_Request()
+}
+
+type Request_SignedRequest struct {
+	SignedRequest *SignedData `protobuf:"bytes,15,opt,name=signed_request,json=signedRequest,proto3,oneof"`
+}
+
+type Request_GetNextId struct {
+	GetNextId *GetNextIdRequest `protobuf:"bytes,1006,opt,name=get_next_id,json=getNextId,proto3,oneof"`
+}
+
+type Request_Authenticate struct {
+	Authenticate *AuthenticateRequest `protobuf:"bytes,1005,opt,name=authenticate,proto3,oneof"`
+}
+
+type Request_FactoryReset struct {
+	FactoryReset *FactoryResetRequest `protobuf:"bytes,1011,opt,name=factory_reset,json=factoryReset,proto3,oneof"`
+}
+
+type Request_GetDeviceInfo struct {
+	GetDeviceInfo *GetDeviceInfoRequest `protobuf:"bytes,1008,opt,name=get_device_info,json=getDeviceInfo,proto3,oneof"`
+}
+
+type Request_GetHistory struct {
+	GetHistory *GetHistoryRequest `protobuf:"bytes,1007,opt,name=get_history,json=getHistory,proto3,oneof"`
+}
+
+type Request_GetLog struct {
+	GetLog *GetLogRequest `protobuf:"bytes,1012,opt,name=get_log,json=getLog,proto3,oneof"`
+}
+
+type Request_GetNetworkInterfaces struct {
+	GetNetworkInterfaces *GetNetworkInterfacesRequest `protobuf:"bytes,1015,opt,name=get_network_interfaces,json=getNetworkInterfaces,proto3,oneof"`
+}
+
+type Request_GetPing struct {
+	GetPing *GetPingRequest `protobuf:"bytes,1009,opt,name=get_ping,json=getPing,proto3,oneof"`
+}
+
+type Request_PingHost struct {
+	PingHost *PingHostRequest `protobuf:"bytes,1016,opt,name=ping_host,json=pingHost,proto3,oneof"`
+}
+
+type Request_GetStatus struct {
+	GetStatus *GetStatusRequest `protobuf:"bytes,1004,opt,name=get_status,json=getStatus,proto3,oneof"`
+}
+
+type Request_Reboot struct {
+	Reboot *RebootRequest `protobuf:"bytes,1001,opt,name=reboot,proto3,oneof"`
+}
+
+type Request_SetSku struct {
+	SetSku *SetSkuRequest `protobuf:"bytes,1013,opt,name=set_sku,json=setSku,proto3,oneof"`
+}
+
+type Request_SetTrustedKeys struct {
+	SetTrustedKeys *SetTrustedKeysRequest `protobuf:"bytes,1010,opt,name=set_trusted_keys,json=setTrustedKeys,proto3,oneof"`
+}
+
+type Request_SpeedTest struct {
+	SpeedTest *SpeedTestRequest `protobuf:"bytes,1003,opt,name=speed_test,json=speedTest,proto3,oneof"`
+}
+
+type Request_Update struct {
+	Update *UpdateRequest `protobuf:"bytes,1014,opt,name=update,proto3,oneof"`
+}
+
+type Request_DishStow struct {
+	DishStow *DishStowRequest `protobuf:"bytes,2002,opt,name=dish_stow,json=dishStow,proto3,oneof"`
+}
+
+type Request_TransceiverIfLoopbackTest struct {
+	TransceiverIfLoopbackTest *TransceiverIFLoopbackTestRequest `protobuf:"bytes,4001,opt,name=transceiver_if_loopback_test,json=transceiverIfLoopbackTest,proto3,oneof"`
+}
+
+type Request_TransceiverGetStatus struct {
+	TransceiverGetStatus *TransceiverGetStatusRequest `protobuf:"bytes,4003,opt,name=transceiver_get_status,json=transceiverGetStatus,proto3,oneof"`
+}
+
+type Request_WifiGetClients struct {
+	WifiGetClients *WifiGetClientsRequest `protobuf:"bytes,3002,opt,name=wifi_get_clients,json=wifiGetClients,proto3,oneof"`
+}
+
+type Request_WifiGetPingMetrics struct {
+	WifiGetPingMetrics *WifiGetPingMetricsRequest `protobuf:"bytes,3007,opt,name=wifi_get_ping_metrics,json=wifiGetPingMetrics,proto3,oneof"`
+}
+
+type Request_WifiSetConfig struct {
+	WifiSetConfig *WifiSetConfigRequest `protobuf:"bytes,3001,opt,name=wifi_set_config,json=wifiSetConfig,proto3,oneof"`
+}
+
+type Request_WifiSetup struct {
+	WifiSetup *WifiSetupRequest `protobuf:"bytes,3003,opt,name=wifi_setup,json=wifiSetup,proto3,oneof"`
+}
+
+func (*Request_SignedRequest) isRequest_Request() {}
+
+func (*Request_GetNextId) isRequest_Request() {}
+
+func (*Request_Authenticate) isRequest_Request() {}
+
+func (*Request_FactoryReset) isRequest_Request() {}
+
+func (*Request_GetDeviceInfo) isRequest_Request() {}
+
+func (*Request_GetHistory) isRequest_Request() {}
+
+func (*Request_GetLog) isRequest_Request() {}
+
+func (*Request_GetNetworkInterfaces) isRequest_Request() {}
+
+func (*Request_GetPing) isRequest_Request() {}
+
+func (*Request_PingHost) isRequest_Request() {}
+
+func (*Request_GetStatus) isRequest_Request() {}
+
+func (*Request_Reboot) isRequest_Request() {}
+
+func (*Request_SetSku) isRequest_Request() {}
+
+func (*Request_SetTrustedKeys) isRequest_Request() {}
+
+func (*Request_SpeedTest) isRequest_Request() {}
+
+func (*Request_Update) isRequest_Request() {}
+
+func (*Request_DishStow) isRequest_Request() {}
+
+func (*Request_TransceiverIfLoopbackTest) isRequest_Request() {}
+
+func (*Request_TransceiverGetStatus) isRequest_Request() {}
+
+func (*Request_WifiGetClients) isRequest_Request() {}
+
+func (*Request_WifiGetPingMetrics) isRequest_Request() {}
+
+func (*Request_WifiSetConfig) isRequest_Request() {}
+
+func (*Request_WifiSetup) isRequest_Request() {}
+
+type Response struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Id     uint64         `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
+	Status *status.Status `protobuf:"bytes,2,opt,name=status,proto3" json:"status,omitempty"`
+	// Types that are assignable to Response:
+	//
+	//	*Response_GetNextId
+	//	*Response_FactoryReset
+	//	*Response_GetDeviceInfo
+	//	*Response_GetLog
+	//	*Response_GetNetworkInterfaces
+	//	*Response_GetPing
+	//	*Response_PingHost
+	//	*Response_Reboot
+	//	*Response_SpeedTest
+	//	*Response_SetSku
+	//	*Response_SetTrustedKeys
+	//	*Response_Update
+	//	*Response_DishAuthenticate
+	//	*Response_DishGetHistory
+	//	*Response_DishGetStatus
+	//	*Response_DishStow
+	//	*Response_TransceiverIfLoopbackTest
+	//	*Response_TransceiverGetStatus
+	//	*Response_WifiAuthenticate
+	//	*Response_WifiGetClients
+	//	*Response_WifiGetHistory
+	//	*Response_WifiGetPingMetrics
+	//	*Response_WifiGetStatus
+	//	*Response_WifiSetConfig
+	//	*Response_WifiSetup
+	Response isResponse_Response `protobuf_oneof:"response"`
+}
+
+func (x *Response) Reset() {
+	*x = Response{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[3]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *Response) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Response) ProtoMessage() {}
+
+func (x *Response) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[3]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use Response.ProtoReflect.Descriptor instead.
+func (*Response) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{3}
+}
+
+func (x *Response) GetId() uint64 {
+	if x != nil {
+		return x.Id
+	}
+	return 0
+}
+
+func (x *Response) GetStatus() *status.Status {
+	if x != nil {
+		return x.Status
+	}
+	return nil
+}
+
+func (m *Response) GetResponse() isResponse_Response {
+	if m != nil {
+		return m.Response
+	}
+	return nil
+}
+
+func (x *Response) GetGetNextId() *GetNextIdResponse {
+	if x, ok := x.GetResponse().(*Response_GetNextId); ok {
+		return x.GetNextId
+	}
+	return nil
+}
+
+func (x *Response) GetFactoryReset() *FactoryResetResponse {
+	if x, ok := x.GetResponse().(*Response_FactoryReset); ok {
+		return x.FactoryReset
+	}
+	return nil
+}
+
+func (x *Response) GetGetDeviceInfo() *GetDeviceInfoResponse {
+	if x, ok := x.GetResponse().(*Response_GetDeviceInfo); ok {
+		return x.GetDeviceInfo
+	}
+	return nil
+}
+
+func (x *Response) GetGetLog() *GetLogResponse {
+	if x, ok := x.GetResponse().(*Response_GetLog); ok {
+		return x.GetLog
+	}
+	return nil
+}
+
+func (x *Response) GetGetNetworkInterfaces() *GetNetworkInterfacesResponse {
+	if x, ok := x.GetResponse().(*Response_GetNetworkInterfaces); ok {
+		return x.GetNetworkInterfaces
+	}
+	return nil
+}
+
+func (x *Response) GetGetPing() *GetPingResponse {
+	if x, ok := x.GetResponse().(*Response_GetPing); ok {
+		return x.GetPing
+	}
+	return nil
+}
+
+func (x *Response) GetPingHost() *PingHostResponse {
+	if x, ok := x.GetResponse().(*Response_PingHost); ok {
+		return x.PingHost
+	}
+	return nil
+}
+
+func (x *Response) GetReboot() *RebootResponse {
+	if x, ok := x.GetResponse().(*Response_Reboot); ok {
+		return x.Reboot
+	}
+	return nil
+}
+
+func (x *Response) GetSpeedTest() *SpeedTestResponse {
+	if x, ok := x.GetResponse().(*Response_SpeedTest); ok {
+		return x.SpeedTest
+	}
+	return nil
+}
+
+func (x *Response) GetSetSku() *SetSkuResponse {
+	if x, ok := x.GetResponse().(*Response_SetSku); ok {
+		return x.SetSku
+	}
+	return nil
+}
+
+func (x *Response) GetSetTrustedKeys() *SetTrustedKeysResponse {
+	if x, ok := x.GetResponse().(*Response_SetTrustedKeys); ok {
+		return x.SetTrustedKeys
+	}
+	return nil
+}
+
+func (x *Response) GetUpdate() *UpdateResponse {
+	if x, ok := x.GetResponse().(*Response_Update); ok {
+		return x.Update
+	}
+	return nil
+}
+
+func (x *Response) GetDishAuthenticate() *DishAuthenticateResponse {
+	if x, ok := x.GetResponse().(*Response_DishAuthenticate); ok {
+		return x.DishAuthenticate
+	}
+	return nil
+}
+
+func (x *Response) GetDishGetHistory() *DishGetHistoryResponse {
+	if x, ok := x.GetResponse().(*Response_DishGetHistory); ok {
+		return x.DishGetHistory
+	}
+	return nil
+}
+
+func (x *Response) GetDishGetStatus() *DishGetStatusResponse {
+	if x, ok := x.GetResponse().(*Response_DishGetStatus); ok {
+		return x.DishGetStatus
+	}
+	return nil
+}
+
+func (x *Response) GetDishStow() *DishStowResponse {
+	if x, ok := x.GetResponse().(*Response_DishStow); ok {
+		return x.DishStow
+	}
+	return nil
+}
+
+func (x *Response) GetTransceiverIfLoopbackTest() *TransceiverIFLoopbackTestResponse {
+	if x, ok := x.GetResponse().(*Response_TransceiverIfLoopbackTest); ok {
+		return x.TransceiverIfLoopbackTest
+	}
+	return nil
+}
+
+func (x *Response) GetTransceiverGetStatus() *TransceiverGetStatusResponse {
+	if x, ok := x.GetResponse().(*Response_TransceiverGetStatus); ok {
+		return x.TransceiverGetStatus
+	}
+	return nil
+}
+
+func (x *Response) GetWifiAuthenticate() *WifiAuthenticateResponse {
+	if x, ok := x.GetResponse().(*Response_WifiAuthenticate); ok {
+		return x.WifiAuthenticate
+	}
+	return nil
+}
+
+func (x *Response) GetWifiGetClients() *WifiGetClientsResponse {
+	if x, ok := x.GetResponse().(*Response_WifiGetClients); ok {
+		return x.WifiGetClients
+	}
+	return nil
+}
+
+func (x *Response) GetWifiGetHistory() *WifiGetHistoryResponse {
+	if x, ok := x.GetResponse().(*Response_WifiGetHistory); ok {
+		return x.WifiGetHistory
+	}
+	return nil
+}
+
+func (x *Response) GetWifiGetPingMetrics() *WifiGetPingMetricsResponse {
+	if x, ok := x.GetResponse().(*Response_WifiGetPingMetrics); ok {
+		return x.WifiGetPingMetrics
+	}
+	return nil
+}
+
+func (x *Response) GetWifiGetStatus() *WifiGetStatusResponse {
+	if x, ok := x.GetResponse().(*Response_WifiGetStatus); ok {
+		return x.WifiGetStatus
+	}
+	return nil
+}
+
+func (x *Response) GetWifiSetConfig() *WifiSetConfigResponse {
+	if x, ok := x.GetResponse().(*Response_WifiSetConfig); ok {
+		return x.WifiSetConfig
+	}
+	return nil
+}
+
+func (x *Response) GetWifiSetup() *WifiSetupResponse {
+	if x, ok := x.GetResponse().(*Response_WifiSetup); ok {
+		return x.WifiSetup
+	}
+	return nil
+}
+
+type isResponse_Response interface {
+	isResponse_Response()
+}
+
+type Response_GetNextId struct {
+	GetNextId *GetNextIdResponse `protobuf:"bytes,1006,opt,name=get_next_id,json=getNextId,proto3,oneof"`
+}
+
+type Response_FactoryReset struct {
+	FactoryReset *FactoryResetResponse `protobuf:"bytes,1011,opt,name=factory_reset,json=factoryReset,proto3,oneof"`
+}
+
+type Response_GetDeviceInfo struct {
+	GetDeviceInfo *GetDeviceInfoResponse `protobuf:"bytes,1004,opt,name=get_device_info,json=getDeviceInfo,proto3,oneof"`
+}
+
+type Response_GetLog struct {
+	GetLog *GetLogResponse `protobuf:"bytes,1012,opt,name=get_log,json=getLog,proto3,oneof"`
+}
+
+type Response_GetNetworkInterfaces struct {
+	GetNetworkInterfaces *GetNetworkInterfacesResponse `protobuf:"bytes,1015,opt,name=get_network_interfaces,json=getNetworkInterfaces,proto3,oneof"`
+}
+
+type Response_GetPing struct {
+	GetPing *GetPingResponse `protobuf:"bytes,1009,opt,name=get_ping,json=getPing,proto3,oneof"`
+}
+
+type Response_PingHost struct {
+	PingHost *PingHostResponse `protobuf:"bytes,1016,opt,name=ping_host,json=pingHost,proto3,oneof"`
+}
+
+type Response_Reboot struct {
+	Reboot *RebootResponse `protobuf:"bytes,1001,opt,name=reboot,proto3,oneof"`
+}
+
+type Response_SpeedTest struct {
+	SpeedTest *SpeedTestResponse `protobuf:"bytes,1003,opt,name=speed_test,json=speedTest,proto3,oneof"`
+}
+
+type Response_SetSku struct {
+	SetSku *SetSkuResponse `protobuf:"bytes,1013,opt,name=set_sku,json=setSku,proto3,oneof"`
+}
+
+type Response_SetTrustedKeys struct {
+	SetTrustedKeys *SetTrustedKeysResponse `protobuf:"bytes,1010,opt,name=set_trusted_keys,json=setTrustedKeys,proto3,oneof"`
+}
+
+type Response_Update struct {
+	Update *UpdateResponse `protobuf:"bytes,1014,opt,name=update,proto3,oneof"`
+}
+
+type Response_DishAuthenticate struct {
+	DishAuthenticate *DishAuthenticateResponse `protobuf:"bytes,2005,opt,name=dish_authenticate,json=dishAuthenticate,proto3,oneof"`
+}
+
+type Response_DishGetHistory struct {
+	DishGetHistory *DishGetHistoryResponse `protobuf:"bytes,2006,opt,name=dish_get_history,json=dishGetHistory,proto3,oneof"`
+}
+
+type Response_DishGetStatus struct {
+	DishGetStatus *DishGetStatusResponse `protobuf:"bytes,2004,opt,name=dish_get_status,json=dishGetStatus,proto3,oneof"`
+}
+
+type Response_DishStow struct {
+	DishStow *DishStowResponse `protobuf:"bytes,2002,opt,name=dish_stow,json=dishStow,proto3,oneof"`
+}
+
+type Response_TransceiverIfLoopbackTest struct {
+	TransceiverIfLoopbackTest *TransceiverIFLoopbackTestResponse `protobuf:"bytes,4001,opt,name=transceiver_if_loopback_test,json=transceiverIfLoopbackTest,proto3,oneof"`
+}
+
+type Response_TransceiverGetStatus struct {
+	TransceiverGetStatus *TransceiverGetStatusResponse `protobuf:"bytes,4003,opt,name=transceiver_get_status,json=transceiverGetStatus,proto3,oneof"`
+}
+
+type Response_WifiAuthenticate struct {
+	WifiAuthenticate *WifiAuthenticateResponse `protobuf:"bytes,3005,opt,name=wifi_authenticate,json=wifiAuthenticate,proto3,oneof"`
+}
+
+type Response_WifiGetClients struct {
+	WifiGetClients *WifiGetClientsResponse `protobuf:"bytes,3002,opt,name=wifi_get_clients,json=wifiGetClients,proto3,oneof"`
+}
+
+type Response_WifiGetHistory struct {
+	WifiGetHistory *WifiGetHistoryResponse `protobuf:"bytes,3006,opt,name=wifi_get_history,json=wifiGetHistory,proto3,oneof"`
+}
+
+type Response_WifiGetPingMetrics struct {
+	WifiGetPingMetrics *WifiGetPingMetricsResponse `protobuf:"bytes,3007,opt,name=wifi_get_ping_metrics,json=wifiGetPingMetrics,proto3,oneof"`
+}
+
+type Response_WifiGetStatus struct {
+	WifiGetStatus *WifiGetStatusResponse `protobuf:"bytes,3004,opt,name=wifi_get_status,json=wifiGetStatus,proto3,oneof"`
+}
+
+type Response_WifiSetConfig struct {
+	WifiSetConfig *WifiSetConfigResponse `protobuf:"bytes,3001,opt,name=wifi_set_config,json=wifiSetConfig,proto3,oneof"`
+}
+
+type Response_WifiSetup struct {
+	WifiSetup *WifiSetupResponse `protobuf:"bytes,3003,opt,name=wifi_setup,json=wifiSetup,proto3,oneof"`
+}
+
+func (*Response_GetNextId) isResponse_Response() {}
+
+func (*Response_FactoryReset) isResponse_Response() {}
+
+func (*Response_GetDeviceInfo) isResponse_Response() {}
+
+func (*Response_GetLog) isResponse_Response() {}
+
+func (*Response_GetNetworkInterfaces) isResponse_Response() {}
+
+func (*Response_GetPing) isResponse_Response() {}
+
+func (*Response_PingHost) isResponse_Response() {}
+
+func (*Response_Reboot) isResponse_Response() {}
+
+func (*Response_SpeedTest) isResponse_Response() {}
+
+func (*Response_SetSku) isResponse_Response() {}
+
+func (*Response_SetTrustedKeys) isResponse_Response() {}
+
+func (*Response_Update) isResponse_Response() {}
+
+func (*Response_DishAuthenticate) isResponse_Response() {}
+
+func (*Response_DishGetHistory) isResponse_Response() {}
+
+func (*Response_DishGetStatus) isResponse_Response() {}
+
+func (*Response_DishStow) isResponse_Response() {}
+
+func (*Response_TransceiverIfLoopbackTest) isResponse_Response() {}
+
+func (*Response_TransceiverGetStatus) isResponse_Response() {}
+
+func (*Response_WifiAuthenticate) isResponse_Response() {}
+
+func (*Response_WifiGetClients) isResponse_Response() {}
+
+func (*Response_WifiGetHistory) isResponse_Response() {}
+
+func (*Response_WifiGetPingMetrics) isResponse_Response() {}
+
+func (*Response_WifiGetStatus) isResponse_Response() {}
+
+func (*Response_WifiSetConfig) isResponse_Response() {}
+
+func (*Response_WifiSetup) isResponse_Response() {}
+
+type Event struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	// Types that are assignable to Event:
+	//
+	//	*Event_WifiNewClientConnected
+	//	*Event_WifiAccountBonding
+	Event isEvent_Event `protobuf_oneof:"event"`
+}
+
+func (x *Event) Reset() {
+	*x = Event{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[4]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *Event) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Event) ProtoMessage() {}
+
+func (x *Event) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[4]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use Event.ProtoReflect.Descriptor instead.
+func (*Event) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{4}
+}
+
+func (m *Event) GetEvent() isEvent_Event {
+	if m != nil {
+		return m.Event
+	}
+	return nil
+}
+
+func (x *Event) GetWifiNewClientConnected() *WifiNewClientConnectedEvent {
+	if x, ok := x.GetEvent().(*Event_WifiNewClientConnected); ok {
+		return x.WifiNewClientConnected
+	}
+	return nil
+}
+
+func (x *Event) GetWifiAccountBonding() *WifiAccountBondingEvent {
+	if x, ok := x.GetEvent().(*Event_WifiAccountBonding); ok {
+		return x.WifiAccountBonding
+	}
+	return nil
+}
+
+type isEvent_Event interface {
+	isEvent_Event()
+}
+
+type Event_WifiNewClientConnected struct {
+	WifiNewClientConnected *WifiNewClientConnectedEvent `protobuf:"bytes,3001,opt,name=wifi_new_client_connected,json=wifiNewClientConnected,proto3,oneof"`
+}
+
+type Event_WifiAccountBonding struct {
+	WifiAccountBonding *WifiAccountBondingEvent `protobuf:"bytes,3002,opt,name=wifi_account_bonding,json=wifiAccountBonding,proto3,oneof"`
+}
+
+func (*Event_WifiNewClientConnected) isEvent_Event() {}
+
+func (*Event_WifiAccountBonding) isEvent_Event() {}
+
+type FactoryResetRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *FactoryResetRequest) Reset() {
+	*x = FactoryResetRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[5]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *FactoryResetRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*FactoryResetRequest) ProtoMessage() {}
+
+func (x *FactoryResetRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[5]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use FactoryResetRequest.ProtoReflect.Descriptor instead.
+func (*FactoryResetRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{5}
+}
+
+type FactoryResetResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *FactoryResetResponse) Reset() {
+	*x = FactoryResetResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[6]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *FactoryResetResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*FactoryResetResponse) ProtoMessage() {}
+
+func (x *FactoryResetResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[6]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use FactoryResetResponse.ProtoReflect.Descriptor instead.
+func (*FactoryResetResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{6}
+}
+
+type GetHistoryRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *GetHistoryRequest) Reset() {
+	*x = GetHistoryRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[7]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetHistoryRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetHistoryRequest) ProtoMessage() {}
+
+func (x *GetHistoryRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[7]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetHistoryRequest.ProtoReflect.Descriptor instead.
+func (*GetHistoryRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{7}
+}
+
+type GetLogRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *GetLogRequest) Reset() {
+	*x = GetLogRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[8]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetLogRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetLogRequest) ProtoMessage() {}
+
+func (x *GetLogRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[8]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetLogRequest.ProtoReflect.Descriptor instead.
+func (*GetLogRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{8}
+}
+
+type GetLogResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Syslog     string `protobuf:"bytes,1,opt,name=syslog,proto3" json:"syslog,omitempty"`
+	OfflineLog string `protobuf:"bytes,2,opt,name=offline_log,json=offlineLog,proto3" json:"offline_log,omitempty"`
+}
+
+func (x *GetLogResponse) Reset() {
+	*x = GetLogResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[9]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetLogResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetLogResponse) ProtoMessage() {}
+
+func (x *GetLogResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[9]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetLogResponse.ProtoReflect.Descriptor instead.
+func (*GetLogResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{9}
+}
+
+func (x *GetLogResponse) GetSyslog() string {
+	if x != nil {
+		return x.Syslog
+	}
+	return ""
+}
+
+func (x *GetLogResponse) GetOfflineLog() string {
+	if x != nil {
+		return x.OfflineLog
+	}
+	return ""
+}
+
+type GetPingRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *GetPingRequest) Reset() {
+	*x = GetPingRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[10]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetPingRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetPingRequest) ProtoMessage() {}
+
+func (x *GetPingRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[10]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetPingRequest.ProtoReflect.Descriptor instead.
+func (*GetPingRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{10}
+}
+
+type GetPingResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Results map[string]*PingResult `protobuf:"bytes,1,rep,name=results,proto3" json:"results,omitempty" protobuf_key:"bytes,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"`
+}
+
+func (x *GetPingResponse) Reset() {
+	*x = GetPingResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[11]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetPingResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetPingResponse) ProtoMessage() {}
+
+func (x *GetPingResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[11]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetPingResponse.ProtoReflect.Descriptor instead.
+func (*GetPingResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{11}
+}
+
+func (x *GetPingResponse) GetResults() map[string]*PingResult {
+	if x != nil {
+		return x.Results
+	}
+	return nil
+}
+
+type PingHostRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Address string `protobuf:"bytes,3,opt,name=address,proto3" json:"address,omitempty"`
+}
+
+func (x *PingHostRequest) Reset() {
+	*x = PingHostRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[12]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *PingHostRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*PingHostRequest) ProtoMessage() {}
+
+func (x *PingHostRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[12]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use PingHostRequest.ProtoReflect.Descriptor instead.
+func (*PingHostRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{12}
+}
+
+func (x *PingHostRequest) GetAddress() string {
+	if x != nil {
+		return x.Address
+	}
+	return ""
+}
+
+type PingHostResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Result *PingResult `protobuf:"bytes,1,opt,name=result,proto3" json:"result,omitempty"`
+}
+
+func (x *PingHostResponse) Reset() {
+	*x = PingHostResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[13]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *PingHostResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*PingHostResponse) ProtoMessage() {}
+
+func (x *PingHostResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[13]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use PingHostResponse.ProtoReflect.Descriptor instead.
+func (*PingHostResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{13}
+}
+
+func (x *PingHostResponse) GetResult() *PingResult {
+	if x != nil {
+		return x.Result
+	}
+	return nil
+}
+
+type GetStatusRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *GetStatusRequest) Reset() {
+	*x = GetStatusRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[14]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetStatusRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetStatusRequest) ProtoMessage() {}
+
+func (x *GetStatusRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[14]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetStatusRequest.ProtoReflect.Descriptor instead.
+func (*GetStatusRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{14}
+}
+
+type RebootRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *RebootRequest) Reset() {
+	*x = RebootRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[15]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *RebootRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*RebootRequest) ProtoMessage() {}
+
+func (x *RebootRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[15]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use RebootRequest.ProtoReflect.Descriptor instead.
+func (*RebootRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{15}
+}
+
+type RebootResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *RebootResponse) Reset() {
+	*x = RebootResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[16]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *RebootResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*RebootResponse) ProtoMessage() {}
+
+func (x *RebootResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[16]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use RebootResponse.ProtoReflect.Descriptor instead.
+func (*RebootResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{16}
+}
+
+type SpeedTestRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *SpeedTestRequest) Reset() {
+	*x = SpeedTestRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[17]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *SpeedTestRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SpeedTestRequest) ProtoMessage() {}
+
+func (x *SpeedTestRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[17]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use SpeedTestRequest.ProtoReflect.Descriptor instead.
+func (*SpeedTestRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{17}
+}
+
+type SpeedTestResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	DownloadBps float32 `protobuf:"fixed32,1,opt,name=download_bps,json=downloadBps,proto3" json:"download_bps,omitempty"`
+	UploadBps   float32 `protobuf:"fixed32,2,opt,name=upload_bps,json=uploadBps,proto3" json:"upload_bps,omitempty"`
+	LatencyS    float32 `protobuf:"fixed32,3,opt,name=latency_s,json=latencyS,proto3" json:"latency_s,omitempty"`
+}
+
+func (x *SpeedTestResponse) Reset() {
+	*x = SpeedTestResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[18]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *SpeedTestResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SpeedTestResponse) ProtoMessage() {}
+
+func (x *SpeedTestResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[18]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use SpeedTestResponse.ProtoReflect.Descriptor instead.
+func (*SpeedTestResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{18}
+}
+
+func (x *SpeedTestResponse) GetDownloadBps() float32 {
+	if x != nil {
+		return x.DownloadBps
+	}
+	return 0
+}
+
+func (x *SpeedTestResponse) GetUploadBps() float32 {
+	if x != nil {
+		return x.UploadBps
+	}
+	return 0
+}
+
+func (x *SpeedTestResponse) GetLatencyS() float32 {
+	if x != nil {
+		return x.LatencyS
+	}
+	return 0
+}
+
+type GetDeviceInfoRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *GetDeviceInfoRequest) Reset() {
+	*x = GetDeviceInfoRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[19]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetDeviceInfoRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetDeviceInfoRequest) ProtoMessage() {}
+
+func (x *GetDeviceInfoRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[19]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetDeviceInfoRequest.ProtoReflect.Descriptor instead.
+func (*GetDeviceInfoRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{19}
+}
+
+type GetDeviceInfoResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	DeviceInfo *DeviceInfo `protobuf:"bytes,1,opt,name=device_info,json=deviceInfo,proto3" json:"device_info,omitempty"`
+}
+
+func (x *GetDeviceInfoResponse) Reset() {
+	*x = GetDeviceInfoResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[20]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetDeviceInfoResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetDeviceInfoResponse) ProtoMessage() {}
+
+func (x *GetDeviceInfoResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[20]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetDeviceInfoResponse.ProtoReflect.Descriptor instead.
+func (*GetDeviceInfoResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{20}
+}
+
+func (x *GetDeviceInfoResponse) GetDeviceInfo() *DeviceInfo {
+	if x != nil {
+		return x.DeviceInfo
+	}
+	return nil
+}
+
+type SetTrustedKeysRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Keys []*PublicKey `protobuf:"bytes,1,rep,name=keys,proto3" json:"keys,omitempty"`
+}
+
+func (x *SetTrustedKeysRequest) Reset() {
+	*x = SetTrustedKeysRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[21]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *SetTrustedKeysRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SetTrustedKeysRequest) ProtoMessage() {}
+
+func (x *SetTrustedKeysRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[21]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use SetTrustedKeysRequest.ProtoReflect.Descriptor instead.
+func (*SetTrustedKeysRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{21}
+}
+
+func (x *SetTrustedKeysRequest) GetKeys() []*PublicKey {
+	if x != nil {
+		return x.Keys
+	}
+	return nil
+}
+
+type SetTrustedKeysResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *SetTrustedKeysResponse) Reset() {
+	*x = SetTrustedKeysResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[22]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *SetTrustedKeysResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SetTrustedKeysResponse) ProtoMessage() {}
+
+func (x *SetTrustedKeysResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[22]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use SetTrustedKeysResponse.ProtoReflect.Descriptor instead.
+func (*SetTrustedKeysResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{22}
+}
+
+type SetSkuRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Sku              string `protobuf:"bytes,1,opt,name=sku,proto3" json:"sku,omitempty"`
+	CountryCode      string `protobuf:"bytes,2,opt,name=country_code,json=countryCode,proto3" json:"country_code,omitempty"`
+	ApplyCountryCode bool   `protobuf:"varint,4,opt,name=apply_country_code,json=applyCountryCode,proto3" json:"apply_country_code,omitempty"`
+}
+
+func (x *SetSkuRequest) Reset() {
+	*x = SetSkuRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[23]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *SetSkuRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SetSkuRequest) ProtoMessage() {}
+
+func (x *SetSkuRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[23]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use SetSkuRequest.ProtoReflect.Descriptor instead.
+func (*SetSkuRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{23}
+}
+
+func (x *SetSkuRequest) GetSku() string {
+	if x != nil {
+		return x.Sku
+	}
+	return ""
+}
+
+func (x *SetSkuRequest) GetCountryCode() string {
+	if x != nil {
+		return x.CountryCode
+	}
+	return ""
+}
+
+func (x *SetSkuRequest) GetApplyCountryCode() bool {
+	if x != nil {
+		return x.ApplyCountryCode
+	}
+	return false
+}
+
+type SetSkuResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *SetSkuResponse) Reset() {
+	*x = SetSkuResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[24]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *SetSkuResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*SetSkuResponse) ProtoMessage() {}
+
+func (x *SetSkuResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[24]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use SetSkuResponse.ProtoReflect.Descriptor instead.
+func (*SetSkuResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{24}
+}
+
+type UpdateRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *UpdateRequest) Reset() {
+	*x = UpdateRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[25]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *UpdateRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*UpdateRequest) ProtoMessage() {}
+
+func (x *UpdateRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[25]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use UpdateRequest.ProtoReflect.Descriptor instead.
+func (*UpdateRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{25}
+}
+
+type UpdateResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *UpdateResponse) Reset() {
+	*x = UpdateResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[26]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *UpdateResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*UpdateResponse) ProtoMessage() {}
+
+func (x *UpdateResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[26]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use UpdateResponse.ProtoReflect.Descriptor instead.
+func (*UpdateResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{26}
+}
+
+type GetNetworkInterfacesRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *GetNetworkInterfacesRequest) Reset() {
+	*x = GetNetworkInterfacesRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[27]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetNetworkInterfacesRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetNetworkInterfacesRequest) ProtoMessage() {}
+
+func (x *GetNetworkInterfacesRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[27]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetNetworkInterfacesRequest.ProtoReflect.Descriptor instead.
+func (*GetNetworkInterfacesRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{27}
+}
+
+type GetNetworkInterfacesResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	NetworkInterfaces []*NetworkInterface `protobuf:"bytes,1006,rep,name=network_interfaces,json=networkInterfaces,proto3" json:"network_interfaces,omitempty"`
+}
+
+func (x *GetNetworkInterfacesResponse) Reset() {
+	*x = GetNetworkInterfacesResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_device_proto_msgTypes[28]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *GetNetworkInterfacesResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*GetNetworkInterfacesResponse) ProtoMessage() {}
+
+func (x *GetNetworkInterfacesResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_device_proto_msgTypes[28]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use GetNetworkInterfacesResponse.ProtoReflect.Descriptor instead.
+func (*GetNetworkInterfacesResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_device_proto_rawDescGZIP(), []int{28}
+}
+
+func (x *GetNetworkInterfacesResponse) GetNetworkInterfaces() []*NetworkInterface {
+	if x != nil {
+		return x.NetworkInterfaces
+	}
+	return nil
+}
+
+var File_spacex_api_device_device_proto protoreflect.FileDescriptor
+
+var file_spacex_api_device_device_proto_rawDesc = []byte{
+	0x0a, 0x1e, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
+	0x12, 0x11, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x1a, 0x25, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f,
+	0x63, 0x6f, 0x6d, 0x6d, 0x6f, 0x6e, 0x2f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x2f, 0x73, 0x74,
+	0x61, 0x74, 0x75, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1f, 0x73, 0x70, 0x61, 0x63,
+	0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2f, 0x63, 0x6f,
+	0x6d, 0x6d, 0x61, 0x6e, 0x64, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1e, 0x73, 0x70, 0x61,
+	0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2f, 0x63,
+	0x6f, 0x6d, 0x6d, 0x6f, 0x6e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1c, 0x73, 0x70, 0x61,
+	0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2f, 0x64,
+	0x69, 0x73, 0x68, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x23, 0x73, 0x70, 0x61, 0x63, 0x65,
+	0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2f, 0x74, 0x72, 0x61,
+	0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1c,
+	0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2f, 0x77, 0x69, 0x66, 0x69, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0x4d, 0x0a, 0x08,
+	0x54, 0x6f, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x12, 0x36, 0x0a, 0x07, 0x72, 0x65, 0x71, 0x75,
+	0x65, 0x73, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1a, 0x2e, 0x53, 0x70, 0x61, 0x63,
+	0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x52, 0x65,
+	0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x07, 0x72, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74,
+	0x42, 0x09, 0x0a, 0x07, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x84, 0x01, 0x0a, 0x0a,
+	0x46, 0x72, 0x6f, 0x6d, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x12, 0x39, 0x0a, 0x08, 0x72, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1b, 0x2e, 0x53,
+	0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x2e, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x08, 0x72, 0x65, 0x73,
+	0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x30, 0x0a, 0x05, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x18, 0x02,
+	0x20, 0x01, 0x28, 0x0b, 0x32, 0x18, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x48, 0x00,
+	0x52, 0x05, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x42, 0x09, 0x0a, 0x07, 0x6d, 0x65, 0x73, 0x73, 0x61,
+	0x67, 0x65, 0x22, 0xee, 0x0e, 0x0a, 0x07, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x0e,
+	0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x02, 0x69, 0x64, 0x12, 0x19,
+	0x0a, 0x08, 0x65, 0x70, 0x6f, 0x63, 0x68, 0x5f, 0x69, 0x64, 0x18, 0x0e, 0x20, 0x01, 0x28, 0x04,
+	0x52, 0x07, 0x65, 0x70, 0x6f, 0x63, 0x68, 0x49, 0x64, 0x12, 0x1b, 0x0a, 0x09, 0x74, 0x61, 0x72,
+	0x67, 0x65, 0x74, 0x5f, 0x69, 0x64, 0x18, 0x0d, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x74, 0x61,
+	0x72, 0x67, 0x65, 0x74, 0x49, 0x64, 0x12, 0x46, 0x0a, 0x0e, 0x73, 0x69, 0x67, 0x6e, 0x65, 0x64,
+	0x5f, 0x72, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x18, 0x0f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d,
+	0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69,
+	0x63, 0x65, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x44, 0x61, 0x74, 0x61, 0x48, 0x00, 0x52,
+	0x0d, 0x73, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x46,
+	0x0a, 0x0b, 0x67, 0x65, 0x74, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f, 0x69, 0x64, 0x18, 0xee, 0x07,
+	0x20, 0x01, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x4e, 0x65, 0x78, 0x74,
+	0x49, 0x64, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x09, 0x67, 0x65, 0x74,
+	0x4e, 0x65, 0x78, 0x74, 0x49, 0x64, 0x12, 0x4d, 0x0a, 0x0c, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e,
+	0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x18, 0xed, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x26, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x41, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x52, 0x65,
+	0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x0c, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74,
+	0x69, 0x63, 0x61, 0x74, 0x65, 0x12, 0x4e, 0x0a, 0x0d, 0x66, 0x61, 0x63, 0x74, 0x6f, 0x72, 0x79,
+	0x5f, 0x72, 0x65, 0x73, 0x65, 0x74, 0x18, 0xf3, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x26, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x46, 0x61, 0x63, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x73, 0x65, 0x74, 0x52, 0x65,
+	0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x0c, 0x66, 0x61, 0x63, 0x74, 0x6f, 0x72, 0x79,
+	0x52, 0x65, 0x73, 0x65, 0x74, 0x12, 0x52, 0x0a, 0x0f, 0x67, 0x65, 0x74, 0x5f, 0x64, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x5f, 0x69, 0x6e, 0x66, 0x6f, 0x18, 0xf0, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32,
+	0x27, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e, 0x66,
+	0x6f, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x0d, 0x67, 0x65, 0x74, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x12, 0x48, 0x0a, 0x0b, 0x67, 0x65, 0x74,
+	0x5f, 0x68, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x18, 0xef, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32,
+	0x24, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65,
+	0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x0a, 0x67, 0x65, 0x74, 0x48, 0x69, 0x73, 0x74,
+	0x6f, 0x72, 0x79, 0x12, 0x3c, 0x0a, 0x07, 0x67, 0x65, 0x74, 0x5f, 0x6c, 0x6f, 0x67, 0x18, 0xf4,
+	0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41,
+	0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x4c, 0x6f, 0x67,
+	0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x06, 0x67, 0x65, 0x74, 0x4c, 0x6f,
+	0x67, 0x12, 0x67, 0x0a, 0x16, 0x67, 0x65, 0x74, 0x5f, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b,
+	0x5f, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x18, 0xf7, 0x07, 0x20, 0x01,
+	0x28, 0x0b, 0x32, 0x2e, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e,
+	0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x4e, 0x65, 0x74, 0x77, 0x6f, 0x72,
+	0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65,
+	0x73, 0x74, 0x48, 0x00, 0x52, 0x14, 0x67, 0x65, 0x74, 0x4e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b,
+	0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x12, 0x3f, 0x0a, 0x08, 0x67, 0x65,
+	0x74, 0x5f, 0x70, 0x69, 0x6e, 0x67, 0x18, 0xf1, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x21, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x47, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74,
+	0x48, 0x00, 0x52, 0x07, 0x67, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x12, 0x42, 0x0a, 0x09, 0x70,
+	0x69, 0x6e, 0x67, 0x5f, 0x68, 0x6f, 0x73, 0x74, 0x18, 0xf8, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32,
+	0x22, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2e, 0x50, 0x69, 0x6e, 0x67, 0x48, 0x6f, 0x73, 0x74, 0x52, 0x65, 0x71, 0x75,
+	0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x08, 0x70, 0x69, 0x6e, 0x67, 0x48, 0x6f, 0x73, 0x74, 0x12,
+	0x45, 0x0a, 0x0a, 0x67, 0x65, 0x74, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0xec, 0x07,
+	0x20, 0x01, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61, 0x74,
+	0x75, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x09, 0x67, 0x65, 0x74,
+	0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x3b, 0x0a, 0x06, 0x72, 0x65, 0x62, 0x6f, 0x6f, 0x74,
+	0x18, 0xe9, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x52, 0x65, 0x62, 0x6f,
+	0x6f, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x06, 0x72, 0x65, 0x62,
+	0x6f, 0x6f, 0x74, 0x12, 0x3c, 0x0a, 0x07, 0x73, 0x65, 0x74, 0x5f, 0x73, 0x6b, 0x75, 0x18, 0xf5,
+	0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41,
+	0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x53, 0x65, 0x74, 0x53, 0x6b, 0x75,
+	0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x06, 0x73, 0x65, 0x74, 0x53, 0x6b,
+	0x75, 0x12, 0x55, 0x0a, 0x10, 0x73, 0x65, 0x74, 0x5f, 0x74, 0x72, 0x75, 0x73, 0x74, 0x65, 0x64,
+	0x5f, 0x6b, 0x65, 0x79, 0x73, 0x18, 0xf2, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x28, 0x2e, 0x53,
+	0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x2e, 0x53, 0x65, 0x74, 0x54, 0x72, 0x75, 0x73, 0x74, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x73, 0x52,
+	0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x0e, 0x73, 0x65, 0x74, 0x54, 0x72, 0x75,
+	0x73, 0x74, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x73, 0x12, 0x45, 0x0a, 0x0a, 0x73, 0x70, 0x65, 0x65,
+	0x64, 0x5f, 0x74, 0x65, 0x73, 0x74, 0x18, 0xeb, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x23, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x53, 0x70, 0x65, 0x65, 0x64, 0x54, 0x65, 0x73, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65,
+	0x73, 0x74, 0x48, 0x00, 0x52, 0x09, 0x73, 0x70, 0x65, 0x65, 0x64, 0x54, 0x65, 0x73, 0x74, 0x12,
+	0x3b, 0x0a, 0x06, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x18, 0xf6, 0x07, 0x20, 0x01, 0x28, 0x0b,
+	0x32, 0x20, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x2e, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65,
+	0x73, 0x74, 0x48, 0x00, 0x52, 0x06, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x12, 0x42, 0x0a, 0x09,
+	0x64, 0x69, 0x73, 0x68, 0x5f, 0x73, 0x74, 0x6f, 0x77, 0x18, 0xd2, 0x0f, 0x20, 0x01, 0x28, 0x0b,
+	0x32, 0x22, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x2e, 0x44, 0x69, 0x73, 0x68, 0x53, 0x74, 0x6f, 0x77, 0x52, 0x65, 0x71,
+	0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x08, 0x64, 0x69, 0x73, 0x68, 0x53, 0x74, 0x6f, 0x77,
+	0x12, 0x77, 0x0a, 0x1c, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x5f,
+	0x69, 0x66, 0x5f, 0x6c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x5f, 0x74, 0x65, 0x73, 0x74,
+	0x18, 0xa1, 0x1f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x33, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x54, 0x72, 0x61, 0x6e,
+	0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x49, 0x46, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63,
+	0x6b, 0x54, 0x65, 0x73, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x19,
+	0x74, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x49, 0x66, 0x4c, 0x6f, 0x6f,
+	0x70, 0x62, 0x61, 0x63, 0x6b, 0x54, 0x65, 0x73, 0x74, 0x12, 0x67, 0x0a, 0x16, 0x74, 0x72, 0x61,
+	0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x73, 0x74, 0x61,
+	0x74, 0x75, 0x73, 0x18, 0xa3, 0x1f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2e, 0x2e, 0x53, 0x70, 0x61,
+	0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x54,
+	0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61,
+	0x74, 0x75, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x14, 0x74, 0x72,
+	0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61, 0x74,
+	0x75, 0x73, 0x12, 0x55, 0x0a, 0x10, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x63,
+	0x6c, 0x69, 0x65, 0x6e, 0x74, 0x73, 0x18, 0xba, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x28, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x73,
+	0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x0e, 0x77, 0x69, 0x66, 0x69, 0x47,
+	0x65, 0x74, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x73, 0x12, 0x62, 0x0a, 0x15, 0x77, 0x69, 0x66,
+	0x69, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x6d, 0x65, 0x74, 0x72, 0x69,
+	0x63, 0x73, 0x18, 0xbf, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2c, 0x2e, 0x53, 0x70, 0x61, 0x63,
+	0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69,
+	0x66, 0x69, 0x47, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x73,
+	0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x12, 0x77, 0x69, 0x66, 0x69, 0x47,
+	0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x73, 0x12, 0x52, 0x0a,
+	0x0f, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x73, 0x65, 0x74, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67,
+	0x18, 0xb9, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x27, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69,
+	0x53, 0x65, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74,
+	0x48, 0x00, 0x52, 0x0d, 0x77, 0x69, 0x66, 0x69, 0x53, 0x65, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69,
+	0x67, 0x12, 0x45, 0x0a, 0x0a, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x73, 0x65, 0x74, 0x75, 0x70, 0x18,
+	0xbb, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e,
+	0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x53,
+	0x65, 0x74, 0x75, 0x70, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x48, 0x00, 0x52, 0x09, 0x77,
+	0x69, 0x66, 0x69, 0x53, 0x65, 0x74, 0x75, 0x70, 0x42, 0x09, 0x0a, 0x07, 0x72, 0x65, 0x71, 0x75,
+	0x65, 0x73, 0x74, 0x22, 0xea, 0x10, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65,
+	0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x02, 0x69, 0x64,
+	0x12, 0x31, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b,
+	0x32, 0x19, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x53, 0x74,
+	0x61, 0x74, 0x75, 0x73, 0x2e, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x06, 0x73, 0x74, 0x61,
+	0x74, 0x75, 0x73, 0x12, 0x47, 0x0a, 0x0b, 0x67, 0x65, 0x74, 0x5f, 0x6e, 0x65, 0x78, 0x74, 0x5f,
+	0x69, 0x64, 0x18, 0xee, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e, 0x53, 0x70, 0x61, 0x63,
+	0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65,
+	0x74, 0x4e, 0x65, 0x78, 0x74, 0x49, 0x64, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48,
+	0x00, 0x52, 0x09, 0x67, 0x65, 0x74, 0x4e, 0x65, 0x78, 0x74, 0x49, 0x64, 0x12, 0x4f, 0x0a, 0x0d,
+	0x66, 0x61, 0x63, 0x74, 0x6f, 0x72, 0x79, 0x5f, 0x72, 0x65, 0x73, 0x65, 0x74, 0x18, 0xf3, 0x07,
+	0x20, 0x01, 0x28, 0x0b, 0x32, 0x27, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x46, 0x61, 0x63, 0x74, 0x6f, 0x72, 0x79,
+	0x52, 0x65, 0x73, 0x65, 0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52,
+	0x0c, 0x66, 0x61, 0x63, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x73, 0x65, 0x74, 0x12, 0x53, 0x0a,
+	0x0f, 0x67, 0x65, 0x74, 0x5f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x5f, 0x69, 0x6e, 0x66, 0x6f,
+	0x18, 0xec, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x28, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73,
+	0x65, 0x48, 0x00, 0x52, 0x0d, 0x67, 0x65, 0x74, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e,
+	0x66, 0x6f, 0x12, 0x3d, 0x0a, 0x07, 0x67, 0x65, 0x74, 0x5f, 0x6c, 0x6f, 0x67, 0x18, 0xf4, 0x07,
+	0x20, 0x01, 0x28, 0x0b, 0x32, 0x21, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x4c, 0x6f, 0x67, 0x52,
+	0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x06, 0x67, 0x65, 0x74, 0x4c, 0x6f,
+	0x67, 0x12, 0x68, 0x0a, 0x16, 0x67, 0x65, 0x74, 0x5f, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b,
+	0x5f, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x18, 0xf7, 0x07, 0x20, 0x01,
+	0x28, 0x0b, 0x32, 0x2f, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e,
+	0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x4e, 0x65, 0x74, 0x77, 0x6f, 0x72,
+	0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x14, 0x67, 0x65, 0x74, 0x4e, 0x65, 0x74, 0x77, 0x6f, 0x72,
+	0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x12, 0x40, 0x0a, 0x08, 0x67,
+	0x65, 0x74, 0x5f, 0x70, 0x69, 0x6e, 0x67, 0x18, 0xf1, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x22,
+	0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69,
+	0x63, 0x65, 0x2e, 0x47, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e,
+	0x73, 0x65, 0x48, 0x00, 0x52, 0x07, 0x67, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x12, 0x43, 0x0a,
+	0x09, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x68, 0x6f, 0x73, 0x74, 0x18, 0xf8, 0x07, 0x20, 0x01, 0x28,
+	0x0b, 0x32, 0x23, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x50, 0x69, 0x6e, 0x67, 0x48, 0x6f, 0x73, 0x74, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x08, 0x70, 0x69, 0x6e, 0x67, 0x48, 0x6f,
+	0x73, 0x74, 0x12, 0x3c, 0x0a, 0x06, 0x72, 0x65, 0x62, 0x6f, 0x6f, 0x74, 0x18, 0xe9, 0x07, 0x20,
+	0x01, 0x28, 0x0b, 0x32, 0x21, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49,
+	0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x52, 0x65, 0x62, 0x6f, 0x6f, 0x74, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x06, 0x72, 0x65, 0x62, 0x6f, 0x6f, 0x74,
+	0x12, 0x46, 0x0a, 0x0a, 0x73, 0x70, 0x65, 0x65, 0x64, 0x5f, 0x74, 0x65, 0x73, 0x74, 0x18, 0xeb,
+	0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41,
+	0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x53, 0x70, 0x65, 0x65, 0x64, 0x54,
+	0x65, 0x73, 0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x09, 0x73,
+	0x70, 0x65, 0x65, 0x64, 0x54, 0x65, 0x73, 0x74, 0x12, 0x3d, 0x0a, 0x07, 0x73, 0x65, 0x74, 0x5f,
+	0x73, 0x6b, 0x75, 0x18, 0xf5, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x21, 0x2e, 0x53, 0x70, 0x61,
+	0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x53,
+	0x65, 0x74, 0x53, 0x6b, 0x75, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52,
+	0x06, 0x73, 0x65, 0x74, 0x53, 0x6b, 0x75, 0x12, 0x56, 0x0a, 0x10, 0x73, 0x65, 0x74, 0x5f, 0x74,
+	0x72, 0x75, 0x73, 0x74, 0x65, 0x64, 0x5f, 0x6b, 0x65, 0x79, 0x73, 0x18, 0xf2, 0x07, 0x20, 0x01,
+	0x28, 0x0b, 0x32, 0x29, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e,
+	0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x53, 0x65, 0x74, 0x54, 0x72, 0x75, 0x73, 0x74, 0x65,
+	0x64, 0x4b, 0x65, 0x79, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52,
+	0x0e, 0x73, 0x65, 0x74, 0x54, 0x72, 0x75, 0x73, 0x74, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x73, 0x12,
+	0x3c, 0x0a, 0x06, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x18, 0xf6, 0x07, 0x20, 0x01, 0x28, 0x0b,
+	0x32, 0x21, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x2e, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x06, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x12, 0x5b, 0x0a,
+	0x11, 0x64, 0x69, 0x73, 0x68, 0x5f, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61,
+	0x74, 0x65, 0x18, 0xd5, 0x0f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x53, 0x70, 0x61, 0x63,
+	0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x44, 0x69,
+	0x73, 0x68, 0x41, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x10, 0x64, 0x69, 0x73, 0x68, 0x41, 0x75,
+	0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x12, 0x56, 0x0a, 0x10, 0x64, 0x69,
+	0x73, 0x68, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x68, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x18, 0xd6,
+	0x0f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41,
+	0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x44, 0x69, 0x73, 0x68, 0x47, 0x65,
+	0x74, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65,
+	0x48, 0x00, 0x52, 0x0e, 0x64, 0x69, 0x73, 0x68, 0x47, 0x65, 0x74, 0x48, 0x69, 0x73, 0x74, 0x6f,
+	0x72, 0x79, 0x12, 0x53, 0x0a, 0x0f, 0x64, 0x69, 0x73, 0x68, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x73,
+	0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0xd4, 0x0f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x28, 0x2e, 0x53,
+	0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x2e, 0x44, 0x69, 0x73, 0x68, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x0d, 0x64, 0x69, 0x73, 0x68, 0x47, 0x65,
+	0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x43, 0x0a, 0x09, 0x64, 0x69, 0x73, 0x68, 0x5f,
+	0x73, 0x74, 0x6f, 0x77, 0x18, 0xd2, 0x0f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x53, 0x70,
+	0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e,
+	0x44, 0x69, 0x73, 0x68, 0x53, 0x74, 0x6f, 0x77, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65,
+	0x48, 0x00, 0x52, 0x08, 0x64, 0x69, 0x73, 0x68, 0x53, 0x74, 0x6f, 0x77, 0x12, 0x78, 0x0a, 0x1c,
+	0x74, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x5f, 0x69, 0x66, 0x5f, 0x6c,
+	0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x5f, 0x74, 0x65, 0x73, 0x74, 0x18, 0xa1, 0x1f, 0x20,
+	0x01, 0x28, 0x0b, 0x32, 0x34, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49,
+	0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69,
+	0x76, 0x65, 0x72, 0x49, 0x46, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x54, 0x65, 0x73,
+	0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x19, 0x74, 0x72, 0x61,
+	0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x49, 0x66, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61,
+	0x63, 0x6b, 0x54, 0x65, 0x73, 0x74, 0x12, 0x68, 0x0a, 0x16, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x63,
+	0x65, 0x69, 0x76, 0x65, 0x72, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73,
+	0x18, 0xa3, 0x1f, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2f, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x54, 0x72, 0x61, 0x6e,
+	0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73,
+	0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x14, 0x74, 0x72, 0x61, 0x6e,
+	0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73,
+	0x12, 0x5b, 0x0a, 0x11, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74,
+	0x69, 0x63, 0x61, 0x74, 0x65, 0x18, 0xbd, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x53,
+	0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x2e, 0x57, 0x69, 0x66, 0x69, 0x41, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74,
+	0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x10, 0x77, 0x69, 0x66,
+	0x69, 0x41, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x12, 0x56, 0x0a,
+	0x10, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x63, 0x6c, 0x69, 0x65, 0x6e, 0x74,
+	0x73, 0x18, 0xba, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65,
+	0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66,
+	0x69, 0x47, 0x65, 0x74, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x0e, 0x77, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x43, 0x6c,
+	0x69, 0x65, 0x6e, 0x74, 0x73, 0x12, 0x56, 0x0a, 0x10, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x67, 0x65,
+	0x74, 0x5f, 0x68, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x18, 0xbe, 0x17, 0x20, 0x01, 0x28, 0x0b,
+	0x32, 0x29, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x48, 0x69, 0x73, 0x74,
+	0x6f, 0x72, 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x0e, 0x77,
+	0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x12, 0x63, 0x0a,
+	0x15, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x6d,
+	0x65, 0x74, 0x72, 0x69, 0x63, 0x73, 0x18, 0xbf, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2d, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x4d, 0x65, 0x74,
+	0x72, 0x69, 0x63, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x12,
+	0x77, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x4d, 0x65, 0x74, 0x72, 0x69,
+	0x63, 0x73, 0x12, 0x53, 0x0a, 0x0f, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x67, 0x65, 0x74, 0x5f, 0x73,
+	0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0xbc, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x28, 0x2e, 0x53,
+	0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x2e, 0x57, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x0d, 0x77, 0x69, 0x66, 0x69, 0x47, 0x65,
+	0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x53, 0x0a, 0x0f, 0x77, 0x69, 0x66, 0x69, 0x5f,
+	0x73, 0x65, 0x74, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x18, 0xb9, 0x17, 0x20, 0x01, 0x28,
+	0x0b, 0x32, 0x28, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x53, 0x65, 0x74, 0x43, 0x6f, 0x6e,
+	0x66, 0x69, 0x67, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x0d, 0x77,
+	0x69, 0x66, 0x69, 0x53, 0x65, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x12, 0x46, 0x0a, 0x0a,
+	0x77, 0x69, 0x66, 0x69, 0x5f, 0x73, 0x65, 0x74, 0x75, 0x70, 0x18, 0xbb, 0x17, 0x20, 0x01, 0x28,
+	0x0b, 0x32, 0x24, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x53, 0x65, 0x74, 0x75, 0x70, 0x52,
+	0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x48, 0x00, 0x52, 0x09, 0x77, 0x69, 0x66, 0x69, 0x53,
+	0x65, 0x74, 0x75, 0x70, 0x42, 0x0a, 0x0a, 0x08, 0x72, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65,
+	0x22, 0xdf, 0x01, 0x0a, 0x05, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x12, 0x6c, 0x0a, 0x19, 0x77, 0x69,
+	0x66, 0x69, 0x5f, 0x6e, 0x65, 0x77, 0x5f, 0x63, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x5f, 0x63, 0x6f,
+	0x6e, 0x6e, 0x65, 0x63, 0x74, 0x65, 0x64, 0x18, 0xb9, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2e,
+	0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69,
+	0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x4e, 0x65, 0x77, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74,
+	0x43, 0x6f, 0x6e, 0x6e, 0x65, 0x63, 0x74, 0x65, 0x64, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x48, 0x00,
+	0x52, 0x16, 0x77, 0x69, 0x66, 0x69, 0x4e, 0x65, 0x77, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x43,
+	0x6f, 0x6e, 0x6e, 0x65, 0x63, 0x74, 0x65, 0x64, 0x12, 0x5f, 0x0a, 0x14, 0x77, 0x69, 0x66, 0x69,
+	0x5f, 0x61, 0x63, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x5f, 0x62, 0x6f, 0x6e, 0x64, 0x69, 0x6e, 0x67,
+	0x18, 0xba, 0x17, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x2a, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69,
+	0x41, 0x63, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x42, 0x6f, 0x6e, 0x64, 0x69, 0x6e, 0x67, 0x45, 0x76,
+	0x65, 0x6e, 0x74, 0x48, 0x00, 0x52, 0x12, 0x77, 0x69, 0x66, 0x69, 0x41, 0x63, 0x63, 0x6f, 0x75,
+	0x6e, 0x74, 0x42, 0x6f, 0x6e, 0x64, 0x69, 0x6e, 0x67, 0x42, 0x07, 0x0a, 0x05, 0x65, 0x76, 0x65,
+	0x6e, 0x74, 0x22, 0x15, 0x0a, 0x13, 0x46, 0x61, 0x63, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x73,
+	0x65, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x16, 0x0a, 0x14, 0x46, 0x61, 0x63,
+	0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x73, 0x65, 0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73,
+	0x65, 0x22, 0x13, 0x0a, 0x11, 0x47, 0x65, 0x74, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x52,
+	0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x0f, 0x0a, 0x0d, 0x47, 0x65, 0x74, 0x4c, 0x6f, 0x67,
+	0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x49, 0x0a, 0x0e, 0x47, 0x65, 0x74, 0x4c, 0x6f,
+	0x67, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x16, 0x0a, 0x06, 0x73, 0x79, 0x73,
+	0x6c, 0x6f, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x73, 0x79, 0x73, 0x6c, 0x6f,
+	0x67, 0x12, 0x1f, 0x0a, 0x0b, 0x6f, 0x66, 0x66, 0x6c, 0x69, 0x6e, 0x65, 0x5f, 0x6c, 0x6f, 0x67,
+	0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x6f, 0x66, 0x66, 0x6c, 0x69, 0x6e, 0x65, 0x4c,
+	0x6f, 0x67, 0x22, 0x10, 0x0a, 0x0e, 0x47, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x52, 0x65, 0x71,
+	0x75, 0x65, 0x73, 0x74, 0x22, 0xb7, 0x01, 0x0a, 0x0f, 0x47, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67,
+	0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x49, 0x0a, 0x07, 0x72, 0x65, 0x73, 0x75,
+	0x6c, 0x74, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x2f, 0x2e, 0x53, 0x70, 0x61, 0x63,
+	0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x47, 0x65,
+	0x74, 0x50, 0x69, 0x6e, 0x67, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x2e, 0x52, 0x65,
+	0x73, 0x75, 0x6c, 0x74, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x07, 0x72, 0x65, 0x73, 0x75,
+	0x6c, 0x74, 0x73, 0x1a, 0x59, 0x0a, 0x0c, 0x52, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x73, 0x45, 0x6e,
+	0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09,
+	0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x33, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02,
+	0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x50, 0x69, 0x6e, 0x67, 0x52, 0x65, 0x73,
+	0x75, 0x6c, 0x74, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x2b,
+	0x0a, 0x0f, 0x50, 0x69, 0x6e, 0x67, 0x48, 0x6f, 0x73, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73,
+	0x74, 0x12, 0x18, 0x0a, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x03, 0x20, 0x01,
+	0x28, 0x09, 0x52, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x22, 0x49, 0x0a, 0x10, 0x50,
+	0x69, 0x6e, 0x67, 0x48, 0x6f, 0x73, 0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12,
+	0x35, 0x0a, 0x06, 0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32,
+	0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2e, 0x50, 0x69, 0x6e, 0x67, 0x52, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x52, 0x06,
+	0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x22, 0x12, 0x0a, 0x10, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61,
+	0x74, 0x75, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x0f, 0x0a, 0x0d, 0x52, 0x65,
+	0x62, 0x6f, 0x6f, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x10, 0x0a, 0x0e, 0x52,
+	0x65, 0x62, 0x6f, 0x6f, 0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x12, 0x0a,
+	0x10, 0x53, 0x70, 0x65, 0x65, 0x64, 0x54, 0x65, 0x73, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73,
+	0x74, 0x22, 0x72, 0x0a, 0x11, 0x53, 0x70, 0x65, 0x65, 0x64, 0x54, 0x65, 0x73, 0x74, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x21, 0x0a, 0x0c, 0x64, 0x6f, 0x77, 0x6e, 0x6c, 0x6f,
+	0x61, 0x64, 0x5f, 0x62, 0x70, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0b, 0x64, 0x6f,
+	0x77, 0x6e, 0x6c, 0x6f, 0x61, 0x64, 0x42, 0x70, 0x73, 0x12, 0x1d, 0x0a, 0x0a, 0x75, 0x70, 0x6c,
+	0x6f, 0x61, 0x64, 0x5f, 0x62, 0x70, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x02, 0x52, 0x09, 0x75,
+	0x70, 0x6c, 0x6f, 0x61, 0x64, 0x42, 0x70, 0x73, 0x12, 0x1b, 0x0a, 0x09, 0x6c, 0x61, 0x74, 0x65,
+	0x6e, 0x63, 0x79, 0x5f, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x02, 0x52, 0x08, 0x6c, 0x61, 0x74,
+	0x65, 0x6e, 0x63, 0x79, 0x53, 0x22, 0x16, 0x0a, 0x14, 0x47, 0x65, 0x74, 0x44, 0x65, 0x76, 0x69,
+	0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x57, 0x0a,
+	0x15, 0x47, 0x65, 0x74, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x3e, 0x0a, 0x0b, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x5f, 0x69, 0x6e, 0x66, 0x6f, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70,
+	0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e,
+	0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x0a, 0x64, 0x65, 0x76, 0x69,
+	0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x22, 0x49, 0x0a, 0x15, 0x53, 0x65, 0x74, 0x54, 0x72, 0x75,
+	0x73, 0x74, 0x65, 0x64, 0x4b, 0x65, 0x79, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12,
+	0x30, 0x0a, 0x04, 0x6b, 0x65, 0x79, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1c, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x50, 0x75, 0x62, 0x6c, 0x69, 0x63, 0x4b, 0x65, 0x79, 0x52, 0x04, 0x6b, 0x65, 0x79,
+	0x73, 0x22, 0x18, 0x0a, 0x16, 0x53, 0x65, 0x74, 0x54, 0x72, 0x75, 0x73, 0x74, 0x65, 0x64, 0x4b,
+	0x65, 0x79, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x72, 0x0a, 0x0d, 0x53,
+	0x65, 0x74, 0x53, 0x6b, 0x75, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x10, 0x0a, 0x03,
+	0x73, 0x6b, 0x75, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x73, 0x6b, 0x75, 0x12, 0x21,
+	0x0a, 0x0c, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x5f, 0x63, 0x6f, 0x64, 0x65, 0x18, 0x02,
+	0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x43, 0x6f, 0x64,
+	0x65, 0x12, 0x2c, 0x0a, 0x12, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x5f, 0x63, 0x6f, 0x75, 0x6e, 0x74,
+	0x72, 0x79, 0x5f, 0x63, 0x6f, 0x64, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x52, 0x10, 0x61,
+	0x70, 0x70, 0x6c, 0x79, 0x43, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x43, 0x6f, 0x64, 0x65, 0x22,
+	0x10, 0x0a, 0x0e, 0x53, 0x65, 0x74, 0x53, 0x6b, 0x75, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73,
+	0x65, 0x22, 0x0f, 0x0a, 0x0d, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65,
+	0x73, 0x74, 0x22, 0x10, 0x0a, 0x0e, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, 0x70,
+	0x6f, 0x6e, 0x73, 0x65, 0x22, 0x1d, 0x0a, 0x1b, 0x47, 0x65, 0x74, 0x4e, 0x65, 0x74, 0x77, 0x6f,
+	0x72, 0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75,
+	0x65, 0x73, 0x74, 0x22, 0x73, 0x0a, 0x1c, 0x47, 0x65, 0x74, 0x4e, 0x65, 0x74, 0x77, 0x6f, 0x72,
+	0x6b, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x12, 0x53, 0x0a, 0x12, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x5f, 0x69,
+	0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x18, 0xee, 0x07, 0x20, 0x03, 0x28, 0x0b,
+	0x32, 0x23, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x2e, 0x4e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x49, 0x6e, 0x74, 0x65,
+	0x72, 0x66, 0x61, 0x63, 0x65, 0x52, 0x11, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x49, 0x6e,
+	0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x32, 0x95, 0x01, 0x0a, 0x06, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x12, 0x48, 0x0a, 0x06, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x12, 0x1b, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x54, 0x6f, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x1a, 0x1d, 0x2e, 0x53, 0x70, 0x61,
+	0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x46,
+	0x72, 0x6f, 0x6d, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x28, 0x01, 0x30, 0x01, 0x12, 0x41, 0x0a,
+	0x06, 0x48, 0x61, 0x6e, 0x64, 0x6c, 0x65, 0x12, 0x1a, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x52, 0x65, 0x71, 0x75,
+	0x65, 0x73, 0x74, 0x1a, 0x1b, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49,
+	0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65,
+	0x42, 0x17, 0x5a, 0x15, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x61,
+	0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f,
+	0x33,
+}
+
+var (
+	file_spacex_api_device_device_proto_rawDescOnce sync.Once
+	file_spacex_api_device_device_proto_rawDescData = file_spacex_api_device_device_proto_rawDesc
+)
+
+func file_spacex_api_device_device_proto_rawDescGZIP() []byte {
+	file_spacex_api_device_device_proto_rawDescOnce.Do(func() {
+		file_spacex_api_device_device_proto_rawDescData = protoimpl.X.CompressGZIP(file_spacex_api_device_device_proto_rawDescData)
+	})
+	return file_spacex_api_device_device_proto_rawDescData
+}
+
+var file_spacex_api_device_device_proto_msgTypes = make([]protoimpl.MessageInfo, 30)
+var file_spacex_api_device_device_proto_goTypes = []interface{}{
+	(*ToDevice)(nil),                          // 0: SpaceX.API.Device.ToDevice
+	(*FromDevice)(nil),                        // 1: SpaceX.API.Device.FromDevice
+	(*Request)(nil),                           // 2: SpaceX.API.Device.Request
+	(*Response)(nil),                          // 3: SpaceX.API.Device.Response
+	(*Event)(nil),                             // 4: SpaceX.API.Device.Event
+	(*FactoryResetRequest)(nil),               // 5: SpaceX.API.Device.FactoryResetRequest
+	(*FactoryResetResponse)(nil),              // 6: SpaceX.API.Device.FactoryResetResponse
+	(*GetHistoryRequest)(nil),                 // 7: SpaceX.API.Device.GetHistoryRequest
+	(*GetLogRequest)(nil),                     // 8: SpaceX.API.Device.GetLogRequest
+	(*GetLogResponse)(nil),                    // 9: SpaceX.API.Device.GetLogResponse
+	(*GetPingRequest)(nil),                    // 10: SpaceX.API.Device.GetPingRequest
+	(*GetPingResponse)(nil),                   // 11: SpaceX.API.Device.GetPingResponse
+	(*PingHostRequest)(nil),                   // 12: SpaceX.API.Device.PingHostRequest
+	(*PingHostResponse)(nil),                  // 13: SpaceX.API.Device.PingHostResponse
+	(*GetStatusRequest)(nil),                  // 14: SpaceX.API.Device.GetStatusRequest
+	(*RebootRequest)(nil),                     // 15: SpaceX.API.Device.RebootRequest
+	(*RebootResponse)(nil),                    // 16: SpaceX.API.Device.RebootResponse
+	(*SpeedTestRequest)(nil),                  // 17: SpaceX.API.Device.SpeedTestRequest
+	(*SpeedTestResponse)(nil),                 // 18: SpaceX.API.Device.SpeedTestResponse
+	(*GetDeviceInfoRequest)(nil),              // 19: SpaceX.API.Device.GetDeviceInfoRequest
+	(*GetDeviceInfoResponse)(nil),             // 20: SpaceX.API.Device.GetDeviceInfoResponse
+	(*SetTrustedKeysRequest)(nil),             // 21: SpaceX.API.Device.SetTrustedKeysRequest
+	(*SetTrustedKeysResponse)(nil),            // 22: SpaceX.API.Device.SetTrustedKeysResponse
+	(*SetSkuRequest)(nil),                     // 23: SpaceX.API.Device.SetSkuRequest
+	(*SetSkuResponse)(nil),                    // 24: SpaceX.API.Device.SetSkuResponse
+	(*UpdateRequest)(nil),                     // 25: SpaceX.API.Device.UpdateRequest
+	(*UpdateResponse)(nil),                    // 26: SpaceX.API.Device.UpdateResponse
+	(*GetNetworkInterfacesRequest)(nil),       // 27: SpaceX.API.Device.GetNetworkInterfacesRequest
+	(*GetNetworkInterfacesResponse)(nil),      // 28: SpaceX.API.Device.GetNetworkInterfacesResponse
+	nil,                                       // 29: SpaceX.API.Device.GetPingResponse.ResultsEntry
+	(*SignedData)(nil),                        // 30: SpaceX.API.Device.SignedData
+	(*GetNextIdRequest)(nil),                  // 31: SpaceX.API.Device.GetNextIdRequest
+	(*AuthenticateRequest)(nil),               // 32: SpaceX.API.Device.AuthenticateRequest
+	(*DishStowRequest)(nil),                   // 33: SpaceX.API.Device.DishStowRequest
+	(*TransceiverIFLoopbackTestRequest)(nil),  // 34: SpaceX.API.Device.TransceiverIFLoopbackTestRequest
+	(*TransceiverGetStatusRequest)(nil),       // 35: SpaceX.API.Device.TransceiverGetStatusRequest
+	(*WifiGetClientsRequest)(nil),             // 36: SpaceX.API.Device.WifiGetClientsRequest
+	(*WifiGetPingMetricsRequest)(nil),         // 37: SpaceX.API.Device.WifiGetPingMetricsRequest
+	(*WifiSetConfigRequest)(nil),              // 38: SpaceX.API.Device.WifiSetConfigRequest
+	(*WifiSetupRequest)(nil),                  // 39: SpaceX.API.Device.WifiSetupRequest
+	(*status.Status)(nil),                     // 40: SpaceX.API.Status.Status
+	(*GetNextIdResponse)(nil),                 // 41: SpaceX.API.Device.GetNextIdResponse
+	(*DishAuthenticateResponse)(nil),          // 42: SpaceX.API.Device.DishAuthenticateResponse
+	(*DishGetHistoryResponse)(nil),            // 43: SpaceX.API.Device.DishGetHistoryResponse
+	(*DishGetStatusResponse)(nil),             // 44: SpaceX.API.Device.DishGetStatusResponse
+	(*DishStowResponse)(nil),                  // 45: SpaceX.API.Device.DishStowResponse
+	(*TransceiverIFLoopbackTestResponse)(nil), // 46: SpaceX.API.Device.TransceiverIFLoopbackTestResponse
+	(*TransceiverGetStatusResponse)(nil),      // 47: SpaceX.API.Device.TransceiverGetStatusResponse
+	(*WifiAuthenticateResponse)(nil),          // 48: SpaceX.API.Device.WifiAuthenticateResponse
+	(*WifiGetClientsResponse)(nil),            // 49: SpaceX.API.Device.WifiGetClientsResponse
+	(*WifiGetHistoryResponse)(nil),            // 50: SpaceX.API.Device.WifiGetHistoryResponse
+	(*WifiGetPingMetricsResponse)(nil),        // 51: SpaceX.API.Device.WifiGetPingMetricsResponse
+	(*WifiGetStatusResponse)(nil),             // 52: SpaceX.API.Device.WifiGetStatusResponse
+	(*WifiSetConfigResponse)(nil),             // 53: SpaceX.API.Device.WifiSetConfigResponse
+	(*WifiSetupResponse)(nil),                 // 54: SpaceX.API.Device.WifiSetupResponse
+	(*WifiNewClientConnectedEvent)(nil),       // 55: SpaceX.API.Device.WifiNewClientConnectedEvent
+	(*WifiAccountBondingEvent)(nil),           // 56: SpaceX.API.Device.WifiAccountBondingEvent
+	(*PingResult)(nil),                        // 57: SpaceX.API.Device.PingResult
+	(*DeviceInfo)(nil),                        // 58: SpaceX.API.Device.DeviceInfo
+	(*PublicKey)(nil),                         // 59: SpaceX.API.Device.PublicKey
+	(*NetworkInterface)(nil),                  // 60: SpaceX.API.Device.NetworkInterface
+}
+var file_spacex_api_device_device_proto_depIdxs = []int32{
+	2,  // 0: SpaceX.API.Device.ToDevice.request:type_name -> SpaceX.API.Device.Request
+	3,  // 1: SpaceX.API.Device.FromDevice.response:type_name -> SpaceX.API.Device.Response
+	4,  // 2: SpaceX.API.Device.FromDevice.event:type_name -> SpaceX.API.Device.Event
+	30, // 3: SpaceX.API.Device.Request.signed_request:type_name -> SpaceX.API.Device.SignedData
+	31, // 4: SpaceX.API.Device.Request.get_next_id:type_name -> SpaceX.API.Device.GetNextIdRequest
+	32, // 5: SpaceX.API.Device.Request.authenticate:type_name -> SpaceX.API.Device.AuthenticateRequest
+	5,  // 6: SpaceX.API.Device.Request.factory_reset:type_name -> SpaceX.API.Device.FactoryResetRequest
+	19, // 7: SpaceX.API.Device.Request.get_device_info:type_name -> SpaceX.API.Device.GetDeviceInfoRequest
+	7,  // 8: SpaceX.API.Device.Request.get_history:type_name -> SpaceX.API.Device.GetHistoryRequest
+	8,  // 9: SpaceX.API.Device.Request.get_log:type_name -> SpaceX.API.Device.GetLogRequest
+	27, // 10: SpaceX.API.Device.Request.get_network_interfaces:type_name -> SpaceX.API.Device.GetNetworkInterfacesRequest
+	10, // 11: SpaceX.API.Device.Request.get_ping:type_name -> SpaceX.API.Device.GetPingRequest
+	12, // 12: SpaceX.API.Device.Request.ping_host:type_name -> SpaceX.API.Device.PingHostRequest
+	14, // 13: SpaceX.API.Device.Request.get_status:type_name -> SpaceX.API.Device.GetStatusRequest
+	15, // 14: SpaceX.API.Device.Request.reboot:type_name -> SpaceX.API.Device.RebootRequest
+	23, // 15: SpaceX.API.Device.Request.set_sku:type_name -> SpaceX.API.Device.SetSkuRequest
+	21, // 16: SpaceX.API.Device.Request.set_trusted_keys:type_name -> SpaceX.API.Device.SetTrustedKeysRequest
+	17, // 17: SpaceX.API.Device.Request.speed_test:type_name -> SpaceX.API.Device.SpeedTestRequest
+	25, // 18: SpaceX.API.Device.Request.update:type_name -> SpaceX.API.Device.UpdateRequest
+	33, // 19: SpaceX.API.Device.Request.dish_stow:type_name -> SpaceX.API.Device.DishStowRequest
+	34, // 20: SpaceX.API.Device.Request.transceiver_if_loopback_test:type_name -> SpaceX.API.Device.TransceiverIFLoopbackTestRequest
+	35, // 21: SpaceX.API.Device.Request.transceiver_get_status:type_name -> SpaceX.API.Device.TransceiverGetStatusRequest
+	36, // 22: SpaceX.API.Device.Request.wifi_get_clients:type_name -> SpaceX.API.Device.WifiGetClientsRequest
+	37, // 23: SpaceX.API.Device.Request.wifi_get_ping_metrics:type_name -> SpaceX.API.Device.WifiGetPingMetricsRequest
+	38, // 24: SpaceX.API.Device.Request.wifi_set_config:type_name -> SpaceX.API.Device.WifiSetConfigRequest
+	39, // 25: SpaceX.API.Device.Request.wifi_setup:type_name -> SpaceX.API.Device.WifiSetupRequest
+	40, // 26: SpaceX.API.Device.Response.status:type_name -> SpaceX.API.Status.Status
+	41, // 27: SpaceX.API.Device.Response.get_next_id:type_name -> SpaceX.API.Device.GetNextIdResponse
+	6,  // 28: SpaceX.API.Device.Response.factory_reset:type_name -> SpaceX.API.Device.FactoryResetResponse
+	20, // 29: SpaceX.API.Device.Response.get_device_info:type_name -> SpaceX.API.Device.GetDeviceInfoResponse
+	9,  // 30: SpaceX.API.Device.Response.get_log:type_name -> SpaceX.API.Device.GetLogResponse
+	28, // 31: SpaceX.API.Device.Response.get_network_interfaces:type_name -> SpaceX.API.Device.GetNetworkInterfacesResponse
+	11, // 32: SpaceX.API.Device.Response.get_ping:type_name -> SpaceX.API.Device.GetPingResponse
+	13, // 33: SpaceX.API.Device.Response.ping_host:type_name -> SpaceX.API.Device.PingHostResponse
+	16, // 34: SpaceX.API.Device.Response.reboot:type_name -> SpaceX.API.Device.RebootResponse
+	18, // 35: SpaceX.API.Device.Response.speed_test:type_name -> SpaceX.API.Device.SpeedTestResponse
+	24, // 36: SpaceX.API.Device.Response.set_sku:type_name -> SpaceX.API.Device.SetSkuResponse
+	22, // 37: SpaceX.API.Device.Response.set_trusted_keys:type_name -> SpaceX.API.Device.SetTrustedKeysResponse
+	26, // 38: SpaceX.API.Device.Response.update:type_name -> SpaceX.API.Device.UpdateResponse
+	42, // 39: SpaceX.API.Device.Response.dish_authenticate:type_name -> SpaceX.API.Device.DishAuthenticateResponse
+	43, // 40: SpaceX.API.Device.Response.dish_get_history:type_name -> SpaceX.API.Device.DishGetHistoryResponse
+	44, // 41: SpaceX.API.Device.Response.dish_get_status:type_name -> SpaceX.API.Device.DishGetStatusResponse
+	45, // 42: SpaceX.API.Device.Response.dish_stow:type_name -> SpaceX.API.Device.DishStowResponse
+	46, // 43: SpaceX.API.Device.Response.transceiver_if_loopback_test:type_name -> SpaceX.API.Device.TransceiverIFLoopbackTestResponse
+	47, // 44: SpaceX.API.Device.Response.transceiver_get_status:type_name -> SpaceX.API.Device.TransceiverGetStatusResponse
+	48, // 45: SpaceX.API.Device.Response.wifi_authenticate:type_name -> SpaceX.API.Device.WifiAuthenticateResponse
+	49, // 46: SpaceX.API.Device.Response.wifi_get_clients:type_name -> SpaceX.API.Device.WifiGetClientsResponse
+	50, // 47: SpaceX.API.Device.Response.wifi_get_history:type_name -> SpaceX.API.Device.WifiGetHistoryResponse
+	51, // 48: SpaceX.API.Device.Response.wifi_get_ping_metrics:type_name -> SpaceX.API.Device.WifiGetPingMetricsResponse
+	52, // 49: SpaceX.API.Device.Response.wifi_get_status:type_name -> SpaceX.API.Device.WifiGetStatusResponse
+	53, // 50: SpaceX.API.Device.Response.wifi_set_config:type_name -> SpaceX.API.Device.WifiSetConfigResponse
+	54, // 51: SpaceX.API.Device.Response.wifi_setup:type_name -> SpaceX.API.Device.WifiSetupResponse
+	55, // 52: SpaceX.API.Device.Event.wifi_new_client_connected:type_name -> SpaceX.API.Device.WifiNewClientConnectedEvent
+	56, // 53: SpaceX.API.Device.Event.wifi_account_bonding:type_name -> SpaceX.API.Device.WifiAccountBondingEvent
+	29, // 54: SpaceX.API.Device.GetPingResponse.results:type_name -> SpaceX.API.Device.GetPingResponse.ResultsEntry
+	57, // 55: SpaceX.API.Device.PingHostResponse.result:type_name -> SpaceX.API.Device.PingResult
+	58, // 56: SpaceX.API.Device.GetDeviceInfoResponse.device_info:type_name -> SpaceX.API.Device.DeviceInfo
+	59, // 57: SpaceX.API.Device.SetTrustedKeysRequest.keys:type_name -> SpaceX.API.Device.PublicKey
+	60, // 58: SpaceX.API.Device.GetNetworkInterfacesResponse.network_interfaces:type_name -> SpaceX.API.Device.NetworkInterface
+	57, // 59: SpaceX.API.Device.GetPingResponse.ResultsEntry.value:type_name -> SpaceX.API.Device.PingResult
+	0,  // 60: SpaceX.API.Device.Device.Stream:input_type -> SpaceX.API.Device.ToDevice
+	2,  // 61: SpaceX.API.Device.Device.Handle:input_type -> SpaceX.API.Device.Request
+	1,  // 62: SpaceX.API.Device.Device.Stream:output_type -> SpaceX.API.Device.FromDevice
+	3,  // 63: SpaceX.API.Device.Device.Handle:output_type -> SpaceX.API.Device.Response
+	62, // [62:64] is the sub-list for method output_type
+	60, // [60:62] is the sub-list for method input_type
+	60, // [60:60] is the sub-list for extension type_name
+	60, // [60:60] is the sub-list for extension extendee
+	0,  // [0:60] is the sub-list for field type_name
+}
+
+func init() { file_spacex_api_device_device_proto_init() }
+func file_spacex_api_device_device_proto_init() {
+	if File_spacex_api_device_device_proto != nil {
+		return
+	}
+	file_spacex_api_device_command_proto_init()
+	file_spacex_api_device_common_proto_init()
+	file_spacex_api_device_dish_proto_init()
+	file_spacex_api_device_transceiver_proto_init()
+	file_spacex_api_device_wifi_proto_init()
+	if !protoimpl.UnsafeEnabled {
+		file_spacex_api_device_device_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*ToDevice); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*FromDevice); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*Request); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*Response); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*Event); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*FactoryResetRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*FactoryResetResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetHistoryRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[8].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetLogRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[9].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetLogResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[10].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetPingRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[11].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetPingResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[12].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*PingHostRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[13].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*PingHostResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[14].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetStatusRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[15].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*RebootRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[16].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*RebootResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[17].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*SpeedTestRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[18].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*SpeedTestResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[19].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetDeviceInfoRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[20].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetDeviceInfoResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[21].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*SetTrustedKeysRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[22].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*SetTrustedKeysResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[23].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*SetSkuRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[24].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*SetSkuResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[25].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*UpdateRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[26].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*UpdateResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[27].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetNetworkInterfacesRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_device_proto_msgTypes[28].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*GetNetworkInterfacesResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+	}
+	file_spacex_api_device_device_proto_msgTypes[0].OneofWrappers = []interface{}{
+		(*ToDevice_Request)(nil),
+	}
+	file_spacex_api_device_device_proto_msgTypes[1].OneofWrappers = []interface{}{
+		(*FromDevice_Response)(nil),
+		(*FromDevice_Event)(nil),
+	}
+	file_spacex_api_device_device_proto_msgTypes[2].OneofWrappers = []interface{}{
+		(*Request_SignedRequest)(nil),
+		(*Request_GetNextId)(nil),
+		(*Request_Authenticate)(nil),
+		(*Request_FactoryReset)(nil),
+		(*Request_GetDeviceInfo)(nil),
+		(*Request_GetHistory)(nil),
+		(*Request_GetLog)(nil),
+		(*Request_GetNetworkInterfaces)(nil),
+		(*Request_GetPing)(nil),
+		(*Request_PingHost)(nil),
+		(*Request_GetStatus)(nil),
+		(*Request_Reboot)(nil),
+		(*Request_SetSku)(nil),
+		(*Request_SetTrustedKeys)(nil),
+		(*Request_SpeedTest)(nil),
+		(*Request_Update)(nil),
+		(*Request_DishStow)(nil),
+		(*Request_TransceiverIfLoopbackTest)(nil),
+		(*Request_TransceiverGetStatus)(nil),
+		(*Request_WifiGetClients)(nil),
+		(*Request_WifiGetPingMetrics)(nil),
+		(*Request_WifiSetConfig)(nil),
+		(*Request_WifiSetup)(nil),
+	}
+	file_spacex_api_device_device_proto_msgTypes[3].OneofWrappers = []interface{}{
+		(*Response_GetNextId)(nil),
+		(*Response_FactoryReset)(nil),
+		(*Response_GetDeviceInfo)(nil),
+		(*Response_GetLog)(nil),
+		(*Response_GetNetworkInterfaces)(nil),
+		(*Response_GetPing)(nil),
+		(*Response_PingHost)(nil),
+		(*Response_Reboot)(nil),
+		(*Response_SpeedTest)(nil),
+		(*Response_SetSku)(nil),
+		(*Response_SetTrustedKeys)(nil),
+		(*Response_Update)(nil),
+		(*Response_DishAuthenticate)(nil),
+		(*Response_DishGetHistory)(nil),
+		(*Response_DishGetStatus)(nil),
+		(*Response_DishStow)(nil),
+		(*Response_TransceiverIfLoopbackTest)(nil),
+		(*Response_TransceiverGetStatus)(nil),
+		(*Response_WifiAuthenticate)(nil),
+		(*Response_WifiGetClients)(nil),
+		(*Response_WifiGetHistory)(nil),
+		(*Response_WifiGetPingMetrics)(nil),
+		(*Response_WifiGetStatus)(nil),
+		(*Response_WifiSetConfig)(nil),
+		(*Response_WifiSetup)(nil),
+	}
+	file_spacex_api_device_device_proto_msgTypes[4].OneofWrappers = []interface{}{
+		(*Event_WifiNewClientConnected)(nil),
+		(*Event_WifiAccountBonding)(nil),
+	}
+	type x struct{}
+	out := protoimpl.TypeBuilder{
+		File: protoimpl.DescBuilder{
+			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+			RawDescriptor: file_spacex_api_device_device_proto_rawDesc,
+			NumEnums:      0,
+			NumMessages:   30,
+			NumExtensions: 0,
+			NumServices:   1,
+		},
+		GoTypes:           file_spacex_api_device_device_proto_goTypes,
+		DependencyIndexes: file_spacex_api_device_device_proto_depIdxs,
+		MessageInfos:      file_spacex_api_device_device_proto_msgTypes,
+	}.Build()
+	File_spacex_api_device_device_proto = out.File
+	file_spacex_api_device_device_proto_rawDesc = nil
+	file_spacex_api_device_device_proto_goTypes = nil
+	file_spacex_api_device_device_proto_depIdxs = nil
+}
blob - /dev/null
blob + f568d24ea0bc03f1511083cdfaa534e5d48443bd (mode 644)
--- /dev/null
+++ device/device_grpc.pb.go
@@ -0,0 +1,174 @@
+// Code generated by protoc-gen-go-grpc. DO NOT EDIT.
+// versions:
+// - protoc-gen-go-grpc v1.2.0
+// - protoc             v3.21.6
+// source: spacex/api/device/device.proto
+
+package device
+
+import (
+	context "context"
+	grpc "google.golang.org/grpc"
+	codes "google.golang.org/grpc/codes"
+	status "google.golang.org/grpc/status"
+)
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the grpc package it is being compiled against.
+// Requires gRPC-Go v1.32.0 or later.
+const _ = grpc.SupportPackageIsVersion7
+
+// DeviceClient is the client API for Device service.
+//
+// For semantics around ctx use and closing/ending streaming RPCs, please refer to https://pkg.go.dev/google.golang.org/grpc/?tab=doc#ClientConn.NewStream.
+type DeviceClient interface {
+	Stream(ctx context.Context, opts ...grpc.CallOption) (Device_StreamClient, error)
+	Handle(ctx context.Context, in *Request, opts ...grpc.CallOption) (*Response, error)
+}
+
+type deviceClient struct {
+	cc grpc.ClientConnInterface
+}
+
+func NewDeviceClient(cc grpc.ClientConnInterface) DeviceClient {
+	return &deviceClient{cc}
+}
+
+func (c *deviceClient) Stream(ctx context.Context, opts ...grpc.CallOption) (Device_StreamClient, error) {
+	stream, err := c.cc.NewStream(ctx, &Device_ServiceDesc.Streams[0], "/SpaceX.API.Device.Device/Stream", opts...)
+	if err != nil {
+		return nil, err
+	}
+	x := &deviceStreamClient{stream}
+	return x, nil
+}
+
+type Device_StreamClient interface {
+	Send(*ToDevice) error
+	Recv() (*FromDevice, error)
+	grpc.ClientStream
+}
+
+type deviceStreamClient struct {
+	grpc.ClientStream
+}
+
+func (x *deviceStreamClient) Send(m *ToDevice) error {
+	return x.ClientStream.SendMsg(m)
+}
+
+func (x *deviceStreamClient) Recv() (*FromDevice, error) {
+	m := new(FromDevice)
+	if err := x.ClientStream.RecvMsg(m); err != nil {
+		return nil, err
+	}
+	return m, nil
+}
+
+func (c *deviceClient) Handle(ctx context.Context, in *Request, opts ...grpc.CallOption) (*Response, error) {
+	out := new(Response)
+	err := c.cc.Invoke(ctx, "/SpaceX.API.Device.Device/Handle", in, out, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+// DeviceServer is the server API for Device service.
+// All implementations must embed UnimplementedDeviceServer
+// for forward compatibility
+type DeviceServer interface {
+	Stream(Device_StreamServer) error
+	Handle(context.Context, *Request) (*Response, error)
+	mustEmbedUnimplementedDeviceServer()
+}
+
+// UnimplementedDeviceServer must be embedded to have forward compatible implementations.
+type UnimplementedDeviceServer struct {
+}
+
+func (UnimplementedDeviceServer) Stream(Device_StreamServer) error {
+	return status.Errorf(codes.Unimplemented, "method Stream not implemented")
+}
+func (UnimplementedDeviceServer) Handle(context.Context, *Request) (*Response, error) {
+	return nil, status.Errorf(codes.Unimplemented, "method Handle not implemented")
+}
+func (UnimplementedDeviceServer) mustEmbedUnimplementedDeviceServer() {}
+
+// UnsafeDeviceServer may be embedded to opt out of forward compatibility for this service.
+// Use of this interface is not recommended, as added methods to DeviceServer will
+// result in compilation errors.
+type UnsafeDeviceServer interface {
+	mustEmbedUnimplementedDeviceServer()
+}
+
+func RegisterDeviceServer(s grpc.ServiceRegistrar, srv DeviceServer) {
+	s.RegisterService(&Device_ServiceDesc, srv)
+}
+
+func _Device_Stream_Handler(srv interface{}, stream grpc.ServerStream) error {
+	return srv.(DeviceServer).Stream(&deviceStreamServer{stream})
+}
+
+type Device_StreamServer interface {
+	Send(*FromDevice) error
+	Recv() (*ToDevice, error)
+	grpc.ServerStream
+}
+
+type deviceStreamServer struct {
+	grpc.ServerStream
+}
+
+func (x *deviceStreamServer) Send(m *FromDevice) error {
+	return x.ServerStream.SendMsg(m)
+}
+
+func (x *deviceStreamServer) Recv() (*ToDevice, error) {
+	m := new(ToDevice)
+	if err := x.ServerStream.RecvMsg(m); err != nil {
+		return nil, err
+	}
+	return m, nil
+}
+
+func _Device_Handle_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(Request)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DeviceServer).Handle(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/SpaceX.API.Device.Device/Handle",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DeviceServer).Handle(ctx, req.(*Request))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+// Device_ServiceDesc is the grpc.ServiceDesc for Device service.
+// It's only intended for direct use with grpc.RegisterService,
+// and not to be introspected or modified (even as a copy)
+var Device_ServiceDesc = grpc.ServiceDesc{
+	ServiceName: "SpaceX.API.Device.Device",
+	HandlerType: (*DeviceServer)(nil),
+	Methods: []grpc.MethodDesc{
+		{
+			MethodName: "Handle",
+			Handler:    _Device_Handle_Handler,
+		},
+	},
+	Streams: []grpc.StreamDesc{
+		{
+			StreamName:    "Stream",
+			Handler:       _Device_Stream_Handler,
+			ServerStreams: true,
+			ClientStreams: true,
+		},
+	},
+	Metadata: "spacex/api/device/device.proto",
+}
blob - /dev/null
blob + 51ada24153ef5af7eb709ac78e27a560e17fecf7 (mode 644)
--- /dev/null
+++ device/dish.pb.go
@@ -0,0 +1,856 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// 	protoc-gen-go v1.28.1
+// 	protoc        v3.21.6
+// source: spacex/api/device/dish.proto
+
+package device
+
+import (
+	protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+	protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+	reflect "reflect"
+	sync "sync"
+)
+
+const (
+	// Verify that this generated code is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+	// Verify that runtime/protoimpl is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+type DishState int32
+
+const (
+	DishState_UNKNOWN   DishState = 0
+	DishState_CONNECTED DishState = 1
+	DishState_SEARCHING DishState = 2
+	DishState_BOOTING   DishState = 3
+)
+
+// Enum value maps for DishState.
+var (
+	DishState_name = map[int32]string{
+		0: "UNKNOWN",
+		1: "CONNECTED",
+		2: "SEARCHING",
+		3: "BOOTING",
+	}
+	DishState_value = map[string]int32{
+		"UNKNOWN":   0,
+		"CONNECTED": 1,
+		"SEARCHING": 2,
+		"BOOTING":   3,
+	}
+)
+
+func (x DishState) Enum() *DishState {
+	p := new(DishState)
+	*p = x
+	return p
+}
+
+func (x DishState) String() string {
+	return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (DishState) Descriptor() protoreflect.EnumDescriptor {
+	return file_spacex_api_device_dish_proto_enumTypes[0].Descriptor()
+}
+
+func (DishState) Type() protoreflect.EnumType {
+	return &file_spacex_api_device_dish_proto_enumTypes[0]
+}
+
+func (x DishState) Number() protoreflect.EnumNumber {
+	return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use DishState.Descriptor instead.
+func (DishState) EnumDescriptor() ([]byte, []int) {
+	return file_spacex_api_device_dish_proto_rawDescGZIP(), []int{0}
+}
+
+type DishStowRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *DishStowRequest) Reset() {
+	*x = DishStowRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_dish_proto_msgTypes[0]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DishStowRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DishStowRequest) ProtoMessage() {}
+
+func (x *DishStowRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_dish_proto_msgTypes[0]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DishStowRequest.ProtoReflect.Descriptor instead.
+func (*DishStowRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_dish_proto_rawDescGZIP(), []int{0}
+}
+
+type DishStowResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *DishStowResponse) Reset() {
+	*x = DishStowResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_dish_proto_msgTypes[1]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DishStowResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DishStowResponse) ProtoMessage() {}
+
+func (x *DishStowResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_dish_proto_msgTypes[1]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DishStowResponse.ProtoReflect.Descriptor instead.
+func (*DishStowResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_dish_proto_rawDescGZIP(), []int{1}
+}
+
+type DishGetHistoryResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Current               uint64    `protobuf:"varint,1,opt,name=current,proto3" json:"current,omitempty"`
+	PopPingDropRate       []float32 `protobuf:"fixed32,1001,rep,packed,name=pop_ping_drop_rate,json=popPingDropRate,proto3" json:"pop_ping_drop_rate,omitempty"`
+	PopPingLatencyMs      []float32 `protobuf:"fixed32,1002,rep,packed,name=pop_ping_latency_ms,json=popPingLatencyMs,proto3" json:"pop_ping_latency_ms,omitempty"`
+	DownlinkThroughputBps []float32 `protobuf:"fixed32,1003,rep,packed,name=downlink_throughput_bps,json=downlinkThroughputBps,proto3" json:"downlink_throughput_bps,omitempty"`
+	UplinkThroughputBps   []float32 `protobuf:"fixed32,1004,rep,packed,name=uplink_throughput_bps,json=uplinkThroughputBps,proto3" json:"uplink_throughput_bps,omitempty"`
+	Snr                   []float32 `protobuf:"fixed32,1005,rep,packed,name=snr,proto3" json:"snr,omitempty"`
+	Scheduled             []bool    `protobuf:"varint,1006,rep,packed,name=scheduled,proto3" json:"scheduled,omitempty"`
+	Obstructed            []bool    `protobuf:"varint,1007,rep,packed,name=obstructed,proto3" json:"obstructed,omitempty"`
+}
+
+func (x *DishGetHistoryResponse) Reset() {
+	*x = DishGetHistoryResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_dish_proto_msgTypes[2]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DishGetHistoryResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DishGetHistoryResponse) ProtoMessage() {}
+
+func (x *DishGetHistoryResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_dish_proto_msgTypes[2]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DishGetHistoryResponse.ProtoReflect.Descriptor instead.
+func (*DishGetHistoryResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_dish_proto_rawDescGZIP(), []int{2}
+}
+
+func (x *DishGetHistoryResponse) GetCurrent() uint64 {
+	if x != nil {
+		return x.Current
+	}
+	return 0
+}
+
+func (x *DishGetHistoryResponse) GetPopPingDropRate() []float32 {
+	if x != nil {
+		return x.PopPingDropRate
+	}
+	return nil
+}
+
+func (x *DishGetHistoryResponse) GetPopPingLatencyMs() []float32 {
+	if x != nil {
+		return x.PopPingLatencyMs
+	}
+	return nil
+}
+
+func (x *DishGetHistoryResponse) GetDownlinkThroughputBps() []float32 {
+	if x != nil {
+		return x.DownlinkThroughputBps
+	}
+	return nil
+}
+
+func (x *DishGetHistoryResponse) GetUplinkThroughputBps() []float32 {
+	if x != nil {
+		return x.UplinkThroughputBps
+	}
+	return nil
+}
+
+func (x *DishGetHistoryResponse) GetSnr() []float32 {
+	if x != nil {
+		return x.Snr
+	}
+	return nil
+}
+
+func (x *DishGetHistoryResponse) GetScheduled() []bool {
+	if x != nil {
+		return x.Scheduled
+	}
+	return nil
+}
+
+func (x *DishGetHistoryResponse) GetObstructed() []bool {
+	if x != nil {
+		return x.Obstructed
+	}
+	return nil
+}
+
+type DishGetStatusResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	DeviceInfo                 *DeviceInfo           `protobuf:"bytes,1,opt,name=device_info,json=deviceInfo,proto3" json:"device_info,omitempty"`
+	DeviceState                *DeviceState          `protobuf:"bytes,2,opt,name=device_state,json=deviceState,proto3" json:"device_state,omitempty"`
+	State                      DishState             `protobuf:"varint,1006,opt,name=state,proto3,enum=SpaceX.API.Device.DishState" json:"state,omitempty"`
+	Alerts                     *DishAlerts           `protobuf:"bytes,1005,opt,name=alerts,proto3" json:"alerts,omitempty"`
+	Snr                        float32               `protobuf:"fixed32,1001,opt,name=snr,proto3" json:"snr,omitempty"`
+	SecondsToFirstNonemptySlot float32               `protobuf:"fixed32,1002,opt,name=seconds_to_first_nonempty_slot,json=secondsToFirstNonemptySlot,proto3" json:"seconds_to_first_nonempty_slot,omitempty"`
+	PopPingDropRate            float32               `protobuf:"fixed32,1003,opt,name=pop_ping_drop_rate,json=popPingDropRate,proto3" json:"pop_ping_drop_rate,omitempty"`
+	DownlinkThroughputBps      float32               `protobuf:"fixed32,1007,opt,name=downlink_throughput_bps,json=downlinkThroughputBps,proto3" json:"downlink_throughput_bps,omitempty"`
+	UplinkThroughputBps        float32               `protobuf:"fixed32,1008,opt,name=uplink_throughput_bps,json=uplinkThroughputBps,proto3" json:"uplink_throughput_bps,omitempty"`
+	PopPingLatencyMs           float32               `protobuf:"fixed32,1009,opt,name=pop_ping_latency_ms,json=popPingLatencyMs,proto3" json:"pop_ping_latency_ms,omitempty"`
+	ObstructionStats           *DishObstructionStats `protobuf:"bytes,1004,opt,name=obstruction_stats,json=obstructionStats,proto3" json:"obstruction_stats,omitempty"`
+}
+
+func (x *DishGetStatusResponse) Reset() {
+	*x = DishGetStatusResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_dish_proto_msgTypes[3]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DishGetStatusResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DishGetStatusResponse) ProtoMessage() {}
+
+func (x *DishGetStatusResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_dish_proto_msgTypes[3]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DishGetStatusResponse.ProtoReflect.Descriptor instead.
+func (*DishGetStatusResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_dish_proto_rawDescGZIP(), []int{3}
+}
+
+func (x *DishGetStatusResponse) GetDeviceInfo() *DeviceInfo {
+	if x != nil {
+		return x.DeviceInfo
+	}
+	return nil
+}
+
+func (x *DishGetStatusResponse) GetDeviceState() *DeviceState {
+	if x != nil {
+		return x.DeviceState
+	}
+	return nil
+}
+
+func (x *DishGetStatusResponse) GetState() DishState {
+	if x != nil {
+		return x.State
+	}
+	return DishState_UNKNOWN
+}
+
+func (x *DishGetStatusResponse) GetAlerts() *DishAlerts {
+	if x != nil {
+		return x.Alerts
+	}
+	return nil
+}
+
+func (x *DishGetStatusResponse) GetSnr() float32 {
+	if x != nil {
+		return x.Snr
+	}
+	return 0
+}
+
+func (x *DishGetStatusResponse) GetSecondsToFirstNonemptySlot() float32 {
+	if x != nil {
+		return x.SecondsToFirstNonemptySlot
+	}
+	return 0
+}
+
+func (x *DishGetStatusResponse) GetPopPingDropRate() float32 {
+	if x != nil {
+		return x.PopPingDropRate
+	}
+	return 0
+}
+
+func (x *DishGetStatusResponse) GetDownlinkThroughputBps() float32 {
+	if x != nil {
+		return x.DownlinkThroughputBps
+	}
+	return 0
+}
+
+func (x *DishGetStatusResponse) GetUplinkThroughputBps() float32 {
+	if x != nil {
+		return x.UplinkThroughputBps
+	}
+	return 0
+}
+
+func (x *DishGetStatusResponse) GetPopPingLatencyMs() float32 {
+	if x != nil {
+		return x.PopPingLatencyMs
+	}
+	return 0
+}
+
+func (x *DishGetStatusResponse) GetObstructionStats() *DishObstructionStats {
+	if x != nil {
+		return x.ObstructionStats
+	}
+	return nil
+}
+
+type DishAlerts struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	MotorsStuck        bool `protobuf:"varint,1,opt,name=motors_stuck,json=motorsStuck,proto3" json:"motors_stuck,omitempty"`
+	ThermalThrottle    bool `protobuf:"varint,3,opt,name=thermal_throttle,json=thermalThrottle,proto3" json:"thermal_throttle,omitempty"`
+	ThermalShutdown    bool `protobuf:"varint,2,opt,name=thermal_shutdown,json=thermalShutdown,proto3" json:"thermal_shutdown,omitempty"`
+	UnexpectedLocation bool `protobuf:"varint,4,opt,name=unexpected_location,json=unexpectedLocation,proto3" json:"unexpected_location,omitempty"`
+}
+
+func (x *DishAlerts) Reset() {
+	*x = DishAlerts{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_dish_proto_msgTypes[4]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DishAlerts) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DishAlerts) ProtoMessage() {}
+
+func (x *DishAlerts) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_dish_proto_msgTypes[4]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DishAlerts.ProtoReflect.Descriptor instead.
+func (*DishAlerts) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_dish_proto_rawDescGZIP(), []int{4}
+}
+
+func (x *DishAlerts) GetMotorsStuck() bool {
+	if x != nil {
+		return x.MotorsStuck
+	}
+	return false
+}
+
+func (x *DishAlerts) GetThermalThrottle() bool {
+	if x != nil {
+		return x.ThermalThrottle
+	}
+	return false
+}
+
+func (x *DishAlerts) GetThermalShutdown() bool {
+	if x != nil {
+		return x.ThermalShutdown
+	}
+	return false
+}
+
+func (x *DishAlerts) GetUnexpectedLocation() bool {
+	if x != nil {
+		return x.UnexpectedLocation
+	}
+	return false
+}
+
+type DishObstructionStats struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	CurrentlyObstructed        bool      `protobuf:"varint,5,opt,name=currently_obstructed,json=currentlyObstructed,proto3" json:"currently_obstructed,omitempty"`
+	FractionObstructed         float32   `protobuf:"fixed32,1,opt,name=fraction_obstructed,json=fractionObstructed,proto3" json:"fraction_obstructed,omitempty"`
+	Last_24HObstructedS        float32   `protobuf:"fixed32,1006,opt,name=last_24h_obstructed_s,json=last24hObstructedS,proto3" json:"last_24h_obstructed_s,omitempty"`
+	ValidS                     float32   `protobuf:"fixed32,4,opt,name=valid_s,json=validS,proto3" json:"valid_s,omitempty"`
+	WedgeFractionObstructed    []float32 `protobuf:"fixed32,2,rep,packed,name=wedge_fraction_obstructed,json=wedgeFractionObstructed,proto3" json:"wedge_fraction_obstructed,omitempty"`
+	WedgeAbsFractionObstructed []float32 `protobuf:"fixed32,3,rep,packed,name=wedge_abs_fraction_obstructed,json=wedgeAbsFractionObstructed,proto3" json:"wedge_abs_fraction_obstructed,omitempty"`
+}
+
+func (x *DishObstructionStats) Reset() {
+	*x = DishObstructionStats{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_dish_proto_msgTypes[5]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DishObstructionStats) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DishObstructionStats) ProtoMessage() {}
+
+func (x *DishObstructionStats) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_dish_proto_msgTypes[5]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DishObstructionStats.ProtoReflect.Descriptor instead.
+func (*DishObstructionStats) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_dish_proto_rawDescGZIP(), []int{5}
+}
+
+func (x *DishObstructionStats) GetCurrentlyObstructed() bool {
+	if x != nil {
+		return x.CurrentlyObstructed
+	}
+	return false
+}
+
+func (x *DishObstructionStats) GetFractionObstructed() float32 {
+	if x != nil {
+		return x.FractionObstructed
+	}
+	return 0
+}
+
+func (x *DishObstructionStats) GetLast_24HObstructedS() float32 {
+	if x != nil {
+		return x.Last_24HObstructedS
+	}
+	return 0
+}
+
+func (x *DishObstructionStats) GetValidS() float32 {
+	if x != nil {
+		return x.ValidS
+	}
+	return 0
+}
+
+func (x *DishObstructionStats) GetWedgeFractionObstructed() []float32 {
+	if x != nil {
+		return x.WedgeFractionObstructed
+	}
+	return nil
+}
+
+func (x *DishObstructionStats) GetWedgeAbsFractionObstructed() []float32 {
+	if x != nil {
+		return x.WedgeAbsFractionObstructed
+	}
+	return nil
+}
+
+type DishAuthenticateResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Dish *ChallengeResponse `protobuf:"bytes,2,opt,name=dish,proto3" json:"dish,omitempty"`
+}
+
+func (x *DishAuthenticateResponse) Reset() {
+	*x = DishAuthenticateResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_dish_proto_msgTypes[6]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *DishAuthenticateResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*DishAuthenticateResponse) ProtoMessage() {}
+
+func (x *DishAuthenticateResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_dish_proto_msgTypes[6]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use DishAuthenticateResponse.ProtoReflect.Descriptor instead.
+func (*DishAuthenticateResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_dish_proto_rawDescGZIP(), []int{6}
+}
+
+func (x *DishAuthenticateResponse) GetDish() *ChallengeResponse {
+	if x != nil {
+		return x.Dish
+	}
+	return nil
+}
+
+var File_spacex_api_device_dish_proto protoreflect.FileDescriptor
+
+var file_spacex_api_device_dish_proto_rawDesc = []byte{
+	0x0a, 0x1c, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2f, 0x64, 0x69, 0x73, 0x68, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x11,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x1a, 0x1e, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x6f, 0x6e, 0x2e, 0x70, 0x72, 0x6f, 0x74,
+	0x6f, 0x22, 0x11, 0x0a, 0x0f, 0x44, 0x69, 0x73, 0x68, 0x53, 0x74, 0x6f, 0x77, 0x52, 0x65, 0x71,
+	0x75, 0x65, 0x73, 0x74, 0x22, 0x12, 0x0a, 0x10, 0x44, 0x69, 0x73, 0x68, 0x53, 0x74, 0x6f, 0x77,
+	0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0xd1, 0x02, 0x0a, 0x16, 0x44, 0x69, 0x73,
+	0x68, 0x47, 0x65, 0x74, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x63, 0x75, 0x72, 0x72, 0x65, 0x6e, 0x74, 0x18, 0x01,
+	0x20, 0x01, 0x28, 0x04, 0x52, 0x07, 0x63, 0x75, 0x72, 0x72, 0x65, 0x6e, 0x74, 0x12, 0x2c, 0x0a,
+	0x12, 0x70, 0x6f, 0x70, 0x5f, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x64, 0x72, 0x6f, 0x70, 0x5f, 0x72,
+	0x61, 0x74, 0x65, 0x18, 0xe9, 0x07, 0x20, 0x03, 0x28, 0x02, 0x52, 0x0f, 0x70, 0x6f, 0x70, 0x50,
+	0x69, 0x6e, 0x67, 0x44, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74, 0x65, 0x12, 0x2e, 0x0a, 0x13, 0x70,
+	0x6f, 0x70, 0x5f, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x5f,
+	0x6d, 0x73, 0x18, 0xea, 0x07, 0x20, 0x03, 0x28, 0x02, 0x52, 0x10, 0x70, 0x6f, 0x70, 0x50, 0x69,
+	0x6e, 0x67, 0x4c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x4d, 0x73, 0x12, 0x37, 0x0a, 0x17, 0x64,
+	0x6f, 0x77, 0x6e, 0x6c, 0x69, 0x6e, 0x6b, 0x5f, 0x74, 0x68, 0x72, 0x6f, 0x75, 0x67, 0x68, 0x70,
+	0x75, 0x74, 0x5f, 0x62, 0x70, 0x73, 0x18, 0xeb, 0x07, 0x20, 0x03, 0x28, 0x02, 0x52, 0x15, 0x64,
+	0x6f, 0x77, 0x6e, 0x6c, 0x69, 0x6e, 0x6b, 0x54, 0x68, 0x72, 0x6f, 0x75, 0x67, 0x68, 0x70, 0x75,
+	0x74, 0x42, 0x70, 0x73, 0x12, 0x33, 0x0a, 0x15, 0x75, 0x70, 0x6c, 0x69, 0x6e, 0x6b, 0x5f, 0x74,
+	0x68, 0x72, 0x6f, 0x75, 0x67, 0x68, 0x70, 0x75, 0x74, 0x5f, 0x62, 0x70, 0x73, 0x18, 0xec, 0x07,
+	0x20, 0x03, 0x28, 0x02, 0x52, 0x13, 0x75, 0x70, 0x6c, 0x69, 0x6e, 0x6b, 0x54, 0x68, 0x72, 0x6f,
+	0x75, 0x67, 0x68, 0x70, 0x75, 0x74, 0x42, 0x70, 0x73, 0x12, 0x11, 0x0a, 0x03, 0x73, 0x6e, 0x72,
+	0x18, 0xed, 0x07, 0x20, 0x03, 0x28, 0x02, 0x52, 0x03, 0x73, 0x6e, 0x72, 0x12, 0x1d, 0x0a, 0x09,
+	0x73, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x64, 0x18, 0xee, 0x07, 0x20, 0x03, 0x28, 0x08,
+	0x52, 0x09, 0x73, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x64, 0x12, 0x1f, 0x0a, 0x0a, 0x6f,
+	0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65, 0x64, 0x18, 0xef, 0x07, 0x20, 0x03, 0x28, 0x08,
+	0x52, 0x0a, 0x6f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65, 0x64, 0x22, 0x82, 0x05, 0x0a,
+	0x15, 0x44, 0x69, 0x73, 0x68, 0x47, 0x65, 0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x3e, 0x0a, 0x0b, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x5f, 0x69, 0x6e, 0x66, 0x6f, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70,
+	0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e,
+	0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x52, 0x0a, 0x64, 0x65, 0x76, 0x69,
+	0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x12, 0x41, 0x0a, 0x0c, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x5f, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x53,
+	0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52, 0x0b, 0x64, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x33, 0x0a, 0x05, 0x73, 0x74, 0x61,
+	0x74, 0x65, 0x18, 0xee, 0x07, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x1c, 0x2e, 0x53, 0x70, 0x61, 0x63,
+	0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x44, 0x69,
+	0x73, 0x68, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x12, 0x36,
+	0x0a, 0x06, 0x61, 0x6c, 0x65, 0x72, 0x74, 0x73, 0x18, 0xed, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32,
+	0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2e, 0x44, 0x69, 0x73, 0x68, 0x41, 0x6c, 0x65, 0x72, 0x74, 0x73, 0x52, 0x06,
+	0x61, 0x6c, 0x65, 0x72, 0x74, 0x73, 0x12, 0x11, 0x0a, 0x03, 0x73, 0x6e, 0x72, 0x18, 0xe9, 0x07,
+	0x20, 0x01, 0x28, 0x02, 0x52, 0x03, 0x73, 0x6e, 0x72, 0x12, 0x43, 0x0a, 0x1e, 0x73, 0x65, 0x63,
+	0x6f, 0x6e, 0x64, 0x73, 0x5f, 0x74, 0x6f, 0x5f, 0x66, 0x69, 0x72, 0x73, 0x74, 0x5f, 0x6e, 0x6f,
+	0x6e, 0x65, 0x6d, 0x70, 0x74, 0x79, 0x5f, 0x73, 0x6c, 0x6f, 0x74, 0x18, 0xea, 0x07, 0x20, 0x01,
+	0x28, 0x02, 0x52, 0x1a, 0x73, 0x65, 0x63, 0x6f, 0x6e, 0x64, 0x73, 0x54, 0x6f, 0x46, 0x69, 0x72,
+	0x73, 0x74, 0x4e, 0x6f, 0x6e, 0x65, 0x6d, 0x70, 0x74, 0x79, 0x53, 0x6c, 0x6f, 0x74, 0x12, 0x2c,
+	0x0a, 0x12, 0x70, 0x6f, 0x70, 0x5f, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x64, 0x72, 0x6f, 0x70, 0x5f,
+	0x72, 0x61, 0x74, 0x65, 0x18, 0xeb, 0x07, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0f, 0x70, 0x6f, 0x70,
+	0x50, 0x69, 0x6e, 0x67, 0x44, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74, 0x65, 0x12, 0x37, 0x0a, 0x17,
+	0x64, 0x6f, 0x77, 0x6e, 0x6c, 0x69, 0x6e, 0x6b, 0x5f, 0x74, 0x68, 0x72, 0x6f, 0x75, 0x67, 0x68,
+	0x70, 0x75, 0x74, 0x5f, 0x62, 0x70, 0x73, 0x18, 0xef, 0x07, 0x20, 0x01, 0x28, 0x02, 0x52, 0x15,
+	0x64, 0x6f, 0x77, 0x6e, 0x6c, 0x69, 0x6e, 0x6b, 0x54, 0x68, 0x72, 0x6f, 0x75, 0x67, 0x68, 0x70,
+	0x75, 0x74, 0x42, 0x70, 0x73, 0x12, 0x33, 0x0a, 0x15, 0x75, 0x70, 0x6c, 0x69, 0x6e, 0x6b, 0x5f,
+	0x74, 0x68, 0x72, 0x6f, 0x75, 0x67, 0x68, 0x70, 0x75, 0x74, 0x5f, 0x62, 0x70, 0x73, 0x18, 0xf0,
+	0x07, 0x20, 0x01, 0x28, 0x02, 0x52, 0x13, 0x75, 0x70, 0x6c, 0x69, 0x6e, 0x6b, 0x54, 0x68, 0x72,
+	0x6f, 0x75, 0x67, 0x68, 0x70, 0x75, 0x74, 0x42, 0x70, 0x73, 0x12, 0x2e, 0x0a, 0x13, 0x70, 0x6f,
+	0x70, 0x5f, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x5f, 0x6d,
+	0x73, 0x18, 0xf1, 0x07, 0x20, 0x01, 0x28, 0x02, 0x52, 0x10, 0x70, 0x6f, 0x70, 0x50, 0x69, 0x6e,
+	0x67, 0x4c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x4d, 0x73, 0x12, 0x55, 0x0a, 0x11, 0x6f, 0x62,
+	0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x73, 0x18,
+	0xec, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x27, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e,
+	0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x44, 0x69, 0x73, 0x68, 0x4f,
+	0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x53, 0x74, 0x61, 0x74, 0x73, 0x52,
+	0x10, 0x6f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x53, 0x74, 0x61, 0x74,
+	0x73, 0x22, 0xb6, 0x01, 0x0a, 0x0a, 0x44, 0x69, 0x73, 0x68, 0x41, 0x6c, 0x65, 0x72, 0x74, 0x73,
+	0x12, 0x21, 0x0a, 0x0c, 0x6d, 0x6f, 0x74, 0x6f, 0x72, 0x73, 0x5f, 0x73, 0x74, 0x75, 0x63, 0x6b,
+	0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0b, 0x6d, 0x6f, 0x74, 0x6f, 0x72, 0x73, 0x53, 0x74,
+	0x75, 0x63, 0x6b, 0x12, 0x29, 0x0a, 0x10, 0x74, 0x68, 0x65, 0x72, 0x6d, 0x61, 0x6c, 0x5f, 0x74,
+	0x68, 0x72, 0x6f, 0x74, 0x74, 0x6c, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0f, 0x74,
+	0x68, 0x65, 0x72, 0x6d, 0x61, 0x6c, 0x54, 0x68, 0x72, 0x6f, 0x74, 0x74, 0x6c, 0x65, 0x12, 0x29,
+	0x0a, 0x10, 0x74, 0x68, 0x65, 0x72, 0x6d, 0x61, 0x6c, 0x5f, 0x73, 0x68, 0x75, 0x74, 0x64, 0x6f,
+	0x77, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0f, 0x74, 0x68, 0x65, 0x72, 0x6d, 0x61,
+	0x6c, 0x53, 0x68, 0x75, 0x74, 0x64, 0x6f, 0x77, 0x6e, 0x12, 0x2f, 0x0a, 0x13, 0x75, 0x6e, 0x65,
+	0x78, 0x70, 0x65, 0x63, 0x74, 0x65, 0x64, 0x5f, 0x6c, 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e,
+	0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x52, 0x12, 0x75, 0x6e, 0x65, 0x78, 0x70, 0x65, 0x63, 0x74,
+	0x65, 0x64, 0x4c, 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0xc6, 0x02, 0x0a, 0x14, 0x44,
+	0x69, 0x73, 0x68, 0x4f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x53, 0x74,
+	0x61, 0x74, 0x73, 0x12, 0x31, 0x0a, 0x14, 0x63, 0x75, 0x72, 0x72, 0x65, 0x6e, 0x74, 0x6c, 0x79,
+	0x5f, 0x6f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65, 0x64, 0x18, 0x05, 0x20, 0x01, 0x28,
+	0x08, 0x52, 0x13, 0x63, 0x75, 0x72, 0x72, 0x65, 0x6e, 0x74, 0x6c, 0x79, 0x4f, 0x62, 0x73, 0x74,
+	0x72, 0x75, 0x63, 0x74, 0x65, 0x64, 0x12, 0x2f, 0x0a, 0x13, 0x66, 0x72, 0x61, 0x63, 0x74, 0x69,
+	0x6f, 0x6e, 0x5f, 0x6f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65, 0x64, 0x18, 0x01, 0x20,
+	0x01, 0x28, 0x02, 0x52, 0x12, 0x66, 0x72, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x4f, 0x62, 0x73,
+	0x74, 0x72, 0x75, 0x63, 0x74, 0x65, 0x64, 0x12, 0x32, 0x0a, 0x15, 0x6c, 0x61, 0x73, 0x74, 0x5f,
+	0x32, 0x34, 0x68, 0x5f, 0x6f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65, 0x64, 0x5f, 0x73,
+	0x18, 0xee, 0x07, 0x20, 0x01, 0x28, 0x02, 0x52, 0x12, 0x6c, 0x61, 0x73, 0x74, 0x32, 0x34, 0x68,
+	0x4f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65, 0x64, 0x53, 0x12, 0x17, 0x0a, 0x07, 0x76,
+	0x61, 0x6c, 0x69, 0x64, 0x5f, 0x73, 0x18, 0x04, 0x20, 0x01, 0x28, 0x02, 0x52, 0x06, 0x76, 0x61,
+	0x6c, 0x69, 0x64, 0x53, 0x12, 0x3a, 0x0a, 0x19, 0x77, 0x65, 0x64, 0x67, 0x65, 0x5f, 0x66, 0x72,
+	0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x6f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65,
+	0x64, 0x18, 0x02, 0x20, 0x03, 0x28, 0x02, 0x52, 0x17, 0x77, 0x65, 0x64, 0x67, 0x65, 0x46, 0x72,
+	0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x4f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65, 0x64,
+	0x12, 0x41, 0x0a, 0x1d, 0x77, 0x65, 0x64, 0x67, 0x65, 0x5f, 0x61, 0x62, 0x73, 0x5f, 0x66, 0x72,
+	0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x6f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x65,
+	0x64, 0x18, 0x03, 0x20, 0x03, 0x28, 0x02, 0x52, 0x1a, 0x77, 0x65, 0x64, 0x67, 0x65, 0x41, 0x62,
+	0x73, 0x46, 0x72, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x4f, 0x62, 0x73, 0x74, 0x72, 0x75, 0x63,
+	0x74, 0x65, 0x64, 0x22, 0x54, 0x0a, 0x18, 0x44, 0x69, 0x73, 0x68, 0x41, 0x75, 0x74, 0x68, 0x65,
+	0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12,
+	0x38, 0x0a, 0x04, 0x64, 0x69, 0x73, 0x68, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x43, 0x68, 0x61, 0x6c, 0x6c, 0x65, 0x6e, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x52, 0x04, 0x64, 0x69, 0x73, 0x68, 0x2a, 0x43, 0x0a, 0x09, 0x44, 0x69, 0x73,
+	0x68, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x0b, 0x0a, 0x07, 0x55, 0x4e, 0x4b, 0x4e, 0x4f, 0x57,
+	0x4e, 0x10, 0x00, 0x12, 0x0d, 0x0a, 0x09, 0x43, 0x4f, 0x4e, 0x4e, 0x45, 0x43, 0x54, 0x45, 0x44,
+	0x10, 0x01, 0x12, 0x0d, 0x0a, 0x09, 0x53, 0x45, 0x41, 0x52, 0x43, 0x48, 0x49, 0x4e, 0x47, 0x10,
+	0x02, 0x12, 0x0b, 0x0a, 0x07, 0x42, 0x4f, 0x4f, 0x54, 0x49, 0x4e, 0x47, 0x10, 0x03, 0x42, 0x17,
+	0x5a, 0x15, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x61, 0x70, 0x69,
+	0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
+}
+
+var (
+	file_spacex_api_device_dish_proto_rawDescOnce sync.Once
+	file_spacex_api_device_dish_proto_rawDescData = file_spacex_api_device_dish_proto_rawDesc
+)
+
+func file_spacex_api_device_dish_proto_rawDescGZIP() []byte {
+	file_spacex_api_device_dish_proto_rawDescOnce.Do(func() {
+		file_spacex_api_device_dish_proto_rawDescData = protoimpl.X.CompressGZIP(file_spacex_api_device_dish_proto_rawDescData)
+	})
+	return file_spacex_api_device_dish_proto_rawDescData
+}
+
+var file_spacex_api_device_dish_proto_enumTypes = make([]protoimpl.EnumInfo, 1)
+var file_spacex_api_device_dish_proto_msgTypes = make([]protoimpl.MessageInfo, 7)
+var file_spacex_api_device_dish_proto_goTypes = []interface{}{
+	(DishState)(0),                   // 0: SpaceX.API.Device.DishState
+	(*DishStowRequest)(nil),          // 1: SpaceX.API.Device.DishStowRequest
+	(*DishStowResponse)(nil),         // 2: SpaceX.API.Device.DishStowResponse
+	(*DishGetHistoryResponse)(nil),   // 3: SpaceX.API.Device.DishGetHistoryResponse
+	(*DishGetStatusResponse)(nil),    // 4: SpaceX.API.Device.DishGetStatusResponse
+	(*DishAlerts)(nil),               // 5: SpaceX.API.Device.DishAlerts
+	(*DishObstructionStats)(nil),     // 6: SpaceX.API.Device.DishObstructionStats
+	(*DishAuthenticateResponse)(nil), // 7: SpaceX.API.Device.DishAuthenticateResponse
+	(*DeviceInfo)(nil),               // 8: SpaceX.API.Device.DeviceInfo
+	(*DeviceState)(nil),              // 9: SpaceX.API.Device.DeviceState
+	(*ChallengeResponse)(nil),        // 10: SpaceX.API.Device.ChallengeResponse
+}
+var file_spacex_api_device_dish_proto_depIdxs = []int32{
+	8,  // 0: SpaceX.API.Device.DishGetStatusResponse.device_info:type_name -> SpaceX.API.Device.DeviceInfo
+	9,  // 1: SpaceX.API.Device.DishGetStatusResponse.device_state:type_name -> SpaceX.API.Device.DeviceState
+	0,  // 2: SpaceX.API.Device.DishGetStatusResponse.state:type_name -> SpaceX.API.Device.DishState
+	5,  // 3: SpaceX.API.Device.DishGetStatusResponse.alerts:type_name -> SpaceX.API.Device.DishAlerts
+	6,  // 4: SpaceX.API.Device.DishGetStatusResponse.obstruction_stats:type_name -> SpaceX.API.Device.DishObstructionStats
+	10, // 5: SpaceX.API.Device.DishAuthenticateResponse.dish:type_name -> SpaceX.API.Device.ChallengeResponse
+	6,  // [6:6] is the sub-list for method output_type
+	6,  // [6:6] is the sub-list for method input_type
+	6,  // [6:6] is the sub-list for extension type_name
+	6,  // [6:6] is the sub-list for extension extendee
+	0,  // [0:6] is the sub-list for field type_name
+}
+
+func init() { file_spacex_api_device_dish_proto_init() }
+func file_spacex_api_device_dish_proto_init() {
+	if File_spacex_api_device_dish_proto != nil {
+		return
+	}
+	file_spacex_api_device_common_proto_init()
+	if !protoimpl.UnsafeEnabled {
+		file_spacex_api_device_dish_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DishStowRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_dish_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DishStowResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_dish_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DishGetHistoryResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_dish_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DishGetStatusResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_dish_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DishAlerts); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_dish_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DishObstructionStats); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_dish_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*DishAuthenticateResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+	}
+	type x struct{}
+	out := protoimpl.TypeBuilder{
+		File: protoimpl.DescBuilder{
+			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+			RawDescriptor: file_spacex_api_device_dish_proto_rawDesc,
+			NumEnums:      1,
+			NumMessages:   7,
+			NumExtensions: 0,
+			NumServices:   0,
+		},
+		GoTypes:           file_spacex_api_device_dish_proto_goTypes,
+		DependencyIndexes: file_spacex_api_device_dish_proto_depIdxs,
+		EnumInfos:         file_spacex_api_device_dish_proto_enumTypes,
+		MessageInfos:      file_spacex_api_device_dish_proto_msgTypes,
+	}.Build()
+	File_spacex_api_device_dish_proto = out.File
+	file_spacex_api_device_dish_proto_rawDesc = nil
+	file_spacex_api_device_dish_proto_goTypes = nil
+	file_spacex_api_device_dish_proto_depIdxs = nil
+}
blob - /dev/null
blob + ca19d45aaaada0254671421c2861689090cff33c (mode 644)
--- /dev/null
+++ device/transceiver.pb.go
@@ -0,0 +1,728 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// 	protoc-gen-go v1.28.1
+// 	protoc        v3.21.6
+// source: spacex/api/device/transceiver.proto
+
+package device
+
+import (
+	protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+	protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+	reflect "reflect"
+	sync "sync"
+)
+
+const (
+	// Verify that this generated code is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+	// Verify that runtime/protoimpl is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+type TransceiverModulatorState int32
+
+const (
+	TransceiverModulatorState_MODSTATE_UNKNOWN  TransceiverModulatorState = 0
+	TransceiverModulatorState_MODSTATE_ENABLED  TransceiverModulatorState = 1
+	TransceiverModulatorState_MODSTATE_DISABLED TransceiverModulatorState = 2
+)
+
+// Enum value maps for TransceiverModulatorState.
+var (
+	TransceiverModulatorState_name = map[int32]string{
+		0: "MODSTATE_UNKNOWN",
+		1: "MODSTATE_ENABLED",
+		2: "MODSTATE_DISABLED",
+	}
+	TransceiverModulatorState_value = map[string]int32{
+		"MODSTATE_UNKNOWN":  0,
+		"MODSTATE_ENABLED":  1,
+		"MODSTATE_DISABLED": 2,
+	}
+)
+
+func (x TransceiverModulatorState) Enum() *TransceiverModulatorState {
+	p := new(TransceiverModulatorState)
+	*p = x
+	return p
+}
+
+func (x TransceiverModulatorState) String() string {
+	return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (TransceiverModulatorState) Descriptor() protoreflect.EnumDescriptor {
+	return file_spacex_api_device_transceiver_proto_enumTypes[0].Descriptor()
+}
+
+func (TransceiverModulatorState) Type() protoreflect.EnumType {
+	return &file_spacex_api_device_transceiver_proto_enumTypes[0]
+}
+
+func (x TransceiverModulatorState) Number() protoreflect.EnumNumber {
+	return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use TransceiverModulatorState.Descriptor instead.
+func (TransceiverModulatorState) EnumDescriptor() ([]byte, []int) {
+	return file_spacex_api_device_transceiver_proto_rawDescGZIP(), []int{0}
+}
+
+type TransceiverTxRxState int32
+
+const (
+	TransceiverTxRxState_TXRX_UNKNOWN  TransceiverTxRxState = 0
+	TransceiverTxRxState_TXRX_ENABLED  TransceiverTxRxState = 1
+	TransceiverTxRxState_TXRX_DISABLED TransceiverTxRxState = 2
+)
+
+// Enum value maps for TransceiverTxRxState.
+var (
+	TransceiverTxRxState_name = map[int32]string{
+		0: "TXRX_UNKNOWN",
+		1: "TXRX_ENABLED",
+		2: "TXRX_DISABLED",
+	}
+	TransceiverTxRxState_value = map[string]int32{
+		"TXRX_UNKNOWN":  0,
+		"TXRX_ENABLED":  1,
+		"TXRX_DISABLED": 2,
+	}
+)
+
+func (x TransceiverTxRxState) Enum() *TransceiverTxRxState {
+	p := new(TransceiverTxRxState)
+	*p = x
+	return p
+}
+
+func (x TransceiverTxRxState) String() string {
+	return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (TransceiverTxRxState) Descriptor() protoreflect.EnumDescriptor {
+	return file_spacex_api_device_transceiver_proto_enumTypes[1].Descriptor()
+}
+
+func (TransceiverTxRxState) Type() protoreflect.EnumType {
+	return &file_spacex_api_device_transceiver_proto_enumTypes[1]
+}
+
+func (x TransceiverTxRxState) Number() protoreflect.EnumNumber {
+	return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use TransceiverTxRxState.Descriptor instead.
+func (TransceiverTxRxState) EnumDescriptor() ([]byte, []int) {
+	return file_spacex_api_device_transceiver_proto_rawDescGZIP(), []int{1}
+}
+
+type TransceiverTransmitBlankingState int32
+
+const (
+	TransceiverTransmitBlankingState_TB_UNKNOWN  TransceiverTransmitBlankingState = 0
+	TransceiverTransmitBlankingState_TB_ENABLED  TransceiverTransmitBlankingState = 1
+	TransceiverTransmitBlankingState_TB_DISABLED TransceiverTransmitBlankingState = 2
+)
+
+// Enum value maps for TransceiverTransmitBlankingState.
+var (
+	TransceiverTransmitBlankingState_name = map[int32]string{
+		0: "TB_UNKNOWN",
+		1: "TB_ENABLED",
+		2: "TB_DISABLED",
+	}
+	TransceiverTransmitBlankingState_value = map[string]int32{
+		"TB_UNKNOWN":  0,
+		"TB_ENABLED":  1,
+		"TB_DISABLED": 2,
+	}
+)
+
+func (x TransceiverTransmitBlankingState) Enum() *TransceiverTransmitBlankingState {
+	p := new(TransceiverTransmitBlankingState)
+	*p = x
+	return p
+}
+
+func (x TransceiverTransmitBlankingState) String() string {
+	return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (TransceiverTransmitBlankingState) Descriptor() protoreflect.EnumDescriptor {
+	return file_spacex_api_device_transceiver_proto_enumTypes[2].Descriptor()
+}
+
+func (TransceiverTransmitBlankingState) Type() protoreflect.EnumType {
+	return &file_spacex_api_device_transceiver_proto_enumTypes[2]
+}
+
+func (x TransceiverTransmitBlankingState) Number() protoreflect.EnumNumber {
+	return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use TransceiverTransmitBlankingState.Descriptor instead.
+func (TransceiverTransmitBlankingState) EnumDescriptor() ([]byte, []int) {
+	return file_spacex_api_device_transceiver_proto_rawDescGZIP(), []int{2}
+}
+
+type TransceiverIFLoopbackTestRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	EnableIfLoopback bool `protobuf:"varint,1,opt,name=enable_if_loopback,json=enableIfLoopback,proto3" json:"enable_if_loopback,omitempty"`
+}
+
+func (x *TransceiverIFLoopbackTestRequest) Reset() {
+	*x = TransceiverIFLoopbackTestRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_transceiver_proto_msgTypes[0]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *TransceiverIFLoopbackTestRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*TransceiverIFLoopbackTestRequest) ProtoMessage() {}
+
+func (x *TransceiverIFLoopbackTestRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_transceiver_proto_msgTypes[0]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use TransceiverIFLoopbackTestRequest.ProtoReflect.Descriptor instead.
+func (*TransceiverIFLoopbackTestRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_transceiver_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *TransceiverIFLoopbackTestRequest) GetEnableIfLoopback() bool {
+	if x != nil {
+		return x.EnableIfLoopback
+	}
+	return false
+}
+
+type TransceiverIFLoopbackTestResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	BerLoopbackTest  float32 `protobuf:"fixed32,1,opt,name=ber_loopback_test,json=berLoopbackTest,proto3" json:"ber_loopback_test,omitempty"`
+	SnrLoopbackTest  float32 `protobuf:"fixed32,2,opt,name=snr_loopback_test,json=snrLoopbackTest,proto3" json:"snr_loopback_test,omitempty"`
+	RssiLoopbackTest float32 `protobuf:"fixed32,3,opt,name=rssi_loopback_test,json=rssiLoopbackTest,proto3" json:"rssi_loopback_test,omitempty"`
+	PllLock          bool    `protobuf:"varint,4,opt,name=pll_lock,json=pllLock,proto3" json:"pll_lock,omitempty"`
+}
+
+func (x *TransceiverIFLoopbackTestResponse) Reset() {
+	*x = TransceiverIFLoopbackTestResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_transceiver_proto_msgTypes[1]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *TransceiverIFLoopbackTestResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*TransceiverIFLoopbackTestResponse) ProtoMessage() {}
+
+func (x *TransceiverIFLoopbackTestResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_transceiver_proto_msgTypes[1]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use TransceiverIFLoopbackTestResponse.ProtoReflect.Descriptor instead.
+func (*TransceiverIFLoopbackTestResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_transceiver_proto_rawDescGZIP(), []int{1}
+}
+
+func (x *TransceiverIFLoopbackTestResponse) GetBerLoopbackTest() float32 {
+	if x != nil {
+		return x.BerLoopbackTest
+	}
+	return 0
+}
+
+func (x *TransceiverIFLoopbackTestResponse) GetSnrLoopbackTest() float32 {
+	if x != nil {
+		return x.SnrLoopbackTest
+	}
+	return 0
+}
+
+func (x *TransceiverIFLoopbackTestResponse) GetRssiLoopbackTest() float32 {
+	if x != nil {
+		return x.RssiLoopbackTest
+	}
+	return 0
+}
+
+func (x *TransceiverIFLoopbackTestResponse) GetPllLock() bool {
+	if x != nil {
+		return x.PllLock
+	}
+	return false
+}
+
+type TransceiverGetStatusRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *TransceiverGetStatusRequest) Reset() {
+	*x = TransceiverGetStatusRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_transceiver_proto_msgTypes[2]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *TransceiverGetStatusRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*TransceiverGetStatusRequest) ProtoMessage() {}
+
+func (x *TransceiverGetStatusRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_transceiver_proto_msgTypes[2]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use TransceiverGetStatusRequest.ProtoReflect.Descriptor instead.
+func (*TransceiverGetStatusRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_transceiver_proto_rawDescGZIP(), []int{2}
+}
+
+type TransceiverGetStatusResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	ModState              TransceiverModulatorState        `protobuf:"varint,1,opt,name=mod_state,json=modState,proto3,enum=SpaceX.API.Device.TransceiverModulatorState" json:"mod_state,omitempty"`
+	DemodState            TransceiverModulatorState        `protobuf:"varint,2,opt,name=demod_state,json=demodState,proto3,enum=SpaceX.API.Device.TransceiverModulatorState" json:"demod_state,omitempty"`
+	TxState               TransceiverTxRxState             `protobuf:"varint,3,opt,name=tx_state,json=txState,proto3,enum=SpaceX.API.Device.TransceiverTxRxState" json:"tx_state,omitempty"`
+	RxState               TransceiverTxRxState             `protobuf:"varint,4,opt,name=rx_state,json=rxState,proto3,enum=SpaceX.API.Device.TransceiverTxRxState" json:"rx_state,omitempty"`
+	State                 DishState                        `protobuf:"varint,1006,opt,name=state,proto3,enum=SpaceX.API.Device.DishState" json:"state,omitempty"`
+	Faults                *TransceiverFaults               `protobuf:"bytes,1007,opt,name=faults,proto3" json:"faults,omitempty"`
+	TransmitBlankingState TransceiverTransmitBlankingState `protobuf:"varint,1008,opt,name=transmit_blanking_state,json=transmitBlankingState,proto3,enum=SpaceX.API.Device.TransceiverTransmitBlankingState" json:"transmit_blanking_state,omitempty"`
+	ModemAsicTemp         float32                          `protobuf:"fixed32,1009,opt,name=modem_asic_temp,json=modemAsicTemp,proto3" json:"modem_asic_temp,omitempty"`
+	TxIfTemp              float32                          `protobuf:"fixed32,1010,opt,name=tx_if_temp,json=txIfTemp,proto3" json:"tx_if_temp,omitempty"`
+}
+
+func (x *TransceiverGetStatusResponse) Reset() {
+	*x = TransceiverGetStatusResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_transceiver_proto_msgTypes[3]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *TransceiverGetStatusResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*TransceiverGetStatusResponse) ProtoMessage() {}
+
+func (x *TransceiverGetStatusResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_transceiver_proto_msgTypes[3]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use TransceiverGetStatusResponse.ProtoReflect.Descriptor instead.
+func (*TransceiverGetStatusResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_transceiver_proto_rawDescGZIP(), []int{3}
+}
+
+func (x *TransceiverGetStatusResponse) GetModState() TransceiverModulatorState {
+	if x != nil {
+		return x.ModState
+	}
+	return TransceiverModulatorState_MODSTATE_UNKNOWN
+}
+
+func (x *TransceiverGetStatusResponse) GetDemodState() TransceiverModulatorState {
+	if x != nil {
+		return x.DemodState
+	}
+	return TransceiverModulatorState_MODSTATE_UNKNOWN
+}
+
+func (x *TransceiverGetStatusResponse) GetTxState() TransceiverTxRxState {
+	if x != nil {
+		return x.TxState
+	}
+	return TransceiverTxRxState_TXRX_UNKNOWN
+}
+
+func (x *TransceiverGetStatusResponse) GetRxState() TransceiverTxRxState {
+	if x != nil {
+		return x.RxState
+	}
+	return TransceiverTxRxState_TXRX_UNKNOWN
+}
+
+func (x *TransceiverGetStatusResponse) GetState() DishState {
+	if x != nil {
+		return x.State
+	}
+	return DishState_UNKNOWN
+}
+
+func (x *TransceiverGetStatusResponse) GetFaults() *TransceiverFaults {
+	if x != nil {
+		return x.Faults
+	}
+	return nil
+}
+
+func (x *TransceiverGetStatusResponse) GetTransmitBlankingState() TransceiverTransmitBlankingState {
+	if x != nil {
+		return x.TransmitBlankingState
+	}
+	return TransceiverTransmitBlankingState_TB_UNKNOWN
+}
+
+func (x *TransceiverGetStatusResponse) GetModemAsicTemp() float32 {
+	if x != nil {
+		return x.ModemAsicTemp
+	}
+	return 0
+}
+
+func (x *TransceiverGetStatusResponse) GetTxIfTemp() float32 {
+	if x != nil {
+		return x.TxIfTemp
+	}
+	return 0
+}
+
+type TransceiverFaults struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	OverTempModemAsicFault bool `protobuf:"varint,1,opt,name=over_temp_modem_asic_fault,json=overTempModemAsicFault,proto3" json:"over_temp_modem_asic_fault,omitempty"`
+	OverTempPcbaFault      bool `protobuf:"varint,2,opt,name=over_temp_pcba_fault,json=overTempPcbaFault,proto3" json:"over_temp_pcba_fault,omitempty"`
+	DcVoltageFault         bool `protobuf:"varint,3,opt,name=dc_voltage_fault,json=dcVoltageFault,proto3" json:"dc_voltage_fault,omitempty"`
+}
+
+func (x *TransceiverFaults) Reset() {
+	*x = TransceiverFaults{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_transceiver_proto_msgTypes[4]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *TransceiverFaults) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*TransceiverFaults) ProtoMessage() {}
+
+func (x *TransceiverFaults) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_transceiver_proto_msgTypes[4]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use TransceiverFaults.ProtoReflect.Descriptor instead.
+func (*TransceiverFaults) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_transceiver_proto_rawDescGZIP(), []int{4}
+}
+
+func (x *TransceiverFaults) GetOverTempModemAsicFault() bool {
+	if x != nil {
+		return x.OverTempModemAsicFault
+	}
+	return false
+}
+
+func (x *TransceiverFaults) GetOverTempPcbaFault() bool {
+	if x != nil {
+		return x.OverTempPcbaFault
+	}
+	return false
+}
+
+func (x *TransceiverFaults) GetDcVoltageFault() bool {
+	if x != nil {
+		return x.DcVoltageFault
+	}
+	return false
+}
+
+var File_spacex_api_device_transceiver_proto protoreflect.FileDescriptor
+
+var file_spacex_api_device_transceiver_proto_rawDesc = []byte{
+	0x0a, 0x23, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2f, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x2e,
+	0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x11, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x1a, 0x1e, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78,
+	0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2f, 0x63, 0x6f, 0x6d, 0x6d,
+	0x6f, 0x6e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1c, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78,
+	0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2f, 0x64, 0x69, 0x73, 0x68,
+	0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0x50, 0x0a, 0x20, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x63,
+	0x65, 0x69, 0x76, 0x65, 0x72, 0x49, 0x46, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x54,
+	0x65, 0x73, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x2c, 0x0a, 0x12, 0x65, 0x6e,
+	0x61, 0x62, 0x6c, 0x65, 0x5f, 0x69, 0x66, 0x5f, 0x6c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b,
+	0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x10, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x49, 0x66,
+	0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x22, 0xc4, 0x01, 0x0a, 0x21, 0x54, 0x72, 0x61,
+	0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x49, 0x46, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61,
+	0x63, 0x6b, 0x54, 0x65, 0x73, 0x74, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x2a,
+	0x0a, 0x11, 0x62, 0x65, 0x72, 0x5f, 0x6c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x5f, 0x74,
+	0x65, 0x73, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0f, 0x62, 0x65, 0x72, 0x4c, 0x6f,
+	0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x54, 0x65, 0x73, 0x74, 0x12, 0x2a, 0x0a, 0x11, 0x73, 0x6e,
+	0x72, 0x5f, 0x6c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x5f, 0x74, 0x65, 0x73, 0x74, 0x18,
+	0x02, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0f, 0x73, 0x6e, 0x72, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61,
+	0x63, 0x6b, 0x54, 0x65, 0x73, 0x74, 0x12, 0x2c, 0x0a, 0x12, 0x72, 0x73, 0x73, 0x69, 0x5f, 0x6c,
+	0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b, 0x5f, 0x74, 0x65, 0x73, 0x74, 0x18, 0x03, 0x20, 0x01,
+	0x28, 0x02, 0x52, 0x10, 0x72, 0x73, 0x73, 0x69, 0x4c, 0x6f, 0x6f, 0x70, 0x62, 0x61, 0x63, 0x6b,
+	0x54, 0x65, 0x73, 0x74, 0x12, 0x19, 0x0a, 0x08, 0x70, 0x6c, 0x6c, 0x5f, 0x6c, 0x6f, 0x63, 0x6b,
+	0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x52, 0x07, 0x70, 0x6c, 0x6c, 0x4c, 0x6f, 0x63, 0x6b, 0x22,
+	0x1d, 0x0a, 0x1b, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x47, 0x65,
+	0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0xea,
+	0x04, 0x0a, 0x1c, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x47, 0x65,
+	0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12,
+	0x49, 0x0a, 0x09, 0x6d, 0x6f, 0x64, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x01, 0x20, 0x01,
+	0x28, 0x0e, 0x32, 0x2c, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e,
+	0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76,
+	0x65, 0x72, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x61, 0x74, 0x6f, 0x72, 0x53, 0x74, 0x61, 0x74, 0x65,
+	0x52, 0x08, 0x6d, 0x6f, 0x64, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x4d, 0x0a, 0x0b, 0x64, 0x65,
+	0x6d, 0x6f, 0x64, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0e, 0x32,
+	0x2c, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2e, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x4d,
+	0x6f, 0x64, 0x75, 0x6c, 0x61, 0x74, 0x6f, 0x72, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52, 0x0a, 0x64,
+	0x65, 0x6d, 0x6f, 0x64, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x42, 0x0a, 0x08, 0x74, 0x78, 0x5f,
+	0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x27, 0x2e, 0x53, 0x70,
+	0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e,
+	0x54, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x54, 0x78, 0x52, 0x78, 0x53,
+	0x74, 0x61, 0x74, 0x65, 0x52, 0x07, 0x74, 0x78, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x42, 0x0a,
+	0x08, 0x72, 0x78, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0e, 0x32,
+	0x27, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2e, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x54,
+	0x78, 0x52, 0x78, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52, 0x07, 0x72, 0x78, 0x53, 0x74, 0x61, 0x74,
+	0x65, 0x12, 0x33, 0x0a, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0xee, 0x07, 0x20, 0x01, 0x28,
+	0x0e, 0x32, 0x1c, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x44, 0x69, 0x73, 0x68, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52,
+	0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x12, 0x3d, 0x0a, 0x06, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x73,
+	0x18, 0xef, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x54, 0x72, 0x61, 0x6e,
+	0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x46, 0x61, 0x75, 0x6c, 0x74, 0x73, 0x52, 0x06, 0x66,
+	0x61, 0x75, 0x6c, 0x74, 0x73, 0x12, 0x6c, 0x0a, 0x17, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x6d, 0x69,
+	0x74, 0x5f, 0x62, 0x6c, 0x61, 0x6e, 0x6b, 0x69, 0x6e, 0x67, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x65,
+	0x18, 0xf0, 0x07, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x33, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x54, 0x72, 0x61, 0x6e,
+	0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x6d, 0x69, 0x74, 0x42,
+	0x6c, 0x61, 0x6e, 0x6b, 0x69, 0x6e, 0x67, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52, 0x15, 0x74, 0x72,
+	0x61, 0x6e, 0x73, 0x6d, 0x69, 0x74, 0x42, 0x6c, 0x61, 0x6e, 0x6b, 0x69, 0x6e, 0x67, 0x53, 0x74,
+	0x61, 0x74, 0x65, 0x12, 0x27, 0x0a, 0x0f, 0x6d, 0x6f, 0x64, 0x65, 0x6d, 0x5f, 0x61, 0x73, 0x69,
+	0x63, 0x5f, 0x74, 0x65, 0x6d, 0x70, 0x18, 0xf1, 0x07, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0d, 0x6d,
+	0x6f, 0x64, 0x65, 0x6d, 0x41, 0x73, 0x69, 0x63, 0x54, 0x65, 0x6d, 0x70, 0x12, 0x1d, 0x0a, 0x0a,
+	0x74, 0x78, 0x5f, 0x69, 0x66, 0x5f, 0x74, 0x65, 0x6d, 0x70, 0x18, 0xf2, 0x07, 0x20, 0x01, 0x28,
+	0x02, 0x52, 0x08, 0x74, 0x78, 0x49, 0x66, 0x54, 0x65, 0x6d, 0x70, 0x22, 0xaa, 0x01, 0x0a, 0x11,
+	0x54, 0x72, 0x61, 0x6e, 0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x46, 0x61, 0x75, 0x6c, 0x74,
+	0x73, 0x12, 0x3a, 0x0a, 0x1a, 0x6f, 0x76, 0x65, 0x72, 0x5f, 0x74, 0x65, 0x6d, 0x70, 0x5f, 0x6d,
+	0x6f, 0x64, 0x65, 0x6d, 0x5f, 0x61, 0x73, 0x69, 0x63, 0x5f, 0x66, 0x61, 0x75, 0x6c, 0x74, 0x18,
+	0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x16, 0x6f, 0x76, 0x65, 0x72, 0x54, 0x65, 0x6d, 0x70, 0x4d,
+	0x6f, 0x64, 0x65, 0x6d, 0x41, 0x73, 0x69, 0x63, 0x46, 0x61, 0x75, 0x6c, 0x74, 0x12, 0x2f, 0x0a,
+	0x14, 0x6f, 0x76, 0x65, 0x72, 0x5f, 0x74, 0x65, 0x6d, 0x70, 0x5f, 0x70, 0x63, 0x62, 0x61, 0x5f,
+	0x66, 0x61, 0x75, 0x6c, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x08, 0x52, 0x11, 0x6f, 0x76, 0x65,
+	0x72, 0x54, 0x65, 0x6d, 0x70, 0x50, 0x63, 0x62, 0x61, 0x46, 0x61, 0x75, 0x6c, 0x74, 0x12, 0x28,
+	0x0a, 0x10, 0x64, 0x63, 0x5f, 0x76, 0x6f, 0x6c, 0x74, 0x61, 0x67, 0x65, 0x5f, 0x66, 0x61, 0x75,
+	0x6c, 0x74, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0e, 0x64, 0x63, 0x56, 0x6f, 0x6c, 0x74,
+	0x61, 0x67, 0x65, 0x46, 0x61, 0x75, 0x6c, 0x74, 0x2a, 0x5e, 0x0a, 0x19, 0x54, 0x72, 0x61, 0x6e,
+	0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x61, 0x74, 0x6f, 0x72,
+	0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x14, 0x0a, 0x10, 0x4d, 0x4f, 0x44, 0x53, 0x54, 0x41, 0x54,
+	0x45, 0x5f, 0x55, 0x4e, 0x4b, 0x4e, 0x4f, 0x57, 0x4e, 0x10, 0x00, 0x12, 0x14, 0x0a, 0x10, 0x4d,
+	0x4f, 0x44, 0x53, 0x54, 0x41, 0x54, 0x45, 0x5f, 0x45, 0x4e, 0x41, 0x42, 0x4c, 0x45, 0x44, 0x10,
+	0x01, 0x12, 0x15, 0x0a, 0x11, 0x4d, 0x4f, 0x44, 0x53, 0x54, 0x41, 0x54, 0x45, 0x5f, 0x44, 0x49,
+	0x53, 0x41, 0x42, 0x4c, 0x45, 0x44, 0x10, 0x02, 0x2a, 0x4d, 0x0a, 0x14, 0x54, 0x72, 0x61, 0x6e,
+	0x73, 0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x54, 0x78, 0x52, 0x78, 0x53, 0x74, 0x61, 0x74, 0x65,
+	0x12, 0x10, 0x0a, 0x0c, 0x54, 0x58, 0x52, 0x58, 0x5f, 0x55, 0x4e, 0x4b, 0x4e, 0x4f, 0x57, 0x4e,
+	0x10, 0x00, 0x12, 0x10, 0x0a, 0x0c, 0x54, 0x58, 0x52, 0x58, 0x5f, 0x45, 0x4e, 0x41, 0x42, 0x4c,
+	0x45, 0x44, 0x10, 0x01, 0x12, 0x11, 0x0a, 0x0d, 0x54, 0x58, 0x52, 0x58, 0x5f, 0x44, 0x49, 0x53,
+	0x41, 0x42, 0x4c, 0x45, 0x44, 0x10, 0x02, 0x2a, 0x53, 0x0a, 0x20, 0x54, 0x72, 0x61, 0x6e, 0x73,
+	0x63, 0x65, 0x69, 0x76, 0x65, 0x72, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x6d, 0x69, 0x74, 0x42, 0x6c,
+	0x61, 0x6e, 0x6b, 0x69, 0x6e, 0x67, 0x53, 0x74, 0x61, 0x74, 0x65, 0x12, 0x0e, 0x0a, 0x0a, 0x54,
+	0x42, 0x5f, 0x55, 0x4e, 0x4b, 0x4e, 0x4f, 0x57, 0x4e, 0x10, 0x00, 0x12, 0x0e, 0x0a, 0x0a, 0x54,
+	0x42, 0x5f, 0x45, 0x4e, 0x41, 0x42, 0x4c, 0x45, 0x44, 0x10, 0x01, 0x12, 0x0f, 0x0a, 0x0b, 0x54,
+	0x42, 0x5f, 0x44, 0x49, 0x53, 0x41, 0x42, 0x4c, 0x45, 0x44, 0x10, 0x02, 0x42, 0x17, 0x5a, 0x15,
+	0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64,
+	0x65, 0x76, 0x69, 0x63, 0x65, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
+}
+
+var (
+	file_spacex_api_device_transceiver_proto_rawDescOnce sync.Once
+	file_spacex_api_device_transceiver_proto_rawDescData = file_spacex_api_device_transceiver_proto_rawDesc
+)
+
+func file_spacex_api_device_transceiver_proto_rawDescGZIP() []byte {
+	file_spacex_api_device_transceiver_proto_rawDescOnce.Do(func() {
+		file_spacex_api_device_transceiver_proto_rawDescData = protoimpl.X.CompressGZIP(file_spacex_api_device_transceiver_proto_rawDescData)
+	})
+	return file_spacex_api_device_transceiver_proto_rawDescData
+}
+
+var file_spacex_api_device_transceiver_proto_enumTypes = make([]protoimpl.EnumInfo, 3)
+var file_spacex_api_device_transceiver_proto_msgTypes = make([]protoimpl.MessageInfo, 5)
+var file_spacex_api_device_transceiver_proto_goTypes = []interface{}{
+	(TransceiverModulatorState)(0),            // 0: SpaceX.API.Device.TransceiverModulatorState
+	(TransceiverTxRxState)(0),                 // 1: SpaceX.API.Device.TransceiverTxRxState
+	(TransceiverTransmitBlankingState)(0),     // 2: SpaceX.API.Device.TransceiverTransmitBlankingState
+	(*TransceiverIFLoopbackTestRequest)(nil),  // 3: SpaceX.API.Device.TransceiverIFLoopbackTestRequest
+	(*TransceiverIFLoopbackTestResponse)(nil), // 4: SpaceX.API.Device.TransceiverIFLoopbackTestResponse
+	(*TransceiverGetStatusRequest)(nil),       // 5: SpaceX.API.Device.TransceiverGetStatusRequest
+	(*TransceiverGetStatusResponse)(nil),      // 6: SpaceX.API.Device.TransceiverGetStatusResponse
+	(*TransceiverFaults)(nil),                 // 7: SpaceX.API.Device.TransceiverFaults
+	(DishState)(0),                            // 8: SpaceX.API.Device.DishState
+}
+var file_spacex_api_device_transceiver_proto_depIdxs = []int32{
+	0, // 0: SpaceX.API.Device.TransceiverGetStatusResponse.mod_state:type_name -> SpaceX.API.Device.TransceiverModulatorState
+	0, // 1: SpaceX.API.Device.TransceiverGetStatusResponse.demod_state:type_name -> SpaceX.API.Device.TransceiverModulatorState
+	1, // 2: SpaceX.API.Device.TransceiverGetStatusResponse.tx_state:type_name -> SpaceX.API.Device.TransceiverTxRxState
+	1, // 3: SpaceX.API.Device.TransceiverGetStatusResponse.rx_state:type_name -> SpaceX.API.Device.TransceiverTxRxState
+	8, // 4: SpaceX.API.Device.TransceiverGetStatusResponse.state:type_name -> SpaceX.API.Device.DishState
+	7, // 5: SpaceX.API.Device.TransceiverGetStatusResponse.faults:type_name -> SpaceX.API.Device.TransceiverFaults
+	2, // 6: SpaceX.API.Device.TransceiverGetStatusResponse.transmit_blanking_state:type_name -> SpaceX.API.Device.TransceiverTransmitBlankingState
+	7, // [7:7] is the sub-list for method output_type
+	7, // [7:7] is the sub-list for method input_type
+	7, // [7:7] is the sub-list for extension type_name
+	7, // [7:7] is the sub-list for extension extendee
+	0, // [0:7] is the sub-list for field type_name
+}
+
+func init() { file_spacex_api_device_transceiver_proto_init() }
+func file_spacex_api_device_transceiver_proto_init() {
+	if File_spacex_api_device_transceiver_proto != nil {
+		return
+	}
+	file_spacex_api_device_common_proto_init()
+	file_spacex_api_device_dish_proto_init()
+	if !protoimpl.UnsafeEnabled {
+		file_spacex_api_device_transceiver_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*TransceiverIFLoopbackTestRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_transceiver_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*TransceiverIFLoopbackTestResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_transceiver_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*TransceiverGetStatusRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_transceiver_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*TransceiverGetStatusResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_transceiver_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*TransceiverFaults); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+	}
+	type x struct{}
+	out := protoimpl.TypeBuilder{
+		File: protoimpl.DescBuilder{
+			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+			RawDescriptor: file_spacex_api_device_transceiver_proto_rawDesc,
+			NumEnums:      3,
+			NumMessages:   5,
+			NumExtensions: 0,
+			NumServices:   0,
+		},
+		GoTypes:           file_spacex_api_device_transceiver_proto_goTypes,
+		DependencyIndexes: file_spacex_api_device_transceiver_proto_depIdxs,
+		EnumInfos:         file_spacex_api_device_transceiver_proto_enumTypes,
+		MessageInfos:      file_spacex_api_device_transceiver_proto_msgTypes,
+	}.Build()
+	File_spacex_api_device_transceiver_proto = out.File
+	file_spacex_api_device_transceiver_proto_rawDesc = nil
+	file_spacex_api_device_transceiver_proto_goTypes = nil
+	file_spacex_api_device_transceiver_proto_depIdxs = nil
+}
blob - /dev/null
blob + c1bc22e5cc29d7bde4a7f59ab0af05015b5b844a (mode 644)
--- /dev/null
+++ device/wifi.pb.go
@@ -0,0 +1,1662 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// 	protoc-gen-go v1.28.1
+// 	protoc        v3.21.6
+// source: spacex/api/device/wifi.proto
+
+package device
+
+import (
+	protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+	protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+	reflect "reflect"
+	sync "sync"
+)
+
+const (
+	// Verify that this generated code is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+	// Verify that runtime/protoimpl is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+type WifiClient_Interface int32
+
+const (
+	WifiClient_UNKNOWN WifiClient_Interface = 0
+	WifiClient_ETH     WifiClient_Interface = 1
+	WifiClient_RF_2GHZ WifiClient_Interface = 2
+	WifiClient_RF_5GHZ WifiClient_Interface = 3
+)
+
+// Enum value maps for WifiClient_Interface.
+var (
+	WifiClient_Interface_name = map[int32]string{
+		0: "UNKNOWN",
+		1: "ETH",
+		2: "RF_2GHZ",
+		3: "RF_5GHZ",
+	}
+	WifiClient_Interface_value = map[string]int32{
+		"UNKNOWN": 0,
+		"ETH":     1,
+		"RF_2GHZ": 2,
+		"RF_5GHZ": 3,
+	}
+)
+
+func (x WifiClient_Interface) Enum() *WifiClient_Interface {
+	p := new(WifiClient_Interface)
+	*p = x
+	return p
+}
+
+func (x WifiClient_Interface) String() string {
+	return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
+}
+
+func (WifiClient_Interface) Descriptor() protoreflect.EnumDescriptor {
+	return file_spacex_api_device_wifi_proto_enumTypes[0].Descriptor()
+}
+
+func (WifiClient_Interface) Type() protoreflect.EnumType {
+	return &file_spacex_api_device_wifi_proto_enumTypes[0]
+}
+
+func (x WifiClient_Interface) Number() protoreflect.EnumNumber {
+	return protoreflect.EnumNumber(x)
+}
+
+// Deprecated: Use WifiClient_Interface.Descriptor instead.
+func (WifiClient_Interface) EnumDescriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{6, 0}
+}
+
+type WifiSetConfigRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	WifiConfig *WifiConfig `protobuf:"bytes,1,opt,name=wifi_config,json=wifiConfig,proto3" json:"wifi_config,omitempty"`
+}
+
+func (x *WifiSetConfigRequest) Reset() {
+	*x = WifiSetConfigRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[0]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiSetConfigRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiSetConfigRequest) ProtoMessage() {}
+
+func (x *WifiSetConfigRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[0]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiSetConfigRequest.ProtoReflect.Descriptor instead.
+func (*WifiSetConfigRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *WifiSetConfigRequest) GetWifiConfig() *WifiConfig {
+	if x != nil {
+		return x.WifiConfig
+	}
+	return nil
+}
+
+type WifiSetConfigResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *WifiSetConfigResponse) Reset() {
+	*x = WifiSetConfigResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[1]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiSetConfigResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiSetConfigResponse) ProtoMessage() {}
+
+func (x *WifiSetConfigResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[1]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiSetConfigResponse.ProtoReflect.Descriptor instead.
+func (*WifiSetConfigResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{1}
+}
+
+type WifiGetClientsRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *WifiGetClientsRequest) Reset() {
+	*x = WifiGetClientsRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[2]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiGetClientsRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiGetClientsRequest) ProtoMessage() {}
+
+func (x *WifiGetClientsRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[2]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiGetClientsRequest.ProtoReflect.Descriptor instead.
+func (*WifiGetClientsRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{2}
+}
+
+type WifiGetClientsResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Clients []*WifiClient `protobuf:"bytes,1,rep,name=clients,proto3" json:"clients,omitempty"`
+}
+
+func (x *WifiGetClientsResponse) Reset() {
+	*x = WifiGetClientsResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[3]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiGetClientsResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiGetClientsResponse) ProtoMessage() {}
+
+func (x *WifiGetClientsResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[3]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiGetClientsResponse.ProtoReflect.Descriptor instead.
+func (*WifiGetClientsResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{3}
+}
+
+func (x *WifiGetClientsResponse) GetClients() []*WifiClient {
+	if x != nil {
+		return x.Clients
+	}
+	return nil
+}
+
+type WifiGetHistoryResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Current       uint64    `protobuf:"varint,1,opt,name=current,proto3" json:"current,omitempty"`
+	PingDropRate  []float32 `protobuf:"fixed32,1001,rep,packed,name=ping_drop_rate,json=pingDropRate,proto3" json:"ping_drop_rate,omitempty"`
+	PingLatencyMs []float32 `protobuf:"fixed32,1002,rep,packed,name=ping_latency_ms,json=pingLatencyMs,proto3" json:"ping_latency_ms,omitempty"`
+}
+
+func (x *WifiGetHistoryResponse) Reset() {
+	*x = WifiGetHistoryResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[4]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiGetHistoryResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiGetHistoryResponse) ProtoMessage() {}
+
+func (x *WifiGetHistoryResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[4]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiGetHistoryResponse.ProtoReflect.Descriptor instead.
+func (*WifiGetHistoryResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{4}
+}
+
+func (x *WifiGetHistoryResponse) GetCurrent() uint64 {
+	if x != nil {
+		return x.Current
+	}
+	return 0
+}
+
+func (x *WifiGetHistoryResponse) GetPingDropRate() []float32 {
+	if x != nil {
+		return x.PingDropRate
+	}
+	return nil
+}
+
+func (x *WifiGetHistoryResponse) GetPingLatencyMs() []float32 {
+	if x != nil {
+		return x.PingLatencyMs
+	}
+	return nil
+}
+
+type WifiNewClientConnectedEvent struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Client *WifiClient `protobuf:"bytes,1,opt,name=client,proto3" json:"client,omitempty"`
+}
+
+func (x *WifiNewClientConnectedEvent) Reset() {
+	*x = WifiNewClientConnectedEvent{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[5]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiNewClientConnectedEvent) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiNewClientConnectedEvent) ProtoMessage() {}
+
+func (x *WifiNewClientConnectedEvent) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[5]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiNewClientConnectedEvent.ProtoReflect.Descriptor instead.
+func (*WifiNewClientConnectedEvent) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{5}
+}
+
+func (x *WifiNewClientConnectedEvent) GetClient() *WifiClient {
+	if x != nil {
+		return x.Client
+	}
+	return nil
+}
+
+type WifiClient struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Name            string               `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
+	MacAddress      string               `protobuf:"bytes,2,opt,name=mac_address,json=macAddress,proto3" json:"mac_address,omitempty"`
+	IpAddress       string               `protobuf:"bytes,3,opt,name=ip_address,json=ipAddress,proto3" json:"ip_address,omitempty"`
+	SignalStrength  float32              `protobuf:"fixed32,4,opt,name=signal_strength,json=signalStrength,proto3" json:"signal_strength,omitempty"`
+	RxStats         *WifiClient_RxStats  `protobuf:"bytes,5,opt,name=rx_stats,json=rxStats,proto3" json:"rx_stats,omitempty"`
+	TxStats         *WifiClient_TxStats  `protobuf:"bytes,6,opt,name=tx_stats,json=txStats,proto3" json:"tx_stats,omitempty"`
+	AssociatedTimeS uint32               `protobuf:"varint,7,opt,name=associated_time_s,json=associatedTimeS,proto3" json:"associated_time_s,omitempty"`
+	ModeStr         string               `protobuf:"bytes,8,opt,name=mode_str,json=modeStr,proto3" json:"mode_str,omitempty"`
+	Iface           WifiClient_Interface `protobuf:"varint,9,opt,name=iface,proto3,enum=SpaceX.API.Device.WifiClient_Interface" json:"iface,omitempty"`
+}
+
+func (x *WifiClient) Reset() {
+	*x = WifiClient{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[6]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiClient) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiClient) ProtoMessage() {}
+
+func (x *WifiClient) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[6]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiClient.ProtoReflect.Descriptor instead.
+func (*WifiClient) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{6}
+}
+
+func (x *WifiClient) GetName() string {
+	if x != nil {
+		return x.Name
+	}
+	return ""
+}
+
+func (x *WifiClient) GetMacAddress() string {
+	if x != nil {
+		return x.MacAddress
+	}
+	return ""
+}
+
+func (x *WifiClient) GetIpAddress() string {
+	if x != nil {
+		return x.IpAddress
+	}
+	return ""
+}
+
+func (x *WifiClient) GetSignalStrength() float32 {
+	if x != nil {
+		return x.SignalStrength
+	}
+	return 0
+}
+
+func (x *WifiClient) GetRxStats() *WifiClient_RxStats {
+	if x != nil {
+		return x.RxStats
+	}
+	return nil
+}
+
+func (x *WifiClient) GetTxStats() *WifiClient_TxStats {
+	if x != nil {
+		return x.TxStats
+	}
+	return nil
+}
+
+func (x *WifiClient) GetAssociatedTimeS() uint32 {
+	if x != nil {
+		return x.AssociatedTimeS
+	}
+	return 0
+}
+
+func (x *WifiClient) GetModeStr() string {
+	if x != nil {
+		return x.ModeStr
+	}
+	return ""
+}
+
+func (x *WifiClient) GetIface() WifiClient_Interface {
+	if x != nil {
+		return x.Iface
+	}
+	return WifiClient_UNKNOWN
+}
+
+type WifiSetupRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Skip            bool   `protobuf:"varint,1,opt,name=skip,proto3" json:"skip,omitempty"`
+	NetworkName     string `protobuf:"bytes,2,opt,name=network_name,json=networkName,proto3" json:"network_name,omitempty"`
+	NetworkPassword string `protobuf:"bytes,3,opt,name=network_password,json=networkPassword,proto3" json:"network_password,omitempty"`
+}
+
+func (x *WifiSetupRequest) Reset() {
+	*x = WifiSetupRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[7]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiSetupRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiSetupRequest) ProtoMessage() {}
+
+func (x *WifiSetupRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[7]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiSetupRequest.ProtoReflect.Descriptor instead.
+func (*WifiSetupRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{7}
+}
+
+func (x *WifiSetupRequest) GetSkip() bool {
+	if x != nil {
+		return x.Skip
+	}
+	return false
+}
+
+func (x *WifiSetupRequest) GetNetworkName() string {
+	if x != nil {
+		return x.NetworkName
+	}
+	return ""
+}
+
+func (x *WifiSetupRequest) GetNetworkPassword() string {
+	if x != nil {
+		return x.NetworkPassword
+	}
+	return ""
+}
+
+type WifiSetupResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *WifiSetupResponse) Reset() {
+	*x = WifiSetupResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[8]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiSetupResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiSetupResponse) ProtoMessage() {}
+
+func (x *WifiSetupResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[8]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiSetupResponse.ProtoReflect.Descriptor instead.
+func (*WifiSetupResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{8}
+}
+
+type WifiGetStatusResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	DeviceInfo           *DeviceInfo  `protobuf:"bytes,3,opt,name=device_info,json=deviceInfo,proto3" json:"device_info,omitempty"`
+	DeviceState          *DeviceState `protobuf:"bytes,4,opt,name=device_state,json=deviceState,proto3" json:"device_state,omitempty"`
+	CaptivePortalEnabled bool         `protobuf:"varint,1,opt,name=captive_portal_enabled,json=captivePortalEnabled,proto3" json:"captive_portal_enabled,omitempty"`
+	// Deprecated: Do not use.
+	Clients        []*WifiClient `protobuf:"bytes,2,rep,name=clients,proto3" json:"clients,omitempty"`
+	SerialNumber   string        `protobuf:"bytes,1001,opt,name=serial_number,json=serialNumber,proto3" json:"serial_number,omitempty"`
+	Sku            string        `protobuf:"bytes,1002,opt,name=sku,proto3" json:"sku,omitempty"`
+	Ipv4WanAddress string        `protobuf:"bytes,1003,opt,name=ipv4_wan_address,json=ipv4WanAddress,proto3" json:"ipv4_wan_address,omitempty"`
+	PingDropRate   float32       `protobuf:"fixed32,1004,opt,name=ping_drop_rate,json=pingDropRate,proto3" json:"ping_drop_rate,omitempty"`
+	PingLatencyMs  float32       `protobuf:"fixed32,1005,opt,name=ping_latency_ms,json=pingLatencyMs,proto3" json:"ping_latency_ms,omitempty"`
+}
+
+func (x *WifiGetStatusResponse) Reset() {
+	*x = WifiGetStatusResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[9]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiGetStatusResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiGetStatusResponse) ProtoMessage() {}
+
+func (x *WifiGetStatusResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[9]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiGetStatusResponse.ProtoReflect.Descriptor instead.
+func (*WifiGetStatusResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{9}
+}
+
+func (x *WifiGetStatusResponse) GetDeviceInfo() *DeviceInfo {
+	if x != nil {
+		return x.DeviceInfo
+	}
+	return nil
+}
+
+func (x *WifiGetStatusResponse) GetDeviceState() *DeviceState {
+	if x != nil {
+		return x.DeviceState
+	}
+	return nil
+}
+
+func (x *WifiGetStatusResponse) GetCaptivePortalEnabled() bool {
+	if x != nil {
+		return x.CaptivePortalEnabled
+	}
+	return false
+}
+
+// Deprecated: Do not use.
+func (x *WifiGetStatusResponse) GetClients() []*WifiClient {
+	if x != nil {
+		return x.Clients
+	}
+	return nil
+}
+
+func (x *WifiGetStatusResponse) GetSerialNumber() string {
+	if x != nil {
+		return x.SerialNumber
+	}
+	return ""
+}
+
+func (x *WifiGetStatusResponse) GetSku() string {
+	if x != nil {
+		return x.Sku
+	}
+	return ""
+}
+
+func (x *WifiGetStatusResponse) GetIpv4WanAddress() string {
+	if x != nil {
+		return x.Ipv4WanAddress
+	}
+	return ""
+}
+
+func (x *WifiGetStatusResponse) GetPingDropRate() float32 {
+	if x != nil {
+		return x.PingDropRate
+	}
+	return 0
+}
+
+func (x *WifiGetStatusResponse) GetPingLatencyMs() float32 {
+	if x != nil {
+		return x.PingLatencyMs
+	}
+	return 0
+}
+
+type WifiAuthenticateRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Challenge *SignedData `protobuf:"bytes,1,opt,name=challenge,proto3" json:"challenge,omitempty"`
+}
+
+func (x *WifiAuthenticateRequest) Reset() {
+	*x = WifiAuthenticateRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[10]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiAuthenticateRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiAuthenticateRequest) ProtoMessage() {}
+
+func (x *WifiAuthenticateRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[10]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiAuthenticateRequest.ProtoReflect.Descriptor instead.
+func (*WifiAuthenticateRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{10}
+}
+
+func (x *WifiAuthenticateRequest) GetChallenge() *SignedData {
+	if x != nil {
+		return x.Challenge
+	}
+	return nil
+}
+
+type WifiAuthenticateResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Wifi *ChallengeResponse `protobuf:"bytes,1,opt,name=wifi,proto3" json:"wifi,omitempty"`
+	Dish *ChallengeResponse `protobuf:"bytes,2,opt,name=dish,proto3" json:"dish,omitempty"`
+}
+
+func (x *WifiAuthenticateResponse) Reset() {
+	*x = WifiAuthenticateResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[11]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiAuthenticateResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiAuthenticateResponse) ProtoMessage() {}
+
+func (x *WifiAuthenticateResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[11]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiAuthenticateResponse.ProtoReflect.Descriptor instead.
+func (*WifiAuthenticateResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{11}
+}
+
+func (x *WifiAuthenticateResponse) GetWifi() *ChallengeResponse {
+	if x != nil {
+		return x.Wifi
+	}
+	return nil
+}
+
+func (x *WifiAuthenticateResponse) GetDish() *ChallengeResponse {
+	if x != nil {
+		return x.Dish
+	}
+	return nil
+}
+
+type WifiAccountBondingEvent struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	DishId string `protobuf:"bytes,1,opt,name=dish_id,json=dishId,proto3" json:"dish_id,omitempty"`
+}
+
+func (x *WifiAccountBondingEvent) Reset() {
+	*x = WifiAccountBondingEvent{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[12]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiAccountBondingEvent) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiAccountBondingEvent) ProtoMessage() {}
+
+func (x *WifiAccountBondingEvent) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[12]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiAccountBondingEvent.ProtoReflect.Descriptor instead.
+func (*WifiAccountBondingEvent) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{12}
+}
+
+func (x *WifiAccountBondingEvent) GetDishId() string {
+	if x != nil {
+		return x.DishId
+	}
+	return ""
+}
+
+type PingMetrics struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	LatencyMeanMs             float32 `protobuf:"fixed32,1,opt,name=latency_mean_ms,json=latencyMeanMs,proto3" json:"latency_mean_ms,omitempty"`
+	LatencyStddevMs           float32 `protobuf:"fixed32,2,opt,name=latency_stddev_ms,json=latencyStddevMs,proto3" json:"latency_stddev_ms,omitempty"`
+	LatencyMeanMs_5M          float32 `protobuf:"fixed32,3,opt,name=latency_mean_ms_5m,json=latencyMeanMs5m,proto3" json:"latency_mean_ms_5m,omitempty"`
+	LatencyMeanMs_1H          float32 `protobuf:"fixed32,4,opt,name=latency_mean_ms_1h,json=latencyMeanMs1h,proto3" json:"latency_mean_ms_1h,omitempty"`
+	LatencyMeanMs_1D          float32 `protobuf:"fixed32,5,opt,name=latency_mean_ms_1d,json=latencyMeanMs1d,proto3" json:"latency_mean_ms_1d,omitempty"`
+	DropRate                  float32 `protobuf:"fixed32,6,opt,name=drop_rate,json=dropRate,proto3" json:"drop_rate,omitempty"`
+	DropRate_5M               float32 `protobuf:"fixed32,7,opt,name=drop_rate_5m,json=dropRate5m,proto3" json:"drop_rate_5m,omitempty"`
+	DropRate_1H               float32 `protobuf:"fixed32,8,opt,name=drop_rate_1h,json=dropRate1h,proto3" json:"drop_rate_1h,omitempty"`
+	DropRate_1D               float32 `protobuf:"fixed32,9,opt,name=drop_rate_1d,json=dropRate1d,proto3" json:"drop_rate_1d,omitempty"`
+	SecondsSinceLastSuccess   float32 `protobuf:"fixed32,10,opt,name=seconds_since_last_success,json=secondsSinceLastSuccess,proto3" json:"seconds_since_last_success,omitempty"`
+	SecondsSinceLast_1SOutage float32 `protobuf:"fixed32,11,opt,name=seconds_since_last_1s_outage,json=secondsSinceLast1sOutage,proto3" json:"seconds_since_last_1s_outage,omitempty"`
+	SecondsSinceLast_5SOutage float32 `protobuf:"fixed32,12,opt,name=seconds_since_last_5s_outage,json=secondsSinceLast5sOutage,proto3" json:"seconds_since_last_5s_outage,omitempty"`
+	HappyHours_1S_1D          float32 `protobuf:"fixed32,13,opt,name=happy_hours_1s_1d,json=happyHours1s1d,proto3" json:"happy_hours_1s_1d,omitempty"`
+	HappyHours_5S_1D          float32 `protobuf:"fixed32,14,opt,name=happy_hours_5s_1d,json=happyHours5s1d,proto3" json:"happy_hours_5s_1d,omitempty"`
+}
+
+func (x *PingMetrics) Reset() {
+	*x = PingMetrics{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[13]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *PingMetrics) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*PingMetrics) ProtoMessage() {}
+
+func (x *PingMetrics) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[13]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use PingMetrics.ProtoReflect.Descriptor instead.
+func (*PingMetrics) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{13}
+}
+
+func (x *PingMetrics) GetLatencyMeanMs() float32 {
+	if x != nil {
+		return x.LatencyMeanMs
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetLatencyStddevMs() float32 {
+	if x != nil {
+		return x.LatencyStddevMs
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetLatencyMeanMs_5M() float32 {
+	if x != nil {
+		return x.LatencyMeanMs_5M
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetLatencyMeanMs_1H() float32 {
+	if x != nil {
+		return x.LatencyMeanMs_1H
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetLatencyMeanMs_1D() float32 {
+	if x != nil {
+		return x.LatencyMeanMs_1D
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetDropRate() float32 {
+	if x != nil {
+		return x.DropRate
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetDropRate_5M() float32 {
+	if x != nil {
+		return x.DropRate_5M
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetDropRate_1H() float32 {
+	if x != nil {
+		return x.DropRate_1H
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetDropRate_1D() float32 {
+	if x != nil {
+		return x.DropRate_1D
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetSecondsSinceLastSuccess() float32 {
+	if x != nil {
+		return x.SecondsSinceLastSuccess
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetSecondsSinceLast_1SOutage() float32 {
+	if x != nil {
+		return x.SecondsSinceLast_1SOutage
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetSecondsSinceLast_5SOutage() float32 {
+	if x != nil {
+		return x.SecondsSinceLast_5SOutage
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetHappyHours_1S_1D() float32 {
+	if x != nil {
+		return x.HappyHours_1S_1D
+	}
+	return 0
+}
+
+func (x *PingMetrics) GetHappyHours_5S_1D() float32 {
+	if x != nil {
+		return x.HappyHours_5S_1D
+	}
+	return 0
+}
+
+type WifiGetPingMetricsRequest struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+}
+
+func (x *WifiGetPingMetricsRequest) Reset() {
+	*x = WifiGetPingMetricsRequest{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[14]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiGetPingMetricsRequest) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiGetPingMetricsRequest) ProtoMessage() {}
+
+func (x *WifiGetPingMetricsRequest) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[14]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiGetPingMetricsRequest.ProtoReflect.Descriptor instead.
+func (*WifiGetPingMetricsRequest) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{14}
+}
+
+type WifiGetPingMetricsResponse struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Internet *PingMetrics `protobuf:"bytes,1,opt,name=internet,proto3" json:"internet,omitempty"`
+}
+
+func (x *WifiGetPingMetricsResponse) Reset() {
+	*x = WifiGetPingMetricsResponse{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[15]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiGetPingMetricsResponse) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiGetPingMetricsResponse) ProtoMessage() {}
+
+func (x *WifiGetPingMetricsResponse) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[15]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiGetPingMetricsResponse.ProtoReflect.Descriptor instead.
+func (*WifiGetPingMetricsResponse) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{15}
+}
+
+func (x *WifiGetPingMetricsResponse) GetInternet() *PingMetrics {
+	if x != nil {
+		return x.Internet
+	}
+	return nil
+}
+
+type WifiClient_RxStats struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Bytes       uint64 `protobuf:"varint,1,opt,name=bytes,proto3" json:"bytes,omitempty"`
+	CountErrors uint64 `protobuf:"varint,2,opt,name=count_errors,json=countErrors,proto3" json:"count_errors,omitempty"`
+}
+
+func (x *WifiClient_RxStats) Reset() {
+	*x = WifiClient_RxStats{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[16]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiClient_RxStats) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiClient_RxStats) ProtoMessage() {}
+
+func (x *WifiClient_RxStats) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[16]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiClient_RxStats.ProtoReflect.Descriptor instead.
+func (*WifiClient_RxStats) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{6, 0}
+}
+
+func (x *WifiClient_RxStats) GetBytes() uint64 {
+	if x != nil {
+		return x.Bytes
+	}
+	return 0
+}
+
+func (x *WifiClient_RxStats) GetCountErrors() uint64 {
+	if x != nil {
+		return x.CountErrors
+	}
+	return 0
+}
+
+type WifiClient_TxStats struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Bytes        uint64 `protobuf:"varint,1,opt,name=bytes,proto3" json:"bytes,omitempty"`
+	SuccessBytes uint64 `protobuf:"varint,2,opt,name=success_bytes,json=successBytes,proto3" json:"success_bytes,omitempty"`
+}
+
+func (x *WifiClient_TxStats) Reset() {
+	*x = WifiClient_TxStats{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_proto_msgTypes[17]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiClient_TxStats) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiClient_TxStats) ProtoMessage() {}
+
+func (x *WifiClient_TxStats) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_proto_msgTypes[17]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiClient_TxStats.ProtoReflect.Descriptor instead.
+func (*WifiClient_TxStats) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_proto_rawDescGZIP(), []int{6, 1}
+}
+
+func (x *WifiClient_TxStats) GetBytes() uint64 {
+	if x != nil {
+		return x.Bytes
+	}
+	return 0
+}
+
+func (x *WifiClient_TxStats) GetSuccessBytes() uint64 {
+	if x != nil {
+		return x.SuccessBytes
+	}
+	return 0
+}
+
+var File_spacex_api_device_wifi_proto protoreflect.FileDescriptor
+
+var file_spacex_api_device_wifi_proto_rawDesc = []byte{
+	0x0a, 0x1c, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2f, 0x77, 0x69, 0x66, 0x69, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x11,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x1a, 0x1e, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x2f, 0x63, 0x6f, 0x6d, 0x6d, 0x6f, 0x6e, 0x2e, 0x70, 0x72, 0x6f, 0x74,
+	0x6f, 0x1a, 0x23, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65,
+	0x76, 0x69, 0x63, 0x65, 0x2f, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67,
+	0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0x56, 0x0a, 0x14, 0x57, 0x69, 0x66, 0x69, 0x53, 0x65,
+	0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x3e,
+	0x0a, 0x0b, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x18, 0x01, 0x20,
+	0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49,
+	0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x43, 0x6f, 0x6e, 0x66,
+	0x69, 0x67, 0x52, 0x0a, 0x77, 0x69, 0x66, 0x69, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x22, 0x17,
+	0x0a, 0x15, 0x57, 0x69, 0x66, 0x69, 0x53, 0x65, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x52,
+	0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x17, 0x0a, 0x15, 0x57, 0x69, 0x66, 0x69, 0x47,
+	0x65, 0x74, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74,
+	0x22, 0x51, 0x0a, 0x16, 0x57, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x43, 0x6c, 0x69, 0x65, 0x6e,
+	0x74, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x37, 0x0a, 0x07, 0x63, 0x6c,
+	0x69, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70,
+	0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e,
+	0x57, 0x69, 0x66, 0x69, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x52, 0x07, 0x63, 0x6c, 0x69, 0x65,
+	0x6e, 0x74, 0x73, 0x22, 0x82, 0x01, 0x0a, 0x16, 0x57, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74, 0x48,
+	0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x18,
+	0x0a, 0x07, 0x63, 0x75, 0x72, 0x72, 0x65, 0x6e, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52,
+	0x07, 0x63, 0x75, 0x72, 0x72, 0x65, 0x6e, 0x74, 0x12, 0x25, 0x0a, 0x0e, 0x70, 0x69, 0x6e, 0x67,
+	0x5f, 0x64, 0x72, 0x6f, 0x70, 0x5f, 0x72, 0x61, 0x74, 0x65, 0x18, 0xe9, 0x07, 0x20, 0x03, 0x28,
+	0x02, 0x52, 0x0c, 0x70, 0x69, 0x6e, 0x67, 0x44, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74, 0x65, 0x12,
+	0x27, 0x0a, 0x0f, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x5f,
+	0x6d, 0x73, 0x18, 0xea, 0x07, 0x20, 0x03, 0x28, 0x02, 0x52, 0x0d, 0x70, 0x69, 0x6e, 0x67, 0x4c,
+	0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x4d, 0x73, 0x22, 0x54, 0x0a, 0x1b, 0x57, 0x69, 0x66, 0x69,
+	0x4e, 0x65, 0x77, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x43, 0x6f, 0x6e, 0x6e, 0x65, 0x63, 0x74,
+	0x65, 0x64, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x12, 0x35, 0x0a, 0x06, 0x63, 0x6c, 0x69, 0x65, 0x6e,
+	0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69,
+	0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x52, 0x06, 0x63, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x22, 0xda,
+	0x04, 0x0a, 0x0a, 0x57, 0x69, 0x66, 0x69, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x12, 0x12, 0x0a,
+	0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d,
+	0x65, 0x12, 0x1f, 0x0a, 0x0b, 0x6d, 0x61, 0x63, 0x5f, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73,
+	0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x6d, 0x61, 0x63, 0x41, 0x64, 0x64, 0x72, 0x65,
+	0x73, 0x73, 0x12, 0x1d, 0x0a, 0x0a, 0x69, 0x70, 0x5f, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73,
+	0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x69, 0x70, 0x41, 0x64, 0x64, 0x72, 0x65, 0x73,
+	0x73, 0x12, 0x27, 0x0a, 0x0f, 0x73, 0x69, 0x67, 0x6e, 0x61, 0x6c, 0x5f, 0x73, 0x74, 0x72, 0x65,
+	0x6e, 0x67, 0x74, 0x68, 0x18, 0x04, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0e, 0x73, 0x69, 0x67, 0x6e,
+	0x61, 0x6c, 0x53, 0x74, 0x72, 0x65, 0x6e, 0x67, 0x74, 0x68, 0x12, 0x40, 0x0a, 0x08, 0x72, 0x78,
+	0x5f, 0x73, 0x74, 0x61, 0x74, 0x73, 0x18, 0x05, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x25, 0x2e, 0x53,
+	0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x2e, 0x57, 0x69, 0x66, 0x69, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x2e, 0x52, 0x78, 0x53, 0x74,
+	0x61, 0x74, 0x73, 0x52, 0x07, 0x72, 0x78, 0x53, 0x74, 0x61, 0x74, 0x73, 0x12, 0x40, 0x0a, 0x08,
+	0x74, 0x78, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x73, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x25,
+	0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69,
+	0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x2e, 0x54, 0x78,
+	0x53, 0x74, 0x61, 0x74, 0x73, 0x52, 0x07, 0x74, 0x78, 0x53, 0x74, 0x61, 0x74, 0x73, 0x12, 0x2a,
+	0x0a, 0x11, 0x61, 0x73, 0x73, 0x6f, 0x63, 0x69, 0x61, 0x74, 0x65, 0x64, 0x5f, 0x74, 0x69, 0x6d,
+	0x65, 0x5f, 0x73, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x0f, 0x61, 0x73, 0x73, 0x6f, 0x63,
+	0x69, 0x61, 0x74, 0x65, 0x64, 0x54, 0x69, 0x6d, 0x65, 0x53, 0x12, 0x19, 0x0a, 0x08, 0x6d, 0x6f,
+	0x64, 0x65, 0x5f, 0x73, 0x74, 0x72, 0x18, 0x08, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x6d, 0x6f,
+	0x64, 0x65, 0x53, 0x74, 0x72, 0x12, 0x3d, 0x0a, 0x05, 0x69, 0x66, 0x61, 0x63, 0x65, 0x18, 0x09,
+	0x20, 0x01, 0x28, 0x0e, 0x32, 0x27, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57, 0x69, 0x66, 0x69, 0x43, 0x6c, 0x69,
+	0x65, 0x6e, 0x74, 0x2e, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x52, 0x05, 0x69,
+	0x66, 0x61, 0x63, 0x65, 0x1a, 0x42, 0x0a, 0x07, 0x52, 0x78, 0x53, 0x74, 0x61, 0x74, 0x73, 0x12,
+	0x14, 0x0a, 0x05, 0x62, 0x79, 0x74, 0x65, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x05,
+	0x62, 0x79, 0x74, 0x65, 0x73, 0x12, 0x21, 0x0a, 0x0c, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x5f, 0x65,
+	0x72, 0x72, 0x6f, 0x72, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04, 0x52, 0x0b, 0x63, 0x6f, 0x75,
+	0x6e, 0x74, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x73, 0x1a, 0x44, 0x0a, 0x07, 0x54, 0x78, 0x53, 0x74,
+	0x61, 0x74, 0x73, 0x12, 0x14, 0x0a, 0x05, 0x62, 0x79, 0x74, 0x65, 0x73, 0x18, 0x01, 0x20, 0x01,
+	0x28, 0x04, 0x52, 0x05, 0x62, 0x79, 0x74, 0x65, 0x73, 0x12, 0x23, 0x0a, 0x0d, 0x73, 0x75, 0x63,
+	0x63, 0x65, 0x73, 0x73, 0x5f, 0x62, 0x79, 0x74, 0x65, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x04,
+	0x52, 0x0c, 0x73, 0x75, 0x63, 0x63, 0x65, 0x73, 0x73, 0x42, 0x79, 0x74, 0x65, 0x73, 0x22, 0x3b,
+	0x0a, 0x09, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x12, 0x0b, 0x0a, 0x07, 0x55,
+	0x4e, 0x4b, 0x4e, 0x4f, 0x57, 0x4e, 0x10, 0x00, 0x12, 0x07, 0x0a, 0x03, 0x45, 0x54, 0x48, 0x10,
+	0x01, 0x12, 0x0b, 0x0a, 0x07, 0x52, 0x46, 0x5f, 0x32, 0x47, 0x48, 0x5a, 0x10, 0x02, 0x12, 0x0b,
+	0x0a, 0x07, 0x52, 0x46, 0x5f, 0x35, 0x47, 0x48, 0x5a, 0x10, 0x03, 0x22, 0x74, 0x0a, 0x10, 0x57,
+	0x69, 0x66, 0x69, 0x53, 0x65, 0x74, 0x75, 0x70, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12,
+	0x12, 0x0a, 0x04, 0x73, 0x6b, 0x69, 0x70, 0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x04, 0x73,
+	0x6b, 0x69, 0x70, 0x12, 0x21, 0x0a, 0x0c, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x5f, 0x6e,
+	0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x6e, 0x65, 0x74, 0x77, 0x6f,
+	0x72, 0x6b, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x29, 0x0a, 0x10, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72,
+	0x6b, 0x5f, 0x70, 0x61, 0x73, 0x73, 0x77, 0x6f, 0x72, 0x64, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09,
+	0x52, 0x0f, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x50, 0x61, 0x73, 0x73, 0x77, 0x6f, 0x72,
+	0x64, 0x22, 0x13, 0x0a, 0x11, 0x57, 0x69, 0x66, 0x69, 0x53, 0x65, 0x74, 0x75, 0x70, 0x52, 0x65,
+	0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0xc1, 0x03, 0x0a, 0x15, 0x57, 0x69, 0x66, 0x69, 0x47,
+	0x65, 0x74, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65,
+	0x12, 0x3e, 0x0a, 0x0b, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x5f, 0x69, 0x6e, 0x66, 0x6f, 0x18,
+	0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41,
+	0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x49, 0x6e, 0x66, 0x6f, 0x52, 0x0a, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f,
+	0x12, 0x41, 0x0a, 0x0c, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x65,
+	0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e,
+	0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x53, 0x74, 0x61, 0x74, 0x65, 0x52, 0x0b, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x53, 0x74,
+	0x61, 0x74, 0x65, 0x12, 0x34, 0x0a, 0x16, 0x63, 0x61, 0x70, 0x74, 0x69, 0x76, 0x65, 0x5f, 0x70,
+	0x6f, 0x72, 0x74, 0x61, 0x6c, 0x5f, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x18, 0x01, 0x20,
+	0x01, 0x28, 0x08, 0x52, 0x14, 0x63, 0x61, 0x70, 0x74, 0x69, 0x76, 0x65, 0x50, 0x6f, 0x72, 0x74,
+	0x61, 0x6c, 0x45, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x12, 0x3b, 0x0a, 0x07, 0x63, 0x6c, 0x69,
+	0x65, 0x6e, 0x74, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70, 0x61,
+	0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x57,
+	0x69, 0x66, 0x69, 0x43, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x42, 0x02, 0x18, 0x01, 0x52, 0x07, 0x63,
+	0x6c, 0x69, 0x65, 0x6e, 0x74, 0x73, 0x12, 0x24, 0x0a, 0x0d, 0x73, 0x65, 0x72, 0x69, 0x61, 0x6c,
+	0x5f, 0x6e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x18, 0xe9, 0x07, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c,
+	0x73, 0x65, 0x72, 0x69, 0x61, 0x6c, 0x4e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x12, 0x11, 0x0a, 0x03,
+	0x73, 0x6b, 0x75, 0x18, 0xea, 0x07, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x73, 0x6b, 0x75, 0x12,
+	0x29, 0x0a, 0x10, 0x69, 0x70, 0x76, 0x34, 0x5f, 0x77, 0x61, 0x6e, 0x5f, 0x61, 0x64, 0x64, 0x72,
+	0x65, 0x73, 0x73, 0x18, 0xeb, 0x07, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0e, 0x69, 0x70, 0x76, 0x34,
+	0x57, 0x61, 0x6e, 0x41, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x12, 0x25, 0x0a, 0x0e, 0x70, 0x69,
+	0x6e, 0x67, 0x5f, 0x64, 0x72, 0x6f, 0x70, 0x5f, 0x72, 0x61, 0x74, 0x65, 0x18, 0xec, 0x07, 0x20,
+	0x01, 0x28, 0x02, 0x52, 0x0c, 0x70, 0x69, 0x6e, 0x67, 0x44, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74,
+	0x65, 0x12, 0x27, 0x0a, 0x0f, 0x70, 0x69, 0x6e, 0x67, 0x5f, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63,
+	0x79, 0x5f, 0x6d, 0x73, 0x18, 0xed, 0x07, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0d, 0x70, 0x69, 0x6e,
+	0x67, 0x4c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x4d, 0x73, 0x22, 0x56, 0x0a, 0x17, 0x57, 0x69,
+	0x66, 0x69, 0x41, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x52, 0x65,
+	0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x3b, 0x0a, 0x09, 0x63, 0x68, 0x61, 0x6c, 0x6c, 0x65, 0x6e,
+	0x67, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65,
+	0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x53, 0x69, 0x67,
+	0x6e, 0x65, 0x64, 0x44, 0x61, 0x74, 0x61, 0x52, 0x09, 0x63, 0x68, 0x61, 0x6c, 0x6c, 0x65, 0x6e,
+	0x67, 0x65, 0x22, 0x8e, 0x01, 0x0a, 0x18, 0x57, 0x69, 0x66, 0x69, 0x41, 0x75, 0x74, 0x68, 0x65,
+	0x6e, 0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12,
+	0x38, 0x0a, 0x04, 0x77, 0x69, 0x66, 0x69, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e,
+	0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63,
+	0x65, 0x2e, 0x43, 0x68, 0x61, 0x6c, 0x6c, 0x65, 0x6e, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x52, 0x04, 0x77, 0x69, 0x66, 0x69, 0x12, 0x38, 0x0a, 0x04, 0x64, 0x69, 0x73,
+	0x68, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x24, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58,
+	0x2e, 0x41, 0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x43, 0x68, 0x61, 0x6c,
+	0x6c, 0x65, 0x6e, 0x67, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x52, 0x04, 0x64,
+	0x69, 0x73, 0x68, 0x22, 0x32, 0x0a, 0x17, 0x57, 0x69, 0x66, 0x69, 0x41, 0x63, 0x63, 0x6f, 0x75,
+	0x6e, 0x74, 0x42, 0x6f, 0x6e, 0x64, 0x69, 0x6e, 0x67, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x12, 0x17,
+	0x0a, 0x07, 0x64, 0x69, 0x73, 0x68, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52,
+	0x06, 0x64, 0x69, 0x73, 0x68, 0x49, 0x64, 0x22, 0xfe, 0x04, 0x0a, 0x0b, 0x50, 0x69, 0x6e, 0x67,
+	0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x73, 0x12, 0x26, 0x0a, 0x0f, 0x6c, 0x61, 0x74, 0x65, 0x6e,
+	0x63, 0x79, 0x5f, 0x6d, 0x65, 0x61, 0x6e, 0x5f, 0x6d, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x02,
+	0x52, 0x0d, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x4d, 0x65, 0x61, 0x6e, 0x4d, 0x73, 0x12,
+	0x2a, 0x0a, 0x11, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x5f, 0x73, 0x74, 0x64, 0x64, 0x65,
+	0x76, 0x5f, 0x6d, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0f, 0x6c, 0x61, 0x74, 0x65,
+	0x6e, 0x63, 0x79, 0x53, 0x74, 0x64, 0x64, 0x65, 0x76, 0x4d, 0x73, 0x12, 0x2b, 0x0a, 0x12, 0x6c,
+	0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x5f, 0x6d, 0x65, 0x61, 0x6e, 0x5f, 0x6d, 0x73, 0x5f, 0x35,
+	0x6d, 0x18, 0x03, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0f, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79,
+	0x4d, 0x65, 0x61, 0x6e, 0x4d, 0x73, 0x35, 0x6d, 0x12, 0x2b, 0x0a, 0x12, 0x6c, 0x61, 0x74, 0x65,
+	0x6e, 0x63, 0x79, 0x5f, 0x6d, 0x65, 0x61, 0x6e, 0x5f, 0x6d, 0x73, 0x5f, 0x31, 0x68, 0x18, 0x04,
+	0x20, 0x01, 0x28, 0x02, 0x52, 0x0f, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x4d, 0x65, 0x61,
+	0x6e, 0x4d, 0x73, 0x31, 0x68, 0x12, 0x2b, 0x0a, 0x12, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79,
+	0x5f, 0x6d, 0x65, 0x61, 0x6e, 0x5f, 0x6d, 0x73, 0x5f, 0x31, 0x64, 0x18, 0x05, 0x20, 0x01, 0x28,
+	0x02, 0x52, 0x0f, 0x6c, 0x61, 0x74, 0x65, 0x6e, 0x63, 0x79, 0x4d, 0x65, 0x61, 0x6e, 0x4d, 0x73,
+	0x31, 0x64, 0x12, 0x1b, 0x0a, 0x09, 0x64, 0x72, 0x6f, 0x70, 0x5f, 0x72, 0x61, 0x74, 0x65, 0x18,
+	0x06, 0x20, 0x01, 0x28, 0x02, 0x52, 0x08, 0x64, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74, 0x65, 0x12,
+	0x20, 0x0a, 0x0c, 0x64, 0x72, 0x6f, 0x70, 0x5f, 0x72, 0x61, 0x74, 0x65, 0x5f, 0x35, 0x6d, 0x18,
+	0x07, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0a, 0x64, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74, 0x65, 0x35,
+	0x6d, 0x12, 0x20, 0x0a, 0x0c, 0x64, 0x72, 0x6f, 0x70, 0x5f, 0x72, 0x61, 0x74, 0x65, 0x5f, 0x31,
+	0x68, 0x18, 0x08, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0a, 0x64, 0x72, 0x6f, 0x70, 0x52, 0x61, 0x74,
+	0x65, 0x31, 0x68, 0x12, 0x20, 0x0a, 0x0c, 0x64, 0x72, 0x6f, 0x70, 0x5f, 0x72, 0x61, 0x74, 0x65,
+	0x5f, 0x31, 0x64, 0x18, 0x09, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0a, 0x64, 0x72, 0x6f, 0x70, 0x52,
+	0x61, 0x74, 0x65, 0x31, 0x64, 0x12, 0x3b, 0x0a, 0x1a, 0x73, 0x65, 0x63, 0x6f, 0x6e, 0x64, 0x73,
+	0x5f, 0x73, 0x69, 0x6e, 0x63, 0x65, 0x5f, 0x6c, 0x61, 0x73, 0x74, 0x5f, 0x73, 0x75, 0x63, 0x63,
+	0x65, 0x73, 0x73, 0x18, 0x0a, 0x20, 0x01, 0x28, 0x02, 0x52, 0x17, 0x73, 0x65, 0x63, 0x6f, 0x6e,
+	0x64, 0x73, 0x53, 0x69, 0x6e, 0x63, 0x65, 0x4c, 0x61, 0x73, 0x74, 0x53, 0x75, 0x63, 0x63, 0x65,
+	0x73, 0x73, 0x12, 0x3e, 0x0a, 0x1c, 0x73, 0x65, 0x63, 0x6f, 0x6e, 0x64, 0x73, 0x5f, 0x73, 0x69,
+	0x6e, 0x63, 0x65, 0x5f, 0x6c, 0x61, 0x73, 0x74, 0x5f, 0x31, 0x73, 0x5f, 0x6f, 0x75, 0x74, 0x61,
+	0x67, 0x65, 0x18, 0x0b, 0x20, 0x01, 0x28, 0x02, 0x52, 0x18, 0x73, 0x65, 0x63, 0x6f, 0x6e, 0x64,
+	0x73, 0x53, 0x69, 0x6e, 0x63, 0x65, 0x4c, 0x61, 0x73, 0x74, 0x31, 0x73, 0x4f, 0x75, 0x74, 0x61,
+	0x67, 0x65, 0x12, 0x3e, 0x0a, 0x1c, 0x73, 0x65, 0x63, 0x6f, 0x6e, 0x64, 0x73, 0x5f, 0x73, 0x69,
+	0x6e, 0x63, 0x65, 0x5f, 0x6c, 0x61, 0x73, 0x74, 0x5f, 0x35, 0x73, 0x5f, 0x6f, 0x75, 0x74, 0x61,
+	0x67, 0x65, 0x18, 0x0c, 0x20, 0x01, 0x28, 0x02, 0x52, 0x18, 0x73, 0x65, 0x63, 0x6f, 0x6e, 0x64,
+	0x73, 0x53, 0x69, 0x6e, 0x63, 0x65, 0x4c, 0x61, 0x73, 0x74, 0x35, 0x73, 0x4f, 0x75, 0x74, 0x61,
+	0x67, 0x65, 0x12, 0x29, 0x0a, 0x11, 0x68, 0x61, 0x70, 0x70, 0x79, 0x5f, 0x68, 0x6f, 0x75, 0x72,
+	0x73, 0x5f, 0x31, 0x73, 0x5f, 0x31, 0x64, 0x18, 0x0d, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0e, 0x68,
+	0x61, 0x70, 0x70, 0x79, 0x48, 0x6f, 0x75, 0x72, 0x73, 0x31, 0x73, 0x31, 0x64, 0x12, 0x29, 0x0a,
+	0x11, 0x68, 0x61, 0x70, 0x70, 0x79, 0x5f, 0x68, 0x6f, 0x75, 0x72, 0x73, 0x5f, 0x35, 0x73, 0x5f,
+	0x31, 0x64, 0x18, 0x0e, 0x20, 0x01, 0x28, 0x02, 0x52, 0x0e, 0x68, 0x61, 0x70, 0x70, 0x79, 0x48,
+	0x6f, 0x75, 0x72, 0x73, 0x35, 0x73, 0x31, 0x64, 0x22, 0x1b, 0x0a, 0x19, 0x57, 0x69, 0x66, 0x69,
+	0x47, 0x65, 0x74, 0x50, 0x69, 0x6e, 0x67, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x73, 0x52, 0x65,
+	0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x58, 0x0a, 0x1a, 0x57, 0x69, 0x66, 0x69, 0x47, 0x65, 0x74,
+	0x50, 0x69, 0x6e, 0x67, 0x4d, 0x65, 0x74, 0x72, 0x69, 0x63, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f,
+	0x6e, 0x73, 0x65, 0x12, 0x3a, 0x0a, 0x08, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x18,
+	0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41,
+	0x50, 0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x2e, 0x50, 0x69, 0x6e, 0x67, 0x4d, 0x65,
+	0x74, 0x72, 0x69, 0x63, 0x73, 0x52, 0x08, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x42,
+	0x17, 0x5a, 0x15, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x61, 0x70,
+	0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
+}
+
+var (
+	file_spacex_api_device_wifi_proto_rawDescOnce sync.Once
+	file_spacex_api_device_wifi_proto_rawDescData = file_spacex_api_device_wifi_proto_rawDesc
+)
+
+func file_spacex_api_device_wifi_proto_rawDescGZIP() []byte {
+	file_spacex_api_device_wifi_proto_rawDescOnce.Do(func() {
+		file_spacex_api_device_wifi_proto_rawDescData = protoimpl.X.CompressGZIP(file_spacex_api_device_wifi_proto_rawDescData)
+	})
+	return file_spacex_api_device_wifi_proto_rawDescData
+}
+
+var file_spacex_api_device_wifi_proto_enumTypes = make([]protoimpl.EnumInfo, 1)
+var file_spacex_api_device_wifi_proto_msgTypes = make([]protoimpl.MessageInfo, 18)
+var file_spacex_api_device_wifi_proto_goTypes = []interface{}{
+	(WifiClient_Interface)(0),           // 0: SpaceX.API.Device.WifiClient.Interface
+	(*WifiSetConfigRequest)(nil),        // 1: SpaceX.API.Device.WifiSetConfigRequest
+	(*WifiSetConfigResponse)(nil),       // 2: SpaceX.API.Device.WifiSetConfigResponse
+	(*WifiGetClientsRequest)(nil),       // 3: SpaceX.API.Device.WifiGetClientsRequest
+	(*WifiGetClientsResponse)(nil),      // 4: SpaceX.API.Device.WifiGetClientsResponse
+	(*WifiGetHistoryResponse)(nil),      // 5: SpaceX.API.Device.WifiGetHistoryResponse
+	(*WifiNewClientConnectedEvent)(nil), // 6: SpaceX.API.Device.WifiNewClientConnectedEvent
+	(*WifiClient)(nil),                  // 7: SpaceX.API.Device.WifiClient
+	(*WifiSetupRequest)(nil),            // 8: SpaceX.API.Device.WifiSetupRequest
+	(*WifiSetupResponse)(nil),           // 9: SpaceX.API.Device.WifiSetupResponse
+	(*WifiGetStatusResponse)(nil),       // 10: SpaceX.API.Device.WifiGetStatusResponse
+	(*WifiAuthenticateRequest)(nil),     // 11: SpaceX.API.Device.WifiAuthenticateRequest
+	(*WifiAuthenticateResponse)(nil),    // 12: SpaceX.API.Device.WifiAuthenticateResponse
+	(*WifiAccountBondingEvent)(nil),     // 13: SpaceX.API.Device.WifiAccountBondingEvent
+	(*PingMetrics)(nil),                 // 14: SpaceX.API.Device.PingMetrics
+	(*WifiGetPingMetricsRequest)(nil),   // 15: SpaceX.API.Device.WifiGetPingMetricsRequest
+	(*WifiGetPingMetricsResponse)(nil),  // 16: SpaceX.API.Device.WifiGetPingMetricsResponse
+	(*WifiClient_RxStats)(nil),          // 17: SpaceX.API.Device.WifiClient.RxStats
+	(*WifiClient_TxStats)(nil),          // 18: SpaceX.API.Device.WifiClient.TxStats
+	(*WifiConfig)(nil),                  // 19: SpaceX.API.Device.WifiConfig
+	(*DeviceInfo)(nil),                  // 20: SpaceX.API.Device.DeviceInfo
+	(*DeviceState)(nil),                 // 21: SpaceX.API.Device.DeviceState
+	(*SignedData)(nil),                  // 22: SpaceX.API.Device.SignedData
+	(*ChallengeResponse)(nil),           // 23: SpaceX.API.Device.ChallengeResponse
+}
+var file_spacex_api_device_wifi_proto_depIdxs = []int32{
+	19, // 0: SpaceX.API.Device.WifiSetConfigRequest.wifi_config:type_name -> SpaceX.API.Device.WifiConfig
+	7,  // 1: SpaceX.API.Device.WifiGetClientsResponse.clients:type_name -> SpaceX.API.Device.WifiClient
+	7,  // 2: SpaceX.API.Device.WifiNewClientConnectedEvent.client:type_name -> SpaceX.API.Device.WifiClient
+	17, // 3: SpaceX.API.Device.WifiClient.rx_stats:type_name -> SpaceX.API.Device.WifiClient.RxStats
+	18, // 4: SpaceX.API.Device.WifiClient.tx_stats:type_name -> SpaceX.API.Device.WifiClient.TxStats
+	0,  // 5: SpaceX.API.Device.WifiClient.iface:type_name -> SpaceX.API.Device.WifiClient.Interface
+	20, // 6: SpaceX.API.Device.WifiGetStatusResponse.device_info:type_name -> SpaceX.API.Device.DeviceInfo
+	21, // 7: SpaceX.API.Device.WifiGetStatusResponse.device_state:type_name -> SpaceX.API.Device.DeviceState
+	7,  // 8: SpaceX.API.Device.WifiGetStatusResponse.clients:type_name -> SpaceX.API.Device.WifiClient
+	22, // 9: SpaceX.API.Device.WifiAuthenticateRequest.challenge:type_name -> SpaceX.API.Device.SignedData
+	23, // 10: SpaceX.API.Device.WifiAuthenticateResponse.wifi:type_name -> SpaceX.API.Device.ChallengeResponse
+	23, // 11: SpaceX.API.Device.WifiAuthenticateResponse.dish:type_name -> SpaceX.API.Device.ChallengeResponse
+	14, // 12: SpaceX.API.Device.WifiGetPingMetricsResponse.internet:type_name -> SpaceX.API.Device.PingMetrics
+	13, // [13:13] is the sub-list for method output_type
+	13, // [13:13] is the sub-list for method input_type
+	13, // [13:13] is the sub-list for extension type_name
+	13, // [13:13] is the sub-list for extension extendee
+	0,  // [0:13] is the sub-list for field type_name
+}
+
+func init() { file_spacex_api_device_wifi_proto_init() }
+func file_spacex_api_device_wifi_proto_init() {
+	if File_spacex_api_device_wifi_proto != nil {
+		return
+	}
+	file_spacex_api_device_common_proto_init()
+	file_spacex_api_device_wifi_config_proto_init()
+	if !protoimpl.UnsafeEnabled {
+		file_spacex_api_device_wifi_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiSetConfigRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiSetConfigResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiGetClientsRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiGetClientsResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiGetHistoryResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiNewClientConnectedEvent); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiClient); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiSetupRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[8].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiSetupResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[9].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiGetStatusResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[10].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiAuthenticateRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[11].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiAuthenticateResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[12].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiAccountBondingEvent); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[13].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*PingMetrics); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[14].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiGetPingMetricsRequest); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[15].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiGetPingMetricsResponse); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[16].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiClient_RxStats); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+		file_spacex_api_device_wifi_proto_msgTypes[17].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiClient_TxStats); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+	}
+	type x struct{}
+	out := protoimpl.TypeBuilder{
+		File: protoimpl.DescBuilder{
+			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+			RawDescriptor: file_spacex_api_device_wifi_proto_rawDesc,
+			NumEnums:      1,
+			NumMessages:   18,
+			NumExtensions: 0,
+			NumServices:   0,
+		},
+		GoTypes:           file_spacex_api_device_wifi_proto_goTypes,
+		DependencyIndexes: file_spacex_api_device_wifi_proto_depIdxs,
+		EnumInfos:         file_spacex_api_device_wifi_proto_enumTypes,
+		MessageInfos:      file_spacex_api_device_wifi_proto_msgTypes,
+	}.Build()
+	File_spacex_api_device_wifi_proto = out.File
+	file_spacex_api_device_wifi_proto_rawDesc = nil
+	file_spacex_api_device_wifi_proto_goTypes = nil
+	file_spacex_api_device_wifi_proto_depIdxs = nil
+}
blob - /dev/null
blob + b4060d5473f2b1c106f7da653be4577736a3df10 (mode 644)
--- /dev/null
+++ device/wifi_config.pb.go
@@ -0,0 +1,241 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// 	protoc-gen-go v1.28.1
+// 	protoc        v3.21.6
+// source: spacex/api/device/wifi_config.proto
+
+package device
+
+import (
+	protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+	protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+	reflect "reflect"
+	sync "sync"
+)
+
+const (
+	// Verify that this generated code is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+	// Verify that runtime/protoimpl is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+type WifiConfig struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	NetworkName          string `protobuf:"bytes,1,opt,name=network_name,json=networkName,proto3" json:"network_name,omitempty"`
+	ApplyNetworkName     bool   `protobuf:"varint,1001,opt,name=apply_network_name,json=applyNetworkName,proto3" json:"apply_network_name,omitempty"`
+	NetworkPassword      string `protobuf:"bytes,2,opt,name=network_password,json=networkPassword,proto3" json:"network_password,omitempty"`
+	ApplyNetworkPassword bool   `protobuf:"varint,1002,opt,name=apply_network_password,json=applyNetworkPassword,proto3" json:"apply_network_password,omitempty"`
+	CountryCode          string `protobuf:"bytes,3,opt,name=country_code,json=countryCode,proto3" json:"country_code,omitempty"`
+	WifiDisabled         bool   `protobuf:"varint,4,opt,name=wifi_disabled,json=wifiDisabled,proto3" json:"wifi_disabled,omitempty"`
+	ApplyWifiDisabled    bool   `protobuf:"varint,1003,opt,name=apply_wifi_disabled,json=applyWifiDisabled,proto3" json:"apply_wifi_disabled,omitempty"`
+	LanIpv4              string `protobuf:"bytes,5,opt,name=lan_ipv4,json=lanIpv4,proto3" json:"lan_ipv4,omitempty"`
+	LanIpv4SubnetMask    string `protobuf:"bytes,6,opt,name=lan_ipv4_subnet_mask,json=lanIpv4SubnetMask,proto3" json:"lan_ipv4_subnet_mask,omitempty"`
+	SetupComplete        bool   `protobuf:"varint,7,opt,name=setup_complete,json=setupComplete,proto3" json:"setup_complete,omitempty"`
+}
+
+func (x *WifiConfig) Reset() {
+	*x = WifiConfig{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_device_wifi_config_proto_msgTypes[0]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *WifiConfig) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*WifiConfig) ProtoMessage() {}
+
+func (x *WifiConfig) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_device_wifi_config_proto_msgTypes[0]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use WifiConfig.ProtoReflect.Descriptor instead.
+func (*WifiConfig) Descriptor() ([]byte, []int) {
+	return file_spacex_api_device_wifi_config_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *WifiConfig) GetNetworkName() string {
+	if x != nil {
+		return x.NetworkName
+	}
+	return ""
+}
+
+func (x *WifiConfig) GetApplyNetworkName() bool {
+	if x != nil {
+		return x.ApplyNetworkName
+	}
+	return false
+}
+
+func (x *WifiConfig) GetNetworkPassword() string {
+	if x != nil {
+		return x.NetworkPassword
+	}
+	return ""
+}
+
+func (x *WifiConfig) GetApplyNetworkPassword() bool {
+	if x != nil {
+		return x.ApplyNetworkPassword
+	}
+	return false
+}
+
+func (x *WifiConfig) GetCountryCode() string {
+	if x != nil {
+		return x.CountryCode
+	}
+	return ""
+}
+
+func (x *WifiConfig) GetWifiDisabled() bool {
+	if x != nil {
+		return x.WifiDisabled
+	}
+	return false
+}
+
+func (x *WifiConfig) GetApplyWifiDisabled() bool {
+	if x != nil {
+		return x.ApplyWifiDisabled
+	}
+	return false
+}
+
+func (x *WifiConfig) GetLanIpv4() string {
+	if x != nil {
+		return x.LanIpv4
+	}
+	return ""
+}
+
+func (x *WifiConfig) GetLanIpv4SubnetMask() string {
+	if x != nil {
+		return x.LanIpv4SubnetMask
+	}
+	return ""
+}
+
+func (x *WifiConfig) GetSetupComplete() bool {
+	if x != nil {
+		return x.SetupComplete
+	}
+	return false
+}
+
+var File_spacex_api_device_wifi_config_proto protoreflect.FileDescriptor
+
+var file_spacex_api_device_wifi_config_proto_rawDesc = []byte{
+	0x0a, 0x23, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76,
+	0x69, 0x63, 0x65, 0x2f, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2e,
+	0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x11, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e, 0x41, 0x50,
+	0x49, 0x2e, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x22, 0xac, 0x03, 0x0a, 0x0a, 0x57, 0x69, 0x66,
+	0x69, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x12, 0x21, 0x0a, 0x0c, 0x6e, 0x65, 0x74, 0x77, 0x6f,
+	0x72, 0x6b, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x6e,
+	0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x2d, 0x0a, 0x12, 0x61, 0x70,
+	0x70, 0x6c, 0x79, 0x5f, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x5f, 0x6e, 0x61, 0x6d, 0x65,
+	0x18, 0xe9, 0x07, 0x20, 0x01, 0x28, 0x08, 0x52, 0x10, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x4e, 0x65,
+	0x74, 0x77, 0x6f, 0x72, 0x6b, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x29, 0x0a, 0x10, 0x6e, 0x65, 0x74,
+	0x77, 0x6f, 0x72, 0x6b, 0x5f, 0x70, 0x61, 0x73, 0x73, 0x77, 0x6f, 0x72, 0x64, 0x18, 0x02, 0x20,
+	0x01, 0x28, 0x09, 0x52, 0x0f, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x50, 0x61, 0x73, 0x73,
+	0x77, 0x6f, 0x72, 0x64, 0x12, 0x35, 0x0a, 0x16, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x5f, 0x6e, 0x65,
+	0x74, 0x77, 0x6f, 0x72, 0x6b, 0x5f, 0x70, 0x61, 0x73, 0x73, 0x77, 0x6f, 0x72, 0x64, 0x18, 0xea,
+	0x07, 0x20, 0x01, 0x28, 0x08, 0x52, 0x14, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x4e, 0x65, 0x74, 0x77,
+	0x6f, 0x72, 0x6b, 0x50, 0x61, 0x73, 0x73, 0x77, 0x6f, 0x72, 0x64, 0x12, 0x21, 0x0a, 0x0c, 0x63,
+	0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x5f, 0x63, 0x6f, 0x64, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28,
+	0x09, 0x52, 0x0b, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x43, 0x6f, 0x64, 0x65, 0x12, 0x23,
+	0x0a, 0x0d, 0x77, 0x69, 0x66, 0x69, 0x5f, 0x64, 0x69, 0x73, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x18,
+	0x04, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0c, 0x77, 0x69, 0x66, 0x69, 0x44, 0x69, 0x73, 0x61, 0x62,
+	0x6c, 0x65, 0x64, 0x12, 0x2f, 0x0a, 0x13, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x5f, 0x77, 0x69, 0x66,
+	0x69, 0x5f, 0x64, 0x69, 0x73, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x18, 0xeb, 0x07, 0x20, 0x01, 0x28,
+	0x08, 0x52, 0x11, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x57, 0x69, 0x66, 0x69, 0x44, 0x69, 0x73, 0x61,
+	0x62, 0x6c, 0x65, 0x64, 0x12, 0x19, 0x0a, 0x08, 0x6c, 0x61, 0x6e, 0x5f, 0x69, 0x70, 0x76, 0x34,
+	0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x6c, 0x61, 0x6e, 0x49, 0x70, 0x76, 0x34, 0x12,
+	0x2f, 0x0a, 0x14, 0x6c, 0x61, 0x6e, 0x5f, 0x69, 0x70, 0x76, 0x34, 0x5f, 0x73, 0x75, 0x62, 0x6e,
+	0x65, 0x74, 0x5f, 0x6d, 0x61, 0x73, 0x6b, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x11, 0x6c,
+	0x61, 0x6e, 0x49, 0x70, 0x76, 0x34, 0x53, 0x75, 0x62, 0x6e, 0x65, 0x74, 0x4d, 0x61, 0x73, 0x6b,
+	0x12, 0x25, 0x0a, 0x0e, 0x73, 0x65, 0x74, 0x75, 0x70, 0x5f, 0x63, 0x6f, 0x6d, 0x70, 0x6c, 0x65,
+	0x74, 0x65, 0x18, 0x07, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0d, 0x73, 0x65, 0x74, 0x75, 0x70, 0x43,
+	0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x42, 0x17, 0x5a, 0x15, 0x73, 0x70, 0x61, 0x63, 0x65,
+	0x78, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x64, 0x65, 0x76, 0x69, 0x63, 0x65,
+	0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
+}
+
+var (
+	file_spacex_api_device_wifi_config_proto_rawDescOnce sync.Once
+	file_spacex_api_device_wifi_config_proto_rawDescData = file_spacex_api_device_wifi_config_proto_rawDesc
+)
+
+func file_spacex_api_device_wifi_config_proto_rawDescGZIP() []byte {
+	file_spacex_api_device_wifi_config_proto_rawDescOnce.Do(func() {
+		file_spacex_api_device_wifi_config_proto_rawDescData = protoimpl.X.CompressGZIP(file_spacex_api_device_wifi_config_proto_rawDescData)
+	})
+	return file_spacex_api_device_wifi_config_proto_rawDescData
+}
+
+var file_spacex_api_device_wifi_config_proto_msgTypes = make([]protoimpl.MessageInfo, 1)
+var file_spacex_api_device_wifi_config_proto_goTypes = []interface{}{
+	(*WifiConfig)(nil), // 0: SpaceX.API.Device.WifiConfig
+}
+var file_spacex_api_device_wifi_config_proto_depIdxs = []int32{
+	0, // [0:0] is the sub-list for method output_type
+	0, // [0:0] is the sub-list for method input_type
+	0, // [0:0] is the sub-list for extension type_name
+	0, // [0:0] is the sub-list for extension extendee
+	0, // [0:0] is the sub-list for field type_name
+}
+
+func init() { file_spacex_api_device_wifi_config_proto_init() }
+func file_spacex_api_device_wifi_config_proto_init() {
+	if File_spacex_api_device_wifi_config_proto != nil {
+		return
+	}
+	if !protoimpl.UnsafeEnabled {
+		file_spacex_api_device_wifi_config_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*WifiConfig); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+	}
+	type x struct{}
+	out := protoimpl.TypeBuilder{
+		File: protoimpl.DescBuilder{
+			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+			RawDescriptor: file_spacex_api_device_wifi_config_proto_rawDesc,
+			NumEnums:      0,
+			NumMessages:   1,
+			NumExtensions: 0,
+			NumServices:   0,
+		},
+		GoTypes:           file_spacex_api_device_wifi_config_proto_goTypes,
+		DependencyIndexes: file_spacex_api_device_wifi_config_proto_depIdxs,
+		MessageInfos:      file_spacex_api_device_wifi_config_proto_msgTypes,
+	}.Build()
+	File_spacex_api_device_wifi_config_proto = out.File
+	file_spacex_api_device_wifi_config_proto_rawDesc = nil
+	file_spacex_api_device_wifi_config_proto_goTypes = nil
+	file_spacex_api_device_wifi_config_proto_depIdxs = nil
+}
blob - /dev/null
blob + 8c710bf7387a38c7fd1185cb0c3c395cc5afe936 (mode 644)
Binary files /dev/null and device.protoset differ
blob - /dev/null
blob + 3d1f7c1daf4e9476dd4164418e5e9595c4dd33a2 (mode 644)
--- /dev/null
+++ go.mod
@@ -0,0 +1,16 @@
+module olowe.co/dishy
+
+go 1.18
+
+require (
+	google.golang.org/grpc v1.51.0
+	google.golang.org/protobuf v1.27.1
+)
+
+require (
+	github.com/golang/protobuf v1.5.2 // indirect
+	golang.org/x/net v0.0.0-20220722155237-a158d28d115b // indirect
+	golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f // indirect
+	golang.org/x/text v0.4.0 // indirect
+	google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013 // indirect
+)
blob - /dev/null
blob + 33a7a3e365203f348302b1899791b0f9156d0815 (mode 644)
--- /dev/null
+++ go.sum
@@ -0,0 +1,78 @@
+cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
+github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
+github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU=
+github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw=
+github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4=
+github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
+github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
+github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
+github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
+github.com/golang/protobuf v1.3.2/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
+github.com/golang/protobuf v1.4.0-rc.1/go.mod h1:ceaxUfeHdC40wWswd/P6IGgMaK3YpKi5j83Wpe3EHw8=
+github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:xKAWHe0F5eneWXFV3EuXVDTCmh+JuBKY0li0aMyXATA=
+github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs=
+github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w=
+github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0=
+github.com/golang/protobuf v1.4.1/go.mod h1:U8fpvMrcmy5pZrNK1lt4xCsGvpyWQ/VVv6QDs8UjoX8=
+github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk=
+github.com/golang/protobuf v1.5.2 h1:ROPKBNFfQgOUMifHyP+KYbvpjbdoFNs+aK7DXlji0Tw=
+github.com/golang/protobuf v1.5.2/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY=
+github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
+github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
+github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
+github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
+github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
+github.com/google/go-cmp v0.5.6 h1:BKbKCqvP6I+rmFHt06ZmyQtvB8xAkWdhFyr0ZUNZcxQ=
+github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA=
+golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
+golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
+golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
+golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU=
+golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
+golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
+golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
+golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
+golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
+golang.org/x/net v0.0.0-20220722155237-a158d28d115b h1:PxfKdU9lEEDYjdIzOtC4qFWgkU2rGHdKlKowJSMN9h0=
+golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
+golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
+golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
+golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
+golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f h1:v4INt8xihDGvnrfjMDVXGxw9wrfxYyCjk0KbXjhR55s=
+golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
+golang.org/x/text v0.4.0 h1:BrVqGRd7+k1DiOgtnFvAkoQEWQvBc25ouMJM6429SFg=
+golang.org/x/text v0.4.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
+golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
+golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY=
+golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
+golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q=
+golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
+golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
+google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
+google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
+google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
+google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc=
+google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013 h1:+kGHl1aib/qcwaRi1CbqBZ1rk19r85MNUf8HaBghugY=
+google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013/go.mod h1:NbSheEEYHJ7i3ixzK3sjbqSGDJWnxyFXZblF3eUsNvo=
+google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
+google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg=
+google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk=
+google.golang.org/grpc v1.51.0 h1:E1eGv1FTqoLIdnBCZufiSHgKjlqG6fKFf6pPWtMTh8U=
+google.golang.org/grpc v1.51.0/go.mod h1:wgNDFcnuBGmxLKI/qn4T+m5BtEBYXJPvibbUPsAIPww=
+google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
+google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0=
+google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM=
+google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE=
+google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo=
+google.golang.org/protobuf v1.22.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
+google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
+google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw=
+google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
+google.golang.org/protobuf v1.27.1 h1:SnqbnDw1V7RiZcXPx5MEeqPv2s79L9i7BJUlG/+RurQ=
+google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
+honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
+honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
blob - /dev/null
blob + f95bb0fde4d4ffe28b8c451986e35906f8ec2df3 (mode 755)
--- /dev/null
+++ protoc.sh
@@ -0,0 +1,61 @@
+#!/bin/sh
+
+# protoc.sh generates Go code for the Starlink Device gRPC service.
+# First it calls grpcurl[1] to fetch the protobuf file descriptor set using server reflection.
+# Using the descriptor set, protoc[2] generates the Go code for the proto files we care about.
+#
+# By default it connects to the default Dishy address (see DefaultDishyAddr).
+# A different address can be specified as an argument. For example:
+#
+#	protoc.sh 172.19.248.42:9100
+#
+# This can be useful if the device is only available through a tunnel or VPN.
+#
+# [1]: https://pkg.go.dev/github.com/fullstorydev/grpcurl
+# [2]: https://grpc.io/docs/protoc-installation/
+
+usage="usage: protoc.sh [address]"
+
+# The Dishy exposes its gRPC service on this adress by default.
+default_dishy_addr=`grep DefaultDishyAddr *.go | awk '{print $4}' | tr -d '"'`
+
+if test $# -ge 2
+then
+	echo $usage
+	exit 1
+fi
+
+addr=$default_dishy_addr
+if test -n "$1"
+then
+	addr=$1
+fi
+grpcurl -plaintext -protoset-out device.protoset $addr describe SpaceX.API.Device.Device
+
+# The protoc command, without proto file arguments, to generate the Go code.
+# From https://grpc.io/docs/languages/go/quickstart/#regenerate-grpc-code
+# For a protobuf reference:
+# https://developers.google.com/protocol-buffers/docs/reference/go-generated
+
+# Strip the spacex.com/api prefix so package imports can be resolved within our Go module.
+# https://developers.google.com/protocol-buffers/docs/reference/go-generated#invocation
+module_opt="--go_opt module=spacex.com/api --go-grpc_opt module=spacex.com/api"
+
+protoc --go_out . --go-grpc_out . --descriptor_set_in device.protoset \
+	$module_opt \
+	spacex/api/common/status/status.proto
+
+# Device proto files import status.proto, so set the corresponding Go
+# package import path for the status package we generated previously.
+gomodule=`grep module go.mod | awk '{print $2}'`
+import_opt="--go_opt Mspacex/api/common/status/status.proto=$gomodule/status"
+files="spacex/api/device/command.proto
+	spacex/api/device/common.proto
+	spacex/api/device/device.proto
+	spacex/api/device/dish.proto
+	spacex/api/device/transceiver.proto
+	spacex/api/device/wifi.proto
+	spacex/api/device/wifi_config.proto"
+protoc --go_out . --go-grpc_out . --descriptor_set_in device.protoset \
+	$module_opt $import_opt \
+	$files
blob - /dev/null
blob + dfb7f76c702196385780c151d6b8681cacf4521a (mode 644)
--- /dev/null
+++ status/status.pb.go
@@ -0,0 +1,154 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// versions:
+// 	protoc-gen-go v1.28.1
+// 	protoc        v3.21.6
+// source: spacex/api/common/status/status.proto
+
+package status
+
+import (
+	protoreflect "google.golang.org/protobuf/reflect/protoreflect"
+	protoimpl "google.golang.org/protobuf/runtime/protoimpl"
+	reflect "reflect"
+	sync "sync"
+)
+
+const (
+	// Verify that this generated code is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
+	// Verify that runtime/protoimpl is sufficiently up-to-date.
+	_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
+)
+
+type Status struct {
+	state         protoimpl.MessageState
+	sizeCache     protoimpl.SizeCache
+	unknownFields protoimpl.UnknownFields
+
+	Code    int32  `protobuf:"varint,1,opt,name=code,proto3" json:"code,omitempty"`
+	Message string `protobuf:"bytes,2,opt,name=message,proto3" json:"message,omitempty"`
+}
+
+func (x *Status) Reset() {
+	*x = Status{}
+	if protoimpl.UnsafeEnabled {
+		mi := &file_spacex_api_common_status_status_proto_msgTypes[0]
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		ms.StoreMessageInfo(mi)
+	}
+}
+
+func (x *Status) String() string {
+	return protoimpl.X.MessageStringOf(x)
+}
+
+func (*Status) ProtoMessage() {}
+
+func (x *Status) ProtoReflect() protoreflect.Message {
+	mi := &file_spacex_api_common_status_status_proto_msgTypes[0]
+	if protoimpl.UnsafeEnabled && x != nil {
+		ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
+		if ms.LoadMessageInfo() == nil {
+			ms.StoreMessageInfo(mi)
+		}
+		return ms
+	}
+	return mi.MessageOf(x)
+}
+
+// Deprecated: Use Status.ProtoReflect.Descriptor instead.
+func (*Status) Descriptor() ([]byte, []int) {
+	return file_spacex_api_common_status_status_proto_rawDescGZIP(), []int{0}
+}
+
+func (x *Status) GetCode() int32 {
+	if x != nil {
+		return x.Code
+	}
+	return 0
+}
+
+func (x *Status) GetMessage() string {
+	if x != nil {
+		return x.Message
+	}
+	return ""
+}
+
+var File_spacex_api_common_status_status_proto protoreflect.FileDescriptor
+
+var file_spacex_api_common_status_status_proto_rawDesc = []byte{
+	0x0a, 0x25, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x63, 0x6f, 0x6d,
+	0x6d, 0x6f, 0x6e, 0x2f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x2f, 0x73, 0x74, 0x61, 0x74, 0x75,
+	0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x11, 0x53, 0x70, 0x61, 0x63, 0x65, 0x58, 0x2e,
+	0x41, 0x50, 0x49, 0x2e, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x22, 0x36, 0x0a, 0x06, 0x53, 0x74,
+	0x61, 0x74, 0x75, 0x73, 0x12, 0x12, 0x0a, 0x04, 0x63, 0x6f, 0x64, 0x65, 0x18, 0x01, 0x20, 0x01,
+	0x28, 0x05, 0x52, 0x04, 0x63, 0x6f, 0x64, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x6d, 0x65, 0x73, 0x73,
+	0x61, 0x67, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x6d, 0x65, 0x73, 0x73, 0x61,
+	0x67, 0x65, 0x42, 0x17, 0x5a, 0x15, 0x73, 0x70, 0x61, 0x63, 0x65, 0x78, 0x2e, 0x63, 0x6f, 0x6d,
+	0x2f, 0x61, 0x70, 0x69, 0x2f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f,
+	0x74, 0x6f, 0x33,
+}
+
+var (
+	file_spacex_api_common_status_status_proto_rawDescOnce sync.Once
+	file_spacex_api_common_status_status_proto_rawDescData = file_spacex_api_common_status_status_proto_rawDesc
+)
+
+func file_spacex_api_common_status_status_proto_rawDescGZIP() []byte {
+	file_spacex_api_common_status_status_proto_rawDescOnce.Do(func() {
+		file_spacex_api_common_status_status_proto_rawDescData = protoimpl.X.CompressGZIP(file_spacex_api_common_status_status_proto_rawDescData)
+	})
+	return file_spacex_api_common_status_status_proto_rawDescData
+}
+
+var file_spacex_api_common_status_status_proto_msgTypes = make([]protoimpl.MessageInfo, 1)
+var file_spacex_api_common_status_status_proto_goTypes = []interface{}{
+	(*Status)(nil), // 0: SpaceX.API.Status.Status
+}
+var file_spacex_api_common_status_status_proto_depIdxs = []int32{
+	0, // [0:0] is the sub-list for method output_type
+	0, // [0:0] is the sub-list for method input_type
+	0, // [0:0] is the sub-list for extension type_name
+	0, // [0:0] is the sub-list for extension extendee
+	0, // [0:0] is the sub-list for field type_name
+}
+
+func init() { file_spacex_api_common_status_status_proto_init() }
+func file_spacex_api_common_status_status_proto_init() {
+	if File_spacex_api_common_status_status_proto != nil {
+		return
+	}
+	if !protoimpl.UnsafeEnabled {
+		file_spacex_api_common_status_status_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
+			switch v := v.(*Status); i {
+			case 0:
+				return &v.state
+			case 1:
+				return &v.sizeCache
+			case 2:
+				return &v.unknownFields
+			default:
+				return nil
+			}
+		}
+	}
+	type x struct{}
+	out := protoimpl.TypeBuilder{
+		File: protoimpl.DescBuilder{
+			GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
+			RawDescriptor: file_spacex_api_common_status_status_proto_rawDesc,
+			NumEnums:      0,
+			NumMessages:   1,
+			NumExtensions: 0,
+			NumServices:   0,
+		},
+		GoTypes:           file_spacex_api_common_status_status_proto_goTypes,
+		DependencyIndexes: file_spacex_api_common_status_status_proto_depIdxs,
+		MessageInfos:      file_spacex_api_common_status_status_proto_msgTypes,
+	}.Build()
+	File_spacex_api_common_status_status_proto = out.File
+	file_spacex_api_common_status_status_proto_rawDesc = nil
+	file_spacex_api_common_status_status_proto_goTypes = nil
+	file_spacex_api_common_status_status_proto_depIdxs = nil
+}