blob: f85d06dfd87377f814a68ecee4b0e49b92cedb6e [file] [log] [blame]
Girish Gowdru0c588b22019-04-23 23:24:56 -04001/*
Joey Armstrong11f5a572024-01-12 19:11:32 -05002 * Copyright 2018-2024 Open Networking Foundation (ONF) and the ONF Contributors
Girish Gowdru0c588b22019-04-23 23:24:56 -04003
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7
8 * http://www.apache.org/licenses/LICENSE-2.0
9
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
Girish Gowdru6a80bbd2019-07-02 07:36:09 -070016
praneeth nalmas55616d62023-02-06 09:19:18 +053017// Package core provides the utility for olt devices, flows and statistics
Scott Bakerdbd960e2020-02-28 08:57:51 -080018package core
Girish Gowdru0c588b22019-04-23 23:24:56 -040019
20import (
21 "context"
khenaidooefff76e2021-12-15 16:51:30 -050022 "fmt"
Akash Sonif49299a2024-04-25 12:06:37 +053023 "sync"
24 "time"
25
khenaidoo106c61a2021-08-11 18:05:46 -040026 conf "github.com/opencord/voltha-lib-go/v7/pkg/config"
Abhay Kumarad506952026-05-08 10:29:15 +000027 "github.com/opencord/voltha-lib-go/v7/pkg/db"
khenaidoo106c61a2021-08-11 18:05:46 -040028 "github.com/opencord/voltha-lib-go/v7/pkg/events/eventif"
29 vgrpc "github.com/opencord/voltha-lib-go/v7/pkg/grpc"
30 "github.com/opencord/voltha-lib-go/v7/pkg/log"
Scott Bakerdbd960e2020-02-28 08:57:51 -080031 "github.com/opencord/voltha-openolt-adapter/internal/pkg/config"
Thomas Lee S94109f12020-03-03 16:39:29 +053032 "github.com/opencord/voltha-openolt-adapter/internal/pkg/olterrors"
Abhay Kumarad506952026-05-08 10:29:15 +000033 rsrcMgr "github.com/opencord/voltha-openolt-adapter/internal/pkg/resourcemanager"
khenaidooefff76e2021-12-15 16:51:30 -050034 "github.com/opencord/voltha-protos/v5/go/adapter_service"
khenaidoo106c61a2021-08-11 18:05:46 -040035 "github.com/opencord/voltha-protos/v5/go/common"
khenaidoodc2116e2021-10-19 17:33:19 -040036 ca "github.com/opencord/voltha-protos/v5/go/core_adapter"
khenaidoo106c61a2021-08-11 18:05:46 -040037 "github.com/opencord/voltha-protos/v5/go/extension"
khenaidoodc2116e2021-10-19 17:33:19 -040038 "github.com/opencord/voltha-protos/v5/go/health"
39 ia "github.com/opencord/voltha-protos/v5/go/inter_adapter"
40 "github.com/opencord/voltha-protos/v5/go/omci"
khenaidoo106c61a2021-08-11 18:05:46 -040041 "github.com/opencord/voltha-protos/v5/go/voltha"
nikesh.krishnan4d644532023-12-16 00:21:07 +053042 "google.golang.org/grpc/codes"
43 "google.golang.org/grpc/status"
bseeniva0b9cbcb2026-02-12 19:11:11 +053044 "google.golang.org/protobuf/types/known/emptypb"
Girish Gowdru0c588b22019-04-23 23:24:56 -040045)
46
praneeth nalmas55616d62023-02-06 09:19:18 +053047// OpenOLT structure holds the OLT information
Girish Gowdru0c588b22019-04-23 23:24:56 -040048type OpenOLT struct {
bseeniva0b9cbcb2026-02-12 19:11:11 +053049 adapter_service.UnimplementedAdapterServiceServer
Akash Kankanala041a2122024-10-16 15:49:22 +053050 eventProxy eventif.EventProxy
Abhilash Laxmeshward0f58cf2022-06-01 12:15:19 +053051 configManager *conf.ConfigManager
52 deviceHandlers map[string]*DeviceHandler
53 coreClient *vgrpc.Client
Abhilash Laxmeshward0f58cf2022-06-01 12:15:19 +053054 config *config.AdapterFlags
Akash Kankanala041a2122024-10-16 15:49:22 +053055 exitChannel chan struct{}
Abhilash Laxmeshward0f58cf2022-06-01 12:15:19 +053056 KVStoreAddress string
57 KVStoreType string
Akash Kankanala041a2122024-10-16 15:49:22 +053058 numOnus int
Abhilash Laxmeshward0f58cf2022-06-01 12:15:19 +053059 HeartbeatCheckInterval time.Duration
60 HeartbeatFailReportInterval time.Duration
61 GrpcTimeoutInterval time.Duration
Akash Kankanala041a2122024-10-16 15:49:22 +053062 rpcTimeout time.Duration
Abhilash Laxmeshward0f58cf2022-06-01 12:15:19 +053063 lockDeviceHandlersMap sync.RWMutex
64 enableONUStats bool
65 enableGemStats bool
Abhilash Laxmeshward0f58cf2022-06-01 12:15:19 +053066 CheckOnuDevExistenceAtOnuDiscovery bool
Sridhar Ravindraab785f22025-07-21 17:20:55 +053067 ForceOnuDiscIndProcessing bool
Abhay Kumarad506952026-05-08 10:29:15 +000068 PonRsrcMgr *db.Backend
69 PonRsrcMgrTech *db.Backend
70 TpDefault *db.Backend
71 Tprofiles *db.Backend
72 TpInstances *db.Backend
Girish Gowdru0c588b22019-04-23 23:24:56 -040073}
74
praneeth nalmas55616d62023-02-06 09:19:18 +053075// NewOpenOLT returns a new instance of OpenOLT
khenaidoo106c61a2021-08-11 18:05:46 -040076func NewOpenOLT(ctx context.Context,
77 coreClient *vgrpc.Client,
Himani Chawlacd407802020-12-10 12:08:59 +053078 eventProxy eventif.EventProxy, cfg *config.AdapterFlags, cm *conf.ConfigManager) *OpenOLT {
Girish Gowdru0c588b22019-04-23 23:24:56 -040079 var openOLT OpenOLT
khenaidooefff76e2021-12-15 16:51:30 -050080 openOLT.exitChannel = make(chan struct{})
Girish Gowdru0c588b22019-04-23 23:24:56 -040081 openOLT.deviceHandlers = make(map[string]*DeviceHandler)
Abhilash Laxmeshwarf9942e92020-01-07 15:32:44 +053082 openOLT.config = cfg
83 openOLT.numOnus = cfg.OnuNumber
khenaidoo106c61a2021-08-11 18:05:46 -040084 openOLT.coreClient = coreClient
Devmalya Paulfb990a52019-07-09 10:01:49 -040085 openOLT.eventProxy = eventProxy
Neha Sharma3f221ae2020-04-29 19:02:12 +000086 openOLT.KVStoreAddress = cfg.KVStoreAddress
Abhilash Laxmeshwarf9942e92020-01-07 15:32:44 +053087 openOLT.KVStoreType = cfg.KVStoreType
88 openOLT.HeartbeatCheckInterval = cfg.HeartbeatCheckInterval
89 openOLT.HeartbeatFailReportInterval = cfg.HeartbeatFailReportInterval
90 openOLT.GrpcTimeoutInterval = cfg.GrpcTimeoutInterval
Girish Gowdru0c588b22019-04-23 23:24:56 -040091 openOLT.lockDeviceHandlersMap = sync.RWMutex{}
Matteo Scandolodfa7a972020-11-06 13:03:40 -080092 openOLT.configManager = cm
Gamze Abakafcbd6e72020-12-17 13:25:16 +000093 openOLT.enableONUStats = cfg.EnableONUStats
94 openOLT.enableGemStats = cfg.EnableGEMStats
khenaidoo106c61a2021-08-11 18:05:46 -040095 openOLT.rpcTimeout = cfg.RPCTimeout
Abhilash Laxmeshward0f58cf2022-06-01 12:15:19 +053096 openOLT.CheckOnuDevExistenceAtOnuDiscovery = cfg.CheckOnuDevExistenceAtOnuDiscovery
Sridhar Ravindraab785f22025-07-21 17:20:55 +053097 openOLT.ForceOnuDiscIndProcessing = cfg.ForceOnuDiscIndProcessing
Abhay Kumarad506952026-05-08 10:29:15 +000098 logger.Infow(ctx, "cm-backend-prefix", log.Fields{"prefix": cm.Backend.PathPrefix})
99 // kvStore backends for resource manager and technology profiles. These are used by the device handlers to store the allocated resources and other relevant information.
100 openOLT.PonRsrcMgr = db.NewBackend(ctx, cfg.KVStoreType, cfg.KVStoreAddress, rsrcMgr.KvstoreTimeout, cm.Backend.PathPrefix+"/resource_manager")
101 openOLT.PonRsrcMgrTech = db.NewBackend(ctx, cfg.KVStoreType, cfg.KVStoreAddress, rsrcMgr.KvstoreTimeout, cm.Backend.PathPrefix+"/resource_manager/config")
102 openOLT.TpDefault = db.NewBackend(ctx, cfg.KVStoreType, cfg.KVStoreAddress, rsrcMgr.KvstoreTimeout, cm.Backend.PathPrefix+"/technology_profiles")
103 // Tprofiles uses a fixed global path because tech-profile definitions are shared across all VOLTHA stacks.
104 openOLT.Tprofiles = db.NewBackend(ctx, cfg.KVStoreType, cfg.KVStoreAddress, rsrcMgr.KvstoreTimeout, "service/voltha/technology_profiles")
105 openOLT.TpInstances = db.NewBackend(ctx, cfg.KVStoreType, cfg.KVStoreAddress, rsrcMgr.KvstoreTimeout, cm.Backend.PathPrefix+"/resource_instances")
106
Girish Gowdru0c588b22019-04-23 23:24:56 -0400107 return &openOLT
108}
109
praneeth nalmas55616d62023-02-06 09:19:18 +0530110// Start starts (logs) the device manager
Girish Gowdru0c588b22019-04-23 23:24:56 -0400111func (oo *OpenOLT) Start(ctx context.Context) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000112 logger.Info(ctx, "starting-device-manager")
113 logger.Info(ctx, "device-manager-started")
Girish Gowdru0c588b22019-04-23 23:24:56 -0400114 return nil
115}
116
praneeth nalmas55616d62023-02-06 09:19:18 +0530117// Stop terminates the session
Girish Gowdru0c588b22019-04-23 23:24:56 -0400118func (oo *OpenOLT) Stop(ctx context.Context) error {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000119 logger.Info(ctx, "stopping-device-manager")
khenaidooefff76e2021-12-15 16:51:30 -0500120 close(oo.exitChannel)
121 // Stop the device handlers
122 oo.stopAllDeviceHandlers(ctx)
123
Abhay Kumarad506952026-05-08 10:29:15 +0000124 // Close shared KV store backends and nil out clients to prevent double-close from downstream CloseKVClient calls.
125 for _, backend := range []*db.Backend{oo.PonRsrcMgr, oo.PonRsrcMgrTech, oo.TpDefault, oo.Tprofiles, oo.TpInstances} {
126 if backend != nil && backend.Client != nil {
127 backend.Client.Close(ctx)
128 backend.Client = nil
129 }
130 }
131
khenaidooefff76e2021-12-15 16:51:30 -0500132 // Stop the core grpc client connection
133 if oo.coreClient != nil {
134 oo.coreClient.Stop(ctx)
135 }
136
Neha Sharma96b7bf22020-06-15 10:37:32 +0000137 logger.Info(ctx, "device-manager-stopped")
Girish Gowdru0c588b22019-04-23 23:24:56 -0400138 return nil
139}
140
Girish Gowdru0c588b22019-04-23 23:24:56 -0400141func (oo *OpenOLT) addDeviceHandlerToMap(agent *DeviceHandler) {
142 oo.lockDeviceHandlersMap.Lock()
143 defer oo.lockDeviceHandlersMap.Unlock()
Thomas Lee S985938d2020-05-04 11:40:41 +0530144 if _, exist := oo.deviceHandlers[agent.device.Id]; !exist {
145 oo.deviceHandlers[agent.device.Id] = agent
Girish Gowdru0c588b22019-04-23 23:24:56 -0400146 }
147}
148
149func (oo *OpenOLT) deleteDeviceHandlerToMap(agent *DeviceHandler) {
150 oo.lockDeviceHandlersMap.Lock()
151 defer oo.lockDeviceHandlersMap.Unlock()
Thomas Lee S985938d2020-05-04 11:40:41 +0530152 delete(oo.deviceHandlers, agent.device.Id)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400153}
154
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700155func (oo *OpenOLT) getDeviceHandler(deviceID string) *DeviceHandler {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400156 oo.lockDeviceHandlersMap.Lock()
157 defer oo.lockDeviceHandlersMap.Unlock()
Girish Gowdru6a80bbd2019-07-02 07:36:09 -0700158 if agent, ok := oo.deviceHandlers[deviceID]; ok {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400159 return agent
160 }
161 return nil
162}
163
khenaidooefff76e2021-12-15 16:51:30 -0500164func (oo *OpenOLT) stopAllDeviceHandlers(ctx context.Context) {
165 oo.lockDeviceHandlersMap.Lock()
166 defer oo.lockDeviceHandlersMap.Unlock()
167 for _, handler := range oo.deviceHandlers {
168 handler.Stop(ctx)
169 }
khenaidoo106c61a2021-08-11 18:05:46 -0400170}
171
172// AdoptDevice creates a new device handler if not present already and then adopts the device
bseeniva0b9cbcb2026-02-12 19:11:11 +0530173func (oo *OpenOLT) AdoptDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
Girish Gowdru0c588b22019-04-23 23:24:56 -0400174 if device == nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400175 return nil, olterrors.NewErrInvalidValue(log.Fields{"device": nil}, nil).Log()
Girish Gowdru0c588b22019-04-23 23:24:56 -0400176 }
divyadesai3af43e12020-08-18 07:10:54 +0000177 logger.Infow(ctx, "adopt-device", log.Fields{"device-id": device.Id})
Girish Gowdru0c588b22019-04-23 23:24:56 -0400178 var handler *DeviceHandler
179 if handler = oo.getDeviceHandler(device.Id); handler == nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400180 handler := NewDeviceHandler(oo.coreClient, oo.eventProxy, device, oo, oo.configManager, oo.config)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400181 oo.addDeviceHandlerToMap(handler)
khenaidoo106c61a2021-08-11 18:05:46 -0400182 go handler.AdoptDevice(log.WithSpanFromContext(context.Background(), ctx), device)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400183 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530184 return &emptypb.Empty{}, nil
Girish Gowdru0c588b22019-04-23 23:24:56 -0400185}
186
praneeth nalmas55616d62023-02-06 09:19:18 +0530187// GetOfpDeviceInfo returns OFP information for the given device
khenaidoodc2116e2021-10-19 17:33:19 -0400188func (oo *OpenOLT) GetOfpDeviceInfo(ctx context.Context, device *voltha.Device) (*ca.SwitchCapability, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400189 logger.Infow(ctx, "get_ofp_device_info", log.Fields{"device-id": device.Id})
Girish Gowdru0c588b22019-04-23 23:24:56 -0400190 if handler := oo.getDeviceHandler(device.Id); handler != nil {
191 return handler.GetOfpDeviceInfo(device)
192 }
Girish Kumarf26e4882020-03-05 06:49:10 +0000193 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": device.Id}, nil)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400194}
195
praneeth nalmas55616d62023-02-06 09:19:18 +0530196// ReconcileDevice unimplemented
bseeniva0b9cbcb2026-02-12 19:11:11 +0530197func (oo *OpenOLT) ReconcileDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530198 if device == nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400199 return nil, olterrors.NewErrInvalidValue(log.Fields{"device": nil}, nil)
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530200 }
divyadesai3af43e12020-08-18 07:10:54 +0000201 logger.Infow(ctx, "reconcile-device", log.Fields{"device-id": device.Id})
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530202 var handler *DeviceHandler
Akash Reddy Kankanala78b627f2026-01-12 08:18:21 +0000203 var dhCtx context.Context
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530204 if handler = oo.getDeviceHandler(device.Id); handler == nil {
Manindere49938d2021-03-19 00:23:24 +0530205 //Setting state to RECONCILING
Nandita Biradar1b590f12024-09-27 10:56:28 +0530206 // Fetch previous state
207 //here we are fetching the previous operation states of the device,so to check which operation state it was previously for proper transition and proper clean up of the resources.
208 PrevOperStatus := device.OperStatus
209
210 // Log previous state
211 logger.Infow(ctx, "previous-device-state", log.Fields{
212 "device-id": device.Id,
213 "previous-operStatus": PrevOperStatus,
214 "Device-connStatus": device.ConnectStatus,
215 })
khenaidoo106c61a2021-08-11 18:05:46 -0400216 cgClient, err := oo.coreClient.GetCoreServiceClient()
Manindere49938d2021-03-19 00:23:24 +0530217 if err != nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400218 return nil, err
Manindere49938d2021-03-19 00:23:24 +0530219 }
khenaidoo106c61a2021-08-11 18:05:46 -0400220 subCtx, cancel := context.WithTimeout(log.WithSpanFromContext(context.Background(), ctx), oo.rpcTimeout)
221 defer cancel()
Nandita Biradar1b590f12024-09-27 10:56:28 +0530222 // Create DeviceStateFilter with new state
223 deviceStateFilter := &ca.DeviceStateFilter{
224 DeviceId: device.Id,
225 OperStatus: voltha.OperStatus_RECONCILING,
226 ConnStatus: device.ConnectStatus,
227 }
228
229 // Log the new state being set
230 logger.Infow(ctx, "setting-new-device-state", log.Fields{
231 "device-id": deviceStateFilter.DeviceId,
232 "new-operStatus": deviceStateFilter.OperStatus,
233 "new-connStatus": deviceStateFilter.ConnStatus,
234 })
khenaidoodc2116e2021-10-19 17:33:19 -0400235 if _, err := cgClient.DeviceStateUpdate(subCtx, &ca.DeviceStateFilter{
khenaidoo106c61a2021-08-11 18:05:46 -0400236 DeviceId: device.Id,
237 OperStatus: voltha.OperStatus_RECONCILING,
Akash Sonif49299a2024-04-25 12:06:37 +0530238 ConnStatus: voltha.ConnectStatus_UNREACHABLE,
khenaidoo106c61a2021-08-11 18:05:46 -0400239 }); err != nil {
240 return nil, olterrors.NewErrAdapter("device-update-failed", log.Fields{"device-id": device.Id}, err)
241 }
242
Akash Sonif49299a2024-04-25 12:06:37 +0530243 // The OperState and connection state of the device is set to RECONCILING and UNREACHABLE in the previous section. This also needs to be set on the
Girish Gowdra0fb24a32021-10-27 15:15:27 -0700244 // locally cached copy of the device struct.
245 device.OperStatus = voltha.OperStatus_RECONCILING
Akash Sonif49299a2024-04-25 12:06:37 +0530246 device.ConnectStatus = voltha.ConnectStatus_UNREACHABLE
Girish Gowdra0fb24a32021-10-27 15:15:27 -0700247 handler := NewDeviceHandler(oo.coreClient, oo.eventProxy, device, oo, oo.configManager, oo.config)
248 handler.adapterPreviouslyConnected = true
Nandita Biradar1b590f12024-09-27 10:56:28 +0530249 handler.prevOperStatus = PrevOperStatus
Girish Gowdra0fb24a32021-10-27 15:15:27 -0700250 oo.addDeviceHandlerToMap(handler)
251 handler.transitionMap = NewTransitionMap(handler)
252
Akash Reddy Kankanala78b627f2026-01-12 08:18:21 +0000253 dhCtx, handler.transitionHandlerCancel = context.WithCancel(log.WithSpanFromContext(context.Background(), ctx))
254 go handler.transitionMap.Handle(dhCtx, DeviceInit)
nikesh.krishnan4d644532023-12-16 00:21:07 +0530255 } else {
256 logger.Warnf(ctx, "device-already-reconciled-or-active", log.Fields{"device-id": device.Id})
bseeniva0b9cbcb2026-02-12 19:11:11 +0530257 return &emptypb.Empty{}, status.Errorf(codes.AlreadyExists, "handler exists: %s", device.Id)
Abhilash Laxmeshwarab0bd522019-10-21 15:05:15 +0530258 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530259 return &emptypb.Empty{}, nil
Girish Gowdru0c588b22019-04-23 23:24:56 -0400260}
261
praneeth nalmas55616d62023-02-06 09:19:18 +0530262// DisableDevice disables the given device
bseeniva0b9cbcb2026-02-12 19:11:11 +0530263func (oo *OpenOLT) DisableDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
divyadesai3af43e12020-08-18 07:10:54 +0000264 logger.Infow(ctx, "disable-device", log.Fields{"device-id": device.Id})
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400265 if handler := oo.getDeviceHandler(device.Id); handler != nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400266 if err := handler.DisableDevice(log.WithSpanFromContext(context.Background(), ctx), device); err != nil {
267 return nil, err
268 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530269 return &emptypb.Empty{}, nil
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400270 }
khenaidoo106c61a2021-08-11 18:05:46 -0400271 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": device.Id}, nil)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400272}
273
praneeth nalmas55616d62023-02-06 09:19:18 +0530274// ReEnableDevice enables the olt device after disable
bseeniva0b9cbcb2026-02-12 19:11:11 +0530275func (oo *OpenOLT) ReEnableDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
divyadesai3af43e12020-08-18 07:10:54 +0000276 logger.Infow(ctx, "reenable-device", log.Fields{"device-id": device.Id})
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400277 if handler := oo.getDeviceHandler(device.Id); handler != nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400278 if err := handler.ReenableDevice(log.WithSpanFromContext(context.Background(), ctx), device); err != nil {
279 return nil, err
280 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530281 return &emptypb.Empty{}, nil
Girish Gowdru5ba46c92019-04-25 05:00:05 -0400282 }
khenaidoo106c61a2021-08-11 18:05:46 -0400283 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": device.Id}, nil)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400284}
285
praneeth nalmas55616d62023-02-06 09:19:18 +0530286// RebootDevice reboots the given device
bseeniva0b9cbcb2026-02-12 19:11:11 +0530287func (oo *OpenOLT) RebootDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
divyadesai3af43e12020-08-18 07:10:54 +0000288 logger.Infow(ctx, "reboot-device", log.Fields{"device-id": device.Id})
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400289 if handler := oo.getDeviceHandler(device.Id); handler != nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400290 if err := handler.RebootDevice(log.WithSpanFromContext(context.Background(), ctx), device); err != nil {
291 return nil, err
292 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530293 return &emptypb.Empty{}, nil
Girish Gowdru0fe5f7e2019-05-28 05:12:27 -0400294 }
khenaidoo106c61a2021-08-11 18:05:46 -0400295 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": device.Id}, nil)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400296}
297
praneeth nalmas55616d62023-02-06 09:19:18 +0530298// DeleteDevice deletes a device
bseeniva0b9cbcb2026-02-12 19:11:11 +0530299func (oo *OpenOLT) DeleteDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
divyadesai3af43e12020-08-18 07:10:54 +0000300 logger.Infow(ctx, "delete-device", log.Fields{"device-id": device.Id})
Devmalya Paul495b94a2019-08-27 19:42:00 -0400301 if handler := oo.getDeviceHandler(device.Id); handler != nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400302 if err := handler.DeleteDevice(log.WithSpanFromContext(context.Background(), ctx), device); err != nil {
Gustavo Silva41af9122022-10-11 11:05:13 -0300303 return nil, err
Devmalya Paul495b94a2019-08-27 19:42:00 -0400304 }
Akash Soni5c76e272024-01-15 04:09:24 +0530305 // Initialize a ticker with a 2-second interval to periodically check the states
306 ticker := time.NewTicker(2 * time.Second)
307 defer ticker.Stop()
308
309 // Set a maximum timeout duration of 30 seconds for the loop
310 timeout := time.After(30 * time.Second)
311
312 for {
313 select {
314 case <-ticker.C:
315 // Check if all processes have stopped
316 if !handler.isHeartbeatCheckActive && !handler.isCollectorActive && !handler.isReadIndicationRoutineActive {
317 logger.Debugf(ctx, "delete-device-handler")
318 oo.deleteDeviceHandlerToMap(handler)
bseeniva0b9cbcb2026-02-12 19:11:11 +0530319 return &emptypb.Empty{}, nil
Akash Soni5c76e272024-01-15 04:09:24 +0530320 }
321 case <-timeout:
322 // Timeout exceeded
323 logger.Warnw(ctx, "delete-device-handler timeout exceeded", log.Fields{"device-id": device.Id})
324 oo.deleteDeviceHandlerToMap(handler) // Clean up anyway
bseeniva0b9cbcb2026-02-12 19:11:11 +0530325 return &emptypb.Empty{}, nil
Akash Soni5c76e272024-01-15 04:09:24 +0530326 }
327 }
Devmalya Paul495b94a2019-08-27 19:42:00 -0400328 }
khenaidoo106c61a2021-08-11 18:05:46 -0400329 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": device.Id}, nil)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400330}
331
praneeth nalmas55616d62023-02-06 09:19:18 +0530332// UpdateFlowsIncrementally updates (add/remove) the flows on a given device
bseeniva0b9cbcb2026-02-12 19:11:11 +0530333func (oo *OpenOLT) UpdateFlowsIncrementally(ctx context.Context, incrFlows *ca.IncrementalFlows) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400334 logger.Infow(ctx, "update_flows_incrementally", log.Fields{"device-id": incrFlows.Device.Id, "flows": incrFlows.Flows, "flowMetadata": incrFlows.FlowMetadata})
335 if handler := oo.getDeviceHandler(incrFlows.Device.Id); handler != nil {
336 if err := handler.UpdateFlowsIncrementally(log.WithSpanFromContext(context.Background(), ctx), incrFlows.Device, incrFlows.Flows, incrFlows.Groups, incrFlows.FlowMetadata); err != nil {
337 return nil, err
338 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530339 return &emptypb.Empty{}, nil
Girish Gowdru0c588b22019-04-23 23:24:56 -0400340 }
khenaidoo106c61a2021-08-11 18:05:46 -0400341 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": incrFlows.Device.Id}, nil)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400342}
343
praneeth nalmas55616d62023-02-06 09:19:18 +0530344// UpdatePmConfig returns PmConfigs nil or error
bseeniva0b9cbcb2026-02-12 19:11:11 +0530345func (oo *OpenOLT) UpdatePmConfig(ctx context.Context, configs *ca.PmConfigsInfo) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400346 logger.Debugw(ctx, "update_pm_config", log.Fields{"device-id": configs.DeviceId, "pm-configs": configs.PmConfigs})
347 if handler := oo.getDeviceHandler(configs.DeviceId); handler != nil {
348 handler.UpdatePmConfig(log.WithSpanFromContext(context.Background(), ctx), configs.PmConfigs)
bseeniva0b9cbcb2026-02-12 19:11:11 +0530349 return &emptypb.Empty{}, nil
Rohan Agrawalda5e0b22020-05-20 11:10:26 +0000350 }
khenaidoo106c61a2021-08-11 18:05:46 -0400351 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": configs.DeviceId}, nil)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400352}
353
praneeth nalmas55616d62023-02-06 09:19:18 +0530354// SendPacketOut sends packet out to the device
bseeniva0b9cbcb2026-02-12 19:11:11 +0530355func (oo *OpenOLT) SendPacketOut(ctx context.Context, packet *ca.PacketOut) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400356 logger.Debugw(ctx, "send_packet_out", log.Fields{"device-id": packet.DeviceId, "egress_port_no": packet.EgressPortNo, "pkt": packet.Packet})
357 if handler := oo.getDeviceHandler(packet.DeviceId); handler != nil {
358 if err := handler.PacketOut(log.WithSpanFromContext(context.Background(), ctx), packet.EgressPortNo, packet.Packet); err != nil {
359 return nil, err
360 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530361 return &emptypb.Empty{}, nil
manikkaraj k9eb6cac2019-05-09 12:32:03 -0400362 }
khenaidoo106c61a2021-08-11 18:05:46 -0400363 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": packet.DeviceId}, nil)
Girish Gowdru0c588b22019-04-23 23:24:56 -0400364}
365
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530366// EnableOnuSerialNumber to Enable onu serial number
bseeniva0b9cbcb2026-02-12 19:11:11 +0530367func (oo *OpenOLT) EnableOnuSerialNumber(ctx context.Context, device *voltha.OnuSerialNumberOnOLTPon) (*emptypb.Empty, error) {
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530368 logger.Infow(ctx, "enable_onu_serial_number", log.Fields{"olt_device_id": device.OltDeviceId, "onu_serial_number": device.SerialNumber})
369 if err := oo.enableDisableOnuSerialNumber(log.WithSpanFromContext(context.Background(), ctx), device, true); err != nil {
370 return nil, err
371 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530372 return &emptypb.Empty{}, nil
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530373}
374
375// DisableOnuSerialNumber to Disable onu serial number
bseeniva0b9cbcb2026-02-12 19:11:11 +0530376func (oo *OpenOLT) DisableOnuSerialNumber(ctx context.Context, device *voltha.OnuSerialNumberOnOLTPon) (*emptypb.Empty, error) {
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530377 logger.Infow(ctx, "disable_onu_serial_number", log.Fields{"olt_device_id": device.OltDeviceId, "onu_serial_number": device.SerialNumber})
378 if err := oo.enableDisableOnuSerialNumber(log.WithSpanFromContext(context.Background(), ctx), device, false); err != nil {
379 return nil, err
380 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530381 return &emptypb.Empty{}, nil
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530382}
383
384// enableDisableOnuSerialNumber to Disable onu or Enable onu
385func (oo *OpenOLT) enableDisableOnuSerialNumber(ctx context.Context, device *voltha.OnuSerialNumberOnOLTPon, enable bool) error {
386 if device.OltDeviceId == nil {
387 return olterrors.NewErrInvalidValue(log.Fields{
388 "reason": "olt device id is required",
389 }, nil)
390 }
391 if device.SerialNumber == "" {
392 return olterrors.NewErrInvalidValue(log.Fields{
393 "reason": "onu_serial_number cannot be empty",
394 }, nil)
395 }
396 if device.Port == nil {
397 return olterrors.NewErrInvalidValue(log.Fields{
398 "reason": "pon port cannot be empty",
399 }, nil)
400 }
401 if handler := oo.getDeviceHandler(device.OltDeviceId.Id); handler != nil {
402 if enable {
403 if err := handler.EnableOnuSerialNumber(ctx, device); err != nil {
404 return olterrors.NewErrAdapter("error-occurred-during-enable-onu-serial-number", log.Fields{"device-id": device.OltDeviceId.Id, "sn": device.SerialNumber}, err)
405 }
406 } else {
407 if err := handler.DisableOnuSerialNumber(ctx, device); err != nil {
408 return olterrors.NewErrAdapter("error-occurred-during-disable-onu-serial-number", log.Fields{"device-id": device.OltDeviceId.Id, "sn": device.SerialNumber}, err)
409 }
410 }
411 return nil
412 }
413 return olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": device.OltDeviceId.Id}, nil)
414}
415
416// EnableOnuDevice to Enable onu
bseeniva0b9cbcb2026-02-12 19:11:11 +0530417func (oo *OpenOLT) EnableOnuDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530418 logger.Infow(ctx, "enable_onu", log.Fields{"onu_device_id": device.Id, "onu_serial_number": device.SerialNumber})
419 if err := oo.enableDisableOnuDevice(log.WithSpanFromContext(context.Background(), ctx), device, true); err != nil {
420 return nil, err
421 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530422 return &emptypb.Empty{}, nil
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530423}
424
425// DisableOnuDevice to Disable onu
bseeniva0b9cbcb2026-02-12 19:11:11 +0530426func (oo *OpenOLT) DisableOnuDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530427 logger.Infow(ctx, "disable_onu", log.Fields{"onu_device_id": device.Id, "onu_serial_number": device.SerialNumber})
428 if err := oo.enableDisableOnuDevice(log.WithSpanFromContext(context.Background(), ctx), device, false); err != nil {
429 return nil, err
430 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530431 return &emptypb.Empty{}, nil
balaji.nagarajan68f56e82025-07-04 15:16:01 +0530432}
433
434// enableDisableOnuDevice to Disable onu or Enable onu
435func (oo *OpenOLT) enableDisableOnuDevice(ctx context.Context, device *voltha.Device, enable bool) error {
436 if device.ParentId == "" {
437 return olterrors.NewErrInvalidValue(log.Fields{
438 "reason": "olt device id is required",
439 }, nil)
440 }
441 if device.SerialNumber == "" {
442 return olterrors.NewErrInvalidValue(log.Fields{
443 "reason": "onu_serial_number cannot be empty",
444 }, nil)
445 }
446 if handler := oo.getDeviceHandler(device.ParentId); handler != nil {
447 if enable {
448 if err := handler.EnableOnu(ctx, device); err != nil {
449 return olterrors.NewErrAdapter("error-occurred-during-enable-onu", log.Fields{"device-id": device.ParentId, "sn": device.SerialNumber}, err)
450 }
451 } else {
452 if err := handler.DisableOnu(ctx, device); err != nil {
453 return olterrors.NewErrAdapter("error-occurred-during-disable-onu", log.Fields{"device-id": device.ParentId, "sn": device.SerialNumber}, err)
454 }
455 }
456 return nil
457 }
458 return olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": device.ParentId}, nil)
459}
460
khenaidoo106c61a2021-08-11 18:05:46 -0400461// EnablePort to Enable PON/NNI interface
bseeniva0b9cbcb2026-02-12 19:11:11 +0530462func (oo *OpenOLT) EnablePort(ctx context.Context, port *voltha.Port) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400463 logger.Infow(ctx, "enable_port", log.Fields{"device-id": port.DeviceId, "port": port})
464 if err := oo.enableDisablePort(log.WithSpanFromContext(context.Background(), ctx), port.DeviceId, port, true); err != nil {
465 return nil, err
466 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530467 return &emptypb.Empty{}, nil
Girish Gowdru0c588b22019-04-23 23:24:56 -0400468}
469
khenaidoo106c61a2021-08-11 18:05:46 -0400470// DisablePort to Disable pon/nni interface
bseeniva0b9cbcb2026-02-12 19:11:11 +0530471func (oo *OpenOLT) DisablePort(ctx context.Context, port *voltha.Port) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400472 logger.Infow(ctx, "disable_port", log.Fields{"device-id": port.DeviceId, "port": port})
473 if err := oo.enableDisablePort(log.WithSpanFromContext(context.Background(), ctx), port.DeviceId, port, false); err != nil {
474 return nil, err
475 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530476 return &emptypb.Empty{}, nil
kesavand39e0aa32020-01-28 20:58:50 -0500477}
478
479// enableDisablePort to Disable pon or Enable PON interface
Neha Sharma96b7bf22020-06-15 10:37:32 +0000480func (oo *OpenOLT) enableDisablePort(ctx context.Context, deviceID string, port *voltha.Port, enablePort bool) error {
divyadesai3af43e12020-08-18 07:10:54 +0000481 logger.Infow(ctx, "enableDisablePort", log.Fields{"device-id": deviceID, "port": port})
kesavand39e0aa32020-01-28 20:58:50 -0500482 if port == nil {
Thomas Lee S94109f12020-03-03 16:39:29 +0530483 return olterrors.NewErrInvalidValue(log.Fields{
David K. Bainbridge794735f2020-02-11 21:01:37 -0800484 "reason": "port cannot be nil",
485 "device-id": deviceID,
Girish Kumarf26e4882020-03-05 06:49:10 +0000486 "port": nil}, nil)
kesavand39e0aa32020-01-28 20:58:50 -0500487 }
488 if handler := oo.getDeviceHandler(deviceID); handler != nil {
divyadesai3af43e12020-08-18 07:10:54 +0000489 logger.Debugw(ctx, "Enable_Disable_Port", log.Fields{"device-id": deviceID, "port": port})
kesavand39e0aa32020-01-28 20:58:50 -0500490 if enablePort {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000491 if err := handler.EnablePort(ctx, port); err != nil {
divyadesai3af43e12020-08-18 07:10:54 +0000492 return olterrors.NewErrAdapter("error-occurred-during-enable-port", log.Fields{"device-id": deviceID, "port": port}, err)
kesavand39e0aa32020-01-28 20:58:50 -0500493 }
494 } else {
Neha Sharma96b7bf22020-06-15 10:37:32 +0000495 if err := handler.DisablePort(ctx, port); err != nil {
divyadesai3af43e12020-08-18 07:10:54 +0000496 return olterrors.NewErrAdapter("error-occurred-during-disable-port", log.Fields{"device-id": deviceID, "port": port}, err)
kesavand39e0aa32020-01-28 20:58:50 -0500497 }
498 }
499 }
500 return nil
501}
Chaitrashree G S1a55b882020-02-04 17:35:35 -0500502
praneeth nalmas55616d62023-02-06 09:19:18 +0530503// ChildDeviceLost deletes the ONU and its references from PONResources
bseeniva0b9cbcb2026-02-12 19:11:11 +0530504func (oo *OpenOLT) ChildDeviceLost(ctx context.Context, childDevice *voltha.Device) (*emptypb.Empty, error) {
Girish Gowdraa0870562021-03-11 14:30:14 -0800505 logger.Infow(ctx, "Child-device-lost", log.Fields{"parent-device-id": childDevice.ParentId, "child-device-id": childDevice.Id})
506 if handler := oo.getDeviceHandler(childDevice.ParentId); handler != nil {
khenaidoo106c61a2021-08-11 18:05:46 -0400507 if err := handler.ChildDeviceLost(log.WithSpanFromContext(context.Background(), ctx), childDevice.ParentPortNo, childDevice.ProxyAddress.OnuId, childDevice.SerialNumber); err != nil {
508 return nil, err
509 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530510 return &emptypb.Empty{}, nil
Chaitrashree G S1a55b882020-02-04 17:35:35 -0500511 }
khenaidoo106c61a2021-08-11 18:05:46 -0400512 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"parent-device-id": childDevice.ParentId}, nil).Log()
Chaitrashree G S1a55b882020-02-04 17:35:35 -0500513}
Scott Baker24f83e22020-03-30 16:14:28 -0700514
khenaidoo106c61a2021-08-11 18:05:46 -0400515// GetExtValue retrieves a value on a particular ONU
khenaidoodc2116e2021-10-19 17:33:19 -0400516func (oo *OpenOLT) GetExtValue(ctx context.Context, extInfo *ca.GetExtValueMessage) (*extension.ReturnValues, error) {
Dinesh Belwalkardb587af2020-02-27 15:37:16 -0800517 var err error
khenaidoodc2116e2021-10-19 17:33:19 -0400518 resp := new(extension.ReturnValues)
khenaidoo106c61a2021-08-11 18:05:46 -0400519 logger.Infow(ctx, "get_ext_value", log.Fields{"parent-device-id": extInfo.ParentDevice.Id, "onu-id": extInfo.ChildDevice.Id})
520 if handler := oo.getDeviceHandler(extInfo.ParentDevice.Id); handler != nil {
521 if resp, err = handler.getExtValue(ctx, extInfo.ChildDevice, extInfo.ValueType); err != nil {
522 logger.Errorw(ctx, "error-occurred-during-get-ext-value",
523 log.Fields{"parent-device-id": extInfo.ParentDevice.Id, "onu-id": extInfo.ChildDevice.Id, "error": err})
Dinesh Belwalkardb587af2020-02-27 15:37:16 -0800524 return nil, err
525 }
526 }
527 return resp, nil
528}
kesavand62126212021-01-12 04:56:06 -0500529
praneeth nalmas55616d62023-02-06 09:19:18 +0530530// GetSingleValue handles get uni status on ONU and ondemand metric on OLT
khenaidoo106c61a2021-08-11 18:05:46 -0400531func (oo *OpenOLT) GetSingleValue(ctx context.Context, request *extension.SingleGetValueRequest) (*extension.SingleGetValueResponse, error) {
532 logger.Infow(ctx, "single_get_value_request", log.Fields{"request": request})
Akash Reddy Kankanalac6b6ca12025-06-12 14:26:57 +0530533 var handler *DeviceHandler
534 var onuDevice *voltha.Device
kesavand62126212021-01-12 04:56:06 -0500535
536 errResp := func(status extension.GetValueResponse_Status,
537 reason extension.GetValueResponse_ErrorReason) *extension.SingleGetValueResponse {
538 return &extension.SingleGetValueResponse{
539 Response: &extension.GetValueResponse{
540 Status: status,
541 ErrReason: reason,
542 },
543 }
544 }
Akash Reddy Kankanalac6b6ca12025-06-12 14:26:57 +0530545
546 switch request.GetRequest().GetRequest().(type) {
547 case *extension.GetValueRequest_OnuStatsFromOlt:
548 handler, onuDevice = oo.GetDeviceHandlerFromChild(ctx, request.TargetId)
549 default:
550 handler = oo.getDeviceHandler(request.TargetId)
551 }
552
553 if handler != nil {
kesavand62126212021-01-12 04:56:06 -0500554 switch reqType := request.GetRequest().GetRequest().(type) {
555 case *extension.GetValueRequest_OltPortInfo:
556 return handler.getOltPortCounters(ctx, reqType.OltPortInfo), nil
Himani Chawla2c8ae0f2021-05-18 23:27:00 +0530557 case *extension.GetValueRequest_OnuPonInfo:
558 return handler.getOnuPonCounters(ctx, reqType.OnuPonInfo), nil
Gamze Abaka85e9a142021-05-26 13:41:39 +0000559 case *extension.GetValueRequest_RxPower:
560 return handler.getRxPower(ctx, reqType.RxPower), nil
praneeth nalmas55616d62023-02-06 09:19:18 +0530561 case *extension.GetValueRequest_OltRxPower:
562 return handler.getPONRxPower(ctx, reqType.OltRxPower), nil
Akash Soni3bcf5e02024-12-03 08:01:48 +0530563 case *extension.GetValueRequest_OffloadedAppsStats:
564 return handler.getOltOffloadStats(ctx, reqType.OffloadedAppsStats), nil
Akash Reddy Kankanalac6b6ca12025-06-12 14:26:57 +0530565 case *extension.GetValueRequest_OnuStatsFromOlt:
566 return handler.getOnuStatsFromOlt(ctx, reqType.OnuStatsFromOlt, onuDevice), nil
Akash Reddy Kankanalad9ec4822025-06-10 22:59:53 +0530567 case *extension.GetValueRequest_OltPonStats:
568 return handler.getPonPortStats(ctx, reqType.OltPonStats), nil
569 case *extension.GetValueRequest_OltNniStats:
570 return handler.getNniPortStats(ctx, reqType.OltNniStats), nil
kesavand62126212021-01-12 04:56:06 -0500571 default:
572 return errResp(extension.GetValueResponse_ERROR, extension.GetValueResponse_UNSUPPORTED), nil
573 }
574 }
575
576 logger.Infow(ctx, "Single_get_value_request failed ", log.Fields{"request": request})
577 return errResp(extension.GetValueResponse_ERROR, extension.GetValueResponse_INVALID_DEVICE_ID), nil
578}
khenaidoo106c61a2021-08-11 18:05:46 -0400579
Akash Soni3bcf5e02024-12-03 08:01:48 +0530580// SetSingleValue is implemented
581func (oo *OpenOLT) SetSingleValue(ctx context.Context, request *extension.SingleSetValueRequest) (*extension.SingleSetValueResponse, error) {
582 logger.Infow(ctx, "single_set_value_request", log.Fields{"request": request})
583
584 errResp := func(status extension.SetValueResponse_Status,
585 reason extension.SetValueResponse_ErrorReason) *extension.SingleSetValueResponse {
586 return &extension.SingleSetValueResponse{
587 Response: &extension.SetValueResponse{
588 Status: status,
589 ErrReason: reason,
590 },
591 }
592 }
593 if handler := oo.getDeviceHandler(request.TargetId); handler != nil {
594 switch reqType := request.GetRequest().GetRequest().(type) {
595 case *extension.SetValueRequest_AppOffloadConfig:
Akash Soni3c75ad72024-12-23 12:09:48 +0530596 return handler.setOltOffload(ctx, reqType.AppOffloadConfig), nil
597 case *extension.SetValueRequest_AppOffloadOnuConfig:
598 return handler.setOnuOffload(ctx, reqType.AppOffloadOnuConfig), nil
Akash Soni3bcf5e02024-12-03 08:01:48 +0530599 default:
600 return errResp(extension.SetValueResponse_ERROR, extension.SetValueResponse_UNSUPPORTED), nil
601 }
602 }
603
604 logger.Infow(ctx, "Single_set_value_request failed ", log.Fields{"request": request})
605 return errResp(extension.SetValueResponse_ERROR, extension.SetValueResponse_INVALID_DEVICE_ID), nil
606}
607
Akash Reddy Kankanalac6b6ca12025-06-12 14:26:57 +0530608func (oo *OpenOLT) GetDeviceHandlerFromChild(ctx context.Context, deviceId string) (*DeviceHandler, *voltha.Device) {
609 oo.lockDeviceHandlersMap.Lock()
610 defer oo.lockDeviceHandlersMap.Unlock()
611
612 for parentId, handler := range oo.deviceHandlers {
613 devices, _ := handler.getChildDevicesFromCore(ctx, parentId)
614 if devices != nil {
615 for _, onuDevice := range devices.Items {
616 if onuDevice.Id == deviceId {
617 return handler, onuDevice
618 }
619 }
620 }
621 }
622 return nil, nil
623}
624
khenaidoo106c61a2021-08-11 18:05:46 -0400625/*
626 * OLT Inter-adapter service
627 */
628
kesavandb9f54fd2021-11-25 20:08:04 +0530629// ProxyOmciRequests proxies an onu sw download OMCI request from the child adapter
bseeniva0b9cbcb2026-02-12 19:11:11 +0530630func (oo *OpenOLT) ProxyOmciRequests(ctx context.Context, request *ia.OmciMessages) (*emptypb.Empty, error) {
kesavandb9f54fd2021-11-25 20:08:04 +0530631 if handler := oo.getDeviceHandler(request.ParentDeviceId); handler != nil {
632 if err := handler.ProxyOmciRequests(ctx, request); err != nil {
Abhilash Laxmeshwar092e6ca2022-12-08 19:51:27 +0530633 return nil, err
kesavandb9f54fd2021-11-25 20:08:04 +0530634 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530635 return &emptypb.Empty{}, nil
kesavandb9f54fd2021-11-25 20:08:04 +0530636 }
637 return nil, olterrors.NewErrNotFound("no-device-handler", log.Fields{"parent-device-id": request.ParentDeviceId, "child-device-id": request.ChildDeviceId}, nil).Log()
638}
639
khenaidoo106c61a2021-08-11 18:05:46 -0400640// ProxyOmciRequest proxies an OMCI request from the child adapter
bseeniva0b9cbcb2026-02-12 19:11:11 +0530641func (oo *OpenOLT) ProxyOmciRequest(ctx context.Context, request *ia.OmciMessage) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400642 logger.Debugw(ctx, "proxy-omci-request", log.Fields{"request": request})
643
644 if handler := oo.getDeviceHandler(request.ParentDeviceId); handler != nil {
645 if err := handler.ProxyOmciMessage(ctx, request); err != nil {
Abhilash Laxmeshwar092e6ca2022-12-08 19:51:27 +0530646 return nil, err
khenaidoo106c61a2021-08-11 18:05:46 -0400647 }
bseeniva0b9cbcb2026-02-12 19:11:11 +0530648 return &emptypb.Empty{}, nil
khenaidoo106c61a2021-08-11 18:05:46 -0400649 }
650 return nil, olterrors.NewErrNotFound("no-device-handler", log.Fields{"parent-device-id": request.ParentDeviceId, "child-device-id": request.ChildDeviceId}, nil).Log()
651}
652
653// GetTechProfileInstance returns an instance of a tech profile
khenaidoodc2116e2021-10-19 17:33:19 -0400654func (oo *OpenOLT) GetTechProfileInstance(ctx context.Context, request *ia.TechProfileInstanceRequestMessage) (*ia.TechProfileDownloadMessage, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400655 logger.Debugw(ctx, "getting-tech-profile-request", log.Fields{"request": request})
656
657 targetDeviceID := request.ParentDeviceId
658 if targetDeviceID == "" {
659 return nil, olterrors.NewErrNotFound("parent-id-empty", log.Fields{"parent-device-id": request.ParentDeviceId, "child-device-id": request.DeviceId}, nil).Log()
660 }
661 if handler := oo.getDeviceHandler(targetDeviceID); handler != nil {
662 return handler.GetTechProfileDownloadMessage(ctx, request)
663 }
664 return nil, olterrors.NewErrNotFound("no-device-handler", log.Fields{"parent-device-id": request.ParentDeviceId, "child-device-id": request.DeviceId}, nil).Log()
khenaidoo106c61a2021-08-11 18:05:46 -0400665}
666
khenaidooefff76e2021-12-15 16:51:30 -0500667// GetHealthStatus is used by a OltAdapterService client to detect a connection
668// lost with the gRPC server hosting the OltAdapterService service
669func (oo *OpenOLT) GetHealthStatus(stream adapter_service.AdapterService_GetHealthStatusServer) error {
670 ctx := context.Background()
671 logger.Debugw(ctx, "receive-stream-connection", log.Fields{"stream": stream})
672
673 if stream == nil {
674 return fmt.Errorf("conn-is-nil %v", stream)
675 }
676 initialRequestTime := time.Now()
677 var remoteClient *common.Connection
678 var tempClient *common.Connection
679 var err error
680loop:
681 for {
682 tempClient, err = stream.Recv()
683 if err != nil {
684 logger.Warnw(ctx, "received-stream-error", log.Fields{"remote-client": remoteClient, "error": err})
685 break loop
686 }
687 // Send a response back
688 err = stream.Send(&health.HealthStatus{State: health.HealthStatus_HEALTHY})
689 if err != nil {
690 logger.Warnw(ctx, "sending-stream-error", log.Fields{"remote-client": remoteClient, "error": err})
691 break loop
692 }
693
694 remoteClient = tempClient
695 logger.Debugw(ctx, "received-keep-alive", log.Fields{"remote-client": remoteClient})
696
697 select {
698 case <-stream.Context().Done():
699 logger.Infow(ctx, "stream-keep-alive-context-done", log.Fields{"remote-client": remoteClient, "error": stream.Context().Err()})
700 break loop
701 case <-oo.exitChannel:
702 logger.Warnw(ctx, "received-stop", log.Fields{"remote-client": remoteClient, "initial-conn-time": initialRequestTime})
703 break loop
704 default:
705 }
706 }
707 logger.Errorw(ctx, "connection-down", log.Fields{"remote-client": remoteClient, "error": err, "initial-conn-time": initialRequestTime})
708 return err
709}
710
Akash Reddy Kankanala78b627f2026-01-12 08:18:21 +0000711// UpdateDevice updates the address of the OLT for now
bseeniva0b9cbcb2026-02-12 19:11:11 +0530712func (oo *OpenOLT) UpdateDevice(ctx context.Context, updateDeviceReq *voltha.UpdateDevice) (*emptypb.Empty, error) {
Akash Reddy Kankanala78b627f2026-01-12 08:18:21 +0000713 logger.Infow(ctx, "update-device", log.Fields{"device": updateDeviceReq})
714 if updateDeviceReq == nil {
715 return nil, fmt.Errorf("nil-device-config")
716 }
717 if updateDeviceReq.Address == nil {
718 return nil, fmt.Errorf("device-address-not-found")
719 }
720 if handler := oo.getDeviceHandler(updateDeviceReq.Id); handler != nil {
721 go handler.UpdateDevice(context.Background(), updateDeviceReq)
bseeniva0b9cbcb2026-02-12 19:11:11 +0530722 return &emptypb.Empty{}, nil
Akash Reddy Kankanala78b627f2026-01-12 08:18:21 +0000723 }
724
725 return nil, olterrors.NewErrNotFound("device-handler", log.Fields{"device-id": updateDeviceReq.Id}, nil).Log()
726}
727
khenaidoo106c61a2021-08-11 18:05:46 -0400728/*
729 *
730 * Unimplemented APIs
731 *
732 */
733
praneeth nalmas55616d62023-02-06 09:19:18 +0530734// SimulateAlarm is unimplemented
khenaidoodc2116e2021-10-19 17:33:19 -0400735func (oo *OpenOLT) SimulateAlarm(context.Context, *ca.SimulateAlarmMessage) (*voltha.OperationResp, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400736 return nil, olterrors.ErrNotImplemented
737}
738
praneeth nalmas55616d62023-02-06 09:19:18 +0530739// SetExtValue is unimplemented
bseeniva0b9cbcb2026-02-12 19:11:11 +0530740func (oo *OpenOLT) SetExtValue(context.Context, *ca.SetExtValueMessage) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400741 return nil, olterrors.ErrNotImplemented
742}
743
praneeth nalmas55616d62023-02-06 09:19:18 +0530744// StartOmciTest not implemented
khenaidoodc2116e2021-10-19 17:33:19 -0400745func (oo *OpenOLT) StartOmciTest(ctx context.Context, test *ca.OMCITest) (*omci.TestResponse, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400746 return nil, olterrors.ErrNotImplemented
747}
748
praneeth nalmas55616d62023-02-06 09:19:18 +0530749// SuppressEvent unimplemented
bseeniva0b9cbcb2026-02-12 19:11:11 +0530750func (oo *OpenOLT) SuppressEvent(ctx context.Context, filter *voltha.EventFilter) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400751 return nil, olterrors.ErrNotImplemented
752}
753
praneeth nalmas55616d62023-02-06 09:19:18 +0530754// UnSuppressEvent unimplemented
bseeniva0b9cbcb2026-02-12 19:11:11 +0530755func (oo *OpenOLT) UnSuppressEvent(ctx context.Context, filter *voltha.EventFilter) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400756 return nil, olterrors.ErrNotImplemented
757}
758
praneeth nalmas55616d62023-02-06 09:19:18 +0530759// DownloadImage is unimplemented
khenaidoodc2116e2021-10-19 17:33:19 -0400760func (oo *OpenOLT) DownloadImage(ctx context.Context, imageInfo *ca.ImageDownloadMessage) (*voltha.ImageDownload, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400761 return nil, olterrors.ErrNotImplemented
762}
763
praneeth nalmas55616d62023-02-06 09:19:18 +0530764// GetImageDownloadStatus is unimplemented
khenaidoodc2116e2021-10-19 17:33:19 -0400765func (oo *OpenOLT) GetImageDownloadStatus(ctx context.Context, imageInfo *ca.ImageDownloadMessage) (*voltha.ImageDownload, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400766 return nil, olterrors.ErrNotImplemented
767}
768
praneeth nalmas55616d62023-02-06 09:19:18 +0530769// CancelImageDownload is unimplemented
khenaidoodc2116e2021-10-19 17:33:19 -0400770func (oo *OpenOLT) CancelImageDownload(ctx context.Context, imageInfo *ca.ImageDownloadMessage) (*voltha.ImageDownload, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400771 return nil, olterrors.ErrNotImplemented
772}
773
praneeth nalmas55616d62023-02-06 09:19:18 +0530774// ActivateImageUpdate is unimplemented
khenaidoodc2116e2021-10-19 17:33:19 -0400775func (oo *OpenOLT) ActivateImageUpdate(ctx context.Context, imageInfo *ca.ImageDownloadMessage) (*voltha.ImageDownload, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400776 return nil, olterrors.ErrNotImplemented
777}
778
praneeth nalmas55616d62023-02-06 09:19:18 +0530779// RevertImageUpdate is unimplemented
khenaidoodc2116e2021-10-19 17:33:19 -0400780func (oo *OpenOLT) RevertImageUpdate(ctx context.Context, imageInfo *ca.ImageDownloadMessage) (*voltha.ImageDownload, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400781 return nil, olterrors.ErrNotImplemented
782}
783
praneeth nalmas55616d62023-02-06 09:19:18 +0530784// DownloadOnuImage unimplemented
khenaidoo106c61a2021-08-11 18:05:46 -0400785func (oo *OpenOLT) DownloadOnuImage(ctx context.Context, request *voltha.DeviceImageDownloadRequest) (*voltha.DeviceImageResponse, error) {
786 return nil, olterrors.ErrNotImplemented
787}
788
praneeth nalmas55616d62023-02-06 09:19:18 +0530789// GetOnuImageStatus unimplemented
khenaidoo106c61a2021-08-11 18:05:46 -0400790func (oo *OpenOLT) GetOnuImageStatus(ctx context.Context, in *voltha.DeviceImageRequest) (*voltha.DeviceImageResponse, error) {
791 return nil, olterrors.ErrNotImplemented
792}
793
praneeth nalmas55616d62023-02-06 09:19:18 +0530794// AbortOnuImageUpgrade unimplemented
khenaidoo106c61a2021-08-11 18:05:46 -0400795func (oo *OpenOLT) AbortOnuImageUpgrade(ctx context.Context, in *voltha.DeviceImageRequest) (*voltha.DeviceImageResponse, error) {
796 return nil, olterrors.ErrNotImplemented
797}
798
praneeth nalmas55616d62023-02-06 09:19:18 +0530799// GetOnuImages unimplemented
khenaidoo106c61a2021-08-11 18:05:46 -0400800func (oo *OpenOLT) GetOnuImages(ctx context.Context, deviceID *common.ID) (*voltha.OnuImages, error) {
801 return nil, olterrors.ErrNotImplemented
802}
803
praneeth nalmas55616d62023-02-06 09:19:18 +0530804// ActivateOnuImage unimplemented
khenaidoo106c61a2021-08-11 18:05:46 -0400805func (oo *OpenOLT) ActivateOnuImage(ctx context.Context, in *voltha.DeviceImageRequest) (*voltha.DeviceImageResponse, error) {
806 return nil, olterrors.ErrNotImplemented
807}
808
praneeth nalmas55616d62023-02-06 09:19:18 +0530809// CommitOnuImage unimplemented
khenaidoo106c61a2021-08-11 18:05:46 -0400810func (oo *OpenOLT) CommitOnuImage(ctx context.Context, in *voltha.DeviceImageRequest) (*voltha.DeviceImageResponse, error) {
811 return nil, olterrors.ErrNotImplemented
812}
813
814// UpdateFlowsBulk is unimplemented
bseeniva0b9cbcb2026-02-12 19:11:11 +0530815func (oo *OpenOLT) UpdateFlowsBulk(ctx context.Context, flows *ca.BulkFlows) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400816 return nil, olterrors.ErrNotImplemented
817}
818
praneeth nalmas55616d62023-02-06 09:19:18 +0530819// SelfTestDevice unimplemented
bseeniva0b9cbcb2026-02-12 19:11:11 +0530820func (oo *OpenOLT) SelfTestDevice(ctx context.Context, device *voltha.Device) (*emptypb.Empty, error) {
khenaidoo106c61a2021-08-11 18:05:46 -0400821 return nil, olterrors.ErrNotImplemented
822}