blob: 22f08f86e1d3ce8a9143e93bf9b403bff951e0c6 [file] [log] [blame]
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001/*
2 * Copyright 2020-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 */
16
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +000017//Package core provides the utility for onu devices, flows and statistics
18package core
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000019
20import (
21 "context"
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000022 "errors"
23 "fmt"
Holger Hildebrandt24d51952020-05-04 14:03:42 +000024 "strconv"
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000025 "sync"
26 "time"
27
khenaidoo7d3c5582021-08-11 18:09:44 -040028 "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/config"
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +000029 "github.com/opencord/voltha-protos/v5/go/openolt"
khenaidoo7d3c5582021-08-11 18:09:44 -040030 "github.com/opencord/voltha-protos/v5/go/tech_profile"
mpagenko1f8e8822021-06-25 14:10:21 +000031
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000032 "github.com/gogo/protobuf/proto"
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000033 "github.com/looplab/fsm"
Holger Hildebrandt9ac0d0f2020-05-13 11:22:02 +000034 me "github.com/opencord/omci-lib-go/generated"
khenaidoo7d3c5582021-08-11 18:09:44 -040035 "github.com/opencord/voltha-lib-go/v7/pkg/db"
36 "github.com/opencord/voltha-lib-go/v7/pkg/events/eventif"
37 flow "github.com/opencord/voltha-lib-go/v7/pkg/flows"
38 vgrpc "github.com/opencord/voltha-lib-go/v7/pkg/grpc"
39 "github.com/opencord/voltha-lib-go/v7/pkg/log"
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +000040 almgr "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/almgr"
41 avcfg "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/avcfg"
42 cmn "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/common"
43 mib "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/mib"
44 otst "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/omcitst"
45 pmmgr "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/pmmgr"
46 "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/swupg"
47 uniprt "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/uniprt"
khenaidoo7d3c5582021-08-11 18:09:44 -040048 vc "github.com/opencord/voltha-protos/v5/go/common"
49 "github.com/opencord/voltha-protos/v5/go/extension"
50 ic "github.com/opencord/voltha-protos/v5/go/inter_container"
51 of "github.com/opencord/voltha-protos/v5/go/openflow_13"
52 oop "github.com/opencord/voltha-protos/v5/go/openolt"
53 "github.com/opencord/voltha-protos/v5/go/voltha"
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000054)
55
mpagenko38662d02021-08-11 09:45:19 +000056// Constants for timeouts
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000057const (
mpagenko38662d02021-08-11 09:45:19 +000058 cTimeOutRemoveUpgrade = 1 //for usage in seconds
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000059)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +000060
mpagenko1cc3cb42020-07-27 15:24:38 +000061const (
62 // events of Device FSM
63 devEvDeviceInit = "devEvDeviceInit"
64 devEvGrpcConnected = "devEvGrpcConnected"
65 devEvGrpcDisconnected = "devEvGrpcDisconnected"
66 devEvDeviceUpInd = "devEvDeviceUpInd"
67 devEvDeviceDownInd = "devEvDeviceDownInd"
68)
69const (
70 // states of Device FSM
71 devStNull = "devStNull"
72 devStDown = "devStDown"
73 devStInit = "devStInit"
74 devStConnected = "devStConnected"
75 devStUp = "devStUp"
76)
77
Holger Hildebrandt24d51952020-05-04 14:03:42 +000078//Event category and subcategory definitions - same as defiend for OLT in eventmgr.go - should be done more centrally
79const (
Himani Chawla4d908332020-08-31 12:30:20 +053080 pon = voltha.EventSubCategory_PON
81 //olt = voltha.EventSubCategory_OLT
82 //ont = voltha.EventSubCategory_ONT
83 //onu = voltha.EventSubCategory_ONU
84 //nni = voltha.EventSubCategory_NNI
85 //service = voltha.EventCategory_SERVICE
86 //security = voltha.EventCategory_SECURITY
87 equipment = voltha.EventCategory_EQUIPMENT
88 //processing = voltha.EventCategory_PROCESSING
89 //environment = voltha.EventCategory_ENVIRONMENT
90 //communication = voltha.EventCategory_COMMUNICATION
Holger Hildebrandt24d51952020-05-04 14:03:42 +000091)
92
93const (
94 cEventObjectType = "ONU"
95)
96const (
97 cOnuActivatedEvent = "ONU_ACTIVATED"
98)
99
mpagenkof1fc3862021-02-16 10:09:52 +0000100type omciIdleCheckStruct struct {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000101 omciIdleCheckFunc func(*deviceHandler, context.Context, cmn.UsedOmciConfigFsms, string) bool
mpagenkof1fc3862021-02-16 10:09:52 +0000102 omciIdleState string
Holger Hildebrandt10d98192021-01-27 15:29:31 +0000103}
104
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000105var fsmOmciIdleStateFuncMap = map[cmn.UsedOmciConfigFsms]omciIdleCheckStruct{
106 cmn.CUploadFsm: {(*deviceHandler).isFsmInOmciIdleStateDefault, mib.CMibUlFsmIdleState},
107 cmn.CDownloadFsm: {(*deviceHandler).isFsmInOmciIdleStateDefault, mib.CMibDlFsmIdleState},
108 cmn.CUniLockFsm: {(*deviceHandler).isFsmInOmciIdleStateDefault, uniprt.CUniFsmIdleState},
109 cmn.CUniUnLockFsm: {(*deviceHandler).isFsmInOmciIdleStateDefault, uniprt.CUniFsmIdleState},
110 cmn.CAniConfigFsm: {(*deviceHandler).isAniConfigFsmInOmciIdleState, avcfg.CAniFsmIdleState},
111 cmn.CUniVlanConfigFsm: {(*deviceHandler).isUniVlanConfigFsmInOmciIdleState, avcfg.CVlanFsmIdleState},
112 cmn.CL2PmFsm: {(*deviceHandler).isFsmInOmciIdleStateDefault, pmmgr.CL2PmFsmIdleState},
113 cmn.COnuUpgradeFsm: {(*deviceHandler).isFsmInOmciIdleStateDefault, swupg.COnuUpgradeFsmIdleState},
Holger Hildebrandt3a644642020-12-02 09:46:18 +0000114}
115
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000116const (
117 cNoReconciling = iota
118 cOnuConfigReconciling
119 cSkipOnuConfigReconciling
120)
121
Himani Chawla6d2ae152020-09-02 13:11:20 +0530122//deviceHandler will interact with the ONU ? device.
123type deviceHandler struct {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000124 DeviceID string
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000125 DeviceType string
126 adminState string
127 device *voltha.Device
128 logicalDeviceID string
129 ProxyAddressID string
130 ProxyAddressType string
Himani Chawla4d908332020-08-31 12:30:20 +0530131 parentID string
Holger Hildebrandt24d51952020-05-04 14:03:42 +0000132 ponPortNumber uint32
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000133
khenaidoo7d3c5582021-08-11 18:09:44 -0400134 coreClient *vgrpc.Client
135 EventProxy eventif.EventProxy
Holger Hildebrandtc54939a2020-06-17 08:14:27 +0000136
Girish Gowdra5a7c4922021-01-22 18:33:41 -0800137 pmConfigs *voltha.PmConfigs
khenaidoo7d3c5582021-08-11 18:09:44 -0400138 config *config.AdapterFlags
Girish Gowdrae09a6202021-01-12 18:10:59 -0800139
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000140 pOpenOnuAc *OpenONUAC
141 pDeviceStateFsm *fsm.FSM
Himani Chawla4d908332020-08-31 12:30:20 +0530142 //pPonPort *voltha.Port
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000143 deviceEntrySet chan bool //channel for DeviceEntry set event
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000144 pOnuOmciDevice *mib.OnuDeviceEntry
145 pOnuTP *avcfg.OnuUniTechProf
146 pOnuMetricsMgr *pmmgr.OnuMetricsManager
147 pAlarmMgr *almgr.OnuAlarmManager
148 pSelfTestHdlr *otst.SelfTestControlBlock
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000149 exitChannel chan int
150 lockDevice sync.RWMutex
151 pOnuIndication *oop.OnuIndication
152 deviceReason uint8
153 mutexDeviceReason sync.RWMutex
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000154 pLockStateFsm *uniprt.LockStateFsm
155 pUnlockStateFsm *uniprt.LockStateFsm
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000156
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000157 //flowMgr *OpenOltFlowMgr
158 //eventMgr *OpenOltEventMgr
159 //resourceMgr *rsrcMgr.OpenOltResourceMgr
160
161 //discOnus sync.Map
162 //onus sync.Map
163 //portStats *OpenOltStatisticsMgr
Holger Hildebrandtff05b682021-03-16 15:02:05 +0000164 collectorIsRunning bool
165 mutexCollectorFlag sync.RWMutex
166 stopCollector chan bool
167 alarmManagerIsRunning bool
168 mutextAlarmManagerFlag sync.RWMutex
169 stopAlarmManager chan bool
170 stopHeartbeatCheck chan bool
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000171 uniEntityMap cmn.OnuUniPortMap
Holger Hildebrandtff05b682021-03-16 15:02:05 +0000172 mutexKvStoreContext sync.Mutex
173 lockVlanConfig sync.RWMutex
mpagenkobc4170a2021-08-17 16:42:10 +0000174 lockVlanAdd sync.RWMutex
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000175 UniVlanConfigFsmMap map[uint8]*avcfg.UniVlanConfigFsm
Holger Hildebrandtff05b682021-03-16 15:02:05 +0000176 lockUpgradeFsm sync.RWMutex
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000177 pOnuUpradeFsm *swupg.OnuUpgradeFsm
Holger Hildebrandtff05b682021-03-16 15:02:05 +0000178 reconciling uint8
179 mutexReconcilingFlag sync.RWMutex
180 chReconcilingFinished chan bool //channel to indicate that reconciling has been finished
Holger Hildebrandt0da7e6f2021-05-12 13:08:43 +0000181 mutexReadyForOmciConfig sync.RWMutex
182 readyForOmciConfig bool
Holger Hildebrandtff05b682021-03-16 15:02:05 +0000183 deletionInProgress bool
184 mutexDeletionInProgressFlag sync.RWMutex
mpagenko38662d02021-08-11 09:45:19 +0000185 pLastUpgradeImageState *voltha.ImageState
186 upgradeFsmChan chan struct{}
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000187}
188
Himani Chawla6d2ae152020-09-02 13:11:20 +0530189//newDeviceHandler creates a new device handler
khenaidoo7d3c5582021-08-11 18:09:44 -0400190func newDeviceHandler(ctx context.Context, cc *vgrpc.Client, ep eventif.EventProxy, device *voltha.Device, adapter *OpenONUAC) *deviceHandler {
Himani Chawla6d2ae152020-09-02 13:11:20 +0530191 var dh deviceHandler
khenaidoo7d3c5582021-08-11 18:09:44 -0400192 dh.coreClient = cc
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000193 dh.EventProxy = ep
khenaidoo7d3c5582021-08-11 18:09:44 -0400194 dh.config = adapter.config
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000195 cloned := (proto.Clone(device)).(*voltha.Device)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000196 dh.DeviceID = cloned.Id
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000197 dh.DeviceType = cloned.Type
198 dh.adminState = "up"
199 dh.device = cloned
200 dh.pOpenOnuAc = adapter
201 dh.exitChannel = make(chan int, 1)
202 dh.lockDevice = sync.RWMutex{}
mpagenko3af1f032020-06-10 08:53:41 +0000203 dh.deviceEntrySet = make(chan bool, 1)
Holger Hildebrandt10d98192021-01-27 15:29:31 +0000204 dh.collectorIsRunning = false
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000205 dh.stopCollector = make(chan bool, 2)
Himani Chawla4c1d4c72021-02-18 12:14:31 +0530206 dh.alarmManagerIsRunning = false
Himani Chawlaac1f5ad2021-02-04 21:21:54 +0530207 dh.stopAlarmManager = make(chan bool, 2)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000208 dh.stopHeartbeatCheck = make(chan bool, 2)
209 //dh.metrics = pmmetrics.NewPmMetrics(cloned.Id, pmmetrics.Frequency(150), pmmetrics.FrequencyOverride(false), pmmetrics.Grouped(false), pmmetrics.Metrics(pmNames))
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000210 //TODO initialize the support classes.
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000211 dh.uniEntityMap = make(map[uint32]*cmn.OnuUniPort)
mpagenkof1fc3862021-02-16 10:09:52 +0000212 dh.lockVlanConfig = sync.RWMutex{}
mpagenkobc4170a2021-08-17 16:42:10 +0000213 dh.lockVlanAdd = sync.RWMutex{}
mpagenko80622a52021-02-09 16:53:23 +0000214 dh.lockUpgradeFsm = sync.RWMutex{}
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000215 dh.UniVlanConfigFsmMap = make(map[uint8]*avcfg.UniVlanConfigFsm)
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000216 dh.reconciling = cNoReconciling
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +0000217 dh.chReconcilingFinished = make(chan bool)
Holger Hildebrandt0da7e6f2021-05-12 13:08:43 +0000218 dh.readyForOmciConfig = false
Holger Hildebrandtff05b682021-03-16 15:02:05 +0000219 dh.deletionInProgress = false
mpagenko38662d02021-08-11 09:45:19 +0000220 dh.pLastUpgradeImageState = &voltha.ImageState{
221 DownloadState: voltha.ImageState_DOWNLOAD_UNKNOWN,
222 Reason: voltha.ImageState_UNKNOWN_ERROR,
223 ImageState: voltha.ImageState_IMAGE_UNKNOWN,
224 }
225 dh.upgradeFsmChan = make(chan struct{})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000226
Girish Gowdra5a7c4922021-01-22 18:33:41 -0800227 if dh.device.PmConfigs != nil { // can happen after onu adapter restart
228 dh.pmConfigs = cloned.PmConfigs
229 } /* else {
230 // will be populated when onu_metrics_mananger is initialized.
231 }*/
Girish Gowdrae09a6202021-01-12 18:10:59 -0800232
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000233 // Device related state machine
234 dh.pDeviceStateFsm = fsm.NewFSM(
mpagenko1cc3cb42020-07-27 15:24:38 +0000235 devStNull,
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000236 fsm.Events{
mpagenko1cc3cb42020-07-27 15:24:38 +0000237 {Name: devEvDeviceInit, Src: []string{devStNull, devStDown}, Dst: devStInit},
238 {Name: devEvGrpcConnected, Src: []string{devStInit}, Dst: devStConnected},
239 {Name: devEvGrpcDisconnected, Src: []string{devStConnected, devStDown}, Dst: devStInit},
240 {Name: devEvDeviceUpInd, Src: []string{devStConnected, devStDown}, Dst: devStUp},
241 {Name: devEvDeviceDownInd, Src: []string{devStUp}, Dst: devStDown},
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000242 },
243 fsm.Callbacks{
dbainbri4d3a0dc2020-12-02 00:33:42 +0000244 "before_event": func(e *fsm.Event) { dh.logStateChange(ctx, e) },
245 ("before_" + devEvDeviceInit): func(e *fsm.Event) { dh.doStateInit(ctx, e) },
246 ("after_" + devEvDeviceInit): func(e *fsm.Event) { dh.postInit(ctx, e) },
247 ("before_" + devEvGrpcConnected): func(e *fsm.Event) { dh.doStateConnected(ctx, e) },
248 ("before_" + devEvGrpcDisconnected): func(e *fsm.Event) { dh.doStateInit(ctx, e) },
249 ("after_" + devEvGrpcDisconnected): func(e *fsm.Event) { dh.postInit(ctx, e) },
250 ("before_" + devEvDeviceUpInd): func(e *fsm.Event) { dh.doStateUp(ctx, e) },
251 ("before_" + devEvDeviceDownInd): func(e *fsm.Event) { dh.doStateDown(ctx, e) },
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000252 },
253 )
mpagenkoaf801632020-07-03 10:00:42 +0000254
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000255 return &dh
256}
257
Himani Chawla6d2ae152020-09-02 13:11:20 +0530258// start save the device to the data model
259func (dh *deviceHandler) start(ctx context.Context) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000260 logger.Debugw(ctx, "starting-device-handler", log.Fields{"device": dh.device, "device-id": dh.DeviceID})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000261 // Add the initial device to the local model
dbainbri4d3a0dc2020-12-02 00:33:42 +0000262 logger.Debug(ctx, "device-handler-started")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000263}
264
Himani Chawla4d908332020-08-31 12:30:20 +0530265/*
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000266// stop stops the device dh. Not much to do for now
Himani Chawla6d2ae152020-09-02 13:11:20 +0530267func (dh *deviceHandler) stop(ctx context.Context) {
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000268 logger.Debug("stopping-device-handler")
269 dh.exitChannel <- 1
270}
Himani Chawla4d908332020-08-31 12:30:20 +0530271*/
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000272
273// ##########################################################################################
Himani Chawla6d2ae152020-09-02 13:11:20 +0530274// deviceHandler methods that implement the adapters interface requests ##### begin #########
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000275
Girish Gowdrae0140f02021-02-02 16:55:09 -0800276//adoptOrReconcileDevice adopts the ONU device
Himani Chawla6d2ae152020-09-02 13:11:20 +0530277func (dh *deviceHandler) adoptOrReconcileDevice(ctx context.Context, device *voltha.Device) {
khenaidoo7d3c5582021-08-11 18:09:44 -0400278 logger.Debugw(ctx, "adopt_or_reconcile_device", log.Fields{"device-id": device.Id, "Address": device.GetHostAndPort()})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000279
dbainbri4d3a0dc2020-12-02 00:33:42 +0000280 logger.Debugw(ctx, "Device FSM: ", log.Fields{"state": string(dh.pDeviceStateFsm.Current())})
mpagenko1cc3cb42020-07-27 15:24:38 +0000281 if dh.pDeviceStateFsm.Is(devStNull) {
282 if err := dh.pDeviceStateFsm.Event(devEvDeviceInit); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000283 logger.Errorw(ctx, "Device FSM: Can't go to state DeviceInit", log.Fields{"err": err})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000284 }
dbainbri4d3a0dc2020-12-02 00:33:42 +0000285 logger.Debugw(ctx, "Device FSM: ", log.Fields{"state": string(dh.pDeviceStateFsm.Current())})
Girish Gowdraaf0ad632021-01-27 13:00:01 -0800286 // device.PmConfigs is not nil in cases when adapter restarts. We should not re-set the core again.
287 if device.PmConfigs == nil {
Girish Gowdra5a7c4922021-01-22 18:33:41 -0800288 // Now, set the initial PM configuration for that device
khenaidoo7d3c5582021-08-11 18:09:44 -0400289 if err := dh.updatePMConfigInCore(ctx, dh.pmConfigs); err != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000290 logger.Errorw(ctx, "error updating pm config to core", log.Fields{"device-id": dh.DeviceID, "err": err})
Girish Gowdra5a7c4922021-01-22 18:33:41 -0800291 }
Girish Gowdrae09a6202021-01-12 18:10:59 -0800292 }
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000293 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000294 logger.Debugw(ctx, "AdoptOrReconcileDevice: Agent/device init already done", log.Fields{"device-id": device.Id})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000295 }
296
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +0000297}
298
khenaidoo7d3c5582021-08-11 18:09:44 -0400299func (dh *deviceHandler) handleOMCIIndication(ctx context.Context, msg *ic.OmciMessage) error {
mpagenko80622a52021-02-09 16:53:23 +0000300 /* msg print moved symmetrically to omci_cc, if wanted here as additional debug, than perhaps only based on additional debug setting!
Himani Chawla26e555c2020-08-31 12:30:20 +0530301 //assuming omci message content is hex coded!
302 // with restricted output of 16(?) bytes would be ...omciMsg.Message[:16]
dbainbri4d3a0dc2020-12-02 00:33:42 +0000303 logger.Debugw(ctx, "inter-adapter-recv-omci", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000304 "device-id": dh.DeviceID, "RxOmciMessage": hex.EncodeToString(omciMsg.Message)})
mpagenko80622a52021-02-09 16:53:23 +0000305 */
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000306 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Himani Chawla26e555c2020-08-31 12:30:20 +0530307 if pDevEntry != nil {
Holger Hildebrandt2fb70892020-10-28 11:53:18 +0000308 if pDevEntry.PDevOmciCC != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000309 return pDevEntry.PDevOmciCC.ReceiveMessage(log.WithSpanFromContext(context.TODO(), ctx), msg.Message)
Holger Hildebrandt2fb70892020-10-28 11:53:18 +0000310 }
khenaidoo7d3c5582021-08-11 18:09:44 -0400311 logger.Debugw(ctx, "omciCC not ready to receive omci messages - incoming omci message ignored", log.Fields{"rxMsg": msg.Message})
Himani Chawla26e555c2020-08-31 12:30:20 +0530312 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000313 logger.Errorw(ctx, "No valid OnuDevice -aborting", log.Fields{"device-id": dh.DeviceID})
314 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
Himani Chawla26e555c2020-08-31 12:30:20 +0530315}
316
khenaidoo7d3c5582021-08-11 18:09:44 -0400317func (dh *deviceHandler) handleTechProfileDownloadRequest(ctx context.Context, techProfMsg *ic.TechProfileDownloadMessage) error {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000318 logger.Infow(ctx, "tech-profile-download-request", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt80129db2020-11-23 10:49:32 +0000319
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000320 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000321 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000322 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
323 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000324 }
Himani Chawla26e555c2020-08-31 12:30:20 +0530325 if dh.pOnuTP == nil {
326 //should normally not happen ...
dbainbri4d3a0dc2020-12-02 00:33:42 +0000327 logger.Errorw(ctx, "onuTechProf instance not set up for DLMsg request - ignoring request",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000328 log.Fields{"device-id": dh.DeviceID})
329 return fmt.Errorf("techProfile DLMsg request while onuTechProf instance not setup: %s", dh.DeviceID)
Himani Chawla26e555c2020-08-31 12:30:20 +0530330 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000331 if !dh.IsReadyForOmciConfig() {
332 logger.Errorw(ctx, "TechProf-set rejected: improper device state", log.Fields{"device-id": dh.DeviceID,
333 "device-state": dh.GetDeviceReasonString()})
334 return fmt.Errorf("improper device state %s on device %s", dh.GetDeviceReasonString(), dh.DeviceID)
Himani Chawla26e555c2020-08-31 12:30:20 +0530335 }
mpagenkofc4f56e2020-11-04 17:17:49 +0000336 //previous state test here was just this one, now extended for more states to reject the SetRequest:
337 // at least 'mib-downloaded' should be reached for processing of this specific ONU configuration
338 // if (dh.deviceReason == "stopping-openomci") || (dh.deviceReason == "omci-admin-lock")
Himani Chawla26e555c2020-08-31 12:30:20 +0530339
Himani Chawla26e555c2020-08-31 12:30:20 +0530340 // we have to lock access to TechProfile processing based on different messageType calls or
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000341 // even to fast subsequent calls of the same messageType as well as OnuKVStore processing due
342 // to possible concurrent access by flow processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000343 dh.pOnuTP.LockTpProcMutex()
344 defer dh.pOnuTP.UnlockTpProcMutex()
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000345
346 if techProfMsg.UniId > 255 {
347 return fmt.Errorf(fmt.Sprintf("received UniId value exceeds range: %d, device-id: %s",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000348 techProfMsg.UniId, dh.DeviceID))
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000349 }
350 uniID := uint8(techProfMsg.UniId)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000351 tpID, err := cmn.GetTpIDFromTpPath(techProfMsg.TpInstancePath)
Girish Gowdra041dcb32020-11-16 16:54:30 -0800352 if err != nil {
Girish Gowdra50e56422021-06-01 16:46:04 -0700353 logger.Errorw(ctx, "error-parsing-tpid-from-tppath", log.Fields{"err": err, "tp-path": techProfMsg.TpInstancePath})
Girish Gowdra041dcb32020-11-16 16:54:30 -0800354 return err
355 }
Girish Gowdra50e56422021-06-01 16:46:04 -0700356 logger.Debugw(ctx, "unmarshal-techprof-msg-body", log.Fields{"uniID": uniID, "tp-path": techProfMsg.TpInstancePath, "tpID": tpID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000357
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000358 if bTpModify := pDevEntry.UpdateOnuUniTpPath(ctx, uniID, uint8(tpID), techProfMsg.TpInstancePath); bTpModify {
Himani Chawla26e555c2020-08-31 12:30:20 +0530359
Girish Gowdra50e56422021-06-01 16:46:04 -0700360 switch tpInst := techProfMsg.TechTpInstance.(type) {
khenaidoo7d3c5582021-08-11 18:09:44 -0400361 case *ic.TechProfileDownloadMessage_TpInstance:
Girish Gowdra50e56422021-06-01 16:46:04 -0700362 logger.Debugw(ctx, "onu-uni-tp-path-modified", log.Fields{"uniID": uniID, "tp-path": techProfMsg.TpInstancePath, "tpID": tpID})
363 // if there has been some change for some uni TechProfilePath
364 //in order to allow concurrent calls to other dh instances we do not wait for execution here
365 //but doing so we can not indicate problems to the caller (who does what with that then?)
366 //by now we just assume straightforward successful execution
367 //TODO!!! Generally: In this scheme it would be good to have some means to indicate
368 // possible problems to the caller later autonomously
Himani Chawla26e555c2020-08-31 12:30:20 +0530369
Girish Gowdra50e56422021-06-01 16:46:04 -0700370 // deadline context to ensure completion of background routines waited for
371 //20200721: 10s proved to be less in 8*8 ONU test on local vbox machine with debug, might be further adapted
372 deadline := time.Now().Add(dh.pOpenOnuAc.maxTimeoutInterAdapterComm) //allowed run time to finish before execution
373 dctx, cancel := context.WithDeadline(context.Background(), deadline)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000374
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000375 dh.pOnuTP.ResetTpProcessingErrorIndication(uniID, tpID)
Girish Gowdra50e56422021-06-01 16:46:04 -0700376
377 var wg sync.WaitGroup
378 wg.Add(1) // for the 1 go routine to finish
379 // attention: deadline completion check and wg.Done is to be done in both routines
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000380 go dh.pOnuTP.ConfigureUniTp(log.WithSpanFromContext(dctx, ctx), uniID, techProfMsg.TpInstancePath, *tpInst.TpInstance, &wg)
Girish Gowdra50e56422021-06-01 16:46:04 -0700381 dh.waitForCompletion(ctx, cancel, &wg, "TechProfDwld") //wait for background process to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000382 if tpErr := dh.pOnuTP.GetTpProcessingErrorIndication(uniID, tpID); tpErr != nil {
383 logger.Errorw(ctx, "error-processing-tp", log.Fields{"device-id": dh.DeviceID, "err": tpErr, "tp-path": techProfMsg.TpInstancePath})
Girish Gowdra50e56422021-06-01 16:46:04 -0700384 return tpErr
385 }
386 deadline = time.Now().Add(dh.pOpenOnuAc.maxTimeoutInterAdapterComm) //allowed run time to finish before execution
387 dctx2, cancel2 := context.WithDeadline(context.Background(), deadline)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000388 pDevEntry.ResetKvProcessingErrorIndication()
Girish Gowdra50e56422021-06-01 16:46:04 -0700389 wg.Add(1) // for the 1 go routine to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000390 go pDevEntry.UpdateOnuKvStore(log.WithSpanFromContext(dctx2, ctx), &wg)
Girish Gowdra50e56422021-06-01 16:46:04 -0700391 dh.waitForCompletion(ctx, cancel2, &wg, "TechProfDwld") //wait for background process to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000392 if kvErr := pDevEntry.GetKvProcessingErrorIndication(); kvErr != nil {
393 logger.Errorw(ctx, "error-updating-KV", log.Fields{"device-id": dh.DeviceID, "err": kvErr, "tp-path": techProfMsg.TpInstancePath})
Girish Gowdra50e56422021-06-01 16:46:04 -0700394 return kvErr
395 }
396 return nil
397 default:
398 logger.Errorw(ctx, "unsupported-tp-instance-type", log.Fields{"tp-path": techProfMsg.TpInstancePath})
399 return fmt.Errorf("unsupported-tp-instance-type--tp-id-%v", techProfMsg.TpInstancePath)
Mahir Gunyel7f4483a2021-05-06 12:53:43 -0700400 }
Himani Chawla26e555c2020-08-31 12:30:20 +0530401 }
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000402 // no change, nothing really to do - return success
Girish Gowdra50e56422021-06-01 16:46:04 -0700403 logger.Debugw(ctx, "onu-uni-tp-path-not-modified", log.Fields{"uniID": uniID, "tp-path": techProfMsg.TpInstancePath, "tpID": tpID})
Himani Chawla26e555c2020-08-31 12:30:20 +0530404 return nil
405}
406
khenaidoo7d3c5582021-08-11 18:09:44 -0400407func (dh *deviceHandler) handleDeleteGemPortRequest(ctx context.Context, delGemPortMsg *ic.DeleteGemPortMessage) error {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000408 logger.Infow(ctx, "delete-gem-port-request", log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +0530409
410 if dh.pOnuTP == nil {
411 //should normally not happen ...
dbainbri4d3a0dc2020-12-02 00:33:42 +0000412 logger.Warnw(ctx, "onuTechProf instance not set up for DelGem request - ignoring request",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000413 log.Fields{"device-id": dh.DeviceID})
414 return fmt.Errorf("techProfile DelGem request while onuTechProf instance not setup: %s", dh.DeviceID)
Himani Chawla26e555c2020-08-31 12:30:20 +0530415 }
Himani Chawla26e555c2020-08-31 12:30:20 +0530416 //compare TECH_PROFILE_DOWNLOAD_REQUEST
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000417 dh.pOnuTP.LockTpProcMutex()
418 defer dh.pOnuTP.UnlockTpProcMutex()
Himani Chawla26e555c2020-08-31 12:30:20 +0530419
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000420 if delGemPortMsg.UniId > 255 {
421 return fmt.Errorf(fmt.Sprintf("received UniId value exceeds range: %d, device-id: %s",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000422 delGemPortMsg.UniId, dh.DeviceID))
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000423 }
424 uniID := uint8(delGemPortMsg.UniId)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000425 tpID, err := cmn.GetTpIDFromTpPath(delGemPortMsg.TpInstancePath)
Girish Gowdra041dcb32020-11-16 16:54:30 -0800426 if err != nil {
Girish Gowdra50e56422021-06-01 16:46:04 -0700427 logger.Errorw(ctx, "error-extracting-tp-id-from-tp-path", log.Fields{"err": err, "tp-path": delGemPortMsg.TpInstancePath})
Girish Gowdra041dcb32020-11-16 16:54:30 -0800428 return err
429 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000430 logger.Infow(ctx, "delete-gem-port-request", log.Fields{"device-id": dh.DeviceID, "uni-id": uniID, "tpID": tpID, "gem": delGemPortMsg.GemPortId})
mpagenkofc4f56e2020-11-04 17:17:49 +0000431 //a removal of some GemPort would never remove the complete TechProfile entry (done on T-Cont)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000432
Mahir Gunyel9545be22021-07-04 15:53:16 -0700433 return dh.deleteTechProfileResource(ctx, uniID, tpID, delGemPortMsg.TpInstancePath,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000434 avcfg.CResourceGemPort, delGemPortMsg.GemPortId)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000435
Himani Chawla26e555c2020-08-31 12:30:20 +0530436}
437
khenaidoo7d3c5582021-08-11 18:09:44 -0400438func (dh *deviceHandler) handleDeleteTcontRequest(ctx context.Context, delTcontMsg *ic.DeleteTcontMessage) error {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000439 logger.Infow(ctx, "delete-tcont-request", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000440
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000441 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000442 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000443 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
444 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000445 }
Himani Chawla26e555c2020-08-31 12:30:20 +0530446 if dh.pOnuTP == nil {
447 //should normally not happen ...
dbainbri4d3a0dc2020-12-02 00:33:42 +0000448 logger.Warnw(ctx, "onuTechProf instance not set up for DelTcont request - ignoring request",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000449 log.Fields{"device-id": dh.DeviceID})
450 return fmt.Errorf("techProfile DelTcont request while onuTechProf instance not setup: %s", dh.DeviceID)
Himani Chawla26e555c2020-08-31 12:30:20 +0530451 }
452
Himani Chawla26e555c2020-08-31 12:30:20 +0530453 //compare TECH_PROFILE_DOWNLOAD_REQUEST
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000454 dh.pOnuTP.LockTpProcMutex()
455 defer dh.pOnuTP.UnlockTpProcMutex()
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000456
457 if delTcontMsg.UniId > 255 {
458 return fmt.Errorf(fmt.Sprintf("received UniId value exceeds range: %d, device-id: %s",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000459 delTcontMsg.UniId, dh.DeviceID))
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000460 }
461 uniID := uint8(delTcontMsg.UniId)
Girish Gowdra50e56422021-06-01 16:46:04 -0700462 tpPath := delTcontMsg.TpInstancePath
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000463 tpID, err := cmn.GetTpIDFromTpPath(tpPath)
Girish Gowdra041dcb32020-11-16 16:54:30 -0800464 if err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000465 logger.Errorw(ctx, "error-extracting-tp-id-from-tp-path", log.Fields{"err": err, "tp-path": tpPath})
Girish Gowdra041dcb32020-11-16 16:54:30 -0800466 return err
467 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000468 logger.Infow(ctx, "delete-tcont-request", log.Fields{"device-id": dh.DeviceID, "uni-id": uniID, "tpID": tpID, "tcont": delTcontMsg.AllocId})
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000469
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000470 pDevEntry.FreeTcont(ctx, uint16(delTcontMsg.AllocId))
Himani Chawla26e555c2020-08-31 12:30:20 +0530471
Mahir Gunyel9545be22021-07-04 15:53:16 -0700472 return dh.deleteTechProfileResource(ctx, uniID, tpID, delTcontMsg.TpInstancePath,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000473 avcfg.CResourceTcont, delTcontMsg.AllocId)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000474
Mahir Gunyel9545be22021-07-04 15:53:16 -0700475}
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000476
Mahir Gunyel9545be22021-07-04 15:53:16 -0700477func (dh *deviceHandler) deleteTechProfileResource(ctx context.Context,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000478 uniID uint8, tpID uint8, pathString string, resource avcfg.ResourceEntry, entryID uint32) error {
479 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Mahir Gunyel9545be22021-07-04 15:53:16 -0700480 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000481 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
482 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
Himani Chawla26e555c2020-08-31 12:30:20 +0530483 }
Mahir Gunyel9545be22021-07-04 15:53:16 -0700484 var resourceName string
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000485 if avcfg.CResourceGemPort == resource {
Mahir Gunyel9545be22021-07-04 15:53:16 -0700486 resourceName = "Gem"
487 } else {
488 resourceName = "Tcont"
489 }
490
491 // deadline context to ensure completion of background routines waited for
492 deadline := time.Now().Add(dh.pOpenOnuAc.maxTimeoutInterAdapterComm) //allowed run time to finish before execution
493 dctx, cancel := context.WithDeadline(context.Background(), deadline)
494
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000495 dh.pOnuTP.ResetTpProcessingErrorIndication(uniID, tpID)
Mahir Gunyel9545be22021-07-04 15:53:16 -0700496
497 var wg sync.WaitGroup
498 wg.Add(1) // for the 1 go routine to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000499 go dh.pOnuTP.DeleteTpResource(log.WithSpanFromContext(dctx, ctx), uniID, tpID, pathString,
Mahir Gunyel9545be22021-07-04 15:53:16 -0700500 resource, entryID, &wg)
501 dh.waitForCompletion(ctx, cancel, &wg, resourceName+"Delete") //wait for background process to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000502 if err := dh.pOnuTP.GetTpProcessingErrorIndication(uniID, tpID); err != nil {
503 logger.Errorw(ctx, err.Error(), log.Fields{"device-id": dh.DeviceID})
Mahir Gunyel9545be22021-07-04 15:53:16 -0700504 return err
505 }
506
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000507 if dh.pOnuTP.IsTechProfileConfigCleared(ctx, uniID, tpID) {
508 logger.Debugw(ctx, "techProfile-config-cleared", log.Fields{"device-id": dh.DeviceID, "uni-id": uniID, "tpID": tpID})
509 if bTpModify := pDevEntry.UpdateOnuUniTpPath(ctx, uniID, tpID, ""); bTpModify {
510 pDevEntry.ResetKvProcessingErrorIndication()
Mahir Gunyel9545be22021-07-04 15:53:16 -0700511 var wg2 sync.WaitGroup
512 dctx2, cancel2 := context.WithDeadline(context.Background(), deadline)
513 wg2.Add(1)
514 // Removal of the gem id mapping represents the removal of the tech profile
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000515 logger.Infow(ctx, "remove-techProfile-indication-in-kv", log.Fields{"device-id": dh.DeviceID, "uni-id": uniID, "tpID": tpID})
516 go pDevEntry.UpdateOnuKvStore(log.WithSpanFromContext(dctx2, ctx), &wg2)
Mahir Gunyel9545be22021-07-04 15:53:16 -0700517 dh.waitForCompletion(ctx, cancel2, &wg2, "TechProfileDeleteOn"+resourceName) //wait for background process to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000518 if err := pDevEntry.GetKvProcessingErrorIndication(); err != nil {
519 logger.Errorw(ctx, err.Error(), log.Fields{"device-id": dh.DeviceID})
Mahir Gunyel9545be22021-07-04 15:53:16 -0700520 return err
521 }
522 }
523 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000524 logger.Debugw(ctx, "delete-tech-profile-resource-completed", log.Fields{"device-id": dh.DeviceID,
Mahir Gunyel9545be22021-07-04 15:53:16 -0700525 "uni-id": uniID, "tpID": tpID, "resource-type": resourceName, "resource-id": entryID})
Himani Chawla26e555c2020-08-31 12:30:20 +0530526 return nil
527}
528
mpagenkodff5dda2020-08-28 11:52:01 +0000529//FlowUpdateIncremental removes and/or adds the flow changes on a given device
dbainbri4d3a0dc2020-12-02 00:33:42 +0000530func (dh *deviceHandler) FlowUpdateIncremental(ctx context.Context,
khenaidoo7d3c5582021-08-11 18:09:44 -0400531 apOfFlowChanges *of.FlowChanges,
532 apOfGroupChanges *of.FlowGroupChanges, apFlowMetaData *voltha.FlowMetadata) error {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000533 logger.Debugw(ctx, "FlowUpdateIncremental started", log.Fields{"device-id": dh.DeviceID, "metadata": apFlowMetaData})
mpagenko01e726e2020-10-23 09:45:29 +0000534 var retError error = nil
535 //Remove flows (always remove flows first - remove old and add new with same cookie may be part of the same request)
mpagenkodff5dda2020-08-28 11:52:01 +0000536 if apOfFlowChanges.ToRemove != nil {
537 for _, flowItem := range apOfFlowChanges.ToRemove.Items {
mpagenkodff5dda2020-08-28 11:52:01 +0000538 if flowItem.GetCookie() == 0 {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000539 logger.Warnw(ctx, "flow-remove no cookie: ignore and continuing on checking further flows", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000540 "device-id": dh.DeviceID})
541 retError = fmt.Errorf("flow-remove no cookie, device-id %s", dh.DeviceID)
mpagenkodff5dda2020-08-28 11:52:01 +0000542 continue
543 }
544 flowInPort := flow.GetInPort(flowItem)
545 if flowInPort == uint32(of.OfpPortNo_OFPP_INVALID) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000546 logger.Warnw(ctx, "flow-remove inPort invalid: ignore and continuing on checking further flows", log.Fields{"device-id": dh.DeviceID})
547 retError = fmt.Errorf("flow-remove inPort invalid, device-id %s", dh.DeviceID)
mpagenko01e726e2020-10-23 09:45:29 +0000548 continue
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000549 //return fmt.Errorf("flow inPort invalid: %s", dh.DeviceID)
mpagenkodff5dda2020-08-28 11:52:01 +0000550 } else if flowInPort == dh.ponPortNumber {
mpagenko01e726e2020-10-23 09:45:29 +0000551 //this is some downstream flow, not regarded as error, just ignored
dbainbri4d3a0dc2020-12-02 00:33:42 +0000552 logger.Debugw(ctx, "flow-remove for downstream: ignore and continuing on checking further flows", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000553 "device-id": dh.DeviceID, "inPort": flowInPort})
mpagenkodff5dda2020-08-28 11:52:01 +0000554 continue
555 } else {
556 // this is the relevant upstream flow
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000557 var loUniPort *cmn.OnuUniPort
mpagenkodff5dda2020-08-28 11:52:01 +0000558 if uniPort, exist := dh.uniEntityMap[flowInPort]; exist {
559 loUniPort = uniPort
560 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000561 logger.Warnw(ctx, "flow-remove inPort not found in UniPorts: ignore and continuing on checking further flows",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000562 log.Fields{"device-id": dh.DeviceID, "inPort": flowInPort})
mpagenko01e726e2020-10-23 09:45:29 +0000563 retError = fmt.Errorf("flow-remove inPort not found in UniPorts, inPort %d, device-id %s",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000564 flowInPort, dh.DeviceID)
mpagenko01e726e2020-10-23 09:45:29 +0000565 continue
mpagenkodff5dda2020-08-28 11:52:01 +0000566 }
567 flowOutPort := flow.GetOutPort(flowItem)
dbainbri4d3a0dc2020-12-02 00:33:42 +0000568 logger.Debugw(ctx, "flow-remove port indications", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000569 "device-id": dh.DeviceID, "inPort": flowInPort, "outPort": flowOutPort,
570 "uniPortName": loUniPort.Name})
dbainbri4d3a0dc2020-12-02 00:33:42 +0000571 err := dh.removeFlowItemFromUniPort(ctx, flowItem, loUniPort)
mpagenko01e726e2020-10-23 09:45:29 +0000572 //try next flow after processing error
mpagenkodff5dda2020-08-28 11:52:01 +0000573 if err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000574 logger.Warnw(ctx, "flow-remove processing error: continuing on checking further flows",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000575 log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko01e726e2020-10-23 09:45:29 +0000576 retError = err
577 continue
578 //return err
579 } else { // if last setting succeeds, overwrite possibly previously set error
580 retError = nil
mpagenkodff5dda2020-08-28 11:52:01 +0000581 }
582 }
583 }
584 }
mpagenko01e726e2020-10-23 09:45:29 +0000585 if apOfFlowChanges.ToAdd != nil {
586 for _, flowItem := range apOfFlowChanges.ToAdd.Items {
587 if flowItem.GetCookie() == 0 {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000588 logger.Debugw(ctx, "incremental flow-add no cookie: ignore and continuing on checking further flows", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000589 "device-id": dh.DeviceID})
590 retError = fmt.Errorf("flow-add no cookie, device-id %s", dh.DeviceID)
mpagenko01e726e2020-10-23 09:45:29 +0000591 continue
592 }
593 flowInPort := flow.GetInPort(flowItem)
594 if flowInPort == uint32(of.OfpPortNo_OFPP_INVALID) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000595 logger.Warnw(ctx, "flow-add inPort invalid: ignore and continuing on checking further flows", log.Fields{"device-id": dh.DeviceID})
596 retError = fmt.Errorf("flow-add inPort invalid, device-id %s", dh.DeviceID)
mpagenko01e726e2020-10-23 09:45:29 +0000597 continue
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000598 //return fmt.Errorf("flow inPort invalid: %s", dh.DeviceID)
mpagenko01e726e2020-10-23 09:45:29 +0000599 } else if flowInPort == dh.ponPortNumber {
600 //this is some downstream flow
dbainbri4d3a0dc2020-12-02 00:33:42 +0000601 logger.Debugw(ctx, "flow-add for downstream: ignore and continuing on checking further flows", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000602 "device-id": dh.DeviceID, "inPort": flowInPort})
mpagenko01e726e2020-10-23 09:45:29 +0000603 continue
604 } else {
605 // this is the relevant upstream flow
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000606 var loUniPort *cmn.OnuUniPort
mpagenko01e726e2020-10-23 09:45:29 +0000607 if uniPort, exist := dh.uniEntityMap[flowInPort]; exist {
608 loUniPort = uniPort
609 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000610 logger.Warnw(ctx, "flow-add inPort not found in UniPorts: ignore and continuing on checking further flows",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000611 log.Fields{"device-id": dh.DeviceID, "inPort": flowInPort})
mpagenko01e726e2020-10-23 09:45:29 +0000612 retError = fmt.Errorf("flow-add inPort not found in UniPorts, inPort %d, device-id %s",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000613 flowInPort, dh.DeviceID)
mpagenko01e726e2020-10-23 09:45:29 +0000614 continue
615 //return fmt.Errorf("flow-parameter inPort %d not found in internal UniPorts", flowInPort)
616 }
mpagenkofc4f56e2020-11-04 17:17:49 +0000617 // let's still assume that we receive the flow-add only in some 'active' device state (as so far observed)
618 // if not, we just throw some error here to have an indication about that, if we really need to support that
619 // then we would need to create some means to activate the internal stored flows
620 // after the device gets active automatically (and still with its dependency to the TechProfile)
621 // for state checking compare also code here: processInterAdapterTechProfileDownloadReqMessage
622 // also abort for the other still possible flows here
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000623 if !dh.IsReadyForOmciConfig() {
624 logger.Errorw(ctx, "flow-add rejected: improper device state", log.Fields{"device-id": dh.DeviceID,
625 "last device-reason": dh.GetDeviceReasonString()})
626 return fmt.Errorf("improper device state on device %s", dh.DeviceID)
mpagenkofc4f56e2020-11-04 17:17:49 +0000627 }
628
mpagenko01e726e2020-10-23 09:45:29 +0000629 flowOutPort := flow.GetOutPort(flowItem)
dbainbri4d3a0dc2020-12-02 00:33:42 +0000630 logger.Debugw(ctx, "flow-add port indications", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000631 "device-id": dh.DeviceID, "inPort": flowInPort, "outPort": flowOutPort,
632 "uniPortName": loUniPort.Name})
ozgecanetsia82b91a62021-05-21 18:54:49 +0300633 err := dh.addFlowItemToUniPort(ctx, flowItem, loUniPort, apFlowMetaData)
mpagenko01e726e2020-10-23 09:45:29 +0000634 //try next flow after processing error
635 if err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000636 logger.Warnw(ctx, "flow-add processing error: continuing on checking further flows",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000637 log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko01e726e2020-10-23 09:45:29 +0000638 retError = err
639 continue
640 //return err
641 } else { // if last setting succeeds, overwrite possibly previously set error
642 retError = nil
643 }
644 }
645 }
646 }
647 return retError
mpagenkodff5dda2020-08-28 11:52:01 +0000648}
649
Himani Chawla6d2ae152020-09-02 13:11:20 +0530650//disableDevice locks the ONU and its UNI/VEIP ports (admin lock via OMCI)
mpagenkofc4f56e2020-11-04 17:17:49 +0000651//following are the expected device states after this activity:
652//Device Admin-State : down (on rwCore), Port-State: UNKNOWN, Conn-State: REACHABLE, Reason: omci-admin-lock
653// (Conn-State: REACHABLE might conflict with some previous ONU Down indication - maybe to be resolved later)
dbainbri4d3a0dc2020-12-02 00:33:42 +0000654func (dh *deviceHandler) disableDevice(ctx context.Context, device *voltha.Device) {
655 logger.Debugw(ctx, "disable-device", log.Fields{"device-id": device.Id, "SerialNumber": device.SerialNumber})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +0000656
mpagenko900ee4b2020-10-12 11:56:34 +0000657 //admin-lock reason can also be used uniquely for setting the DeviceState accordingly
mpagenkofc4f56e2020-11-04 17:17:49 +0000658 //note that disableDevice sequences in some 'ONU active' state may yield also
659 // "tech...delete-success" or "omci-flow-deleted" according to further received requests in the end
mpagenko900ee4b2020-10-12 11:56:34 +0000660 // - inblock state checking to prevent possibly unneeded processing (on command repitition)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000661 if dh.getDeviceReason() != cmn.DrOmciAdminLock {
mpagenkofc4f56e2020-11-04 17:17:49 +0000662 //disable-device shall be just a UNi/ONU-G related admin state setting
663 //all other configurations/FSM's shall not be impacted and shall execute as required by the system
mpagenko900ee4b2020-10-12 11:56:34 +0000664
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000665 if dh.IsReadyForOmciConfig() {
mpagenko01e726e2020-10-23 09:45:29 +0000666 // disable UNI ports/ONU
667 // *** should generate UniDisableStateDone event - used to disable the port(s) on success
668 if dh.pLockStateFsm == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000669 dh.createUniLockFsm(ctx, true, cmn.UniDisableStateDone)
mpagenko01e726e2020-10-23 09:45:29 +0000670 } else { //LockStateFSM already init
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000671 dh.pLockStateFsm.SetSuccessEvent(cmn.UniDisableStateDone)
dbainbri4d3a0dc2020-12-02 00:33:42 +0000672 dh.runUniLockFsm(ctx, true)
mpagenko01e726e2020-10-23 09:45:29 +0000673 }
674 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000675 logger.Debugw(ctx, "DeviceStateUpdate upon disable", log.Fields{"ConnectStatus": voltha.ConnectStatus_REACHABLE,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000676 "OperStatus": voltha.OperStatus_UNKNOWN, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -0400677 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000678 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -0400679 ConnStatus: voltha.ConnectStatus_REACHABLE,
680 OperStatus: voltha.OperStatus_UNKNOWN,
681 }); err != nil {
mpagenko01e726e2020-10-23 09:45:29 +0000682 //TODO with VOL-3045/VOL-3046: return the error and stop further processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000683 logger.Errorw(ctx, "error-updating-device-state", log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko01e726e2020-10-23 09:45:29 +0000684 }
mpagenko01e726e2020-10-23 09:45:29 +0000685 // DeviceReason to update acc.to modified py code as per beginning of Sept 2020
Holger Hildebrandt80129db2020-11-23 10:49:32 +0000686
687 //TODO with VOL-3045/VOL-3046: catch and return error, valid for all occurrences in the codebase
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000688 _ = dh.deviceReasonUpdate(ctx, cmn.DrOmciAdminLock, true)
mpagenko3af1f032020-06-10 08:53:41 +0000689 }
ozgecanetsiafce57b12020-05-25 14:39:35 +0300690 }
691}
692
Himani Chawla6d2ae152020-09-02 13:11:20 +0530693//reEnableDevice unlocks the ONU and its UNI/VEIP ports (admin unlock via OMCI)
dbainbri4d3a0dc2020-12-02 00:33:42 +0000694func (dh *deviceHandler) reEnableDevice(ctx context.Context, device *voltha.Device) {
695 logger.Debugw(ctx, "reenable-device", log.Fields{"device-id": device.Id, "SerialNumber": device.SerialNumber})
mpagenko3af1f032020-06-10 08:53:41 +0000696
mpagenkoaa3afe92021-05-21 16:20:58 +0000697 //setting readyForOmciConfig here is just a workaround for BBSIM testing in the sequence
mpagenkofc4f56e2020-11-04 17:17:49 +0000698 // OnuSoftReboot-disable-enable, because BBSIM does not generate a new OnuIndication-Up event after SoftReboot
699 // which is the assumption for real ONU's, where the ready-state is then set according to the following MibUpload/Download
700 // for real ONU's that should have nearly no influence
701 // Note that for real ONU's there is anyway a problematic situation with following sequence:
702 // OnuIndication-Dw (or not active at all) (- disable) - enable: here already the LockFsm may run into timeout (no OmciResponse)
703 // but that anyway is hopefully resolved by some OnuIndication-Up event (maybe to be tested)
704 // one could also argue, that a device-enable should also enable attempts for specific omci configuration
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000705 dh.SetReadyForOmciConfig(true) //needed to allow subsequent flow/techProf config (on BBSIM)
mpagenkofc4f56e2020-11-04 17:17:49 +0000706
Holger Hildebrandtccd390c2020-05-29 13:49:04 +0000707 // enable ONU/UNI ports
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000708 // *** should generate cmn.UniEnableStateDone event - used to disable the port(s) on success
Holger Hildebrandtccd390c2020-05-29 13:49:04 +0000709 if dh.pUnlockStateFsm == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000710 dh.createUniLockFsm(ctx, false, cmn.UniEnableStateDone)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +0000711 } else { //UnlockStateFSM already init
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000712 dh.pUnlockStateFsm.SetSuccessEvent(cmn.UniEnableStateDone)
dbainbri4d3a0dc2020-12-02 00:33:42 +0000713 dh.runUniLockFsm(ctx, false)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +0000714 }
ozgecanetsiafce57b12020-05-25 14:39:35 +0300715}
716
dbainbri4d3a0dc2020-12-02 00:33:42 +0000717func (dh *deviceHandler) reconcileDeviceOnuInd(ctx context.Context) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000718 logger.Debugw(ctx, "reconciling - simulate onu indication", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtf41a1602020-08-19 09:52:50 +0000719
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000720 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000721 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000722 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000723 return
724 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000725 if err := pDevEntry.RestoreDataFromOnuKvStore(log.WithSpanFromContext(context.TODO(), ctx)); err != nil {
mpagenko2418ab02020-11-12 12:58:06 +0000726 if err == fmt.Errorf("no-ONU-data-found") {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000727 logger.Debugw(ctx, "no persistent data found - abort reconciling", log.Fields{"device-id": dh.DeviceID})
mpagenko2418ab02020-11-12 12:58:06 +0000728 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000729 logger.Errorw(ctx, "reconciling - restoring OnuTp-data failed - abort", log.Fields{"err": err, "device-id": dh.DeviceID})
mpagenko2418ab02020-11-12 12:58:06 +0000730 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000731 dh.StopReconciling(ctx, false)
Holger Hildebrandtf41a1602020-08-19 09:52:50 +0000732 return
Holger Hildebrandt9ca8b132020-08-07 14:45:03 +0000733 }
Himani Chawla4d908332020-08-31 12:30:20 +0530734 var onuIndication oop.OnuIndication
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000735 pDevEntry.MutexPersOnuConfig.RLock()
736 onuIndication.IntfId = pDevEntry.SOnuPersistentData.PersIntfID
737 onuIndication.OnuId = pDevEntry.SOnuPersistentData.PersOnuID
738 onuIndication.OperState = pDevEntry.SOnuPersistentData.PersOperState
739 onuIndication.AdminState = pDevEntry.SOnuPersistentData.PersAdminState
740 pDevEntry.MutexPersOnuConfig.RUnlock()
dbainbri4d3a0dc2020-12-02 00:33:42 +0000741 _ = dh.createInterface(ctx, &onuIndication)
Holger Hildebrandtf41a1602020-08-19 09:52:50 +0000742}
743
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000744func (dh *deviceHandler) ReconcileDeviceTechProf(ctx context.Context) {
745 logger.Debugw(ctx, "reconciling - trigger tech profile config", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtf41a1602020-08-19 09:52:50 +0000746
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000747 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000748 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000749 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
750 if !dh.IsSkipOnuConfigReconciling() {
751 dh.StopReconciling(ctx, false)
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000752 }
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000753 return
754 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000755 dh.pOnuTP.LockTpProcMutex()
756 defer dh.pOnuTP.UnlockTpProcMutex()
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000757
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000758 pDevEntry.MutexPersOnuConfig.RLock()
mpagenko2dc896e2021-08-02 12:03:59 +0000759 persMutexLock := true
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000760 if len(pDevEntry.SOnuPersistentData.PersUniConfig) == 0 {
761 pDevEntry.MutexPersOnuConfig.RUnlock()
dbainbri4d3a0dc2020-12-02 00:33:42 +0000762 logger.Debugw(ctx, "reconciling - no uni-configs have been stored before adapter restart - terminate reconcilement",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000763 log.Fields{"device-id": dh.DeviceID})
764 if !dh.IsSkipOnuConfigReconciling() {
765 dh.StopReconciling(ctx, true)
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000766 }
Holger Hildebrandt3a644642020-12-02 09:46:18 +0000767 return
768 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000769 flowsFound := false
Girish Gowdra50e56422021-06-01 16:46:04 -0700770 techProfsFound := false
771 techProfInstLoadFailed := false
772outerLoop:
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000773 for _, uniData := range pDevEntry.SOnuPersistentData.PersUniConfig {
Holger Hildebrandt3a644642020-12-02 09:46:18 +0000774 //TODO: check for uni-port specific reconcilement in case of multi-uni-port-per-onu-support
775 if len(uniData.PersTpPathMap) == 0 {
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000776 logger.Debugw(ctx, "reconciling - no TPs stored for uniID",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000777 log.Fields{"uni-id": uniData.PersUniID, "device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000778 continue
Holger Hildebrandt3a644642020-12-02 09:46:18 +0000779 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000780 //release MutexPersOnuConfig before TechProfile (ANIConfig) processing as otherwise the reception of
781 // OMCI frames may get completely stuck due to lock request within IncrementMibDataSync() at OMCI
mpagenko2dc896e2021-08-02 12:03:59 +0000782 // frame reception may also lock the complete OMCI reception processing based on mutexRxSchedMap
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000783 pDevEntry.MutexPersOnuConfig.RUnlock()
mpagenko2dc896e2021-08-02 12:03:59 +0000784 persMutexLock = false
Girish Gowdra50e56422021-06-01 16:46:04 -0700785 techProfsFound = true // set to true if we found TP once for any UNI port
Girish Gowdra041dcb32020-11-16 16:54:30 -0800786 for tpID := range uniData.PersTpPathMap {
Girish Gowdra50e56422021-06-01 16:46:04 -0700787 // Request the TpInstance again from the openolt adapter in case of reconcile
khenaidoo7d3c5582021-08-11 18:09:44 -0400788 iaTechTpInst, err := dh.getTechProfileInstanceFromParentAdapter(ctx,
789 dh.device.ProxyAddress.AdapterEndpoint,
790 &ic.TechProfileInstanceRequestMessage{
791 DeviceId: dh.device.Id,
792 TpInstancePath: uniData.PersTpPathMap[tpID],
793 ParentDeviceId: dh.parentID,
794 ParentPonPort: dh.device.ParentPortNo,
795 OnuId: dh.device.ProxyAddress.OnuId,
796 UniId: uint32(uniData.PersUniID),
797 })
Girish Gowdra50e56422021-06-01 16:46:04 -0700798 if err != nil || iaTechTpInst == nil {
799 logger.Errorw(ctx, "error fetching tp instance",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000800 log.Fields{"tp-id": tpID, "tpPath": uniData.PersTpPathMap[tpID], "uni-id": uniData.PersUniID, "device-id": dh.DeviceID, "err": err})
Girish Gowdra50e56422021-06-01 16:46:04 -0700801 techProfInstLoadFailed = true // stop loading tp instance as soon as we hit failure
802 break outerLoop
803 }
804 var tpInst tech_profile.TechProfileInstance
805 switch techTpInst := iaTechTpInst.TechTpInstance.(type) {
khenaidoo7d3c5582021-08-11 18:09:44 -0400806 case *ic.TechProfileDownloadMessage_TpInstance: // supports only GPON, XGPON, XGS-PON
Girish Gowdra50e56422021-06-01 16:46:04 -0700807 tpInst = *techTpInst.TpInstance
mpagenko2dc896e2021-08-02 12:03:59 +0000808 logger.Debugw(ctx, "received-tp-instance-successfully-after-reconcile", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000809 "tp-id": tpID, "tpPath": uniData.PersTpPathMap[tpID], "uni-id": uniData.PersUniID, "device-id": dh.DeviceID})
Girish Gowdra50e56422021-06-01 16:46:04 -0700810 default: // do not support epon or other tech
mpagenko2dc896e2021-08-02 12:03:59 +0000811 logger.Errorw(ctx, "unsupported-tech-profile", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000812 "tp-id": tpID, "tpPath": uniData.PersTpPathMap[tpID], "uni-id": uniData.PersUniID, "device-id": dh.DeviceID})
Girish Gowdra50e56422021-06-01 16:46:04 -0700813 techProfInstLoadFailed = true // stop loading tp instance as soon as we hit failure
814 break outerLoop
815 }
816
Girish Gowdra041dcb32020-11-16 16:54:30 -0800817 // deadline context to ensure completion of background routines waited for
818 //20200721: 10s proved to be less in 8*8 ONU test on local vbox machine with debug, might be further adapted
819 deadline := time.Now().Add(dh.pOpenOnuAc.maxTimeoutInterAdapterComm) //allowed run time to finish before execution
dbainbri4d3a0dc2020-12-02 00:33:42 +0000820 dctx, cancel := context.WithDeadline(ctx, deadline)
Holger Hildebrandtf41a1602020-08-19 09:52:50 +0000821
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000822 dh.pOnuTP.ResetTpProcessingErrorIndication(uniData.PersUniID, tpID)
Girish Gowdra041dcb32020-11-16 16:54:30 -0800823 var wg sync.WaitGroup
824 wg.Add(1) // for the 1 go routine to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000825 go dh.pOnuTP.ConfigureUniTp(log.WithSpanFromContext(dctx, ctx), uniData.PersUniID, uniData.PersTpPathMap[tpID], tpInst, &wg)
dbainbri4d3a0dc2020-12-02 00:33:42 +0000826 dh.waitForCompletion(ctx, cancel, &wg, "TechProfReconcile") //wait for background process to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000827 if err := dh.pOnuTP.GetTpProcessingErrorIndication(uniData.PersUniID, tpID); err != nil {
828 logger.Errorw(ctx, err.Error(), log.Fields{"device-id": dh.DeviceID})
Girish Gowdra50e56422021-06-01 16:46:04 -0700829 techProfInstLoadFailed = true // stop loading tp instance as soon as we hit failure
830 break outerLoop
Girish Gowdra041dcb32020-11-16 16:54:30 -0800831 }
mpagenko2dc896e2021-08-02 12:03:59 +0000832 } // for all TpPath entries for this UNI
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000833 if len(uniData.PersFlowParams) != 0 {
834 flowsFound = true
Holger Hildebrandt3a644642020-12-02 09:46:18 +0000835 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000836 pDevEntry.MutexPersOnuConfig.RLock() //set protection again for loop test on SOnuPersistentData
mpagenko2dc896e2021-08-02 12:03:59 +0000837 persMutexLock = true
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000838 } // for all UNI entries from SOnuPersistentData
839 if persMutexLock { // if loop was left with MutexPersOnuConfig still set
840 pDevEntry.MutexPersOnuConfig.RUnlock()
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000841 }
mpagenko2dc896e2021-08-02 12:03:59 +0000842
843 //had to move techProf/flow result evaluation into separate function due to SCA complexity limit
844 dh.updateReconcileStates(ctx, techProfsFound, techProfInstLoadFailed, flowsFound)
845}
846
847func (dh *deviceHandler) updateReconcileStates(ctx context.Context,
848 abTechProfsFound bool, abTechProfInstLoadFailed bool, abFlowsFound bool) {
849 if !abTechProfsFound {
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000850 logger.Debugw(ctx, "reconciling - no TPs have been stored before adapter restart - terminate reconcilement",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000851 log.Fields{"device-id": dh.DeviceID})
852 if !dh.IsSkipOnuConfigReconciling() {
853 dh.StopReconciling(ctx, true)
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000854 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000855 return
856 }
mpagenko2dc896e2021-08-02 12:03:59 +0000857 if abTechProfInstLoadFailed {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000858 dh.SetDeviceReason(cmn.DrTechProfileConfigDownloadFailed)
859 dh.StopReconciling(ctx, false)
Girish Gowdra50e56422021-06-01 16:46:04 -0700860 return
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000861 } else if dh.IsSkipOnuConfigReconciling() {
862 dh.SetDeviceReason(cmn.DrTechProfileConfigDownloadSuccess)
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000863 }
mpagenko2dc896e2021-08-02 12:03:59 +0000864 if !abFlowsFound {
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000865 logger.Debugw(ctx, "reconciling - no flows have been stored before adapter restart - terminate reconcilement",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000866 log.Fields{"device-id": dh.DeviceID})
867 if !dh.IsSkipOnuConfigReconciling() {
868 dh.StopReconciling(ctx, true)
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000869 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000870 }
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000871}
872
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000873func (dh *deviceHandler) ReconcileDeviceFlowConfig(ctx context.Context) {
874 logger.Debugw(ctx, "reconciling - trigger flow config", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000875
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000876 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000877 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000878 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
879 if !dh.IsSkipOnuConfigReconciling() {
880 dh.StopReconciling(ctx, false)
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000881 }
Holger Hildebrandtf41a1602020-08-19 09:52:50 +0000882 return
883 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000884
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000885 pDevEntry.MutexPersOnuConfig.RLock()
886 if len(pDevEntry.SOnuPersistentData.PersUniConfig) == 0 {
887 pDevEntry.MutexPersOnuConfig.RUnlock()
dbainbri4d3a0dc2020-12-02 00:33:42 +0000888 logger.Debugw(ctx, "reconciling - no uni-configs have been stored before adapter restart - terminate reconcilement",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000889 log.Fields{"device-id": dh.DeviceID})
890 if !dh.IsSkipOnuConfigReconciling() {
891 dh.StopReconciling(ctx, true)
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000892 }
Holger Hildebrandt3a644642020-12-02 09:46:18 +0000893 return
894 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000895 flowsFound := false
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000896 for _, uniData := range pDevEntry.SOnuPersistentData.PersUniConfig {
Holger Hildebrandt3a644642020-12-02 09:46:18 +0000897 //TODO: check for uni-port specific reconcilement in case of multi-uni-port-per-onu-support
898 if len(uniData.PersFlowParams) == 0 {
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000899 logger.Debugw(ctx, "reconciling - no flows stored for uniID",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000900 log.Fields{"uni-id": uniData.PersUniID, "device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000901 continue
902 }
903 if len(uniData.PersTpPathMap) == 0 {
904 logger.Warnw(ctx, "reconciling - flows but no TPs stored for uniID",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000905 log.Fields{"uni-id": uniData.PersUniID, "device-id": dh.DeviceID})
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000906 // It doesn't make sense to configure any flows if no TPs are available
907 continue
Holger Hildebrandt3a644642020-12-02 09:46:18 +0000908 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000909 //release MutexPersOnuConfig before VlanConfig processing as otherwise the reception of
910 // OMCI frames may get completely stuck due to lock request within IncrementMibDataSync() at OMCI
mpagenko2dc896e2021-08-02 12:03:59 +0000911 // frame reception may also lock the complete OMCI reception processing based on mutexRxSchedMap
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000912 pDevEntry.MutexPersOnuConfig.RUnlock()
mpagenko2dc896e2021-08-02 12:03:59 +0000913
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000914 var uniPort *cmn.OnuUniPort
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000915 var exist bool
dbainbri4d3a0dc2020-12-02 00:33:42 +0000916 uniNo := mkUniPortNum(ctx, dh.pOnuIndication.GetIntfId(), dh.pOnuIndication.GetOnuId(), uint32(uniData.PersUniID))
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000917 if uniPort, exist = dh.uniEntityMap[uniNo]; !exist {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000918 logger.Errorw(ctx, "reconciling - OnuUniPort data not found - terminate reconcilement",
919 log.Fields{"uniNo": uniNo, "device-id": dh.DeviceID})
920 if !dh.IsSkipOnuConfigReconciling() {
921 dh.StopReconciling(ctx, false)
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000922 }
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000923 return
924 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000925 flowsFound = true
Andrea Campanellaf66ac6e2021-05-24 17:09:20 +0200926 lastFlowToReconcile := false
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000927 flowsProcessed := 0
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000928 pDevEntry.SetReconcilingFlows(true)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000929 for _, flowData := range uniData.PersFlowParams {
mpagenko2dc896e2021-08-02 12:03:59 +0000930 logger.Debugw(ctx, "reconciling - add flow with cookie slice", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000931 "device-id": dh.DeviceID, "uni-id": uniData.PersUniID, "cookies": flowData.CookieSlice})
Andrea Campanellaf66ac6e2021-05-24 17:09:20 +0200932 if flowsProcessed == len(uniData.PersFlowParams)-1 {
933 lastFlowToReconcile = true
934 }
mpagenko01e726e2020-10-23 09:45:29 +0000935 //the slice can be passed 'by value' here, - which internally passes its reference copy
mpagenko7d14de12021-07-27 08:31:56 +0000936 dh.lockVlanConfig.Lock()
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000937 if _, exist = dh.UniVlanConfigFsmMap[uniData.PersUniID]; exist {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000938 if err := dh.UniVlanConfigFsmMap[uniData.PersUniID].SetUniFlowParams(ctx, flowData.VlanRuleParams.TpID,
mpagenko01e726e2020-10-23 09:45:29 +0000939 flowData.CookieSlice, uint16(flowData.VlanRuleParams.MatchVid), uint16(flowData.VlanRuleParams.SetVid),
ozgecanetsia82b91a62021-05-21 18:54:49 +0300940 uint8(flowData.VlanRuleParams.SetPcp), lastFlowToReconcile, flowData.Meter); err != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000941 logger.Errorw(ctx, err.Error(), log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000942 }
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000943 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +0000944 if err := dh.createVlanFilterFsm(ctx, uniPort, flowData.VlanRuleParams.TpID, flowData.CookieSlice,
mpagenko01e726e2020-10-23 09:45:29 +0000945 uint16(flowData.VlanRuleParams.MatchVid), uint16(flowData.VlanRuleParams.SetVid),
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000946 uint8(flowData.VlanRuleParams.SetPcp), cmn.OmciVlanFilterAddDone, lastFlowToReconcile, flowData.Meter); err != nil {
947 logger.Errorw(ctx, err.Error(), log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000948 }
949 }
mpagenko7d14de12021-07-27 08:31:56 +0000950 dh.lockVlanConfig.Unlock()
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000951 flowsProcessed++
mpagenko2dc896e2021-08-02 12:03:59 +0000952 } //for all flows of this UNI
953 logger.Debugw(ctx, "reconciling - flows processed", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000954 "device-id": dh.DeviceID, "uni-id": uniData.PersUniID, "flowsProcessed": flowsProcessed,
955 "NumUniFlows": dh.UniVlanConfigFsmMap[uniData.PersUniID].NumUniFlows,
956 "ConfiguredUniFlow": dh.UniVlanConfigFsmMap[uniData.PersUniID].ConfiguredUniFlow})
Andrea Campanellaf66ac6e2021-05-24 17:09:20 +0200957 // this can't be used as global finished reconciling flag because
958 // assumes is getting called before the state machines for the last flow is completed,
959 // while this is not guaranteed.
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000960 //dh.SetReconcilingFlows(false)
961 pDevEntry.MutexPersOnuConfig.RLock() //set protection again for loop test on SOnuPersistentData
962 } // for all UNI entries from SOnuPersistentData
963 pDevEntry.MutexPersOnuConfig.RUnlock()
mpagenko2dc896e2021-08-02 12:03:59 +0000964
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000965 if !flowsFound {
966 logger.Debugw(ctx, "reconciling - no flows have been stored before adapter restart - terminate reconcilement",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000967 log.Fields{"device-id": dh.DeviceID})
968 if !dh.IsSkipOnuConfigReconciling() {
969 dh.StopReconciling(ctx, true)
Holger Hildebrandt7e9de862021-03-26 14:01:49 +0000970 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +0000971 return
972 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000973 if dh.IsSkipOnuConfigReconciling() {
974 dh.SetDeviceReason(cmn.DrOmciFlowsPushed)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000975 }
976}
977
Holger Hildebrandt1b8f4ad2021-03-25 15:53:51 +0000978func (dh *deviceHandler) reconcileEnd(ctx context.Context) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000979 logger.Debugw(ctx, "reconciling - completed!", log.Fields{"device-id": dh.DeviceID})
980 dh.StopReconciling(ctx, true)
Holger Hildebrandt9ca8b132020-08-07 14:45:03 +0000981}
982
dbainbri4d3a0dc2020-12-02 00:33:42 +0000983func (dh *deviceHandler) deleteDevicePersistencyData(ctx context.Context) error {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000984 logger.Debugw(ctx, "delete device persistency data", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000985
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000986 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000987 if pDevEntry == nil {
mpagenko2418ab02020-11-12 12:58:06 +0000988 //IfDevEntry does not exist here, no problem - no persistent data should have been stored
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000989 logger.Debugw(ctx, "OnuDevice does not exist - nothing to delete", log.Fields{"device-id": dh.DeviceID})
mpagenko2418ab02020-11-12 12:58:06 +0000990 return nil
Holger Hildebrandt9ca8b132020-08-07 14:45:03 +0000991 }
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000992
993 // deadline context to ensure completion of background routines waited for
994 //20200721: 10s proved to be less in 8*8 ONU test on local vbox machine with debug, might be further adapted
Himani Chawlad96df182020-09-28 11:12:02 +0530995 deadline := time.Now().Add(dh.pOpenOnuAc.maxTimeoutInterAdapterComm) //allowed run time to finish before execution
dbainbri4d3a0dc2020-12-02 00:33:42 +0000996 dctx, cancel := context.WithDeadline(ctx, deadline)
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000997
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +0000998 pDevEntry.ResetKvProcessingErrorIndication()
Holger Hildebrandt47555e72020-09-21 11:07:24 +0000999
1000 var wg sync.WaitGroup
1001 wg.Add(1) // for the 1 go routine to finish
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001002 go pDevEntry.DeleteDataFromOnuKvStore(log.WithSpanFromContext(dctx, ctx), &wg)
dbainbri4d3a0dc2020-12-02 00:33:42 +00001003 dh.waitForCompletion(ctx, cancel, &wg, "DeleteDevice") //wait for background process to finish
Holger Hildebrandt47555e72020-09-21 11:07:24 +00001004
Holger Hildebrandt9ca8b132020-08-07 14:45:03 +00001005 // TODO: further actions - stop metrics and FSMs, remove device ...
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001006 return pDevEntry.GetKvProcessingErrorIndication()
Holger Hildebrandt9ca8b132020-08-07 14:45:03 +00001007}
1008
mpagenko15ff4a52021-03-02 10:09:20 +00001009//func (dh *deviceHandler) rebootDevice(ctx context.Context, device *voltha.Device) error {
1010// before this change here return like this was used:
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001011// return fmt.Errorf("device-unreachable: %s, %s", dh.DeviceID, device.SerialNumber)
mpagenko15ff4a52021-03-02 10:09:20 +00001012//was and is called in background - error return does not make sense
1013func (dh *deviceHandler) rebootDevice(ctx context.Context, aCheckDeviceState bool, device *voltha.Device) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001014 logger.Infow(ctx, "reboot-device", log.Fields{"device-id": dh.DeviceID, "SerialNumber": dh.device.SerialNumber})
mpagenko15ff4a52021-03-02 10:09:20 +00001015 if aCheckDeviceState && device.ConnectStatus != voltha.ConnectStatus_REACHABLE {
dbainbri4d3a0dc2020-12-02 00:33:42 +00001016 logger.Errorw(ctx, "device-unreachable", log.Fields{"device-id": device.Id, "SerialNumber": device.SerialNumber})
mpagenko15ff4a52021-03-02 10:09:20 +00001017 return
ozgecanetsiae11479f2020-07-06 09:44:47 +03001018 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001019 if err := dh.pOnuOmciDevice.Reboot(log.WithSpanFromContext(context.TODO(), ctx)); err != nil {
Himani Chawla4d908332020-08-31 12:30:20 +05301020 //TODO with VOL-3045/VOL-3046: return the error and stop further processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001021 logger.Errorw(ctx, "error-rebooting-device", log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko15ff4a52021-03-02 10:09:20 +00001022 return
Himani Chawla4d908332020-08-31 12:30:20 +05301023 }
mpagenko01e726e2020-10-23 09:45:29 +00001024
1025 //transfer the possibly modified logical uni port state
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001026 dh.DisableUniPortStateUpdate(ctx)
mpagenko01e726e2020-10-23 09:45:29 +00001027
dbainbri4d3a0dc2020-12-02 00:33:42 +00001028 logger.Debugw(ctx, "call DeviceStateUpdate upon reboot", log.Fields{"ConnectStatus": voltha.ConnectStatus_REACHABLE,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001029 "OperStatus": voltha.OperStatus_DISCOVERED, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04001030 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001031 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04001032 ConnStatus: voltha.ConnectStatus_REACHABLE,
1033 OperStatus: voltha.OperStatus_DISCOVERED,
1034 }); err != nil {
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001035 //TODO with VOL-3045/VOL-3046: return the error and stop further processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001036 logger.Errorw(ctx, "error-updating-device-state", log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko15ff4a52021-03-02 10:09:20 +00001037 return
ozgecanetsiae11479f2020-07-06 09:44:47 +03001038 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001039 if err := dh.deviceReasonUpdate(ctx, cmn.DrRebooting, true); err != nil {
mpagenko15ff4a52021-03-02 10:09:20 +00001040 return
ozgecanetsiae11479f2020-07-06 09:44:47 +03001041 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001042 dh.SetReadyForOmciConfig(false)
mpagenko8b07c1b2020-11-26 10:36:31 +00001043 //no specific activity to synchronize any internal FSM to the 'rebooted' state is explicitly done here
1044 // the expectation ids for a real device, that it will be synced with the expected following 'down' indication
1045 // as BBSIM does not support this testing requires explicite disable/enable device calls in which sequence also
1046 // all other FSM's should be synchronized again
ozgecanetsiae11479f2020-07-06 09:44:47 +03001047}
1048
mpagenkoc8bba412021-01-15 15:38:44 +00001049//doOnuSwUpgrade initiates the SW download transfer to the ONU and on success activates the (inactive) image
mpagenko38662d02021-08-11 09:45:19 +00001050// used only for old - R2.7 style - upgrade API
mpagenko80622a52021-02-09 16:53:23 +00001051func (dh *deviceHandler) doOnuSwUpgrade(ctx context.Context, apImageDsc *voltha.ImageDownload,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001052 apDownloadManager *swupg.AdapterDownloadManager) error {
mpagenko80622a52021-02-09 16:53:23 +00001053 logger.Debugw(ctx, "onuSwUpgrade requested", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001054 "device-id": dh.DeviceID, "image-name": (*apImageDsc).Name})
mpagenko80622a52021-02-09 16:53:23 +00001055
1056 var err error
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001057 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
mpagenko15ff4a52021-03-02 10:09:20 +00001058 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001059 logger.Errorw(ctx, "start Onu SW upgrade rejected: no valid OnuDevice", log.Fields{"device-id": dh.DeviceID})
1060 return fmt.Errorf("start Onu SW upgrade rejected: no valid OnuDevice for device-id: %s", dh.DeviceID)
mpagenko15ff4a52021-03-02 10:09:20 +00001061 }
1062
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001063 if dh.IsReadyForOmciConfig() {
mpagenko15ff4a52021-03-02 10:09:20 +00001064 var inactiveImageID uint16
1065 if inactiveImageID, err = pDevEntry.GetInactiveImageMeID(ctx); err == nil {
1066 dh.lockUpgradeFsm.Lock()
1067 defer dh.lockUpgradeFsm.Unlock()
1068 if dh.pOnuUpradeFsm == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001069 err = dh.createOnuUpgradeFsm(ctx, pDevEntry, cmn.OmciOnuSwUpgradeDone)
mpagenko15ff4a52021-03-02 10:09:20 +00001070 if err == nil {
1071 if err = dh.pOnuUpradeFsm.SetDownloadParams(ctx, inactiveImageID, apImageDsc, apDownloadManager); err != nil {
1072 logger.Errorw(ctx, "onu upgrade fsm could not set parameters", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001073 "device-id": dh.DeviceID, "error": err})
mpagenko15ff4a52021-03-02 10:09:20 +00001074 }
1075 } else {
1076 logger.Errorw(ctx, "onu upgrade fsm could not be created", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001077 "device-id": dh.DeviceID, "error": err})
mpagenko80622a52021-02-09 16:53:23 +00001078 }
mpagenko15ff4a52021-03-02 10:09:20 +00001079 } else { //OnuSw upgrade already running - restart (with possible abort of running)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001080 logger.Debugw(ctx, "Onu SW upgrade already running - abort", log.Fields{"device-id": dh.DeviceID})
1081 dh.pOnuUpradeFsm.CancelProcessing(ctx, true, voltha.ImageState_CANCELLED_ON_REQUEST) //complete abort
1082 //no effort spent anymore for the old API to automatically cancel and restart the download
1083 // like done for the new API
1084 logger.Debugw(ctx, "Onu SW upgrade already running - abort", log.Fields{"device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00001085 dh.pOnuUpradeFsm.CancelProcessing(ctx, true, voltha.ImageState_CANCELLED_ON_REQUEST) //complete abort
1086 //no effort spent anymore for the old API to automatically cancel and restart the download
1087 // like done for the new API
mpagenko80622a52021-02-09 16:53:23 +00001088 }
mpagenko15ff4a52021-03-02 10:09:20 +00001089 } else {
1090 logger.Errorw(ctx, "start Onu SW upgrade rejected: no inactive image", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001091 "device-id": dh.DeviceID, "error": err})
mpagenko80622a52021-02-09 16:53:23 +00001092 }
1093 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001094 logger.Errorw(ctx, "start Onu SW upgrade rejected: no active OMCI connection", log.Fields{"device-id": dh.DeviceID})
1095 err = fmt.Errorf("start Onu SW upgrade rejected: no active OMCI connection for device-id: %s", dh.DeviceID)
mpagenko80622a52021-02-09 16:53:23 +00001096 }
1097 return err
mpagenkoc8bba412021-01-15 15:38:44 +00001098}
1099
mpagenkoc26d4c02021-05-06 14:27:57 +00001100//onuSwUpgradeAfterDownload initiates the SW download transfer to the ONU with activate and commit options
1101// after the OnuImage has been downloaded to the adapter, called in background
1102func (dh *deviceHandler) onuSwUpgradeAfterDownload(ctx context.Context, apImageRequest *voltha.DeviceImageDownloadRequest,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001103 apDownloadManager *swupg.FileDownloadManager, aImageIdentifier string) {
mpagenkoc26d4c02021-05-06 14:27:57 +00001104
1105 var err error
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001106 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
mpagenkoc26d4c02021-05-06 14:27:57 +00001107 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001108 logger.Errorw(ctx, "start Onu SW upgrade rejected: no valid OnuDevice", log.Fields{"device-id": dh.DeviceID})
mpagenkoc26d4c02021-05-06 14:27:57 +00001109 return
1110 }
1111
1112 var inactiveImageID uint16
1113 if inactiveImageID, err = pDevEntry.GetInactiveImageMeID(ctx); err == nil {
1114 logger.Debugw(ctx, "onuSwUpgrade requested", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001115 "device-id": dh.DeviceID, "image-version": apImageRequest.Image.Version, "to onu-image": inactiveImageID})
mpagenko38662d02021-08-11 09:45:19 +00001116
1117 dh.lockUpgradeFsm.RLock()
1118 lopOnuUpradeFsm := dh.pOnuUpradeFsm
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001119 //lockUpgradeFsm must be release before cancellation as this may implicitly request RemoveOnuUpgradeFsm()
mpagenko38662d02021-08-11 09:45:19 +00001120 dh.lockUpgradeFsm.RUnlock()
1121 if lopOnuUpradeFsm != nil {
1122 //OnuSw upgrade already running on this device (e.g. with activate/commit not yet set)
1123 // abort the current processing, running upgrades are always aborted by newer request
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001124 logger.Debugw(ctx, "Onu SW upgrade already running - abort previous activity", log.Fields{"device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00001125 //flush the remove upgradeFsmChan channel
1126 select {
1127 case <-dh.upgradeFsmChan:
1128 logger.Debug(ctx, "flushed-upgrade-fsm-channel")
1129 default:
mpagenkoc26d4c02021-05-06 14:27:57 +00001130 }
mpagenko38662d02021-08-11 09:45:19 +00001131 lopOnuUpradeFsm.CancelProcessing(ctx, true, voltha.ImageState_CANCELLED_ON_REQUEST) //complete abort
1132 select {
1133 case <-time.After(cTimeOutRemoveUpgrade * time.Second):
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001134 logger.Errorw(ctx, "could not remove Upgrade FSM in time, aborting", log.Fields{"device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00001135 //should not appear, can't proceed with new upgrade, perhaps operator can retry manually later
1136 return
1137 case <-dh.upgradeFsmChan:
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001138 logger.Debugw(ctx, "recent Upgrade FSM removed, proceed with new request", log.Fields{"device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00001139 }
mpagenkoc26d4c02021-05-06 14:27:57 +00001140 }
mpagenko38662d02021-08-11 09:45:19 +00001141
1142 //here it can be assumed that no running upgrade processing exists (anymore)
1143 //OmciOnuSwUpgradeDone could be used to create some Kafka event with information on upgrade completion,
1144 // but none yet defined
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001145 err = dh.createOnuUpgradeFsm(ctx, pDevEntry, cmn.OmciOnuSwUpgradeDone)
mpagenko38662d02021-08-11 09:45:19 +00001146 if err == nil {
1147 if err = dh.pOnuUpradeFsm.SetDownloadParamsAfterDownload(ctx, inactiveImageID,
1148 apImageRequest, apDownloadManager, aImageIdentifier); err != nil {
1149 logger.Errorw(ctx, "onu upgrade fsm could not set parameters", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001150 "device-id": dh.DeviceID, "error": err})
mpagenkoc26d4c02021-05-06 14:27:57 +00001151 return
1152 }
mpagenko38662d02021-08-11 09:45:19 +00001153 } else {
1154 logger.Errorw(ctx, "onu upgrade fsm could not be created", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001155 "device-id": dh.DeviceID, "error": err})
mpagenkoc26d4c02021-05-06 14:27:57 +00001156 }
1157 return
1158 }
1159 logger.Errorw(ctx, "start Onu SW upgrade rejected: no inactive image", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001160 "device-id": dh.DeviceID, "error": err})
mpagenkoc26d4c02021-05-06 14:27:57 +00001161}
1162
1163//onuSwActivateRequest ensures activation of the requested image with commit options
mpagenko183647c2021-06-08 15:25:04 +00001164func (dh *deviceHandler) onuSwActivateRequest(ctx context.Context,
1165 aVersion string, aCommitRequest bool) (*voltha.ImageState, error) {
mpagenkoc26d4c02021-05-06 14:27:57 +00001166 var err error
1167 //SW activation for the ONU image may have two use cases, one of them is selected here according to following prioritization:
1168 // 1.) activation of the image for a started upgrade process (in case the running upgrade runs on the requested image)
1169 // 2.) activation of the inactive image
1170
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001171 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
mpagenkoc26d4c02021-05-06 14:27:57 +00001172 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001173 logger.Errorw(ctx, "Onu image activation rejected: no valid OnuDevice", log.Fields{"device-id": dh.DeviceID})
1174 return nil, fmt.Errorf("no valid OnuDevice for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001175 }
1176 dh.lockUpgradeFsm.RLock()
1177 if dh.pOnuUpradeFsm != nil {
1178 dh.lockUpgradeFsm.RUnlock()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001179 onuVolthaDevice, getErr := dh.getDeviceFromCore(ctx, dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001180 if getErr != nil || onuVolthaDevice == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001181 logger.Errorw(ctx, "Failed to fetch Onu device for image activation", log.Fields{"device-id": dh.DeviceID, "err": getErr})
1182 return nil, fmt.Errorf("could not fetch device for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001183 }
1184 // use the OnuVendor identification from this device for the internal unique name
1185 imageIdentifier := onuVolthaDevice.VendorId + aVersion //head on vendor ID of the ONU
mpagenko38662d02021-08-11 09:45:19 +00001186 // 1.) check a started upgrade process and relay the activation request to it
mpagenkoc26d4c02021-05-06 14:27:57 +00001187 if err = dh.pOnuUpradeFsm.SetActivationParamsRunning(ctx, imageIdentifier, aCommitRequest); err != nil {
mpagenko183647c2021-06-08 15:25:04 +00001188 //if some ONU upgrade is ongoing we do not accept some explicit ONU image-version related activation
mpagenkoc26d4c02021-05-06 14:27:57 +00001189 logger.Errorw(ctx, "onu upgrade fsm did not accept activation while running", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001190 "device-id": dh.DeviceID, "error": err})
1191 return nil, fmt.Errorf("activation not accepted for this version for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001192 }
mpagenko183647c2021-06-08 15:25:04 +00001193 logger.Debugw(ctx, "image activation acknowledged by onu upgrade processing", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001194 "device-id": dh.DeviceID, "image-id": imageIdentifier})
mpagenko38662d02021-08-11 09:45:19 +00001195 pImageStates := dh.pOnuUpradeFsm.GetImageStates(ctx, "", aVersion)
mpagenko183647c2021-06-08 15:25:04 +00001196 return pImageStates, nil
mpagenkoc26d4c02021-05-06 14:27:57 +00001197 } //else
1198 dh.lockUpgradeFsm.RUnlock()
1199
1200 // 2.) check if requested image-version equals the inactive one and start its activation
1201 // (image version is not [yet] checked - would be possible, but with increased effort ...)
1202 var inactiveImageID uint16
1203 if inactiveImageID, err = pDevEntry.GetInactiveImageMeID(ctx); err != nil || inactiveImageID > 1 {
1204 logger.Errorw(ctx, "get inactive image failed", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001205 "device-id": dh.DeviceID, "err": err, "image-id": inactiveImageID})
1206 return nil, fmt.Errorf("no valid inactive image found for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001207 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001208 err = dh.createOnuUpgradeFsm(ctx, pDevEntry, cmn.OmciOnuSwUpgradeDone)
mpagenkoc26d4c02021-05-06 14:27:57 +00001209 if err == nil {
1210 if err = dh.pOnuUpradeFsm.SetActivationParamsStart(ctx, aVersion,
1211 inactiveImageID, aCommitRequest); err != nil {
1212 logger.Errorw(ctx, "onu upgrade fsm did not accept activation to start", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001213 "device-id": dh.DeviceID, "error": err})
1214 return nil, fmt.Errorf("activation to start from scratch not accepted for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001215 }
1216 logger.Debugw(ctx, "inactive image activation acknowledged by onu upgrade", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001217 "device-id": dh.DeviceID, "image-version": aVersion})
mpagenko38662d02021-08-11 09:45:19 +00001218 pImageStates := dh.pOnuUpradeFsm.GetImageStates(ctx, "", aVersion)
mpagenko183647c2021-06-08 15:25:04 +00001219 return pImageStates, nil
mpagenkoc26d4c02021-05-06 14:27:57 +00001220 } //else
1221 logger.Errorw(ctx, "onu upgrade fsm could not be created", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001222 "device-id": dh.DeviceID, "error": err})
1223 return nil, fmt.Errorf("could not start upgradeFsm for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001224}
1225
1226//onuSwCommitRequest ensures commitment of the requested image
mpagenko183647c2021-06-08 15:25:04 +00001227func (dh *deviceHandler) onuSwCommitRequest(ctx context.Context,
1228 aVersion string) (*voltha.ImageState, error) {
mpagenkoc26d4c02021-05-06 14:27:57 +00001229 var err error
1230 //SW commitment for the ONU image may have two use cases, one of them is selected here according to following prioritization:
1231 // 1.) commitment of the image for a started upgrade process (in case the running upgrade runs on the requested image)
1232 // 2.) commitment of the active image
1233
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001234 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
mpagenkoc26d4c02021-05-06 14:27:57 +00001235 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001236 logger.Errorw(ctx, "Onu image commitment rejected: no valid OnuDevice", log.Fields{"device-id": dh.DeviceID})
1237 return nil, fmt.Errorf("no valid OnuDevice for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001238 }
1239 dh.lockUpgradeFsm.RLock()
1240 if dh.pOnuUpradeFsm != nil {
1241 dh.lockUpgradeFsm.RUnlock()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001242 onuVolthaDevice, getErr := dh.getDeviceFromCore(ctx, dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001243 if getErr != nil || onuVolthaDevice == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001244 logger.Errorw(ctx, "Failed to fetch Onu device for image commitment", log.Fields{"device-id": dh.DeviceID, "err": getErr})
1245 return nil, fmt.Errorf("could not fetch device for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001246 }
1247 // use the OnuVendor identification from this device for the internal unique name
1248 imageIdentifier := onuVolthaDevice.VendorId + aVersion //head on vendor ID of the ONU
mpagenko38662d02021-08-11 09:45:19 +00001249 // 1.) check a started upgrade process and relay the commitment request to it
1250 // the running upgrade may be based either on the imageIdentifier (started from download)
1251 // or on the imageVersion (started from pure activation)
1252 if err = dh.pOnuUpradeFsm.SetCommitmentParamsRunning(ctx, imageIdentifier, aVersion); err != nil {
1253 //if some ONU upgrade is ongoing we do not accept some explicit different ONU image-version related commitment
mpagenkoc26d4c02021-05-06 14:27:57 +00001254 logger.Errorw(ctx, "onu upgrade fsm did not accept commitment while running", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001255 "device-id": dh.DeviceID, "error": err})
1256 return nil, fmt.Errorf("commitment not accepted for this version for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001257 }
mpagenko183647c2021-06-08 15:25:04 +00001258 logger.Debugw(ctx, "image commitment acknowledged by onu upgrade processing", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001259 "device-id": dh.DeviceID, "image-id": imageIdentifier})
mpagenko38662d02021-08-11 09:45:19 +00001260 pImageStates := dh.pOnuUpradeFsm.GetImageStates(ctx, "", aVersion)
mpagenko183647c2021-06-08 15:25:04 +00001261 return pImageStates, nil
mpagenkoc26d4c02021-05-06 14:27:57 +00001262 } //else
1263 dh.lockUpgradeFsm.RUnlock()
1264
mpagenko183647c2021-06-08 15:25:04 +00001265 // 2.) use the active image to directly commit
mpagenkoc26d4c02021-05-06 14:27:57 +00001266 var activeImageID uint16
1267 if activeImageID, err = pDevEntry.GetActiveImageMeID(ctx); err != nil || activeImageID > 1 {
1268 logger.Errorw(ctx, "get active image failed", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001269 "device-id": dh.DeviceID, "err": err, "image-id": activeImageID})
1270 return nil, fmt.Errorf("no valid active image found for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001271 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001272 err = dh.createOnuUpgradeFsm(ctx, pDevEntry, cmn.OmciOnuSwUpgradeDone)
mpagenkoc26d4c02021-05-06 14:27:57 +00001273 if err == nil {
1274 if err = dh.pOnuUpradeFsm.SetCommitmentParamsStart(ctx, aVersion, activeImageID); err != nil {
1275 logger.Errorw(ctx, "onu upgrade fsm did not accept commitment to start", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001276 "device-id": dh.DeviceID, "error": err})
1277 return nil, fmt.Errorf("commitment to start from scratch not accepted for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001278 }
1279 logger.Debugw(ctx, "active image commitment acknowledged by onu upgrade", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001280 "device-id": dh.DeviceID, "image-version": aVersion})
mpagenko38662d02021-08-11 09:45:19 +00001281 pImageStates := dh.pOnuUpradeFsm.GetImageStates(ctx, "", aVersion)
mpagenko183647c2021-06-08 15:25:04 +00001282 return pImageStates, nil
mpagenkoc26d4c02021-05-06 14:27:57 +00001283 } //else
1284 logger.Errorw(ctx, "onu upgrade fsm could not be created", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001285 "device-id": dh.DeviceID, "error": err})
1286 return nil, fmt.Errorf("could not start upgradeFsm for device-id: %s", dh.DeviceID)
mpagenkoc26d4c02021-05-06 14:27:57 +00001287}
1288
mpagenkoaa3afe92021-05-21 16:20:58 +00001289func (dh *deviceHandler) requestOnuSwUpgradeState(ctx context.Context, aImageIdentifier string,
mpagenko38662d02021-08-11 09:45:19 +00001290 aVersion string) *voltha.ImageState {
1291 var pImageState *voltha.ImageState
mpagenkoaa3afe92021-05-21 16:20:58 +00001292 dh.lockUpgradeFsm.RLock()
mpagenko38662d02021-08-11 09:45:19 +00001293 defer dh.lockUpgradeFsm.RUnlock()
mpagenkoaa3afe92021-05-21 16:20:58 +00001294 if dh.pOnuUpradeFsm != nil {
mpagenko38662d02021-08-11 09:45:19 +00001295 pImageState = dh.pOnuUpradeFsm.GetImageStates(ctx, aImageIdentifier, aVersion)
1296 } else { //use the last stored ImageState (if the requested Imageversion coincides)
1297 if aVersion == dh.pLastUpgradeImageState.Version {
1298 pImageState = dh.pLastUpgradeImageState
1299 } else { //state request for an image version different from last processed image version
1300 pImageState = &voltha.ImageState{
1301 Version: aVersion,
1302 //we cannot state something concerning this version
1303 DownloadState: voltha.ImageState_DOWNLOAD_UNKNOWN,
1304 Reason: voltha.ImageState_NO_ERROR,
1305 ImageState: voltha.ImageState_IMAGE_UNKNOWN,
1306 }
mpagenkoaa3afe92021-05-21 16:20:58 +00001307 }
1308 }
mpagenko38662d02021-08-11 09:45:19 +00001309 return pImageState
mpagenkoaa3afe92021-05-21 16:20:58 +00001310}
1311
1312func (dh *deviceHandler) cancelOnuSwUpgrade(ctx context.Context, aImageIdentifier string,
1313 aVersion string, pDeviceImageState *voltha.DeviceImageState) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001314 pDeviceImageState.DeviceId = dh.DeviceID
mpagenko7455fd42021-06-10 16:25:55 +00001315 pDeviceImageState.ImageState.Version = aVersion
mpagenkoaa3afe92021-05-21 16:20:58 +00001316 dh.lockUpgradeFsm.RLock()
1317 if dh.pOnuUpradeFsm != nil {
mpagenko38662d02021-08-11 09:45:19 +00001318 if aVersion == dh.pOnuUpradeFsm.GetImageVersion(ctx) {
1319 // so then we cancel the upgrade operation
1320 // but before we still request the actual ImageState (which should not change with the cancellation)
1321 pDeviceImageState.ImageState.ImageState = dh.pOnuUpradeFsm.GetSpecificImageState(ctx)
1322 dh.lockUpgradeFsm.RUnlock()
1323 pDeviceImageState.ImageState.DownloadState = voltha.ImageState_DOWNLOAD_CANCELLED
1324 pDeviceImageState.ImageState.Reason = voltha.ImageState_CANCELLED_ON_REQUEST
1325 dh.pOnuUpradeFsm.CancelProcessing(ctx, true, voltha.ImageState_CANCELLED_ON_REQUEST) //complete abort
1326 } else { //nothing to cancel, states unknown
1327 dh.lockUpgradeFsm.RUnlock()
1328 pDeviceImageState.ImageState.DownloadState = voltha.ImageState_DOWNLOAD_UNKNOWN
1329 pDeviceImageState.ImageState.Reason = voltha.ImageState_NO_ERROR
1330 pDeviceImageState.ImageState.ImageState = voltha.ImageState_IMAGE_UNKNOWN
1331 }
mpagenkoaa3afe92021-05-21 16:20:58 +00001332 } else {
mpagenko38662d02021-08-11 09:45:19 +00001333 // if no upgrade is ongoing, nothing is canceled and accordingly the states of the requested image are unknown
1334 // reset also the dh handler LastUpgradeImageState (not relevant anymore/cleared)
1335 (*dh.pLastUpgradeImageState).DownloadState = voltha.ImageState_DOWNLOAD_UNKNOWN
1336 (*dh.pLastUpgradeImageState).Reason = voltha.ImageState_NO_ERROR
1337 (*dh.pLastUpgradeImageState).ImageState = voltha.ImageState_IMAGE_UNKNOWN
1338 (*dh.pLastUpgradeImageState).Version = "" //reset to 'no (relevant) upgrade done' (like initial state)
mpagenkoaa3afe92021-05-21 16:20:58 +00001339 dh.lockUpgradeFsm.RUnlock()
1340 pDeviceImageState.ImageState.DownloadState = voltha.ImageState_DOWNLOAD_UNKNOWN
1341 pDeviceImageState.ImageState.Reason = voltha.ImageState_NO_ERROR
mpagenko38662d02021-08-11 09:45:19 +00001342 pDeviceImageState.ImageState.ImageState = voltha.ImageState_IMAGE_UNKNOWN
1343 //an abort request to a not active upgrade processing can be used to reset the device upgrade states completely
mpagenkoaa3afe92021-05-21 16:20:58 +00001344 }
1345}
1346
Holger Hildebrandtfb402a62021-05-26 14:40:49 +00001347func (dh *deviceHandler) getOnuImages(ctx context.Context) (*voltha.OnuImages, error) {
1348
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001349 var onuImageStatus *swupg.OnuImageStatus
Holger Hildebrandtfb402a62021-05-26 14:40:49 +00001350
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001351 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandtfb402a62021-05-26 14:40:49 +00001352 if pDevEntry != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001353 onuImageStatus = swupg.NewOnuImageStatus(dh, pDevEntry)
1354 pDevEntry.MutexOnuImageStatus.Lock()
1355 pDevEntry.POnuImageStatus = onuImageStatus
1356 pDevEntry.MutexOnuImageStatus.Unlock()
Holger Hildebrandtfb402a62021-05-26 14:40:49 +00001357
1358 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001359 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtfb402a62021-05-26 14:40:49 +00001360 return nil, fmt.Errorf("no-valid-OnuDevice-aborting")
1361 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001362 images, err := onuImageStatus.GetOnuImageStatus(ctx)
1363 pDevEntry.MutexOnuImageStatus.Lock()
1364 pDevEntry.POnuImageStatus = nil
1365 pDevEntry.MutexOnuImageStatus.Unlock()
Holger Hildebrandtfb402a62021-05-26 14:40:49 +00001366 return images, err
1367}
1368
Himani Chawla6d2ae152020-09-02 13:11:20 +05301369// deviceHandler methods that implement the adapters interface requests## end #########
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001370// #####################################################################################
1371
1372// ################ to be updated acc. needs of ONU Device ########################
Himani Chawla6d2ae152020-09-02 13:11:20 +05301373// deviceHandler StateMachine related state transition methods ##### begin #########
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001374
dbainbri4d3a0dc2020-12-02 00:33:42 +00001375func (dh *deviceHandler) logStateChange(ctx context.Context, e *fsm.Event) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001376 logger.Debugw(ctx, "Device FSM: ", log.Fields{"event name": string(e.Event), "src state": string(e.Src), "dst state": string(e.Dst), "device-id": dh.DeviceID})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001377}
1378
1379// doStateInit provides the device update to the core
dbainbri4d3a0dc2020-12-02 00:33:42 +00001380func (dh *deviceHandler) doStateInit(ctx context.Context, e *fsm.Event) {
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001381
dbainbri4d3a0dc2020-12-02 00:33:42 +00001382 logger.Debug(ctx, "doStateInit-started")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001383 var err error
1384
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001385 // populate what we know. rest comes later after mib sync
1386 dh.device.Root = false
1387 dh.device.Vendor = "OpenONU"
1388 dh.device.Model = "go"
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001389 dh.device.Reason = cmn.DeviceReasonMap[cmn.DrActivatingOnu]
1390 dh.SetDeviceReason(cmn.DrActivatingOnu)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001391
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001392 dh.logicalDeviceID = dh.DeviceID // really needed - what for ??? //TODO!!!
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001393
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001394 if !dh.IsReconciling() {
1395 logger.Infow(ctx, "DeviceUpdate", log.Fields{"deviceReason": dh.device.Reason, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04001396 if err := dh.updateDeviceInCore(ctx, dh.device); err != nil {
1397 logger.Errorw(ctx, "device-update-failed", log.Fields{"device-id": dh.device.Id, "error": err})
1398 }
Himani Chawlac07fda02020-12-09 16:21:21 +05301399 //TODO Need to Update Device Reason To CORE as part of device update userstory
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001400 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00001401 logger.Debugw(ctx, "reconciling - don't notify core about DeviceUpdate",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001402 log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001403 }
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001404
Himani Chawla4d908332020-08-31 12:30:20 +05301405 dh.parentID = dh.device.ParentId
Holger Hildebrandt24d51952020-05-04 14:03:42 +00001406 dh.ponPortNumber = dh.device.ParentPortNo
1407
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001408 // store proxy parameters for later communication - assumption: invariant, else they have to be requested dynamically!!
1409 dh.ProxyAddressID = dh.device.ProxyAddress.GetDeviceId()
1410 dh.ProxyAddressType = dh.device.ProxyAddress.GetDeviceType()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001411 logger.Debugw(ctx, "device-updated", log.Fields{"device-id": dh.DeviceID, "proxyAddressID": dh.ProxyAddressID,
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001412 "proxyAddressType": dh.ProxyAddressType, "SNR": dh.device.SerialNumber,
Himani Chawla4d908332020-08-31 12:30:20 +05301413 "ParentId": dh.parentID, "ParentPortNo": dh.ponPortNumber})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001414
1415 /*
1416 self._pon = PonPort.create(self, self._pon_port_number)
1417 self._pon.add_peer(self.parent_id, self._pon_port_number)
1418 self.logger.debug('adding-pon-port-to-agent',
1419 type=self._pon.get_port().type,
1420 admin_state=self._pon.get_port().admin_state,
1421 oper_status=self._pon.get_port().oper_status,
1422 )
1423 */
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001424 if !dh.IsReconciling() {
1425 logger.Debugw(ctx, "adding-pon-port", log.Fields{"device-id": dh.DeviceID, "ponPortNo": dh.ponPortNumber})
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001426 var ponPortNo uint32 = 1
1427 if dh.ponPortNumber != 0 {
1428 ponPortNo = dh.ponPortNumber
1429 }
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001430
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001431 pPonPort := &voltha.Port{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001432 DeviceId: dh.DeviceID,
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001433 PortNo: ponPortNo,
1434 Label: fmt.Sprintf("pon-%d", ponPortNo),
1435 Type: voltha.Port_PON_ONU,
1436 OperStatus: voltha.OperStatus_ACTIVE,
Himani Chawla4d908332020-08-31 12:30:20 +05301437 Peers: []*voltha.Port_PeerPort{{DeviceId: dh.parentID, // Peer device is OLT
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001438 PortNo: ponPortNo}}, // Peer port is parent's port number
1439 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001440 if err = dh.CreatePortInCore(ctx, pPonPort); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00001441 logger.Fatalf(ctx, "Device FSM: PortCreated-failed-%s", err)
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001442 e.Cancel(err)
1443 return
1444 }
1445 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001446 logger.Debugw(ctx, "reconciling - pon-port already added", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001447 }
dbainbri4d3a0dc2020-12-02 00:33:42 +00001448 logger.Debug(ctx, "doStateInit-done")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001449}
1450
1451// postInit setups the DeviceEntry for the conerned device
dbainbri4d3a0dc2020-12-02 00:33:42 +00001452func (dh *deviceHandler) postInit(ctx context.Context, e *fsm.Event) {
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001453
dbainbri4d3a0dc2020-12-02 00:33:42 +00001454 logger.Debug(ctx, "postInit-started")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001455 var err error
1456 /*
1457 dh.Client = oop.NewOpenoltClient(dh.clientCon)
1458 dh.pTransitionMap.Handle(ctx, GrpcConnected)
1459 return nil
1460 */
dbainbri4d3a0dc2020-12-02 00:33:42 +00001461 if err = dh.addOnuDeviceEntry(log.WithSpanFromContext(context.TODO(), ctx)); err != nil {
1462 logger.Fatalf(ctx, "Device FSM: addOnuDeviceEntry-failed-%s", err)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001463 e.Cancel(err)
1464 return
1465 }
1466
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001467 if dh.IsReconciling() {
dbainbri4d3a0dc2020-12-02 00:33:42 +00001468 go dh.reconcileDeviceOnuInd(ctx)
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001469 // reconcilement will be continued after mib download is done
1470 }
Girish Gowdrae09a6202021-01-12 18:10:59 -08001471
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001472 /*
1473 ############################################################################
1474 # Setup Alarm handler
1475 self.events = AdapterEvents(self.core_proxy, device.id, self.logical_device_id,
1476 device.serial_number)
1477 ############################################################################
1478 # Setup PM configuration for this device
1479 # Pass in ONU specific options
1480 kwargs = {
1481 OnuPmMetrics.DEFAULT_FREQUENCY_KEY: OnuPmMetrics.DEFAULT_ONU_COLLECTION_FREQUENCY,
1482 'heartbeat': self.heartbeat,
1483 OnuOmciPmMetrics.OMCI_DEV_KEY: self._onu_omci_device
1484 }
1485 self.logger.debug('create-pm-metrics', device_id=device.id, serial_number=device.serial_number)
1486 self._pm_metrics = OnuPmMetrics(self.events, self.core_proxy, self.device_id,
1487 self.logical_device_id, device.serial_number,
1488 grouped=True, freq_override=False, **kwargs)
1489 pm_config = self._pm_metrics.make_proto()
1490 self._onu_omci_device.set_pm_config(self._pm_metrics.omci_pm.openomci_interval_pm)
1491 self.logger.info("initial-pm-config", device_id=device.id, serial_number=device.serial_number)
1492 yield self.core_proxy.device_pm_config_update(pm_config, init=True)
1493
1494 # Note, ONU ID and UNI intf set in add_uni_port method
1495 self._onu_omci_device.alarm_synchronizer.set_alarm_params(mgr=self.events,
1496 ani_ports=[self._pon])
1497
1498 # Code to Run OMCI Test Action
1499 kwargs_omci_test_action = {
1500 OmciTestRequest.DEFAULT_FREQUENCY_KEY:
1501 OmciTestRequest.DEFAULT_COLLECTION_FREQUENCY
1502 }
1503 serial_number = device.serial_number
1504 self._test_request = OmciTestRequest(self.core_proxy,
1505 self.omci_agent, self.device_id,
1506 AniG, serial_number,
1507 self.logical_device_id,
1508 exclusive=False,
1509 **kwargs_omci_test_action)
1510
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001511 self.Enabled = True
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001512 else:
1513 self.logger.info('onu-already-activated')
1514 */
Girish Gowdrae09a6202021-01-12 18:10:59 -08001515
dbainbri4d3a0dc2020-12-02 00:33:42 +00001516 logger.Debug(ctx, "postInit-done")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001517}
1518
1519// doStateConnected get the device info and update to voltha core
1520// for comparison of the original method (not that easy to uncomment): compare here:
1521// voltha-openolt-adapter/adaptercore/device_handler.go
1522// -> this one obviously initiates all communication interfaces of the device ...?
dbainbri4d3a0dc2020-12-02 00:33:42 +00001523func (dh *deviceHandler) doStateConnected(ctx context.Context, e *fsm.Event) {
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001524
dbainbri4d3a0dc2020-12-02 00:33:42 +00001525 logger.Debug(ctx, "doStateConnected-started")
Himani Chawla4d908332020-08-31 12:30:20 +05301526 err := errors.New("device FSM: function not implemented yet")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001527 e.Cancel(err)
dbainbri4d3a0dc2020-12-02 00:33:42 +00001528 logger.Debug(ctx, "doStateConnected-done")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001529}
1530
1531// doStateUp handle the onu up indication and update to voltha core
dbainbri4d3a0dc2020-12-02 00:33:42 +00001532func (dh *deviceHandler) doStateUp(ctx context.Context, e *fsm.Event) {
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001533
dbainbri4d3a0dc2020-12-02 00:33:42 +00001534 logger.Debug(ctx, "doStateUp-started")
Himani Chawla4d908332020-08-31 12:30:20 +05301535 err := errors.New("device FSM: function not implemented yet")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001536 e.Cancel(err)
dbainbri4d3a0dc2020-12-02 00:33:42 +00001537 logger.Debug(ctx, "doStateUp-done")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001538
1539 /*
1540 // Synchronous call to update device state - this method is run in its own go routine
1541 if err := dh.coreProxy.DeviceStateUpdate(ctx, dh.device.Id, voltha.ConnectStatus_REACHABLE,
1542 voltha.OperStatus_ACTIVE); err != nil {
mpagenko01e726e2020-10-23 09:45:29 +00001543 logger.Errorw("Failed to update device with OLT UP indication", log.Fields{"device-id": dh.device.Id, "error": err})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001544 return err
1545 }
1546 return nil
1547 */
1548}
1549
1550// doStateDown handle the onu down indication
dbainbri4d3a0dc2020-12-02 00:33:42 +00001551func (dh *deviceHandler) doStateDown(ctx context.Context, e *fsm.Event) {
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001552
dbainbri4d3a0dc2020-12-02 00:33:42 +00001553 logger.Debug(ctx, "doStateDown-started")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001554 var err error
1555
Holger Hildebrandt24d51952020-05-04 14:03:42 +00001556 device := dh.device
1557 if device == nil {
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001558 /*TODO: needs to handle error scenarios */
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001559 logger.Errorw(ctx, "Failed to fetch handler device", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001560 e.Cancel(err)
1561 return
1562 }
1563
1564 cloned := proto.Clone(device).(*voltha.Device)
dbainbri4d3a0dc2020-12-02 00:33:42 +00001565 logger.Debugw(ctx, "do-state-down", log.Fields{"ClonedDeviceID": cloned.Id})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001566 /*
1567 // Update the all ports state on that device to disable
1568 if er := dh.coreProxy.PortsStateUpdate(ctx, cloned.Id, voltha.OperStatus_UNKNOWN); er != nil {
mpagenko01e726e2020-10-23 09:45:29 +00001569 logger.Errorw("updating-ports-failed", log.Fields{"device-id": device.Id, "error": er})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001570 return er
1571 }
1572
1573 //Update the device oper state and connection status
1574 cloned.OperStatus = voltha.OperStatus_UNKNOWN
1575 cloned.ConnectStatus = common.ConnectStatus_UNREACHABLE
1576 dh.device = cloned
1577
1578 if er := dh.coreProxy.DeviceStateUpdate(ctx, cloned.Id, cloned.ConnectStatus, cloned.OperStatus); er != nil {
mpagenko01e726e2020-10-23 09:45:29 +00001579 logger.Errorw("error-updating-device-state", log.Fields{"device-id": device.Id, "error": er})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001580 return er
1581 }
1582
1583 //get the child device for the parent device
1584 onuDevices, err := dh.coreProxy.GetChildDevices(ctx, dh.device.Id)
1585 if err != nil {
mpagenko01e726e2020-10-23 09:45:29 +00001586 logger.Errorw("failed to get child devices information", log.Fields{"device-id": dh.device.Id, "error": err})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001587 return err
1588 }
1589 for _, onuDevice := range onuDevices.Items {
1590
1591 // Update onu state as down in onu adapter
1592 onuInd := oop.OnuIndication{}
1593 onuInd.OperState = "down"
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001594 er := dh.adapterProxy.SendInterAdapterMessage(ctx, &onuInd, ic.InterAdapterMessageType_ONU_IND_REQUEST,
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001595 "openolt", onuDevice.Type, onuDevice.Id, onuDevice.ProxyAddress.DeviceId, "")
1596 if er != nil {
1597 logger.Errorw("Failed to send inter-adapter-message", log.Fields{"OnuInd": onuInd,
mpagenko01e726e2020-10-23 09:45:29 +00001598 "From Adapter": "openolt", "DevieType": onuDevice.Type, "device-id": onuDevice.Id})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001599 //Do not return here and continue to process other ONUs
1600 }
1601 }
1602 // * Discovered ONUs entries need to be cleared , since after OLT
1603 // is up, it starts sending discovery indications again* /
1604 dh.discOnus = sync.Map{}
mpagenko01e726e2020-10-23 09:45:29 +00001605 logger.Debugw("do-state-down-end", log.Fields{"device-id": device.Id})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001606 return nil
1607 */
Himani Chawla4d908332020-08-31 12:30:20 +05301608 err = errors.New("device FSM: function not implemented yet")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001609 e.Cancel(err)
dbainbri4d3a0dc2020-12-02 00:33:42 +00001610 logger.Debug(ctx, "doStateDown-done")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001611}
1612
Himani Chawla6d2ae152020-09-02 13:11:20 +05301613// deviceHandler StateMachine related state transition methods ##### end #########
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001614// #################################################################################
1615
1616// ###################################################
Himani Chawla6d2ae152020-09-02 13:11:20 +05301617// deviceHandler utility methods ##### begin #########
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001618
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001619//GetOnuDeviceEntry gets the ONU device entry and may wait until its value is defined
1620func (dh *deviceHandler) GetOnuDeviceEntry(ctx context.Context, aWait bool) *mib.OnuDeviceEntry {
mpagenko3af1f032020-06-10 08:53:41 +00001621 dh.lockDevice.RLock()
1622 pOnuDeviceEntry := dh.pOnuOmciDevice
1623 if aWait && pOnuDeviceEntry == nil {
1624 //keep the read sema short to allow for subsequent write
1625 dh.lockDevice.RUnlock()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001626 logger.Debugw(ctx, "Waiting for DeviceEntry to be set ...", log.Fields{"device-id": dh.DeviceID})
mpagenko3af1f032020-06-10 08:53:41 +00001627 // based on concurrent processing the deviceEntry setup may not yet be finished at his point
1628 // so it might be needed to wait here for that event with some timeout
1629 select {
1630 case <-time.After(60 * time.Second): //timer may be discussed ...
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001631 logger.Errorw(ctx, "No valid DeviceEntry set after maxTime", log.Fields{"device-id": dh.DeviceID})
mpagenko3af1f032020-06-10 08:53:41 +00001632 return nil
1633 case <-dh.deviceEntrySet:
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001634 logger.Debugw(ctx, "devicEntry ready now - continue", log.Fields{"device-id": dh.DeviceID})
mpagenko3af1f032020-06-10 08:53:41 +00001635 // if written now, we can return the written value without sema
1636 return dh.pOnuOmciDevice
1637 }
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001638 }
mpagenko3af1f032020-06-10 08:53:41 +00001639 dh.lockDevice.RUnlock()
1640 return pOnuDeviceEntry
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001641}
1642
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001643//setDeviceHandlerEntries sets the ONU device entry within the handler
1644func (dh *deviceHandler) setDeviceHandlerEntries(apDeviceEntry *mib.OnuDeviceEntry, apOnuTp *avcfg.OnuUniTechProf,
1645 apOnuMetricsMgr *pmmgr.OnuMetricsManager, apOnuAlarmMgr *almgr.OnuAlarmManager, apSelfTestHdlr *otst.SelfTestControlBlock) {
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001646 dh.lockDevice.Lock()
1647 defer dh.lockDevice.Unlock()
mpagenkoaf801632020-07-03 10:00:42 +00001648 dh.pOnuOmciDevice = apDeviceEntry
1649 dh.pOnuTP = apOnuTp
Girish Gowdrae09a6202021-01-12 18:10:59 -08001650 dh.pOnuMetricsMgr = apOnuMetricsMgr
Himani Chawlaac1f5ad2021-02-04 21:21:54 +05301651 dh.pAlarmMgr = apOnuAlarmMgr
Girish Gowdra6afb56a2021-04-27 17:47:57 -07001652 dh.pSelfTestHdlr = apSelfTestHdlr
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001653}
1654
Himani Chawla6d2ae152020-09-02 13:11:20 +05301655//addOnuDeviceEntry creates a new ONU device or returns the existing
1656func (dh *deviceHandler) addOnuDeviceEntry(ctx context.Context) error {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001657 logger.Debugw(ctx, "adding-deviceEntry", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001658
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001659 deviceEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001660 if deviceEntry == nil {
1661 /* costum_me_map in python code seems always to be None,
1662 we omit that here first (declaration unclear) -> todo at Adapter specialization ...*/
1663 /* also no 'clock' argument - usage open ...*/
1664 /* and no alarm_db yet (oo.alarm_db) */
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001665 deviceEntry = mib.NewOnuDeviceEntry(ctx, dh.coreClient, dh, dh.pOpenOnuAc)
1666 onuTechProfProc := avcfg.NewOnuUniTechProf(ctx, dh, deviceEntry)
1667 onuMetricsMgr := pmmgr.NewOnuMetricsManager(ctx, dh, deviceEntry)
1668 onuAlarmManager := almgr.NewAlarmManager(ctx, dh, deviceEntry)
1669 selfTestHdlr := otst.NewSelfTestMsgHandlerCb(ctx, dh, deviceEntry)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001670 //error treatment possible //TODO!!!
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001671 dh.setDeviceHandlerEntries(deviceEntry, onuTechProfProc, onuMetricsMgr, onuAlarmManager, selfTestHdlr)
mpagenko3af1f032020-06-10 08:53:41 +00001672 // fire deviceEntry ready event to spread to possibly waiting processing
1673 dh.deviceEntrySet <- true
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001674 logger.Debugw(ctx, "onuDeviceEntry-added", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001675 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001676 logger.Debugw(ctx, "onuDeviceEntry-add: Device already exists", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001677 }
1678 // might be updated with some error handling !!!
1679 return nil
1680}
1681
dbainbri4d3a0dc2020-12-02 00:33:42 +00001682func (dh *deviceHandler) createInterface(ctx context.Context, onuind *oop.OnuIndication) error {
1683 logger.Debugw(ctx, "create_interface-started", log.Fields{"OnuId": onuind.GetOnuId(),
Holger Hildebrandt24d51952020-05-04 14:03:42 +00001684 "OnuIntfId": onuind.GetIntfId(), "OnuSerialNumber": onuind.GetSerialNumber()})
1685
1686 dh.pOnuIndication = onuind // let's revise if storing the pointer is sufficient...
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001687
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001688 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00001689 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001690 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
1691 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00001692 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001693 if !dh.IsReconciling() {
1694 if err := dh.StorePersistentData(ctx); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00001695 logger.Warnw(ctx, "store persistent data error - continue as there will be additional write attempts",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001696 log.Fields{"device-id": dh.DeviceID, "err": err})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00001697 }
dbainbri4d3a0dc2020-12-02 00:33:42 +00001698 logger.Debugw(ctx, "call DeviceStateUpdate upon create interface", log.Fields{"ConnectStatus": voltha.ConnectStatus_REACHABLE,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001699 "OperStatus": voltha.OperStatus_ACTIVATING, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04001700
1701 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001702 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04001703 OperStatus: voltha.OperStatus_ACTIVATING,
1704 ConnStatus: voltha.ConnectStatus_REACHABLE,
1705 }); err != nil {
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001706 //TODO with VOL-3045/VOL-3046: return the error and stop further processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001707 logger.Errorw(ctx, "error-updating-device-state", log.Fields{"device-id": dh.DeviceID, "error": err})
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001708 }
1709 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00001710 logger.Debugw(ctx, "reconciling - don't notify core about DeviceStateUpdate to ACTIVATING",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001711 log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00001712
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001713 pDevEntry.MutexPersOnuConfig.RLock()
1714 if !pDevEntry.SOnuPersistentData.PersUniUnlockDone {
1715 pDevEntry.MutexPersOnuConfig.RUnlock()
dbainbri4d3a0dc2020-12-02 00:33:42 +00001716 logger.Debugw(ctx, "reconciling - uni-ports were not unlocked before adapter restart - resume with a normal start-up",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001717 log.Fields{"device-id": dh.DeviceID})
1718 dh.StopReconciling(ctx, true)
Holger Hildebrandt0da7e6f2021-05-12 13:08:43 +00001719 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001720 pDevEntry.MutexPersOnuConfig.RUnlock()
Holger Hildebrandt3a644642020-12-02 09:46:18 +00001721 }
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001722 }
Holger Hildebrandt24d51952020-05-04 14:03:42 +00001723 // It does not look to me as if makes sense to work with the real core device here, (not the stored clone)?
1724 // in this code the GetDevice would just make a check if the DeviceID's Device still exists in core
1725 // in python code it looks as the started onu_omci_device might have been updated with some new instance state of the core device
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001726 // but I would not know why, and the go code anyway does not work with the device directly anymore in the mib.OnuDeviceEntry
Holger Hildebrandt24d51952020-05-04 14:03:42 +00001727 // so let's just try to keep it simple ...
1728 /*
dbainbri4d3a0dc2020-12-02 00:33:42 +00001729 device, err := dh.coreProxy.GetDevice(log.WithSpanFromContext(context.TODO(), ctx), dh.device.Id, dh.device.Id)
Holger Hildebrandt24d51952020-05-04 14:03:42 +00001730 if err != nil || device == nil {
1731 //TODO: needs to handle error scenarios
1732 logger.Errorw("Failed to fetch device device at creating If", log.Fields{"err": err})
1733 return errors.New("Voltha Device not found")
1734 }
1735 */
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001736
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001737 if err := pDevEntry.Start(log.WithSpanFromContext(context.TODO(), ctx)); err != nil {
Holger Hildebrandt3a644642020-12-02 09:46:18 +00001738 return err
mpagenko3af1f032020-06-10 08:53:41 +00001739 }
Holger Hildebrandt3a644642020-12-02 09:46:18 +00001740
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001741 _ = dh.deviceReasonUpdate(ctx, cmn.DrStartingOpenomci, !dh.IsReconciling())
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001742
1743 /* this might be a good time for Omci Verify message? */
1744 verifyExec := make(chan bool)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001745 omciVerify := otst.NewOmciTestRequest(log.WithSpanFromContext(context.TODO(), ctx),
mpagenko3af1f032020-06-10 08:53:41 +00001746 dh.device.Id, pDevEntry.PDevOmciCC,
mpagenko900ee4b2020-10-12 11:56:34 +00001747 true, true) //exclusive and allowFailure (anyway not yet checked)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001748 omciVerify.PerformOmciTest(log.WithSpanFromContext(context.TODO(), ctx), verifyExec)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001749
1750 /* give the handler some time here to wait for the OMCi verification result
1751 after Timeout start and try MibUpload FSM anyway
1752 (to prevent stopping on just not supported OMCI verification from ONU) */
1753 select {
Holger Hildebrandt366ef192021-05-05 11:07:44 +00001754 case <-time.After(pDevEntry.PDevOmciCC.GetMaxOmciTimeoutWithRetries() * time.Second):
dbainbri4d3a0dc2020-12-02 00:33:42 +00001755 logger.Warn(ctx, "omci start-verification timed out (continue normal)")
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001756 case testresult := <-verifyExec:
dbainbri4d3a0dc2020-12-02 00:33:42 +00001757 logger.Infow(ctx, "Omci start verification done", log.Fields{"result": testresult})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001758 }
1759
1760 /* In py code it looks earlier (on activate ..)
1761 # Code to Run OMCI Test Action
1762 kwargs_omci_test_action = {
1763 OmciTestRequest.DEFAULT_FREQUENCY_KEY:
1764 OmciTestRequest.DEFAULT_COLLECTION_FREQUENCY
1765 }
1766 serial_number = device.serial_number
1767 self._test_request = OmciTestRequest(self.core_proxy,
1768 self.omci_agent, self.device_id,
1769 AniG, serial_number,
1770 self.logical_device_id,
1771 exclusive=False,
1772 **kwargs_omci_test_action)
1773 ...
1774 # Start test requests after a brief pause
1775 if not self._test_request_started:
1776 self._test_request_started = True
1777 tststart = _STARTUP_RETRY_WAIT * (random.randint(1, 5))
1778 reactor.callLater(tststart, self._test_request.start_collector)
1779
1780 */
1781 /* which is then: in omci_test_request.py : */
1782 /*
1783 def start_collector(self, callback=None):
1784 """
1785 Start the collection loop for an adapter if the frequency > 0
1786
1787 :param callback: (callable) Function to call to collect PM data
1788 """
1789 self.logger.info("starting-pm-collection", device_name=self.name, default_freq=self.default_freq)
1790 if callback is None:
1791 callback = self.perform_test_omci
1792
1793 if self.lc is None:
1794 self.lc = LoopingCall(callback)
1795
1796 if self.default_freq > 0:
1797 self.lc.start(interval=self.default_freq / 10)
1798
1799 def perform_test_omci(self):
1800 """
1801 Perform the initial test request
1802 """
1803 ani_g_entities = self._device.configuration.ani_g_entities
1804 ani_g_entities_ids = list(ani_g_entities.keys()) if ani_g_entities \
1805 is not None else None
1806 self._entity_id = ani_g_entities_ids[0]
1807 self.logger.info('perform-test', entity_class=self._entity_class,
1808 entity_id=self._entity_id)
1809 try:
1810 frame = MEFrame(self._entity_class, self._entity_id, []).test()
1811 result = yield self._device.omci_cc.send(frame)
1812 if not result.fields['omci_message'].fields['success_code']:
1813 self.logger.info('Self-Test Submitted Successfully',
1814 code=result.fields[
1815 'omci_message'].fields['success_code'])
1816 else:
1817 raise TestFailure('Test Failure: {}'.format(
1818 result.fields['omci_message'].fields['success_code']))
1819 except TimeoutError as e:
1820 self.deferred.errback(failure.Failure(e))
1821
1822 except Exception as e:
1823 self.logger.exception('perform-test-Error', e=e,
1824 class_id=self._entity_class,
1825 entity_id=self._entity_id)
1826 self.deferred.errback(failure.Failure(e))
1827
1828 */
1829
1830 // PM related heartbeat??? !!!TODO....
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001831 //self._heartbeat.Enabled = True
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001832
mpagenko1cc3cb42020-07-27 15:24:38 +00001833 /* Note: Even though FSM calls look 'synchronous' here, FSM is running in background with the effect that possible errors
1834 * within the MibUpload are not notified in the OnuIndication response, this might be acceptable here,
1835 * as further OltAdapter processing may rely on the deviceReason event 'MibUploadDone' as a result of the FSM processing
Himani Chawla4d908332020-08-31 12:30:20 +05301836 * otherwise some processing synchronization would be required - cmp. e.g TechProfile processing
mpagenko1cc3cb42020-07-27 15:24:38 +00001837 */
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001838 //call MibUploadFSM - transition up to state UlStInSync
1839 pMibUlFsm := pDevEntry.PMibUploadFsm.PFsm
Holger Hildebrandt9ac0d0f2020-05-13 11:22:02 +00001840 if pMibUlFsm != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001841 if pMibUlFsm.Is(mib.UlStDisabled) {
1842 if err := pMibUlFsm.Event(mib.UlEvStart); err != nil {
1843 logger.Errorw(ctx, "MibSyncFsm: Can't go to state starting", log.Fields{"device-id": dh.DeviceID, "err": err})
1844 return fmt.Errorf("can't go to state starting: %s", dh.DeviceID)
Himani Chawla4d908332020-08-31 12:30:20 +05301845 }
dbainbri4d3a0dc2020-12-02 00:33:42 +00001846 logger.Debugw(ctx, "MibSyncFsm", log.Fields{"state": string(pMibUlFsm.Current())})
Himani Chawla4d908332020-08-31 12:30:20 +05301847 //Determine ONU status and start/re-start MIB Synchronization tasks
1848 //Determine if this ONU has ever synchronized
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001849 if pDevEntry.IsNewOnu() {
1850 if err := pMibUlFsm.Event(mib.UlEvResetMib); err != nil {
1851 logger.Errorw(ctx, "MibSyncFsm: Can't go to state resetting_mib", log.Fields{"device-id": dh.DeviceID, "err": err})
1852 return fmt.Errorf("can't go to state resetting_mib: %s", dh.DeviceID)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001853 }
Himani Chawla4d908332020-08-31 12:30:20 +05301854 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001855 if err := pMibUlFsm.Event(mib.UlEvExamineMds); err != nil {
1856 logger.Errorw(ctx, "MibSyncFsm: Can't go to state examine_mds", log.Fields{"device-id": dh.DeviceID, "err": err})
1857 return fmt.Errorf("can't go to examine_mds: %s", dh.DeviceID)
Himani Chawla4d908332020-08-31 12:30:20 +05301858 }
dbainbri4d3a0dc2020-12-02 00:33:42 +00001859 logger.Debugw(ctx, "state of MibSyncFsm", log.Fields{"state": string(pMibUlFsm.Current())})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001860 }
Holger Hildebrandt9ac0d0f2020-05-13 11:22:02 +00001861 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00001862 logger.Errorw(ctx, "wrong state of MibSyncFsm - want: disabled", log.Fields{"have": string(pMibUlFsm.Current()),
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001863 "device-id": dh.DeviceID})
1864 return fmt.Errorf("wrong state of MibSyncFsm: %s", dh.DeviceID)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001865 }
1866 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001867 logger.Errorw(ctx, "MibSyncFsm invalid - cannot be executed!!", log.Fields{"device-id": dh.DeviceID})
1868 return fmt.Errorf("can't execute MibSync: %s", dh.DeviceID)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001869 }
1870 return nil
1871}
1872
dbainbri4d3a0dc2020-12-02 00:33:42 +00001873func (dh *deviceHandler) updateInterface(ctx context.Context, onuind *oop.OnuIndication) error {
mpagenko3af1f032020-06-10 08:53:41 +00001874 //state checking to prevent unneeded processing (eg. on ONU 'unreachable' and 'down')
mpagenkofc4f56e2020-11-04 17:17:49 +00001875 // (but note that the deviceReason may also have changed to e.g. TechProf*Delete_Success in between)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001876 if dh.getDeviceReason() != cmn.DrStoppingOpenomci {
1877 logger.Debugw(ctx, "updateInterface-started - stopping-device", log.Fields{"device-id": dh.DeviceID})
mpagenko2418ab02020-11-12 12:58:06 +00001878
mpagenko900ee4b2020-10-12 11:56:34 +00001879 //stop all running FSM processing - make use of the DH-state as mirrored in the deviceReason
1880 //here no conflict with aborted FSM's should arise as a complete OMCI initialization is assumed on ONU-Up
1881 //but that might change with some simple MDS check on ONU-Up treatment -> attention!!!
Holger Hildebrandt10d98192021-01-27 15:29:31 +00001882 if err := dh.resetFsms(ctx, true); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00001883 logger.Errorw(ctx, "error-updateInterface at FSM stop",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001884 log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko900ee4b2020-10-12 11:56:34 +00001885 // abort: system behavior is just unstable ...
1886 return err
1887 }
mpagenkoa40e99a2020-11-17 13:50:39 +00001888 //all stored persistent data are not valid anymore (loosing knowledge about the connected ONU)
dbainbri4d3a0dc2020-12-02 00:33:42 +00001889 _ = dh.deleteDevicePersistencyData(ctx) //ignore possible errors here and continue, hope is that data is synchronized with new ONU-Up
mpagenko900ee4b2020-10-12 11:56:34 +00001890
1891 //deviceEntry stop without omciCC reset here, regarding the OMCI_CC still valid for this ONU
1892 // - in contrary to disableDevice - compare with processUniDisableStateDoneEvent
1893 //stop the device entry which resets the attached omciCC
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001894 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
mpagenko3af1f032020-06-10 08:53:41 +00001895 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001896 logger.Errorw(ctx, "No valid OnuDevice -aborting", log.Fields{"device-id": dh.DeviceID})
1897 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
mpagenko3af1f032020-06-10 08:53:41 +00001898 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001899 _ = pDevEntry.Stop(log.WithSpanFromContext(context.TODO(), ctx), false)
mpagenko3af1f032020-06-10 08:53:41 +00001900
1901 //TODO!!! remove existing traffic profiles
1902 /* from py code, if TP's exist, remove them - not yet implemented
1903 self._tp = dict()
1904 # Let TP download happen again
1905 for uni_id in self._tp_service_specific_task:
1906 self._tp_service_specific_task[uni_id].clear()
1907 for uni_id in self._tech_profile_download_done:
1908 self._tech_profile_download_done[uni_id].clear()
1909 */
1910
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001911 dh.DisableUniPortStateUpdate(ctx)
mpagenko3af1f032020-06-10 08:53:41 +00001912
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001913 dh.SetReadyForOmciConfig(false)
mpagenkofc4f56e2020-11-04 17:17:49 +00001914
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001915 if err := dh.deviceReasonUpdate(ctx, cmn.DrStoppingOpenomci, true); err != nil {
mpagenko3af1f032020-06-10 08:53:41 +00001916 // abort: system behavior is just unstable ...
1917 return err
1918 }
dbainbri4d3a0dc2020-12-02 00:33:42 +00001919 logger.Debugw(ctx, "call DeviceStateUpdate upon update interface", log.Fields{"ConnectStatus": voltha.ConnectStatus_UNREACHABLE,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001920 "OperStatus": voltha.OperStatus_DISCOVERED, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04001921 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001922 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04001923 ConnStatus: voltha.ConnectStatus_UNREACHABLE,
1924 OperStatus: voltha.OperStatus_DISCOVERED,
1925 }); err != nil {
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00001926 //TODO with VOL-3045/VOL-3046: return the error and stop further processing
dbainbri4d3a0dc2020-12-02 00:33:42 +00001927 logger.Errorw(ctx, "error-updating-device-state unreachable-discovered",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001928 log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko3af1f032020-06-10 08:53:41 +00001929 // abort: system behavior is just unstable ...
1930 return err
1931 }
1932 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001933 logger.Debugw(ctx, "updateInterface - device already stopped", log.Fields{"device-id": dh.DeviceID})
mpagenko3af1f032020-06-10 08:53:41 +00001934 }
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00001935 return nil
1936}
1937
Holger Hildebrandt10d98192021-01-27 15:29:31 +00001938func (dh *deviceHandler) resetFsms(ctx context.Context, includingMibSyncFsm bool) error {
mpagenko900ee4b2020-10-12 11:56:34 +00001939 //all possible FSM's are stopped or reset here to ensure their transition to 'disabled'
1940 //it is not sufficient to stop/reset the latest running FSM as done in previous versions
1941 // as after down/up procedures all FSM's might be active/ongoing (in theory)
1942 // and using the stop/reset event should never harm
1943
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001944 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
mpagenko900ee4b2020-10-12 11:56:34 +00001945 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001946 logger.Errorw(ctx, "No valid OnuDevice -aborting", log.Fields{"device-id": dh.DeviceID})
1947 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
mpagenko900ee4b2020-10-12 11:56:34 +00001948 }
Holger Hildebrandtc8ece362021-05-17 12:01:10 +00001949 if pDevEntry.PDevOmciCC != nil {
mpagenko8cd1bf72021-06-22 10:11:19 +00001950 pDevEntry.PDevOmciCC.CancelRequestMonitoring(ctx)
Holger Hildebrandtc8ece362021-05-17 12:01:10 +00001951 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001952 pDevEntry.MutexOnuImageStatus.RLock()
1953 if pDevEntry.POnuImageStatus != nil {
1954 pDevEntry.POnuImageStatus.CancelProcessing(ctx)
Holger Hildebrandtfb402a62021-05-26 14:40:49 +00001955 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001956 pDevEntry.MutexOnuImageStatus.RUnlock()
mpagenkoaa3afe92021-05-21 16:20:58 +00001957
Holger Hildebrandt10d98192021-01-27 15:29:31 +00001958 if includingMibSyncFsm {
Holger Hildebrandtb4563ab2021-04-14 10:27:20 +00001959 pDevEntry.CancelProcessing(ctx)
mpagenko900ee4b2020-10-12 11:56:34 +00001960 }
1961 //MibDownload may run
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001962 pMibDlFsm := pDevEntry.PMibDownloadFsm.PFsm
mpagenko900ee4b2020-10-12 11:56:34 +00001963 if pMibDlFsm != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001964 _ = pMibDlFsm.Event(mib.DlEvReset)
mpagenko900ee4b2020-10-12 11:56:34 +00001965 }
1966 //port lock/unlock FSM's may be active
1967 if dh.pUnlockStateFsm != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001968 _ = dh.pUnlockStateFsm.PAdaptFsm.PFsm.Event(uniprt.UniEvReset)
mpagenko900ee4b2020-10-12 11:56:34 +00001969 }
1970 if dh.pLockStateFsm != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001971 _ = dh.pLockStateFsm.PAdaptFsm.PFsm.Event(uniprt.UniEvReset)
mpagenko900ee4b2020-10-12 11:56:34 +00001972 }
1973 //techProfile related PonAniConfigFsm FSM may be active
1974 if dh.pOnuTP != nil {
1975 // should always be the case here
1976 // FSM stop maybe encapsulated as OnuTP method - perhaps later in context of module splitting
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001977 if dh.pOnuTP.PAniConfigFsm != nil {
1978 for uniTP := range dh.pOnuTP.PAniConfigFsm {
1979 dh.pOnuTP.PAniConfigFsm[uniTP].CancelProcessing(ctx)
Girish Gowdra041dcb32020-11-16 16:54:30 -08001980 }
mpagenko900ee4b2020-10-12 11:56:34 +00001981 }
1982 for _, uniPort := range dh.uniEntityMap {
mpagenko900ee4b2020-10-12 11:56:34 +00001983 // reset the possibly existing VlanConfigFsm
mpagenkof1fc3862021-02-16 10:09:52 +00001984 dh.lockVlanConfig.RLock()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001985 if pVlanFilterFsm, exist := dh.UniVlanConfigFsmMap[uniPort.UniID]; exist {
mpagenko900ee4b2020-10-12 11:56:34 +00001986 //VlanFilterFsm exists and was already started
mpagenko7d6bb022021-03-11 15:07:55 +00001987 dh.lockVlanConfig.RUnlock()
1988 //reset of all Fsm is always accompanied by global persistency data removal
1989 // no need to remove specific data
1990 pVlanFilterFsm.RequestClearPersistency(false)
1991 //ensure the FSM processing is stopped in case waiting for some response
mpagenko73143992021-04-09 15:17:10 +00001992 pVlanFilterFsm.CancelProcessing(ctx)
mpagenkof1fc3862021-02-16 10:09:52 +00001993 } else {
1994 dh.lockVlanConfig.RUnlock()
mpagenko900ee4b2020-10-12 11:56:34 +00001995 }
1996 }
1997 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00001998 if dh.GetCollectorIsRunning() {
Holger Hildebrandt10d98192021-01-27 15:29:31 +00001999 // Stop collector routine
2000 dh.stopCollector <- true
2001 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002002 if dh.GetAlarmManagerIsRunning(ctx) {
Himani Chawla4c1d4c72021-02-18 12:14:31 +05302003 dh.stopAlarmManager <- true
2004 }
Girish Gowdra10123c02021-08-30 11:52:06 -07002005 if dh.pSelfTestHdlr.GetSelfTestHandlerIsRunning() {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002006 dh.pSelfTestHdlr.StopSelfTestModule <- true
Girish Gowdra10123c02021-08-30 11:52:06 -07002007 }
Himani Chawla4c1d4c72021-02-18 12:14:31 +05302008
mpagenko80622a52021-02-09 16:53:23 +00002009 //reset a possibly running upgrade FSM
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002010 // (note the Upgrade FSM may stay alive e.g. in state UpgradeStWaitForCommit to endure the ONU reboot)
mpagenko80622a52021-02-09 16:53:23 +00002011 dh.lockUpgradeFsm.RLock()
mpagenko38662d02021-08-11 09:45:19 +00002012 lopOnuUpradeFsm := dh.pOnuUpradeFsm
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002013 //lockUpgradeFsm must be release before cancellation as this may implicitly request RemoveOnuUpgradeFsm()
mpagenko80622a52021-02-09 16:53:23 +00002014 dh.lockUpgradeFsm.RUnlock()
mpagenko38662d02021-08-11 09:45:19 +00002015 if lopOnuUpradeFsm != nil {
2016 lopOnuUpradeFsm.CancelProcessing(ctx, false, voltha.ImageState_CANCELLED_ON_ONU_STATE) //conditional cancel
2017 }
mpagenko80622a52021-02-09 16:53:23 +00002018
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002019 logger.Infow(ctx, "resetFsms done", log.Fields{"device-id": dh.DeviceID})
mpagenko900ee4b2020-10-12 11:56:34 +00002020 return nil
2021}
2022
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002023func (dh *deviceHandler) processMibDatabaseSyncEvent(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
2024 logger.Debugw(ctx, "MibInSync event received, adding uni ports and locking the ONU interfaces", log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302025
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002026 // store persistent data collected during MIB upload processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002027 if err := dh.StorePersistentData(ctx); err != nil {
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002028 logger.Warnw(ctx, "store persistent data error - continue as there will be additional write attempts",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002029 log.Fields{"device-id": dh.DeviceID, "err": err})
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002030 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002031 _ = dh.deviceReasonUpdate(ctx, cmn.DrDiscoveryMibsyncComplete, !dh.IsReconciling())
2032 dh.AddAllUniPorts(ctx)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002033
mpagenkoa40e99a2020-11-17 13:50:39 +00002034 /* 200605: lock processing after initial MIBUpload removed now as the ONU should be in the lock state per default here */
2035 /* 201117: build_dt-berlin-pod-openonugo_1T8GEM_voltha_DT_openonugo_master_test runs into error TC
2036 * 'Test Disable ONUs and OLT Then Delete ONUs and OLT for DT' with Sercom ONU, which obviously needs
2037 * disable/enable toggling here to allow traffic
2038 * but moreover it might be useful for tracking the interface operState changes if this will be implemented,
2039 * like the py comment says:
2040 * # start by locking all the unis till mib sync and initial mib is downloaded
2041 * # this way we can capture the port down/up events when we are ready
2042 */
Himani Chawla26e555c2020-08-31 12:30:20 +05302043
mpagenkoa40e99a2020-11-17 13:50:39 +00002044 // Init Uni Ports to Admin locked state
2045 // *** should generate UniLockStateDone event *****
2046 if dh.pLockStateFsm == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002047 dh.createUniLockFsm(ctx, true, cmn.UniLockStateDone)
mpagenkoa40e99a2020-11-17 13:50:39 +00002048 } else { //LockStateFSM already init
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002049 dh.pLockStateFsm.SetSuccessEvent(cmn.UniLockStateDone)
dbainbri4d3a0dc2020-12-02 00:33:42 +00002050 dh.runUniLockFsm(ctx, true)
mpagenkoa40e99a2020-11-17 13:50:39 +00002051 }
2052}
2053
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002054func (dh *deviceHandler) processUniLockStateDoneEvent(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
2055 logger.Infow(ctx, "UniLockStateDone event: Starting MIB download", log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302056 /* Mib download procedure -
2057 ***** should run over 'downloaded' state and generate MibDownloadDone event *****
2058 */
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002059 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002060 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002061 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002062 return
2063 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002064 pMibDlFsm := pDevEntry.PMibDownloadFsm.PFsm
Himani Chawla26e555c2020-08-31 12:30:20 +05302065 if pMibDlFsm != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002066 if pMibDlFsm.Is(mib.DlStDisabled) {
2067 if err := pMibDlFsm.Event(mib.DlEvStart); err != nil {
2068 logger.Errorw(ctx, "MibDownloadFsm: Can't go to state starting", log.Fields{"device-id": dh.DeviceID, "err": err})
Himani Chawla26e555c2020-08-31 12:30:20 +05302069 // maybe try a FSM reset and then again ... - TODO!!!
2070 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002071 logger.Debugw(ctx, "MibDownloadFsm", log.Fields{"state": string(pMibDlFsm.Current())})
Himani Chawla26e555c2020-08-31 12:30:20 +05302072 // maybe use more specific states here for the specific download steps ...
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002073 if err := pMibDlFsm.Event(mib.DlEvCreateGal); err != nil {
2074 logger.Errorw(ctx, "MibDownloadFsm: Can't start CreateGal", log.Fields{"device-id": dh.DeviceID, "err": err})
Himani Chawla26e555c2020-08-31 12:30:20 +05302075 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002076 logger.Debugw(ctx, "state of MibDownloadFsm", log.Fields{"state": string(pMibDlFsm.Current())})
Himani Chawla26e555c2020-08-31 12:30:20 +05302077 //Begin MIB data download (running autonomously)
2078 }
2079 }
2080 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002081 logger.Errorw(ctx, "wrong state of MibDownloadFsm - want: disabled", log.Fields{"have": string(pMibDlFsm.Current()),
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002082 "device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302083 // maybe try a FSM reset and then again ... - TODO!!!
2084 }
2085 /***** Mib download started */
2086 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002087 logger.Errorw(ctx, "MibDownloadFsm invalid - cannot be executed!!", log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302088 }
2089}
2090
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002091func (dh *deviceHandler) processMibDownloadDoneEvent(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
2092 logger.Debugw(ctx, "MibDownloadDone event received, unlocking the ONU interfaces", log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302093 //initiate DevStateUpdate
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002094 if !dh.IsReconciling() {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002095 logger.Debugw(ctx, "call DeviceStateUpdate upon mib-download done", log.Fields{"ConnectStatus": voltha.ConnectStatus_REACHABLE,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002096 "OperStatus": voltha.OperStatus_ACTIVE, "device-id": dh.DeviceID})
mpagenko15ff4a52021-03-02 10:09:20 +00002097 //we allow a possible OnuSw image commit only in the normal startup, not at reconciling
2098 // in case of adapter restart connected to an ONU upgrade I would not rely on the image quality
2099 // maybe some 'forced' commitment can be done in this situation from system management (or upgrade restarted)
2100 dh.checkOnOnuImageCommit(ctx)
khenaidoo7d3c5582021-08-11 18:09:44 -04002101 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002102 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04002103 ConnStatus: voltha.ConnectStatus_REACHABLE,
2104 OperStatus: voltha.OperStatus_ACTIVE,
2105 }); err != nil {
Himani Chawla26e555c2020-08-31 12:30:20 +05302106 //TODO with VOL-3045/VOL-3046: return the error and stop further processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002107 logger.Errorw(ctx, "error-updating-device-state", log.Fields{"device-id": dh.DeviceID, "error": err})
Himani Chawla26e555c2020-08-31 12:30:20 +05302108 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002109 logger.Debugw(ctx, "dev state updated to 'Oper.Active'", log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302110 }
2111 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002112 logger.Debugw(ctx, "reconciling - don't notify core about DeviceStateUpdate to ACTIVE",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002113 log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302114 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002115 _ = dh.deviceReasonUpdate(ctx, cmn.DrInitialMibDownloaded, !dh.IsReconciling())
Girish Gowdrae0140f02021-02-02 16:55:09 -08002116
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002117 if !dh.GetCollectorIsRunning() {
Girish Gowdra7b0ee5c2021-03-19 21:48:15 -07002118 // Start PM collector routine
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002119 go dh.StartCollector(ctx)
Girish Gowdra7b0ee5c2021-03-19 21:48:15 -07002120 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002121 if !dh.GetAlarmManagerIsRunning(ctx) {
2122 go dh.StartAlarmManager(ctx)
Girish Gowdra7b0ee5c2021-03-19 21:48:15 -07002123 }
2124
Girish Gowdrae0140f02021-02-02 16:55:09 -08002125 // Initialize classical L2 PM Interval Counters
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002126 if err := dh.pOnuMetricsMgr.PAdaptFsm.PFsm.Event(pmmgr.L2PmEventInit); err != nil {
Girish Gowdrae0140f02021-02-02 16:55:09 -08002127 // There is no way we should be landing here, but if we do then
2128 // there is nothing much we can do about this other than log error
2129 logger.Errorw(ctx, "error starting l2 pm fsm", log.Fields{"device-id": dh.device.Id, "err": err})
2130 }
2131
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002132 dh.SetReadyForOmciConfig(true)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002133
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002134 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002135 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002136 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002137 return
2138 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002139 pDevEntry.MutexPersOnuConfig.RLock()
2140 if dh.IsReconciling() && pDevEntry.SOnuPersistentData.PersUniDisableDone {
2141 pDevEntry.MutexPersOnuConfig.RUnlock()
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002142 logger.Debugw(ctx, "reconciling - uni-ports were disabled by admin before adapter restart - keep the ports locked",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002143 log.Fields{"device-id": dh.DeviceID})
2144 go dh.ReconcileDeviceTechProf(ctx)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002145 // reconcilement will be continued after ani config is done
2146 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002147 pDevEntry.MutexPersOnuConfig.RUnlock()
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002148 // *** should generate UniUnlockStateDone event *****
2149 if dh.pUnlockStateFsm == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002150 dh.createUniLockFsm(ctx, false, cmn.UniUnlockStateDone)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002151 } else { //UnlockStateFSM already init
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002152 dh.pUnlockStateFsm.SetSuccessEvent(cmn.UniUnlockStateDone)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002153 dh.runUniLockFsm(ctx, false)
2154 }
Himani Chawla26e555c2020-08-31 12:30:20 +05302155 }
2156}
2157
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002158func (dh *deviceHandler) processUniUnlockStateDoneEvent(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
2159 dh.EnableUniPortStateUpdate(ctx) //cmp python yield self.enable_ports()
Himani Chawla26e555c2020-08-31 12:30:20 +05302160
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002161 if !dh.IsReconciling() {
2162 logger.Infow(ctx, "UniUnlockStateDone event: Sending OnuUp event", log.Fields{"device-id": dh.DeviceID})
ozgecanetsia2f05ed32021-05-31 17:13:48 +03002163 raisedTs := time.Now().Unix()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002164 go dh.sendOnuOperStateEvent(ctx, voltha.OperStatus_ACTIVE, dh.DeviceID, raisedTs) //cmp python onu_active_event
2165 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002166 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002167 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002168 return
2169 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002170 pDevEntry.MutexPersOnuConfig.Lock()
2171 pDevEntry.SOnuPersistentData.PersUniUnlockDone = true
2172 pDevEntry.MutexPersOnuConfig.Unlock()
2173 if err := dh.StorePersistentData(ctx); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002174 logger.Warnw(ctx, "store persistent data error - continue for now as there will be additional write attempts",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002175 log.Fields{"device-id": dh.DeviceID, "err": err})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002176 }
Himani Chawla26e555c2020-08-31 12:30:20 +05302177 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002178 logger.Debugw(ctx, "reconciling - don't notify core that onu went to active but trigger tech profile config",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002179 log.Fields{"device-id": dh.DeviceID})
2180 go dh.ReconcileDeviceTechProf(ctx)
Holger Hildebrandt47555e72020-09-21 11:07:24 +00002181 // reconcilement will be continued after ani config is done
Himani Chawla26e555c2020-08-31 12:30:20 +05302182 }
2183}
2184
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002185func (dh *deviceHandler) processUniDisableStateDoneEvent(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002186 logger.Debugw(ctx, "DeviceStateUpdate upon disable", log.Fields{"ConnectStatus": voltha.ConnectStatus_REACHABLE,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002187 "OperStatus": voltha.OperStatus_UNKNOWN, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04002188
2189 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002190 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04002191 ConnStatus: voltha.ConnectStatus_REACHABLE,
2192 OperStatus: voltha.OperStatus_UNKNOWN,
2193 }); err != nil {
mpagenko900ee4b2020-10-12 11:56:34 +00002194 //TODO with VOL-3045/VOL-3046: return the error and stop further processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002195 logger.Errorw(ctx, "error-updating-device-state", log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko900ee4b2020-10-12 11:56:34 +00002196 }
2197
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002198 logger.Debugw(ctx, "DeviceReasonUpdate upon disable", log.Fields{"reason": cmn.DeviceReasonMap[cmn.DrOmciAdminLock], "device-id": dh.DeviceID})
mpagenko900ee4b2020-10-12 11:56:34 +00002199 // DeviceReason to update acc.to modified py code as per beginning of Sept 2020
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002200 _ = dh.deviceReasonUpdate(ctx, cmn.DrOmciAdminLock, true)
mpagenko900ee4b2020-10-12 11:56:34 +00002201
2202 //transfer the modified logical uni port state
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002203 dh.DisableUniPortStateUpdate(ctx)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002204
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002205 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002206 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002207 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002208 return
2209 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002210 pDevEntry.MutexPersOnuConfig.Lock()
2211 pDevEntry.SOnuPersistentData.PersUniDisableDone = true
2212 pDevEntry.MutexPersOnuConfig.Unlock()
2213 if err := dh.StorePersistentData(ctx); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002214 logger.Warnw(ctx, "store persistent data error - continue for now as there will be additional write attempts",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002215 log.Fields{"device-id": dh.DeviceID, "err": err})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002216 }
mpagenko900ee4b2020-10-12 11:56:34 +00002217}
2218
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002219func (dh *deviceHandler) processUniEnableStateDoneEvent(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002220 logger.Debugw(ctx, "DeviceStateUpdate upon re-enable", log.Fields{"ConnectStatus": voltha.ConnectStatus_REACHABLE,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002221 "OperStatus": voltha.OperStatus_ACTIVE, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04002222 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002223 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04002224 ConnStatus: voltha.ConnectStatus_REACHABLE,
2225 OperStatus: voltha.OperStatus_ACTIVE,
2226 }); err != nil {
mpagenko900ee4b2020-10-12 11:56:34 +00002227 //TODO with VOL-3045/VOL-3046: return the error and stop further processing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002228 logger.Errorw(ctx, "error-updating-device-state", log.Fields{"device-id": dh.DeviceID, "error": err})
mpagenko900ee4b2020-10-12 11:56:34 +00002229 }
2230
dbainbri4d3a0dc2020-12-02 00:33:42 +00002231 logger.Debugw(ctx, "DeviceReasonUpdate upon re-enable", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002232 "reason": cmn.DeviceReasonMap[cmn.DrOnuReenabled], "device-id": dh.DeviceID})
mpagenko900ee4b2020-10-12 11:56:34 +00002233 // DeviceReason to update acc.to modified py code as per beginning of Sept 2020
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002234 _ = dh.deviceReasonUpdate(ctx, cmn.DrOnuReenabled, true)
mpagenko900ee4b2020-10-12 11:56:34 +00002235
2236 //transfer the modified logical uni port state
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002237 dh.EnableUniPortStateUpdate(ctx)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002238
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002239 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002240 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002241 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002242 return
2243 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002244 pDevEntry.MutexPersOnuConfig.Lock()
2245 pDevEntry.SOnuPersistentData.PersUniDisableDone = false
2246 pDevEntry.MutexPersOnuConfig.Unlock()
2247 if err := dh.StorePersistentData(ctx); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002248 logger.Warnw(ctx, "store persistent data error - continue for now as there will be additional write attempts",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002249 log.Fields{"device-id": dh.DeviceID, "err": err})
Holger Hildebrandt3a644642020-12-02 09:46:18 +00002250 }
mpagenko900ee4b2020-10-12 11:56:34 +00002251}
2252
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002253func (dh *deviceHandler) processOmciAniConfigDoneEvent(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
2254 if devEvent == cmn.OmciAniConfigDone {
2255 logger.Debugw(ctx, "OmciAniConfigDone event received", log.Fields{"device-id": dh.DeviceID})
mpagenkofc4f56e2020-11-04 17:17:49 +00002256 // attention: the device reason update is done based on ONU-UNI-Port related activity
2257 // - which may cause some inconsistency
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002258 if dh.getDeviceReason() != cmn.DrTechProfileConfigDownloadSuccess {
mpagenkofc4f56e2020-11-04 17:17:49 +00002259 // which may be the case from some previous actvity even on this UNI Port (but also other UNI ports)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002260 _ = dh.deviceReasonUpdate(ctx, cmn.DrTechProfileConfigDownloadSuccess, !dh.IsReconciling())
Himani Chawla26e555c2020-08-31 12:30:20 +05302261 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002262 if dh.IsReconciling() {
2263 go dh.ReconcileDeviceFlowConfig(ctx)
mpagenkofc4f56e2020-11-04 17:17:49 +00002264 }
2265 } else { // should be the OmciAniResourceRemoved block
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002266 logger.Debugw(ctx, "OmciAniResourceRemoved event received", log.Fields{"device-id": dh.DeviceID})
mpagenkofc4f56e2020-11-04 17:17:49 +00002267 // attention: the device reason update is done based on ONU-UNI-Port related activity
2268 // - which may cause some inconsistency
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002269 if dh.getDeviceReason() != cmn.DrTechProfileConfigDeleteSuccess {
mpagenkofc4f56e2020-11-04 17:17:49 +00002270 // which may be the case from some previous actvity even on this ONU port (but also other UNI ports)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002271 _ = dh.deviceReasonUpdate(ctx, cmn.DrTechProfileConfigDeleteSuccess, true)
mpagenkofc4f56e2020-11-04 17:17:49 +00002272 }
Holger Hildebrandt47555e72020-09-21 11:07:24 +00002273 }
Himani Chawla26e555c2020-08-31 12:30:20 +05302274}
2275
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002276func (dh *deviceHandler) processOmciVlanFilterDoneEvent(ctx context.Context, aDevEvent cmn.OnuDeviceEvent) {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002277 logger.Debugw(ctx, "OmciVlanFilterDone event received",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002278 log.Fields{"device-id": dh.DeviceID, "event": aDevEvent})
Himani Chawla26e555c2020-08-31 12:30:20 +05302279 // attention: the device reason update is done based on ONU-UNI-Port related activity
2280 // - which may cause some inconsistency
Himani Chawla26e555c2020-08-31 12:30:20 +05302281
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002282 if aDevEvent == cmn.OmciVlanFilterAddDone || aDevEvent == cmn.OmciVlanFilterAddDoneNoKvStore {
2283 if dh.getDeviceReason() != cmn.DrOmciFlowsPushed {
mpagenkofc4f56e2020-11-04 17:17:49 +00002284 // which may be the case from some previous actvity on another UNI Port of the ONU
2285 // or even some previous flow add activity on the same port
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002286 _ = dh.deviceReasonUpdate(ctx, cmn.DrOmciFlowsPushed, !dh.IsReconciling())
2287 if dh.IsReconciling() {
Holger Hildebrandt1b8f4ad2021-03-25 15:53:51 +00002288 go dh.reconcileEnd(ctx)
mpagenkofc4f56e2020-11-04 17:17:49 +00002289 }
2290 }
2291 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002292 if dh.getDeviceReason() != cmn.DrOmciFlowsDeleted {
mpagenkofc4f56e2020-11-04 17:17:49 +00002293 //not relevant for reconcile
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002294 _ = dh.deviceReasonUpdate(ctx, cmn.DrOmciFlowsDeleted, true)
Holger Hildebrandt47555e72020-09-21 11:07:24 +00002295 }
Himani Chawla26e555c2020-08-31 12:30:20 +05302296 }
mpagenkof1fc3862021-02-16 10:09:52 +00002297
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002298 if aDevEvent == cmn.OmciVlanFilterAddDone || aDevEvent == cmn.OmciVlanFilterRemDone {
mpagenkof1fc3862021-02-16 10:09:52 +00002299 //events that request KvStore write
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002300 if err := dh.StorePersistentData(ctx); err != nil {
mpagenkof1fc3862021-02-16 10:09:52 +00002301 logger.Warnw(ctx, "store persistent data error - continue for now as there will be additional write attempts",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002302 log.Fields{"device-id": dh.DeviceID, "err": err})
mpagenkof1fc3862021-02-16 10:09:52 +00002303 }
2304 } else {
2305 logger.Debugw(ctx, "OmciVlanFilter*Done* - write to KvStore not requested",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002306 log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt10d98192021-01-27 15:29:31 +00002307 }
Himani Chawla26e555c2020-08-31 12:30:20 +05302308}
2309
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002310//DeviceProcStatusUpdate evaluates possible processing events and initiates according next activities
2311func (dh *deviceHandler) DeviceProcStatusUpdate(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
Himani Chawla4d908332020-08-31 12:30:20 +05302312 switch devEvent {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002313 case cmn.MibDatabaseSync:
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002314 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002315 dh.processMibDatabaseSyncEvent(ctx, devEvent)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002316 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002317 case cmn.UniLockStateDone:
mpagenkoa40e99a2020-11-17 13:50:39 +00002318 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002319 dh.processUniLockStateDoneEvent(ctx, devEvent)
mpagenkoa40e99a2020-11-17 13:50:39 +00002320 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002321 case cmn.MibDownloadDone:
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002322 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002323 dh.processMibDownloadDoneEvent(ctx, devEvent)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002324 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002325 case cmn.UniUnlockStateDone:
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002326 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002327 dh.processUniUnlockStateDoneEvent(ctx, devEvent)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002328 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002329 case cmn.UniEnableStateDone:
mpagenko900ee4b2020-10-12 11:56:34 +00002330 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002331 dh.processUniEnableStateDoneEvent(ctx, devEvent)
mpagenko900ee4b2020-10-12 11:56:34 +00002332 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002333 case cmn.UniDisableStateDone:
mpagenko900ee4b2020-10-12 11:56:34 +00002334 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002335 dh.processUniDisableStateDoneEvent(ctx, devEvent)
mpagenko900ee4b2020-10-12 11:56:34 +00002336 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002337 case cmn.OmciAniConfigDone, cmn.OmciAniResourceRemoved:
mpagenko3dbcdd22020-07-22 07:38:45 +00002338 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002339 dh.processOmciAniConfigDoneEvent(ctx, devEvent)
mpagenko3dbcdd22020-07-22 07:38:45 +00002340 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002341 case cmn.OmciVlanFilterAddDone, cmn.OmciVlanFilterAddDoneNoKvStore, cmn.OmciVlanFilterRemDone, cmn.OmciVlanFilterRemDoneNoKvStore:
mpagenkodff5dda2020-08-28 11:52:01 +00002342 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002343 dh.processOmciVlanFilterDoneEvent(ctx, devEvent)
mpagenkodff5dda2020-08-28 11:52:01 +00002344 }
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002345 default:
2346 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002347 logger.Debugw(ctx, "unhandled-device-event", log.Fields{"device-id": dh.DeviceID, "event": devEvent})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002348 }
2349 } //switch
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00002350}
2351
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002352func (dh *deviceHandler) addUniPort(ctx context.Context, aUniInstNo uint16, aUniID uint8, aPortType cmn.UniPortType) {
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002353 // parameters are IntfId, OnuId, uniId
dbainbri4d3a0dc2020-12-02 00:33:42 +00002354 uniNo := mkUniPortNum(ctx, dh.pOnuIndication.GetIntfId(), dh.pOnuIndication.GetOnuId(),
Himani Chawla4d908332020-08-31 12:30:20 +05302355 uint32(aUniID))
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002356 if _, present := dh.uniEntityMap[uniNo]; present {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002357 logger.Warnw(ctx, "OnuUniPort-add: Port already exists", log.Fields{"for InstanceId": aUniInstNo})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00002358 } else {
Himani Chawla4d908332020-08-31 12:30:20 +05302359 //with arguments aUniID, a_portNo, aPortType
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002360 pUniPort := cmn.NewOnuUniPort(ctx, aUniID, uniNo, aUniInstNo, aPortType)
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00002361 if pUniPort == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002362 logger.Warnw(ctx, "OnuUniPort-add: Could not create Port", log.Fields{"for InstanceId": aUniInstNo})
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00002363 } else {
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002364 //store UniPort with the System-PortNumber key
2365 dh.uniEntityMap[uniNo] = pUniPort
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002366 if !dh.IsReconciling() {
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00002367 // create announce the UniPort to the core as VOLTHA Port object
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002368 if err := pUniPort.CreateVolthaPort(ctx, dh); err == nil {
2369 logger.Infow(ctx, "OnuUniPort-added", log.Fields{"for PortNo": uniNo})
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00002370 } //error logging already within UniPort method
2371 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002372 logger.Debugw(ctx, "reconciling - OnuUniPort already added", log.Fields{"for PortNo": uniNo, "device-id": dh.DeviceID})
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00002373 }
Holger Hildebrandt0f9b88d2020-04-20 13:33:25 +00002374 }
2375 }
2376}
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002377
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002378func (dh *deviceHandler) AddAllUniPorts(ctx context.Context) {
2379 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002380 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002381 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002382 return
2383 }
2384 i := uint8(0) //UNI Port limit: see MaxUnisPerOnu (by now 16) (OMCI supports max 255 p.b.)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002385 if pptpInstKeys := pDevEntry.GetOnuDB().GetSortedInstKeys(
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002386 ctx, me.PhysicalPathTerminationPointEthernetUniClassID); len(pptpInstKeys) > 0 {
2387 for _, mgmtEntityID := range pptpInstKeys {
2388 logger.Debugw(ctx, "Add PPTPEthUni port for MIB-stored instance:", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002389 "device-id": dh.DeviceID, "PPTPEthUni EntityID": mgmtEntityID})
2390 dh.addUniPort(ctx, mgmtEntityID, i, cmn.UniPPTP)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002391 i++
2392 }
2393 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002394 logger.Debugw(ctx, "No PPTP instances found", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002395 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002396 if veipInstKeys := pDevEntry.GetOnuDB().GetSortedInstKeys(
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002397 ctx, me.VirtualEthernetInterfacePointClassID); len(veipInstKeys) > 0 {
2398 for _, mgmtEntityID := range veipInstKeys {
2399 logger.Debugw(ctx, "Add VEIP for MIB-stored instance:", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002400 "device-id": dh.DeviceID, "VEIP EntityID": mgmtEntityID})
2401 dh.addUniPort(ctx, mgmtEntityID, i, cmn.UniVEIP)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002402 i++
2403 }
2404 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002405 logger.Debugw(ctx, "No VEIP instances found", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002406 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002407 if potsInstKeys := pDevEntry.GetOnuDB().GetSortedInstKeys(
ozgecanetsia124d9732021-09-16 14:31:57 +03002408 ctx, me.PhysicalPathTerminationPointPotsUniClassID); len(potsInstKeys) > 0 {
2409 for _, mgmtEntityID := range potsInstKeys {
2410 logger.Debugw(ctx, "Add PPTP Pots UNI for MIB-stored instance:", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002411 "device-id": dh.DeviceID, "PPTP Pots UNI EntityID": mgmtEntityID})
2412 dh.addUniPort(ctx, mgmtEntityID, i, cmn.UniPPTPPots)
ozgecanetsia124d9732021-09-16 14:31:57 +03002413 i++
2414 }
2415 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002416 logger.Debugw(ctx, "No PPTP Pots UNI instances found", log.Fields{"device-id": dh.DeviceID})
ozgecanetsia124d9732021-09-16 14:31:57 +03002417 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002418 if i == 0 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002419 logger.Warnw(ctx, "No UniG instances found", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002420 }
2421}
2422
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002423// EnableUniPortStateUpdate enables UniPortState and update core port state accordingly
2424func (dh *deviceHandler) EnableUniPortStateUpdate(ctx context.Context) {
Holger Hildebrandtbe674422020-05-05 13:05:30 +00002425 // py code was updated 2003xx to activate the real ONU UNI ports per OMCI (VEIP or PPTP)
Himani Chawla4d908332020-08-31 12:30:20 +05302426 // but towards core only the first port active state is signaled
Holger Hildebrandtbe674422020-05-05 13:05:30 +00002427 // with following remark:
2428 // # TODO: for now only support the first UNI given no requirement for multiple uni yet. Also needed to reduce flow
2429 // # load on the core
2430
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002431 // lock_ports(false) as done in py code here is shifted to separate call from device event processing
Holger Hildebrandtbe674422020-05-05 13:05:30 +00002432
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002433 for uniNo, uniPort := range dh.uniEntityMap {
mpagenko3af1f032020-06-10 08:53:41 +00002434 // only if this port is validated for operState transfer
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002435 if (1<<uniPort.UniID)&dh.pOpenOnuAc.config.UniPortMask == (1 << uniPort.UniID) {
2436 logger.Infow(ctx, "OnuUniPort-forced-OperState-ACTIVE", log.Fields{"for PortNo": uniNo, "device-id": dh.DeviceID})
2437 uniPort.SetOperState(vc.OperStatus_ACTIVE)
2438 if !dh.IsReconciling() {
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00002439 //maybe also use getter functions on uniPort - perhaps later ...
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002440 go func(port *cmn.OnuUniPort) {
khenaidoo7d3c5582021-08-11 18:09:44 -04002441 if err := dh.updatePortStateInCore(ctx, &ic.PortState{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002442 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04002443 PortType: voltha.Port_ETHERNET_UNI,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002444 PortNo: port.PortNo,
2445 OperStatus: port.OperState,
khenaidoo7d3c5582021-08-11 18:09:44 -04002446 }); err != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002447 logger.Errorw(ctx, "port-state-update-failed", log.Fields{"error": err, "port-no": uniPort.PortNo, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04002448 }
2449 }(uniPort)
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00002450 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002451 logger.Debugw(ctx, "reconciling - don't notify core about PortStateUpdate", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtf41a1602020-08-19 09:52:50 +00002452 }
mpagenko3af1f032020-06-10 08:53:41 +00002453 }
2454 }
2455}
2456
2457// Disable UniPortState and update core port state accordingly
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002458func (dh *deviceHandler) DisableUniPortStateUpdate(ctx context.Context) {
2459 // compare EnableUniPortStateUpdate() above
mpagenko3af1f032020-06-10 08:53:41 +00002460 // -> use current restriction to operate only on first UNI port as inherited from actual Py code
2461 for uniNo, uniPort := range dh.uniEntityMap {
2462 // only if this port is validated for operState transfer
Matteo Scandolo20d180c2021-06-10 17:20:21 +02002463
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002464 if (1<<uniPort.UniID)&dh.pOpenOnuAc.config.UniPortMask == (1 << uniPort.UniID) {
2465 logger.Infow(ctx, "OnuUniPort-forced-OperState-UNKNOWN", log.Fields{"for PortNo": uniNo, "device-id": dh.DeviceID})
2466 uniPort.SetOperState(vc.OperStatus_UNKNOWN)
2467 if !dh.IsReconciling() {
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002468 //maybe also use getter functions on uniPort - perhaps later ...
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002469 go func(port *cmn.OnuUniPort) {
khenaidoo7d3c5582021-08-11 18:09:44 -04002470 if err := dh.updatePortStateInCore(ctx, &ic.PortState{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002471 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04002472 PortType: voltha.Port_ETHERNET_UNI,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002473 PortNo: port.PortNo,
2474 OperStatus: port.OperState,
khenaidoo7d3c5582021-08-11 18:09:44 -04002475 }); err != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002476 logger.Errorw(ctx, "port-state-update-failed", log.Fields{"error": err, "port-no": uniPort.PortNo, "device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04002477 }
2478 }(uniPort)
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002479 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002480 logger.Debugw(ctx, "reconciling - don't notify core about PortStateUpdate", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +00002481 }
2482
Holger Hildebrandtbe674422020-05-05 13:05:30 +00002483 }
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002484 }
2485}
2486
2487// ONU_Active/Inactive announcement on system KAFKA bus
2488// tried to re-use procedure of oltUpDownIndication from openolt_eventmgr.go with used values from Py code
dbainbri4d3a0dc2020-12-02 00:33:42 +00002489func (dh *deviceHandler) sendOnuOperStateEvent(ctx context.Context, aOperState vc.OperStatus_Types, aDeviceID string, raisedTs int64) {
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002490 var de voltha.DeviceEvent
2491 eventContext := make(map[string]string)
2492 //Populating event context
2493 // assume giving ParentId in GetDevice twice really gives the ParentDevice (there is no GetParentDevice()...)
khenaidoo7d3c5582021-08-11 18:09:44 -04002494 parentDevice, err := dh.getDeviceFromCore(ctx, dh.parentID)
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002495 if err != nil || parentDevice == nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002496 logger.Errorw(ctx, "Failed to fetch parent device for OnuEvent",
Himani Chawla4d908332020-08-31 12:30:20 +05302497 log.Fields{"parentID": dh.parentID, "err": err})
Holger Hildebrandt7ec14c42021-05-28 14:21:58 +00002498 return //TODO with VOL-3045: rw-core is unresponsive: report error and/or perform self-initiated onu-reset?
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002499 }
2500 oltSerialNumber := parentDevice.SerialNumber
2501
2502 eventContext["pon-id"] = strconv.FormatUint(uint64(dh.pOnuIndication.IntfId), 10)
2503 eventContext["onu-id"] = strconv.FormatUint(uint64(dh.pOnuIndication.OnuId), 10)
2504 eventContext["serial-number"] = dh.device.SerialNumber
ssiddiqui1221d1a2021-02-15 11:12:51 +05302505 eventContext["olt-serial-number"] = oltSerialNumber
2506 eventContext["device-id"] = aDeviceID
2507 eventContext["registration-id"] = aDeviceID //py: string(device_id)??
ozgecanetsiaf0a76b62021-05-31 17:42:09 +03002508 eventContext["num-of-unis"] = strconv.Itoa(len(dh.uniEntityMap))
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002509 if deviceEntry := dh.GetOnuDeviceEntry(ctx, false); deviceEntry != nil {
2510 deviceEntry.MutexPersOnuConfig.RLock()
2511 eventContext["equipment-id"] = deviceEntry.SOnuPersistentData.PersEquipmentID
2512 deviceEntry.MutexPersOnuConfig.RUnlock()
2513 eventContext["software-version"] = deviceEntry.GetActiveImageVersion(ctx)
2514 deviceEntry.MutexPersOnuConfig.RLock()
2515 eventContext["vendor"] = deviceEntry.SOnuPersistentData.PersVendorID
2516 deviceEntry.MutexPersOnuConfig.RUnlock()
2517 eventContext["inactive-software-version"] = deviceEntry.GetInactiveImageVersion(ctx)
ozgecanetsiaf0a76b62021-05-31 17:42:09 +03002518 logger.Debugw(ctx, "prepare ONU_ACTIVATED event",
2519 log.Fields{"device-id": aDeviceID, "EventContext": eventContext})
2520 } else {
2521 logger.Errorw(ctx, "Failed to fetch device-entry. ONU_ACTIVATED event is not sent",
2522 log.Fields{"device-id": aDeviceID})
2523 return
2524 }
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002525
2526 /* Populating device event body */
2527 de.Context = eventContext
Himani Chawla4d908332020-08-31 12:30:20 +05302528 de.ResourceId = aDeviceID
2529 if aOperState == voltha.OperStatus_ACTIVE {
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002530 de.DeviceEventName = fmt.Sprintf("%s_%s", cOnuActivatedEvent, "RAISE_EVENT")
2531 de.Description = fmt.Sprintf("%s Event - %s - %s",
2532 cEventObjectType, cOnuActivatedEvent, "Raised")
2533 } else {
2534 de.DeviceEventName = fmt.Sprintf("%s_%s", cOnuActivatedEvent, "CLEAR_EVENT")
2535 de.Description = fmt.Sprintf("%s Event - %s - %s",
2536 cEventObjectType, cOnuActivatedEvent, "Cleared")
2537 }
2538 /* Send event to KAFKA */
dbainbri4d3a0dc2020-12-02 00:33:42 +00002539 if err := dh.EventProxy.SendDeviceEvent(ctx, &de, equipment, pon, raisedTs); err != nil {
2540 logger.Warnw(ctx, "could not send ONU_ACTIVATED event",
Himani Chawla4d908332020-08-31 12:30:20 +05302541 log.Fields{"device-id": aDeviceID, "error": err})
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002542 }
dbainbri4d3a0dc2020-12-02 00:33:42 +00002543 logger.Debugw(ctx, "ctx, ONU_ACTIVATED event sent to KAFKA",
Himani Chawla4d908332020-08-31 12:30:20 +05302544 log.Fields{"device-id": aDeviceID, "with-EventName": de.DeviceEventName})
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002545}
2546
Himani Chawla4d908332020-08-31 12:30:20 +05302547// createUniLockFsm initializes and runs the UniLock FSM to transfer the OMCI related commands for port lock/unlock
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002548func (dh *deviceHandler) createUniLockFsm(ctx context.Context, aAdminState bool, devEvent cmn.OnuDeviceEvent) {
2549 chLSFsm := make(chan cmn.Message, 2048)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002550 var sFsmName string
Himani Chawla4d908332020-08-31 12:30:20 +05302551 if aAdminState {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002552 logger.Debugw(ctx, "createLockStateFSM", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002553 sFsmName = "LockStateFSM"
2554 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002555 logger.Debugw(ctx, "createUnlockStateFSM", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002556 sFsmName = "UnLockStateFSM"
2557 }
mpagenko3af1f032020-06-10 08:53:41 +00002558
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002559 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
mpagenko3af1f032020-06-10 08:53:41 +00002560 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002561 logger.Errorw(ctx, "No valid OnuDevice -aborting", log.Fields{"device-id": dh.DeviceID})
mpagenko3af1f032020-06-10 08:53:41 +00002562 return
2563 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002564 pLSFsm := uniprt.NewLockStateFsm(ctx, aAdminState, devEvent, sFsmName, dh, pDevEntry, chLSFsm)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002565 if pLSFsm != nil {
Himani Chawla4d908332020-08-31 12:30:20 +05302566 if aAdminState {
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002567 dh.pLockStateFsm = pLSFsm
2568 } else {
2569 dh.pUnlockStateFsm = pLSFsm
2570 }
dbainbri4d3a0dc2020-12-02 00:33:42 +00002571 dh.runUniLockFsm(ctx, aAdminState)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002572 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002573 logger.Errorw(ctx, "LockStateFSM could not be created - abort!!", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002574 }
2575}
2576
2577// runUniLockFsm starts the UniLock FSM to transfer the OMCI related commands for port lock/unlock
dbainbri4d3a0dc2020-12-02 00:33:42 +00002578func (dh *deviceHandler) runUniLockFsm(ctx context.Context, aAdminState bool) {
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002579 /* Uni Port lock/unlock procedure -
2580 ***** should run via 'adminDone' state and generate the argument requested event *****
2581 */
2582 var pLSStatemachine *fsm.FSM
Himani Chawla4d908332020-08-31 12:30:20 +05302583 if aAdminState {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002584 pLSStatemachine = dh.pLockStateFsm.PAdaptFsm.PFsm
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002585 //make sure the opposite FSM is not running and if so, terminate it as not relevant anymore
2586 if (dh.pUnlockStateFsm != nil) &&
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002587 (dh.pUnlockStateFsm.PAdaptFsm.PFsm.Current() != uniprt.UniStDisabled) {
2588 _ = dh.pUnlockStateFsm.PAdaptFsm.PFsm.Event(uniprt.UniEvReset)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002589 }
2590 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002591 pLSStatemachine = dh.pUnlockStateFsm.PAdaptFsm.PFsm
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002592 //make sure the opposite FSM is not running and if so, terminate it as not relevant anymore
2593 if (dh.pLockStateFsm != nil) &&
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002594 (dh.pLockStateFsm.PAdaptFsm.PFsm.Current() != uniprt.UniStDisabled) {
2595 _ = dh.pLockStateFsm.PAdaptFsm.PFsm.Event(uniprt.UniEvReset)
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002596 }
2597 }
2598 if pLSStatemachine != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002599 if pLSStatemachine.Is(uniprt.UniStDisabled) {
2600 if err := pLSStatemachine.Event(uniprt.UniEvStart); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002601 logger.Warnw(ctx, "LockStateFSM: can't start", log.Fields{"err": err})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002602 // maybe try a FSM reset and then again ... - TODO!!!
2603 } else {
2604 /***** LockStateFSM started */
dbainbri4d3a0dc2020-12-02 00:33:42 +00002605 logger.Debugw(ctx, "LockStateFSM started", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002606 "state": pLSStatemachine.Current(), "device-id": dh.DeviceID})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002607 }
2608 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002609 logger.Warnw(ctx, "wrong state of LockStateFSM - want: disabled", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002610 "have": pLSStatemachine.Current(), "device-id": dh.DeviceID})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002611 // maybe try a FSM reset and then again ... - TODO!!!
2612 }
2613 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002614 logger.Errorw(ctx, "LockStateFSM StateMachine invalid - cannot be executed!!", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtccd390c2020-05-29 13:49:04 +00002615 // maybe try a FSM reset and then again ... - TODO!!!
2616 }
2617}
2618
mpagenko80622a52021-02-09 16:53:23 +00002619// createOnuUpgradeFsm initializes and runs the Onu Software upgrade FSM
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002620func (dh *deviceHandler) createOnuUpgradeFsm(ctx context.Context, apDevEntry *mib.OnuDeviceEntry, aDevEvent cmn.OnuDeviceEvent) error {
mpagenko80622a52021-02-09 16:53:23 +00002621 //in here lockUpgradeFsm is already locked
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002622 chUpgradeFsm := make(chan cmn.Message, 2048)
mpagenko80622a52021-02-09 16:53:23 +00002623 var sFsmName = "OnuSwUpgradeFSM"
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002624 logger.Debugw(ctx, "create OnuSwUpgradeFSM", log.Fields{"device-id": dh.DeviceID})
mpagenko15ff4a52021-03-02 10:09:20 +00002625 if apDevEntry.PDevOmciCC == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002626 logger.Errorw(ctx, "no valid OnuDevice or omciCC - abort", log.Fields{"device-id": dh.DeviceID})
mpagenko15ff4a52021-03-02 10:09:20 +00002627 return fmt.Errorf(fmt.Sprintf("no valid omciCC - abort for device-id: %s", dh.device.Id))
mpagenko80622a52021-02-09 16:53:23 +00002628 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002629 dh.pOnuUpradeFsm = swupg.NewOnuUpgradeFsm(ctx, dh, apDevEntry, apDevEntry.GetOnuDB(), aDevEvent,
mpagenko80622a52021-02-09 16:53:23 +00002630 sFsmName, chUpgradeFsm)
2631 if dh.pOnuUpradeFsm != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002632 pUpgradeStatemachine := dh.pOnuUpradeFsm.PAdaptFsm.PFsm
mpagenko80622a52021-02-09 16:53:23 +00002633 if pUpgradeStatemachine != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002634 if pUpgradeStatemachine.Is(swupg.UpgradeStDisabled) {
2635 if err := pUpgradeStatemachine.Event(swupg.UpgradeEvStart); err != nil {
mpagenko80622a52021-02-09 16:53:23 +00002636 logger.Errorw(ctx, "OnuSwUpgradeFSM: can't start", log.Fields{"err": err})
2637 // maybe try a FSM reset and then again ... - TODO!!!
2638 return fmt.Errorf(fmt.Sprintf("OnuSwUpgradeFSM could not be started for device-id: %s", dh.device.Id))
2639 }
2640 /***** LockStateFSM started */
mpagenko38662d02021-08-11 09:45:19 +00002641 //reset the last stored upgrade states
2642 (*dh.pLastUpgradeImageState).DownloadState = voltha.ImageState_DOWNLOAD_STARTED //already with updated state
2643 (*dh.pLastUpgradeImageState).Reason = voltha.ImageState_NO_ERROR
2644 (*dh.pLastUpgradeImageState).ImageState = voltha.ImageState_IMAGE_UNKNOWN
mpagenko80622a52021-02-09 16:53:23 +00002645 logger.Debugw(ctx, "OnuSwUpgradeFSM started", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002646 "state": pUpgradeStatemachine.Current(), "device-id": dh.DeviceID})
mpagenko80622a52021-02-09 16:53:23 +00002647 } else {
2648 logger.Errorw(ctx, "wrong state of OnuSwUpgradeFSM to start - want: disabled", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002649 "have": pUpgradeStatemachine.Current(), "device-id": dh.DeviceID})
mpagenko80622a52021-02-09 16:53:23 +00002650 // maybe try a FSM reset and then again ... - TODO!!!
2651 return fmt.Errorf(fmt.Sprintf("OnuSwUpgradeFSM could not be started for device-id: %s, wrong internal state", dh.device.Id))
2652 }
2653 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002654 logger.Errorw(ctx, "OnuSwUpgradeFSM internal FSM invalid - cannot be executed!!", log.Fields{"device-id": dh.DeviceID})
mpagenko80622a52021-02-09 16:53:23 +00002655 // maybe try a FSM reset and then again ... - TODO!!!
2656 return fmt.Errorf(fmt.Sprintf("OnuSwUpgradeFSM internal FSM could not be created for device-id: %s", dh.device.Id))
2657 }
2658 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002659 logger.Errorw(ctx, "OnuSwUpgradeFSM could not be created - abort", log.Fields{"device-id": dh.DeviceID})
mpagenko80622a52021-02-09 16:53:23 +00002660 return fmt.Errorf(fmt.Sprintf("OnuSwUpgradeFSM could not be created - abort for device-id: %s", dh.device.Id))
2661 }
2662 return nil
2663}
2664
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002665// RemoveOnuUpgradeFsm clears the Onu Software upgrade FSM
2666func (dh *deviceHandler) RemoveOnuUpgradeFsm(ctx context.Context, apImageState *voltha.ImageState) {
mpagenko80622a52021-02-09 16:53:23 +00002667 logger.Debugw(ctx, "remove OnuSwUpgradeFSM StateMachine", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002668 "device-id": dh.DeviceID})
mpagenko80622a52021-02-09 16:53:23 +00002669 dh.lockUpgradeFsm.Lock()
mpagenko80622a52021-02-09 16:53:23 +00002670 dh.pOnuUpradeFsm = nil //resource clearing is left to garbage collector
mpagenko38662d02021-08-11 09:45:19 +00002671 dh.pLastUpgradeImageState = apImageState
2672 dh.lockUpgradeFsm.Unlock()
2673 //signal upgradeFsm removed using non-blocking channel send
2674 select {
2675 case dh.upgradeFsmChan <- struct{}{}:
2676 default:
2677 logger.Debugw(ctx, "removed-UpgradeFsm signal not send on upgradeFsmChan (no receiver)", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002678 "device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00002679 }
mpagenko80622a52021-02-09 16:53:23 +00002680}
2681
mpagenko15ff4a52021-03-02 10:09:20 +00002682// checkOnOnuImageCommit verifies if the ONU is in some upgrade state that allows for image commit and if tries to commit
2683func (dh *deviceHandler) checkOnOnuImageCommit(ctx context.Context) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002684 pDevEntry := dh.GetOnuDeviceEntry(ctx, false)
mpagenko15ff4a52021-03-02 10:09:20 +00002685 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002686 logger.Errorw(ctx, "No valid OnuDevice -aborting checkOnOnuImageCommit", log.Fields{"device-id": dh.DeviceID})
mpagenko15ff4a52021-03-02 10:09:20 +00002687 return
2688 }
2689
2690 dh.lockUpgradeFsm.RLock()
2691 defer dh.lockUpgradeFsm.RUnlock()
2692 if dh.pOnuUpradeFsm != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002693 pUpgradeStatemachine := dh.pOnuUpradeFsm.PAdaptFsm.PFsm
mpagenko15ff4a52021-03-02 10:09:20 +00002694 if pUpgradeStatemachine != nil {
2695 // commit is only processed in case out upgrade FSM indicates the according state (for automatic commit)
2696 // (some manual forced commit could do without)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002697 UpgradeState := pUpgradeStatemachine.Current()
2698 if (UpgradeState == swupg.UpgradeStWaitForCommit) ||
2699 (UpgradeState == swupg.UpgradeStRequestingActivate) {
2700 // also include UpgradeStRequestingActivate as it may be left in case the ActivateResponse just got lost
mpagenko183647c2021-06-08 15:25:04 +00002701 // here no need to update the upgrade image state to activated as the state will be immediately be set to committing
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002702 if pDevEntry.IsImageToBeCommitted(ctx, dh.pOnuUpradeFsm.InactiveImageMeID) {
mpagenko1f8e8822021-06-25 14:10:21 +00002703 activeImageID, errImg := pDevEntry.GetActiveImageMeID(ctx)
2704 if errImg != nil {
2705 logger.Errorw(ctx, "OnuSwUpgradeFSM abort - could not get active image after reboot",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002706 log.Fields{"device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00002707 dh.pOnuUpradeFsm.CancelProcessing(ctx, true, voltha.ImageState_CANCELLED_ON_ONU_STATE) //complete abort
mpagenko15ff4a52021-03-02 10:09:20 +00002708 return
2709 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002710 if activeImageID == dh.pOnuUpradeFsm.InactiveImageMeID {
2711 if (UpgradeState == swupg.UpgradeStRequestingActivate) && !dh.pOnuUpradeFsm.GetCommitFlag(ctx) {
mpagenko1f8e8822021-06-25 14:10:21 +00002712 // if FSM was waiting on activateResponse, new image is active, but FSM shall not commit, then:
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002713 if err := pUpgradeStatemachine.Event(swupg.UpgradeEvActivationDone); err != nil {
mpagenko1f8e8822021-06-25 14:10:21 +00002714 logger.Errorw(ctx, "OnuSwUpgradeFSM: can't call activate-done event", log.Fields{"err": err})
2715 return
2716 }
2717 logger.Debugw(ctx, "OnuSwUpgradeFSM activate-done after reboot", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002718 "state": UpgradeState, "device-id": dh.DeviceID})
mpagenko1f8e8822021-06-25 14:10:21 +00002719 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002720 //FSM in waitForCommit or (UpgradeStRequestingActivate [lost ActivateResp] and commit allowed)
2721 if err := pUpgradeStatemachine.Event(swupg.UpgradeEvCommitSw); err != nil {
mpagenko1f8e8822021-06-25 14:10:21 +00002722 logger.Errorw(ctx, "OnuSwUpgradeFSM: can't call commit event", log.Fields{"err": err})
2723 return
2724 }
2725 logger.Debugw(ctx, "OnuSwUpgradeFSM commit image requested", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002726 "state": UpgradeState, "device-id": dh.DeviceID})
mpagenko1f8e8822021-06-25 14:10:21 +00002727 }
2728 } else {
2729 logger.Errorw(ctx, "OnuSwUpgradeFSM waiting to commit/on ActivateResponse, but load did not start with expected image Id",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002730 log.Fields{"device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00002731 dh.pOnuUpradeFsm.CancelProcessing(ctx, true, voltha.ImageState_CANCELLED_ON_ONU_STATE) //complete abort
mpagenko1f8e8822021-06-25 14:10:21 +00002732 return
2733 }
mpagenko15ff4a52021-03-02 10:09:20 +00002734 } else {
2735 logger.Errorw(ctx, "OnuSwUpgradeFSM waiting to commit, but nothing to commit on ONU - abort upgrade",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002736 log.Fields{"device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00002737 dh.pOnuUpradeFsm.CancelProcessing(ctx, true, voltha.ImageState_CANCELLED_ON_ONU_STATE) //complete abort
mpagenko15ff4a52021-03-02 10:09:20 +00002738 return
2739 }
mpagenko183647c2021-06-08 15:25:04 +00002740 } else {
2741 //upgrade FSM is active but not waiting for commit: maybe because commit flag is not set
2742 // upgrade FSM is to be informed if the current active image is the one that was used in upgrade for the download
2743 if activeImageID, err := pDevEntry.GetActiveImageMeID(ctx); err == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002744 if dh.pOnuUpradeFsm.InactiveImageMeID == activeImageID {
mpagenko183647c2021-06-08 15:25:04 +00002745 logger.Debugw(ctx, "OnuSwUpgradeFSM image state set to activated", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002746 "state": pUpgradeStatemachine.Current(), "device-id": dh.DeviceID})
mpagenko38662d02021-08-11 09:45:19 +00002747 dh.pOnuUpradeFsm.SetImageStateActive(ctx)
mpagenko183647c2021-06-08 15:25:04 +00002748 }
2749 }
mpagenko15ff4a52021-03-02 10:09:20 +00002750 }
2751 }
2752 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002753 logger.Debugw(ctx, "no ONU image to be committed", log.Fields{"device-id": dh.DeviceID})
mpagenko15ff4a52021-03-02 10:09:20 +00002754 }
2755}
2756
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002757//SetBackend provides a DB backend for the specified path on the existing KV client
2758func (dh *deviceHandler) SetBackend(ctx context.Context, aBasePathKvStore string) *db.Backend {
Matteo Scandolo127c59d2021-01-28 11:31:18 -08002759
2760 logger.Debugw(ctx, "SetKVStoreBackend", log.Fields{"IpTarget": dh.pOpenOnuAc.KVStoreAddress,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002761 "BasePathKvStore": aBasePathKvStore, "device-id": dh.DeviceID})
Girish Gowdra50e56422021-06-01 16:46:04 -07002762 // kvbackend := db.NewBackend(ctx, dh.pOpenOnuAc.KVStoreType, dh.pOpenOnuAc.KVStoreAddress, dh.pOpenOnuAc.KVStoreTimeout, aBasePathKvStore)
mpagenkoaf801632020-07-03 10:00:42 +00002763 kvbackend := &db.Backend{
2764 Client: dh.pOpenOnuAc.kvClient,
2765 StoreType: dh.pOpenOnuAc.KVStoreType,
2766 /* address config update acc. to [VOL-2736] */
Matteo Scandolo127c59d2021-01-28 11:31:18 -08002767 Address: dh.pOpenOnuAc.KVStoreAddress,
mpagenkoaf801632020-07-03 10:00:42 +00002768 Timeout: dh.pOpenOnuAc.KVStoreTimeout,
2769 PathPrefix: aBasePathKvStore}
Holger Hildebrandtc54939a2020-06-17 08:14:27 +00002770
mpagenkoaf801632020-07-03 10:00:42 +00002771 return kvbackend
Holger Hildebrandt24d51952020-05-04 14:03:42 +00002772}
khenaidoo7d3c5582021-08-11 18:09:44 -04002773func (dh *deviceHandler) getFlowOfbFields(ctx context.Context, apFlowItem *of.OfpFlowStats, loMatchVlan *uint16,
Himani Chawla26e555c2020-08-31 12:30:20 +05302774 loAddPcp *uint8, loIPProto *uint32) {
mpagenkodff5dda2020-08-28 11:52:01 +00002775
mpagenkodff5dda2020-08-28 11:52:01 +00002776 for _, field := range flow.GetOfbFields(apFlowItem) {
2777 switch field.Type {
2778 case of.OxmOfbFieldTypes_OFPXMT_OFB_ETH_TYPE:
2779 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002780 logger.Debugw(ctx, "flow type EthType", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002781 "EthType": strconv.FormatInt(int64(field.GetEthType()), 16)})
2782 }
mpagenko01e726e2020-10-23 09:45:29 +00002783 /* TT related temporary workaround - should not be needed anymore
mpagenkodff5dda2020-08-28 11:52:01 +00002784 case of.OxmOfbFieldTypes_OFPXMT_OFB_IP_PROTO:
2785 {
Himani Chawla26e555c2020-08-31 12:30:20 +05302786 *loIPProto = field.GetIpProto()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002787 logger.Debugw("flow type IpProto", log.Fields{"device-id": dh.DeviceID,
Himani Chawla26e555c2020-08-31 12:30:20 +05302788 "IpProto": strconv.FormatInt(int64(*loIPProto), 16)})
2789 if *loIPProto == 2 {
mpagenkodff5dda2020-08-28 11:52:01 +00002790 // some workaround for TT workflow at proto == 2 (IGMP trap) -> ignore the flow
2791 // avoids installing invalid EVTOCD rule
mpagenko01e726e2020-10-23 09:45:29 +00002792 logger.Debugw("flow type IpProto 2: TT workaround: ignore flow",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002793 log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302794 return
mpagenkodff5dda2020-08-28 11:52:01 +00002795 }
2796 }
mpagenko01e726e2020-10-23 09:45:29 +00002797 */
mpagenkodff5dda2020-08-28 11:52:01 +00002798 case of.OxmOfbFieldTypes_OFPXMT_OFB_VLAN_VID:
2799 {
Himani Chawla26e555c2020-08-31 12:30:20 +05302800 *loMatchVlan = uint16(field.GetVlanVid())
mpagenkodff5dda2020-08-28 11:52:01 +00002801 loMatchVlanMask := uint16(field.GetVlanVidMask())
Himani Chawla26e555c2020-08-31 12:30:20 +05302802 if !(*loMatchVlan == uint16(of.OfpVlanId_OFPVID_PRESENT) &&
mpagenkodff5dda2020-08-28 11:52:01 +00002803 loMatchVlanMask == uint16(of.OfpVlanId_OFPVID_PRESENT)) {
Himani Chawla26e555c2020-08-31 12:30:20 +05302804 *loMatchVlan = *loMatchVlan & 0xFFF // not transparent: copy only ID bits
mpagenkodff5dda2020-08-28 11:52:01 +00002805 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002806 logger.Debugw(ctx, "flow field type", log.Fields{"device-id": dh.DeviceID,
Himani Chawla26e555c2020-08-31 12:30:20 +05302807 "VID": strconv.FormatInt(int64(*loMatchVlan), 16)})
mpagenkodff5dda2020-08-28 11:52:01 +00002808 }
2809 case of.OxmOfbFieldTypes_OFPXMT_OFB_VLAN_PCP:
2810 {
Himani Chawla26e555c2020-08-31 12:30:20 +05302811 *loAddPcp = uint8(field.GetVlanPcp())
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002812 logger.Debugw(ctx, "flow field type", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002813 "PCP": loAddPcp})
2814 }
2815 case of.OxmOfbFieldTypes_OFPXMT_OFB_UDP_DST:
2816 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002817 logger.Debugw(ctx, "flow field type", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002818 "UDP-DST": strconv.FormatInt(int64(field.GetUdpDst()), 16)})
2819 }
2820 case of.OxmOfbFieldTypes_OFPXMT_OFB_UDP_SRC:
2821 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002822 logger.Debugw(ctx, "flow field type", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002823 "UDP-SRC": strconv.FormatInt(int64(field.GetUdpSrc()), 16)})
2824 }
2825 case of.OxmOfbFieldTypes_OFPXMT_OFB_IPV4_DST:
2826 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002827 logger.Debugw(ctx, "flow field type", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002828 "IPv4-DST": field.GetIpv4Dst()})
2829 }
2830 case of.OxmOfbFieldTypes_OFPXMT_OFB_IPV4_SRC:
2831 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002832 logger.Debugw(ctx, "flow field type", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002833 "IPv4-SRC": field.GetIpv4Src()})
2834 }
2835 case of.OxmOfbFieldTypes_OFPXMT_OFB_METADATA:
2836 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002837 logger.Debugw(ctx, "flow field type", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002838 "Metadata": field.GetTableMetadata()})
2839 }
2840 /*
2841 default:
2842 {
2843 //all other entires ignored
2844 }
2845 */
2846 }
2847 } //for all OfbFields
Himani Chawla26e555c2020-08-31 12:30:20 +05302848}
mpagenkodff5dda2020-08-28 11:52:01 +00002849
khenaidoo7d3c5582021-08-11 18:09:44 -04002850func (dh *deviceHandler) getFlowActions(ctx context.Context, apFlowItem *of.OfpFlowStats, loSetPcp *uint8, loSetVlan *uint16) {
mpagenkodff5dda2020-08-28 11:52:01 +00002851 for _, action := range flow.GetActions(apFlowItem) {
2852 switch action.Type {
2853 /* not used:
2854 case of.OfpActionType_OFPAT_OUTPUT:
2855 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002856 logger.Debugw("flow action type", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002857 "Output": action.GetOutput()})
2858 }
2859 */
2860 case of.OfpActionType_OFPAT_PUSH_VLAN:
2861 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002862 logger.Debugw(ctx, "flow action type", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002863 "PushEthType": strconv.FormatInt(int64(action.GetPush().Ethertype), 16)})
2864 }
2865 case of.OfpActionType_OFPAT_SET_FIELD:
2866 {
2867 pActionSetField := action.GetSetField()
2868 if pActionSetField.Field.OxmClass != of.OfpOxmClass_OFPXMC_OPENFLOW_BASIC {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002869 logger.Warnw(ctx, "flow action SetField invalid OxmClass (ignored)", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002870 "OxcmClass": pActionSetField.Field.OxmClass})
2871 }
2872 if pActionSetField.Field.GetOfbField().Type == of.OxmOfbFieldTypes_OFPXMT_OFB_VLAN_VID {
Himani Chawla26e555c2020-08-31 12:30:20 +05302873 *loSetVlan = uint16(pActionSetField.Field.GetOfbField().GetVlanVid())
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002874 logger.Debugw(ctx, "flow Set VLAN from SetField action", log.Fields{"device-id": dh.DeviceID,
Himani Chawla26e555c2020-08-31 12:30:20 +05302875 "SetVlan": strconv.FormatInt(int64(*loSetVlan), 16)})
mpagenkodff5dda2020-08-28 11:52:01 +00002876 } else if pActionSetField.Field.GetOfbField().Type == of.OxmOfbFieldTypes_OFPXMT_OFB_VLAN_PCP {
Himani Chawla26e555c2020-08-31 12:30:20 +05302877 *loSetPcp = uint8(pActionSetField.Field.GetOfbField().GetVlanPcp())
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002878 logger.Debugw(ctx, "flow Set PCP from SetField action", log.Fields{"device-id": dh.DeviceID,
Himani Chawla26e555c2020-08-31 12:30:20 +05302879 "SetPcp": *loSetPcp})
mpagenkodff5dda2020-08-28 11:52:01 +00002880 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002881 logger.Warnw(ctx, "flow action SetField invalid FieldType", log.Fields{"device-id": dh.DeviceID,
mpagenkodff5dda2020-08-28 11:52:01 +00002882 "Type": pActionSetField.Field.GetOfbField().Type})
2883 }
2884 }
2885 /*
2886 default:
2887 {
2888 //all other entires ignored
2889 }
2890 */
2891 }
2892 } //for all Actions
Himani Chawla26e555c2020-08-31 12:30:20 +05302893}
2894
2895//addFlowItemToUniPort parses the actual flow item to add it to the UniPort
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002896func (dh *deviceHandler) addFlowItemToUniPort(ctx context.Context, apFlowItem *of.OfpFlowStats, apUniPort *cmn.OnuUniPort,
ozgecanetsia82b91a62021-05-21 18:54:49 +03002897 apFlowMetaData *voltha.FlowMetadata) error {
Himani Chawla26e555c2020-08-31 12:30:20 +05302898 var loSetVlan uint16 = uint16(of.OfpVlanId_OFPVID_NONE) //noValidEntry
2899 var loMatchVlan uint16 = uint16(of.OfpVlanId_OFPVID_PRESENT) //reserved VLANID entry
2900 var loAddPcp, loSetPcp uint8
2901 var loIPProto uint32
2902 /* the TechProfileId is part of the flow Metadata - compare also comment within
2903 * OLT-Adapter:openolt_flowmgr.go
2904 * Metadata 8 bytes:
2905 * Most Significant 2 Bytes = Inner VLAN
2906 * Next 2 Bytes = Tech Profile ID(TPID)
2907 * Least Significant 4 Bytes = Port ID
2908 * Flow Metadata carries Tech-Profile (TP) ID and is mandatory in all
2909 * subscriber related flows.
2910 */
2911
dbainbri4d3a0dc2020-12-02 00:33:42 +00002912 metadata := flow.GetMetadataFromWriteMetadataAction(ctx, apFlowItem)
Himani Chawla26e555c2020-08-31 12:30:20 +05302913 if metadata == 0 {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002914 logger.Debugw(ctx, "flow-add invalid metadata - abort",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002915 log.Fields{"device-id": dh.DeviceID})
2916 return fmt.Errorf("flow-add invalid metadata: %s", dh.DeviceID)
Himani Chawla26e555c2020-08-31 12:30:20 +05302917 }
mpagenko551a4d42020-12-08 18:09:20 +00002918 loTpID := uint8(flow.GetTechProfileIDFromWriteMetaData(ctx, metadata))
mpagenko01e726e2020-10-23 09:45:29 +00002919 loCookie := apFlowItem.GetCookie()
2920 loCookieSlice := []uint64{loCookie}
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002921 logger.Debugw(ctx, "flow-add base indications", log.Fields{"device-id": dh.DeviceID,
mpagenko01e726e2020-10-23 09:45:29 +00002922 "TechProf-Id": loTpID, "cookie": loCookie})
Himani Chawla26e555c2020-08-31 12:30:20 +05302923
dbainbri4d3a0dc2020-12-02 00:33:42 +00002924 dh.getFlowOfbFields(ctx, apFlowItem, &loMatchVlan, &loAddPcp, &loIPProto)
mpagenko01e726e2020-10-23 09:45:29 +00002925 /* TT related temporary workaround - should not be needed anymore
Himani Chawla26e555c2020-08-31 12:30:20 +05302926 if loIPProto == 2 {
2927 // some workaround for TT workflow at proto == 2 (IGMP trap) -> ignore the flow
2928 // avoids installing invalid EVTOCD rule
mpagenko01e726e2020-10-23 09:45:29 +00002929 logger.Debugw("flow-add type IpProto 2: TT workaround: ignore flow",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002930 log.Fields{"device-id": dh.DeviceID})
Himani Chawla26e555c2020-08-31 12:30:20 +05302931 return nil
2932 }
mpagenko01e726e2020-10-23 09:45:29 +00002933 */
dbainbri4d3a0dc2020-12-02 00:33:42 +00002934 dh.getFlowActions(ctx, apFlowItem, &loSetPcp, &loSetVlan)
mpagenkodff5dda2020-08-28 11:52:01 +00002935
2936 if loSetVlan == uint16(of.OfpVlanId_OFPVID_NONE) && loMatchVlan != uint16(of.OfpVlanId_OFPVID_PRESENT) {
dbainbri4d3a0dc2020-12-02 00:33:42 +00002937 logger.Errorw(ctx, "flow-add aborted - SetVlanId undefined, but MatchVid set", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002938 "device-id": dh.DeviceID, "UniPort": apUniPort.PortNo,
mpagenkodff5dda2020-08-28 11:52:01 +00002939 "set_vid": strconv.FormatInt(int64(loSetVlan), 16),
2940 "match_vid": strconv.FormatInt(int64(loMatchVlan), 16)})
2941 //TODO!!: Use DeviceId within the error response to rwCore
2942 // likewise also in other error response cases to calling components as requested in [VOL-3458]
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002943 return fmt.Errorf("flow-add Set/Match VlanId inconsistent: %s", dh.DeviceID)
mpagenkodff5dda2020-08-28 11:52:01 +00002944 }
2945 if loSetVlan == uint16(of.OfpVlanId_OFPVID_NONE) && loMatchVlan == uint16(of.OfpVlanId_OFPVID_PRESENT) {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002946 logger.Debugw(ctx, "flow-add vlan-any/copy", log.Fields{"device-id": dh.DeviceID})
mpagenkodff5dda2020-08-28 11:52:01 +00002947 loSetVlan = loMatchVlan //both 'transparent' (copy any)
2948 } else {
2949 //looks like OMCI value 4097 (copyFromOuter - for Uni double tagged) is not supported here
2950 if loSetVlan != uint16(of.OfpVlanId_OFPVID_PRESENT) {
2951 // not set to transparent
Himani Chawla26e555c2020-08-31 12:30:20 +05302952 loSetVlan &= 0x0FFF //mask VID bits as prerequisite for vlanConfigFsm
mpagenkodff5dda2020-08-28 11:52:01 +00002953 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002954 logger.Debugw(ctx, "flow-add vlan-set", log.Fields{"device-id": dh.DeviceID})
mpagenkodff5dda2020-08-28 11:52:01 +00002955 }
mpagenko9a304ea2020-12-16 15:54:01 +00002956
ozgecanetsia82b91a62021-05-21 18:54:49 +03002957 var meter *voltha.OfpMeterConfig
2958 if apFlowMetaData != nil {
2959 meter = apFlowMetaData.Meters[0]
2960 }
mpagenkobc4170a2021-08-17 16:42:10 +00002961 //mutex protection as the update_flow rpc maybe running concurrently for different flows, perhaps also activities
2962 // must be set including the execution of createVlanFilterFsm() to avoid unintended creation of FSM's
2963 // when different rules are requested concurrently for the same uni
2964 // (also vlan persistency data does not support multiple FSM's on the same UNI correctly!)
2965 dh.lockVlanAdd.Lock() //prevent multiple add activities to start in parallel
2966 dh.lockVlanConfig.RLock() //read protection on UniVlanConfigFsmMap (removeFlowItemFromUniPort)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002967 logger.Debugw(ctx, "flow-add got lock", log.Fields{"device-id": dh.DeviceID, "tpID": loTpID, "uniID": apUniPort.UniID})
2968 if _, exist := dh.UniVlanConfigFsmMap[apUniPort.UniID]; exist {
mpagenkobc4170a2021-08-17 16:42:10 +00002969 //SetUniFlowParams() may block on some rule that is suspended-to-add
2970 // in order to allow for according flow removal lockVlanConfig may only be used with RLock here
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002971 err := dh.UniVlanConfigFsmMap[apUniPort.UniID].SetUniFlowParams(ctx, loTpID, loCookieSlice,
ozgecanetsia82b91a62021-05-21 18:54:49 +03002972 loMatchVlan, loSetVlan, loSetPcp, false, meter)
mpagenkobc4170a2021-08-17 16:42:10 +00002973 dh.lockVlanConfig.RUnlock()
2974 dh.lockVlanAdd.Unlock() //re-admit new Add-flow-processing
mpagenkof1fc3862021-02-16 10:09:52 +00002975 return err
mpagenkodff5dda2020-08-28 11:52:01 +00002976 }
mpagenkobc4170a2021-08-17 16:42:10 +00002977 dh.lockVlanConfig.RUnlock()
2978 dh.lockVlanConfig.Lock() //createVlanFilterFsm should always be a non-blocking operation and requires r+w lock
mpagenko7d14de12021-07-27 08:31:56 +00002979 err := dh.createVlanFilterFsm(ctx, apUniPort, loTpID, loCookieSlice,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002980 loMatchVlan, loSetVlan, loSetPcp, cmn.OmciVlanFilterAddDone, false, meter)
mpagenko7d14de12021-07-27 08:31:56 +00002981 dh.lockVlanConfig.Unlock()
mpagenkobc4170a2021-08-17 16:42:10 +00002982 dh.lockVlanAdd.Unlock() //re-admit new Add-flow-processing
mpagenko7d14de12021-07-27 08:31:56 +00002983 return err
mpagenko01e726e2020-10-23 09:45:29 +00002984}
2985
2986//removeFlowItemFromUniPort parses the actual flow item to remove it from the UniPort
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002987func (dh *deviceHandler) removeFlowItemFromUniPort(ctx context.Context, apFlowItem *of.OfpFlowStats, apUniPort *cmn.OnuUniPort) error {
mpagenko01e726e2020-10-23 09:45:29 +00002988 //optimization and assumption: the flow cookie uniquely identifies the flow and with that the internal rule
2989 //hence only the cookie is used here to find the relevant flow and possibly remove the rule
2990 //no extra check is done on the rule parameters
2991 //accordingly the removal is done only once - for the first found flow with that cookie, even though
2992 // at flow creation is not assured, that the same cookie is not configured for different flows - just assumed
2993 //additionally it is assumed here, that removal can only be done for one cookie per flow in a sequence (different
2994 // from addFlow - where at reconcilement multiple cookies per flow ) can be configured in one sequence)
mpagenkofc4f56e2020-11-04 17:17:49 +00002995 // - some possible 'delete-all' sequence would have to be implemented separately (where the cookies are don't care anyway)
mpagenko01e726e2020-10-23 09:45:29 +00002996 loCookie := apFlowItem.GetCookie()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00002997 logger.Debugw(ctx, "flow-remove base indications", log.Fields{"device-id": dh.DeviceID, "cookie": loCookie})
mpagenko01e726e2020-10-23 09:45:29 +00002998
2999 /* TT related temporary workaround - should not be needed anymore
3000 for _, field := range flow.GetOfbFields(apFlowItem) {
3001 if field.Type == of.OxmOfbFieldTypes_OFPXMT_OFB_IP_PROTO {
3002 loIPProto := field.GetIpProto()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003003 logger.Debugw(ctx, "flow type IpProto", log.Fields{"device-id": dh.DeviceID,
mpagenko01e726e2020-10-23 09:45:29 +00003004 "IpProto": strconv.FormatInt(int64(loIPProto), 16)})
3005 if loIPProto == 2 {
3006 // some workaround for TT workflow on proto == 2 (IGMP trap) -> the flow was not added, no need to remove
mpagenko551a4d42020-12-08 18:09:20 +00003007 logger.Debugw(ctx, "flow-remove type IpProto 2: TT workaround: ignore flow",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003008 log.Fields{"device-id": dh.DeviceID})
mpagenko01e726e2020-10-23 09:45:29 +00003009 return nil
3010 }
3011 }
3012 } //for all OfbFields
3013 */
3014
mpagenko9a304ea2020-12-16 15:54:01 +00003015 //mutex protection as the update_flow rpc maybe running concurrently for different flows, perhaps also activities
mpagenkof1fc3862021-02-16 10:09:52 +00003016 dh.lockVlanConfig.RLock()
3017 defer dh.lockVlanConfig.RUnlock()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003018 logger.Debugw(ctx, "flow-remove got RLock", log.Fields{"device-id": dh.DeviceID, "uniID": apUniPort.UniID})
3019 if _, exist := dh.UniVlanConfigFsmMap[apUniPort.UniID]; exist {
3020 return dh.UniVlanConfigFsmMap[apUniPort.UniID].RemoveUniFlowParams(ctx, loCookie)
mpagenko01e726e2020-10-23 09:45:29 +00003021 }
dbainbri4d3a0dc2020-12-02 00:33:42 +00003022 logger.Debugw(ctx, "flow-remove called, but no flow is configured (no VlanConfigFsm, flow already removed) ",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003023 log.Fields{"device-id": dh.DeviceID})
mpagenko01e726e2020-10-23 09:45:29 +00003024 //but as we regard the flow as not existing = removed we respond just ok
mpagenkofc4f56e2020-11-04 17:17:49 +00003025 // and treat the reason accordingly (which in the normal removal procedure is initiated by the FSM)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003026 go dh.DeviceProcStatusUpdate(ctx, cmn.OmciVlanFilterRemDone)
mpagenkofc4f56e2020-11-04 17:17:49 +00003027
mpagenko01e726e2020-10-23 09:45:29 +00003028 return nil
mpagenkodff5dda2020-08-28 11:52:01 +00003029}
3030
Himani Chawla26e555c2020-08-31 12:30:20 +05303031// createVlanFilterFsm initializes and runs the VlanFilter FSM to transfer OMCI related VLAN config
mpagenko9a304ea2020-12-16 15:54:01 +00003032// if this function is called from possibly concurrent processes it must be mutex-protected from the caller!
mpagenko7d14de12021-07-27 08:31:56 +00003033// precondition: dh.lockVlanConfig is locked by the caller!
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003034func (dh *deviceHandler) createVlanFilterFsm(ctx context.Context, apUniPort *cmn.OnuUniPort, aTpID uint8, aCookieSlice []uint64,
3035 aMatchVlan uint16, aSetVlan uint16, aSetPcp uint8, aDevEvent cmn.OnuDeviceEvent, lastFlowToReconcile bool, aMeter *voltha.OfpMeterConfig) error {
3036 chVlanFilterFsm := make(chan cmn.Message, 2048)
mpagenkodff5dda2020-08-28 11:52:01 +00003037
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003038 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
mpagenkodff5dda2020-08-28 11:52:01 +00003039 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003040 logger.Errorw(ctx, "No valid OnuDevice -aborting", log.Fields{"device-id": dh.DeviceID})
3041 return fmt.Errorf("no valid OnuDevice for device-id %x - aborting", dh.DeviceID)
mpagenkodff5dda2020-08-28 11:52:01 +00003042 }
3043
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003044 pVlanFilterFsm := avcfg.NewUniVlanConfigFsm(ctx, dh, pDevEntry, pDevEntry.PDevOmciCC, apUniPort, dh.pOnuTP,
3045 pDevEntry.GetOnuDB(), aTpID, aDevEvent, "UniVlanConfigFsm", chVlanFilterFsm,
ozgecanetsia82b91a62021-05-21 18:54:49 +03003046 dh.pOpenOnuAc.AcceptIncrementalEvto, aCookieSlice, aMatchVlan, aSetVlan, aSetPcp, lastFlowToReconcile, aMeter)
mpagenkodff5dda2020-08-28 11:52:01 +00003047 if pVlanFilterFsm != nil {
mpagenko7d14de12021-07-27 08:31:56 +00003048 //dh.lockVlanConfig is locked (by caller) throughout the state transition to 'starting'
3049 // to prevent unintended (ignored) events to be sent there (from parallel processing)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003050 dh.UniVlanConfigFsmMap[apUniPort.UniID] = pVlanFilterFsm
3051 pVlanFilterStatemachine := pVlanFilterFsm.PAdaptFsm.PFsm
mpagenkodff5dda2020-08-28 11:52:01 +00003052 if pVlanFilterStatemachine != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003053 if pVlanFilterStatemachine.Is(avcfg.VlanStDisabled) {
3054 if err := pVlanFilterStatemachine.Event(avcfg.VlanEvStart); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00003055 logger.Warnw(ctx, "UniVlanConfigFsm: can't start", log.Fields{"err": err})
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003056 return fmt.Errorf("can't start UniVlanConfigFsm for device-id %x", dh.DeviceID)
mpagenkodff5dda2020-08-28 11:52:01 +00003057 }
Himani Chawla26e555c2020-08-31 12:30:20 +05303058 /***** UniVlanConfigFsm started */
dbainbri4d3a0dc2020-12-02 00:33:42 +00003059 logger.Debugw(ctx, "UniVlanConfigFsm started", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003060 "state": pVlanFilterStatemachine.Current(), "device-id": dh.DeviceID,
3061 "UniPort": apUniPort.PortNo})
mpagenkodff5dda2020-08-28 11:52:01 +00003062 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00003063 logger.Warnw(ctx, "wrong state of UniVlanConfigFsm - want: disabled", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003064 "have": pVlanFilterStatemachine.Current(), "device-id": dh.DeviceID})
3065 return fmt.Errorf("uniVlanConfigFsm not in expected disabled state for device-id %x", dh.DeviceID)
mpagenkodff5dda2020-08-28 11:52:01 +00003066 }
3067 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00003068 logger.Errorw(ctx, "UniVlanConfigFsm StateMachine invalid - cannot be executed!!", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003069 "device-id": dh.DeviceID})
3070 return fmt.Errorf("uniVlanConfigFsm invalid for device-id %x", dh.DeviceID)
mpagenkodff5dda2020-08-28 11:52:01 +00003071 }
3072 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00003073 logger.Errorw(ctx, "UniVlanConfigFsm could not be created - abort!!", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003074 "device-id": dh.DeviceID, "UniPort": apUniPort.PortNo})
3075 return fmt.Errorf("uniVlanConfigFsm could not be created for device-id %x", dh.DeviceID)
mpagenkodff5dda2020-08-28 11:52:01 +00003076 }
3077 return nil
3078}
3079
mpagenkofc4f56e2020-11-04 17:17:49 +00003080//VerifyVlanConfigRequest checks on existence of a given uniPort
3081// and starts verification of flow config based on that
mpagenko551a4d42020-12-08 18:09:20 +00003082func (dh *deviceHandler) VerifyVlanConfigRequest(ctx context.Context, aUniID uint8, aTpID uint8) {
mpagenkofc4f56e2020-11-04 17:17:49 +00003083 //ensure that the given uniID is available (configured) in the UniPort class (used for OMCI entities)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003084 var pCurrentUniPort *cmn.OnuUniPort
mpagenkofc4f56e2020-11-04 17:17:49 +00003085 for _, uniPort := range dh.uniEntityMap {
3086 // only if this port is validated for operState transfer
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003087 if uniPort.UniID == uint8(aUniID) {
mpagenkofc4f56e2020-11-04 17:17:49 +00003088 pCurrentUniPort = uniPort
3089 break //found - end search loop
3090 }
3091 }
3092 if pCurrentUniPort == nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00003093 logger.Debugw(ctx, "VerifyVlanConfig aborted: requested uniID not found in PortDB",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003094 log.Fields{"device-id": dh.DeviceID, "uni-id": aUniID})
mpagenkofc4f56e2020-11-04 17:17:49 +00003095 return
3096 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003097 dh.VerifyUniVlanConfigRequest(ctx, pCurrentUniPort, aTpID)
mpagenkofc4f56e2020-11-04 17:17:49 +00003098}
3099
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003100//VerifyUniVlanConfigRequest checks on existence of flow configuration and starts it accordingly
3101func (dh *deviceHandler) VerifyUniVlanConfigRequest(ctx context.Context, apUniPort *cmn.OnuUniPort, aTpID uint8) {
mpagenkodff5dda2020-08-28 11:52:01 +00003102 //TODO!! verify and start pending flow configuration
3103 //some pending config request my exist in case the UniVlanConfig FSM was already started - with internal data -
3104 //but execution was set to 'on hold' as first the TechProfile config had to be applied
mpagenkof1fc3862021-02-16 10:09:52 +00003105
3106 dh.lockVlanConfig.RLock()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003107 if pVlanFilterFsm, exist := dh.UniVlanConfigFsmMap[apUniPort.UniID]; exist {
mpagenkof1fc3862021-02-16 10:09:52 +00003108 dh.lockVlanConfig.RUnlock()
mpagenkodff5dda2020-08-28 11:52:01 +00003109 //VlanFilterFsm exists and was already started (assumed to wait for TechProfile execution here)
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003110 pVlanFilterStatemachine := pVlanFilterFsm.PAdaptFsm.PFsm
mpagenkodff5dda2020-08-28 11:52:01 +00003111 if pVlanFilterStatemachine != nil {
mpagenko551a4d42020-12-08 18:09:20 +00003112 //if this was an event of the TP processing that was waited for in the VlanFilterFsm
3113 if pVlanFilterFsm.GetWaitingTpID() == aTpID {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003114 if pVlanFilterStatemachine.Is(avcfg.VlanStWaitingTechProf) {
3115 if err := pVlanFilterStatemachine.Event(avcfg.VlanEvContinueConfig); err != nil {
mpagenko551a4d42020-12-08 18:09:20 +00003116 logger.Warnw(ctx, "UniVlanConfigFsm: can't continue processing", log.Fields{"err": err,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003117 "device-id": dh.DeviceID, "UniPort": apUniPort.PortNo})
mpagenko551a4d42020-12-08 18:09:20 +00003118 } else {
3119 /***** UniVlanConfigFsm continued */
3120 logger.Debugw(ctx, "UniVlanConfigFsm continued", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003121 "state": pVlanFilterStatemachine.Current(), "device-id": dh.DeviceID,
3122 "UniPort": apUniPort.PortNo})
mpagenko551a4d42020-12-08 18:09:20 +00003123 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003124 } else if pVlanFilterStatemachine.Is(avcfg.VlanStIncrFlowWaitTP) {
3125 if err := pVlanFilterStatemachine.Event(avcfg.VlanEvIncrFlowConfig); err != nil {
mpagenko551a4d42020-12-08 18:09:20 +00003126 logger.Warnw(ctx, "UniVlanConfigFsm: can't continue processing", log.Fields{"err": err,
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003127 "device-id": dh.DeviceID, "UniPort": apUniPort.PortNo})
mpagenko551a4d42020-12-08 18:09:20 +00003128 } else {
3129 /***** UniVlanConfigFsm continued */
3130 logger.Debugw(ctx, "UniVlanConfigFsm continued with incremental flow", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003131 "state": pVlanFilterStatemachine.Current(), "device-id": dh.DeviceID,
3132 "UniPort": apUniPort.PortNo})
mpagenko551a4d42020-12-08 18:09:20 +00003133 }
mpagenkodff5dda2020-08-28 11:52:01 +00003134 } else {
mpagenko551a4d42020-12-08 18:09:20 +00003135 logger.Debugw(ctx, "no state of UniVlanConfigFsm to be continued", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003136 "have": pVlanFilterStatemachine.Current(), "device-id": dh.DeviceID,
3137 "UniPort": apUniPort.PortNo})
mpagenkodff5dda2020-08-28 11:52:01 +00003138 }
3139 } else {
mpagenko551a4d42020-12-08 18:09:20 +00003140 logger.Debugw(ctx, "TechProfile Ready event for TpId that was not waited for in the VlanConfigFsm - continue waiting", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003141 "state": pVlanFilterStatemachine.Current(), "device-id": dh.DeviceID,
3142 "UniPort": apUniPort.PortNo, "techprofile-id (done)": aTpID})
mpagenkodff5dda2020-08-28 11:52:01 +00003143 }
3144 } else {
dbainbri4d3a0dc2020-12-02 00:33:42 +00003145 logger.Debugw(ctx, "UniVlanConfigFsm StateMachine does not exist, no flow processing", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003146 "device-id": dh.DeviceID, "UniPort": apUniPort.PortNo})
mpagenkodff5dda2020-08-28 11:52:01 +00003147 }
mpagenkof1fc3862021-02-16 10:09:52 +00003148 } else {
3149 dh.lockVlanConfig.RUnlock()
3150 }
mpagenkodff5dda2020-08-28 11:52:01 +00003151}
3152
3153//RemoveVlanFilterFsm deletes the stored pointer to the VlanConfigFsm
3154// intention is to provide this method to be called from VlanConfigFsm itself, when resources (and methods!) are cleaned up
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003155func (dh *deviceHandler) RemoveVlanFilterFsm(ctx context.Context, apUniPort *cmn.OnuUniPort) {
dbainbri4d3a0dc2020-12-02 00:33:42 +00003156 logger.Debugw(ctx, "remove UniVlanConfigFsm StateMachine", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003157 "device-id": dh.DeviceID, "uniPort": apUniPort.PortNo})
mpagenkodff5dda2020-08-28 11:52:01 +00003158 //save to do, even if entry dows not exist
mpagenkof1fc3862021-02-16 10:09:52 +00003159 dh.lockVlanConfig.Lock()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003160 delete(dh.UniVlanConfigFsmMap, apUniPort.UniID)
mpagenkof1fc3862021-02-16 10:09:52 +00003161 dh.lockVlanConfig.Unlock()
mpagenkodff5dda2020-08-28 11:52:01 +00003162}
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003163
mpagenkof1fc3862021-02-16 10:09:52 +00003164//startWritingOnuDataToKvStore initiates the KVStore write of ONU persistent data
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003165func (dh *deviceHandler) startWritingOnuDataToKvStore(ctx context.Context, aPDevEntry *mib.OnuDeviceEntry) error {
mpagenkof1fc3862021-02-16 10:09:52 +00003166 dh.mutexKvStoreContext.Lock() //this write routine may (could) be called with the same context,
3167 defer dh.mutexKvStoreContext.Unlock() //this write routine may (could) be called with the same context,
3168 // obviously then parallel processing on the cancel must be avoided
3169 // deadline context to ensure completion of background routines waited for
3170 //20200721: 10s proved to be less in 8*8 ONU test on local vbox machine with debug, might be further adapted
3171 deadline := time.Now().Add(dh.pOpenOnuAc.maxTimeoutInterAdapterComm) //allowed run time to finish before execution
3172 dctx, cancel := context.WithDeadline(context.Background(), deadline)
3173
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003174 aPDevEntry.ResetKvProcessingErrorIndication()
mpagenkof1fc3862021-02-16 10:09:52 +00003175 var wg sync.WaitGroup
3176 wg.Add(1) // for the 1 go routine to finish
3177
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003178 go aPDevEntry.UpdateOnuKvStore(log.WithSpanFromContext(dctx, ctx), &wg)
mpagenkof1fc3862021-02-16 10:09:52 +00003179 dh.waitForCompletion(ctx, cancel, &wg, "UpdateKvStore") //wait for background process to finish
3180
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003181 return aPDevEntry.GetKvProcessingErrorIndication()
mpagenkof1fc3862021-02-16 10:09:52 +00003182}
3183
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003184//StorePersUniFlowConfig updates local storage of OnuUniFlowConfig and writes it into kv-store afterwards to have it
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003185//available for potential reconcilement
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003186func (dh *deviceHandler) StorePersUniFlowConfig(ctx context.Context, aUniID uint8,
3187 aUniVlanFlowParams *[]cmn.UniVlanFlowParams, aWriteToKvStore bool) error {
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003188
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003189 if dh.IsReconciling() {
3190 logger.Debugw(ctx, "reconciling - don't store persistent UniFlowConfig", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003191 return nil
3192 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003193 logger.Debugw(ctx, "Store or clear persistent UniFlowConfig", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003194
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003195 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003196 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003197 logger.Errorw(ctx, "No valid OnuDevice - aborting", log.Fields{"device-id": dh.DeviceID})
3198 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003199 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003200 pDevEntry.UpdateOnuUniFlowConfig(aUniID, aUniVlanFlowParams)
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003201
mpagenkof1fc3862021-02-16 10:09:52 +00003202 if aWriteToKvStore {
3203 return dh.startWritingOnuDataToKvStore(ctx, pDevEntry)
3204 }
3205 return nil
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003206}
3207
dbainbri4d3a0dc2020-12-02 00:33:42 +00003208func (dh *deviceHandler) waitForCompletion(ctx context.Context, cancel context.CancelFunc, wg *sync.WaitGroup, aCallerIdent string) {
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003209 defer cancel() //ensure termination of context (may be pro forma)
3210 wg.Wait()
dbainbri4d3a0dc2020-12-02 00:33:42 +00003211 logger.Debugw(ctx, "WaitGroup processing completed", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003212 "device-id": dh.DeviceID, "called from": aCallerIdent})
Holger Hildebrandt47555e72020-09-21 11:07:24 +00003213}
3214
dbainbri4d3a0dc2020-12-02 00:33:42 +00003215func (dh *deviceHandler) deviceReasonUpdate(ctx context.Context, deviceReason uint8, notifyCore bool) error {
Holger Hildebrandt80129db2020-11-23 10:49:32 +00003216
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003217 dh.SetDeviceReason(deviceReason)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00003218 if notifyCore {
Holger Hildebrandt80129db2020-11-23 10:49:32 +00003219 //TODO with VOL-3045/VOL-3046: return the error and stop further processing at calling position
khenaidoo7d3c5582021-08-11 18:09:44 -04003220 if err := dh.updateDeviceReasonInCore(ctx, &ic.DeviceReason{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003221 DeviceId: dh.DeviceID,
3222 Reason: cmn.DeviceReasonMap[deviceReason],
khenaidoo7d3c5582021-08-11 18:09:44 -04003223 }); err != nil {
dbainbri4d3a0dc2020-12-02 00:33:42 +00003224 logger.Errorf(ctx, "DeviceReasonUpdate error: %s",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003225 log.Fields{"device-id": dh.DeviceID, "error": err}, cmn.DeviceReasonMap[deviceReason])
Holger Hildebrandt80129db2020-11-23 10:49:32 +00003226 return err
3227 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003228 logger.Infof(ctx, "DeviceReasonUpdate success: %s - device-id: %s", cmn.DeviceReasonMap[deviceReason], dh.DeviceID)
Holger Hildebrandt80129db2020-11-23 10:49:32 +00003229 return nil
3230 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003231 logger.Infof(ctx, "Don't notify core about DeviceReasonUpdate: %s - device-id: %s", cmn.DeviceReasonMap[deviceReason], dh.DeviceID)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00003232 return nil
3233}
3234
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003235func (dh *deviceHandler) StorePersistentData(ctx context.Context) error {
3236 pDevEntry := dh.GetOnuDeviceEntry(ctx, true)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00003237 if pDevEntry == nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003238 logger.Warnw(ctx, "No valid OnuDevice", log.Fields{"device-id": dh.DeviceID})
3239 return fmt.Errorf("no valid OnuDevice: %s", dh.DeviceID)
Holger Hildebrandt3a644642020-12-02 09:46:18 +00003240 }
mpagenkof1fc3862021-02-16 10:09:52 +00003241 return dh.startWritingOnuDataToKvStore(ctx, pDevEntry)
Holger Hildebrandt80129db2020-11-23 10:49:32 +00003242}
3243
ozgecanetsiab5000ef2020-11-27 14:38:20 +03003244// getUniPortMEEntityID takes uniPortNo as the input and returns the Entity ID corresponding to this UNI-G ME Instance
ozgecanetsia72e1c9f2021-05-26 17:26:29 +03003245// nolint: unused
ozgecanetsiab5000ef2020-11-27 14:38:20 +03003246func (dh *deviceHandler) getUniPortMEEntityID(uniPortNo uint32) (uint16, error) {
3247 dh.lockDevice.RLock()
3248 defer dh.lockDevice.RUnlock()
3249 if uniPort, ok := dh.uniEntityMap[uniPortNo]; ok {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003250 return uniPort.EntityID, nil
ozgecanetsiab5000ef2020-11-27 14:38:20 +03003251 }
3252 return 0, errors.New("error-fetching-uni-port")
3253}
Girish Gowdrae09a6202021-01-12 18:10:59 -08003254
3255// updatePmConfig updates the pm metrics config.
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003256func (dh *deviceHandler) updatePmConfig(ctx context.Context, pmConfigs *voltha.PmConfigs) error {
3257 var errorsList []error
3258 logger.Infow(ctx, "update-pm-config", log.Fields{"device-id": dh.device.Id, "new-pm-configs": pmConfigs, "old-pm-config": dh.pmConfigs})
Girish Gowdrae09a6202021-01-12 18:10:59 -08003259
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003260 errorsList = append(dh.handleGlobalPmConfigUpdates(ctx, pmConfigs), errorsList...)
3261 errorsList = append(dh.handleGroupPmConfigUpdates(ctx, pmConfigs), errorsList...)
3262 errorsList = append(dh.handleStandalonePmConfigUpdates(ctx, pmConfigs), errorsList...)
3263
3264 // Note that if more than one pm config field is updated in a given call, it is possible that partial pm config is handled
3265 // successfully.
3266 // TODO: Although it is possible to revert to old config in case of partial failure, the code becomes quite complex. Needs more investigation
3267 // Is it possible the rw-core reverts to old config on partial failure but adapter retains a partial new config?
3268 if len(errorsList) > 0 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003269 logger.Errorw(ctx, "one-or-more-pm-config-failed", log.Fields{"device-id": dh.DeviceID, "pmConfig": dh.pmConfigs})
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003270 return fmt.Errorf("errors-handling-one-or-more-pm-config, errors:%v", errorsList)
Girish Gowdrae09a6202021-01-12 18:10:59 -08003271 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003272 logger.Infow(ctx, "pm-config-updated", log.Fields{"device-id": dh.DeviceID, "pmConfig": dh.pmConfigs})
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003273 return nil
Girish Gowdrae09a6202021-01-12 18:10:59 -08003274}
3275
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003276func (dh *deviceHandler) handleGlobalPmConfigUpdates(ctx context.Context, pmConfigs *voltha.PmConfigs) []error {
3277 var err error
3278 var errorsList []error
Girish Gowdra36ccf7d2021-02-25 20:42:51 -08003279 logger.Infow(ctx, "handling-global-pm-config-params - start", log.Fields{"device-id": dh.device.Id})
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003280
3281 if pmConfigs.DefaultFreq != dh.pmConfigs.DefaultFreq {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003282 if err = dh.pOnuMetricsMgr.UpdateDefaultFrequency(ctx, pmConfigs); err != nil {
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003283 errorsList = append(errorsList, err)
3284 }
3285 }
Girish Gowdra36ccf7d2021-02-25 20:42:51 -08003286 logger.Infow(ctx, "handling-global-pm-config-params - done", log.Fields{"device-id": dh.device.Id})
mpagenko15ff4a52021-03-02 10:09:20 +00003287
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003288 return errorsList
3289}
3290
3291func (dh *deviceHandler) handleGroupPmConfigUpdates(ctx context.Context, pmConfigs *voltha.PmConfigs) []error {
3292 var err error
3293 var errorsList []error
Girish Gowdra36ccf7d2021-02-25 20:42:51 -08003294 logger.Debugw(ctx, "handling-group-pm-config-params - start", log.Fields{"device-id": dh.device.Id})
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003295 // Check if group metric related config is updated
3296 for _, v := range pmConfigs.Groups {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003297 dh.pOnuMetricsMgr.OnuMetricsManagerLock.RLock()
3298 m, ok := dh.pOnuMetricsMgr.GroupMetricMap[v.GroupName]
3299 dh.pOnuMetricsMgr.OnuMetricsManagerLock.RUnlock()
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003300
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003301 if ok && m.Frequency != v.GroupFreq {
3302 if err = dh.pOnuMetricsMgr.UpdateGroupFreq(ctx, v.GroupName, pmConfigs); err != nil {
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003303 errorsList = append(errorsList, err)
3304 }
3305 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003306 if ok && m.Enabled != v.Enabled {
3307 if err = dh.pOnuMetricsMgr.UpdateGroupSupport(ctx, v.GroupName, pmConfigs); err != nil {
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003308 errorsList = append(errorsList, err)
3309 }
3310 }
3311 }
Girish Gowdra36ccf7d2021-02-25 20:42:51 -08003312 logger.Debugw(ctx, "handling-group-pm-config-params - done", log.Fields{"device-id": dh.device.Id})
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003313 return errorsList
3314}
3315
3316func (dh *deviceHandler) handleStandalonePmConfigUpdates(ctx context.Context, pmConfigs *voltha.PmConfigs) []error {
3317 var err error
3318 var errorsList []error
Girish Gowdra36ccf7d2021-02-25 20:42:51 -08003319 logger.Debugw(ctx, "handling-individual-pm-config-params - start", log.Fields{"device-id": dh.device.Id})
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003320 // Check if standalone metric related config is updated
3321 for _, v := range pmConfigs.Metrics {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003322 dh.pOnuMetricsMgr.OnuMetricsManagerLock.RLock()
3323 m, ok := dh.pOnuMetricsMgr.StandaloneMetricMap[v.Name]
3324 dh.pOnuMetricsMgr.OnuMetricsManagerLock.RUnlock()
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003325
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003326 if ok && m.Frequency != v.SampleFreq {
3327 if err = dh.pOnuMetricsMgr.UpdateMetricFreq(ctx, v.Name, pmConfigs); err != nil {
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003328 errorsList = append(errorsList, err)
3329 }
3330 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003331 if ok && m.Enabled != v.Enabled {
3332 if err = dh.pOnuMetricsMgr.UpdateMetricSupport(ctx, v.Name, pmConfigs); err != nil {
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003333 errorsList = append(errorsList, err)
3334 }
3335 }
3336 }
Girish Gowdra36ccf7d2021-02-25 20:42:51 -08003337 logger.Debugw(ctx, "handling-individual-pm-config-params - done", log.Fields{"device-id": dh.device.Id})
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003338 return errorsList
3339}
3340
3341// nolint: gocyclo
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003342func (dh *deviceHandler) StartCollector(ctx context.Context) {
Girish Gowdrae09a6202021-01-12 18:10:59 -08003343 logger.Debugf(ctx, "startingCollector")
3344
3345 // Start routine to process OMCI GET Responses
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003346 go dh.pOnuMetricsMgr.ProcessOmciMessages(ctx)
Himani Chawla43f95ff2021-06-03 00:24:12 +05303347 // Create Extended Frame PM ME
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003348 go dh.pOnuMetricsMgr.CreateEthernetFrameExtendedPMME(ctx)
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003349 // Initialize the next metric collection time.
3350 // Normally done when the onu_metrics_manager is initialized the first time, but needed again later when ONU is
3351 // reset like onu rebooted.
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003352 dh.pOnuMetricsMgr.InitializeMetricCollectionTime(ctx)
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003353 dh.setCollectorIsRunning(true)
Girish Gowdrae09a6202021-01-12 18:10:59 -08003354 for {
3355 select {
3356 case <-dh.stopCollector:
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003357 dh.setCollectorIsRunning(false)
Girish Gowdrae09a6202021-01-12 18:10:59 -08003358 logger.Debugw(ctx, "stopping-collector-for-onu", log.Fields{"device-id": dh.device.Id})
Girish Gowdrae0140f02021-02-02 16:55:09 -08003359 // Stop the L2 PM FSM
3360 go func() {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003361 if dh.pOnuMetricsMgr.PAdaptFsm != nil && dh.pOnuMetricsMgr.PAdaptFsm.PFsm != nil {
3362 if err := dh.pOnuMetricsMgr.PAdaptFsm.PFsm.Event(pmmgr.L2PmEventStop); err != nil {
3363 logger.Errorw(ctx, "error calling event", log.Fields{"device-id": dh.DeviceID, "err": err})
Girish Gowdrae0140f02021-02-02 16:55:09 -08003364 }
3365 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003366 logger.Errorw(ctx, "metrics manager fsm not initialized", log.Fields{"device-id": dh.DeviceID})
Girish Gowdrae0140f02021-02-02 16:55:09 -08003367 }
3368 }()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003369 if dh.pOnuMetricsMgr.GetOmciProcessingStatus() {
3370 dh.pOnuMetricsMgr.StopProcessingOmciResponses <- true // Stop the OMCI GET response processing routine
Girish Gowdra7b0ee5c2021-03-19 21:48:15 -07003371 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003372 if dh.pOnuMetricsMgr.GetTickGenerationStatus() {
3373 dh.pOnuMetricsMgr.StopTicks <- true
Girish Gowdra7b0ee5c2021-03-19 21:48:15 -07003374 }
Girish Gowdrae0140f02021-02-02 16:55:09 -08003375
Girish Gowdrae09a6202021-01-12 18:10:59 -08003376 return
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003377 case <-time.After(time.Duration(pmmgr.FrequencyGranularity) * time.Second): // Check every FrequencyGranularity to see if it is time for collecting metrics
3378 if !dh.pmConfigs.FreqOverride { // If FreqOverride is false, then NextGlobalMetricCollectionTime applies
3379 // If the current time is eqaul to or greater than the NextGlobalMetricCollectionTime, collect the group and standalone metrics
3380 if time.Now().Equal(dh.pOnuMetricsMgr.NextGlobalMetricCollectionTime) || time.Now().After(dh.pOnuMetricsMgr.NextGlobalMetricCollectionTime) {
3381 go dh.pOnuMetricsMgr.CollectAllGroupAndStandaloneMetrics(ctx)
Girish Gowdraaf0ad632021-01-27 13:00:01 -08003382 // Update the next metric collection time.
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003383 dh.pOnuMetricsMgr.NextGlobalMetricCollectionTime = time.Now().Add(time.Duration(dh.pmConfigs.DefaultFreq) * time.Second)
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003384 }
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003385 } else {
3386 if dh.pmConfigs.Grouped { // metrics are managed as a group
3387 // parse through the group and standalone metrics to see it is time to collect their metrics
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003388 dh.pOnuMetricsMgr.OnuMetricsManagerLock.RLock() // Rlock as we are reading GroupMetricMap and StandaloneMetricMap
Girish Gowdrae09a6202021-01-12 18:10:59 -08003389
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003390 for n, g := range dh.pOnuMetricsMgr.GroupMetricMap {
3391 // If the group is enabled AND (current time is equal to OR after NextCollectionInterval, collect the group metric)
Girish Gowdrae0140f02021-02-02 16:55:09 -08003392 // Since the L2 PM counters are collected in a separate FSM, we should avoid those counters in the check.
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003393 if g.Enabled && !g.IsL2PMCounter && (time.Now().Equal(g.NextCollectionInterval) || time.Now().After(g.NextCollectionInterval)) {
3394 go dh.pOnuMetricsMgr.CollectGroupMetric(ctx, n)
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003395 }
3396 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003397 for n, m := range dh.pOnuMetricsMgr.StandaloneMetricMap {
3398 // If the standalone is enabled AND (current time is equal to OR after NextCollectionInterval, collect the metric)
3399 if m.Enabled && (time.Now().Equal(m.NextCollectionInterval) || time.Now().After(m.NextCollectionInterval)) {
3400 go dh.pOnuMetricsMgr.CollectStandaloneMetric(ctx, n)
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003401 }
3402 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003403 dh.pOnuMetricsMgr.OnuMetricsManagerLock.RUnlock()
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003404
3405 // parse through the group and update the next metric collection time
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003406 dh.pOnuMetricsMgr.OnuMetricsManagerLock.Lock() // Lock as we are writing the next metric collection time
3407 for _, g := range dh.pOnuMetricsMgr.GroupMetricMap {
3408 // If group enabled, and the NextCollectionInterval is old (before or equal to current time), update the next collection time stamp
Girish Gowdrae0140f02021-02-02 16:55:09 -08003409 // Since the L2 PM counters are collected and managed in a separate FSM, we should avoid those counters in the check.
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003410 if g.Enabled && !g.IsL2PMCounter && (g.NextCollectionInterval.Before(time.Now()) || g.NextCollectionInterval.Equal(time.Now())) {
3411 g.NextCollectionInterval = time.Now().Add(time.Duration(g.Frequency) * time.Second)
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003412 }
3413 }
3414 // parse through the standalone metrics and update the next metric collection time
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003415 for _, m := range dh.pOnuMetricsMgr.StandaloneMetricMap {
3416 // If standalone metrics enabled, and the NextCollectionInterval is old (before or equal to current time), update the next collection time stamp
3417 if m.Enabled && (m.NextCollectionInterval.Before(time.Now()) || m.NextCollectionInterval.Equal(time.Now())) {
3418 m.NextCollectionInterval = time.Now().Add(time.Duration(m.Frequency) * time.Second)
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003419 }
3420 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003421 dh.pOnuMetricsMgr.OnuMetricsManagerLock.Unlock()
Girish Gowdra5a7c4922021-01-22 18:33:41 -08003422 } /* else { // metrics are not managed as a group
3423 // TODO: We currently do not have standalone metrics. When available, add code here to fetch the metric.
3424 } */
3425 }
Girish Gowdrae09a6202021-01-12 18:10:59 -08003426 }
3427 }
3428}
kesavandfdf77632021-01-26 23:40:33 -05003429
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003430func (dh *deviceHandler) GetUniPortStatus(ctx context.Context, uniInfo *extension.GetOnuUniInfoRequest) *extension.SingleGetValueResponse {
kesavandfdf77632021-01-26 23:40:33 -05003431
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003432 portStatus := uniprt.NewUniPortStatus(dh, dh.pOnuOmciDevice.PDevOmciCC)
3433 return portStatus.GetUniPortStatus(ctx, uniInfo.UniIndex)
kesavandfdf77632021-01-26 23:40:33 -05003434}
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003435
Himani Chawla43f95ff2021-06-03 00:24:12 +05303436func (dh *deviceHandler) getOnuOMCICounters(ctx context.Context, onuInfo *extension.GetOmciEthernetFrameExtendedPmRequest) *extension.SingleGetValueResponse {
3437 if dh.pOnuMetricsMgr == nil {
3438 return &extension.SingleGetValueResponse{
3439 Response: &extension.GetValueResponse{
3440 Status: extension.GetValueResponse_ERROR,
3441 ErrReason: extension.GetValueResponse_INTERNAL_ERROR,
3442 },
3443 }
3444 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003445 resp := dh.pOnuMetricsMgr.CollectEthernetFrameExtendedPMCounters(ctx)
Himani Chawla43f95ff2021-06-03 00:24:12 +05303446 return resp
3447}
3448
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003449func (dh *deviceHandler) isFsmInOmciIdleState(ctx context.Context, PFsm *fsm.FSM, wantedState string) bool {
3450 if PFsm == nil {
mpagenkof1fc3862021-02-16 10:09:52 +00003451 return true //FSM not active - so there is no activity on omci
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003452 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003453 return PFsm.Current() == wantedState
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003454}
3455
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003456func (dh *deviceHandler) isFsmInOmciIdleStateDefault(ctx context.Context, omciFsm cmn.UsedOmciConfigFsms, wantedState string) bool {
3457 var PFsm *fsm.FSM
mpagenkof1fc3862021-02-16 10:09:52 +00003458 //note/TODO!!: might be that access to all these specific FSM; pointers need a semaphore protection as well, cmp lockUpgradeFsm
3459 switch omciFsm {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003460 case cmn.CUploadFsm:
mpagenkof1fc3862021-02-16 10:09:52 +00003461 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003462 PFsm = dh.pOnuOmciDevice.PMibUploadFsm.PFsm
mpagenkof1fc3862021-02-16 10:09:52 +00003463 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003464 case cmn.CDownloadFsm:
mpagenkof1fc3862021-02-16 10:09:52 +00003465 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003466 PFsm = dh.pOnuOmciDevice.PMibDownloadFsm.PFsm
mpagenkof1fc3862021-02-16 10:09:52 +00003467 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003468 case cmn.CUniLockFsm:
mpagenkof1fc3862021-02-16 10:09:52 +00003469 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003470 PFsm = dh.pLockStateFsm.PAdaptFsm.PFsm
mpagenkof1fc3862021-02-16 10:09:52 +00003471 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003472 case cmn.CUniUnLockFsm:
mpagenkof1fc3862021-02-16 10:09:52 +00003473 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003474 PFsm = dh.pUnlockStateFsm.PAdaptFsm.PFsm
mpagenkof1fc3862021-02-16 10:09:52 +00003475 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003476 case cmn.CL2PmFsm:
mpagenkof1fc3862021-02-16 10:09:52 +00003477 {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003478 if dh.pOnuMetricsMgr != nil && dh.pOnuMetricsMgr.PAdaptFsm != nil {
3479 PFsm = dh.pOnuMetricsMgr.PAdaptFsm.PFsm
mpagenkof1fc3862021-02-16 10:09:52 +00003480 } else {
3481 return true //FSM not active - so there is no activity on omci
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003482 }
3483 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003484 case cmn.COnuUpgradeFsm:
mpagenko80622a52021-02-09 16:53:23 +00003485 {
3486 dh.lockUpgradeFsm.RLock()
3487 defer dh.lockUpgradeFsm.RUnlock()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003488 PFsm = dh.pOnuUpradeFsm.PAdaptFsm.PFsm
mpagenko80622a52021-02-09 16:53:23 +00003489 }
mpagenkof1fc3862021-02-16 10:09:52 +00003490 default:
3491 {
3492 logger.Errorw(ctx, "invalid stateMachine selected for idle check", log.Fields{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003493 "device-id": dh.DeviceID, "selectedFsm number": omciFsm})
mpagenkof1fc3862021-02-16 10:09:52 +00003494 return false //logical error in FSM check, do not not indicate 'idle' - we can't be sure
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003495 }
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003496 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003497 return dh.isFsmInOmciIdleState(ctx, PFsm, wantedState)
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003498}
3499
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003500func (dh *deviceHandler) isAniConfigFsmInOmciIdleState(ctx context.Context, omciFsm cmn.UsedOmciConfigFsms, idleState string) bool {
3501 for _, v := range dh.pOnuTP.PAniConfigFsm {
3502 if !dh.isFsmInOmciIdleState(ctx, v.PAdaptFsm.PFsm, idleState) {
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003503 return false
3504 }
3505 }
3506 return true
3507}
3508
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003509func (dh *deviceHandler) isUniVlanConfigFsmInOmciIdleState(ctx context.Context, omciFsm cmn.UsedOmciConfigFsms, idleState string) bool {
mpagenkof1fc3862021-02-16 10:09:52 +00003510 dh.lockVlanConfig.RLock()
3511 defer dh.lockVlanConfig.RUnlock()
3512 for _, v := range dh.UniVlanConfigFsmMap {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003513 if !dh.isFsmInOmciIdleState(ctx, v.PAdaptFsm.PFsm, idleState) {
mpagenkof1fc3862021-02-16 10:09:52 +00003514 return false
3515 }
3516 }
3517 return true //FSM not active - so there is no activity on omci
3518}
3519
3520func (dh *deviceHandler) checkUserServiceExists(ctx context.Context) bool {
3521 dh.lockVlanConfig.RLock()
3522 defer dh.lockVlanConfig.RUnlock()
3523 for _, v := range dh.UniVlanConfigFsmMap {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003524 if v.PAdaptFsm.PFsm != nil {
3525 if v.PAdaptFsm.PFsm.Is(avcfg.CVlanFsmConfiguredState) {
mpagenkof1fc3862021-02-16 10:09:52 +00003526 return true //there is at least one VLAN FSM with some active configuration
3527 }
3528 }
3529 }
3530 return false //there is no VLAN FSM with some active configuration
3531}
3532
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003533func (dh *deviceHandler) CheckAuditStartCondition(ctx context.Context, callingFsm cmn.UsedOmciConfigFsms) bool {
mpagenkof1fc3862021-02-16 10:09:52 +00003534 for fsmName, fsmStruct := range fsmOmciIdleStateFuncMap {
3535 if fsmName != callingFsm && !fsmStruct.omciIdleCheckFunc(dh, ctx, fsmName, fsmStruct.omciIdleState) {
3536 return false
3537 }
3538 }
3539 // a further check is done to identify, if at least some data traffic related configuration exists
3540 // so that a user of this ONU could be 'online' (otherwise it makes no sense to check the MDS [with the intention to keep the user service up])
3541 return dh.checkUserServiceExists(ctx)
3542}
3543
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003544func (dh *deviceHandler) PrepareReconcilingWithActiveAdapter(ctx context.Context) {
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003545 logger.Debugw(ctx, "prepare to reconcile the ONU with adapter using persistency data", log.Fields{"device-id": dh.device.Id})
3546 if err := dh.resetFsms(ctx, false); err != nil {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003547 logger.Errorw(ctx, "reset of FSMs failed!", log.Fields{"device-id": dh.DeviceID, "error": err})
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003548 // TODO: fatal error reset ONU, delete deviceHandler!
3549 return
3550 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003551 dh.uniEntityMap = make(map[uint32]*cmn.OnuUniPort)
3552 dh.StartReconciling(ctx, false)
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003553}
3554
3555func (dh *deviceHandler) setCollectorIsRunning(flagValue bool) {
3556 dh.mutexCollectorFlag.Lock()
3557 dh.collectorIsRunning = flagValue
3558 dh.mutexCollectorFlag.Unlock()
3559}
3560
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003561func (dh *deviceHandler) GetCollectorIsRunning() bool {
Holger Hildebrandt10d98192021-01-27 15:29:31 +00003562 dh.mutexCollectorFlag.RLock()
3563 flagValue := dh.collectorIsRunning
3564 dh.mutexCollectorFlag.RUnlock()
3565 return flagValue
3566}
Himani Chawlaac1f5ad2021-02-04 21:21:54 +05303567
Himani Chawla4c1d4c72021-02-18 12:14:31 +05303568func (dh *deviceHandler) setAlarmManagerIsRunning(flagValue bool) {
3569 dh.mutextAlarmManagerFlag.Lock()
3570 dh.alarmManagerIsRunning = flagValue
3571 dh.mutextAlarmManagerFlag.Unlock()
3572}
3573
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003574func (dh *deviceHandler) GetAlarmManagerIsRunning(ctx context.Context) bool {
Himani Chawla4c1d4c72021-02-18 12:14:31 +05303575 dh.mutextAlarmManagerFlag.RLock()
3576 flagValue := dh.alarmManagerIsRunning
Himani Chawla1472c682021-03-17 17:11:14 +05303577 logger.Debugw(ctx, "alarm-manager-is-running", log.Fields{"flag": dh.alarmManagerIsRunning})
Himani Chawla4c1d4c72021-02-18 12:14:31 +05303578 dh.mutextAlarmManagerFlag.RUnlock()
3579 return flagValue
3580}
3581
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003582func (dh *deviceHandler) StartAlarmManager(ctx context.Context) {
Himani Chawlaac1f5ad2021-02-04 21:21:54 +05303583 logger.Debugf(ctx, "startingAlarmManager")
3584
3585 // Start routine to process OMCI GET Responses
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003586 go dh.pAlarmMgr.StartOMCIAlarmMessageProcessing(ctx)
Himani Chawla4c1d4c72021-02-18 12:14:31 +05303587 dh.setAlarmManagerIsRunning(true)
Himani Chawlaac1f5ad2021-02-04 21:21:54 +05303588 if stop := <-dh.stopAlarmManager; stop {
3589 logger.Debugw(ctx, "stopping-collector-for-onu", log.Fields{"device-id": dh.device.Id})
Himani Chawla4c1d4c72021-02-18 12:14:31 +05303590 dh.setAlarmManagerIsRunning(false)
Himani Chawlad3dac422021-03-13 02:31:31 +05303591 go func() {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003592 if dh.pAlarmMgr.AlarmSyncFsm != nil && dh.pAlarmMgr.AlarmSyncFsm.PFsm != nil {
3593 _ = dh.pAlarmMgr.AlarmSyncFsm.PFsm.Event(almgr.AsEvStop)
Himani Chawla1472c682021-03-17 17:11:14 +05303594 }
Himani Chawlad3dac422021-03-13 02:31:31 +05303595 }()
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003596 dh.pAlarmMgr.StopProcessingOmciMessages <- true // Stop the OMCI routines if any(This will stop the fsms also)
3597 dh.pAlarmMgr.StopAlarmAuditTimer <- struct{}{}
Himani Chawla1472c682021-03-17 17:11:14 +05303598 logger.Debugw(ctx, "sent-all-stop-signals-to-alarm-manager", log.Fields{"device-id": dh.device.Id})
Himani Chawlaac1f5ad2021-02-04 21:21:54 +05303599 }
3600}
Holger Hildebrandt38985dc2021-02-18 16:25:20 +00003601
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003602func (dh *deviceHandler) StartReconciling(ctx context.Context, skipOnuConfig bool) {
3603 logger.Debugw(ctx, "start reconciling", log.Fields{"skipOnuConfig": skipOnuConfig, "device-id": dh.DeviceID})
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003604
Maninder7961d722021-06-16 22:10:28 +05303605 connectStatus := voltha.ConnectStatus_UNREACHABLE
3606 operState := voltha.OperStatus_UNKNOWN
3607
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003608 if !dh.IsReconciling() {
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003609 go func() {
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003610 logger.Debugw(ctx, "wait for channel signal or timeout",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003611 log.Fields{"timeout": dh.pOpenOnuAc.maxTimeoutReconciling, "device-id": dh.DeviceID})
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003612 select {
Holger Hildebrandtb4563ab2021-04-14 10:27:20 +00003613 case success := <-dh.chReconcilingFinished:
3614 if success {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003615 if onuDevEntry := dh.GetOnuDeviceEntry(ctx, true); onuDevEntry == nil {
Maninderb5187552021-03-23 22:23:42 +05303616 logger.Errorw(ctx, "No valid OnuDevice - aborting Core DeviceStateUpdate",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003617 log.Fields{"device-id": dh.DeviceID})
Maninderb5187552021-03-23 22:23:42 +05303618 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003619 if onuDevEntry.SOnuPersistentData.PersOperState == "up" {
Maninderb5187552021-03-23 22:23:42 +05303620 connectStatus = voltha.ConnectStatus_REACHABLE
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003621 if !onuDevEntry.SOnuPersistentData.PersUniDisableDone {
3622 if onuDevEntry.SOnuPersistentData.PersUniUnlockDone {
Maninderb5187552021-03-23 22:23:42 +05303623 operState = voltha.OperStatus_ACTIVE
3624 } else {
3625 operState = voltha.OperStatus_ACTIVATING
3626 }
3627 }
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003628 } else if onuDevEntry.SOnuPersistentData.PersOperState == "down" ||
3629 onuDevEntry.SOnuPersistentData.PersOperState == "unknown" ||
3630 onuDevEntry.SOnuPersistentData.PersOperState == "" {
Maninderb5187552021-03-23 22:23:42 +05303631 operState = voltha.OperStatus_DISCOVERED
3632 }
3633
3634 logger.Debugw(ctx, "Core DeviceStateUpdate", log.Fields{"connectStatus": connectStatus, "operState": operState})
Maninderb5187552021-03-23 22:23:42 +05303635 }
Holger Hildebrandtb4563ab2021-04-14 10:27:20 +00003636 logger.Debugw(ctx, "reconciling has been finished in time",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003637 log.Fields{"device-id": dh.DeviceID})
khenaidoo7d3c5582021-08-11 18:09:44 -04003638 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003639 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04003640 ConnStatus: connectStatus,
3641 OperStatus: operState,
3642 }); err != nil {
Maninder7961d722021-06-16 22:10:28 +05303643 logger.Errorw(ctx, "unable to update device state to core",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003644 log.Fields{"device-id": dh.DeviceID, "Err": err})
Maninder7961d722021-06-16 22:10:28 +05303645 }
Holger Hildebrandtb4563ab2021-04-14 10:27:20 +00003646 } else {
Maninderb5187552021-03-23 22:23:42 +05303647 logger.Errorw(ctx, "wait for reconciling aborted",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003648 log.Fields{"device-id": dh.DeviceID})
Maninder7961d722021-06-16 22:10:28 +05303649
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003650 if onuDevEntry := dh.GetOnuDeviceEntry(ctx, true); onuDevEntry == nil {
Maninder7961d722021-06-16 22:10:28 +05303651 logger.Errorw(ctx, "No valid OnuDevice",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003652 log.Fields{"device-id": dh.DeviceID})
3653 } else if onuDevEntry.SOnuPersistentData.PersOperState == "up" {
Maninder7961d722021-06-16 22:10:28 +05303654 connectStatus = voltha.ConnectStatus_REACHABLE
3655 }
3656
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003657 dh.deviceReconcileFailedUpdate(ctx, cmn.DrReconcileCanceled, connectStatus)
Holger Hildebrandtb4563ab2021-04-14 10:27:20 +00003658 }
Holger Hildebrandt38985dc2021-02-18 16:25:20 +00003659 case <-time.After(dh.pOpenOnuAc.maxTimeoutReconciling):
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003660 logger.Errorw(ctx, "timeout waiting for reconciling to be finished!",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003661 log.Fields{"device-id": dh.DeviceID})
Maninder7961d722021-06-16 22:10:28 +05303662
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003663 if onuDevEntry := dh.GetOnuDeviceEntry(ctx, true); onuDevEntry == nil {
Maninder7961d722021-06-16 22:10:28 +05303664 logger.Errorw(ctx, "No valid OnuDevice",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003665 log.Fields{"device-id": dh.DeviceID})
3666 } else if onuDevEntry.SOnuPersistentData.PersOperState == "up" {
Maninder7961d722021-06-16 22:10:28 +05303667 connectStatus = voltha.ConnectStatus_REACHABLE
3668 }
3669
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003670 dh.deviceReconcileFailedUpdate(ctx, cmn.DrReconcileMaxTimeout, connectStatus)
Maninder7961d722021-06-16 22:10:28 +05303671
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003672 }
3673 dh.mutexReconcilingFlag.Lock()
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003674 dh.reconciling = cNoReconciling
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003675 dh.mutexReconcilingFlag.Unlock()
3676 }()
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003677 }
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003678 dh.mutexReconcilingFlag.Lock()
3679 if skipOnuConfig {
3680 dh.reconciling = cSkipOnuConfigReconciling
3681 } else {
3682 dh.reconciling = cOnuConfigReconciling
3683 }
3684 dh.mutexReconcilingFlag.Unlock()
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003685}
3686
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003687func (dh *deviceHandler) StopReconciling(ctx context.Context, success bool) {
3688 logger.Debugw(ctx, "stop reconciling", log.Fields{"device-id": dh.DeviceID, "success": success})
3689 if dh.IsReconciling() {
Girish Gowdra50e56422021-06-01 16:46:04 -07003690 dh.chReconcilingFinished <- success
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003691 } else {
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003692 logger.Infow(ctx, "reconciling is not running", log.Fields{"device-id": dh.DeviceID})
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003693 }
3694}
3695
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003696func (dh *deviceHandler) IsReconciling() bool {
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003697 dh.mutexReconcilingFlag.RLock()
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003698 defer dh.mutexReconcilingFlag.RUnlock()
3699 return dh.reconciling != cNoReconciling
3700}
3701
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003702func (dh *deviceHandler) IsSkipOnuConfigReconciling() bool {
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003703 dh.mutexReconcilingFlag.RLock()
3704 defer dh.mutexReconcilingFlag.RUnlock()
3705 return dh.reconciling == cSkipOnuConfigReconciling
3706}
3707
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003708func (dh *deviceHandler) SetDeviceReason(value uint8) {
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003709 dh.mutexDeviceReason.Lock()
3710 dh.deviceReason = value
3711 dh.mutexDeviceReason.Unlock()
3712}
3713
3714func (dh *deviceHandler) getDeviceReason() uint8 {
3715 dh.mutexDeviceReason.RLock()
3716 value := dh.deviceReason
3717 dh.mutexDeviceReason.RUnlock()
Holger Hildebrandtf37b3d72021-02-17 10:25:22 +00003718 return value
3719}
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003720
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003721func (dh *deviceHandler) GetDeviceReasonString() string {
3722 return cmn.DeviceReasonMap[dh.getDeviceReason()]
Holger Hildebrandtbe523842021-03-10 10:47:18 +00003723}
Holger Hildebrandtb4563ab2021-04-14 10:27:20 +00003724
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003725func (dh *deviceHandler) SetReadyForOmciConfig(flagValue bool) {
Holger Hildebrandt0da7e6f2021-05-12 13:08:43 +00003726 dh.mutexReadyForOmciConfig.Lock()
3727 dh.readyForOmciConfig = flagValue
3728 dh.mutexReadyForOmciConfig.Unlock()
3729}
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003730func (dh *deviceHandler) IsReadyForOmciConfig() bool {
Holger Hildebrandt0da7e6f2021-05-12 13:08:43 +00003731 dh.mutexReadyForOmciConfig.RLock()
3732 flagValue := dh.readyForOmciConfig
3733 dh.mutexReadyForOmciConfig.RUnlock()
3734 return flagValue
3735}
Maninder7961d722021-06-16 22:10:28 +05303736
3737func (dh *deviceHandler) deviceReconcileFailedUpdate(ctx context.Context, deviceReason uint8, connectStatus voltha.ConnectStatus_Types) {
3738 if err := dh.deviceReasonUpdate(ctx, deviceReason, true); err != nil {
3739 logger.Errorw(ctx, "unable to update device reason to core",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003740 log.Fields{"device-id": dh.DeviceID, "Err": err})
Maninder7961d722021-06-16 22:10:28 +05303741 }
3742
3743 logger.Debugw(ctx, "Core DeviceStateUpdate", log.Fields{"connectStatus": connectStatus, "operState": voltha.OperStatus_RECONCILING_FAILED})
khenaidoo7d3c5582021-08-11 18:09:44 -04003744 if err := dh.updateDeviceStateInCore(ctx, &ic.DeviceStateFilter{
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003745 DeviceId: dh.DeviceID,
khenaidoo7d3c5582021-08-11 18:09:44 -04003746 ConnStatus: connectStatus,
3747 OperStatus: voltha.OperStatus_RECONCILING_FAILED,
3748 }); err != nil {
Maninder7961d722021-06-16 22:10:28 +05303749 logger.Errorw(ctx, "unable to update device state to core",
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003750 log.Fields{"device-id": dh.DeviceID, "Err": err})
Maninder7961d722021-06-16 22:10:28 +05303751 }
3752}
khenaidoo7d3c5582021-08-11 18:09:44 -04003753
3754/*
3755Helper functions to communicate with Core
3756*/
3757
3758func (dh *deviceHandler) getDeviceFromCore(ctx context.Context, deviceID string) (*voltha.Device, error) {
3759 cClient, err := dh.coreClient.GetCoreServiceClient()
3760 if err != nil || cClient == nil {
3761 return nil, err
3762 }
3763 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.RPCTimeout)
3764 defer cancel()
3765 logger.Debugw(subCtx, "get-device-from-core", log.Fields{"device-id": deviceID})
3766 return cClient.GetDevice(subCtx, &vc.ID{Id: deviceID})
3767}
3768
3769func (dh *deviceHandler) updateDeviceStateInCore(ctx context.Context, deviceStateFilter *ic.DeviceStateFilter) error {
3770 cClient, err := dh.coreClient.GetCoreServiceClient()
3771 if err != nil || cClient == nil {
3772 return err
3773 }
3774 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.RPCTimeout)
3775 defer cancel()
3776 _, err = cClient.DeviceStateUpdate(subCtx, deviceStateFilter)
3777 logger.Debugw(subCtx, "device-updated-in-core", log.Fields{"device-state": deviceStateFilter, "error": err})
3778 return err
3779}
3780
3781func (dh *deviceHandler) updatePMConfigInCore(ctx context.Context, pmConfigs *voltha.PmConfigs) error {
3782 cClient, err := dh.coreClient.GetCoreServiceClient()
3783 if err != nil || cClient == nil {
3784 return err
3785 }
3786 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.RPCTimeout)
3787 defer cancel()
3788 _, err = cClient.DevicePMConfigUpdate(subCtx, pmConfigs)
3789 logger.Debugw(subCtx, "pmconfig-updated-in-core", log.Fields{"pm-configs": pmConfigs, "error": err})
3790 return err
3791}
3792
3793func (dh *deviceHandler) updateDeviceInCore(ctx context.Context, device *voltha.Device) error {
3794 cClient, err := dh.coreClient.GetCoreServiceClient()
3795 if err != nil || cClient == nil {
3796 return err
3797 }
3798 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.RPCTimeout)
3799 defer cancel()
3800 _, err = cClient.DeviceUpdate(subCtx, device)
3801 logger.Debugw(subCtx, "device-updated-in-core", log.Fields{"device-id": device.Id, "error": err})
3802 return err
3803}
3804
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003805func (dh *deviceHandler) CreatePortInCore(ctx context.Context, port *voltha.Port) error {
khenaidoo7d3c5582021-08-11 18:09:44 -04003806 cClient, err := dh.coreClient.GetCoreServiceClient()
3807 if err != nil || cClient == nil {
3808 return err
3809 }
3810 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.RPCTimeout)
3811 defer cancel()
3812 _, err = cClient.PortCreated(subCtx, port)
3813 logger.Debugw(subCtx, "port-created-in-core", log.Fields{"port": port, "error": err})
3814 return err
3815}
3816
3817func (dh *deviceHandler) updatePortStateInCore(ctx context.Context, portState *ic.PortState) error {
3818 cClient, err := dh.coreClient.GetCoreServiceClient()
3819 if err != nil || cClient == nil {
3820 return err
3821 }
3822 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.RPCTimeout)
3823 defer cancel()
3824 _, err = cClient.PortStateUpdate(subCtx, portState)
3825 logger.Debugw(subCtx, "port-state-updated-in-core", log.Fields{"port-state": portState, "error": err})
3826 return err
3827}
3828
3829func (dh *deviceHandler) updateDeviceReasonInCore(ctx context.Context, reason *ic.DeviceReason) error {
3830 cClient, err := dh.coreClient.GetCoreServiceClient()
3831 if err != nil || cClient == nil {
3832 return err
3833 }
3834 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.RPCTimeout)
3835 defer cancel()
3836 _, err = cClient.DeviceReasonUpdate(subCtx, reason)
3837 logger.Debugw(subCtx, "device-reason-updated-in-core", log.Fields{"reason": reason, "error": err})
3838 return err
3839}
3840
3841/*
3842Helper functions to communicate with parent adapter
3843*/
3844
3845func (dh *deviceHandler) getTechProfileInstanceFromParentAdapter(ctx context.Context, parentEndpoint string,
3846 request *ic.TechProfileInstanceRequestMessage) (*ic.TechProfileDownloadMessage, error) {
3847 pgClient, err := dh.pOpenOnuAc.getParentAdapterServiceClient(parentEndpoint)
3848 if err != nil || pgClient == nil {
3849 return nil, err
3850 }
3851 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.MaxTimeoutInterAdapterComm)
3852 defer cancel()
3853 logger.Debugw(subCtx, "get-tech-profile-instance", log.Fields{"request": request, "parent-endpoint": parentEndpoint})
3854 return pgClient.GetTechProfileInstance(subCtx, request)
3855}
3856
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003857func (dh *deviceHandler) SendOMCIRequest(ctx context.Context, parentEndpoint string, request *ic.OmciMessage) error {
khenaidoo7d3c5582021-08-11 18:09:44 -04003858 pgClient, err := dh.pOpenOnuAc.getParentAdapterServiceClient(parentEndpoint)
3859 if err != nil || pgClient == nil {
3860 return err
3861 }
3862 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), dh.config.MaxTimeoutInterAdapterComm)
3863 defer cancel()
3864 logger.Debugw(subCtx, "send-omci-request", log.Fields{"request": request, "parent-endpoint": parentEndpoint})
3865 _, err = pgClient.ProxyOmciRequest(subCtx, request)
3866 if err != nil {
3867 logger.Errorw(ctx, "omci-failure", log.Fields{"request": request, "error": err, "request-parent": request.ParentDeviceId, "request-child": request.ChildDeviceId, "request-proxy": request.ProxyAddress})
3868 }
3869 return err
3870}
Holger Hildebrandt4b5e73f2021-08-19 06:51:21 +00003871
3872// GetDeviceID - TODO: add comment
3873func (dh *deviceHandler) GetDeviceID() string {
3874 return dh.DeviceID
3875}
3876
3877// GetProxyAddressID - TODO: add comment
3878func (dh *deviceHandler) GetProxyAddressID() string {
3879 return dh.device.ProxyAddress.GetDeviceId()
3880}
3881
3882// GetProxyAddressType - TODO: add comment
3883func (dh *deviceHandler) GetProxyAddressType() string {
3884 return dh.device.ProxyAddress.GetDeviceType()
3885}
3886
3887// GetProxyAddress - TODO: add comment
3888func (dh *deviceHandler) GetProxyAddress() *voltha.Device_ProxyAddress {
3889 return dh.device.ProxyAddress
3890}
3891
3892// GetEventProxy - TODO: add comment
3893func (dh *deviceHandler) GetEventProxy() eventif.EventProxy {
3894 return dh.EventProxy
3895}
3896
3897// GetOmciTimeout - TODO: add comment
3898func (dh *deviceHandler) GetOmciTimeout() int {
3899 return dh.pOpenOnuAc.omciTimeout
3900}
3901
3902// GetAlarmAuditInterval - TODO: add comment
3903func (dh *deviceHandler) GetAlarmAuditInterval() time.Duration {
3904 return dh.pOpenOnuAc.alarmAuditInterval
3905}
3906
3907// GetDlToOnuTimeout4M - TODO: add comment
3908func (dh *deviceHandler) GetDlToOnuTimeout4M() time.Duration {
3909 return dh.pOpenOnuAc.dlToOnuTimeout4M
3910}
3911
3912// GetUniEntityMap - TODO: add comment
3913func (dh *deviceHandler) GetUniEntityMap() *cmn.OnuUniPortMap {
3914 return &dh.uniEntityMap
3915}
3916
3917// GetPonPortNumber - TODO: add comment
3918func (dh *deviceHandler) GetPonPortNumber() *uint32 {
3919 return &dh.ponPortNumber
3920}
3921
3922// GetUniVlanConfigFsm - TODO: add comment
3923func (dh *deviceHandler) GetUniVlanConfigFsm(uniID uint8) cmn.IuniVlanConfigFsm {
3924 return dh.UniVlanConfigFsmMap[uniID]
3925}
3926
3927// GetOnuAlarmManager - TODO: add comment
3928func (dh *deviceHandler) GetOnuAlarmManager() cmn.IonuAlarmManager {
3929 return dh.pAlarmMgr
3930}
3931
3932// GetOnuMetricsManager - TODO: add comment
3933func (dh *deviceHandler) GetOnuMetricsManager() cmn.IonuMetricsManager {
3934 return dh.pOnuMetricsMgr
3935}
3936
3937// GetOnuTP - TODO: add comment
3938func (dh *deviceHandler) GetOnuTP() cmn.IonuUniTechProf {
3939 return dh.pOnuTP
3940}
3941
3942// GetBackendPathPrefix - TODO: add comment
3943func (dh *deviceHandler) GetBackendPathPrefix() string {
3944 return dh.pOpenOnuAc.cm.Backend.PathPrefix
3945}
3946
3947// GetOnuIndication - TODO: add comment
3948func (dh *deviceHandler) GetOnuIndication() *openolt.OnuIndication {
3949 return dh.pOnuIndication
3950}
3951
3952// RLockMutexDeletionInProgressFlag - TODO: add comment
3953func (dh *deviceHandler) RLockMutexDeletionInProgressFlag() {
3954 dh.mutexDeletionInProgressFlag.RLock()
3955}
3956
3957// RUnlockMutexDeletionInProgressFlag - TODO: add comment
3958func (dh *deviceHandler) RUnlockMutexDeletionInProgressFlag() {
3959 dh.mutexDeletionInProgressFlag.RUnlock()
3960}
3961
3962// GetDeletionInProgress - TODO: add comment
3963func (dh *deviceHandler) GetDeletionInProgress() bool {
3964 return dh.deletionInProgress
3965}
3966
3967// GetPmConfigs - TODO: add comment
3968func (dh *deviceHandler) GetPmConfigs() *voltha.PmConfigs {
3969 return dh.pmConfigs
3970}
3971
3972// GetDeviceType - TODO: add comment
3973func (dh *deviceHandler) GetDeviceType() string {
3974 return dh.DeviceType
3975}
3976
3977// GetLogicalDeviceID - TODO: add comment
3978func (dh *deviceHandler) GetLogicalDeviceID() string {
3979 return dh.logicalDeviceID
3980}
3981
3982// GetDevice - TODO: add comment
3983func (dh *deviceHandler) GetDevice() *voltha.Device {
3984 return dh.device
3985}
3986
3987// GetMetricsEnabled - TODO: add comment
3988func (dh *deviceHandler) GetMetricsEnabled() bool {
3989 return dh.pOpenOnuAc.MetricsEnabled
3990}
3991
3992// InitPmConfigs - TODO: add comment
3993func (dh *deviceHandler) InitPmConfigs() {
3994 dh.pmConfigs = &voltha.PmConfigs{}
3995}
3996
3997// GetUniPortMask - TODO: add comment
3998func (dh *deviceHandler) GetUniPortMask() int {
3999 return dh.pOpenOnuAc.config.UniPortMask
4000}