Commit 1a6661b2 authored by Manuel Kieweg's avatar Manuel Kieweg 🤷
Browse files

Merge branch 'develop' into prepare-merge-develop

parents f09ee28f 9113cd5f
author: da/net research group <danet.fbi.h-da.de>
year: 2021
license: BSD
......@@ -12,4 +12,6 @@ documentation/design/*.pdf
.idea/modules.xml
.idea/vcs.xml
.idea/workspace.xml
restconf/bin/bin
\ No newline at end of file
restconf/bin/bin
test/.terraform.local/
configs/gosdn.toml
\ No newline at end of file
......@@ -3,143 +3,22 @@ variables:
DOCKER_IMAGE_SHA: $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA
stages:
- .pre
- test
- build
- deploy
- documentation
- apply
- integration-test
- .post
before_script:
- git config --global url."https://$GO_MODULES_USER:$GO_MODULES_ACCESS_TOKEN@code.fbi.h-da.de".insteadOf "https://code.fbi.h-da.de"
code-quality-master:
image: golangci/golangci-lint:latest-alpine
stage: test
rules:
- if: $CI_PIPELINE_SOURCE == "merge_request_event" && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME == $CI_DEFAULT_BRANCH
- if: $CI_DEFAULT_BRANCH
script:
# writes golangci-lint output to gl-code-quality-report.json
- golangci-lint run --config .ci/.golangci-master.yml --out-format code-climate | tee gl-code-quality-report.json
artifacts:
reports:
codequality: gl-code-quality-report.json
paths:
- gl-code-quality-report.json
code-quality:
image: golangci/golangci-lint:latest-alpine
stage: test
allow_failure: true
rules:
- if: $CI_PIPELINE_SOURCE == "merge_request_event" && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME != $CI_DEFAULT_BRANCH
script:
# writes golangci-lint output to gl-code-quality-report.json
- golangci-lint run --config .ci/.golangci.yml --out-format code-climate | tee gl-code-quality-report.json
artifacts:
reports:
codequality: gl-code-quality-report.json
paths:
- gl-code-quality-report.json
documentation:pdf:
default:
before_script:
- pwd
image:
name: pandoc/latex
entrypoint:
- ''
stage: documentation
rules:
- changes:
- documentation/design/*.md
script:
- cd documentation/design
- pandoc --filter pandoc-citeproc --bibliography=bibliography.bib --csl=acm-sig-proceedings.csl
--variable papersize=a4paper -s *.md -o documentation.pdf
artifacts:
paths:
- documentation/design/documentation.pdf
.mdbook_common: &rust
image:
name: $CI_REGISTRY/danet/internetworking/mdbook:latest
entrypoint:
- ''
stage: documentation
script:
- mdbook build documentation --dest-dir public
documentation:static:
rules:
- if: '$CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH'
artifacts:
paths:
- public
expire_in: 1 week
<<: *rust
documentation:test:
rules:
- if: '$CI_PIPELINE_SOURCE == "merge_request_event"'
<<: *rust
build:docker:
stage: build
tags:
- baremetal
rules:
- if: $CI_PIPELINE_SOURCE == "merge_request_event" && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME == $CI_DEFAULT_BRANCH
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
- if: $CI_COMMIT_TAG
script:
- >
docker build \
--build-arg GITLAB_USER=$GO_MODULES_USER \
--build-arg GITLAB_TOKEN=$GO_MODULES_ACCESS_TOKEN \
-t $DOCKER_IMAGE_SHA .
.deploy: &deploy
stage: deploy
needs: ["build:docker"]
tags:
- baremetal
script:
- docker login -u gitlab-ci-token -p $CI_JOB_TOKEN $CI_REGISTRY
- docker tag $DOCKER_IMAGE_SHA $TAG
- docker push $TAG
- curl --insecure -X POST $HOOK
deploy:develop:
variables:
TAG: $CI_REGISTRY_IMAGE:develop
HOOK: $PORTAINER_HOOK_DEVELOP
rules:
- if: $CI_PIPELINE_SOURCE == "merge_request_event" && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME == $CI_DEFAULT_BRANCH
<<: *deploy
deploy:tagged:
variables:
TAG: $CI_REGISTRY_IMAGE:CI_COMMIT_TAG
rules:
- if: $CI_COMMIT_TAG
<<: *deploy
deploy:latest:
variables:
TAG: $CI_REGISTRY_IMAGE:latest
HOOK: $PORTAINER_HOOK_LATEST
rules:
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
<<: *deploy
sast:
variables:
SAST_ANALYZER_IMAGE_TAG: '2'
SAST_EXCLUDED_PATHS: spec, test, tests, tmp
SEARCH_MAX_DEPTH: '4'
- git config --global url."https://$GO_MODULES_USER:$GO_MODULES_ACCESS_TOKEN@code.fbi.h-da.de".insteadOf "https://code.fbi.h-da.de"
include:
- template: Security/SAST.gitlab-ci.yml
- template: Dependency-Scanning.gitlab-ci.yml
- template: Security/License-Scanning.gitlab-ci.yml
- local: '/build/ci/.code-quality-ci.yml'
- local: '/build/ci/.documentation-ci.yml'
- local: '/build/ci/.security-and-compliance-ci.yml'
- local: '/build/ci/.build-container.yml'
- local: '/build/ci/.test.yml'
- local: '/build/ci/.terraform-ci.yml'
\ No newline at end of file
# goSDN Architecture
This document describes the the high-level architecture of the goSDN project. All contributors should familiarize themselves with it. To avoid too much divergence from the changing code this document does focus on high-level concepts instead of implementation details.
## Bird's Eye View
[<img src="documentation/architecture.png" style="height:50%; width:50%" > ](documentation/architecture.png)
On the highest level goSDn provides a gRPC northbound-interface and two types of southbound-interfaces: RESTCONF and gRPC-based. The northbound interface allows the interaction with a running goSDN daemon and may allow the stacking of multiple controllers in the future. The southbound interface (SBI) capabilities are split in `nucleus` models and plugins. The supported `nucleus` models are OpenConfig yang [openconfig-yang](https://github.com/openconfig/yang) and TAPI. Third party models and more SBI-transports can be attached using the go plugin architecture.
The internal data representation uses [ygot](https://github.com/openconfig/ygot) generated go-structs.
It is important to note that these go-structs are generated from yang models and thus are not generic data structures. This means that the `nucleus` code is organized in silos, i.e., one particular southbound-interface is visible in the `nucleus`, as the internal data representation depend on the used yang modes in the southbound-interface.
## Code Map
This section briefly describes important directories and data structures. It also introduces important API calls to relevant libraries.
It also mentions **architecture invariants** and **API boundaries**
### `api`
API specification for gRPC and protobuf definitions.
**Architecture invariant:** To import gRPC related protobuf definitions use `pb` as an import prefix. For gNMI related protobuf definitions use `gpb`
### `forks`
Forks of `google/gnxi/gnmi` and `arista/goarista/gnmi` for gNMI server and client respectively. Subject of change once we converge to own clients and servers.
### `nucleus/principalNetworkDomain`
`nucleus` is the core package of goSDN. The main data structure is the `principalNetworkDomain` (PND). It reflects one administrative entity, i.e., as set of connected network devices, and is the source of truth for network state and configuration. A PND is SBI agnostic and supports multiple SBI implementations simultaneously.
**API boundary:** The PND' is the only way to interact with an `orchestratedNetworkingDevice`
### `nucleus/device`
This is the representation of an `orchestratedNetworkingDevice` (OND). An `orchestratedNetworkingDevice` is the network device that is directly managed by goSDN. It holds a reference to the device's `transport` and `southboundInterface` implementation. It contains a fakeroot device based on its attached SBI.
**Architecture invariant:** The device is does not provide any functionality to upper API layers.
### `nucleus/southbound`
Implementation of SBI specifics. Provides SBI models to other callers and SBI specific function deviations.
**Architecture invariant:** Only SBIs defined by a YANG model will be supported by goSDN.
### `nucleus/transport` `nucleus/gnmi_transport` `nucleus/restconf_transport`
Transport between goSDN and ONDs. Current core implementations are gNMI and RESTCONF. Additionally to implementing the transports the packages also provide a mapping from general purpose goSDN API calls to diverging SBI API calls.
For example `gNMI::Subscribe` and `RESTCONF::Push` are mapped to `gosdn::Subscribe`.
The `gnmi_transport` implementation uses `ytypes.SetNode` to write to a device struct.
FROM golang:1.15-alpine AS builder
FROM golang:1.15-buster AS builder
ARG GITLAB_USER
ARG GITLAB_TOKEN
ARG BUILDARGS
WORKDIR /src/gosdn
COPY . .
RUN apk add git
RUN apt-get update && apt-get install -y git
RUN git config --global url."https://$GITLAB_USER:$GITLAB_TOKEN@code.fbi.h-da.de".insteadOf "https://code.fbi.h-da.de"
RUN go mod download
RUN CGO_ENABLED=0 GOOS=linux go build
RUN GOOS=linux go build $BUILDARGS ./cmd/gosdn
FROM alpine:latest
FROM debian:latest
EXPOSE 8080
EXPOSE 55055
COPY --from=builder /src/gosdn/gosdn .
COPY --from=builder /src/gosdn/gosdn.toml .
COPY --from=builder /src/gosdn/clients.toml .
COPY --from=builder /src/gosdn/configs ./configs
ENTRYPOINT [ "./gosdn" ]
CMD [""]
BSD 3-Clause License
Copyright (c) 2020, da/net
Copyright © 2021 da/net research group <danet.fbi.h-da.de>
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this
list of conditions and the following disclaimer.
1. Redistributions of source code must retain the above copyright notice,
this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.
2. Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.
* Neither the name of the copyright holder nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
3. Neither the name of the copyright holder nor the names of its contributors
may be used to endorse or promote products derived from this software
without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
......
# GoSDN
### CI Status Master
[![coverage report](https://code.fbi.h-da.de/cocsn/gosdn/badges/master/coverage.svg)](https://code.fbi.h-da.de/cocsn/gosdn/-/commits/master)
[![pipeline status](https://code.fbi.h-da.de/cocsn/gosdn/badges/master/pipeline.svg)](https://code.fbi.h-da.de/cocsn/gosdn/-/commits/master)
### CI Status Develop
[![coverage report](https://code.fbi.h-da.de/cocsn/gosdn/badges/develop/coverage.svg)](https://code.fbi.h-da.de/cocsn/gosdn/-/commits/develop)
[![pipeline status](https://code.fbi.h-da.de/cocsn/gosdn/badges/develop/pipeline.svg)](https://code.fbi.h-da.de/cocsn/gosdn/-/commits/develop)
The GIT repo for the GoSDN design and implementation. GoSDN is intended to be controller for Software Defined Networks (SDN) that follows a modern software architecture design and a well-documented implementation in the go language.
## Generate Code Stubs
......@@ -15,4 +25,4 @@ gosdn
## Documentation
The latest documentatiion generated on the master branch can be downloaded [here](https://code.fbi.h-da.de/cocsn/gosdn/-/jobs).
\ No newline at end of file
The latest documentatiion generated on the master branch can be downloaded [here](https://code.fbi.h-da.de/cocsn/gosdn/-/jobs).
// openconfig.enums is generated by proto_generator as a protobuf
// representation of a YANG schema.
//
// Input schema modules:
// - ../yang-models/models/openconfig/release/models/interfaces/openconfig-interfaces.yang
// Include paths:
// - ../yang-models/models/...
// Code generated by protoc-gen-go. DO NOT EDIT.
// versions:
// protoc-gen-go v1.25.0-devel
// protoc v3.13.0
// source: openconfig/enums/enums.proto
package gosdn
import (
proto "github.com/golang/protobuf/proto"
_ "github.com/openconfig/ygot/proto/yext"
_ "github.com/openconfig/ygot/proto/ywrapper"
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)
)
// This is a compile-time assertion that a sufficiently up-to-date version
// of the legacy proto package is being used.
const _ = proto.ProtoPackageIsVersion4
// IETFInterfacesInterfaceType represents an enumerated type generated for the YANG identity interface-type.
type IETFInterfacesInterfaceType int32
const (
IETFInterfacesInterfaceType_IETFINTERFACESINTERFACETYPE_UNSET IETFInterfacesInterfaceType = 0
)
// Enum value maps for IETFInterfacesInterfaceType.
var (
IETFInterfacesInterfaceType_name = map[int32]string{
0: "IETFINTERFACESINTERFACETYPE_UNSET",
}
IETFInterfacesInterfaceType_value = map[string]int32{
"IETFINTERFACESINTERFACETYPE_UNSET": 0,
}
)
func (x IETFInterfacesInterfaceType) Enum() *IETFInterfacesInterfaceType {
p := new(IETFInterfacesInterfaceType)
*p = x
return p
}
func (x IETFInterfacesInterfaceType) String() string {
return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x))
}
func (IETFInterfacesInterfaceType) Descriptor() protoreflect.EnumDescriptor {
return file_openconfig_enums_enums_proto_enumTypes[0].Descriptor()
}
func (IETFInterfacesInterfaceType) Type() protoreflect.EnumType {
return &file_openconfig_enums_enums_proto_enumTypes[0]
}
func (x IETFInterfacesInterfaceType) Number() protoreflect.EnumNumber {
return protoreflect.EnumNumber(x)
}
// Deprecated: Use IETFInterfacesInterfaceType.Descriptor instead.
func (IETFInterfacesInterfaceType) EnumDescriptor() ([]byte, []int) {
return file_openconfig_enums_enums_proto_rawDescGZIP(), []int{0}
}
var File_openconfig_enums_enums_proto protoreflect.FileDescriptor
var file_openconfig_enums_enums_proto_rawDesc = []byte{
0x0a, 0x1c, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2f, 0x65, 0x6e, 0x75,
0x6d, 0x73, 0x2f, 0x65, 0x6e, 0x75, 0x6d, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x10,
0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2e, 0x65, 0x6e, 0x75, 0x6d, 0x73,
0x1a, 0x38, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6f, 0x70, 0x65,
0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2f, 0x79, 0x67, 0x6f, 0x74, 0x2f, 0x70, 0x72, 0x6f,
0x74, 0x6f, 0x2f, 0x79, 0x77, 0x72, 0x61, 0x70, 0x70, 0x65, 0x72, 0x2f, 0x79, 0x77, 0x72, 0x61,
0x70, 0x70, 0x65, 0x72, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x30, 0x67, 0x69, 0x74, 0x68,
0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69,
0x67, 0x2f, 0x79, 0x67, 0x6f, 0x74, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x79, 0x65, 0x78,
0x74, 0x2f, 0x79, 0x65, 0x78, 0x74, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2a, 0x44, 0x0a, 0x1b,
0x49, 0x45, 0x54, 0x46, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x49, 0x6e,
0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x54, 0x79, 0x70, 0x65, 0x12, 0x25, 0x0a, 0x21, 0x49,
0x45, 0x54, 0x46, 0x49, 0x4e, 0x54, 0x45, 0x52, 0x46, 0x41, 0x43, 0x45, 0x53, 0x49, 0x4e, 0x54,
0x45, 0x52, 0x46, 0x41, 0x43, 0x45, 0x54, 0x59, 0x50, 0x45, 0x5f, 0x55, 0x4e, 0x53, 0x45, 0x54,
0x10, 0x00, 0x42, 0x20, 0x5a, 0x1e, 0x67, 0x69, 0x74, 0x6c, 0x61, 0x62, 0x2e, 0x66, 0x62, 0x69,
0x2e, 0x68, 0x2d, 0x64, 0x61, 0x2e, 0x64, 0x65, 0x2f, 0x63, 0x6f, 0x63, 0x73, 0x6e, 0x2f, 0x67,
0x6f, 0x73, 0x64, 0x6e, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
}
var (
file_openconfig_enums_enums_proto_rawDescOnce sync.Once
file_openconfig_enums_enums_proto_rawDescData = file_openconfig_enums_enums_proto_rawDesc
)
func file_openconfig_enums_enums_proto_rawDescGZIP() []byte {
file_openconfig_enums_enums_proto_rawDescOnce.Do(func() {
file_openconfig_enums_enums_proto_rawDescData = protoimpl.X.CompressGZIP(file_openconfig_enums_enums_proto_rawDescData)
})
return file_openconfig_enums_enums_proto_rawDescData
}
var file_openconfig_enums_enums_proto_enumTypes = make([]protoimpl.EnumInfo, 1)
var file_openconfig_enums_enums_proto_goTypes = []interface{}{
(IETFInterfacesInterfaceType)(0), // 0: openconfig.enums.IETFInterfacesInterfaceType
}
var file_openconfig_enums_enums_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_openconfig_enums_enums_proto_init() }
func file_openconfig_enums_enums_proto_init() {
if File_openconfig_enums_enums_proto != nil {
return
}
type x struct{}
out := protoimpl.TypeBuilder{
File: protoimpl.DescBuilder{
GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
RawDescriptor: file_openconfig_enums_enums_proto_rawDesc,
NumEnums: 1,
NumMessages: 0,
NumExtensions: 0,
NumServices: 0,
},
GoTypes: file_openconfig_enums_enums_proto_goTypes,
DependencyIndexes: file_openconfig_enums_enums_proto_depIdxs,
EnumInfos: file_openconfig_enums_enums_proto_enumTypes,
}.Build()
File_openconfig_enums_enums_proto = out.File
file_openconfig_enums_enums_proto_rawDesc = nil
file_openconfig_enums_enums_proto_goTypes = nil
file_openconfig_enums_enums_proto_depIdxs = nil
}
// openconfig is generated by proto_generator as a protobuf
// representation of a YANG schema.
//
// Input schema modules:
// - ../yang-models/models/openconfig/release/models/interfaces/openconfig-interfaces.yang
// Include paths:
// - ../yang-models/models/...
// Code generated by protoc-gen-go. DO NOT EDIT.
// versions:
// protoc-gen-go v1.25.0-devel
// protoc v3.13.0
// source: openconfig/openconfig.proto
package gosdn
import (
proto "github.com/golang/protobuf/proto"
_ "github.com/openconfig/ygot/proto/yext"
_ "github.com/openconfig/ygot/proto/ywrapper"
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)
)
// This is a compile-time assertion that a sufficiently up-to-date version
// of the legacy proto package is being used.
const _ = proto.ProtoPackageIsVersion4
type Device struct {
state protoimpl.MessageState
sizeCache protoimpl.SizeCache
unknownFields protoimpl.UnknownFields
Interfaces *Interfaces `protobuf:"bytes,85031486,opt,name=interfaces,proto3" json:"interfaces,omitempty"`
}
func (x *Device) Reset() {
*x = Device{}
if protoimpl.UnsafeEnabled {
mi := &file_openconfig_openconfig_proto_msgTypes[0]
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
ms.StoreMessageInfo(mi)
}
}
func (x *Device) String() string {
return protoimpl.X.MessageStringOf(x)
}
func (*Device) ProtoMessage() {}
func (x *Device) ProtoReflect() protoreflect.Message {
mi := &file_openconfig_openconfig_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 Device.ProtoReflect.Descriptor instead.
func (*Device) Descriptor() ([]byte, []int) {
return file_openconfig_openconfig_proto_rawDescGZIP(), []int{0}
}
func (x *Device) GetInterfaces() *Interfaces {
if x != nil {
return x.Interfaces
}
return nil
}
var File_openconfig_openconfig_proto protoreflect.FileDescriptor
var file_openconfig_openconfig_proto_rawDesc = []byte{
0x0a, 0x1b, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2f, 0x6f, 0x70, 0x65,
0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0a, 0x6f,
0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x1a, 0x38, 0x67, 0x69, 0x74, 0x68, 0x75,
0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67,
0x2f, 0x79, 0x67, 0x6f, 0x74, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x79, 0x77, 0x72, 0x61,
0x70, 0x70, 0x65, 0x72, 0x2f, 0x79, 0x77, 0x72, 0x61, 0x70, 0x70, 0x65, 0x72, 0x2e, 0x70, 0x72,
0x6f, 0x74, 0x6f, 0x1a, 0x30, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f,
0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2f, 0x79, 0x67, 0x6f, 0x74, 0x2f,
0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x79, 0x65, 0x78, 0x74, 0x2f, 0x79, 0x65, 0x78, 0x74, 0x2e,
0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x3c, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69,
0x67, 0x2f, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x5f, 0x69, 0x6e, 0x74,
0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x2f, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66,
0x69, 0x67, 0x5f, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x2e, 0x70, 0x72,
0x6f, 0x74, 0x6f, 0x22, 0x69, 0x0a, 0x06, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x12, 0x5f, 0x0a,
0x0a, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x18, 0xbe, 0xf4, 0xc5, 0x28,
0x20, 0x01, 0x28, 0x0b, 0x32, 0x2c, 0x2e, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69,
0x67, 0x2e, 0x6f, 0x70, 0x65, 0x6e, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x5f, 0x69, 0x6e, 0x74,
0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x2e, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63,
0x65, 0x73, 0x42, 0x0e, 0x82, 0x41, 0x0b, 0x2f, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63,
0x65, 0x73, 0x52, 0x0a, 0x69, 0x6e, 0x74, 0x65, 0x72, 0x66, 0x61, 0x63, 0x65, 0x73, 0x42, 0x20,
0x5a, 0x1e, 0x67, 0x69, 0x74, 0x6c, 0x61, 0x62, 0x2e, 0x66, 0x62, 0x69, 0x2e, 0x68, 0x2d, 0x64,
0x61, 0x2e, 0x64, 0x65, 0x2f, 0x63, 0x6f, 0x63, 0x73, 0x6e, 0x2f, 0x67, 0x6f, 0x73, 0x64, 0x6e,
0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
}
var (
file_openconfig_openconfig_proto_rawDescOnce sync.Once
file_openconfig_openconfig_proto_rawDescData = file_openconfig_openconfig_proto_rawDesc
)
func file_openconfig_openconfig_proto_rawDescGZIP() []byte {
file_openconfig_openconfig_proto_rawDescOnce.Do(func() {
file_openconfig_openconfig_proto_rawDescData = protoimpl.X.CompressGZIP(file_openconfig_openconfig_proto_rawDescData)
})
return file_openconfig_openconfig_proto_rawDescData
}
var file_openconfig_openconfig_proto_msgTypes = make([]protoimpl.MessageInfo, 1)
var file_openconfig_openconfig_proto_goTypes = []interface{}{
(*Device)(nil), // 0: openconfig.Device
(*Interfaces)(nil), // 1: openconfig.openconfig_interfaces.Interfaces
}
var file_openconfig_openconfig_proto_depIdxs = []int32{
1, // 0: openconfig.Device.interfaces:type_name -> openconfig.openconfig_interfaces.Interfaces
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_openconfig_openconfig_proto_init() }
func file_openconfig_openconfig_proto_init() {
if File_openconfig_openconfig_proto != nil {
return
}
file_openconfig_openconfig_interfaces_openconfig_interfaces_proto_init()
if !protoimpl.UnsafeEnabled {