blob: fdb08592a86436171f7554fc95e6b617e93a25b5 [file] [log] [blame]
Phaneendra Manda4c62c802019-03-06 21:37:49 +05301/*
2 * Copyright 2018-present Open Networking Foundation
3
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7
8 * http://www.apache.org/licenses/LICENSE-2.0
9
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
Girish Gowdru6a80bbd2019-07-02 07:36:09 -070016
Scott Bakerdbd960e2020-02-28 08:57:51 -080017//Package core provides the utility for olt devices, flows and statistics
18package core
Phaneendra Manda4c62c802019-03-06 21:37:49 +053019
20import (
cuilin20187b2a8c32019-03-26 19:52:28 -070021 "context"
Matt Jeanneretceea2e02020-03-27 14:19:57 -040022 "encoding/binary"
Matt Jeanneret1359c732019-08-01 21:40:02 -040023 "encoding/hex"
Girish Gowdra491a9c62021-01-06 16:43:07 -080024 "errors"
cuilin20187b2a8c32019-03-26 19:52:28 -070025 "fmt"
26 "io"
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -040027 "net"
cuilin20187b2a8c32019-03-26 19:52:28 -070028 "strconv"
29 "strings"
30 "sync"
31 "time"
Phaneendra Manda4c62c802019-03-06 21:37:49 +053032
Matteo Scandolo945e4012019-12-12 14:16:11 -080033 "github.com/cenkalti/backoff/v3"
cuilin20187b2a8c32019-03-26 19:52:28 -070034 "github.com/gogo/protobuf/proto"
35 "github.com/golang/protobuf/ptypes"
Girish Kumar93e91742020-07-27 16:43:19 +000036 grpc_middleware "github.com/grpc-ecosystem/go-grpc-middleware"
37 grpc_opentracing "github.com/grpc-ecosystem/go-grpc-middleware/tracing/opentracing"
Girish Gowdraa09aeab2020-09-14 16:30:52 -070038 "github.com/opencord/voltha-lib-go/v4/pkg/adapters/adapterif"
Matteo Scandolodfa7a972020-11-06 13:03:40 -080039 "github.com/opencord/voltha-lib-go/v4/pkg/config"
Himani Chawlacd407802020-12-10 12:08:59 +053040 "github.com/opencord/voltha-lib-go/v4/pkg/events/eventif"
Girish Gowdra491a9c62021-01-06 16:43:07 -080041 flow_utils "github.com/opencord/voltha-lib-go/v4/pkg/flows"
Girish Gowdraa09aeab2020-09-14 16:30:52 -070042 "github.com/opencord/voltha-lib-go/v4/pkg/log"
43 "github.com/opencord/voltha-lib-go/v4/pkg/pmmetrics"
Matteo Scandolodfa7a972020-11-06 13:03:40 -080044
Thomas Lee S94109f12020-03-03 16:39:29 +053045 "github.com/opencord/voltha-openolt-adapter/internal/pkg/olterrors"
Scott Bakerdbd960e2020-02-28 08:57:51 -080046 rsrcMgr "github.com/opencord/voltha-openolt-adapter/internal/pkg/resourcemanager"
Girish Gowdraa09aeab2020-09-14 16:30:52 -070047 "github.com/opencord/voltha-protos/v4/go/common"
kesavand62126212021-01-12 04:56:06 -050048 "github.com/opencord/voltha-protos/v4/go/extension"
Girish Gowdraa09aeab2020-09-14 16:30:52 -070049 ic "github.com/opencord/voltha-protos/v4/go/inter_container"
50 of "github.com/opencord/voltha-protos/v4/go/openflow_13"
51 oop "github.com/opencord/voltha-protos/v4/go/openolt"
52 "github.com/opencord/voltha-protos/v4/go/voltha"
cuilin20187b2a8c32019-03-26 19:52:28 -070053 "google.golang.org/grpc"
Devmalya Paula1efa642020-04-20 01:36:43 -040054 "google.golang.org/grpc/codes"
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -040055 "google.golang.org/grpc/status"
Phaneendra Manda4c62c802019-03-06 21:37:49 +053056)
57
salmansiddiqui7ac62132019-08-22 03:58:50 +000058// Constants for number of retries and for timeout
Manikkaraj kb1d51442019-07-23 10:41:02 -040059const (
Girish Gowdra491a9c62021-01-06 16:43:07 -080060 InvalidPort = 0xffffffff
61 MaxNumOfGroupHandlerChannels = 256
62
63 McastFlowOrGroupAdd = "McastFlowOrGroupAdd"
64 McastFlowOrGroupModify = "McastFlowOrGroupModify"
65 McastFlowOrGroupRemove = "McastFlowOrGroupRemove"
kesavand62126212021-01-12 04:56:06 -050066 oltPortInfoTimeout = 3
Manikkaraj kb1d51442019-07-23 10:41:02 -040067)
68
Phaneendra Manda4c62c802019-03-06 21:37:49 +053069//DeviceHandler will interact with the OLT device.
70type DeviceHandler struct {
Matteo Scandolodfa7a972020-11-06 13:03:40 -080071 cm *config.ConfigManager
cuilin20187b2a8c32019-03-26 19:52:28 -070072 device *voltha.Device
kdarapu381c6902019-07-31 18:23:16 +053073 coreProxy adapterif.CoreProxy
74 AdapterProxy adapterif.AdapterProxy
Himani Chawlacd407802020-12-10 12:08:59 +053075 EventProxy eventif.EventProxy
cuilin20187b2a8c32019-03-26 19:52:28 -070076 openOLT *OpenOLT
cuilin20187b2a8c32019-03-26 19:52:28 -070077 exitChannel chan int
78 lockDevice sync.RWMutex
manikkaraj kbf256be2019-03-25 00:13:48 +053079 Client oop.OpenoltClient
cuilin20187b2a8c32019-03-26 19:52:28 -070080 transitionMap *TransitionMap
81 clientCon *grpc.ClientConn
Girish Gowdra9602eb42020-09-09 15:50:39 -070082 flowMgr []*OpenOltFlowMgr
83 groupMgr *OpenOltGroupMgr
Devmalya Paulfb990a52019-07-09 10:01:49 -040084 eventMgr *OpenOltEventMgr
manikkaraj kbf256be2019-03-25 00:13:48 +053085 resourceMgr *rsrcMgr.OpenOltResourceMgr
Naga Manjunatha8dc9372019-10-31 23:01:18 +053086
Girish Gowdra3ab6d212020-03-24 17:33:15 -070087 discOnus sync.Map
88 onus sync.Map
89 portStats *OpenOltStatisticsMgr
90 metrics *pmmetrics.PmMetrics
91 stopCollector chan bool
92 stopHeartbeatCheck chan bool
93 activePorts sync.Map
94 stopIndications chan bool
95 isReadIndicationRoutineActive bool
Girish Gowdracefae192020-03-19 18:14:10 -070096
Mahir Gunyelb0046752021-02-26 13:51:05 -080097 totalPonPorts uint32
98 perPonOnuIndicationChannel map[uint32]onuIndicationChannels
99 perPonOnuIndicationChannelLock sync.Mutex
Girish Gowdra491a9c62021-01-06 16:43:07 -0800100
101 // Slice of channels. Each channel in slice, index by (mcast-group-id modulo MaxNumOfGroupHandlerChannels)
102 // A go routine per index, waits on a unique channel for incoming mcast flow or group (add/modify/remove).
103 incomingMcastFlowOrGroup []chan McastFlowOrGroupControlBlock
Gamze Abakac2c32a62021-03-11 11:44:18 +0000104
105 adapterPreviouslyConnected bool
106 agentPreviouslyConnected bool
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700107}
108
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700109//OnuDevice represents ONU related info
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700110type OnuDevice struct {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700111 deviceID string
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700112 deviceType string
113 serialNumber string
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700114 onuID uint32
115 intfID uint32
116 proxyDeviceID string
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +0530117 losRaised bool
Devmalya Paula1efa642020-04-20 01:36:43 -0400118 rdiRaised bool
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700119}
120
Mahir Gunyelb0046752021-02-26 13:51:05 -0800121type onuIndicationMsg struct {
122 ctx context.Context
123 indication *oop.Indication
Mahir Gunyel2fb81472020-12-16 23:18:34 -0800124}
125
126type onuIndicationChannels struct {
Mahir Gunyelb0046752021-02-26 13:51:05 -0800127 indicationChannel chan onuIndicationMsg
Mahir Gunyel2fb81472020-12-16 23:18:34 -0800128 stopChannel chan struct{}
129}
130
Girish Gowdra491a9c62021-01-06 16:43:07 -0800131//McastFlowOrGroupControlBlock is created per mcast flow/group add/modify/remove and pushed on the incomingMcastFlowOrGroup channel slice
132//The McastFlowOrGroupControlBlock is then picked by the mcastFlowOrGroupChannelHandlerRoutine for further processing.
133//There are MaxNumOfGroupHandlerChannels number of mcastFlowOrGroupChannelHandlerRoutine routines which monitor for any incoming mcast flow/group messages
134//and process them serially. The mcast flow/group are assigned these routines based on formula (group-id modulo MaxNumOfGroupHandlerChannels)
135type McastFlowOrGroupControlBlock struct {
136 ctx context.Context // Flow/group handler context
137 flowOrGroupAction string // one of McastFlowOrGroupAdd, McastFlowOrGroupModify or McastFlowOrGroupDelete
138 flow *voltha.OfpFlowStats // Flow message (can be nil or valid flow)
139 group *voltha.OfpGroupEntry // Group message (can be nil or valid group)
140 errChan *chan error // channel to report the mcast Flow/group handling error
141}
142
Naga Manjunath7615e552019-10-11 22:35:47 +0530143var pmNames = []string{
144 "rx_bytes",
145 "rx_packets",
146 "rx_mcast_packets",
147 "rx_bcast_packets",
148 "tx_bytes",
149 "tx_packets",
150 "tx_mcast_packets",
151 "tx_bcast_packets",
152}
153
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700154//NewOnuDevice creates a new Onu Device
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +0530155func NewOnuDevice(devID, deviceTp, serialNum string, onuID, intfID uint32, proxyDevID string, losRaised bool) *OnuDevice {
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700156 var device OnuDevice
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700157 device.deviceID = devID
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700158 device.deviceType = deviceTp
159 device.serialNumber = serialNum
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700160 device.onuID = onuID
161 device.intfID = intfID
162 device.proxyDeviceID = proxyDevID
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +0530163 device.losRaised = losRaised
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700164 return &device
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530165}
166
167//NewDeviceHandler creates a new device handler
Himani Chawlacd407802020-12-10 12:08:59 +0530168func NewDeviceHandler(cp adapterif.CoreProxy, ap adapterif.AdapterProxy, ep eventif.EventProxy, device *voltha.Device, adapter *OpenOLT, cm *config.ConfigManager) *DeviceHandler {
cuilin20187b2a8c32019-03-26 19:52:28 -0700169 var dh DeviceHandler
Matteo Scandolodfa7a972020-11-06 13:03:40 -0800170 dh.cm = cm
cuilin20187b2a8c32019-03-26 19:52:28 -0700171 dh.coreProxy = cp
Girish Gowdru0c588b22019-04-23 23:24:56 -0400172 dh.AdapterProxy = ap
Devmalya Paulfb990a52019-07-09 10:01:49 -0400173 dh.EventProxy = ep
cuilin20187b2a8c32019-03-26 19:52:28 -0700174 cloned := (proto.Clone(device)).(*voltha.Device)
cuilin20187b2a8c32019-03-26 19:52:28 -0700175 dh.device = cloned
176 dh.openOLT = adapter
177 dh.exitChannel = make(chan int, 1)
178 dh.lockDevice = sync.RWMutex{}
Naga Manjunath7615e552019-10-11 22:35:47 +0530179 dh.stopCollector = make(chan bool, 2)
Abhilash Laxmeshwarf9942e92020-01-07 15:32:44 +0530180 dh.stopHeartbeatCheck = make(chan bool, 2)
Naga Manjunath7615e552019-10-11 22:35:47 +0530181 dh.metrics = pmmetrics.NewPmMetrics(cloned.Id, pmmetrics.Frequency(150), pmmetrics.FrequencyOverride(false), pmmetrics.Grouped(false), pmmetrics.Metrics(pmNames))
Chaitrashree G Sef088112020-02-03 21:39:27 -0500182 dh.activePorts = sync.Map{}
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400183 dh.stopIndications = make(chan bool, 1)
Mahir Gunyelb0046752021-02-26 13:51:05 -0800184 dh.perPonOnuIndicationChannel = make(map[uint32]onuIndicationChannels)
Girish Gowdra491a9c62021-01-06 16:43:07 -0800185 // Create a slice of buffered channels for handling concurrent mcast flow/group.
186 dh.incomingMcastFlowOrGroup = make([]chan McastFlowOrGroupControlBlock, MaxNumOfGroupHandlerChannels)
187 for i := range dh.incomingMcastFlowOrGroup {
188 dh.incomingMcastFlowOrGroup[i] = make(chan McastFlowOrGroupControlBlock, MaxNumOfGroupHandlerChannels)
189 // Spin up a go routine to handling incoming mcast flow/group (add/modify/remove).
190 // There will be MaxNumOfGroupHandlerChannels number of mcastFlowOrGroupChannelHandlerRoutine go routines.
191 // These routines will be blocked on the dh.incomingMcastFlowOrGroup[mcast-group-id modulo MaxNumOfGroupHandlerChannels] channel
192 // for incoming mcast flow/group to be processed serially.
193 go dh.mcastFlowOrGroupChannelHandlerRoutine(dh.incomingMcastFlowOrGroup[i])
194 }
cuilin20187b2a8c32019-03-26 19:52:28 -0700195 //TODO initialize the support classes.
196 return &dh
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530197}
198
199// start save the device to the data model
200func (dh *DeviceHandler) start(ctx context.Context) {
cuilin20187b2a8c32019-03-26 19:52:28 -0700201 dh.lockDevice.Lock()
202 defer dh.lockDevice.Unlock()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000203 logger.Debugw(ctx, "starting-device-agent", log.Fields{"device": dh.device})
cuilin20187b2a8c32019-03-26 19:52:28 -0700204 // Add the initial device to the local model
Neha Sharma96b7bf22020-06-15 10:37:32 +0000205 logger.Debug(ctx, "device-agent-started")
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530206}
207
208// stop stops the device dh. Not much to do for now
209func (dh *DeviceHandler) stop(ctx context.Context) {
cuilin20187b2a8c32019-03-26 19:52:28 -0700210 dh.lockDevice.Lock()
211 defer dh.lockDevice.Unlock()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000212 logger.Debug(ctx, "stopping-device-agent")
cuilin20187b2a8c32019-03-26 19:52:28 -0700213 dh.exitChannel <- 1
Neha Sharma96b7bf22020-06-15 10:37:32 +0000214 logger.Debug(ctx, "device-agent-stopped")
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530215}
216
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400217func macifyIP(ip net.IP) string {
218 if len(ip) > 0 {
219 oct1 := strconv.FormatInt(int64(ip[12]), 16)
220 oct2 := strconv.FormatInt(int64(ip[13]), 16)
221 oct3 := strconv.FormatInt(int64(ip[14]), 16)
222 oct4 := strconv.FormatInt(int64(ip[15]), 16)
223 return fmt.Sprintf("00:00:%02v:%02v:%02v:%02v", oct1, oct2, oct3, oct4)
224 }
225 return ""
226}
227
Neha Sharma96b7bf22020-06-15 10:37:32 +0000228func generateMacFromHost(ctx context.Context, host string) (string, error) {
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400229 var genmac string
230 var addr net.IP
231 var ips []string
232 var err error
233
Neha Sharma96b7bf22020-06-15 10:37:32 +0000234 logger.Debugw(ctx, "generating-mac-from-host", log.Fields{"host": host})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400235
236 if addr = net.ParseIP(host); addr == nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000237 logger.Debugw(ctx, "looking-up-hostname", log.Fields{"host": host})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400238
239 if ips, err = net.LookupHost(host); err == nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000240 logger.Debugw(ctx, "dns-result-ips", log.Fields{"ips": ips})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400241 if addr = net.ParseIP(ips[0]); addr == nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000242 return "", olterrors.NewErrInvalidValue(log.Fields{"ip": ips[0]}, nil)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400243 }
244 genmac = macifyIP(addr)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000245 logger.Debugw(ctx, "using-ip-as-mac",
Shrey Baid807a2a02020-04-09 12:52:45 +0530246 log.Fields{"host": ips[0],
247 "mac": genmac})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400248 return genmac, nil
249 }
Girish Kumarf26e4882020-03-05 06:49:10 +0000250 return "", olterrors.NewErrAdapter("cannot-resolve-hostname-to-ip", log.Fields{"host": host}, err)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400251 }
252
253 genmac = macifyIP(addr)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000254 logger.Debugw(ctx, "using-ip-as-mac",
Shrey Baid807a2a02020-04-09 12:52:45 +0530255 log.Fields{"host": host,
256 "mac": genmac})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400257 return genmac, nil
258}
259
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530260func macAddressToUint32Array(mac string) []uint32 {
cuilin20187b2a8c32019-03-26 19:52:28 -0700261 slist := strings.Split(mac, ":")
262 result := make([]uint32, len(slist))
263 var err error
264 var tmp int64
265 for index, val := range slist {
266 if tmp, err = strconv.ParseInt(val, 16, 32); err != nil {
267 return []uint32{1, 2, 3, 4, 5, 6}
268 }
269 result[index] = uint32(tmp)
270 }
271 return result
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530272}
273
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700274//GetportLabel returns the label for the NNI and the PON port based on port number and port type
David K. Bainbridge794735f2020-02-11 21:01:37 -0800275func GetportLabel(portNum uint32, portType voltha.Port_PortType) (string, error) {
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530276
David K. Bainbridge794735f2020-02-11 21:01:37 -0800277 switch portType {
278 case voltha.Port_ETHERNET_NNI:
279 return fmt.Sprintf("nni-%d", portNum), nil
280 case voltha.Port_PON_OLT:
281 return fmt.Sprintf("pon-%d", portNum), nil
cuilin20187b2a8c32019-03-26 19:52:28 -0700282 }
David K. Bainbridge794735f2020-02-11 21:01:37 -0800283
Girish Kumarf26e4882020-03-05 06:49:10 +0000284 return "", olterrors.NewErrInvalidValue(log.Fields{"port-type": portType}, nil)
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530285}
286
Neha Sharma96b7bf22020-06-15 10:37:32 +0000287func (dh *DeviceHandler) addPort(ctx context.Context, intfID uint32, portType voltha.Port_PortType, state string) error {
Esin Karamanccb714b2019-11-29 15:02:06 +0000288 var operStatus common.OperStatus_Types
cuilin20187b2a8c32019-03-26 19:52:28 -0700289 if state == "up" {
290 operStatus = voltha.OperStatus_ACTIVE
kesavand39e0aa32020-01-28 20:58:50 -0500291 //populating the intfStatus map
Chaitrashree G Sef088112020-02-03 21:39:27 -0500292 dh.activePorts.Store(intfID, true)
cuilin20187b2a8c32019-03-26 19:52:28 -0700293 } else {
294 operStatus = voltha.OperStatus_DISCOVERED
Chaitrashree G Sef088112020-02-03 21:39:27 -0500295 dh.activePorts.Store(intfID, false)
cuilin20187b2a8c32019-03-26 19:52:28 -0700296 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700297 portNum := IntfIDToPortNo(intfID, portType)
Chaitrashree G Sc0878ec2020-05-21 04:59:53 -0400298 label, err := GetportLabel(intfID, portType)
David K. Bainbridge794735f2020-02-11 21:01:37 -0800299 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000300 return olterrors.NewErrNotFound("port-label", log.Fields{"port-number": portNum, "port-type": portType}, err)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400301 }
Chaitrashree G Sded0a832020-01-09 20:21:48 -0500302
Neha Sharma8f4e4322020-08-06 10:51:53 +0000303 if port, err := dh.coreProxy.GetDevicePort(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, portNum); err == nil && port.Type == portType {
Girish Kumara1ea2aa2020-08-19 18:14:22 +0000304 logger.Debug(ctx, "port-already-exists-updating-oper-status-of-port")
Neha Sharma8f4e4322020-08-06 10:51:53 +0000305 if err := dh.coreProxy.PortStateUpdate(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, portType, portNum, operStatus); err != nil {
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400306 return olterrors.NewErrAdapter("failed-to-update-port-state", log.Fields{
307 "device-id": dh.device.Id,
308 "port-type": portType,
309 "port-number": portNum,
310 "oper-status": operStatus}, err).Log()
Chaitrashree G Sded0a832020-01-09 20:21:48 -0500311 }
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400312 return nil
Chaitrashree G Sded0a832020-01-09 20:21:48 -0500313 }
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400314 // Now create Port
Girish Gowdra631ef3d2020-06-15 10:45:52 -0700315 capacity := uint32(of.OfpPortFeatures_OFPPF_1GB_FD | of.OfpPortFeatures_OFPPF_FIBER)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400316 port := &voltha.Port{
cuilin20187b2a8c32019-03-26 19:52:28 -0700317 PortNo: portNum,
318 Label: label,
319 Type: portType,
320 OperStatus: operStatus,
Girish Gowdra631ef3d2020-06-15 10:45:52 -0700321 OfpPort: &of.OfpPort{
322 HwAddr: macAddressToUint32Array(dh.device.MacAddress),
323 Config: 0,
324 State: uint32(of.OfpPortState_OFPPS_LIVE),
325 Curr: capacity,
326 Advertised: capacity,
327 Peer: capacity,
328 CurrSpeed: uint32(of.OfpPortFeatures_OFPPF_1GB_FD),
329 MaxSpeed: uint32(of.OfpPortFeatures_OFPPF_1GB_FD),
330 },
cuilin20187b2a8c32019-03-26 19:52:28 -0700331 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000332 logger.Debugw(ctx, "sending-port-update-to-core", log.Fields{"port": port})
cuilin20187b2a8c32019-03-26 19:52:28 -0700333 // Synchronous call to update device - this method is run in its own go routine
Neha Sharma8f4e4322020-08-06 10:51:53 +0000334 if err := dh.coreProxy.PortCreated(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, port); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000335 return olterrors.NewErrAdapter("error-creating-port", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -0800336 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +0000337 "port-type": portType}, err)
Girish Gowdru1110ef22019-06-24 11:17:59 -0400338 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000339 go dh.updateLocalDevice(ctx)
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530340 return nil
341}
342
Kent Hagermane6ff1012020-07-14 15:07:53 -0400343func (dh *DeviceHandler) updateLocalDevice(ctx context.Context) {
Neha Sharma8f4e4322020-08-06 10:51:53 +0000344 device, err := dh.coreProxy.GetDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, dh.device.Id)
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530345 if err != nil || device == nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400346 logger.Errorf(ctx, "device-not-found", log.Fields{"device-id": dh.device.Id}, err)
347 return
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530348 }
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800349 dh.lockDevice.Lock()
350 defer dh.lockDevice.Unlock()
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530351 dh.device = device
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530352}
353
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700354// nolint: gocyclo
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530355// readIndications to read the indications from the OLT device
David K. Bainbridge794735f2020-02-11 21:01:37 -0800356func (dh *DeviceHandler) readIndications(ctx context.Context) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000357 defer logger.Debugw(ctx, "indications-ended", log.Fields{"device-id": dh.device.Id})
Girish Gowdra3ab6d212020-03-24 17:33:15 -0700358 defer func() {
359 dh.lockDevice.Lock()
360 dh.isReadIndicationRoutineActive = false
361 dh.lockDevice.Unlock()
362 }()
Girish Gowdra3f974912020-03-23 20:35:18 -0700363 indications, err := dh.startOpenOltIndicationStream(ctx)
cuilin20187b2a8c32019-03-26 19:52:28 -0700364 if err != nil {
Girish Gowdra3f974912020-03-23 20:35:18 -0700365 return err
cuilin20187b2a8c32019-03-26 19:52:28 -0700366 }
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400367 /* get device state */
npujarec5762e2020-01-01 14:08:48 +0530368 device, err := dh.coreProxy.GetDevice(ctx, dh.device.Id, dh.device.Id)
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400369 if err != nil || device == nil {
370 /*TODO: needs to handle error scenarios */
Girish Kumarf26e4882020-03-05 06:49:10 +0000371 return olterrors.NewErrNotFound("device", log.Fields{"device-id": dh.device.Id}, err)
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400372 }
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400373
David Bainbridgef5879ca2019-12-13 21:17:54 +0000374 // Create an exponential backoff around re-enabling indications. The
375 // maximum elapsed time for the back off is set to 0 so that we will
376 // continue to retry. The max interval defaults to 1m, but is set
377 // here for code clarity
378 indicationBackoff := backoff.NewExponentialBackOff()
379 indicationBackoff.MaxElapsedTime = 0
380 indicationBackoff.MaxInterval = 1 * time.Minute
Girish Gowdra3f974912020-03-23 20:35:18 -0700381
Girish Gowdra3ab6d212020-03-24 17:33:15 -0700382 dh.lockDevice.Lock()
383 dh.isReadIndicationRoutineActive = true
384 dh.lockDevice.Unlock()
385
Girish Gowdra3f974912020-03-23 20:35:18 -0700386Loop:
cuilin20187b2a8c32019-03-26 19:52:28 -0700387 for {
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400388 select {
389 case <-dh.stopIndications:
divyadesai3af43e12020-08-18 07:10:54 +0000390 logger.Debugw(ctx, "stopping-collecting-indications-for-olt", log.Fields{"device-id": dh.device.Id})
Girish Gowdra3f974912020-03-23 20:35:18 -0700391 break Loop
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400392 default:
393 indication, err := indications.Recv()
394 if err == io.EOF {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000395 logger.Infow(ctx, "eof-for-indications",
Shrey Baid807a2a02020-04-09 12:52:45 +0530396 log.Fields{"err": err,
Thomas Lee S985938d2020-05-04 11:40:41 +0530397 "device-id": dh.device.Id})
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400398 // Use an exponential back off to prevent getting into a tight loop
399 duration := indicationBackoff.NextBackOff()
400 if duration == backoff.Stop {
401 // If we reach a maximum then warn and reset the backoff
402 // timer and keep attempting.
Neha Sharma96b7bf22020-06-15 10:37:32 +0000403 logger.Warnw(ctx, "maximum-indication-backoff-reached--resetting-backoff-timer",
Shrey Baid807a2a02020-04-09 12:52:45 +0530404 log.Fields{"max-indication-backoff": indicationBackoff.MaxElapsedTime,
Thomas Lee S985938d2020-05-04 11:40:41 +0530405 "device-id": dh.device.Id})
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400406 indicationBackoff.Reset()
407 }
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700408
409 // On failure process a backoff timer while watching for stopIndications
410 // events
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700411 backoffTimer := time.NewTimer(indicationBackoff.NextBackOff())
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700412 select {
413 case <-dh.stopIndications:
divyadesai3af43e12020-08-18 07:10:54 +0000414 logger.Debugw(ctx, "stopping-collecting-indications-for-olt", log.Fields{"device-id": dh.device.Id})
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700415 if !backoffTimer.Stop() {
416 <-backoffTimer.C
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700417 }
418 break Loop
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700419 case <-backoffTimer.C:
420 // backoffTimer expired continue
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700421 }
Girish Gowdra3f974912020-03-23 20:35:18 -0700422 if indications, err = dh.startOpenOltIndicationStream(ctx); err != nil {
423 return err
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400424 }
425 continue
David Bainbridgef5879ca2019-12-13 21:17:54 +0000426 }
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530427 if err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000428 logger.Errorw(ctx, "read-indication-error",
Shrey Baid807a2a02020-04-09 12:52:45 +0530429 log.Fields{"err": err,
Thomas Lee S985938d2020-05-04 11:40:41 +0530430 "device-id": dh.device.Id})
Girish Gowdra3f974912020-03-23 20:35:18 -0700431 // Close the stream, and re-initialize it
432 if err = indications.CloseSend(); err != nil {
433 // Ok to ignore here, because we landed here due to a problem on the stream
434 // In all probability, the closeSend call may fail
Neha Sharma96b7bf22020-06-15 10:37:32 +0000435 logger.Debugw(ctx, "error-closing-send stream--error-ignored",
Shrey Baid807a2a02020-04-09 12:52:45 +0530436 log.Fields{"err": err,
Thomas Lee S985938d2020-05-04 11:40:41 +0530437 "device-id": dh.device.Id})
Girish Gowdra3f974912020-03-23 20:35:18 -0700438 }
439 if indications, err = dh.startOpenOltIndicationStream(ctx); err != nil {
440 return err
441 }
442 // once we re-initialized the indication stream, continue to read indications
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400443 continue
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530444 }
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400445 // Reset backoff if we have a successful receive
446 indicationBackoff.Reset()
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400447 // When OLT is admin down, ignore all indications.
Thomas Lee S985938d2020-05-04 11:40:41 +0530448 if device.AdminState == voltha.AdminState_DISABLED && !isIndicationAllowedDuringOltAdminDown(indication) {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000449 logger.Debugw(ctx, "olt-is-admin-down, ignore indication",
Shrey Baid807a2a02020-04-09 12:52:45 +0530450 log.Fields{"indication": indication,
Thomas Lee S985938d2020-05-04 11:40:41 +0530451 "device-id": dh.device.Id})
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400452 continue
Devmalya Paul495b94a2019-08-27 19:42:00 -0400453 }
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400454 dh.handleIndication(ctx, indication)
cuilin20187b2a8c32019-03-26 19:52:28 -0700455 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700456 }
Girish Gowdra3f974912020-03-23 20:35:18 -0700457 // Close the send stream
458 _ = indications.CloseSend() // Ok to ignore error, as we stopping the readIndication anyway
Girish Gowdra3ab6d212020-03-24 17:33:15 -0700459
Girish Gowdra3f974912020-03-23 20:35:18 -0700460 return nil
461}
462
463func (dh *DeviceHandler) startOpenOltIndicationStream(ctx context.Context) (oop.Openolt_EnableIndicationClient, error) {
464
465 indications, err := dh.Client.EnableIndication(ctx, new(oop.Empty))
466 if err != nil {
467 return nil, olterrors.NewErrCommunication("indication-read-failure", log.Fields{"device-id": dh.device.Id}, err).Log()
468 }
469 if indications == nil {
470 return nil, olterrors.NewErrInvalidValue(log.Fields{"indications": nil, "device-id": dh.device.Id}, nil).Log()
471 }
472
473 return indications, nil
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400474}
475
476// isIndicationAllowedDuringOltAdminDown returns true if the indication is allowed during OLT Admin down, else false
477func isIndicationAllowedDuringOltAdminDown(indication *oop.Indication) bool {
478 switch indication.Data.(type) {
479 case *oop.Indication_OltInd, *oop.Indication_IntfInd, *oop.Indication_IntfOperInd:
480 return true
481
482 default:
483 return false
484 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700485}
486
David K. Bainbridge794735f2020-02-11 21:01:37 -0800487func (dh *DeviceHandler) handleOltIndication(ctx context.Context, oltIndication *oop.OltIndication) error {
Girish Gowdrac1b9d5e2021-04-22 12:47:44 -0700488 raisedTs := time.Now().Unix()
Gamze Abakaa1a50522019-10-03 19:28:27 +0000489 if oltIndication.OperState == "up" && dh.transitionMap.currentDeviceState != deviceStateUp {
npujarec5762e2020-01-01 14:08:48 +0530490 dh.transitionMap.Handle(ctx, DeviceUpInd)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700491 } else if oltIndication.OperState == "down" {
npujarec5762e2020-01-01 14:08:48 +0530492 dh.transitionMap.Handle(ctx, DeviceDownInd)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700493 }
Daniele Rossi051466a2019-07-26 13:39:37 +0000494 // Send or clear Alarm
Neha Sharma96b7bf22020-06-15 10:37:32 +0000495 if err := dh.eventMgr.oltUpDownIndication(ctx, oltIndication, dh.device.Id, raisedTs); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +0530496 return olterrors.NewErrAdapter("failed-indication", log.Fields{
divyadesai3af43e12020-08-18 07:10:54 +0000497 "device-id": dh.device.Id,
David K. Bainbridge794735f2020-02-11 21:01:37 -0800498 "indication": oltIndication,
Girish Kumarf26e4882020-03-05 06:49:10 +0000499 "timestamp": raisedTs}, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -0800500 }
501 return nil
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700502}
503
David K. Bainbridge794735f2020-02-11 21:01:37 -0800504// nolint: gocyclo
npujarec5762e2020-01-01 14:08:48 +0530505func (dh *DeviceHandler) handleIndication(ctx context.Context, indication *oop.Indication) {
Girish Gowdrac1b9d5e2021-04-22 12:47:44 -0700506 raisedTs := time.Now().Unix()
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700507 switch indication.Data.(type) {
508 case *oop.Indication_OltInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000509 span, ctx := log.CreateChildSpan(ctx, "olt-indication", log.Fields{"device-id": dh.device.Id})
510 defer span.Finish()
511
David K. Bainbridge794735f2020-02-11 21:01:37 -0800512 if err := dh.handleOltIndication(ctx, indication.GetOltInd()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400513 _ = olterrors.NewErrAdapter("handle-indication-error", log.Fields{"type": "olt", "device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800514 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700515 case *oop.Indication_IntfInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000516 span, ctx := log.CreateChildSpan(ctx, "interface-indication", log.Fields{"device-id": dh.device.Id})
517 defer span.Finish()
518
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700519 intfInd := indication.GetIntfInd()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800520 go func() {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000521 if err := dh.addPort(ctx, intfInd.GetIntfId(), voltha.Port_PON_OLT, intfInd.GetOperState()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400522 _ = olterrors.NewErrAdapter("handle-indication-error", log.Fields{"type": "interface", "device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800523 }
524 }()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000525 logger.Infow(ctx, "received-interface-indication", log.Fields{"InterfaceInd": intfInd, "device-id": dh.device.Id})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700526 case *oop.Indication_IntfOperInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000527 span, ctx := log.CreateChildSpan(ctx, "interface-oper-indication", log.Fields{"device-id": dh.device.Id})
528 defer span.Finish()
529
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700530 intfOperInd := indication.GetIntfOperInd()
531 if intfOperInd.GetType() == "nni" {
David K. Bainbridge794735f2020-02-11 21:01:37 -0800532 go func() {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000533 if err := dh.addPort(ctx, intfOperInd.GetIntfId(), voltha.Port_ETHERNET_NNI, intfOperInd.GetOperState()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400534 _ = olterrors.NewErrAdapter("handle-indication-error", log.Fields{"type": "interface-oper-nni", "device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800535 }
536 }()
Kent Hagermane6ff1012020-07-14 15:07:53 -0400537 if err := dh.resourceMgr.AddNNIToKVStore(ctx, intfOperInd.GetIntfId()); err != nil {
538 logger.Warn(ctx, err)
539 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700540 } else if intfOperInd.GetType() == "pon" {
541 // TODO: Check what needs to be handled here for When PON PORT down, ONU will be down
542 // Handle pon port update
David K. Bainbridge794735f2020-02-11 21:01:37 -0800543 go func() {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000544 if err := dh.addPort(ctx, intfOperInd.GetIntfId(), voltha.Port_PON_OLT, intfOperInd.GetOperState()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400545 _ = olterrors.NewErrAdapter("handle-indication-error", log.Fields{"type": "interface-oper-pon", "device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800546 }
547 }()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000548 go dh.eventMgr.oltIntfOperIndication(ctx, indication.GetIntfOperInd(), dh.device.Id, raisedTs)
cuilin20187b2a8c32019-03-26 19:52:28 -0700549 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000550 logger.Infow(ctx, "received-interface-oper-indication",
Shrey Baid807a2a02020-04-09 12:52:45 +0530551 log.Fields{"interfaceOperInd": intfOperInd,
Thomas Lee S985938d2020-05-04 11:40:41 +0530552 "device-id": dh.device.Id})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700553 case *oop.Indication_OnuDiscInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000554 span, ctx := log.CreateChildSpan(ctx, "onu-discovery-indication", log.Fields{"device-id": dh.device.Id})
555 defer span.Finish()
556
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700557 onuDiscInd := indication.GetOnuDiscInd()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000558 logger.Infow(ctx, "received-onu-discovery-indication", log.Fields{"OnuDiscInd": onuDiscInd, "device-id": dh.device.Id})
Mahir Gunyel2fb81472020-12-16 23:18:34 -0800559 //put message to channel and return immediately
Mahir Gunyelb0046752021-02-26 13:51:05 -0800560 dh.putOnuIndicationToChannel(ctx, indication, onuDiscInd.GetIntfId())
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700561 case *oop.Indication_OnuInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000562 span, ctx := log.CreateChildSpan(ctx, "onu-indication", log.Fields{"device-id": dh.device.Id})
563 defer span.Finish()
564
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700565 onuInd := indication.GetOnuInd()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000566 logger.Infow(ctx, "received-onu-indication", log.Fields{"OnuInd": onuInd, "device-id": dh.device.Id})
Mahir Gunyel2fb81472020-12-16 23:18:34 -0800567 //put message to channel and return immediately
Mahir Gunyelb0046752021-02-26 13:51:05 -0800568 dh.putOnuIndicationToChannel(ctx, indication, onuInd.GetIntfId())
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700569 case *oop.Indication_OmciInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000570 span, ctx := log.CreateChildSpan(ctx, "omci-indication", log.Fields{"device-id": dh.device.Id})
571 defer span.Finish()
572
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700573 omciInd := indication.GetOmciInd()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000574 logger.Debugw(ctx, "received-omci-indication", log.Fields{"intf-id": omciInd.IntfId, "onu-id": omciInd.OnuId, "device-id": dh.device.Id})
David K. Bainbridge794735f2020-02-11 21:01:37 -0800575 go func() {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000576 if err := dh.omciIndication(ctx, omciInd); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400577 _ = olterrors.NewErrAdapter("handle-indication-error", log.Fields{"type": "omci", "device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800578 }
579 }()
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700580 case *oop.Indication_PktInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000581 span, ctx := log.CreateChildSpan(ctx, "packet-indication", log.Fields{"device-id": dh.device.Id})
582 defer span.Finish()
583
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700584 pktInd := indication.GetPktInd()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000585 logger.Debugw(ctx, "received-packet-indication", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -0700586 "intf-type": pktInd.IntfId,
587 "intf-id": pktInd.IntfId,
588 "gem-port-id": pktInd.GemportId,
589 "port-no": pktInd.PortNo,
590 "device-id": dh.device.Id,
591 })
592
593 if logger.V(log.DebugLevel) {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000594 logger.Debugw(ctx, "received-packet-indication-packet", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -0700595 "intf-type": pktInd.IntfId,
596 "intf-id": pktInd.IntfId,
597 "gem-port-id": pktInd.GemportId,
598 "port-no": pktInd.PortNo,
599 "packet": hex.EncodeToString(pktInd.Pkt),
600 "device-id": dh.device.Id,
601 })
602 }
603
David K. Bainbridge794735f2020-02-11 21:01:37 -0800604 go func() {
605 if err := dh.handlePacketIndication(ctx, pktInd); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400606 _ = olterrors.NewErrAdapter("handle-indication-error", log.Fields{"type": "packet", "device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800607 }
608 }()
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700609 case *oop.Indication_PortStats:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000610 span, ctx := log.CreateChildSpan(ctx, "port-statistics-indication", log.Fields{"device-id": dh.device.Id})
611 defer span.Finish()
612
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700613 portStats := indication.GetPortStats()
Girish Gowdra9602eb42020-09-09 15:50:39 -0700614 go dh.portStats.PortStatisticsIndication(ctx, portStats, dh.totalPonPorts)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700615 case *oop.Indication_FlowStats:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000616 span, ctx := log.CreateChildSpan(ctx, "flow-stats-indication", log.Fields{"device-id": dh.device.Id})
617 defer span.Finish()
618
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700619 flowStats := indication.GetFlowStats()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000620 logger.Infow(ctx, "received-flow-stats", log.Fields{"FlowStats": flowStats, "device-id": dh.device.Id})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700621 case *oop.Indication_AlarmInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000622 span, ctx := log.CreateChildSpan(ctx, "alarm-indication", log.Fields{"device-id": dh.device.Id})
623 defer span.Finish()
624
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700625 alarmInd := indication.GetAlarmInd()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000626 logger.Infow(ctx, "received-alarm-indication", log.Fields{"AlarmInd": alarmInd, "device-id": dh.device.Id})
627 go dh.eventMgr.ProcessEvents(ctx, alarmInd, dh.device.Id, raisedTs)
cuilin20187b2a8c32019-03-26 19:52:28 -0700628 }
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530629}
630
631// doStateUp handle the olt up indication and update to voltha core
npujarec5762e2020-01-01 14:08:48 +0530632func (dh *DeviceHandler) doStateUp(ctx context.Context) error {
Thomas Lee S85f37312020-04-03 17:06:12 +0530633 //starting the stat collector
Neha Sharma96b7bf22020-06-15 10:37:32 +0000634 go startCollector(ctx, dh)
Thomas Lee S85f37312020-04-03 17:06:12 +0530635
Girish Gowdru0c588b22019-04-23 23:24:56 -0400636 // Synchronous call to update device state - this method is run in its own go routine
npujarec5762e2020-01-01 14:08:48 +0530637 if err := dh.coreProxy.DeviceStateUpdate(ctx, dh.device.Id, voltha.ConnectStatus_REACHABLE,
Girish Gowdru0c588b22019-04-23 23:24:56 -0400638 voltha.OperStatus_ACTIVE); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000639 return olterrors.NewErrAdapter("device-update-failed", log.Fields{"device-id": dh.device.Id}, err)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400640 }
Gamze Abaka07868a52020-12-17 14:19:28 +0000641
642 //Clear olt communication failure event
643 dh.device.ConnectStatus = voltha.ConnectStatus_REACHABLE
644 dh.device.OperStatus = voltha.OperStatus_ACTIVE
Girish Gowdrac1b9d5e2021-04-22 12:47:44 -0700645 raisedTs := time.Now().Unix()
Gamze Abaka07868a52020-12-17 14:19:28 +0000646 go dh.eventMgr.oltCommunicationEvent(ctx, dh.device, raisedTs)
647
Gamze Abakac2c32a62021-03-11 11:44:18 +0000648 //check adapter and agent reconcile status
649 //reboot olt if needed (olt disconnection case)
650 if dh.adapterPreviouslyConnected != dh.agentPreviouslyConnected {
651 logger.Warnw(ctx, "different-reconcile-status-between-adapter-and-agent-rebooting-device",
652 log.Fields{
653 "device-id": dh.device.Id,
654 "adapter-status": dh.adapterPreviouslyConnected,
655 "agent-status": dh.agentPreviouslyConnected,
656 })
657 _ = dh.RebootDevice(ctx, dh.device)
658 }
659
Girish Gowdru0c588b22019-04-23 23:24:56 -0400660 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530661}
662
663// doStateDown handle the olt down indication
npujarec5762e2020-01-01 14:08:48 +0530664func (dh *DeviceHandler) doStateDown(ctx context.Context) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000665 logger.Debugw(ctx, "do-state-down-start", log.Fields{"device-id": dh.device.Id})
Girish Gowdrud4245152019-05-10 00:47:31 -0400666
npujarec5762e2020-01-01 14:08:48 +0530667 device, err := dh.coreProxy.GetDevice(ctx, dh.device.Id, dh.device.Id)
Girish Gowdrud4245152019-05-10 00:47:31 -0400668 if err != nil || device == nil {
669 /*TODO: needs to handle error scenarios */
Girish Kumarf26e4882020-03-05 06:49:10 +0000670 return olterrors.NewErrNotFound("device", log.Fields{"device-id": dh.device.Id}, err)
Girish Gowdrud4245152019-05-10 00:47:31 -0400671 }
672
673 cloned := proto.Clone(device).(*voltha.Device)
Girish Gowdrud4245152019-05-10 00:47:31 -0400674
675 //Update the device oper state and connection status
676 cloned.OperStatus = voltha.OperStatus_UNKNOWN
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800677 dh.lockDevice.Lock()
Girish Gowdrud4245152019-05-10 00:47:31 -0400678 dh.device = cloned
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800679 dh.lockDevice.Unlock()
Girish Gowdrud4245152019-05-10 00:47:31 -0400680
David K. Bainbridge794735f2020-02-11 21:01:37 -0800681 if err = dh.coreProxy.DeviceStateUpdate(ctx, cloned.Id, cloned.ConnectStatus, cloned.OperStatus); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000682 return olterrors.NewErrAdapter("state-update-failed", log.Fields{"device-id": device.Id}, err)
Girish Gowdrud4245152019-05-10 00:47:31 -0400683 }
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400684
685 //get the child device for the parent device
npujarec5762e2020-01-01 14:08:48 +0530686 onuDevices, err := dh.coreProxy.GetChildDevices(ctx, dh.device.Id)
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400687 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000688 return olterrors.NewErrAdapter("child-device-fetch-failed", log.Fields{"device-id": dh.device.Id}, err)
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400689 }
690 for _, onuDevice := range onuDevices.Items {
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400691 // Update onu state as down in onu adapter
692 onuInd := oop.OnuIndication{}
693 onuInd.OperState = "down"
David K. Bainbridge794735f2020-02-11 21:01:37 -0800694 err := dh.AdapterProxy.SendInterAdapterMessage(ctx, &onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
serkant.uluderya4aff1862020-09-17 23:35:26 +0300695 dh.openOLT.config.Topic, onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
David K. Bainbridge794735f2020-02-11 21:01:37 -0800696 if err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400697 _ = olterrors.NewErrCommunication("inter-adapter-send-failed", log.Fields{
serkant.uluderya4aff1862020-09-17 23:35:26 +0300698 "source": dh.openOLT.config.Topic,
David K. Bainbridge794735f2020-02-11 21:01:37 -0800699 "onu-indicator": onuInd,
700 "device-type": onuDevice.Type,
701 "device-id": onuDevice.Id}, err).LogAt(log.ErrorLevel)
serkant.uluderya245caba2019-09-24 23:15:29 -0700702 //Do not return here and continue to process other ONUs
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800703 } else {
704 logger.Debugw(ctx, "sending inter adapter down ind to onu success", log.Fields{"olt-device-id": device.Id, "onu-device-id": onuDevice.Id})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700705 }
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400706 }
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800707 dh.lockDevice.Lock()
serkant.uluderya245caba2019-09-24 23:15:29 -0700708 /* Discovered ONUs entries need to be cleared , since after OLT
709 is up, it starts sending discovery indications again*/
Naga Manjunatha8dc9372019-10-31 23:01:18 +0530710 dh.discOnus = sync.Map{}
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800711 dh.lockDevice.Unlock()
712
Neha Sharma96b7bf22020-06-15 10:37:32 +0000713 logger.Debugw(ctx, "do-state-down-end", log.Fields{"device-id": device.Id})
cuilin20187b2a8c32019-03-26 19:52:28 -0700714 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530715}
716
717// doStateInit dial the grpc before going to init state
npujarec5762e2020-01-01 14:08:48 +0530718func (dh *DeviceHandler) doStateInit(ctx context.Context) error {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400719 var err error
Girish Kumar93e91742020-07-27 16:43:19 +0000720 // Use Intercepters to automatically inject and publish Open Tracing Spans by this GRPC client
721 dh.clientCon, err = grpc.Dial(dh.device.GetHostAndPort(),
722 grpc.WithInsecure(),
723 grpc.WithBlock(),
724 grpc.WithStreamInterceptor(grpc_middleware.ChainStreamClient(
Girish Kumar935f7af2020-08-18 11:59:42 +0000725 grpc_opentracing.StreamClientInterceptor(grpc_opentracing.WithTracer(log.ActiveTracerProxy{})),
Girish Kumar93e91742020-07-27 16:43:19 +0000726 )),
727 grpc.WithUnaryInterceptor(grpc_middleware.ChainUnaryClient(
Girish Kumar935f7af2020-08-18 11:59:42 +0000728 grpc_opentracing.UnaryClientInterceptor(grpc_opentracing.WithTracer(log.ActiveTracerProxy{})),
Girish Kumar93e91742020-07-27 16:43:19 +0000729 )))
730
731 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +0530732 return olterrors.NewErrCommunication("dial-failure", log.Fields{
Thomas Lee S985938d2020-05-04 11:40:41 +0530733 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +0000734 "host-and-port": dh.device.GetHostAndPort()}, err)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400735 }
736 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530737}
738
739// postInit create olt client instance to invoke RPC on the olt device
npujarec5762e2020-01-01 14:08:48 +0530740func (dh *DeviceHandler) postInit(ctx context.Context) error {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400741 dh.Client = oop.NewOpenoltClient(dh.clientCon)
npujarec5762e2020-01-01 14:08:48 +0530742 dh.transitionMap.Handle(ctx, GrpcConnected)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400743 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530744}
745
746// doStateConnected get the device info and update to voltha core
npujarec5762e2020-01-01 14:08:48 +0530747func (dh *DeviceHandler) doStateConnected(ctx context.Context) error {
Thomas Lee S985938d2020-05-04 11:40:41 +0530748 var err error
Neha Sharma96b7bf22020-06-15 10:37:32 +0000749 logger.Debugw(ctx, "olt-device-connected", log.Fields{"device-id": dh.device.Id})
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400750
751 // Case where OLT is disabled and then rebooted.
Thomas Lee S985938d2020-05-04 11:40:41 +0530752 device, err := dh.coreProxy.GetDevice(ctx, dh.device.Id, dh.device.Id)
753 if err != nil || device == nil {
754 /*TODO: needs to handle error scenarios */
755 return olterrors.NewErrAdapter("device-fetch-failed", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
756 }
757 if device.AdminState == voltha.AdminState_DISABLED {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000758 logger.Debugln(ctx, "do-state-connected--device-admin-state-down")
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400759
760 cloned := proto.Clone(device).(*voltha.Device)
761 cloned.ConnectStatus = voltha.ConnectStatus_REACHABLE
762 cloned.OperStatus = voltha.OperStatus_UNKNOWN
763 dh.device = cloned
Thomas Lee S985938d2020-05-04 11:40:41 +0530764 if err = dh.coreProxy.DeviceStateUpdate(ctx, cloned.Id, cloned.ConnectStatus, cloned.OperStatus); err != nil {
765 return olterrors.NewErrAdapter("device-state-update-failed", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400766 }
767
Chaitrashree G S44124192019-08-07 20:21:36 -0400768 // Since the device was disabled before the OLT was rebooted, enforce the OLT to be Disabled after re-connection.
npujarec5762e2020-01-01 14:08:48 +0530769 _, err = dh.Client.DisableOlt(ctx, new(oop.Empty))
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400770 if err != nil {
Thomas Lee S985938d2020-05-04 11:40:41 +0530771 return olterrors.NewErrAdapter("olt-disable-failed", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400772 }
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400773 // We should still go ahead an initialize various device handler modules so that when OLT is re-enabled, we have
774 // all the modules initialized and ready to handle incoming ONUs.
775
Thomas Lee S985938d2020-05-04 11:40:41 +0530776 err = dh.initializeDeviceHandlerModules(ctx)
777 if err != nil {
778 return olterrors.NewErrAdapter("device-handler-initialization-failed", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400779 }
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400780
781 // Start reading indications
David K. Bainbridge794735f2020-02-11 21:01:37 -0800782 go func() {
Thomas Lee S985938d2020-05-04 11:40:41 +0530783 if err = dh.readIndications(ctx); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400784 _ = olterrors.NewErrAdapter("indication-read-failure", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
David K. Bainbridge794735f2020-02-11 21:01:37 -0800785 }
786 }()
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700787
788 go startHeartbeatCheck(ctx, dh)
789
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400790 return nil
791 }
792
Neha Sharma8f4e4322020-08-06 10:51:53 +0000793 ports, err := dh.coreProxy.ListDevicePorts(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id)
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400794 if err != nil {
Girish Gowdrud4245152019-05-10 00:47:31 -0400795 /*TODO: needs to handle error scenarios */
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400796 return olterrors.NewErrAdapter("fetch-ports-failed", log.Fields{"device-id": dh.device.Id}, err)
Girish Gowdrud4245152019-05-10 00:47:31 -0400797 }
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400798 dh.populateActivePorts(ctx, ports)
799 if err := dh.disableAdminDownPorts(ctx, ports); err != nil {
800 return olterrors.NewErrAdapter("port-status-update-failed", log.Fields{"ports": ports}, err)
Girish Gowdrud4245152019-05-10 00:47:31 -0400801 }
802
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400803 if err := dh.initializeDeviceHandlerModules(ctx); err != nil {
Thomas Lee S985938d2020-05-04 11:40:41 +0530804 return olterrors.NewErrAdapter("device-handler-initialization-failed", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400805 }
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530806
cuilin20187b2a8c32019-03-26 19:52:28 -0700807 // Start reading indications
David K. Bainbridge794735f2020-02-11 21:01:37 -0800808 go func() {
809 if err := dh.readIndications(ctx); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400810 _ = olterrors.NewErrAdapter("read-indications-failure", log.Fields{"device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800811 }
812 }()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000813 go dh.updateLocalDevice(ctx)
Rohan Agrawalda5e0b22020-05-20 11:10:26 +0000814
815 if device.PmConfigs != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000816 dh.UpdatePmConfig(ctx, device.PmConfigs)
Rohan Agrawalda5e0b22020-05-20 11:10:26 +0000817 }
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700818
819 go startHeartbeatCheck(ctx, dh)
820
cuilin20187b2a8c32019-03-26 19:52:28 -0700821 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530822}
823
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400824func (dh *DeviceHandler) initializeDeviceHandlerModules(ctx context.Context) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000825 deviceInfo, err := dh.populateDeviceInfo(ctx)
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400826
827 if err != nil {
828 return olterrors.NewErrAdapter("populate-device-info-failed", log.Fields{"device-id": dh.device.Id}, err)
829 }
Girish Gowdra9602eb42020-09-09 15:50:39 -0700830 dh.totalPonPorts = deviceInfo.GetPonPorts()
Gamze Abakac2c32a62021-03-11 11:44:18 +0000831 dh.agentPreviouslyConnected = deviceInfo.PreviouslyConnected
Girish Gowdra9602eb42020-09-09 15:50:39 -0700832
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400833 // Instantiate resource manager
Matteo Scandolodfa7a972020-11-06 13:03:40 -0800834 if dh.resourceMgr = rsrcMgr.NewResourceMgr(ctx, dh.device.Id, dh.openOLT.KVStoreAddress, dh.openOLT.KVStoreType, dh.device.Type, deviceInfo, dh.cm.Backend.PathPrefix); dh.resourceMgr == nil {
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400835 return olterrors.ErrResourceManagerInstantiating
836 }
837
Girish Gowdra9602eb42020-09-09 15:50:39 -0700838 dh.groupMgr = NewGroupManager(ctx, dh, dh.resourceMgr)
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400839
Girish Gowdra9602eb42020-09-09 15:50:39 -0700840 dh.flowMgr = make([]*OpenOltFlowMgr, dh.totalPonPorts)
841 for i := range dh.flowMgr {
842 // Instantiate flow manager
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700843 if dh.flowMgr[i] = NewFlowManager(ctx, dh, dh.resourceMgr, dh.groupMgr, uint32(i)); dh.flowMgr[i] == nil {
Girish Gowdra9602eb42020-09-09 15:50:39 -0700844 return olterrors.ErrResourceManagerInstantiating
845 }
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400846 }
Girish Gowdra9602eb42020-09-09 15:50:39 -0700847
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400848 /* TODO: Instantiate Alarm , stats , BW managers */
849 /* Instantiating Event Manager to handle Alarms and KPIs */
850 dh.eventMgr = NewEventMgr(dh.EventProxy, dh)
851
852 // Stats config for new device
Neha Sharma96b7bf22020-06-15 10:37:32 +0000853 dh.portStats = NewOpenOltStatsMgr(ctx, dh)
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400854
855 return nil
856
857}
858
Neha Sharma96b7bf22020-06-15 10:37:32 +0000859func (dh *DeviceHandler) populateDeviceInfo(ctx context.Context) (*oop.DeviceInfo, error) {
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400860 var err error
861 var deviceInfo *oop.DeviceInfo
862
Neha Sharma8f4e4322020-08-06 10:51:53 +0000863 deviceInfo, err = dh.Client.GetDeviceInfo(log.WithSpanFromContext(context.Background(), ctx), new(oop.Empty))
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400864
865 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000866 return nil, olterrors.NewErrPersistence("get", "device", 0, nil, err)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400867 }
868 if deviceInfo == nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000869 return nil, olterrors.NewErrInvalidValue(log.Fields{"device": nil}, nil)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400870 }
871
Neha Sharma96b7bf22020-06-15 10:37:32 +0000872 logger.Debugw(ctx, "fetched-device-info", log.Fields{"deviceInfo": deviceInfo, "device-id": dh.device.Id})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400873 dh.device.Root = true
874 dh.device.Vendor = deviceInfo.Vendor
875 dh.device.Model = deviceInfo.Model
876 dh.device.SerialNumber = deviceInfo.DeviceSerialNumber
877 dh.device.HardwareVersion = deviceInfo.HardwareVersion
878 dh.device.FirmwareVersion = deviceInfo.FirmwareVersion
879
880 if deviceInfo.DeviceId == "" {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000881 logger.Warnw(ctx, "no-device-id-provided-using-host", log.Fields{"hostport": dh.device.GetHostAndPort()})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400882 host := strings.Split(dh.device.GetHostAndPort(), ":")[0]
Neha Sharma96b7bf22020-06-15 10:37:32 +0000883 genmac, err := generateMacFromHost(ctx, host)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400884 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000885 return nil, olterrors.NewErrAdapter("failed-to-generate-mac-host", log.Fields{"host": host}, err)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400886 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000887 logger.Debugw(ctx, "using-host-for-mac-address", log.Fields{"host": host, "mac": genmac})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400888 dh.device.MacAddress = genmac
889 } else {
890 dh.device.MacAddress = deviceInfo.DeviceId
891 }
892
893 // Synchronous call to update device - this method is run in its own go routine
Neha Sharma8f4e4322020-08-06 10:51:53 +0000894 if err := dh.coreProxy.DeviceUpdate(log.WithSpanFromContext(context.TODO(), ctx), dh.device); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000895 return nil, olterrors.NewErrAdapter("device-update-failed", log.Fields{"device-id": dh.device.Id}, err)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400896 }
897
898 return deviceInfo, nil
899}
900
Neha Sharma96b7bf22020-06-15 10:37:32 +0000901func startCollector(ctx context.Context, dh *DeviceHandler) {
902 logger.Debugf(ctx, "starting-collector")
Naga Manjunath7615e552019-10-11 22:35:47 +0530903 for {
904 select {
905 case <-dh.stopCollector:
divyadesai3af43e12020-08-18 07:10:54 +0000906 logger.Debugw(ctx, "stopping-collector-for-olt", log.Fields{"device-id": dh.device.Id})
Naga Manjunath7615e552019-10-11 22:35:47 +0530907 return
Rohan Agrawalda5e0b22020-05-20 11:10:26 +0000908 case <-time.After(time.Duration(dh.metrics.ToPmConfigs().DefaultFreq) * time.Second):
Girish Gowdra34815db2020-05-11 17:18:04 -0700909
Neha Sharma8f4e4322020-08-06 10:51:53 +0000910 ports, err := dh.coreProxy.ListDevicePorts(log.WithSpanFromContext(context.Background(), ctx), dh.device.Id)
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400911 if err != nil {
912 logger.Warnw(ctx, "failed-to-list-ports", log.Fields{"device-id": dh.device.Id, "error": err})
913 continue
914 }
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530915 for _, port := range ports {
916 // NNI Stats
917 if port.Type == voltha.Port_ETHERNET_NNI {
918 intfID := PortNoToIntfID(port.PortNo, voltha.Port_ETHERNET_NNI)
919 cmnni := dh.portStats.collectNNIMetrics(intfID)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000920 logger.Debugw(ctx, "collect-nni-metrics", log.Fields{"metrics": cmnni})
Gamze Abakafcbd6e72020-12-17 13:25:16 +0000921 go dh.portStats.publishMetrics(ctx, NNIStats, cmnni, port, dh.device.Id, dh.device.Type)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000922 logger.Debugw(ctx, "publish-nni-metrics", log.Fields{"nni-port": port.Label})
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530923 }
924 // PON Stats
925 if port.Type == voltha.Port_PON_OLT {
926 intfID := PortNoToIntfID(port.PortNo, voltha.Port_PON_OLT)
927 if val, ok := dh.activePorts.Load(intfID); ok && val == true {
928 cmpon := dh.portStats.collectPONMetrics(intfID)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000929 logger.Debugw(ctx, "collect-pon-metrics", log.Fields{"metrics": cmpon})
Gamze Abakafcbd6e72020-12-17 13:25:16 +0000930 go dh.portStats.publishMetrics(ctx, PONStats, cmpon, port, dh.device.Id, dh.device.Type)
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530931 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000932 logger.Debugw(ctx, "publish-pon-metrics", log.Fields{"pon-port": port.Label})
Gamze Abakafcbd6e72020-12-17 13:25:16 +0000933
934 //ONU & Gem Stats
935 onuGemInfo := dh.flowMgr[intfID].onuGemInfo
936 if len(onuGemInfo) != 0 {
937 go dh.portStats.collectOnuAndGemStats(ctx, onuGemInfo)
938 }
Chaitrashree G Sef088112020-02-03 21:39:27 -0500939 }
Naga Manjunath7615e552019-10-11 22:35:47 +0530940 }
941 }
942 }
943}
944
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700945//AdoptDevice adopts the OLT device
npujarec5762e2020-01-01 14:08:48 +0530946func (dh *DeviceHandler) AdoptDevice(ctx context.Context, device *voltha.Device) {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400947 dh.transitionMap = NewTransitionMap(dh)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000948 logger.Infow(ctx, "adopt-device", log.Fields{"device-id": device.Id, "Address": device.GetHostAndPort()})
npujarec5762e2020-01-01 14:08:48 +0530949 dh.transitionMap.Handle(ctx, DeviceInit)
Naga Manjunath7615e552019-10-11 22:35:47 +0530950
951 // Now, set the initial PM configuration for that device
Kent Hagermane6ff1012020-07-14 15:07:53 -0400952 if err := dh.coreProxy.DevicePMConfigUpdate(ctx, dh.metrics.ToPmConfigs()); err != nil {
953 _ = olterrors.NewErrAdapter("error-updating-performance-metrics", log.Fields{"device-id": device.Id}, err).LogAt(log.ErrorLevel)
Naga Manjunath7615e552019-10-11 22:35:47 +0530954 }
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530955}
956
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700957//GetOfpDeviceInfo Gets the Ofp information of the given device
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530958func (dh *DeviceHandler) GetOfpDeviceInfo(device *voltha.Device) (*ic.SwitchCapability, error) {
cuilin20187b2a8c32019-03-26 19:52:28 -0700959 return &ic.SwitchCapability{
960 Desc: &of.OfpDesc{
Devmalya Paul70dd4972019-06-10 15:19:17 +0530961 MfrDesc: "VOLTHA Project",
cuilin20187b2a8c32019-03-26 19:52:28 -0700962 HwDesc: "open_pon",
963 SwDesc: "open_pon",
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700964 SerialNum: device.SerialNumber,
cuilin20187b2a8c32019-03-26 19:52:28 -0700965 },
966 SwitchFeatures: &of.OfpSwitchFeatures{
967 NBuffers: 256,
968 NTables: 2,
969 Capabilities: uint32(of.OfpCapabilities_OFPC_FLOW_STATS |
970 of.OfpCapabilities_OFPC_TABLE_STATS |
971 of.OfpCapabilities_OFPC_PORT_STATS |
972 of.OfpCapabilities_OFPC_GROUP_STATS),
973 },
974 }, nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530975}
976
Neha Sharma96b7bf22020-06-15 10:37:32 +0000977func (dh *DeviceHandler) omciIndication(ctx context.Context, omciInd *oop.OmciIndication) error {
978 logger.Debugw(ctx, "omci-indication", log.Fields{"intf-id": omciInd.IntfId, "onu-id": omciInd.OnuId, "device-id": dh.device.Id})
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700979 var deviceType string
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700980 var deviceID string
981 var proxyDeviceID string
cuilin20187b2a8c32019-03-26 19:52:28 -0700982
Matt Jeanneretceea2e02020-03-27 14:19:57 -0400983 transid := extractOmciTransactionID(omciInd.Pkt)
Matteo Scandolo92186242020-06-12 10:54:18 -0700984 if logger.V(log.DebugLevel) {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000985 logger.Debugw(ctx, "recv-omci-msg", log.Fields{"intf-id": omciInd.IntfId, "onu-id": omciInd.OnuId, "device-id": dh.device.Id,
Matteo Scandolo92186242020-06-12 10:54:18 -0700986 "omci-transaction-id": transid, "omci-msg": hex.EncodeToString(omciInd.Pkt)})
987 }
Matt Jeanneretceea2e02020-03-27 14:19:57 -0400988
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700989 onuKey := dh.formOnuKey(omciInd.IntfId, omciInd.OnuId)
Naga Manjunatha8dc9372019-10-31 23:01:18 +0530990
991 if onuInCache, ok := dh.onus.Load(onuKey); !ok {
992
Neha Sharma96b7bf22020-06-15 10:37:32 +0000993 logger.Debugw(ctx, "omci-indication-for-a-device-not-in-cache.", log.Fields{"intf-id": omciInd.IntfId, "onu-id": omciInd.OnuId, "device-id": dh.device.Id})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700994 ponPort := IntfIDToPortNo(omciInd.GetIntfId(), voltha.Port_PON_OLT)
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700995 kwargs := make(map[string]interface{})
996 kwargs["onu_id"] = omciInd.OnuId
997 kwargs["parent_port_no"] = ponPort
cuilin20187b2a8c32019-03-26 19:52:28 -0700998
Neha Sharma8f4e4322020-08-06 10:51:53 +0000999 onuDevice, err := dh.coreProxy.GetChildDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, kwargs)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001000 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301001 return olterrors.NewErrNotFound("onu", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001002 "intf-id": omciInd.IntfId,
1003 "onu-id": omciInd.OnuId}, err)
cuilin20187b2a8c32019-03-26 19:52:28 -07001004 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001005 deviceType = onuDevice.Type
1006 deviceID = onuDevice.Id
1007 proxyDeviceID = onuDevice.ProxyAddress.DeviceId
1008 //if not exist in cache, then add to cache.
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301009 dh.onus.Store(onuKey, NewOnuDevice(deviceID, deviceType, onuDevice.SerialNumber, omciInd.OnuId, omciInd.IntfId, proxyDeviceID, false))
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001010 } else {
1011 //found in cache
Neha Sharma96b7bf22020-06-15 10:37:32 +00001012 logger.Debugw(ctx, "omci-indication-for-a-device-in-cache.", log.Fields{"intf-id": omciInd.IntfId, "onu-id": omciInd.OnuId, "device-id": dh.device.Id})
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301013 deviceType = onuInCache.(*OnuDevice).deviceType
1014 deviceID = onuInCache.(*OnuDevice).deviceID
1015 proxyDeviceID = onuInCache.(*OnuDevice).proxyDeviceID
cuilin20187b2a8c32019-03-26 19:52:28 -07001016 }
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001017
1018 omciMsg := &ic.InterAdapterOmciMessage{Message: omciInd.Pkt}
Neha Sharma8f4e4322020-08-06 10:51:53 +00001019 if err := dh.AdapterProxy.SendInterAdapterMessage(log.WithSpanFromContext(context.Background(), ctx), omciMsg,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001020 ic.InterAdapterMessageType_OMCI_REQUEST, dh.openOLT.config.Topic, deviceType,
David K. Bainbridge794735f2020-02-11 21:01:37 -08001021 deviceID, proxyDeviceID, ""); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301022 return olterrors.NewErrCommunication("omci-request", log.Fields{
serkant.uluderya4aff1862020-09-17 23:35:26 +03001023 "source": dh.openOLT.config.Topic,
David K. Bainbridge794735f2020-02-11 21:01:37 -08001024 "destination": deviceType,
1025 "onu-id": deviceID,
Girish Kumarf26e4882020-03-05 06:49:10 +00001026 "proxy-device-id": proxyDeviceID}, err)
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001027 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001028 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +05301029}
1030
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001031//ProcessInterAdapterMessage sends the proxied messages to the target device
1032// If the proxy address is not found in the unmarshalled message, it first fetches the onu device for which the message
1033// is meant, and then send the unmarshalled omci message to this onu
Neha Sharma96b7bf22020-06-15 10:37:32 +00001034func (dh *DeviceHandler) ProcessInterAdapterMessage(ctx context.Context, msg *ic.InterAdapterMessage) error {
1035 logger.Debugw(ctx, "process-inter-adapter-message", log.Fields{"msgID": msg.Header.Id})
cuilin20187b2a8c32019-03-26 19:52:28 -07001036 if msg.Header.Type == ic.InterAdapterMessageType_OMCI_REQUEST {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001037 msgID := msg.Header.Id
cuilin20187b2a8c32019-03-26 19:52:28 -07001038 fromTopic := msg.Header.FromTopic
1039 toTopic := msg.Header.ToTopic
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001040 toDeviceID := msg.Header.ToDeviceId
1041 proxyDeviceID := msg.Header.ProxyDeviceId
cuilin20187b2a8c32019-03-26 19:52:28 -07001042
Neha Sharma96b7bf22020-06-15 10:37:32 +00001043 logger.Debugw(ctx, "omci-request-message-header", log.Fields{"msgID": msgID, "fromTopic": fromTopic, "toTopic": toTopic, "toDeviceID": toDeviceID, "proxyDeviceID": proxyDeviceID})
cuilin20187b2a8c32019-03-26 19:52:28 -07001044
1045 msgBody := msg.GetBody()
1046
1047 omciMsg := &ic.InterAdapterOmciMessage{}
1048 if err := ptypes.UnmarshalAny(msgBody, omciMsg); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001049 return olterrors.NewErrAdapter("cannot-unmarshal-omci-msg-body", log.Fields{"msgbody": msgBody}, err)
cuilin20187b2a8c32019-03-26 19:52:28 -07001050 }
1051
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001052 if omciMsg.GetProxyAddress() == nil {
Neha Sharma8f4e4322020-08-06 10:51:53 +00001053 onuDevice, err := dh.coreProxy.GetDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, toDeviceID)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001054 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301055 return olterrors.NewErrNotFound("onu", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001056 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001057 "onu-device-id": toDeviceID}, err)
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001058 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001059 logger.Debugw(ctx, "device-retrieved-from-core", log.Fields{"msgID": msgID, "fromTopic": fromTopic, "toTopic": toTopic, "toDeviceID": toDeviceID, "proxyDeviceID": proxyDeviceID})
1060 if err := dh.sendProxiedMessage(ctx, onuDevice, omciMsg); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301061 return olterrors.NewErrCommunication("send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001062 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001063 "onu-device-id": toDeviceID}, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -08001064 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001065 } else {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001066 logger.Debugw(ctx, "proxy-address-found-in-omci-message", log.Fields{"msgID": msgID, "fromTopic": fromTopic, "toTopic": toTopic, "toDeviceID": toDeviceID, "proxyDeviceID": proxyDeviceID})
1067 if err := dh.sendProxiedMessage(ctx, nil, omciMsg); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301068 return olterrors.NewErrCommunication("send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001069 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001070 "onu-device-id": toDeviceID}, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -08001071 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001072 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001073 } else {
Girish Kumarf26e4882020-03-05 06:49:10 +00001074 return olterrors.NewErrInvalidValue(log.Fields{"inter-adapter-message-type": msg.Header.Type}, nil)
cuilin20187b2a8c32019-03-26 19:52:28 -07001075 }
1076 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +05301077}
1078
Neha Sharma96b7bf22020-06-15 10:37:32 +00001079func (dh *DeviceHandler) sendProxiedMessage(ctx context.Context, onuDevice *voltha.Device, omciMsg *ic.InterAdapterOmciMessage) error {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001080 var intfID uint32
1081 var onuID uint32
Esin Karamanccb714b2019-11-29 15:02:06 +00001082 var connectStatus common.ConnectStatus_Types
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001083 if onuDevice != nil {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001084 intfID = onuDevice.ProxyAddress.GetChannelId()
1085 onuID = onuDevice.ProxyAddress.GetOnuId()
1086 connectStatus = onuDevice.ConnectStatus
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001087 } else {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001088 intfID = omciMsg.GetProxyAddress().GetChannelId()
1089 onuID = omciMsg.GetProxyAddress().GetOnuId()
1090 connectStatus = omciMsg.GetConnectStatus()
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001091 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001092 if connectStatus != voltha.ConnectStatus_REACHABLE {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001093 logger.Debugw(ctx, "onu-not-reachable--cannot-send-omci", log.Fields{"intf-id": intfID, "onu-id": onuID})
David K. Bainbridge794735f2020-02-11 21:01:37 -08001094
Thomas Lee S94109f12020-03-03 16:39:29 +05301095 return olterrors.NewErrCommunication("unreachable", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001096 "intf-id": intfID,
1097 "onu-id": onuID}, nil)
cuilin20187b2a8c32019-03-26 19:52:28 -07001098 }
1099
Matt Jeanneretceea2e02020-03-27 14:19:57 -04001100 // TODO: OpenOLT Agent oop.OmciMsg expects a hex encoded string for OMCI packets rather than the actual bytes.
1101 // Fix this in the agent and then we can pass byte array as Pkt: omciMsg.Message.
lcuie24ef182019-04-29 22:58:36 -07001102 var omciMessage *oop.OmciMsg
Matt Jeanneretceea2e02020-03-27 14:19:57 -04001103 hexPkt := make([]byte, hex.EncodedLen(len(omciMsg.Message)))
1104 hex.Encode(hexPkt, omciMsg.Message)
1105 omciMessage = &oop.OmciMsg{IntfId: intfID, OnuId: onuID, Pkt: hexPkt}
1106
1107 // TODO: Below logging illustrates the "stringify" of the omci Pkt.
1108 // once above is fixed this log line can change to just use hex.EncodeToString(omciMessage.Pkt)
1109 transid := extractOmciTransactionID(omciMsg.Message)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001110 logger.Debugw(ctx, "sent-omci-msg", log.Fields{"intf-id": intfID, "onu-id": onuID,
Matt Jeanneretceea2e02020-03-27 14:19:57 -04001111 "omciTransactionID": transid, "omciMsg": string(omciMessage.Pkt)})
cuilin20187b2a8c32019-03-26 19:52:28 -07001112
Neha Sharma8f4e4322020-08-06 10:51:53 +00001113 _, err := dh.Client.OmciMsgOut(log.WithSpanFromContext(context.Background(), ctx), omciMessage)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001114 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301115 return olterrors.NewErrCommunication("omci-send-failed", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001116 "intf-id": intfID,
1117 "onu-id": onuID,
1118 "message": omciMessage}, err)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001119 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001120 return nil
cuilin20187b2a8c32019-03-26 19:52:28 -07001121}
1122
David K. Bainbridge794735f2020-02-11 21:01:37 -08001123func (dh *DeviceHandler) activateONU(ctx context.Context, intfID uint32, onuID int64, serialNum *oop.SerialNumber, serialNumber string) error {
kesavand494c2082020-08-31 11:16:12 +05301124 logger.Debugw(ctx, "activate-onu", log.Fields{"intf-id": intfID, "onu-id": onuID, "serialNum": serialNum, "serialNumber": serialNumber, "device-id": dh.device.Id, "OmccEncryption": dh.openOLT.config.OmccEncryption})
Girish Gowdra9602eb42020-09-09 15:50:39 -07001125 if err := dh.flowMgr[intfID].UpdateOnuInfo(ctx, intfID, uint32(onuID), serialNumber); err != nil {
Matteo Scandolo92186242020-06-12 10:54:18 -07001126 return olterrors.NewErrAdapter("onu-activate-failed", log.Fields{"onu": onuID, "intf-id": intfID}, err)
Andrea Campanellab83b39d2020-03-30 11:41:16 +02001127 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001128 // TODO: need resource manager
1129 var pir uint32 = 1000000
kesavand494c2082020-08-31 11:16:12 +05301130 Onu := oop.Onu{IntfId: intfID, OnuId: uint32(onuID), SerialNumber: serialNum, Pir: pir, OmccEncryption: dh.openOLT.config.OmccEncryption}
npujarec5762e2020-01-01 14:08:48 +05301131 if _, err := dh.Client.ActivateOnu(ctx, &Onu); err != nil {
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001132 st, _ := status.FromError(err)
1133 if st.Code() == codes.AlreadyExists {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001134 logger.Debugw(ctx, "onu-activation-in-progress", log.Fields{"SerialNumber": serialNumber, "onu-id": onuID, "device-id": dh.device.Id})
1135
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001136 } else {
Thomas Lee S985938d2020-05-04 11:40:41 +05301137 return olterrors.NewErrAdapter("onu-activate-failed", log.Fields{"onu": Onu, "device-id": dh.device.Id}, err)
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001138 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001139 } else {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001140 logger.Infow(ctx, "activated-onu", log.Fields{"SerialNumber": serialNumber, "device-id": dh.device.Id})
cuilin20187b2a8c32019-03-26 19:52:28 -07001141 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001142 return nil
cuilin20187b2a8c32019-03-26 19:52:28 -07001143}
1144
Mahir Gunyelb0046752021-02-26 13:51:05 -08001145func (dh *DeviceHandler) onuDiscIndication(ctx context.Context, onuDiscInd *oop.OnuDiscIndication) error {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001146 channelID := onuDiscInd.GetIntfId()
1147 parentPortNo := IntfIDToPortNo(onuDiscInd.GetIntfId(), voltha.Port_PON_OLT)
Matt Jeanneret53539512019-07-20 14:47:02 -04001148
Mahir Gunyelb0046752021-02-26 13:51:05 -08001149 sn := dh.stringifySerialNumber(onuDiscInd.SerialNumber)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001150 logger.Infow(ctx, "new-discovery-indication", log.Fields{"sn": sn})
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301151
cuilin20187b2a8c32019-03-26 19:52:28 -07001152 kwargs := make(map[string]interface{})
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001153 if sn != "" {
1154 kwargs["serial_number"] = sn
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001155 } else {
Girish Kumarf26e4882020-03-05 06:49:10 +00001156 return olterrors.NewErrInvalidValue(log.Fields{"serial-number": sn}, nil)
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001157 }
1158
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301159 var alarmInd oop.OnuAlarmIndication
Girish Gowdrac1b9d5e2021-04-22 12:47:44 -07001160 raisedTs := time.Now().Unix()
Amit Ghoshe5c6a852020-02-10 15:09:46 +00001161 if _, loaded := dh.discOnus.LoadOrStore(sn, true); loaded {
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301162
1163 /* When PON cable disconnected and connected back from OLT, it was expected OnuAlarmIndication
1164 with "los_status: off" should be raised but BAL does not raise this Alarm hence manually sending
1165 OnuLosClear event on receiving OnuDiscoveryIndication for the Onu after checking whether
1166 OnuLosRaise event sent for it */
1167 dh.onus.Range(func(Onukey interface{}, onuInCache interface{}) bool {
1168 if onuInCache.(*OnuDevice).serialNumber == sn && onuInCache.(*OnuDevice).losRaised {
1169 if onuDiscInd.GetIntfId() != onuInCache.(*OnuDevice).intfID {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001170 logger.Warnw(ctx, "onu-is-on-a-different-intf-id-now", log.Fields{
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301171 "previousIntfId": onuInCache.(*OnuDevice).intfID,
1172 "currentIntfId": onuDiscInd.GetIntfId()})
1173 // TODO:: Should we need to ignore raising OnuLosClear event
1174 // when onu connected to different PON?
1175 }
1176 alarmInd.IntfId = onuInCache.(*OnuDevice).intfID
1177 alarmInd.OnuId = onuInCache.(*OnuDevice).onuID
1178 alarmInd.LosStatus = statusCheckOff
Kent Hagermane6ff1012020-07-14 15:07:53 -04001179 go func() {
1180 if err := dh.eventMgr.onuAlarmIndication(ctx, &alarmInd, onuInCache.(*OnuDevice).deviceID, raisedTs); err != nil {
1181 logger.Debugw(ctx, "indication-failed", log.Fields{"error": err})
1182 }
1183 }()
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301184 }
1185 return true
1186 })
1187
Neha Sharma96b7bf22020-06-15 10:37:32 +00001188 logger.Warnw(ctx, "onu-sn-is-already-being-processed", log.Fields{"sn": sn})
David K. Bainbridge794735f2020-02-11 21:01:37 -08001189 return nil
Amit Ghoshe5c6a852020-02-10 15:09:46 +00001190 }
1191
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001192 var onuID uint32
Matteo Scandolo945e4012019-12-12 14:16:11 -08001193
1194 // check the ONU is already know to the OLT
1195 // NOTE the second time the ONU is discovered this should return a device
1196 onuDevice, err := dh.coreProxy.GetChildDevice(ctx, dh.device.Id, kwargs)
1197
1198 if err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001199 logger.Debugw(ctx, "core-proxy-get-child-device-failed", log.Fields{"parentDevice": dh.device.Id, "err": err, "sn": sn})
Matteo Scandolo945e4012019-12-12 14:16:11 -08001200 if e, ok := status.FromError(err); ok {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001201 logger.Debugw(ctx, "core-proxy-get-child-device-failed-with-code", log.Fields{"errCode": e.Code(), "sn": sn})
Matteo Scandolo945e4012019-12-12 14:16:11 -08001202 switch e.Code() {
1203 case codes.Internal:
1204 // this probably means NOT FOUND, so just create a new device
1205 onuDevice = nil
1206 case codes.DeadlineExceeded:
1207 // if the call times out, cleanup and exit
1208 dh.discOnus.Delete(sn)
Girish Kumarf26e4882020-03-05 06:49:10 +00001209 return olterrors.NewErrTimeout("get-child-device", log.Fields{"device-id": dh.device.Id}, err)
Matteo Scandolo945e4012019-12-12 14:16:11 -08001210 }
1211 }
1212 }
1213
1214 if onuDevice == nil {
1215 // NOTE this should happen a single time, and only if GetChildDevice returns NotFound
Neha Sharma96b7bf22020-06-15 10:37:32 +00001216 logger.Debugw(ctx, "creating-new-onu", log.Fields{"sn": sn})
Matteo Scandolo945e4012019-12-12 14:16:11 -08001217 // we need to create a new ChildDevice
Matt Jeanneret53539512019-07-20 14:47:02 -04001218 ponintfid := onuDiscInd.GetIntfId()
npujarec5762e2020-01-01 14:08:48 +05301219 onuID, err = dh.resourceMgr.GetONUID(ctx, ponintfid)
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001220
Neha Sharma96b7bf22020-06-15 10:37:32 +00001221 logger.Infow(ctx, "creating-new-onu-got-onu-id", log.Fields{"sn": sn, "onuId": onuID})
Matteo Scandolo945e4012019-12-12 14:16:11 -08001222
1223 if err != nil {
1224 // if we can't create an ID in resource manager,
1225 // cleanup and exit
Matteo Scandolo945e4012019-12-12 14:16:11 -08001226 dh.discOnus.Delete(sn)
Girish Kumarf26e4882020-03-05 06:49:10 +00001227 return olterrors.NewErrAdapter("resource-manager-get-onu-id-failed", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001228 "pon-intf-id": ponintfid,
1229 "serial-number": sn}, err)
Matteo Scandolo945e4012019-12-12 14:16:11 -08001230 }
1231
Neha Sharma8f4e4322020-08-06 10:51:53 +00001232 if onuDevice, err = dh.coreProxy.ChildDeviceDetected(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, int(parentPortNo),
Matteo Scandolo945e4012019-12-12 14:16:11 -08001233 "", int(channelID), string(onuDiscInd.SerialNumber.GetVendorId()), sn, int64(onuID)); err != nil {
Matteo Scandolo945e4012019-12-12 14:16:11 -08001234 dh.discOnus.Delete(sn)
1235 dh.resourceMgr.FreeonuID(ctx, ponintfid, []uint32{onuID}) // NOTE I'm not sure this method is actually cleaning up the right thing
Thomas Lee S94109f12020-03-03 16:39:29 +05301236 return olterrors.NewErrAdapter("core-proxy-child-device-detected-failed", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001237 "pon-intf-id": ponintfid,
1238 "serial-number": sn}, err)
Matteo Scandolo945e4012019-12-12 14:16:11 -08001239 }
Girish Gowdrac1b9d5e2021-04-22 12:47:44 -07001240 if err := dh.eventMgr.OnuDiscoveryIndication(ctx, onuDiscInd, dh.device.Id, onuDevice.Id, onuID, sn, time.Now().Unix()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -04001241 logger.Warnw(ctx, "discovery-indication-failed", log.Fields{"error": err})
1242 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001243 logger.Infow(ctx, "onu-child-device-added",
Shrey Baid807a2a02020-04-09 12:52:45 +05301244 log.Fields{"onuDevice": onuDevice,
1245 "sn": sn,
Matteo Scandolo92186242020-06-12 10:54:18 -07001246 "onu-id": onuID,
Thomas Lee S985938d2020-05-04 11:40:41 +05301247 "device-id": dh.device.Id})
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001248 }
Matteo Scandolo945e4012019-12-12 14:16:11 -08001249
1250 // we can now use the existing ONU Id
1251 onuID = onuDevice.ProxyAddress.OnuId
Mahir Gunyele77977b2019-06-27 05:36:22 -07001252 //Insert the ONU into cache to use in OnuIndication.
1253 //TODO: Do we need to remove this from the cache on ONU change, or wait for overwritten on next discovery.
Neha Sharma96b7bf22020-06-15 10:37:32 +00001254 logger.Debugw(ctx, "onu-discovery-indication-key-create",
Matteo Scandolo92186242020-06-12 10:54:18 -07001255 log.Fields{"onu-id": onuID,
Shrey Baid807a2a02020-04-09 12:52:45 +05301256 "intfId": onuDiscInd.GetIntfId(),
1257 "sn": sn})
Mahir Gunyele77977b2019-06-27 05:36:22 -07001258 onuKey := dh.formOnuKey(onuDiscInd.GetIntfId(), onuID)
Matt Jeanneret53539512019-07-20 14:47:02 -04001259
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301260 onuDev := NewOnuDevice(onuDevice.Id, onuDevice.Type, onuDevice.SerialNumber, onuID, onuDiscInd.GetIntfId(), onuDevice.ProxyAddress.DeviceId, false)
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301261 dh.onus.Store(onuKey, onuDev)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001262 logger.Debugw(ctx, "new-onu-device-discovered",
Shrey Baid807a2a02020-04-09 12:52:45 +05301263 log.Fields{"onu": onuDev,
1264 "sn": sn})
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001265
Kent Hagermane6ff1012020-07-14 15:07:53 -04001266 if err := dh.coreProxy.DeviceStateUpdate(ctx, onuDevice.Id, common.ConnectStatus_REACHABLE, common.OperStatus_DISCOVERED); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301267 return olterrors.NewErrAdapter("failed-to-update-device-state", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001268 "device-id": onuDevice.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001269 "serial-number": sn}, err)
cuilin20187b2a8c32019-03-26 19:52:28 -07001270 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001271 logger.Infow(ctx, "onu-discovered-reachable", log.Fields{"device-id": onuDevice.Id, "sn": sn})
Kent Hagermane6ff1012020-07-14 15:07:53 -04001272 if err := dh.activateONU(ctx, onuDiscInd.IntfId, int64(onuID), onuDiscInd.SerialNumber, sn); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301273 return olterrors.NewErrAdapter("onu-activation-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001274 "device-id": onuDevice.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001275 "serial-number": sn}, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -08001276 }
1277 return nil
cuilin20187b2a8c32019-03-26 19:52:28 -07001278}
1279
Mahir Gunyelb0046752021-02-26 13:51:05 -08001280func (dh *DeviceHandler) onuIndication(ctx context.Context, onuInd *oop.OnuIndication) error {
cuilin20187b2a8c32019-03-26 19:52:28 -07001281
1282 kwargs := make(map[string]interface{})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001283 ponPort := IntfIDToPortNo(onuInd.GetIntfId(), voltha.Port_PON_OLT)
Mahir Gunyele77977b2019-06-27 05:36:22 -07001284 var onuDevice *voltha.Device
David K. Bainbridge794735f2020-02-11 21:01:37 -08001285 var err error
Mahir Gunyele77977b2019-06-27 05:36:22 -07001286 foundInCache := false
Neha Sharma96b7bf22020-06-15 10:37:32 +00001287 logger.Debugw(ctx, "onu-indication-key-create",
Shrey Baid807a2a02020-04-09 12:52:45 +05301288 log.Fields{"onuId": onuInd.OnuId,
1289 "intfId": onuInd.GetIntfId(),
Thomas Lee S985938d2020-05-04 11:40:41 +05301290 "device-id": dh.device.Id})
Mahir Gunyele77977b2019-06-27 05:36:22 -07001291 onuKey := dh.formOnuKey(onuInd.GetIntfId(), onuInd.OnuId)
Mahir Gunyelb0046752021-02-26 13:51:05 -08001292 serialNumber := dh.stringifySerialNumber(onuInd.SerialNumber)
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301293
David K. Bainbridge794735f2020-02-11 21:01:37 -08001294 errFields := log.Fields{"device-id": dh.device.Id}
1295
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301296 if onuInCache, ok := dh.onus.Load(onuKey); ok {
1297
Mahir Gunyele77977b2019-06-27 05:36:22 -07001298 //If ONU id is discovered before then use GetDevice to get onuDevice because it is cheaper.
1299 foundInCache = true
David K. Bainbridge794735f2020-02-11 21:01:37 -08001300 errFields["onu-id"] = onuInCache.(*OnuDevice).deviceID
Kent Hagermane6ff1012020-07-14 15:07:53 -04001301 onuDevice, err = dh.coreProxy.GetDevice(ctx, dh.device.Id, onuInCache.(*OnuDevice).deviceID)
cuilin20187b2a8c32019-03-26 19:52:28 -07001302 } else {
Mahir Gunyele77977b2019-06-27 05:36:22 -07001303 //If ONU not found in adapter cache then we have to use GetChildDevice to get onuDevice
1304 if serialNumber != "" {
1305 kwargs["serial_number"] = serialNumber
David K. Bainbridge794735f2020-02-11 21:01:37 -08001306 errFields["serial-number"] = serialNumber
Mahir Gunyele77977b2019-06-27 05:36:22 -07001307 } else {
1308 kwargs["onu_id"] = onuInd.OnuId
1309 kwargs["parent_port_no"] = ponPort
David K. Bainbridge794735f2020-02-11 21:01:37 -08001310 errFields["onu-id"] = onuInd.OnuId
1311 errFields["parent-port-no"] = ponPort
Mahir Gunyele77977b2019-06-27 05:36:22 -07001312 }
Neha Sharma8f4e4322020-08-06 10:51:53 +00001313 onuDevice, err = dh.coreProxy.GetChildDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, kwargs)
cuilin20187b2a8c32019-03-26 19:52:28 -07001314 }
Mahir Gunyele77977b2019-06-27 05:36:22 -07001315
David K. Bainbridge794735f2020-02-11 21:01:37 -08001316 if err != nil || onuDevice == nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001317 return olterrors.NewErrNotFound("onu-device", errFields, err)
cuilin20187b2a8c32019-03-26 19:52:28 -07001318 }
1319
David K. Bainbridge794735f2020-02-11 21:01:37 -08001320 if onuDevice.ParentPortNo != ponPort {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001321 logger.Warnw(ctx, "onu-is-on-a-different-intf-id-now", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001322 "previousIntfId": onuDevice.ParentPortNo,
1323 "currentIntfId": ponPort})
1324 }
1325
1326 if onuDevice.ProxyAddress.OnuId != onuInd.OnuId {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001327 logger.Warnw(ctx, "onu-id-mismatch-possible-if-voltha-and-olt-rebooted", log.Fields{
Shrey Baid807a2a02020-04-09 12:52:45 +05301328 "expected-onu-id": onuDevice.ProxyAddress.OnuId,
1329 "received-onu-id": onuInd.OnuId,
Thomas Lee S985938d2020-05-04 11:40:41 +05301330 "device-id": dh.device.Id})
David K. Bainbridge794735f2020-02-11 21:01:37 -08001331 }
1332 if !foundInCache {
1333 onuKey := dh.formOnuKey(onuInd.GetIntfId(), onuInd.GetOnuId())
1334
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301335 dh.onus.Store(onuKey, NewOnuDevice(onuDevice.Id, onuDevice.Type, onuDevice.SerialNumber, onuInd.GetOnuId(), onuInd.GetIntfId(), onuDevice.ProxyAddress.DeviceId, false))
David K. Bainbridge794735f2020-02-11 21:01:37 -08001336
1337 }
kesavand7cf3a052020-08-28 12:49:18 +05301338 if onuInd.OperState == "down" && onuInd.FailReason != oop.OnuIndication_ONU_ACTIVATION_FAIL_REASON_NONE {
Girish Gowdrac1b9d5e2021-04-22 12:47:44 -07001339 if err := dh.eventMgr.onuActivationIndication(ctx, onuActivationFailEvent, onuInd, dh.device.Id, time.Now().Unix()); err != nil {
kesavand7cf3a052020-08-28 12:49:18 +05301340 logger.Warnw(ctx, "onu-activation-indication-reporting-failed", log.Fields{"error": err})
1341 }
1342 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001343 if err := dh.updateOnuStates(ctx, onuDevice, onuInd); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001344 return olterrors.NewErrCommunication("state-update-failed", errFields, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -08001345 }
1346 return nil
cuilin20187b2a8c32019-03-26 19:52:28 -07001347}
1348
Neha Sharma96b7bf22020-06-15 10:37:32 +00001349func (dh *DeviceHandler) updateOnuStates(ctx context.Context, onuDevice *voltha.Device, onuInd *oop.OnuIndication) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001350 logger.Debugw(ctx, "onu-indication-for-state", log.Fields{"onuIndication": onuInd, "device-id": onuDevice.Id, "operStatus": onuDevice.OperStatus, "adminStatus": onuDevice.AdminState})
Girish Gowdra748de5c2020-07-01 10:27:52 -07001351 if onuInd.AdminState == "down" || onuInd.OperState == "down" {
1352 // The ONU has gone admin_state "down" or oper_state "down" - we expect the ONU to send discovery again
1353 // The ONU admin_state is "up" while "oper_state" is down in cases where ONU activation fails. In this case
1354 // the ONU sends Discovery again.
Girish Gowdra429f9502020-05-04 13:22:16 -07001355 dh.discOnus.Delete(onuDevice.SerialNumber)
Amit Ghosh9bbc5652020-02-17 13:37:32 +00001356 // Tests have shown that we sometimes get OperState as NOT down even if AdminState is down, forcing it
1357 if onuInd.OperState != "down" {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001358 logger.Warnw(ctx, "onu-admin-state-down", log.Fields{"operState": onuInd.OperState})
Amit Ghosh9bbc5652020-02-17 13:37:32 +00001359 onuInd.OperState = "down"
1360 }
1361 }
1362
David K. Bainbridge794735f2020-02-11 21:01:37 -08001363 switch onuInd.OperState {
1364 case "down":
Neha Sharma96b7bf22020-06-15 10:37:32 +00001365 logger.Debugw(ctx, "sending-interadapter-onu-indication", log.Fields{"onuIndication": onuInd, "device-id": onuDevice.Id, "operStatus": onuDevice.OperStatus, "adminStatus": onuDevice.AdminState})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001366 // TODO NEW CORE do not hardcode adapter name. Handler needs Adapter reference
npujarec5762e2020-01-01 14:08:48 +05301367 err := dh.AdapterProxy.SendInterAdapterMessage(ctx, onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001368 dh.openOLT.config.Topic, onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001369 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301370 return olterrors.NewErrCommunication("inter-adapter-send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001371 "onu-indicator": onuInd,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001372 "source": dh.openOLT.config.Topic,
David K. Bainbridge794735f2020-02-11 21:01:37 -08001373 "device-type": onuDevice.Type,
Girish Kumarf26e4882020-03-05 06:49:10 +00001374 "device-id": onuDevice.Id}, err)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001375 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001376 case "up":
Neha Sharma96b7bf22020-06-15 10:37:32 +00001377 logger.Debugw(ctx, "sending-interadapter-onu-indication", log.Fields{"onuIndication": onuInd, "device-id": onuDevice.Id, "operStatus": onuDevice.OperStatus, "adminStatus": onuDevice.AdminState})
Matt Jeanneret53539512019-07-20 14:47:02 -04001378 // TODO NEW CORE do not hardcode adapter name. Handler needs Adapter reference
npujarec5762e2020-01-01 14:08:48 +05301379 err := dh.AdapterProxy.SendInterAdapterMessage(ctx, onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001380 dh.openOLT.config.Topic, onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001381 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301382 return olterrors.NewErrCommunication("inter-adapter-send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001383 "onu-indicator": onuInd,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001384 "source": dh.openOLT.config.Topic,
David K. Bainbridge794735f2020-02-11 21:01:37 -08001385 "device-type": onuDevice.Type,
Girish Kumarf26e4882020-03-05 06:49:10 +00001386 "device-id": onuDevice.Id}, err)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001387 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001388 default:
Girish Kumarf26e4882020-03-05 06:49:10 +00001389 return olterrors.NewErrInvalidValue(log.Fields{"oper-state": onuInd.OperState}, nil)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001390 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001391 return nil
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001392}
1393
cuilin20187b2a8c32019-03-26 19:52:28 -07001394func (dh *DeviceHandler) stringifySerialNumber(serialNum *oop.SerialNumber) string {
1395 if serialNum != nil {
1396 return string(serialNum.VendorId) + dh.stringifyVendorSpecific(serialNum.VendorSpecific)
cuilin20187b2a8c32019-03-26 19:52:28 -07001397 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001398 return ""
cuilin20187b2a8c32019-03-26 19:52:28 -07001399}
Chaitrashree G S1a55b882020-02-04 17:35:35 -05001400func (dh *DeviceHandler) deStringifySerialNumber(serialNum string) (*oop.SerialNumber, error) {
1401 decodedStr, err := hex.DecodeString(serialNum[4:])
1402 if err != nil {
1403 return nil, err
1404 }
1405 return &oop.SerialNumber{
1406 VendorId: []byte(serialNum[:4]),
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001407 VendorSpecific: decodedStr,
Chaitrashree G S1a55b882020-02-04 17:35:35 -05001408 }, nil
1409}
cuilin20187b2a8c32019-03-26 19:52:28 -07001410
1411func (dh *DeviceHandler) stringifyVendorSpecific(vendorSpecific []byte) string {
Mahir Gunyelb0046752021-02-26 13:51:05 -08001412 if len(vendorSpecific) > 3 {
1413 tmp := fmt.Sprintf("%x", (uint32(vendorSpecific[0])>>4)&0x0f) +
1414 fmt.Sprintf("%x", uint32(vendorSpecific[0]&0x0f)) +
1415 fmt.Sprintf("%x", (uint32(vendorSpecific[1])>>4)&0x0f) +
1416 fmt.Sprintf("%x", (uint32(vendorSpecific[1]))&0x0f) +
1417 fmt.Sprintf("%x", (uint32(vendorSpecific[2])>>4)&0x0f) +
1418 fmt.Sprintf("%x", (uint32(vendorSpecific[2]))&0x0f) +
1419 fmt.Sprintf("%x", (uint32(vendorSpecific[3])>>4)&0x0f) +
1420 fmt.Sprintf("%x", (uint32(vendorSpecific[3]))&0x0f)
1421 return tmp
1422 }
1423 return ""
cuilin20187b2a8c32019-03-26 19:52:28 -07001424}
1425
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001426//UpdateFlowsBulk upates the bulk flow
1427func (dh *DeviceHandler) UpdateFlowsBulk() error {
Thomas Lee S94109f12020-03-03 16:39:29 +05301428 return olterrors.ErrNotImplemented
cuilin20187b2a8c32019-03-26 19:52:28 -07001429}
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001430
1431//GetChildDevice returns the child device for given parent port and onu id
Neha Sharma96b7bf22020-06-15 10:37:32 +00001432func (dh *DeviceHandler) GetChildDevice(ctx context.Context, parentPort, onuID uint32) (*voltha.Device, error) {
1433 logger.Debugw(ctx, "getchilddevice",
Shrey Baid807a2a02020-04-09 12:52:45 +05301434 log.Fields{"pon-port": parentPort,
Matteo Scandolo92186242020-06-12 10:54:18 -07001435 "onu-id": onuID,
Thomas Lee S985938d2020-05-04 11:40:41 +05301436 "device-id": dh.device.Id})
Girish Gowdru0c588b22019-04-23 23:24:56 -04001437 kwargs := make(map[string]interface{})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001438 kwargs["onu_id"] = onuID
Girish Gowdru0c588b22019-04-23 23:24:56 -04001439 kwargs["parent_port_no"] = parentPort
Neha Sharma8f4e4322020-08-06 10:51:53 +00001440 onuDevice, err := dh.coreProxy.GetChildDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, kwargs)
Girish Gowdru0c588b22019-04-23 23:24:56 -04001441 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001442 return nil, olterrors.NewErrNotFound("onu-device", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001443 "intf-id": parentPort,
1444 "onu-id": onuID}, err)
Girish Gowdru0c588b22019-04-23 23:24:56 -04001445 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001446 logger.Debugw(ctx, "successfully-received-child-device-from-core", log.Fields{"child-device-id": onuDevice.Id, "child-device-sn": onuDevice.SerialNumber})
David K. Bainbridge794735f2020-02-11 21:01:37 -08001447 return onuDevice, nil
manikkaraj kbf256be2019-03-25 00:13:48 +05301448}
1449
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001450// SendPacketInToCore sends packet-in to core
1451// For this, it calls SendPacketIn of the core-proxy which uses a device specific topic to send the request.
1452// The adapter handling the device creates a device specific topic
Neha Sharma96b7bf22020-06-15 10:37:32 +00001453func (dh *DeviceHandler) SendPacketInToCore(ctx context.Context, logicalPort uint32, packetPayload []byte) error {
Matteo Scandolo92186242020-06-12 10:54:18 -07001454 if logger.V(log.DebugLevel) {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001455 logger.Debugw(ctx, "send-packet-in-to-core", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001456 "port": logicalPort,
1457 "packet": hex.EncodeToString(packetPayload),
1458 "device-id": dh.device.Id,
1459 })
1460 }
Neha Sharma8f4e4322020-08-06 10:51:53 +00001461 if err := dh.coreProxy.SendPacketIn(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, logicalPort, packetPayload); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301462 return olterrors.NewErrCommunication("packet-send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001463 "source": "adapter",
1464 "destination": "core",
1465 "device-id": dh.device.Id,
1466 "logical-port": logicalPort,
Girish Kumarf26e4882020-03-05 06:49:10 +00001467 "packet": hex.EncodeToString(packetPayload)}, err)
manikkaraj k9eb6cac2019-05-09 12:32:03 -04001468 }
Matteo Scandolo92186242020-06-12 10:54:18 -07001469 if logger.V(log.DebugLevel) {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001470 logger.Debugw(ctx, "sent-packet-in-to-core-successfully", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001471 "packet": hex.EncodeToString(packetPayload),
1472 "device-id": dh.device.Id,
1473 })
1474 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001475 return nil
manikkaraj k9eb6cac2019-05-09 12:32:03 -04001476}
1477
Rohan Agrawalda5e0b22020-05-20 11:10:26 +00001478// UpdatePmConfig updates the pm metrics.
Neha Sharma96b7bf22020-06-15 10:37:32 +00001479func (dh *DeviceHandler) UpdatePmConfig(ctx context.Context, pmConfigs *voltha.PmConfigs) {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001480 logger.Infow(ctx, "update-pm-configs", log.Fields{"device-id": dh.device.Id, "pm-configs": pmConfigs})
Rohan Agrawalda5e0b22020-05-20 11:10:26 +00001481
1482 if pmConfigs.DefaultFreq != dh.metrics.ToPmConfigs().DefaultFreq {
1483 dh.metrics.UpdateFrequency(pmConfigs.DefaultFreq)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001484 logger.Debugf(ctx, "frequency-updated")
Rohan Agrawalda5e0b22020-05-20 11:10:26 +00001485 }
1486
Kent Hagermane6ff1012020-07-14 15:07:53 -04001487 if !pmConfigs.Grouped {
Rohan Agrawalda5e0b22020-05-20 11:10:26 +00001488 metrics := dh.metrics.GetSubscriberMetrics()
1489 for _, m := range pmConfigs.Metrics {
1490 metrics[m.Name].Enabled = m.Enabled
1491
1492 }
1493 }
1494}
1495
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001496//UpdateFlowsIncrementally updates the device flow
npujarec5762e2020-01-01 14:08:48 +05301497func (dh *DeviceHandler) UpdateFlowsIncrementally(ctx context.Context, device *voltha.Device, flows *of.FlowChanges, groups *of.FlowGroupChanges, flowMetadata *voltha.FlowMetadata) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001498 logger.Debugw(ctx, "received-incremental-flowupdate-in-device-handler", log.Fields{"device-id": device.Id, "flows": flows, "groups": groups, "flowMetadata": flowMetadata})
Andrea Campanellac63bba92020-03-10 17:01:04 +01001499
Girish Gowdra491a9c62021-01-06 16:43:07 -08001500 var err error
Andrea Campanellac63bba92020-03-10 17:01:04 +01001501 var errorsList []error
1502
Girish Gowdru0c588b22019-04-23 23:24:56 -04001503 if flows != nil {
Manjunath Vanarajulu28c3e822019-05-16 11:14:28 -04001504 for _, flow := range flows.ToRemove.Items {
Girish Gowdrafb3d6102020-10-16 16:32:36 -07001505 ponIf := dh.getPonIfFromFlow(flow)
Girish Gowdracefae192020-03-19 18:14:10 -07001506
Neha Sharma96b7bf22020-06-15 10:37:32 +00001507 logger.Debugw(ctx, "removing-flow",
Shrey Baid807a2a02020-04-09 12:52:45 +05301508 log.Fields{"device-id": device.Id,
Girish Gowdra9602eb42020-09-09 15:50:39 -07001509 "ponIf": ponIf,
Shrey Baid807a2a02020-04-09 12:52:45 +05301510 "flowToRemove": flow})
Girish Gowdra491a9c62021-01-06 16:43:07 -08001511 if flow_utils.HasGroup(flow) {
1512 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, flow, nil, McastFlowOrGroupRemove)
1513 } else {
1514 err = dh.flowMgr[ponIf].RouteFlowToOnuChannel(ctx, flow, false, nil)
1515 }
Girish Gowdracefae192020-03-19 18:14:10 -07001516 if err != nil {
1517 errorsList = append(errorsList, err)
1518 }
Manjunath Vanarajulu28c3e822019-05-16 11:14:28 -04001519 }
Girish Gowdra3d633032019-12-10 16:37:05 +05301520
1521 for _, flow := range flows.ToAdd.Items {
Girish Gowdrafb3d6102020-10-16 16:32:36 -07001522 ponIf := dh.getPonIfFromFlow(flow)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001523 logger.Debugw(ctx, "adding-flow",
Shrey Baid807a2a02020-04-09 12:52:45 +05301524 log.Fields{"device-id": device.Id,
Girish Gowdra9602eb42020-09-09 15:50:39 -07001525 "ponIf": ponIf,
Shrey Baid807a2a02020-04-09 12:52:45 +05301526 "flowToAdd": flow})
Girish Gowdra491a9c62021-01-06 16:43:07 -08001527 if flow_utils.HasGroup(flow) {
1528 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, flow, nil, McastFlowOrGroupAdd)
1529 } else {
1530 err = dh.flowMgr[ponIf].RouteFlowToOnuChannel(ctx, flow, true, flowMetadata)
1531 }
Andrea Campanellac63bba92020-03-10 17:01:04 +01001532 if err != nil {
1533 errorsList = append(errorsList, err)
1534 }
Girish Gowdra3d633032019-12-10 16:37:05 +05301535 }
Girish Gowdru0c588b22019-04-23 23:24:56 -04001536 }
Esin Karamanccb714b2019-11-29 15:02:06 +00001537
Girish Gowdracefae192020-03-19 18:14:10 -07001538 // Whether we need to synchronize multicast group adds and modifies like flow add and delete needs to be investigated
Esin Karamanccb714b2019-11-29 15:02:06 +00001539 if groups != nil {
1540 for _, group := range groups.ToAdd.Items {
Girish Gowdra491a9c62021-01-06 16:43:07 -08001541 // err = dh.groupMgr.AddGroup(ctx, group)
1542 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, nil, group, McastFlowOrGroupAdd)
Andrea Campanellac63bba92020-03-10 17:01:04 +01001543 if err != nil {
1544 errorsList = append(errorsList, err)
1545 }
Esin Karamanccb714b2019-11-29 15:02:06 +00001546 }
1547 for _, group := range groups.ToUpdate.Items {
Girish Gowdra491a9c62021-01-06 16:43:07 -08001548 // err = dh.groupMgr.ModifyGroup(ctx, group)
1549 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, nil, group, McastFlowOrGroupModify)
Andrea Campanellac63bba92020-03-10 17:01:04 +01001550 if err != nil {
1551 errorsList = append(errorsList, err)
1552 }
Esin Karamanccb714b2019-11-29 15:02:06 +00001553 }
Esin Karamand519bbf2020-07-01 11:16:03 +00001554 for _, group := range groups.ToRemove.Items {
Girish Gowdra491a9c62021-01-06 16:43:07 -08001555 // err = dh.groupMgr.DeleteGroup(ctx, group)
1556 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, nil, group, McastFlowOrGroupRemove)
Esin Karamand519bbf2020-07-01 11:16:03 +00001557 if err != nil {
1558 errorsList = append(errorsList, err)
1559 }
Esin Karamanccb714b2019-11-29 15:02:06 +00001560 }
1561 }
Andrea Campanellac63bba92020-03-10 17:01:04 +01001562 if len(errorsList) > 0 {
1563 return fmt.Errorf("errors-installing-flows-groups, errors:%v", errorsList)
1564 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001565 logger.Debugw(ctx, "updated-flows-incrementally-successfully", log.Fields{"device-id": dh.device.Id})
Girish Gowdru0c588b22019-04-23 23:24:56 -04001566 return nil
manikkaraj kbf256be2019-03-25 00:13:48 +05301567}
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001568
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001569//DisableDevice disables the given device
1570//It marks the following for the given device:
1571//Device-Handler Admin-State : down
1572//Device Port-State: UNKNOWN
1573//Device Oper-State: UNKNOWN
Neha Sharma96b7bf22020-06-15 10:37:32 +00001574func (dh *DeviceHandler) DisableDevice(ctx context.Context, device *voltha.Device) error {
Chaitrashree G S44124192019-08-07 20:21:36 -04001575 /* On device disable ,admin state update has to be done prior sending request to agent since
1576 the indication thread may processes invalid indications of ONU and OLT*/
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001577 if dh.Client != nil {
Neha Sharma8f4e4322020-08-06 10:51:53 +00001578 if _, err := dh.Client.DisableOlt(log.WithSpanFromContext(context.Background(), ctx), new(oop.Empty)); err != nil {
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001579 if e, ok := status.FromError(err); ok && e.Code() == codes.Internal {
Girish Kumarf26e4882020-03-05 06:49:10 +00001580 return olterrors.NewErrAdapter("olt-disable-failed", log.Fields{"device-id": device.Id}, err)
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001581 }
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001582 }
Chaitrashree G S44124192019-08-07 20:21:36 -04001583 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001584 logger.Debugw(ctx, "olt-disabled", log.Fields{"device-id": device.Id})
Chaitrashree G S44124192019-08-07 20:21:36 -04001585 /* Discovered ONUs entries need to be cleared , since on device disable the child devices goes to
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001586 UNREACHABLE state which needs to be configured again*/
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301587
1588 dh.discOnus = sync.Map{}
1589 dh.onus = sync.Map{}
1590
Thomas Lee S85f37312020-04-03 17:06:12 +05301591 //stopping the stats collector
1592 dh.stopCollector <- true
1593
Neha Sharma96b7bf22020-06-15 10:37:32 +00001594 go dh.notifyChildDevices(ctx, "unreachable")
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001595 cloned := proto.Clone(device).(*voltha.Device)
Thomas Lee S985938d2020-05-04 11:40:41 +05301596 //Update device Admin state
1597 dh.device = cloned
kdarapu1afeceb2020-02-12 01:38:09 -05001598 // Update the all pon ports state on that device to disable and NNI remains active as NNI remains active in openolt agent.
Neha Sharma8f4e4322020-08-06 10:51:53 +00001599 if err := dh.coreProxy.PortsStateUpdate(log.WithSpanFromContext(context.TODO(), ctx), cloned.Id, ^uint32(1<<voltha.Port_PON_OLT), voltha.OperStatus_UNKNOWN); err != nil {
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001600 return olterrors.NewErrAdapter("ports-state-update-failed", log.Fields{"device-id": device.Id}, err)
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001601 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001602 logger.Debugw(ctx, "disable-device-end", log.Fields{"device-id": device.Id})
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001603 return nil
1604}
1605
Neha Sharma96b7bf22020-06-15 10:37:32 +00001606func (dh *DeviceHandler) notifyChildDevices(ctx context.Context, state string) {
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001607 // Update onu state as unreachable in onu adapter
1608 onuInd := oop.OnuIndication{}
Abhilash Laxmeshwarf9942e92020-01-07 15:32:44 +05301609 onuInd.OperState = state
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001610 //get the child device for the parent device
Neha Sharma8f4e4322020-08-06 10:51:53 +00001611 onuDevices, err := dh.coreProxy.GetChildDevices(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id)
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001612 if err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001613 logger.Errorw(ctx, "failed-to-get-child-devices-information", log.Fields{"device-id": dh.device.Id, "error": err})
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001614 }
1615 if onuDevices != nil {
1616 for _, onuDevice := range onuDevices.Items {
Neha Sharma8f4e4322020-08-06 10:51:53 +00001617 err := dh.AdapterProxy.SendInterAdapterMessage(log.WithSpanFromContext(context.TODO(), ctx), &onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001618 dh.openOLT.config.Topic, onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001619 if err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001620 logger.Errorw(ctx, "failed-to-send-inter-adapter-message", log.Fields{"OnuInd": onuInd,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001621 "From Adapter": dh.openOLT.config.Topic, "DeviceType": onuDevice.Type, "device-id": onuDevice.Id})
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001622 }
1623
1624 }
1625 }
1626
1627}
1628
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001629//ReenableDevice re-enables the olt device after disable
1630//It marks the following for the given device:
1631//Device-Handler Admin-State : up
1632//Device Port-State: ACTIVE
1633//Device Oper-State: ACTIVE
Neha Sharma96b7bf22020-06-15 10:37:32 +00001634func (dh *DeviceHandler) ReenableDevice(ctx context.Context, device *voltha.Device) error {
Neha Sharma8f4e4322020-08-06 10:51:53 +00001635 if _, err := dh.Client.ReenableOlt(log.WithSpanFromContext(context.Background(), ctx), new(oop.Empty)); err != nil {
Abhilash Laxmeshwar5b302e12020-01-09 15:15:14 +05301636 if e, ok := status.FromError(err); ok && e.Code() == codes.Internal {
Girish Kumarf26e4882020-03-05 06:49:10 +00001637 return olterrors.NewErrAdapter("olt-reenable-failed", log.Fields{"device-id": dh.device.Id}, err)
Abhilash Laxmeshwar5b302e12020-01-09 15:15:14 +05301638 }
1639 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001640 logger.Debug(ctx, "olt-reenabled")
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001641
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001642 // Update the all ports state on that device to enable
kesavand39e0aa32020-01-28 20:58:50 -05001643
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001644 ports, err := dh.coreProxy.ListDevicePorts(ctx, device.Id)
1645 if err != nil {
divyadesai3af43e12020-08-18 07:10:54 +00001646 return olterrors.NewErrAdapter("list-ports-failed", log.Fields{"device-id": device.Id}, err)
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001647 }
1648 if err := dh.disableAdminDownPorts(ctx, ports); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001649 return olterrors.NewErrAdapter("port-status-update-failed-after-olt-reenable", log.Fields{"device": device}, err)
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001650 }
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001651 //Update the device oper status as ACTIVE
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001652 device.OperStatus = voltha.OperStatus_ACTIVE
1653 dh.device = device
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001654
Neha Sharma8f4e4322020-08-06 10:51:53 +00001655 if err := dh.coreProxy.DeviceStateUpdate(log.WithSpanFromContext(context.TODO(), ctx), device.Id, device.ConnectStatus, device.OperStatus); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301656 return olterrors.NewErrAdapter("state-update-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001657 "device-id": device.Id,
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001658 "connect-status": device.ConnectStatus,
1659 "oper-status": device.OperStatus}, err)
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001660 }
kesavand39e0aa32020-01-28 20:58:50 -05001661
Neha Sharma96b7bf22020-06-15 10:37:32 +00001662 logger.Debugw(ctx, "reenabledevice-end", log.Fields{"device-id": device.Id})
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001663
1664 return nil
1665}
manikkaraj k9eb6cac2019-05-09 12:32:03 -04001666
npujarec5762e2020-01-01 14:08:48 +05301667func (dh *DeviceHandler) clearUNIData(ctx context.Context, onu *rsrcMgr.OnuGemInfo) error {
Devmalya Paul495b94a2019-08-27 19:42:00 -04001668 var uniID uint32
1669 var err error
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +05301670 for _, port := range onu.UniPorts {
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001671 uniID = UniIDFromPortNum(port)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001672 logger.Debugw(ctx, "clearing-resource-data-for-uni-port", log.Fields{"port": port, "uni-id": uniID})
A R Karthick1f85b802019-10-11 05:06:05 +00001673 /* Delete tech-profile instance from the KV store */
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001674 if err = dh.flowMgr[onu.IntfID].DeleteTechProfileInstances(ctx, onu.IntfID, onu.OnuID, uniID); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001675 logger.Debugw(ctx, "failed-to-remove-tech-profile-instance-for-onu", log.Fields{"onu-id": onu.OnuID})
Devmalya Paul495b94a2019-08-27 19:42:00 -04001676 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001677 logger.Debugw(ctx, "deleted-tech-profile-instance-for-onu", log.Fields{"onu-id": onu.OnuID})
npujarec5762e2020-01-01 14:08:48 +05301678 tpIDList := dh.resourceMgr.GetTechProfileIDForOnu(ctx, onu.IntfID, onu.OnuID, uniID)
Gamze Abakafee36392019-10-03 11:17:24 +00001679 for _, tpID := range tpIDList {
Girish Gowdraa482f272021-03-24 23:04:19 -07001680 if err = dh.resourceMgr.RemoveMeterInfoForOnu(ctx, "upstream", onu.IntfID, onu.OnuID, uniID, tpID); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001681 logger.Debugw(ctx, "failed-to-remove-meter-id-for-onu-upstream", log.Fields{"onu-id": onu.OnuID})
Gamze Abakafee36392019-10-03 11:17:24 +00001682 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001683 logger.Debugw(ctx, "removed-meter-id-for-onu-upstream", log.Fields{"onu-id": onu.OnuID})
Girish Gowdraa482f272021-03-24 23:04:19 -07001684 if err = dh.resourceMgr.RemoveMeterInfoForOnu(ctx, "downstream", onu.IntfID, onu.OnuID, uniID, tpID); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001685 logger.Debugw(ctx, "failed-to-remove-meter-id-for-onu-downstream", log.Fields{"onu-id": onu.OnuID})
Gamze Abakafee36392019-10-03 11:17:24 +00001686 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001687 logger.Debugw(ctx, "removed-meter-id-for-onu-downstream", log.Fields{"onu-id": onu.OnuID})
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +05301688 }
npujarec5762e2020-01-01 14:08:48 +05301689 dh.resourceMgr.FreePONResourcesForONU(ctx, onu.IntfID, onu.OnuID, uniID)
1690 if err = dh.resourceMgr.RemoveTechProfileIDsForOnu(ctx, onu.IntfID, onu.OnuID, uniID); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001691 logger.Debugw(ctx, "failed-to-remove-tech-profile-id-for-onu", log.Fields{"onu-id": onu.OnuID})
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +05301692 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001693 logger.Debugw(ctx, "removed-tech-profile-id-for-onu", log.Fields{"onu-id": onu.OnuID})
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001694 if err = dh.resourceMgr.DeletePacketInGemPortForOnu(ctx, onu.IntfID, onu.OnuID, port); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001695 logger.Debugw(ctx, "failed-to-remove-gemport-pkt-in", log.Fields{"intfid": onu.IntfID, "onuid": onu.OnuID, "uniId": uniID})
A R Karthick