blob: 8eaf0bf59950bc506a72516b50b1b8d3793fcaf1 [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 Gunyel2fb81472020-12-16 23:18:34 -080097 totalPonPorts uint32
98 perOnuChannel map[string]onuIndicationChannels
99 perOnuChannelLock 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
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700104}
105
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700106//OnuDevice represents ONU related info
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700107type OnuDevice struct {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700108 deviceID string
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700109 deviceType string
110 serialNumber string
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700111 onuID uint32
112 intfID uint32
113 proxyDeviceID string
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +0530114 losRaised bool
Devmalya Paula1efa642020-04-20 01:36:43 -0400115 rdiRaised bool
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700116}
117
Mahir Gunyel2fb81472020-12-16 23:18:34 -0800118type perOnuIndication struct {
119 ctx context.Context
120 indication *oop.Indication
121 serialNumber string
122}
123
124type onuIndicationChannels struct {
125 indicationChannel chan perOnuIndication
126 stopChannel chan struct{}
127}
128
Girish Gowdra491a9c62021-01-06 16:43:07 -0800129//McastFlowOrGroupControlBlock is created per mcast flow/group add/modify/remove and pushed on the incomingMcastFlowOrGroup channel slice
130//The McastFlowOrGroupControlBlock is then picked by the mcastFlowOrGroupChannelHandlerRoutine for further processing.
131//There are MaxNumOfGroupHandlerChannels number of mcastFlowOrGroupChannelHandlerRoutine routines which monitor for any incoming mcast flow/group messages
132//and process them serially. The mcast flow/group are assigned these routines based on formula (group-id modulo MaxNumOfGroupHandlerChannels)
133type McastFlowOrGroupControlBlock struct {
134 ctx context.Context // Flow/group handler context
135 flowOrGroupAction string // one of McastFlowOrGroupAdd, McastFlowOrGroupModify or McastFlowOrGroupDelete
136 flow *voltha.OfpFlowStats // Flow message (can be nil or valid flow)
137 group *voltha.OfpGroupEntry // Group message (can be nil or valid group)
138 errChan *chan error // channel to report the mcast Flow/group handling error
139}
140
Naga Manjunath7615e552019-10-11 22:35:47 +0530141var pmNames = []string{
142 "rx_bytes",
143 "rx_packets",
144 "rx_mcast_packets",
145 "rx_bcast_packets",
146 "tx_bytes",
147 "tx_packets",
148 "tx_mcast_packets",
149 "tx_bcast_packets",
150}
151
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700152//NewOnuDevice creates a new Onu Device
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +0530153func NewOnuDevice(devID, deviceTp, serialNum string, onuID, intfID uint32, proxyDevID string, losRaised bool) *OnuDevice {
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700154 var device OnuDevice
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700155 device.deviceID = devID
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700156 device.deviceType = deviceTp
157 device.serialNumber = serialNum
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700158 device.onuID = onuID
159 device.intfID = intfID
160 device.proxyDeviceID = proxyDevID
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +0530161 device.losRaised = losRaised
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700162 return &device
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530163}
164
165//NewDeviceHandler creates a new device handler
Himani Chawlacd407802020-12-10 12:08:59 +0530166func 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 -0700167 var dh DeviceHandler
Matteo Scandolodfa7a972020-11-06 13:03:40 -0800168 dh.cm = cm
cuilin20187b2a8c32019-03-26 19:52:28 -0700169 dh.coreProxy = cp
Girish Gowdru0c588b22019-04-23 23:24:56 -0400170 dh.AdapterProxy = ap
Devmalya Paulfb990a52019-07-09 10:01:49 -0400171 dh.EventProxy = ep
cuilin20187b2a8c32019-03-26 19:52:28 -0700172 cloned := (proto.Clone(device)).(*voltha.Device)
cuilin20187b2a8c32019-03-26 19:52:28 -0700173 dh.device = cloned
174 dh.openOLT = adapter
175 dh.exitChannel = make(chan int, 1)
176 dh.lockDevice = sync.RWMutex{}
Naga Manjunath7615e552019-10-11 22:35:47 +0530177 dh.stopCollector = make(chan bool, 2)
Abhilash Laxmeshwarf9942e92020-01-07 15:32:44 +0530178 dh.stopHeartbeatCheck = make(chan bool, 2)
Naga Manjunath7615e552019-10-11 22:35:47 +0530179 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 -0500180 dh.activePorts = sync.Map{}
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400181 dh.stopIndications = make(chan bool, 1)
Mahir Gunyel2fb81472020-12-16 23:18:34 -0800182 dh.perOnuChannel = make(map[string]onuIndicationChannels)
Girish Gowdra491a9c62021-01-06 16:43:07 -0800183 // Create a slice of buffered channels for handling concurrent mcast flow/group.
184 dh.incomingMcastFlowOrGroup = make([]chan McastFlowOrGroupControlBlock, MaxNumOfGroupHandlerChannels)
185 for i := range dh.incomingMcastFlowOrGroup {
186 dh.incomingMcastFlowOrGroup[i] = make(chan McastFlowOrGroupControlBlock, MaxNumOfGroupHandlerChannels)
187 // Spin up a go routine to handling incoming mcast flow/group (add/modify/remove).
188 // There will be MaxNumOfGroupHandlerChannels number of mcastFlowOrGroupChannelHandlerRoutine go routines.
189 // These routines will be blocked on the dh.incomingMcastFlowOrGroup[mcast-group-id modulo MaxNumOfGroupHandlerChannels] channel
190 // for incoming mcast flow/group to be processed serially.
191 go dh.mcastFlowOrGroupChannelHandlerRoutine(dh.incomingMcastFlowOrGroup[i])
192 }
cuilin20187b2a8c32019-03-26 19:52:28 -0700193 //TODO initialize the support classes.
194 return &dh
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530195}
196
197// start save the device to the data model
198func (dh *DeviceHandler) start(ctx context.Context) {
cuilin20187b2a8c32019-03-26 19:52:28 -0700199 dh.lockDevice.Lock()
200 defer dh.lockDevice.Unlock()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000201 logger.Debugw(ctx, "starting-device-agent", log.Fields{"device": dh.device})
cuilin20187b2a8c32019-03-26 19:52:28 -0700202 // Add the initial device to the local model
Neha Sharma96b7bf22020-06-15 10:37:32 +0000203 logger.Debug(ctx, "device-agent-started")
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530204}
205
206// stop stops the device dh. Not much to do for now
207func (dh *DeviceHandler) stop(ctx context.Context) {
cuilin20187b2a8c32019-03-26 19:52:28 -0700208 dh.lockDevice.Lock()
209 defer dh.lockDevice.Unlock()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000210 logger.Debug(ctx, "stopping-device-agent")
cuilin20187b2a8c32019-03-26 19:52:28 -0700211 dh.exitChannel <- 1
Neha Sharma96b7bf22020-06-15 10:37:32 +0000212 logger.Debug(ctx, "device-agent-stopped")
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530213}
214
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400215func macifyIP(ip net.IP) string {
216 if len(ip) > 0 {
217 oct1 := strconv.FormatInt(int64(ip[12]), 16)
218 oct2 := strconv.FormatInt(int64(ip[13]), 16)
219 oct3 := strconv.FormatInt(int64(ip[14]), 16)
220 oct4 := strconv.FormatInt(int64(ip[15]), 16)
221 return fmt.Sprintf("00:00:%02v:%02v:%02v:%02v", oct1, oct2, oct3, oct4)
222 }
223 return ""
224}
225
Neha Sharma96b7bf22020-06-15 10:37:32 +0000226func generateMacFromHost(ctx context.Context, host string) (string, error) {
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400227 var genmac string
228 var addr net.IP
229 var ips []string
230 var err error
231
Neha Sharma96b7bf22020-06-15 10:37:32 +0000232 logger.Debugw(ctx, "generating-mac-from-host", log.Fields{"host": host})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400233
234 if addr = net.ParseIP(host); addr == nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000235 logger.Debugw(ctx, "looking-up-hostname", log.Fields{"host": host})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400236
237 if ips, err = net.LookupHost(host); err == nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000238 logger.Debugw(ctx, "dns-result-ips", log.Fields{"ips": ips})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400239 if addr = net.ParseIP(ips[0]); addr == nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000240 return "", olterrors.NewErrInvalidValue(log.Fields{"ip": ips[0]}, nil)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400241 }
242 genmac = macifyIP(addr)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000243 logger.Debugw(ctx, "using-ip-as-mac",
Shrey Baid807a2a02020-04-09 12:52:45 +0530244 log.Fields{"host": ips[0],
245 "mac": genmac})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400246 return genmac, nil
247 }
Girish Kumarf26e4882020-03-05 06:49:10 +0000248 return "", olterrors.NewErrAdapter("cannot-resolve-hostname-to-ip", log.Fields{"host": host}, err)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400249 }
250
251 genmac = macifyIP(addr)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000252 logger.Debugw(ctx, "using-ip-as-mac",
Shrey Baid807a2a02020-04-09 12:52:45 +0530253 log.Fields{"host": host,
254 "mac": genmac})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400255 return genmac, nil
256}
257
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530258func macAddressToUint32Array(mac string) []uint32 {
cuilin20187b2a8c32019-03-26 19:52:28 -0700259 slist := strings.Split(mac, ":")
260 result := make([]uint32, len(slist))
261 var err error
262 var tmp int64
263 for index, val := range slist {
264 if tmp, err = strconv.ParseInt(val, 16, 32); err != nil {
265 return []uint32{1, 2, 3, 4, 5, 6}
266 }
267 result[index] = uint32(tmp)
268 }
269 return result
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530270}
271
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700272//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 -0800273func GetportLabel(portNum uint32, portType voltha.Port_PortType) (string, error) {
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530274
David K. Bainbridge794735f2020-02-11 21:01:37 -0800275 switch portType {
276 case voltha.Port_ETHERNET_NNI:
277 return fmt.Sprintf("nni-%d", portNum), nil
278 case voltha.Port_PON_OLT:
279 return fmt.Sprintf("pon-%d", portNum), nil
cuilin20187b2a8c32019-03-26 19:52:28 -0700280 }
David K. Bainbridge794735f2020-02-11 21:01:37 -0800281
Girish Kumarf26e4882020-03-05 06:49:10 +0000282 return "", olterrors.NewErrInvalidValue(log.Fields{"port-type": portType}, nil)
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530283}
284
Neha Sharma96b7bf22020-06-15 10:37:32 +0000285func (dh *DeviceHandler) addPort(ctx context.Context, intfID uint32, portType voltha.Port_PortType, state string) error {
Esin Karamanccb714b2019-11-29 15:02:06 +0000286 var operStatus common.OperStatus_Types
cuilin20187b2a8c32019-03-26 19:52:28 -0700287 if state == "up" {
288 operStatus = voltha.OperStatus_ACTIVE
kesavand39e0aa32020-01-28 20:58:50 -0500289 //populating the intfStatus map
Chaitrashree G Sef088112020-02-03 21:39:27 -0500290 dh.activePorts.Store(intfID, true)
cuilin20187b2a8c32019-03-26 19:52:28 -0700291 } else {
292 operStatus = voltha.OperStatus_DISCOVERED
Chaitrashree G Sef088112020-02-03 21:39:27 -0500293 dh.activePorts.Store(intfID, false)
cuilin20187b2a8c32019-03-26 19:52:28 -0700294 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700295 portNum := IntfIDToPortNo(intfID, portType)
Chaitrashree G Sc0878ec2020-05-21 04:59:53 -0400296 label, err := GetportLabel(intfID, portType)
David K. Bainbridge794735f2020-02-11 21:01:37 -0800297 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000298 return olterrors.NewErrNotFound("port-label", log.Fields{"port-number": portNum, "port-type": portType}, err)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400299 }
Chaitrashree G Sded0a832020-01-09 20:21:48 -0500300
Neha Sharma8f4e4322020-08-06 10:51:53 +0000301 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 +0000302 logger.Debug(ctx, "port-already-exists-updating-oper-status-of-port")
Neha Sharma8f4e4322020-08-06 10:51:53 +0000303 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 -0400304 return olterrors.NewErrAdapter("failed-to-update-port-state", log.Fields{
305 "device-id": dh.device.Id,
306 "port-type": portType,
307 "port-number": portNum,
308 "oper-status": operStatus}, err).Log()
Chaitrashree G Sded0a832020-01-09 20:21:48 -0500309 }
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400310 return nil
Chaitrashree G Sded0a832020-01-09 20:21:48 -0500311 }
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400312 // Now create Port
Girish Gowdra631ef3d2020-06-15 10:45:52 -0700313 capacity := uint32(of.OfpPortFeatures_OFPPF_1GB_FD | of.OfpPortFeatures_OFPPF_FIBER)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400314 port := &voltha.Port{
cuilin20187b2a8c32019-03-26 19:52:28 -0700315 PortNo: portNum,
316 Label: label,
317 Type: portType,
318 OperStatus: operStatus,
Girish Gowdra631ef3d2020-06-15 10:45:52 -0700319 OfpPort: &of.OfpPort{
320 HwAddr: macAddressToUint32Array(dh.device.MacAddress),
321 Config: 0,
322 State: uint32(of.OfpPortState_OFPPS_LIVE),
323 Curr: capacity,
324 Advertised: capacity,
325 Peer: capacity,
326 CurrSpeed: uint32(of.OfpPortFeatures_OFPPF_1GB_FD),
327 MaxSpeed: uint32(of.OfpPortFeatures_OFPPF_1GB_FD),
328 },
cuilin20187b2a8c32019-03-26 19:52:28 -0700329 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000330 logger.Debugw(ctx, "sending-port-update-to-core", log.Fields{"port": port})
cuilin20187b2a8c32019-03-26 19:52:28 -0700331 // Synchronous call to update device - this method is run in its own go routine
Neha Sharma8f4e4322020-08-06 10:51:53 +0000332 if err := dh.coreProxy.PortCreated(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, port); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000333 return olterrors.NewErrAdapter("error-creating-port", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -0800334 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +0000335 "port-type": portType}, err)
Girish Gowdru1110ef22019-06-24 11:17:59 -0400336 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000337 go dh.updateLocalDevice(ctx)
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530338 return nil
339}
340
Kent Hagermane6ff1012020-07-14 15:07:53 -0400341func (dh *DeviceHandler) updateLocalDevice(ctx context.Context) {
Neha Sharma8f4e4322020-08-06 10:51:53 +0000342 device, err := dh.coreProxy.GetDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, dh.device.Id)
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530343 if err != nil || device == nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400344 logger.Errorf(ctx, "device-not-found", log.Fields{"device-id": dh.device.Id}, err)
345 return
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530346 }
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800347 dh.lockDevice.Lock()
348 defer dh.lockDevice.Unlock()
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530349 dh.device = device
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530350}
351
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700352// nolint: gocyclo
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530353// readIndications to read the indications from the OLT device
David K. Bainbridge794735f2020-02-11 21:01:37 -0800354func (dh *DeviceHandler) readIndications(ctx context.Context) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000355 defer logger.Debugw(ctx, "indications-ended", log.Fields{"device-id": dh.device.Id})
Girish Gowdra3ab6d212020-03-24 17:33:15 -0700356 defer func() {
357 dh.lockDevice.Lock()
358 dh.isReadIndicationRoutineActive = false
359 dh.lockDevice.Unlock()
360 }()
Girish Gowdra3f974912020-03-23 20:35:18 -0700361 indications, err := dh.startOpenOltIndicationStream(ctx)
cuilin20187b2a8c32019-03-26 19:52:28 -0700362 if err != nil {
Girish Gowdra3f974912020-03-23 20:35:18 -0700363 return err
cuilin20187b2a8c32019-03-26 19:52:28 -0700364 }
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400365 /* get device state */
npujarec5762e2020-01-01 14:08:48 +0530366 device, err := dh.coreProxy.GetDevice(ctx, dh.device.Id, dh.device.Id)
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400367 if err != nil || device == nil {
368 /*TODO: needs to handle error scenarios */
Girish Kumarf26e4882020-03-05 06:49:10 +0000369 return olterrors.NewErrNotFound("device", log.Fields{"device-id": dh.device.Id}, err)
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400370 }
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400371
David Bainbridgef5879ca2019-12-13 21:17:54 +0000372 // Create an exponential backoff around re-enabling indications. The
373 // maximum elapsed time for the back off is set to 0 so that we will
374 // continue to retry. The max interval defaults to 1m, but is set
375 // here for code clarity
376 indicationBackoff := backoff.NewExponentialBackOff()
377 indicationBackoff.MaxElapsedTime = 0
378 indicationBackoff.MaxInterval = 1 * time.Minute
Girish Gowdra3f974912020-03-23 20:35:18 -0700379
Girish Gowdra3ab6d212020-03-24 17:33:15 -0700380 dh.lockDevice.Lock()
381 dh.isReadIndicationRoutineActive = true
382 dh.lockDevice.Unlock()
383
Girish Gowdra3f974912020-03-23 20:35:18 -0700384Loop:
cuilin20187b2a8c32019-03-26 19:52:28 -0700385 for {
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400386 select {
387 case <-dh.stopIndications:
divyadesai3af43e12020-08-18 07:10:54 +0000388 logger.Debugw(ctx, "stopping-collecting-indications-for-olt", log.Fields{"device-id": dh.device.Id})
Girish Gowdra3f974912020-03-23 20:35:18 -0700389 break Loop
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400390 default:
391 indication, err := indications.Recv()
392 if err == io.EOF {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000393 logger.Infow(ctx, "eof-for-indications",
Shrey Baid807a2a02020-04-09 12:52:45 +0530394 log.Fields{"err": err,
Thomas Lee S985938d2020-05-04 11:40:41 +0530395 "device-id": dh.device.Id})
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400396 // Use an exponential back off to prevent getting into a tight loop
397 duration := indicationBackoff.NextBackOff()
398 if duration == backoff.Stop {
399 // If we reach a maximum then warn and reset the backoff
400 // timer and keep attempting.
Neha Sharma96b7bf22020-06-15 10:37:32 +0000401 logger.Warnw(ctx, "maximum-indication-backoff-reached--resetting-backoff-timer",
Shrey Baid807a2a02020-04-09 12:52:45 +0530402 log.Fields{"max-indication-backoff": indicationBackoff.MaxElapsedTime,
Thomas Lee S985938d2020-05-04 11:40:41 +0530403 "device-id": dh.device.Id})
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400404 indicationBackoff.Reset()
405 }
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700406
407 // On failure process a backoff timer while watching for stopIndications
408 // events
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700409 backoffTimer := time.NewTimer(indicationBackoff.NextBackOff())
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700410 select {
411 case <-dh.stopIndications:
divyadesai3af43e12020-08-18 07:10:54 +0000412 logger.Debugw(ctx, "stopping-collecting-indications-for-olt", log.Fields{"device-id": dh.device.Id})
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700413 if !backoffTimer.Stop() {
414 <-backoffTimer.C
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700415 }
416 break Loop
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700417 case <-backoffTimer.C:
418 // backoffTimer expired continue
David Bainbridge95a3fcf2020-06-09 10:49:31 -0700419 }
Girish Gowdra3f974912020-03-23 20:35:18 -0700420 if indications, err = dh.startOpenOltIndicationStream(ctx); err != nil {
421 return err
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400422 }
423 continue
David Bainbridgef5879ca2019-12-13 21:17:54 +0000424 }
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530425 if err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000426 logger.Errorw(ctx, "read-indication-error",
Shrey Baid807a2a02020-04-09 12:52:45 +0530427 log.Fields{"err": err,
Thomas Lee S985938d2020-05-04 11:40:41 +0530428 "device-id": dh.device.Id})
Girish Gowdra3f974912020-03-23 20:35:18 -0700429 // Close the stream, and re-initialize it
430 if err = indications.CloseSend(); err != nil {
431 // Ok to ignore here, because we landed here due to a problem on the stream
432 // In all probability, the closeSend call may fail
Neha Sharma96b7bf22020-06-15 10:37:32 +0000433 logger.Debugw(ctx, "error-closing-send stream--error-ignored",
Shrey Baid807a2a02020-04-09 12:52:45 +0530434 log.Fields{"err": err,
Thomas Lee S985938d2020-05-04 11:40:41 +0530435 "device-id": dh.device.Id})
Girish Gowdra3f974912020-03-23 20:35:18 -0700436 }
437 if indications, err = dh.startOpenOltIndicationStream(ctx); err != nil {
438 return err
439 }
440 // once we re-initialized the indication stream, continue to read indications
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400441 continue
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530442 }
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400443 // Reset backoff if we have a successful receive
444 indicationBackoff.Reset()
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400445 // When OLT is admin down, ignore all indications.
Thomas Lee S985938d2020-05-04 11:40:41 +0530446 if device.AdminState == voltha.AdminState_DISABLED && !isIndicationAllowedDuringOltAdminDown(indication) {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000447 logger.Debugw(ctx, "olt-is-admin-down, ignore indication",
Shrey Baid807a2a02020-04-09 12:52:45 +0530448 log.Fields{"indication": indication,
Thomas Lee S985938d2020-05-04 11:40:41 +0530449 "device-id": dh.device.Id})
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400450 continue
Devmalya Paul495b94a2019-08-27 19:42:00 -0400451 }
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400452 dh.handleIndication(ctx, indication)
cuilin20187b2a8c32019-03-26 19:52:28 -0700453 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700454 }
Girish Gowdra3f974912020-03-23 20:35:18 -0700455 // Close the send stream
456 _ = indications.CloseSend() // Ok to ignore error, as we stopping the readIndication anyway
Girish Gowdra3ab6d212020-03-24 17:33:15 -0700457
Girish Gowdra3f974912020-03-23 20:35:18 -0700458 return nil
459}
460
461func (dh *DeviceHandler) startOpenOltIndicationStream(ctx context.Context) (oop.Openolt_EnableIndicationClient, error) {
462
463 indications, err := dh.Client.EnableIndication(ctx, new(oop.Empty))
464 if err != nil {
465 return nil, olterrors.NewErrCommunication("indication-read-failure", log.Fields{"device-id": dh.device.Id}, err).Log()
466 }
467 if indications == nil {
468 return nil, olterrors.NewErrInvalidValue(log.Fields{"indications": nil, "device-id": dh.device.Id}, nil).Log()
469 }
470
471 return indications, nil
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400472}
473
474// isIndicationAllowedDuringOltAdminDown returns true if the indication is allowed during OLT Admin down, else false
475func isIndicationAllowedDuringOltAdminDown(indication *oop.Indication) bool {
476 switch indication.Data.(type) {
477 case *oop.Indication_OltInd, *oop.Indication_IntfInd, *oop.Indication_IntfOperInd:
478 return true
479
480 default:
481 return false
482 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700483}
484
David K. Bainbridge794735f2020-02-11 21:01:37 -0800485func (dh *DeviceHandler) handleOltIndication(ctx context.Context, oltIndication *oop.OltIndication) error {
Daniele Rossi051466a2019-07-26 13:39:37 +0000486 raisedTs := time.Now().UnixNano()
Gamze Abakaa1a50522019-10-03 19:28:27 +0000487 if oltIndication.OperState == "up" && dh.transitionMap.currentDeviceState != deviceStateUp {
npujarec5762e2020-01-01 14:08:48 +0530488 dh.transitionMap.Handle(ctx, DeviceUpInd)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700489 } else if oltIndication.OperState == "down" {
npujarec5762e2020-01-01 14:08:48 +0530490 dh.transitionMap.Handle(ctx, DeviceDownInd)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700491 }
Daniele Rossi051466a2019-07-26 13:39:37 +0000492 // Send or clear Alarm
Neha Sharma96b7bf22020-06-15 10:37:32 +0000493 if err := dh.eventMgr.oltUpDownIndication(ctx, oltIndication, dh.device.Id, raisedTs); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +0530494 return olterrors.NewErrAdapter("failed-indication", log.Fields{
divyadesai3af43e12020-08-18 07:10:54 +0000495 "device-id": dh.device.Id,
David K. Bainbridge794735f2020-02-11 21:01:37 -0800496 "indication": oltIndication,
Girish Kumarf26e4882020-03-05 06:49:10 +0000497 "timestamp": raisedTs}, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -0800498 }
499 return nil
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700500}
501
David K. Bainbridge794735f2020-02-11 21:01:37 -0800502// nolint: gocyclo
npujarec5762e2020-01-01 14:08:48 +0530503func (dh *DeviceHandler) handleIndication(ctx context.Context, indication *oop.Indication) {
Devmalya Paulfb990a52019-07-09 10:01:49 -0400504 raisedTs := time.Now().UnixNano()
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700505 switch indication.Data.(type) {
506 case *oop.Indication_OltInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000507 span, ctx := log.CreateChildSpan(ctx, "olt-indication", log.Fields{"device-id": dh.device.Id})
508 defer span.Finish()
509
David K. Bainbridge794735f2020-02-11 21:01:37 -0800510 if err := dh.handleOltIndication(ctx, indication.GetOltInd()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400511 _ = olterrors.NewErrAdapter("handle-indication-error", log.Fields{"type": "olt", "device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800512 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700513 case *oop.Indication_IntfInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000514 span, ctx := log.CreateChildSpan(ctx, "interface-indication", log.Fields{"device-id": dh.device.Id})
515 defer span.Finish()
516
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700517 intfInd := indication.GetIntfInd()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800518 go func() {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000519 if err := dh.addPort(ctx, intfInd.GetIntfId(), voltha.Port_PON_OLT, intfInd.GetOperState()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400520 _ = olterrors.NewErrAdapter("handle-indication-error", log.Fields{"type": "interface", "device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800521 }
522 }()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000523 logger.Infow(ctx, "received-interface-indication", log.Fields{"InterfaceInd": intfInd, "device-id": dh.device.Id})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700524 case *oop.Indication_IntfOperInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000525 span, ctx := log.CreateChildSpan(ctx, "interface-oper-indication", log.Fields{"device-id": dh.device.Id})
526 defer span.Finish()
527
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700528 intfOperInd := indication.GetIntfOperInd()
529 if intfOperInd.GetType() == "nni" {
David K. Bainbridge794735f2020-02-11 21:01:37 -0800530 go func() {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000531 if err := dh.addPort(ctx, intfOperInd.GetIntfId(), voltha.Port_ETHERNET_NNI, intfOperInd.GetOperState()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400532 _ = 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 -0800533 }
534 }()
Kent Hagermane6ff1012020-07-14 15:07:53 -0400535 if err := dh.resourceMgr.AddNNIToKVStore(ctx, intfOperInd.GetIntfId()); err != nil {
536 logger.Warn(ctx, err)
537 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700538 } else if intfOperInd.GetType() == "pon" {
539 // TODO: Check what needs to be handled here for When PON PORT down, ONU will be down
540 // Handle pon port update
David K. Bainbridge794735f2020-02-11 21:01:37 -0800541 go func() {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000542 if err := dh.addPort(ctx, intfOperInd.GetIntfId(), voltha.Port_PON_OLT, intfOperInd.GetOperState()); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400543 _ = 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 -0800544 }
545 }()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000546 go dh.eventMgr.oltIntfOperIndication(ctx, indication.GetIntfOperInd(), dh.device.Id, raisedTs)
cuilin20187b2a8c32019-03-26 19:52:28 -0700547 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000548 logger.Infow(ctx, "received-interface-oper-indication",
Shrey Baid807a2a02020-04-09 12:52:45 +0530549 log.Fields{"interfaceOperInd": intfOperInd,
Thomas Lee S985938d2020-05-04 11:40:41 +0530550 "device-id": dh.device.Id})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700551 case *oop.Indication_OnuDiscInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000552 span, ctx := log.CreateChildSpan(ctx, "onu-discovery-indication", log.Fields{"device-id": dh.device.Id})
553 defer span.Finish()
554
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700555 onuDiscInd := indication.GetOnuDiscInd()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000556 logger.Infow(ctx, "received-onu-discovery-indication", log.Fields{"OnuDiscInd": onuDiscInd, "device-id": dh.device.Id})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700557 sn := dh.stringifySerialNumber(onuDiscInd.SerialNumber)
Mahir Gunyel2fb81472020-12-16 23:18:34 -0800558 //put message to channel and return immediately
559 dh.putOnuIndicationToChannel(ctx, indication, sn)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700560 case *oop.Indication_OnuInd:
Neha Sharma8f4e4322020-08-06 10:51:53 +0000561 span, ctx := log.CreateChildSpan(ctx, "onu-indication", log.Fields{"device-id": dh.device.Id})
562 defer span.Finish()
563
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700564 onuInd := indication.GetOnuInd()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000565 logger.Infow(ctx, "received-onu-indication", log.Fields{"OnuInd": onuInd, "device-id": dh.device.Id})
Mahir Gunyel2fb81472020-12-16 23:18:34 -0800566 sn := dh.stringifySerialNumber(onuInd.SerialNumber)
567 //put message to channel and return immediately
568 dh.putOnuIndicationToChannel(ctx, indication, sn)
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
645 raisedTs := time.Now().UnixNano()
646 go dh.eventMgr.oltCommunicationEvent(ctx, dh.device, raisedTs)
647
Girish Gowdru0c588b22019-04-23 23:24:56 -0400648 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530649}
650
651// doStateDown handle the olt down indication
npujarec5762e2020-01-01 14:08:48 +0530652func (dh *DeviceHandler) doStateDown(ctx context.Context) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000653 logger.Debugw(ctx, "do-state-down-start", log.Fields{"device-id": dh.device.Id})
Girish Gowdrud4245152019-05-10 00:47:31 -0400654
npujarec5762e2020-01-01 14:08:48 +0530655 device, err := dh.coreProxy.GetDevice(ctx, dh.device.Id, dh.device.Id)
Girish Gowdrud4245152019-05-10 00:47:31 -0400656 if err != nil || device == nil {
657 /*TODO: needs to handle error scenarios */
Girish Kumarf26e4882020-03-05 06:49:10 +0000658 return olterrors.NewErrNotFound("device", log.Fields{"device-id": dh.device.Id}, err)
Girish Gowdrud4245152019-05-10 00:47:31 -0400659 }
660
661 cloned := proto.Clone(device).(*voltha.Device)
Girish Gowdrud4245152019-05-10 00:47:31 -0400662
663 //Update the device oper state and connection status
664 cloned.OperStatus = voltha.OperStatus_UNKNOWN
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800665 dh.lockDevice.Lock()
Girish Gowdrud4245152019-05-10 00:47:31 -0400666 dh.device = cloned
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800667 dh.lockDevice.Unlock()
Girish Gowdrud4245152019-05-10 00:47:31 -0400668
David K. Bainbridge794735f2020-02-11 21:01:37 -0800669 if err = dh.coreProxy.DeviceStateUpdate(ctx, cloned.Id, cloned.ConnectStatus, cloned.OperStatus); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000670 return olterrors.NewErrAdapter("state-update-failed", log.Fields{"device-id": device.Id}, err)
Girish Gowdrud4245152019-05-10 00:47:31 -0400671 }
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400672
673 //get the child device for the parent device
npujarec5762e2020-01-01 14:08:48 +0530674 onuDevices, err := dh.coreProxy.GetChildDevices(ctx, dh.device.Id)
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400675 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000676 return olterrors.NewErrAdapter("child-device-fetch-failed", log.Fields{"device-id": dh.device.Id}, err)
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400677 }
678 for _, onuDevice := range onuDevices.Items {
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400679 // Update onu state as down in onu adapter
680 onuInd := oop.OnuIndication{}
681 onuInd.OperState = "down"
David K. Bainbridge794735f2020-02-11 21:01:37 -0800682 err := dh.AdapterProxy.SendInterAdapterMessage(ctx, &onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
serkant.uluderya4aff1862020-09-17 23:35:26 +0300683 dh.openOLT.config.Topic, onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
David K. Bainbridge794735f2020-02-11 21:01:37 -0800684 if err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400685 _ = olterrors.NewErrCommunication("inter-adapter-send-failed", log.Fields{
serkant.uluderya4aff1862020-09-17 23:35:26 +0300686 "source": dh.openOLT.config.Topic,
David K. Bainbridge794735f2020-02-11 21:01:37 -0800687 "onu-indicator": onuInd,
688 "device-type": onuDevice.Type,
689 "device-id": onuDevice.Id}, err).LogAt(log.ErrorLevel)
serkant.uluderya245caba2019-09-24 23:15:29 -0700690 //Do not return here and continue to process other ONUs
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800691 } else {
692 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 -0700693 }
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -0400694 }
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800695 dh.lockDevice.Lock()
serkant.uluderya245caba2019-09-24 23:15:29 -0700696 /* Discovered ONUs entries need to be cleared , since after OLT
697 is up, it starts sending discovery indications again*/
Naga Manjunatha8dc9372019-10-31 23:01:18 +0530698 dh.discOnus = sync.Map{}
Girish Gowdrabe811ff2021-01-26 17:12:12 -0800699 dh.lockDevice.Unlock()
700
Neha Sharma96b7bf22020-06-15 10:37:32 +0000701 logger.Debugw(ctx, "do-state-down-end", log.Fields{"device-id": device.Id})
cuilin20187b2a8c32019-03-26 19:52:28 -0700702 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530703}
704
705// doStateInit dial the grpc before going to init state
npujarec5762e2020-01-01 14:08:48 +0530706func (dh *DeviceHandler) doStateInit(ctx context.Context) error {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400707 var err error
Girish Kumar93e91742020-07-27 16:43:19 +0000708 // Use Intercepters to automatically inject and publish Open Tracing Spans by this GRPC client
709 dh.clientCon, err = grpc.Dial(dh.device.GetHostAndPort(),
710 grpc.WithInsecure(),
711 grpc.WithBlock(),
712 grpc.WithStreamInterceptor(grpc_middleware.ChainStreamClient(
Girish Kumar935f7af2020-08-18 11:59:42 +0000713 grpc_opentracing.StreamClientInterceptor(grpc_opentracing.WithTracer(log.ActiveTracerProxy{})),
Girish Kumar93e91742020-07-27 16:43:19 +0000714 )),
715 grpc.WithUnaryInterceptor(grpc_middleware.ChainUnaryClient(
Girish Kumar935f7af2020-08-18 11:59:42 +0000716 grpc_opentracing.UnaryClientInterceptor(grpc_opentracing.WithTracer(log.ActiveTracerProxy{})),
Girish Kumar93e91742020-07-27 16:43:19 +0000717 )))
718
719 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +0530720 return olterrors.NewErrCommunication("dial-failure", log.Fields{
Thomas Lee S985938d2020-05-04 11:40:41 +0530721 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +0000722 "host-and-port": dh.device.GetHostAndPort()}, err)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400723 }
724 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530725}
726
727// postInit create olt client instance to invoke RPC on the olt device
npujarec5762e2020-01-01 14:08:48 +0530728func (dh *DeviceHandler) postInit(ctx context.Context) error {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400729 dh.Client = oop.NewOpenoltClient(dh.clientCon)
npujarec5762e2020-01-01 14:08:48 +0530730 dh.transitionMap.Handle(ctx, GrpcConnected)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400731 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530732}
733
734// doStateConnected get the device info and update to voltha core
npujarec5762e2020-01-01 14:08:48 +0530735func (dh *DeviceHandler) doStateConnected(ctx context.Context) error {
Thomas Lee S985938d2020-05-04 11:40:41 +0530736 var err error
Neha Sharma96b7bf22020-06-15 10:37:32 +0000737 logger.Debugw(ctx, "olt-device-connected", log.Fields{"device-id": dh.device.Id})
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400738
739 // Case where OLT is disabled and then rebooted.
Thomas Lee S985938d2020-05-04 11:40:41 +0530740 device, err := dh.coreProxy.GetDevice(ctx, dh.device.Id, dh.device.Id)
741 if err != nil || device == nil {
742 /*TODO: needs to handle error scenarios */
743 return olterrors.NewErrAdapter("device-fetch-failed", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
744 }
745 if device.AdminState == voltha.AdminState_DISABLED {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000746 logger.Debugln(ctx, "do-state-connected--device-admin-state-down")
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400747
748 cloned := proto.Clone(device).(*voltha.Device)
749 cloned.ConnectStatus = voltha.ConnectStatus_REACHABLE
750 cloned.OperStatus = voltha.OperStatus_UNKNOWN
751 dh.device = cloned
Thomas Lee S985938d2020-05-04 11:40:41 +0530752 if err = dh.coreProxy.DeviceStateUpdate(ctx, cloned.Id, cloned.ConnectStatus, cloned.OperStatus); err != nil {
753 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 -0400754 }
755
Chaitrashree G S44124192019-08-07 20:21:36 -0400756 // 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 +0530757 _, err = dh.Client.DisableOlt(ctx, new(oop.Empty))
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400758 if err != nil {
Thomas Lee S985938d2020-05-04 11:40:41 +0530759 return olterrors.NewErrAdapter("olt-disable-failed", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400760 }
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400761 // We should still go ahead an initialize various device handler modules so that when OLT is re-enabled, we have
762 // all the modules initialized and ready to handle incoming ONUs.
763
Thomas Lee S985938d2020-05-04 11:40:41 +0530764 err = dh.initializeDeviceHandlerModules(ctx)
765 if err != nil {
766 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 -0400767 }
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400768
769 // Start reading indications
David K. Bainbridge794735f2020-02-11 21:01:37 -0800770 go func() {
Thomas Lee S985938d2020-05-04 11:40:41 +0530771 if err = dh.readIndications(ctx); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400772 _ = olterrors.NewErrAdapter("indication-read-failure", log.Fields{"device-id": dh.device.Id}, err).LogAt(log.ErrorLevel)
David K. Bainbridge794735f2020-02-11 21:01:37 -0800773 }
774 }()
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700775
776 go startHeartbeatCheck(ctx, dh)
777
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400778 return nil
779 }
780
Neha Sharma8f4e4322020-08-06 10:51:53 +0000781 ports, err := dh.coreProxy.ListDevicePorts(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id)
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400782 if err != nil {
Girish Gowdrud4245152019-05-10 00:47:31 -0400783 /*TODO: needs to handle error scenarios */
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400784 return olterrors.NewErrAdapter("fetch-ports-failed", log.Fields{"device-id": dh.device.Id}, err)
Girish Gowdrud4245152019-05-10 00:47:31 -0400785 }
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400786 dh.populateActivePorts(ctx, ports)
787 if err := dh.disableAdminDownPorts(ctx, ports); err != nil {
788 return olterrors.NewErrAdapter("port-status-update-failed", log.Fields{"ports": ports}, err)
Girish Gowdrud4245152019-05-10 00:47:31 -0400789 }
790
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400791 if err := dh.initializeDeviceHandlerModules(ctx); err != nil {
Thomas Lee S985938d2020-05-04 11:40:41 +0530792 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 -0400793 }
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530794
cuilin20187b2a8c32019-03-26 19:52:28 -0700795 // Start reading indications
David K. Bainbridge794735f2020-02-11 21:01:37 -0800796 go func() {
797 if err := dh.readIndications(ctx); err != nil {
Kent Hagermane6ff1012020-07-14 15:07:53 -0400798 _ = olterrors.NewErrAdapter("read-indications-failure", log.Fields{"device-id": dh.device.Id}, err).Log()
David K. Bainbridge794735f2020-02-11 21:01:37 -0800799 }
800 }()
Neha Sharma96b7bf22020-06-15 10:37:32 +0000801 go dh.updateLocalDevice(ctx)
Rohan Agrawalda5e0b22020-05-20 11:10:26 +0000802
803 if device.PmConfigs != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000804 dh.UpdatePmConfig(ctx, device.PmConfigs)
Rohan Agrawalda5e0b22020-05-20 11:10:26 +0000805 }
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700806
807 go startHeartbeatCheck(ctx, dh)
808
cuilin20187b2a8c32019-03-26 19:52:28 -0700809 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530810}
811
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400812func (dh *DeviceHandler) initializeDeviceHandlerModules(ctx context.Context) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000813 deviceInfo, err := dh.populateDeviceInfo(ctx)
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400814
815 if err != nil {
816 return olterrors.NewErrAdapter("populate-device-info-failed", log.Fields{"device-id": dh.device.Id}, err)
817 }
Girish Gowdra9602eb42020-09-09 15:50:39 -0700818 dh.totalPonPorts = deviceInfo.GetPonPorts()
819
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400820 // Instantiate resource manager
Matteo Scandolodfa7a972020-11-06 13:03:40 -0800821 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 -0400822 return olterrors.ErrResourceManagerInstantiating
823 }
824
Girish Gowdra9602eb42020-09-09 15:50:39 -0700825 dh.groupMgr = NewGroupManager(ctx, dh, dh.resourceMgr)
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400826
Girish Gowdra9602eb42020-09-09 15:50:39 -0700827 dh.flowMgr = make([]*OpenOltFlowMgr, dh.totalPonPorts)
828 for i := range dh.flowMgr {
829 // Instantiate flow manager
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700830 if dh.flowMgr[i] = NewFlowManager(ctx, dh, dh.resourceMgr, dh.groupMgr, uint32(i)); dh.flowMgr[i] == nil {
Girish Gowdra9602eb42020-09-09 15:50:39 -0700831 return olterrors.ErrResourceManagerInstantiating
832 }
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400833 }
Girish Gowdra9602eb42020-09-09 15:50:39 -0700834
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400835 /* TODO: Instantiate Alarm , stats , BW managers */
836 /* Instantiating Event Manager to handle Alarms and KPIs */
837 dh.eventMgr = NewEventMgr(dh.EventProxy, dh)
838
839 // Stats config for new device
Neha Sharma96b7bf22020-06-15 10:37:32 +0000840 dh.portStats = NewOpenOltStatsMgr(ctx, dh)
Chaitrashree G Sa4649252020-03-11 21:24:11 -0400841
842 return nil
843
844}
845
Neha Sharma96b7bf22020-06-15 10:37:32 +0000846func (dh *DeviceHandler) populateDeviceInfo(ctx context.Context) (*oop.DeviceInfo, error) {
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400847 var err error
848 var deviceInfo *oop.DeviceInfo
849
Neha Sharma8f4e4322020-08-06 10:51:53 +0000850 deviceInfo, err = dh.Client.GetDeviceInfo(log.WithSpanFromContext(context.Background(), ctx), new(oop.Empty))
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400851
852 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000853 return nil, olterrors.NewErrPersistence("get", "device", 0, nil, err)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400854 }
855 if deviceInfo == nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000856 return nil, olterrors.NewErrInvalidValue(log.Fields{"device": nil}, nil)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400857 }
858
Neha Sharma96b7bf22020-06-15 10:37:32 +0000859 logger.Debugw(ctx, "fetched-device-info", log.Fields{"deviceInfo": deviceInfo, "device-id": dh.device.Id})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400860 dh.device.Root = true
861 dh.device.Vendor = deviceInfo.Vendor
862 dh.device.Model = deviceInfo.Model
863 dh.device.SerialNumber = deviceInfo.DeviceSerialNumber
864 dh.device.HardwareVersion = deviceInfo.HardwareVersion
865 dh.device.FirmwareVersion = deviceInfo.FirmwareVersion
866
867 if deviceInfo.DeviceId == "" {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000868 logger.Warnw(ctx, "no-device-id-provided-using-host", log.Fields{"hostport": dh.device.GetHostAndPort()})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400869 host := strings.Split(dh.device.GetHostAndPort(), ":")[0]
Neha Sharma96b7bf22020-06-15 10:37:32 +0000870 genmac, err := generateMacFromHost(ctx, host)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400871 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000872 return nil, olterrors.NewErrAdapter("failed-to-generate-mac-host", log.Fields{"host": host}, err)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400873 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000874 logger.Debugw(ctx, "using-host-for-mac-address", log.Fields{"host": host, "mac": genmac})
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400875 dh.device.MacAddress = genmac
876 } else {
877 dh.device.MacAddress = deviceInfo.DeviceId
878 }
879
880 // Synchronous call to update device - this method is run in its own go routine
Neha Sharma8f4e4322020-08-06 10:51:53 +0000881 if err := dh.coreProxy.DeviceUpdate(log.WithSpanFromContext(context.TODO(), ctx), dh.device); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +0000882 return nil, olterrors.NewErrAdapter("device-update-failed", log.Fields{"device-id": dh.device.Id}, err)
Matt Jeanneretf4fdcd72019-07-19 20:03:23 -0400883 }
884
885 return deviceInfo, nil
886}
887
Neha Sharma96b7bf22020-06-15 10:37:32 +0000888func startCollector(ctx context.Context, dh *DeviceHandler) {
889 logger.Debugf(ctx, "starting-collector")
Naga Manjunath7615e552019-10-11 22:35:47 +0530890 for {
891 select {
892 case <-dh.stopCollector:
divyadesai3af43e12020-08-18 07:10:54 +0000893 logger.Debugw(ctx, "stopping-collector-for-olt", log.Fields{"device-id": dh.device.Id})
Naga Manjunath7615e552019-10-11 22:35:47 +0530894 return
Rohan Agrawalda5e0b22020-05-20 11:10:26 +0000895 case <-time.After(time.Duration(dh.metrics.ToPmConfigs().DefaultFreq) * time.Second):
Girish Gowdra34815db2020-05-11 17:18:04 -0700896
Neha Sharma8f4e4322020-08-06 10:51:53 +0000897 ports, err := dh.coreProxy.ListDevicePorts(log.WithSpanFromContext(context.Background(), ctx), dh.device.Id)
Kent Hagermanf1db18b2020-07-08 13:38:15 -0400898 if err != nil {
899 logger.Warnw(ctx, "failed-to-list-ports", log.Fields{"device-id": dh.device.Id, "error": err})
900 continue
901 }
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530902 for _, port := range ports {
903 // NNI Stats
904 if port.Type == voltha.Port_ETHERNET_NNI {
905 intfID := PortNoToIntfID(port.PortNo, voltha.Port_ETHERNET_NNI)
906 cmnni := dh.portStats.collectNNIMetrics(intfID)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000907 logger.Debugw(ctx, "collect-nni-metrics", log.Fields{"metrics": cmnni})
Gamze Abakafcbd6e72020-12-17 13:25:16 +0000908 go dh.portStats.publishMetrics(ctx, NNIStats, cmnni, port, dh.device.Id, dh.device.Type)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000909 logger.Debugw(ctx, "publish-nni-metrics", log.Fields{"nni-port": port.Label})
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530910 }
911 // PON Stats
912 if port.Type == voltha.Port_PON_OLT {
913 intfID := PortNoToIntfID(port.PortNo, voltha.Port_PON_OLT)
914 if val, ok := dh.activePorts.Load(intfID); ok && val == true {
915 cmpon := dh.portStats.collectPONMetrics(intfID)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000916 logger.Debugw(ctx, "collect-pon-metrics", log.Fields{"metrics": cmpon})
Gamze Abakafcbd6e72020-12-17 13:25:16 +0000917 go dh.portStats.publishMetrics(ctx, PONStats, cmpon, port, dh.device.Id, dh.device.Type)
Kishore Darapuaaf9c102020-05-04 13:06:57 +0530918 }
Neha Sharma96b7bf22020-06-15 10:37:32 +0000919 logger.Debugw(ctx, "publish-pon-metrics", log.Fields{"pon-port": port.Label})
Gamze Abakafcbd6e72020-12-17 13:25:16 +0000920
921 //ONU & Gem Stats
922 onuGemInfo := dh.flowMgr[intfID].onuGemInfo
923 if len(onuGemInfo) != 0 {
924 go dh.portStats.collectOnuAndGemStats(ctx, onuGemInfo)
925 }
Chaitrashree G Sef088112020-02-03 21:39:27 -0500926 }
Naga Manjunath7615e552019-10-11 22:35:47 +0530927 }
928 }
929 }
930}
931
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700932//AdoptDevice adopts the OLT device
npujarec5762e2020-01-01 14:08:48 +0530933func (dh *DeviceHandler) AdoptDevice(ctx context.Context, device *voltha.Device) {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400934 dh.transitionMap = NewTransitionMap(dh)
Neha Sharma96b7bf22020-06-15 10:37:32 +0000935 logger.Infow(ctx, "adopt-device", log.Fields{"device-id": device.Id, "Address": device.GetHostAndPort()})
npujarec5762e2020-01-01 14:08:48 +0530936 dh.transitionMap.Handle(ctx, DeviceInit)
Naga Manjunath7615e552019-10-11 22:35:47 +0530937
938 // Now, set the initial PM configuration for that device
Kent Hagermane6ff1012020-07-14 15:07:53 -0400939 if err := dh.coreProxy.DevicePMConfigUpdate(ctx, dh.metrics.ToPmConfigs()); err != nil {
940 _ = olterrors.NewErrAdapter("error-updating-performance-metrics", log.Fields{"device-id": device.Id}, err).LogAt(log.ErrorLevel)
Naga Manjunath7615e552019-10-11 22:35:47 +0530941 }
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530942}
943
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700944//GetOfpDeviceInfo Gets the Ofp information of the given device
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530945func (dh *DeviceHandler) GetOfpDeviceInfo(device *voltha.Device) (*ic.SwitchCapability, error) {
cuilin20187b2a8c32019-03-26 19:52:28 -0700946 return &ic.SwitchCapability{
947 Desc: &of.OfpDesc{
Devmalya Paul70dd4972019-06-10 15:19:17 +0530948 MfrDesc: "VOLTHA Project",
cuilin20187b2a8c32019-03-26 19:52:28 -0700949 HwDesc: "open_pon",
950 SwDesc: "open_pon",
Girish Gowdraa09aeab2020-09-14 16:30:52 -0700951 SerialNum: device.SerialNumber,
cuilin20187b2a8c32019-03-26 19:52:28 -0700952 },
953 SwitchFeatures: &of.OfpSwitchFeatures{
954 NBuffers: 256,
955 NTables: 2,
956 Capabilities: uint32(of.OfpCapabilities_OFPC_FLOW_STATS |
957 of.OfpCapabilities_OFPC_TABLE_STATS |
958 of.OfpCapabilities_OFPC_PORT_STATS |
959 of.OfpCapabilities_OFPC_GROUP_STATS),
960 },
961 }, nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +0530962}
963
Neha Sharma96b7bf22020-06-15 10:37:32 +0000964func (dh *DeviceHandler) omciIndication(ctx context.Context, omciInd *oop.OmciIndication) error {
965 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 -0700966 var deviceType string
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700967 var deviceID string
968 var proxyDeviceID string
cuilin20187b2a8c32019-03-26 19:52:28 -0700969
Matt Jeanneretceea2e02020-03-27 14:19:57 -0400970 transid := extractOmciTransactionID(omciInd.Pkt)
Matteo Scandolo92186242020-06-12 10:54:18 -0700971 if logger.V(log.DebugLevel) {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000972 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 -0700973 "omci-transaction-id": transid, "omci-msg": hex.EncodeToString(omciInd.Pkt)})
974 }
Matt Jeanneretceea2e02020-03-27 14:19:57 -0400975
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700976 onuKey := dh.formOnuKey(omciInd.IntfId, omciInd.OnuId)
Naga Manjunatha8dc9372019-10-31 23:01:18 +0530977
978 if onuInCache, ok := dh.onus.Load(onuKey); !ok {
979
Neha Sharma96b7bf22020-06-15 10:37:32 +0000980 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 -0700981 ponPort := IntfIDToPortNo(omciInd.GetIntfId(), voltha.Port_PON_OLT)
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700982 kwargs := make(map[string]interface{})
983 kwargs["onu_id"] = omciInd.OnuId
984 kwargs["parent_port_no"] = ponPort
cuilin20187b2a8c32019-03-26 19:52:28 -0700985
Neha Sharma8f4e4322020-08-06 10:51:53 +0000986 onuDevice, err := dh.coreProxy.GetChildDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, kwargs)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700987 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +0530988 return olterrors.NewErrNotFound("onu", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -0700989 "intf-id": omciInd.IntfId,
990 "onu-id": omciInd.OnuId}, err)
cuilin20187b2a8c32019-03-26 19:52:28 -0700991 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700992 deviceType = onuDevice.Type
993 deviceID = onuDevice.Id
994 proxyDeviceID = onuDevice.ProxyAddress.DeviceId
995 //if not exist in cache, then add to cache.
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +0530996 dh.onus.Store(onuKey, NewOnuDevice(deviceID, deviceType, onuDevice.SerialNumber, omciInd.OnuId, omciInd.IntfId, proxyDeviceID, false))
Mahir Gunyela3f9add2019-06-06 15:13:19 -0700997 } else {
998 //found in cache
Neha Sharma96b7bf22020-06-15 10:37:32 +0000999 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 +05301000 deviceType = onuInCache.(*OnuDevice).deviceType
1001 deviceID = onuInCache.(*OnuDevice).deviceID
1002 proxyDeviceID = onuInCache.(*OnuDevice).proxyDeviceID
cuilin20187b2a8c32019-03-26 19:52:28 -07001003 }
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001004
1005 omciMsg := &ic.InterAdapterOmciMessage{Message: omciInd.Pkt}
Neha Sharma8f4e4322020-08-06 10:51:53 +00001006 if err := dh.AdapterProxy.SendInterAdapterMessage(log.WithSpanFromContext(context.Background(), ctx), omciMsg,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001007 ic.InterAdapterMessageType_OMCI_REQUEST, dh.openOLT.config.Topic, deviceType,
David K. Bainbridge794735f2020-02-11 21:01:37 -08001008 deviceID, proxyDeviceID, ""); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301009 return olterrors.NewErrCommunication("omci-request", log.Fields{
serkant.uluderya4aff1862020-09-17 23:35:26 +03001010 "source": dh.openOLT.config.Topic,
David K. Bainbridge794735f2020-02-11 21:01:37 -08001011 "destination": deviceType,
1012 "onu-id": deviceID,
Girish Kumarf26e4882020-03-05 06:49:10 +00001013 "proxy-device-id": proxyDeviceID}, err)
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001014 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001015 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +05301016}
1017
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001018//ProcessInterAdapterMessage sends the proxied messages to the target device
1019// If the proxy address is not found in the unmarshalled message, it first fetches the onu device for which the message
1020// is meant, and then send the unmarshalled omci message to this onu
Neha Sharma96b7bf22020-06-15 10:37:32 +00001021func (dh *DeviceHandler) ProcessInterAdapterMessage(ctx context.Context, msg *ic.InterAdapterMessage) error {
1022 logger.Debugw(ctx, "process-inter-adapter-message", log.Fields{"msgID": msg.Header.Id})
cuilin20187b2a8c32019-03-26 19:52:28 -07001023 if msg.Header.Type == ic.InterAdapterMessageType_OMCI_REQUEST {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001024 msgID := msg.Header.Id
cuilin20187b2a8c32019-03-26 19:52:28 -07001025 fromTopic := msg.Header.FromTopic
1026 toTopic := msg.Header.ToTopic
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001027 toDeviceID := msg.Header.ToDeviceId
1028 proxyDeviceID := msg.Header.ProxyDeviceId
cuilin20187b2a8c32019-03-26 19:52:28 -07001029
Neha Sharma96b7bf22020-06-15 10:37:32 +00001030 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 -07001031
1032 msgBody := msg.GetBody()
1033
1034 omciMsg := &ic.InterAdapterOmciMessage{}
1035 if err := ptypes.UnmarshalAny(msgBody, omciMsg); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001036 return olterrors.NewErrAdapter("cannot-unmarshal-omci-msg-body", log.Fields{"msgbody": msgBody}, err)
cuilin20187b2a8c32019-03-26 19:52:28 -07001037 }
1038
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001039 if omciMsg.GetProxyAddress() == nil {
Neha Sharma8f4e4322020-08-06 10:51:53 +00001040 onuDevice, err := dh.coreProxy.GetDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, toDeviceID)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001041 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301042 return olterrors.NewErrNotFound("onu", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001043 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001044 "onu-device-id": toDeviceID}, err)
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001045 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001046 logger.Debugw(ctx, "device-retrieved-from-core", log.Fields{"msgID": msgID, "fromTopic": fromTopic, "toTopic": toTopic, "toDeviceID": toDeviceID, "proxyDeviceID": proxyDeviceID})
1047 if err := dh.sendProxiedMessage(ctx, onuDevice, omciMsg); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301048 return olterrors.NewErrCommunication("send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001049 "device-id": dh.device.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001050 "onu-device-id": toDeviceID}, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -08001051 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001052 } else {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001053 logger.Debugw(ctx, "proxy-address-found-in-omci-message", log.Fields{"msgID": msgID, "fromTopic": fromTopic, "toTopic": toTopic, "toDeviceID": toDeviceID, "proxyDeviceID": proxyDeviceID})
1054 if err := dh.sendProxiedMessage(ctx, nil, omciMsg); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301055 return olterrors.NewErrCommunication("send-failed", 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)
David K. Bainbridge794735f2020-02-11 21:01:37 -08001058 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001059 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001060 } else {
Girish Kumarf26e4882020-03-05 06:49:10 +00001061 return olterrors.NewErrInvalidValue(log.Fields{"inter-adapter-message-type": msg.Header.Type}, nil)
cuilin20187b2a8c32019-03-26 19:52:28 -07001062 }
1063 return nil
Phaneendra Manda4c62c802019-03-06 21:37:49 +05301064}
1065
Neha Sharma96b7bf22020-06-15 10:37:32 +00001066func (dh *DeviceHandler) sendProxiedMessage(ctx context.Context, onuDevice *voltha.Device, omciMsg *ic.InterAdapterOmciMessage) error {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001067 var intfID uint32
1068 var onuID uint32
Esin Karamanccb714b2019-11-29 15:02:06 +00001069 var connectStatus common.ConnectStatus_Types
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001070 if onuDevice != nil {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001071 intfID = onuDevice.ProxyAddress.GetChannelId()
1072 onuID = onuDevice.ProxyAddress.GetOnuId()
1073 connectStatus = onuDevice.ConnectStatus
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001074 } else {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001075 intfID = omciMsg.GetProxyAddress().GetChannelId()
1076 onuID = omciMsg.GetProxyAddress().GetOnuId()
1077 connectStatus = omciMsg.GetConnectStatus()
Mahir Gunyela3f9add2019-06-06 15:13:19 -07001078 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001079 if connectStatus != voltha.ConnectStatus_REACHABLE {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001080 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 -08001081
Thomas Lee S94109f12020-03-03 16:39:29 +05301082 return olterrors.NewErrCommunication("unreachable", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001083 "intf-id": intfID,
1084 "onu-id": onuID}, nil)
cuilin20187b2a8c32019-03-26 19:52:28 -07001085 }
1086
Matt Jeanneretceea2e02020-03-27 14:19:57 -04001087 // TODO: OpenOLT Agent oop.OmciMsg expects a hex encoded string for OMCI packets rather than the actual bytes.
1088 // Fix this in the agent and then we can pass byte array as Pkt: omciMsg.Message.
lcuie24ef182019-04-29 22:58:36 -07001089 var omciMessage *oop.OmciMsg
Matt Jeanneretceea2e02020-03-27 14:19:57 -04001090 hexPkt := make([]byte, hex.EncodedLen(len(omciMsg.Message)))
1091 hex.Encode(hexPkt, omciMsg.Message)
1092 omciMessage = &oop.OmciMsg{IntfId: intfID, OnuId: onuID, Pkt: hexPkt}
1093
1094 // TODO: Below logging illustrates the "stringify" of the omci Pkt.
1095 // once above is fixed this log line can change to just use hex.EncodeToString(omciMessage.Pkt)
1096 transid := extractOmciTransactionID(omciMsg.Message)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001097 logger.Debugw(ctx, "sent-omci-msg", log.Fields{"intf-id": intfID, "onu-id": onuID,
Matt Jeanneretceea2e02020-03-27 14:19:57 -04001098 "omciTransactionID": transid, "omciMsg": string(omciMessage.Pkt)})
cuilin20187b2a8c32019-03-26 19:52:28 -07001099
Neha Sharma8f4e4322020-08-06 10:51:53 +00001100 _, err := dh.Client.OmciMsgOut(log.WithSpanFromContext(context.Background(), ctx), omciMessage)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001101 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301102 return olterrors.NewErrCommunication("omci-send-failed", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001103 "intf-id": intfID,
1104 "onu-id": onuID,
1105 "message": omciMessage}, err)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001106 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001107 return nil
cuilin20187b2a8c32019-03-26 19:52:28 -07001108}
1109
David K. Bainbridge794735f2020-02-11 21:01:37 -08001110func (dh *DeviceHandler) activateONU(ctx context.Context, intfID uint32, onuID int64, serialNum *oop.SerialNumber, serialNumber string) error {
kesavand494c2082020-08-31 11:16:12 +05301111 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 -07001112 if err := dh.flowMgr[intfID].UpdateOnuInfo(ctx, intfID, uint32(onuID), serialNumber); err != nil {
Matteo Scandolo92186242020-06-12 10:54:18 -07001113 return olterrors.NewErrAdapter("onu-activate-failed", log.Fields{"onu": onuID, "intf-id": intfID}, err)
Andrea Campanellab83b39d2020-03-30 11:41:16 +02001114 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001115 // TODO: need resource manager
1116 var pir uint32 = 1000000
kesavand494c2082020-08-31 11:16:12 +05301117 Onu := oop.Onu{IntfId: intfID, OnuId: uint32(onuID), SerialNumber: serialNum, Pir: pir, OmccEncryption: dh.openOLT.config.OmccEncryption}
npujarec5762e2020-01-01 14:08:48 +05301118 if _, err := dh.Client.ActivateOnu(ctx, &Onu); err != nil {
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001119 st, _ := status.FromError(err)
1120 if st.Code() == codes.AlreadyExists {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001121 logger.Debugw(ctx, "onu-activation-in-progress", log.Fields{"SerialNumber": serialNumber, "onu-id": onuID, "device-id": dh.device.Id})
1122
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001123 } else {
Thomas Lee S985938d2020-05-04 11:40:41 +05301124 return olterrors.NewErrAdapter("onu-activate-failed", log.Fields{"onu": Onu, "device-id": dh.device.Id}, err)
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001125 }
cuilin20187b2a8c32019-03-26 19:52:28 -07001126 } else {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001127 logger.Infow(ctx, "activated-onu", log.Fields{"SerialNumber": serialNumber, "device-id": dh.device.Id})
cuilin20187b2a8c32019-03-26 19:52:28 -07001128 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001129 return nil
cuilin20187b2a8c32019-03-26 19:52:28 -07001130}
1131
David K. Bainbridge794735f2020-02-11 21:01:37 -08001132func (dh *DeviceHandler) onuDiscIndication(ctx context.Context, onuDiscInd *oop.OnuDiscIndication, sn string) error {
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001133 channelID := onuDiscInd.GetIntfId()
1134 parentPortNo := IntfIDToPortNo(onuDiscInd.GetIntfId(), voltha.Port_PON_OLT)
Matt Jeanneret53539512019-07-20 14:47:02 -04001135
Neha Sharma96b7bf22020-06-15 10:37:32 +00001136 logger.Infow(ctx, "new-discovery-indication", log.Fields{"sn": sn})
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301137
cuilin20187b2a8c32019-03-26 19:52:28 -07001138 kwargs := make(map[string]interface{})
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001139 if sn != "" {
1140 kwargs["serial_number"] = sn
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001141 } else {
Girish Kumarf26e4882020-03-05 06:49:10 +00001142 return olterrors.NewErrInvalidValue(log.Fields{"serial-number": sn}, nil)
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001143 }
1144
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301145 var alarmInd oop.OnuAlarmIndication
1146 raisedTs := time.Now().UnixNano()
Amit Ghoshe5c6a852020-02-10 15:09:46 +00001147 if _, loaded := dh.discOnus.LoadOrStore(sn, true); loaded {
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301148
1149 /* When PON cable disconnected and connected back from OLT, it was expected OnuAlarmIndication
1150 with "los_status: off" should be raised but BAL does not raise this Alarm hence manually sending
1151 OnuLosClear event on receiving OnuDiscoveryIndication for the Onu after checking whether
1152 OnuLosRaise event sent for it */
1153 dh.onus.Range(func(Onukey interface{}, onuInCache interface{}) bool {
1154 if onuInCache.(*OnuDevice).serialNumber == sn && onuInCache.(*OnuDevice).losRaised {
1155 if onuDiscInd.GetIntfId() != onuInCache.(*OnuDevice).intfID {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001156 logger.Warnw(ctx, "onu-is-on-a-different-intf-id-now", log.Fields{
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301157 "previousIntfId": onuInCache.(*OnuDevice).intfID,
1158 "currentIntfId": onuDiscInd.GetIntfId()})
1159 // TODO:: Should we need to ignore raising OnuLosClear event
1160 // when onu connected to different PON?
1161 }
1162 alarmInd.IntfId = onuInCache.(*OnuDevice).intfID
1163 alarmInd.OnuId = onuInCache.(*OnuDevice).onuID
1164 alarmInd.LosStatus = statusCheckOff
Kent Hagermane6ff1012020-07-14 15:07:53 -04001165 go func() {
1166 if err := dh.eventMgr.onuAlarmIndication(ctx, &alarmInd, onuInCache.(*OnuDevice).deviceID, raisedTs); err != nil {
1167 logger.Debugw(ctx, "indication-failed", log.Fields{"error": err})
1168 }
1169 }()
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301170 }
1171 return true
1172 })
1173
Neha Sharma96b7bf22020-06-15 10:37:32 +00001174 logger.Warnw(ctx, "onu-sn-is-already-being-processed", log.Fields{"sn": sn})
David K. Bainbridge794735f2020-02-11 21:01:37 -08001175 return nil
Amit Ghoshe5c6a852020-02-10 15:09:46 +00001176 }
1177
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001178 var onuID uint32
Matteo Scandolo945e4012019-12-12 14:16:11 -08001179
1180 // check the ONU is already know to the OLT
1181 // NOTE the second time the ONU is discovered this should return a device
1182 onuDevice, err := dh.coreProxy.GetChildDevice(ctx, dh.device.Id, kwargs)
1183
1184 if err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001185 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 -08001186 if e, ok := status.FromError(err); ok {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001187 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 -08001188 switch e.Code() {
1189 case codes.Internal:
1190 // this probably means NOT FOUND, so just create a new device
1191 onuDevice = nil
1192 case codes.DeadlineExceeded:
1193 // if the call times out, cleanup and exit
1194 dh.discOnus.Delete(sn)
Girish Kumarf26e4882020-03-05 06:49:10 +00001195 return olterrors.NewErrTimeout("get-child-device", log.Fields{"device-id": dh.device.Id}, err)
Matteo Scandolo945e4012019-12-12 14:16:11 -08001196 }
1197 }
1198 }
1199
1200 if onuDevice == nil {
1201 // NOTE this should happen a single time, and only if GetChildDevice returns NotFound
Neha Sharma96b7bf22020-06-15 10:37:32 +00001202 logger.Debugw(ctx, "creating-new-onu", log.Fields{"sn": sn})
Matteo Scandolo945e4012019-12-12 14:16:11 -08001203 // we need to create a new ChildDevice
Matt Jeanneret53539512019-07-20 14:47:02 -04001204 ponintfid := onuDiscInd.GetIntfId()
npujarec5762e2020-01-01 14:08:48 +05301205 onuID, err = dh.resourceMgr.GetONUID(ctx, ponintfid)
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001206
Neha Sharma96b7bf22020-06-15 10:37:32 +00001207 logger.Infow(ctx, "creating-new-onu-got-onu-id", log.Fields{"sn": sn, "onuId": onuID})
Matteo Scandolo945e4012019-12-12 14:16:11 -08001208
1209 if err != nil {
1210 // if we can't create an ID in resource manager,
1211 // cleanup and exit
Matteo Scandolo945e4012019-12-12 14:16:11 -08001212 dh.discOnus.Delete(sn)
Girish Kumarf26e4882020-03-05 06:49:10 +00001213 return olterrors.NewErrAdapter("resource-manager-get-onu-id-failed", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001214 "pon-intf-id": ponintfid,
1215 "serial-number": sn}, err)
Matteo Scandolo945e4012019-12-12 14:16:11 -08001216 }
1217
Neha Sharma8f4e4322020-08-06 10:51:53 +00001218 if onuDevice, err = dh.coreProxy.ChildDeviceDetected(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, int(parentPortNo),
Matteo Scandolo945e4012019-12-12 14:16:11 -08001219 "", int(channelID), string(onuDiscInd.SerialNumber.GetVendorId()), sn, int64(onuID)); err != nil {
Matteo Scandolo945e4012019-12-12 14:16:11 -08001220 dh.discOnus.Delete(sn)
1221 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 +05301222 return olterrors.NewErrAdapter("core-proxy-child-device-detected-failed", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001223 "pon-intf-id": ponintfid,
1224 "serial-number": sn}, err)
Matteo Scandolo945e4012019-12-12 14:16:11 -08001225 }
Kent Hagermane6ff1012020-07-14 15:07:53 -04001226 if err := dh.eventMgr.OnuDiscoveryIndication(ctx, onuDiscInd, dh.device.Id, onuDevice.Id, onuID, sn, time.Now().UnixNano()); err != nil {
1227 logger.Warnw(ctx, "discovery-indication-failed", log.Fields{"error": err})
1228 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001229 logger.Infow(ctx, "onu-child-device-added",
Shrey Baid807a2a02020-04-09 12:52:45 +05301230 log.Fields{"onuDevice": onuDevice,
1231 "sn": sn,
Matteo Scandolo92186242020-06-12 10:54:18 -07001232 "onu-id": onuID,
Thomas Lee S985938d2020-05-04 11:40:41 +05301233 "device-id": dh.device.Id})
Chaitrashree G Sbe6ab942019-05-24 06:42:49 -04001234 }
Matteo Scandolo945e4012019-12-12 14:16:11 -08001235
1236 // we can now use the existing ONU Id
1237 onuID = onuDevice.ProxyAddress.OnuId
Mahir Gunyele77977b2019-06-27 05:36:22 -07001238 //Insert the ONU into cache to use in OnuIndication.
1239 //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 +00001240 logger.Debugw(ctx, "onu-discovery-indication-key-create",
Matteo Scandolo92186242020-06-12 10:54:18 -07001241 log.Fields{"onu-id": onuID,
Shrey Baid807a2a02020-04-09 12:52:45 +05301242 "intfId": onuDiscInd.GetIntfId(),
1243 "sn": sn})
Mahir Gunyele77977b2019-06-27 05:36:22 -07001244 onuKey := dh.formOnuKey(onuDiscInd.GetIntfId(), onuID)
Matt Jeanneret53539512019-07-20 14:47:02 -04001245
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301246 onuDev := NewOnuDevice(onuDevice.Id, onuDevice.Type, onuDevice.SerialNumber, onuID, onuDiscInd.GetIntfId(), onuDevice.ProxyAddress.DeviceId, false)
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301247 dh.onus.Store(onuKey, onuDev)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001248 logger.Debugw(ctx, "new-onu-device-discovered",
Shrey Baid807a2a02020-04-09 12:52:45 +05301249 log.Fields{"onu": onuDev,
1250 "sn": sn})
Chaitrashree G S35b5d802019-07-08 23:12:03 -04001251
Kent Hagermane6ff1012020-07-14 15:07:53 -04001252 if err := dh.coreProxy.DeviceStateUpdate(ctx, onuDevice.Id, common.ConnectStatus_REACHABLE, common.OperStatus_DISCOVERED); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301253 return olterrors.NewErrAdapter("failed-to-update-device-state", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001254 "device-id": onuDevice.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001255 "serial-number": sn}, err)
cuilin20187b2a8c32019-03-26 19:52:28 -07001256 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001257 logger.Infow(ctx, "onu-discovered-reachable", log.Fields{"device-id": onuDevice.Id, "sn": sn})
Kent Hagermane6ff1012020-07-14 15:07:53 -04001258 if err := dh.activateONU(ctx, onuDiscInd.IntfId, int64(onuID), onuDiscInd.SerialNumber, sn); err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301259 return olterrors.NewErrAdapter("onu-activation-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001260 "device-id": onuDevice.Id,
Girish Kumarf26e4882020-03-05 06:49:10 +00001261 "serial-number": sn}, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -08001262 }
1263 return nil
cuilin20187b2a8c32019-03-26 19:52:28 -07001264}
1265
Mahir Gunyel2fb81472020-12-16 23:18:34 -08001266func (dh *DeviceHandler) onuIndication(ctx context.Context, onuInd *oop.OnuIndication, serialNumber string) error {
cuilin20187b2a8c32019-03-26 19:52:28 -07001267
1268 kwargs := make(map[string]interface{})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001269 ponPort := IntfIDToPortNo(onuInd.GetIntfId(), voltha.Port_PON_OLT)
Mahir Gunyele77977b2019-06-27 05:36:22 -07001270 var onuDevice *voltha.Device
David K. Bainbridge794735f2020-02-11 21:01:37 -08001271 var err error
Mahir Gunyele77977b2019-06-27 05:36:22 -07001272 foundInCache := false
Neha Sharma96b7bf22020-06-15 10:37:32 +00001273 logger.Debugw(ctx, "onu-indication-key-create",
Shrey Baid807a2a02020-04-09 12:52:45 +05301274 log.Fields{"onuId": onuInd.OnuId,
1275 "intfId": onuInd.GetIntfId(),
Thomas Lee S985938d2020-05-04 11:40:41 +05301276 "device-id": dh.device.Id})
Mahir Gunyele77977b2019-06-27 05:36:22 -07001277 onuKey := dh.formOnuKey(onuInd.GetIntfId(), onuInd.OnuId)
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301278
David K. Bainbridge794735f2020-02-11 21:01:37 -08001279 errFields := log.Fields{"device-id": dh.device.Id}
1280
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301281 if onuInCache, ok := dh.onus.Load(onuKey); ok {
1282
Mahir Gunyele77977b2019-06-27 05:36:22 -07001283 //If ONU id is discovered before then use GetDevice to get onuDevice because it is cheaper.
1284 foundInCache = true
David K. Bainbridge794735f2020-02-11 21:01:37 -08001285 errFields["onu-id"] = onuInCache.(*OnuDevice).deviceID
Kent Hagermane6ff1012020-07-14 15:07:53 -04001286 onuDevice, err = dh.coreProxy.GetDevice(ctx, dh.device.Id, onuInCache.(*OnuDevice).deviceID)
cuilin20187b2a8c32019-03-26 19:52:28 -07001287 } else {
Mahir Gunyele77977b2019-06-27 05:36:22 -07001288 //If ONU not found in adapter cache then we have to use GetChildDevice to get onuDevice
1289 if serialNumber != "" {
1290 kwargs["serial_number"] = serialNumber
David K. Bainbridge794735f2020-02-11 21:01:37 -08001291 errFields["serial-number"] = serialNumber
Mahir Gunyele77977b2019-06-27 05:36:22 -07001292 } else {
1293 kwargs["onu_id"] = onuInd.OnuId
1294 kwargs["parent_port_no"] = ponPort
David K. Bainbridge794735f2020-02-11 21:01:37 -08001295 errFields["onu-id"] = onuInd.OnuId
1296 errFields["parent-port-no"] = ponPort
Mahir Gunyele77977b2019-06-27 05:36:22 -07001297 }
Neha Sharma8f4e4322020-08-06 10:51:53 +00001298 onuDevice, err = dh.coreProxy.GetChildDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, kwargs)
cuilin20187b2a8c32019-03-26 19:52:28 -07001299 }
Mahir Gunyele77977b2019-06-27 05:36:22 -07001300
David K. Bainbridge794735f2020-02-11 21:01:37 -08001301 if err != nil || onuDevice == nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001302 return olterrors.NewErrNotFound("onu-device", errFields, err)
cuilin20187b2a8c32019-03-26 19:52:28 -07001303 }
1304
David K. Bainbridge794735f2020-02-11 21:01:37 -08001305 if onuDevice.ParentPortNo != ponPort {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001306 logger.Warnw(ctx, "onu-is-on-a-different-intf-id-now", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001307 "previousIntfId": onuDevice.ParentPortNo,
1308 "currentIntfId": ponPort})
1309 }
1310
1311 if onuDevice.ProxyAddress.OnuId != onuInd.OnuId {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001312 logger.Warnw(ctx, "onu-id-mismatch-possible-if-voltha-and-olt-rebooted", log.Fields{
Shrey Baid807a2a02020-04-09 12:52:45 +05301313 "expected-onu-id": onuDevice.ProxyAddress.OnuId,
1314 "received-onu-id": onuInd.OnuId,
Thomas Lee S985938d2020-05-04 11:40:41 +05301315 "device-id": dh.device.Id})
David K. Bainbridge794735f2020-02-11 21:01:37 -08001316 }
1317 if !foundInCache {
1318 onuKey := dh.formOnuKey(onuInd.GetIntfId(), onuInd.GetOnuId())
1319
Thiyagarajan Subramani34a00282020-03-10 20:19:31 +05301320 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 -08001321
1322 }
kesavand7cf3a052020-08-28 12:49:18 +05301323 if onuInd.OperState == "down" && onuInd.FailReason != oop.OnuIndication_ONU_ACTIVATION_FAIL_REASON_NONE {
1324 if err := dh.eventMgr.onuActivationIndication(ctx, onuActivationFailEvent, onuInd, dh.device.Id, time.Now().UnixNano()); err != nil {
1325 logger.Warnw(ctx, "onu-activation-indication-reporting-failed", log.Fields{"error": err})
1326 }
1327 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001328 if err := dh.updateOnuStates(ctx, onuDevice, onuInd); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001329 return olterrors.NewErrCommunication("state-update-failed", errFields, err)
David K. Bainbridge794735f2020-02-11 21:01:37 -08001330 }
1331 return nil
cuilin20187b2a8c32019-03-26 19:52:28 -07001332}
1333
Neha Sharma96b7bf22020-06-15 10:37:32 +00001334func (dh *DeviceHandler) updateOnuStates(ctx context.Context, onuDevice *voltha.Device, onuInd *oop.OnuIndication) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001335 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 -07001336 if onuInd.AdminState == "down" || onuInd.OperState == "down" {
1337 // The ONU has gone admin_state "down" or oper_state "down" - we expect the ONU to send discovery again
1338 // The ONU admin_state is "up" while "oper_state" is down in cases where ONU activation fails. In this case
1339 // the ONU sends Discovery again.
Girish Gowdra429f9502020-05-04 13:22:16 -07001340 dh.discOnus.Delete(onuDevice.SerialNumber)
Amit Ghosh9bbc5652020-02-17 13:37:32 +00001341 // Tests have shown that we sometimes get OperState as NOT down even if AdminState is down, forcing it
1342 if onuInd.OperState != "down" {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001343 logger.Warnw(ctx, "onu-admin-state-down", log.Fields{"operState": onuInd.OperState})
Amit Ghosh9bbc5652020-02-17 13:37:32 +00001344 onuInd.OperState = "down"
1345 }
1346 }
1347
David K. Bainbridge794735f2020-02-11 21:01:37 -08001348 switch onuInd.OperState {
1349 case "down":
Neha Sharma96b7bf22020-06-15 10:37:32 +00001350 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 -07001351 // TODO NEW CORE do not hardcode adapter name. Handler needs Adapter reference
npujarec5762e2020-01-01 14:08:48 +05301352 err := dh.AdapterProxy.SendInterAdapterMessage(ctx, onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001353 dh.openOLT.config.Topic, onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001354 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301355 return olterrors.NewErrCommunication("inter-adapter-send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001356 "onu-indicator": onuInd,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001357 "source": dh.openOLT.config.Topic,
David K. Bainbridge794735f2020-02-11 21:01:37 -08001358 "device-type": onuDevice.Type,
Girish Kumarf26e4882020-03-05 06:49:10 +00001359 "device-id": onuDevice.Id}, err)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001360 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001361 case "up":
Neha Sharma96b7bf22020-06-15 10:37:32 +00001362 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 -04001363 // TODO NEW CORE do not hardcode adapter name. Handler needs Adapter reference
npujarec5762e2020-01-01 14:08:48 +05301364 err := dh.AdapterProxy.SendInterAdapterMessage(ctx, onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001365 dh.openOLT.config.Topic, onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001366 if err != nil {
Thomas Lee S94109f12020-03-03 16:39:29 +05301367 return olterrors.NewErrCommunication("inter-adapter-send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001368 "onu-indicator": onuInd,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001369 "source": dh.openOLT.config.Topic,
David K. Bainbridge794735f2020-02-11 21:01:37 -08001370 "device-type": onuDevice.Type,
Girish Kumarf26e4882020-03-05 06:49:10 +00001371 "device-id": onuDevice.Id}, err)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001372 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001373 default:
Girish Kumarf26e4882020-03-05 06:49:10 +00001374 return olterrors.NewErrInvalidValue(log.Fields{"oper-state": onuInd.OperState}, nil)
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001375 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001376 return nil
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001377}
1378
cuilin20187b2a8c32019-03-26 19:52:28 -07001379func (dh *DeviceHandler) stringifySerialNumber(serialNum *oop.SerialNumber) string {
1380 if serialNum != nil {
1381 return string(serialNum.VendorId) + dh.stringifyVendorSpecific(serialNum.VendorSpecific)
cuilin20187b2a8c32019-03-26 19:52:28 -07001382 }
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001383 return ""
cuilin20187b2a8c32019-03-26 19:52:28 -07001384}
Chaitrashree G S1a55b882020-02-04 17:35:35 -05001385func (dh *DeviceHandler) deStringifySerialNumber(serialNum string) (*oop.SerialNumber, error) {
1386 decodedStr, err := hex.DecodeString(serialNum[4:])
1387 if err != nil {
1388 return nil, err
1389 }
1390 return &oop.SerialNumber{
1391 VendorId: []byte(serialNum[:4]),
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001392 VendorSpecific: decodedStr,
Chaitrashree G S1a55b882020-02-04 17:35:35 -05001393 }, nil
1394}
cuilin20187b2a8c32019-03-26 19:52:28 -07001395
1396func (dh *DeviceHandler) stringifyVendorSpecific(vendorSpecific []byte) string {
1397 tmp := fmt.Sprintf("%x", (uint32(vendorSpecific[0])>>4)&0x0f) +
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001398 fmt.Sprintf("%x", uint32(vendorSpecific[0]&0x0f)) +
cuilin20187b2a8c32019-03-26 19:52:28 -07001399 fmt.Sprintf("%x", (uint32(vendorSpecific[1])>>4)&0x0f) +
1400 fmt.Sprintf("%x", (uint32(vendorSpecific[1]))&0x0f) +
1401 fmt.Sprintf("%x", (uint32(vendorSpecific[2])>>4)&0x0f) +
1402 fmt.Sprintf("%x", (uint32(vendorSpecific[2]))&0x0f) +
1403 fmt.Sprintf("%x", (uint32(vendorSpecific[3])>>4)&0x0f) +
1404 fmt.Sprintf("%x", (uint32(vendorSpecific[3]))&0x0f)
1405 return tmp
1406}
1407
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001408//UpdateFlowsBulk upates the bulk flow
1409func (dh *DeviceHandler) UpdateFlowsBulk() error {
Thomas Lee S94109f12020-03-03 16:39:29 +05301410 return olterrors.ErrNotImplemented
cuilin20187b2a8c32019-03-26 19:52:28 -07001411}
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001412
1413//GetChildDevice returns the child device for given parent port and onu id
Neha Sharma96b7bf22020-06-15 10:37:32 +00001414func (dh *DeviceHandler) GetChildDevice(ctx context.Context, parentPort, onuID uint32) (*voltha.Device, error) {
1415 logger.Debugw(ctx, "getchilddevice",
Shrey Baid807a2a02020-04-09 12:52:45 +05301416 log.Fields{"pon-port": parentPort,
Matteo Scandolo92186242020-06-12 10:54:18 -07001417 "onu-id": onuID,
Thomas Lee S985938d2020-05-04 11:40:41 +05301418 "device-id": dh.device.Id})
Girish Gowdru0c588b22019-04-23 23:24:56 -04001419 kwargs := make(map[string]interface{})
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001420 kwargs["onu_id"] = onuID
Girish Gowdru0c588b22019-04-23 23:24:56 -04001421 kwargs["parent_port_no"] = parentPort
Neha Sharma8f4e4322020-08-06 10:51:53 +00001422 onuDevice, err := dh.coreProxy.GetChildDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, kwargs)
Girish Gowdru0c588b22019-04-23 23:24:56 -04001423 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001424 return nil, olterrors.NewErrNotFound("onu-device", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001425 "intf-id": parentPort,
1426 "onu-id": onuID}, err)
Girish Gowdru0c588b22019-04-23 23:24:56 -04001427 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001428 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 -08001429 return onuDevice, nil
manikkaraj kbf256be2019-03-25 00:13:48 +05301430}
1431
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001432// SendPacketInToCore sends packet-in to core
1433// For this, it calls SendPacketIn of the core-proxy which uses a device specific topic to send the request.
1434// The adapter handling the device creates a device specific topic
Neha Sharma96b7bf22020-06-15 10:37:32 +00001435func (dh *DeviceHandler) SendPacketInToCore(ctx context.Context, logicalPort uint32, packetPayload []byte) error {
Matteo Scandolo92186242020-06-12 10:54:18 -07001436 if logger.V(log.DebugLevel) {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001437 logger.Debugw(ctx, "send-packet-in-to-core", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001438 "port": logicalPort,
1439 "packet": hex.EncodeToString(packetPayload),
1440 "device-id": dh.device.Id,
1441 })
1442 }
Neha Sharma8f4e4322020-08-06 10:51:53 +00001443 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 +05301444 return olterrors.NewErrCommunication("packet-send-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001445 "source": "adapter",
1446 "destination": "core",
1447 "device-id": dh.device.Id,
1448 "logical-port": logicalPort,
Girish Kumarf26e4882020-03-05 06:49:10 +00001449 "packet": hex.EncodeToString(packetPayload)}, err)
manikkaraj k9eb6cac2019-05-09 12:32:03 -04001450 }
Matteo Scandolo92186242020-06-12 10:54:18 -07001451 if logger.V(log.DebugLevel) {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001452 logger.Debugw(ctx, "sent-packet-in-to-core-successfully", log.Fields{
Matteo Scandolo92186242020-06-12 10:54:18 -07001453 "packet": hex.EncodeToString(packetPayload),
1454 "device-id": dh.device.Id,
1455 })
1456 }
David K. Bainbridge794735f2020-02-11 21:01:37 -08001457 return nil
manikkaraj k9eb6cac2019-05-09 12:32:03 -04001458}
1459
Rohan Agrawalda5e0b22020-05-20 11:10:26 +00001460// UpdatePmConfig updates the pm metrics.
Neha Sharma96b7bf22020-06-15 10:37:32 +00001461func (dh *DeviceHandler) UpdatePmConfig(ctx context.Context, pmConfigs *voltha.PmConfigs) {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001462 logger.Infow(ctx, "update-pm-configs", log.Fields{"device-id": dh.device.Id, "pm-configs": pmConfigs})
Rohan Agrawalda5e0b22020-05-20 11:10:26 +00001463
1464 if pmConfigs.DefaultFreq != dh.metrics.ToPmConfigs().DefaultFreq {
1465 dh.metrics.UpdateFrequency(pmConfigs.DefaultFreq)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001466 logger.Debugf(ctx, "frequency-updated")
Rohan Agrawalda5e0b22020-05-20 11:10:26 +00001467 }
1468
Kent Hagermane6ff1012020-07-14 15:07:53 -04001469 if !pmConfigs.Grouped {
Rohan Agrawalda5e0b22020-05-20 11:10:26 +00001470 metrics := dh.metrics.GetSubscriberMetrics()
1471 for _, m := range pmConfigs.Metrics {
1472 metrics[m.Name].Enabled = m.Enabled
1473
1474 }
1475 }
1476}
1477
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001478//UpdateFlowsIncrementally updates the device flow
npujarec5762e2020-01-01 14:08:48 +05301479func (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 +00001480 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 +01001481
Girish Gowdra491a9c62021-01-06 16:43:07 -08001482 var err error
Andrea Campanellac63bba92020-03-10 17:01:04 +01001483 var errorsList []error
1484
Girish Gowdru0c588b22019-04-23 23:24:56 -04001485 if flows != nil {
Manjunath Vanarajulu28c3e822019-05-16 11:14:28 -04001486 for _, flow := range flows.ToRemove.Items {
Girish Gowdrafb3d6102020-10-16 16:32:36 -07001487 ponIf := dh.getPonIfFromFlow(flow)
Girish Gowdracefae192020-03-19 18:14:10 -07001488
Neha Sharma96b7bf22020-06-15 10:37:32 +00001489 logger.Debugw(ctx, "removing-flow",
Shrey Baid807a2a02020-04-09 12:52:45 +05301490 log.Fields{"device-id": device.Id,
Girish Gowdra9602eb42020-09-09 15:50:39 -07001491 "ponIf": ponIf,
Shrey Baid807a2a02020-04-09 12:52:45 +05301492 "flowToRemove": flow})
Girish Gowdra491a9c62021-01-06 16:43:07 -08001493 if flow_utils.HasGroup(flow) {
1494 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, flow, nil, McastFlowOrGroupRemove)
1495 } else {
1496 err = dh.flowMgr[ponIf].RouteFlowToOnuChannel(ctx, flow, false, nil)
1497 }
Girish Gowdracefae192020-03-19 18:14:10 -07001498 if err != nil {
1499 errorsList = append(errorsList, err)
1500 }
Manjunath Vanarajulu28c3e822019-05-16 11:14:28 -04001501 }
Girish Gowdra3d633032019-12-10 16:37:05 +05301502
1503 for _, flow := range flows.ToAdd.Items {
Girish Gowdrafb3d6102020-10-16 16:32:36 -07001504 ponIf := dh.getPonIfFromFlow(flow)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001505 logger.Debugw(ctx, "adding-flow",
Shrey Baid807a2a02020-04-09 12:52:45 +05301506 log.Fields{"device-id": device.Id,
Girish Gowdra9602eb42020-09-09 15:50:39 -07001507 "ponIf": ponIf,
Shrey Baid807a2a02020-04-09 12:52:45 +05301508 "flowToAdd": flow})
Girish Gowdra491a9c62021-01-06 16:43:07 -08001509 if flow_utils.HasGroup(flow) {
1510 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, flow, nil, McastFlowOrGroupAdd)
1511 } else {
1512 err = dh.flowMgr[ponIf].RouteFlowToOnuChannel(ctx, flow, true, flowMetadata)
1513 }
Andrea Campanellac63bba92020-03-10 17:01:04 +01001514 if err != nil {
1515 errorsList = append(errorsList, err)
1516 }
Girish Gowdra3d633032019-12-10 16:37:05 +05301517 }
Girish Gowdru0c588b22019-04-23 23:24:56 -04001518 }
Esin Karamanccb714b2019-11-29 15:02:06 +00001519
Girish Gowdracefae192020-03-19 18:14:10 -07001520 // 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 +00001521 if groups != nil {
1522 for _, group := range groups.ToAdd.Items {
Girish Gowdra491a9c62021-01-06 16:43:07 -08001523 // err = dh.groupMgr.AddGroup(ctx, group)
1524 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, nil, group, McastFlowOrGroupAdd)
Andrea Campanellac63bba92020-03-10 17:01:04 +01001525 if err != nil {
1526 errorsList = append(errorsList, err)
1527 }
Esin Karamanccb714b2019-11-29 15:02:06 +00001528 }
1529 for _, group := range groups.ToUpdate.Items {
Girish Gowdra491a9c62021-01-06 16:43:07 -08001530 // err = dh.groupMgr.ModifyGroup(ctx, group)
1531 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, nil, group, McastFlowOrGroupModify)
Andrea Campanellac63bba92020-03-10 17:01:04 +01001532 if err != nil {
1533 errorsList = append(errorsList, err)
1534 }
Esin Karamanccb714b2019-11-29 15:02:06 +00001535 }
Esin Karamand519bbf2020-07-01 11:16:03 +00001536 for _, group := range groups.ToRemove.Items {
Girish Gowdra491a9c62021-01-06 16:43:07 -08001537 // err = dh.groupMgr.DeleteGroup(ctx, group)
1538 err = dh.RouteMcastFlowOrGroupMsgToChannel(ctx, nil, group, McastFlowOrGroupRemove)
Esin Karamand519bbf2020-07-01 11:16:03 +00001539 if err != nil {
1540 errorsList = append(errorsList, err)
1541 }
Esin Karamanccb714b2019-11-29 15:02:06 +00001542 }
1543 }
Andrea Campanellac63bba92020-03-10 17:01:04 +01001544 if len(errorsList) > 0 {
1545 return fmt.Errorf("errors-installing-flows-groups, errors:%v", errorsList)
1546 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001547 logger.Debugw(ctx, "updated-flows-incrementally-successfully", log.Fields{"device-id": dh.device.Id})
Girish Gowdru0c588b22019-04-23 23:24:56 -04001548 return nil
manikkaraj kbf256be2019-03-25 00:13:48 +05301549}
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001550
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001551//DisableDevice disables the given device
1552//It marks the following for the given device:
1553//Device-Handler Admin-State : down
1554//Device Port-State: UNKNOWN
1555//Device Oper-State: UNKNOWN
Neha Sharma96b7bf22020-06-15 10:37:32 +00001556func (dh *DeviceHandler) DisableDevice(ctx context.Context, device *voltha.Device) error {
Chaitrashree G S44124192019-08-07 20:21:36 -04001557 /* On device disable ,admin state update has to be done prior sending request to agent since
1558 the indication thread may processes invalid indications of ONU and OLT*/
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001559 if dh.Client != nil {
Neha Sharma8f4e4322020-08-06 10:51:53 +00001560 if _, err := dh.Client.DisableOlt(log.WithSpanFromContext(context.Background(), ctx), new(oop.Empty)); err != nil {
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001561 if e, ok := status.FromError(err); ok && e.Code() == codes.Internal {
Girish Kumarf26e4882020-03-05 06:49:10 +00001562 return olterrors.NewErrAdapter("olt-disable-failed", log.Fields{"device-id": device.Id}, err)
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001563 }
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001564 }
Chaitrashree G S44124192019-08-07 20:21:36 -04001565 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001566 logger.Debugw(ctx, "olt-disabled", log.Fields{"device-id": device.Id})
Chaitrashree G S44124192019-08-07 20:21:36 -04001567 /* Discovered ONUs entries need to be cleared , since on device disable the child devices goes to
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001568 UNREACHABLE state which needs to be configured again*/
Naga Manjunatha8dc9372019-10-31 23:01:18 +05301569
1570 dh.discOnus = sync.Map{}
1571 dh.onus = sync.Map{}
1572
Thomas Lee S85f37312020-04-03 17:06:12 +05301573 //stopping the stats collector
1574 dh.stopCollector <- true
1575
Neha Sharma96b7bf22020-06-15 10:37:32 +00001576 go dh.notifyChildDevices(ctx, "unreachable")
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001577 cloned := proto.Clone(device).(*voltha.Device)
Thomas Lee S985938d2020-05-04 11:40:41 +05301578 //Update device Admin state
1579 dh.device = cloned
kdarapu1afeceb2020-02-12 01:38:09 -05001580 // 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 +00001581 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 -04001582 return olterrors.NewErrAdapter("ports-state-update-failed", log.Fields{"device-id": device.Id}, err)
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001583 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001584 logger.Debugw(ctx, "disable-device-end", log.Fields{"device-id": device.Id})
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001585 return nil
1586}
1587
Neha Sharma96b7bf22020-06-15 10:37:32 +00001588func (dh *DeviceHandler) notifyChildDevices(ctx context.Context, state string) {
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001589 // Update onu state as unreachable in onu adapter
1590 onuInd := oop.OnuIndication{}
Abhilash Laxmeshwarf9942e92020-01-07 15:32:44 +05301591 onuInd.OperState = state
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001592 //get the child device for the parent device
Neha Sharma8f4e4322020-08-06 10:51:53 +00001593 onuDevices, err := dh.coreProxy.GetChildDevices(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id)
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001594 if err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001595 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 -04001596 }
1597 if onuDevices != nil {
1598 for _, onuDevice := range onuDevices.Items {
Neha Sharma8f4e4322020-08-06 10:51:53 +00001599 err := dh.AdapterProxy.SendInterAdapterMessage(log.WithSpanFromContext(context.TODO(), ctx), &onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001600 dh.openOLT.config.Topic, onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001601 if err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001602 logger.Errorw(ctx, "failed-to-send-inter-adapter-message", log.Fields{"OnuInd": onuInd,
serkant.uluderya4aff1862020-09-17 23:35:26 +03001603 "From Adapter": dh.openOLT.config.Topic, "DeviceType": onuDevice.Type, "device-id": onuDevice.Id})
Chaitrashree G S3b4c0352019-09-09 20:59:29 -04001604 }
1605
1606 }
1607 }
1608
1609}
1610
Girish Gowdru6a80bbd2019-07-02 07:36:09 -07001611//ReenableDevice re-enables the olt device after disable
1612//It marks the following for the given device:
1613//Device-Handler Admin-State : up
1614//Device Port-State: ACTIVE
1615//Device Oper-State: ACTIVE
Neha Sharma96b7bf22020-06-15 10:37:32 +00001616func (dh *DeviceHandler) ReenableDevice(ctx context.Context, device *voltha.Device) error {
Neha Sharma8f4e4322020-08-06 10:51:53 +00001617 if _, err := dh.Client.ReenableOlt(log.WithSpanFromContext(context.Background(), ctx), new(oop.Empty)); err != nil {
Abhilash Laxmeshwar5b302e12020-01-09 15:15:14 +05301618 if e, ok := status.FromError(err); ok && e.Code() == codes.Internal {
Girish Kumarf26e4882020-03-05 06:49:10 +00001619 return olterrors.NewErrAdapter("olt-reenable-failed", log.Fields{"device-id": dh.device.Id}, err)
Abhilash Laxmeshwar5b302e12020-01-09 15:15:14 +05301620 }
1621 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001622 logger.Debug(ctx, "olt-reenabled")
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001623
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001624 // Update the all ports state on that device to enable
kesavand39e0aa32020-01-28 20:58:50 -05001625
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001626 ports, err := dh.coreProxy.ListDevicePorts(ctx, device.Id)
1627 if err != nil {
divyadesai3af43e12020-08-18 07:10:54 +00001628 return olterrors.NewErrAdapter("list-ports-failed", log.Fields{"device-id": device.Id}, err)
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001629 }
1630 if err := dh.disableAdminDownPorts(ctx, ports); err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001631 return olterrors.NewErrAdapter("port-status-update-failed-after-olt-reenable", log.Fields{"device": device}, err)
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001632 }
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001633 //Update the device oper status as ACTIVE
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001634 device.OperStatus = voltha.OperStatus_ACTIVE
1635 dh.device = device
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001636
Neha Sharma8f4e4322020-08-06 10:51:53 +00001637 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 +05301638 return olterrors.NewErrAdapter("state-update-failed", log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -08001639 "device-id": device.Id,
Kent Hagermanf1db18b2020-07-08 13:38:15 -04001640 "connect-status": device.ConnectStatus,
1641 "oper-status": device.OperStatus}, err)
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001642 }
kesavand39e0aa32020-01-28 20:58:50 -05001643
Neha Sharma96b7bf22020-06-15 10:37:32 +00001644 logger.Debugw(ctx, "reenabledevice-end", log.Fields{"device-id": device.Id})
Girish Gowdru5ba46c92019-04-25 05:00:05 -04001645
1646 return nil
1647}
manikkaraj k9eb6cac2019-05-09 12:32:03 -04001648
npujarec5762e2020-01-01 14:08:48 +05301649func (dh *DeviceHandler) clearUNIData(ctx context.Context, onu *rsrcMgr.OnuGemInfo) error {
Devmalya Paul495b94a2019-08-27 19:42:00 -04001650 var uniID uint32
1651 var err error
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +05301652 for _, port := range onu.UniPorts {
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001653 uniID = UniIDFromPortNum(port)
Neha Sharma96b7bf22020-06-15 10:37:32 +00001654 logger.Debugw(ctx, "clearing-resource-data-for-uni-port", log.Fields{"port": port, "uni-id": uniID})
A R Karthick1f85b802019-10-11 05:06:05 +00001655 /* Delete tech-profile instance from the KV store */
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001656 if err = dh.flowMgr[onu.IntfID].DeleteTechProfileInstances(ctx, onu.IntfID, onu.OnuID, uniID); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001657 logger.Debugw(ctx, "failed-to-remove-tech-profile-instance-for-onu", log.Fields{"onu-id": onu.OnuID})
Devmalya Paul495b94a2019-08-27 19:42:00 -04001658 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001659 logger.Debugw(ctx, "deleted-tech-profile-instance-for-onu", log.Fields{"onu-id": onu.OnuID})
npujarec5762e2020-01-01 14:08:48 +05301660 tpIDList := dh.resourceMgr.GetTechProfileIDForOnu(ctx, onu.IntfID, onu.OnuID, uniID)
Gamze Abakafee36392019-10-03 11:17:24 +00001661 for _, tpID := range tpIDList {
npujarec5762e2020-01-01 14:08:48 +05301662 if err = dh.resourceMgr.RemoveMeterIDForOnu(ctx, "upstream", onu.IntfID, onu.OnuID, uniID, tpID); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001663 logger.Debugw(ctx, "failed-to-remove-meter-id-for-onu-upstream", log.Fields{"onu-id": onu.OnuID})
Gamze Abakafee36392019-10-03 11:17:24 +00001664 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001665 logger.Debugw(ctx, "removed-meter-id-for-onu-upstream", log.Fields{"onu-id": onu.OnuID})
npujarec5762e2020-01-01 14:08:48 +05301666 if err = dh.resourceMgr.RemoveMeterIDForOnu(ctx, "downstream", onu.IntfID, onu.OnuID, uniID, tpID); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001667 logger.Debugw(ctx, "failed-to-remove-meter-id-for-onu-downstream", log.Fields{"onu-id": onu.OnuID})
Gamze Abakafee36392019-10-03 11:17:24 +00001668 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001669 logger.Debugw(ctx, "removed-meter-id-for-onu-downstream", log.Fields{"onu-id": onu.OnuID})
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +05301670 }
npujarec5762e2020-01-01 14:08:48 +05301671 dh.resourceMgr.FreePONResourcesForONU(ctx, onu.IntfID, onu.OnuID, uniID)
1672 if err = dh.resourceMgr.RemoveTechProfileIDsForOnu(ctx, onu.IntfID, onu.OnuID, uniID); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001673 logger.Debugw(ctx, "failed-to-remove-tech-profile-id-for-onu", log.Fields{"onu-id": onu.OnuID})
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +05301674 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001675 logger.Debugw(ctx, "removed-tech-profile-id-for-onu", log.Fields{"onu-id": onu.OnuID})
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001676 if err = dh.resourceMgr.DeletePacketInGemPortForOnu(ctx, onu.IntfID, onu.OnuID, port); err != nil {
Neha Sharma96b7bf22020-06-15 10:37:32 +00001677 logger.Debugw(ctx, "failed-to-remove-gemport-pkt-in", log.Fields{"intfid": onu.IntfID, "onuid": onu.OnuID, "uniId": uniID})
A R Karthick1f85b802019-10-11 05:06:05 +00001678 }
Girish Gowdraa09aeab2020-09-14 16:30:52 -07001679 if err = dh.resourceMgr.RemoveAllFlowsForIntfOnuUniKey(ctx, onu.IntfID, int32(onu.OnuID), int32(uniID)); err != nil {
1680 logger.Debugw(ctx, "failed-to-remove-flow-for", log.Fields{"intfid": onu.IntfID, "onuid": onu.OnuID, "uniId": uniID})
1681 }
Devmalya Paul495b94a2019-08-27 19:42:00 -04001682 }
1683 return nil
1684}
1685
npujarec5762e2020-01-01 14:08:48 +05301686func (dh *DeviceHandler) clearNNIData(ctx context.Context) error {
Devmalya Paul495b94a2019-08-27 19:42:00 -04001687 nniUniID := -1
1688 nniOnuID := -1
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +05301689
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001690 if dh.resourceMgr == nil {
Thomas Lee S985938d2020-05-04 11:40:41 +05301691 return olterrors.NewErrNotFound("resource-manager", log.Fields{"device-id": dh.device.Id}, nil)
Serkant Uluderya89ff40c2019-10-17 16:02:25 -07001692 }
Devmalya Paul495b94a2019-08-27 19:42:00 -04001693 //Free the flow-ids for the NNI port
npujarec5762e2020-01-01 14:08:48 +05301694 nni, err := dh.resourceMgr.GetNNIFromKVStore(ctx)
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +05301695 if err != nil {
Girish Kumarf26e4882020-03-05 06:49:10 +00001696 return olterrors.NewErrPersistence("get", "nni", 0, nil, err)
Devmalya Paul495b94a2019-08-27 19:42:00 -04001697 }
Neha Sharma96b7bf22020-06-15 10:37:32 +00001698 logger.Debugw(ctx, "nni-", log.Fields{"nni": nni})
Abhilash Laxmeshwar