// Copyright (c) 2018 Open Networking Foundation
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at:
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

syntax = "proto3";
package openolt;
import "google/api/annotations.proto";

service Openolt {

    rpc ActivateOnu(Onu) returns (Empty) {
        option (google.api.http) = {
          post: "/v1/EnableOnu"
          body: "*"
        };
    }

    rpc OmciMsgOut(OmciMsg) returns (Empty) {
        option (google.api.http) = {
          post: "/v1/OmciMsgOut"
          body: "*"
        };
    }

    rpc OnuPacketOut(OnuPacket) returns (Empty) {
        option (google.api.http) = {
          post: "/v1/OnuPacketOut"
          body: "*"
        };
    }

    rpc UplinkPacketOut(UplinkPacket) returns (Empty) {
        option (google.api.http) = {
          post: "/v1/UplinkPacketOut"
          body: "*"
        };
    }

    rpc FlowAdd(Flow) returns (Empty) {
        option (google.api.http) = {
          post: "/v1/FlowAdd"
          body: "*"
        };
    }

    rpc HeartbeatCheck(Empty) returns (Heartbeat) {
        option (google.api.http) = {
          post: "/v1/HeartbeatCheck"
          body: "*"
        };
    }

    rpc EnablePonIf(Interface) returns (Empty) {
        option (google.api.http) = {
            post: "/v1/EnablePonIf"
            body: "*"
        };
    }

    rpc DisablePonIf(Interface) returns (Empty) {
        option (google.api.http) = {
            post: "/v1/DisablePonIf"
            body: "*"
        };
    }

    rpc EnableIndication(Empty) returns (stream Indication) {}
}

message Indication {
    oneof data {
        OltIndication olt_ind = 1;
        IntfIndication intf_ind = 2;
        IntfOperIndication intf_oper_ind = 3;
        OnuDiscIndication onu_disc_ind = 4;
        OnuIndication onu_ind = 5;
        OmciIndication omci_ind = 6;
        PacketIndication pkt_ind = 7;
        PortStatistics port_stats = 8;
        FlowStatistics flow_stats = 9;
        AlarmIndication alarm_ind= 10;
    }
}

message AlarmIndication {
    oneof data {
        LosIndication los_ind = 1;
        DyingGaspIndication dying_gasp_ind = 2;
        OnuAlarmIndication onu_alarm_ind = 3;
        OnuStartupFailureIndication onu_startup_fail_ind = 4;
        OnuSignalDegradeIndication onu_signal_degrade_ind = 5;
        OnuDriftOfWindowIndication onu_drift_of_window_ind = 6;
        OnuLossOfOmciChannelIndication onu_loss_omci_ind = 7;
        OnuSignalsFailureIndication onu_signals_fail_ind = 8;
        OnuTransmissionInterferenceWarning onu_tiwi_ind = 9;
        OnuActivationFailureIndication onu_activation_fail_ind = 10;
        OnuProcessingErrorIndication onu_processing_error_ind = 11;
    }
}

message OltIndication {
    string oper_state = 1;	// up, down
}

message IntfIndication {
    fixed32 intf_id = 1;
    string oper_state = 2;      // up, down
}

message OnuDiscIndication {
    fixed32 intf_id = 1;
    SerialNumber serial_number = 2;
}

message OnuIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string oper_state = 3;      // up, down
    string admin_state = 5;     // up, down
    SerialNumber serial_number = 4;
}

message IntfOperIndication {
    string type = 1;		// nni, pon
    fixed32 intf_id = 2;
    string oper_state = 3;      // up, down
}

message OmciIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    bytes pkt = 3;
}

message PacketIndication {
    fixed32 intf_id = 1;
    fixed32 gemport_id = 2;
    fixed32 flow_id = 3;
    bytes pkt = 4;
}

message Interface {
    fixed32 intf_id = 1;
}

message Heartbeat {
    fixed32 heartbeat_signature = 1;
}

message Onu {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    SerialNumber serial_number = 3;
}

message OmciMsg {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    bytes pkt = 3;
}

message OnuPacket {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    bytes pkt = 3;
}

message UplinkPacket {
    fixed32 intf_id = 1;
    bytes pkt = 2;
}

message Classifier {
    fixed32 o_tpid = 1;
    fixed32 o_vid = 2;
    fixed32 i_tpid = 3;
    fixed32 i_vid = 4;
    fixed32 o_pbits = 5;
    fixed32 i_pbits = 6;
    fixed32 eth_type = 7;
    bytes dst_mac = 8;
    bytes src_mac = 9;
    fixed32 ip_proto = 10;
    fixed32 dst_ip = 11;
    fixed32 src_ip = 12;
    fixed32 src_port = 13;
    fixed32 dst_port = 14;
    string pkt_tag_type = 15;	// untagged, single_tag, double_tag
}

message ActionCmd {
    bool add_outer_tag = 1;
    bool remove_outer_tag = 2;
    bool trap_to_host = 3;
}

message Action {
    ActionCmd cmd = 1;
    fixed32 o_vid = 2;
    fixed32 o_pbits = 3;
    fixed32 o_tpid = 4;
    fixed32 i_vid = 5;
    fixed32 i_pbits = 6;
    fixed32 i_tpid = 7;
}

message Flow {
    fixed32 access_intf_id = 1;
    fixed32 onu_id = 2;
    fixed32 flow_id = 3;
    string flow_type = 4;	// upstream, downstream, broadcast, multicast
    fixed32 network_intf_id = 5;
    fixed32 gemport_id = 6;
    Classifier classifier = 7;
    Action action = 8;
    fixed32 priority = 9;
}

message SerialNumber {
    bytes vendor_id = 1;
    bytes vendor_specific = 2;
}

message PortStatistics {
    fixed32 intf_id = 1;
    fixed64 rx_bytes = 2;
    fixed64 rx_packets = 3;
    fixed64 rx_ucast_packets = 4;
    fixed64 rx_mcast_packets = 5;
    fixed64 rx_bcast_packets = 6;
    fixed64 rx_error_packets = 7;
    fixed64 tx_bytes = 8;
    fixed64 tx_packets = 9;
    fixed64 tx_ucast_packets = 10;
    fixed64 tx_mcast_packets = 11;
    fixed64 tx_bcast_packets = 12;
    fixed64 tx_error_packets = 13;
    fixed64 rx_crc_errors = 14;
    fixed64 bip_errors = 15;
    fixed32 timestamp = 16;
}

message FlowStatistics {
    fixed32 flow_id = 1;
    fixed64 rx_bytes = 2;
    fixed64 rx_packets = 3;
    fixed64 tx_bytes = 8;
    fixed64 tx_packets = 9;
    fixed32 timestamp = 16;
}

message LosIndication {
    fixed32 intf_id = 1;
    string status = 2;
}

message DyingGaspIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string status = 3;
}

message OnuAlarmIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string los_status = 3;
    string lob_status = 4;
    string lopc_miss_status = 5;
    string lopc_mic_error_status = 6;
}

message OnuStartupFailureIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string status = 3;
}

message OnuSignalDegradeIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string status = 3;
    fixed32 inverse_bit_error_rate = 4;
}

message OnuDriftOfWindowIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string status = 3;
    fixed32 drift = 4;
    fixed32 new_eqd = 5;
}

message OnuLossOfOmciChannelIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string status = 3;
}

message OnuSignalsFailureIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string status = 3;
    fixed32 inverse_bit_error_rate = 4;
}

message OnuTransmissionInterferenceWarning {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
    string status = 3;
    fixed32 drift = 4;
}

message OnuActivationFailureIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
}

message OnuProcessingErrorIndication {
    fixed32 intf_id = 1;
    fixed32 onu_id = 2;
}


message Empty {}
