// Code generated by protoc-gen-go. DO NOT EDIT.
// source: opencensus/proto/agent/common/v1/common.proto

package v1

import (
	fmt "fmt"
	proto "github.com/golang/protobuf/proto"
	timestamp "github.com/golang/protobuf/ptypes/timestamp"
	math "math"
)

// Reference imports to suppress errors if they are not otherwise used.
var _ = proto.Marshal
var _ = fmt.Errorf
var _ = math.Inf

// This is a compile-time assertion to ensure that this generated file
// is compatible with the proto package it is being compiled against.
// A compilation error at this line likely means your copy of the
// proto package needs to be updated.
const _ = proto.ProtoPackageIsVersion3 // please upgrade the proto package

type LibraryInfo_Language int32

const (
	LibraryInfo_LANGUAGE_UNSPECIFIED LibraryInfo_Language = 0
	LibraryInfo_CPP                  LibraryInfo_Language = 1
	LibraryInfo_C_SHARP              LibraryInfo_Language = 2
	LibraryInfo_ERLANG               LibraryInfo_Language = 3
	LibraryInfo_GO_LANG              LibraryInfo_Language = 4
	LibraryInfo_JAVA                 LibraryInfo_Language = 5
	LibraryInfo_NODE_JS              LibraryInfo_Language = 6
	LibraryInfo_PHP                  LibraryInfo_Language = 7
	LibraryInfo_PYTHON               LibraryInfo_Language = 8
	LibraryInfo_RUBY                 LibraryInfo_Language = 9
	LibraryInfo_WEB_JS               LibraryInfo_Language = 10
)

var LibraryInfo_Language_name = map[int32]string{
	0:  "LANGUAGE_UNSPECIFIED",
	1:  "CPP",
	2:  "C_SHARP",
	3:  "ERLANG",
	4:  "GO_LANG",
	5:  "JAVA",
	6:  "NODE_JS",
	7:  "PHP",
	8:  "PYTHON",
	9:  "RUBY",
	10: "WEB_JS",
}

var LibraryInfo_Language_value = map[string]int32{
	"LANGUAGE_UNSPECIFIED": 0,
	"CPP":                  1,
	"C_SHARP":              2,
	"ERLANG":               3,
	"GO_LANG":              4,
	"JAVA":                 5,
	"NODE_JS":              6,
	"PHP":                  7,
	"PYTHON":               8,
	"RUBY":                 9,
	"WEB_JS":               10,
}

func (x LibraryInfo_Language) String() string {
	return proto.EnumName(LibraryInfo_Language_name, int32(x))
}

func (LibraryInfo_Language) EnumDescriptor() ([]byte, []int) {
	return fileDescriptor_126c72ed8a252c84, []int{2, 0}
}

// Identifier metadata of the Node that produces the span or tracing data.
// Note, this is not the metadata about the Node or service that is described by associated spans.
// In the future we plan to extend the identifier proto definition to support
// additional information (e.g cloud id, etc.)
type Node struct {
	// Identifier that uniquely identifies a process within a VM/container.
	Identifier *ProcessIdentifier `protobuf:"bytes,1,opt,name=identifier,proto3" json:"identifier,omitempty"`
	// Information on the OpenCensus Library that initiates the stream.
	LibraryInfo *LibraryInfo `protobuf:"bytes,2,opt,name=library_info,json=libraryInfo,proto3" json:"library_info,omitempty"`
	// Additional information on service.
	ServiceInfo *ServiceInfo `protobuf:"bytes,3,opt,name=service_info,json=serviceInfo,proto3" json:"service_info,omitempty"`
	// Additional attributes.
	Attributes           map[string]string `protobuf:"bytes,4,rep,name=attributes,proto3" json:"attributes,omitempty" protobuf_key:"bytes,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"`
	XXX_NoUnkeyedLiteral struct{}          `json:"-"`
	XXX_unrecognized     []byte            `json:"-"`
	XXX_sizecache        int32             `json:"-"`
}

func (m *Node) Reset()         { *m = Node{} }
func (m *Node) String() string { return proto.CompactTextString(m) }
func (*Node) ProtoMessage()    {}
func (*Node) Descriptor() ([]byte, []int) {
	return fileDescriptor_126c72ed8a252c84, []int{0}
}

func (m *Node) XXX_Unmarshal(b []byte) error {
	return xxx_messageInfo_Node.Unmarshal(m, b)
}
func (m *Node) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
	return xxx_messageInfo_Node.Marshal(b, m, deterministic)
}
func (m *Node) XXX_Merge(src proto.Message) {
	xxx_messageInfo_Node.Merge(m, src)
}
func (m *Node) XXX_Size() int {
	return xxx_messageInfo_Node.Size(m)
}
func (m *Node) XXX_DiscardUnknown() {
	xxx_messageInfo_Node.DiscardUnknown(m)
}

var xxx_messageInfo_Node proto.InternalMessageInfo

func (m *Node) GetIdentifier() *ProcessIdentifier {
	if m != nil {
		return m.Identifier
	}
	return nil
}

func (m *Node) GetLibraryInfo() *LibraryInfo {
	if m != nil {
		return m.LibraryInfo
	}
	return nil
}

func (m *Node) GetServiceInfo() *ServiceInfo {
	if m != nil {
		return m.ServiceInfo
	}
	return nil
}

func (m *Node) GetAttributes() map[string]string {
	if m != nil {
		return m.Attributes
	}
	return nil
}

// Identifier that uniquely identifies a process within a VM/container.
type ProcessIdentifier struct {
	// The host name. Usually refers to the machine/container name.
	// For example: os.Hostname() in Go, socket.gethostname() in Python.
	HostName string `protobuf:"bytes,1,opt,name=host_name,json=hostName,proto3" json:"host_name,omitempty"`
	// Process id.
	Pid uint32 `protobuf:"varint,2,opt,name=pid,proto3" json:"pid,omitempty"`
	// Start time of this ProcessIdentifier. Represented in epoch time.
	StartTimestamp       *timestamp.Timestamp `protobuf:"bytes,3,opt,name=start_timestamp,json=startTimestamp,proto3" json:"start_timestamp,omitempty"`
	XXX_NoUnkeyedLiteral struct{}             `json:"-"`
	XXX_unrecognized     []byte               `json:"-"`
	XXX_sizecache        int32                `json:"-"`
}

func (m *ProcessIdentifier) Reset()         { *m = ProcessIdentifier{} }
func (m *ProcessIdentifier) String() string { return proto.CompactTextString(m) }
func (*ProcessIdentifier) ProtoMessage()    {}
func (*ProcessIdentifier) Descriptor() ([]byte, []int) {
	return fileDescriptor_126c72ed8a252c84, []int{1}
}

func (m *ProcessIdentifier) XXX_Unmarshal(b []byte) error {
	return xxx_messageInfo_ProcessIdentifier.Unmarshal(m, b)
}
func (m *ProcessIdentifier) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
	return xxx_messageInfo_ProcessIdentifier.Marshal(b, m, deterministic)
}
func (m *ProcessIdentifier) XXX_Merge(src proto.Message) {
	xxx_messageInfo_ProcessIdentifier.Merge(m, src)
}
func (m *ProcessIdentifier) XXX_Size() int {
	return xxx_messageInfo_ProcessIdentifier.Size(m)
}
func (m *ProcessIdentifier) XXX_DiscardUnknown() {
	xxx_messageInfo_ProcessIdentifier.DiscardUnknown(m)
}

var xxx_messageInfo_ProcessIdentifier proto.InternalMessageInfo

func (m *ProcessIdentifier) GetHostName() string {
	if m != nil {
		return m.HostName
	}
	return ""
}

func (m *ProcessIdentifier) GetPid() uint32 {
	if m != nil {
		return m.Pid
	}
	return 0
}

func (m *ProcessIdentifier) GetStartTimestamp() *timestamp.Timestamp {
	if m != nil {
		return m.StartTimestamp
	}
	return nil
}

// Information on OpenCensus Library.
type LibraryInfo struct {
	// Language of OpenCensus Library.
	Language LibraryInfo_Language `protobuf:"varint,1,opt,name=language,proto3,enum=opencensus.proto.agent.common.v1.LibraryInfo_Language" json:"language,omitempty"`
	// Version of Agent exporter of Library.
	ExporterVersion string `protobuf:"bytes,2,opt,name=exporter_version,json=exporterVersion,proto3" json:"exporter_version,omitempty"`
	// Version of OpenCensus Library.
	CoreLibraryVersion   string   `protobuf:"bytes,3,opt,name=core_library_version,json=coreLibraryVersion,proto3" json:"core_library_version,omitempty"`
	XXX_NoUnkeyedLiteral struct{} `json:"-"`
	XXX_unrecognized     []byte   `json:"-"`
	XXX_sizecache        int32    `json:"-"`
}

func (m *LibraryInfo) Reset()         { *m = LibraryInfo{} }
func (m *LibraryInfo) String() string { return proto.CompactTextString(m) }
func (*LibraryInfo) ProtoMessage()    {}
func (*LibraryInfo) Descriptor() ([]byte, []int) {
	return fileDescriptor_126c72ed8a252c84, []int{2}
}

func (m *LibraryInfo) XXX_Unmarshal(b []byte) error {
	return xxx_messageInfo_LibraryInfo.Unmarshal(m, b)
}
func (m *LibraryInfo) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
	return xxx_messageInfo_LibraryInfo.Marshal(b, m, deterministic)
}
func (m *LibraryInfo) XXX_Merge(src proto.Message) {
	xxx_messageInfo_LibraryInfo.Merge(m, src)
}
func (m *LibraryInfo) XXX_Size() int {
	return xxx_messageInfo_LibraryInfo.Size(m)
}
func (m *LibraryInfo) XXX_DiscardUnknown() {
	xxx_messageInfo_LibraryInfo.DiscardUnknown(m)
}

var xxx_messageInfo_LibraryInfo proto.InternalMessageInfo

func (m *LibraryInfo) GetLanguage() LibraryInfo_Language {
	if m != nil {
		return m.Language
	}
	return LibraryInfo_LANGUAGE_UNSPECIFIED
}

func (m *LibraryInfo) GetExporterVersion() string {
	if m != nil {
		return m.ExporterVersion
	}
	return ""
}

func (m *LibraryInfo) GetCoreLibraryVersion() string {
	if m != nil {
		return m.CoreLibraryVersion
	}
	return ""
}

// Additional service information.
type ServiceInfo struct {
	// Name of the service.
	Name                 string   `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"`
	XXX_NoUnkeyedLiteral struct{} `json:"-"`
	XXX_unrecognized     []byte   `json:"-"`
	XXX_sizecache        int32    `json:"-"`
}

func (m *ServiceInfo) Reset()         { *m = ServiceInfo{} }
func (m *ServiceInfo) String() string { return proto.CompactTextString(m) }
func (*ServiceInfo) ProtoMessage()    {}
func (*ServiceInfo) Descriptor() ([]byte, []int) {
	return fileDescriptor_126c72ed8a252c84, []int{3}
}

func (m *ServiceInfo) XXX_Unmarshal(b []byte) error {
	return xxx_messageInfo_ServiceInfo.Unmarshal(m, b)
}
func (m *ServiceInfo) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
	return xxx_messageInfo_ServiceInfo.Marshal(b, m, deterministic)
}
func (m *ServiceInfo) XXX_Merge(src proto.Message) {
	xxx_messageInfo_ServiceInfo.Merge(m, src)
}
func (m *ServiceInfo) XXX_Size() int {
	return xxx_messageInfo_ServiceInfo.Size(m)
}
func (m *ServiceInfo) XXX_DiscardUnknown() {
	xxx_messageInfo_ServiceInfo.DiscardUnknown(m)
}

var xxx_messageInfo_ServiceInfo proto.InternalMessageInfo

func (m *ServiceInfo) GetName() string {
	if m != nil {
		return m.Name
	}
	return ""
}

func init() {
	proto.RegisterEnum("opencensus.proto.agent.common.v1.LibraryInfo_Language", LibraryInfo_Language_name, LibraryInfo_Language_value)
	proto.RegisterType((*Node)(nil), "opencensus.proto.agent.common.v1.Node")
	proto.RegisterMapType((map[string]string)(nil), "opencensus.proto.agent.common.v1.Node.AttributesEntry")
	proto.RegisterType((*ProcessIdentifier)(nil), "opencensus.proto.agent.common.v1.ProcessIdentifier")
	proto.RegisterType((*LibraryInfo)(nil), "opencensus.proto.agent.common.v1.LibraryInfo")
	proto.RegisterType((*ServiceInfo)(nil), "opencensus.proto.agent.common.v1.ServiceInfo")
}

func init() {
	proto.RegisterFile("opencensus/proto/agent/common/v1/common.proto", fileDescriptor_126c72ed8a252c84)
}

var fileDescriptor_126c72ed8a252c84 = []byte{
	// 618 bytes of a gzipped FileDescriptorProto
	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x8c, 0x94, 0x4f, 0x6e, 0xda, 0x4e,
	0x14, 0xc7, 0x7f, 0xc6, 0x24, 0x81, 0xe7, 0x5f, 0x13, 0x77, 0x94, 0x05, 0x4a, 0x17, 0xa5, 0x74,
	0x93, 0x2e, 0xb0, 0x9b, 0x44, 0xaa, 0xaa, 0x4a, 0x5d, 0x18, 0xe2, 0x26, 0x44, 0x11, 0x58, 0x26,
	0xa1, 0x4a, 0x37, 0x96, 0x21, 0x83, 0x33, 0x2a, 0x9e, 0x41, 0xe3, 0x31, 0x2a, 0x27, 0xe8, 0x09,
	0xda, 0x03, 0xf4, 0x50, 0x3d, 0x44, 0x4f, 0x51, 0xcd, 0x8c, 0x01, 0xab, 0x59, 0x90, 0xdd, 0xfb,
	0xf3, 0xfd, 0x7e, 0x9e, 0xf5, 0xe6, 0xc9, 0xd0, 0x66, 0x73, 0x4c, 0x27, 0x98, 0x66, 0x79, 0xe6,
	0xce, 0x39, 0x13, 0xcc, 0x8d, 0x13, 0x4c, 0x85, 0x3b, 0x61, 0x69, 0xca, 0xa8, 0xbb, 0x38, 0x29,
	0x22, 0x47, 0x35, 0x51, 0x73, 0x23, 0xd7, 0x15, 0x47, 0xc9, 0x9d, 0x42, 0xb4, 0x38, 0x39, 0x7a,
	0x99, 0x30, 0x96, 0xcc, 0xb0, 0x86, 0x8d, 0xf3, 0xa9, 0x2b, 0x48, 0x8a, 0x33, 0x11, 0xa7, 0x73,
	0x6d, 0x68, 0xfd, 0x34, 0xa1, 0xda, 0x67, 0xf7, 0x18, 0x0d, 0x01, 0xc8, 0x3d, 0xa6, 0x82, 0x4c,
	0x09, 0xe6, 0x0d, 0xa3, 0x69, 0x1c, 0x5b, 0xa7, 0x67, 0xce, 0xb6, 0x01, 0x4e, 0xc0, 0xd9, 0x04,
	0x67, 0x59, 0x6f, 0x6d, 0x0d, 0x4b, 0x18, 0x14, 0xc0, 0xff, 0x33, 0x32, 0xe6, 0x31, 0x5f, 0x46,
	0x84, 0x4e, 0x59, 0xa3, 0xa2, 0xb0, 0xed, 0xed, 0xd8, 0x6b, 0xed, 0xea, 0xd1, 0x29, 0x0b, 0xad,
	0xd9, 0x26, 0x91, 0xc4, 0x0c, 0xf3, 0x05, 0x99, 0x60, 0x4d, 0x34, 0x9f, 0x4a, 0x1c, 0x6a, 0x97,
	0x26, 0x66, 0x9b, 0x04, 0x8d, 0x00, 0x62, 0x21, 0x38, 0x19, 0xe7, 0x02, 0x67, 0x8d, 0x6a, 0xd3,
	0x3c, 0xb6, 0x4e, 0xdf, 0x6d, 0xe7, 0xc9, 0xa5, 0x39, 0xde, 0xda, 0xe8, 0x53, 0xc1, 0x97, 0x61,
	0x89, 0x74, 0xf4, 0x11, 0x0e, 0xfe, 0x69, 0x23, 0x1b, 0xcc, 0xaf, 0x78, 0xa9, 0x96, 0x5b, 0x0f,
	0x65, 0x88, 0x0e, 0x61, 0x67, 0x11, 0xcf, 0x72, 0xac, 0x36, 0x53, 0x0f, 0x75, 0xf2, 0xa1, 0xf2,
	0xde, 0x68, 0x7d, 0x37, 0xe0, 0xf9, 0xa3, 0xe5, 0xa2, 0x17, 0x50, 0x7f, 0x60, 0x99, 0x88, 0x68,
	0x9c, 0xe2, 0x82, 0x53, 0x93, 0x85, 0x7e, 0x9c, 0x62, 0x89, 0x9f, 0x93, 0x7b, 0x85, 0x7a, 0x16,
	0xca, 0x10, 0x75, 0xe1, 0x20, 0x13, 0x31, 0x17, 0xd1, 0xfa, 0xd9, 0x8b, 0x85, 0x1d, 0x39, 0xfa,
	0x30, 0x9c, 0xd5, 0x61, 0x38, 0x37, 0x2b, 0x45, 0xb8, 0xaf, 0x2c, 0xeb, 0xbc, 0xf5, 0xbb, 0x02,
	0x56, 0xe9, 0x3d, 0x50, 0x08, 0xb5, 0x59, 0x4c, 0x93, 0x3c, 0x4e, 0xf4, 0x27, 0xec, 0x3f, 0x65,
	0x5d, 0x25, 0x80, 0x73, 0x5d, 0xb8, 0xc3, 0x35, 0x07, 0xbd, 0x01, 0x1b, 0x7f, 0x9b, 0x33, 0x2e,
	0x30, 0x8f, 0x16, 0x98, 0x67, 0x84, 0xd1, 0x62, 0x25, 0x07, 0xab, 0xfa, 0x48, 0x97, 0xd1, 0x5b,
	0x38, 0x9c, 0x30, 0x8e, 0xa3, 0xd5, 0x61, 0xad, 0xe4, 0xa6, 0x92, 0x23, 0xd9, 0x2b, 0x86, 0x15,
	0x8e, 0xd6, 0x0f, 0x03, 0x6a, 0xab, 0x99, 0xa8, 0x01, 0x87, 0xd7, 0x5e, 0xff, 0xe2, 0xd6, 0xbb,
	0xf0, 0xa3, 0xdb, 0xfe, 0x30, 0xf0, 0xbb, 0xbd, 0x4f, 0x3d, 0xff, 0xdc, 0xfe, 0x0f, 0xed, 0x81,
	0xd9, 0x0d, 0x02, 0xdb, 0x40, 0x16, 0xec, 0x75, 0xa3, 0xe1, 0xa5, 0x17, 0x06, 0x76, 0x05, 0x01,
	0xec, 0xfa, 0xa1, 0x74, 0xd8, 0xa6, 0x6c, 0x5c, 0x0c, 0x22, 0x95, 0x54, 0x51, 0x0d, 0xaa, 0x57,
	0xde, 0xc8, 0xb3, 0x77, 0x64, 0xb9, 0x3f, 0x38, 0xf7, 0xa3, 0xab, 0xa1, 0xbd, 0x2b, 0x29, 0xc1,
	0x65, 0x60, 0xef, 0x49, 0x63, 0x70, 0x77, 0x73, 0x39, 0xe8, 0xdb, 0x35, 0xa9, 0x0d, 0x6f, 0x3b,
	0x77, 0x76, 0x5d, 0x56, 0x3f, 0xfb, 0x1d, 0x29, 0x85, 0xd6, 0x2b, 0xb0, 0x4a, 0x57, 0x89, 0x10,
	0x54, 0x4b, 0xcf, 0xaa, 0xe2, 0xce, 0x2f, 0x03, 0x5e, 0x13, 0xb6, 0x75, 0xbd, 0x1d, 0xab, 0xab,
	0xc2, 0x40, 0x36, 0x03, 0xe3, 0x4b, 0x2f, 0x21, 0xe2, 0x21, 0x1f, 0x4b, 0x81, 0xab, 0x7d, 0x6d,
	0x42, 0x33, 0xc1, 0xf3, 0x14, 0x53, 0x11, 0x0b, 0xc2, 0xa8, 0xbb, 0x41, 0xb6, 0xf5, 0x9f, 0x26,
	0xc1, 0xb4, 0x9d, 0x3c, 0xfa, 0xe1, 0xfc, 0xa9, 0x34, 0x07, 0x73, 0x4c, 0xbb, 0x7a, 0xb8, 0xe2,
	0x3b, 0x9e, 0x1a, 0xae, 0x27, 0x3a, 0xa3, 0x93, 0xf1, 0xae, 0x02, 0x9c, 0xfd, 0x0d, 0x00, 0x00,
	0xff, 0xff, 0xe3, 0x53, 0x74, 0x5e, 0xbe, 0x04, 0x00, 0x00,
}
