blob: 303bae371d584ae84e590fc2f3817972988b7398 [file] [log] [blame]
khenaidooab1f7bd2019-11-14 14:00:27 -05001/*
2 * Copyright 2019-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 */
npujar1d86a522019-11-14 17:11:16 +053016
khenaidooab1f7bd2019-11-14 14:00:27 -050017package mocks
18
19import (
20 "context"
21 "fmt"
npujar1d86a522019-11-14 17:11:16 +053022 "strings"
khenaidoo67b22152020-03-02 16:01:25 -050023 "sync"
npujar1d86a522019-11-14 17:11:16 +053024
khenaidooab1f7bd2019-11-14 14:00:27 -050025 "github.com/gogo/protobuf/proto"
serkant.uluderya2ae470f2020-01-21 11:13:09 -080026 "github.com/opencord/voltha-lib-go/v3/pkg/adapters/adapterif"
27 com "github.com/opencord/voltha-lib-go/v3/pkg/adapters/common"
28 "github.com/opencord/voltha-lib-go/v3/pkg/log"
29 ic "github.com/opencord/voltha-protos/v3/go/inter_container"
30 of "github.com/opencord/voltha-protos/v3/go/openflow_13"
31 "github.com/opencord/voltha-protos/v3/go/voltha"
khenaidooab1f7bd2019-11-14 14:00:27 -050032)
33
34const (
khenaidoo67b22152020-03-02 16:01:25 -050035 numONUPerOLT = 4
36 startingUNIPortNo = 100
khenaidooab1f7bd2019-11-14 14:00:27 -050037)
38
npujar1d86a522019-11-14 17:11:16 +053039// OLTAdapter represent OLT adapter
khenaidooab1f7bd2019-11-14 14:00:27 -050040type OLTAdapter struct {
khenaidoo67b22152020-03-02 16:01:25 -050041 flows map[uint64]*voltha.OfpFlowStats
42 lock sync.Mutex
khenaidooab1f7bd2019-11-14 14:00:27 -050043 Adapter
44}
45
npujar1d86a522019-11-14 17:11:16 +053046// NewOLTAdapter - creates OLT adapter instance
khenaidooab1f7bd2019-11-14 14:00:27 -050047func NewOLTAdapter(cp adapterif.CoreProxy) *OLTAdapter {
khenaidoo67b22152020-03-02 16:01:25 -050048 return &OLTAdapter{
49 flows: map[uint64]*voltha.OfpFlowStats{},
50 Adapter: Adapter{
51 coreProxy: cp,
52 },
53 }
khenaidooab1f7bd2019-11-14 14:00:27 -050054}
55
npujar1d86a522019-11-14 17:11:16 +053056// Adopt_device creates new handler for added device
57func (oltA *OLTAdapter) Adopt_device(device *voltha.Device) error { // nolint
khenaidooab1f7bd2019-11-14 14:00:27 -050058 go func() {
59 d := proto.Clone(device).(*voltha.Device)
60 d.Root = true
61 d.Vendor = "olt_adapter_mock"
62 d.Model = "go-mock"
63 d.SerialNumber = com.GetRandomSerialNumber()
64 d.MacAddress = strings.ToUpper(com.GetRandomMacAddress())
65 oltA.storeDevice(d)
66 if res := oltA.coreProxy.DeviceUpdate(context.TODO(), d); res != nil {
67 log.Fatalf("deviceUpdate-failed-%s", res)
68 }
69 nniPort := &voltha.Port{
70 PortNo: 2,
71 Label: fmt.Sprintf("nni-%d", 2),
72 Type: voltha.Port_ETHERNET_NNI,
73 OperStatus: voltha.OperStatus_ACTIVE,
74 }
75 var err error
76 if err = oltA.coreProxy.PortCreated(context.TODO(), d.Id, nniPort); err != nil {
77 log.Fatalf("PortCreated-failed-%s", err)
78 }
79
80 ponPort := &voltha.Port{
81 PortNo: 1,
82 Label: fmt.Sprintf("pon-%d", 1),
83 Type: voltha.Port_PON_OLT,
84 OperStatus: voltha.OperStatus_ACTIVE,
85 }
86 if err = oltA.coreProxy.PortCreated(context.TODO(), d.Id, ponPort); err != nil {
87 log.Fatalf("PortCreated-failed-%s", err)
88 }
89
90 d.ConnectStatus = voltha.ConnectStatus_REACHABLE
91 d.OperStatus = voltha.OperStatus_ACTIVE
92
93 if err = oltA.coreProxy.DeviceStateUpdate(context.TODO(), d.Id, d.ConnectStatus, d.OperStatus); err != nil {
94 log.Fatalf("Device-state-update-failed-%s", err)
95 }
96
97 //Get the latest device data from the Core
98 if d, err = oltA.coreProxy.GetDevice(context.TODO(), d.Id, d.Id); err != nil {
99 log.Fatalf("getting-device-failed-%s", err)
100 }
101
102 if err = oltA.updateDevice(d); err != nil {
103 log.Fatalf("saving-device-failed-%s", err)
104 }
105
106 // Register Child devices
khenaidoo67b22152020-03-02 16:01:25 -0500107 initialUniPortNo := startingUNIPortNo
khenaidooab1f7bd2019-11-14 14:00:27 -0500108 for i := 0; i < numONUPerOLT; i++ {
109 go func(seqNo int) {
110 if _, err := oltA.coreProxy.ChildDeviceDetected(
111 context.TODO(),
112 d.Id,
113 1,
114 "onu_adapter_mock",
115 initialUniPortNo+seqNo,
116 "onu_adapter_mock",
117 com.GetRandomSerialNumber(),
118 int64(seqNo)); err != nil {
119 log.Fatalf("failure-sending-child-device-%s", err)
120 }
121 }(i)
122 }
123 }()
124 return nil
125}
126
npujar1d86a522019-11-14 17:11:16 +0530127// Get_ofp_device_info returns ofp device info
128func (oltA *OLTAdapter) Get_ofp_device_info(device *voltha.Device) (*ic.SwitchCapability, error) { // nolint
khenaidooab1f7bd2019-11-14 14:00:27 -0500129 if d := oltA.getDevice(device.Id); d == nil {
130 log.Fatalf("device-not-found-%s", device.Id)
131 }
132 return &ic.SwitchCapability{
133 Desc: &of.OfpDesc{
134 HwDesc: "olt_adapter_mock",
135 SwDesc: "olt_adapter_mock",
136 SerialNum: "12345678",
137 },
138 SwitchFeatures: &of.OfpSwitchFeatures{
139 NBuffers: 256,
140 NTables: 2,
141 Capabilities: uint32(of.OfpCapabilities_OFPC_FLOW_STATS |
142 of.OfpCapabilities_OFPC_TABLE_STATS |
143 of.OfpCapabilities_OFPC_PORT_STATS |
144 of.OfpCapabilities_OFPC_GROUP_STATS),
145 },
146 }, nil
147}
148
npujar1d86a522019-11-14 17:11:16 +0530149// Get_ofp_port_info returns ofp port info
150func (oltA *OLTAdapter) Get_ofp_port_info(device *voltha.Device, portNo int64) (*ic.PortCapability, error) { // nolint
khenaidooab1f7bd2019-11-14 14:00:27 -0500151 if d := oltA.getDevice(device.Id); d == nil {
152 log.Fatalf("device-not-found-%s", device.Id)
153 }
154 capability := uint32(of.OfpPortFeatures_OFPPF_1GB_FD | of.OfpPortFeatures_OFPPF_FIBER)
155 return &ic.PortCapability{
156 Port: &voltha.LogicalPort{
157 OfpPort: &of.OfpPort{
158 HwAddr: macAddressToUint32Array("11:22:33:44:55:66"),
159 Config: 0,
160 State: uint32(of.OfpPortState_OFPPS_LIVE),
161 Curr: capability,
162 Advertised: capability,
163 Peer: capability,
164 CurrSpeed: uint32(of.OfpPortFeatures_OFPPF_1GB_FD),
165 MaxSpeed: uint32(of.OfpPortFeatures_OFPPF_1GB_FD),
166 },
167 DeviceId: device.Id,
npujar1d86a522019-11-14 17:11:16 +0530168 DevicePortNo: uint32(portNo),
khenaidooab1f7bd2019-11-14 14:00:27 -0500169 },
170 }, nil
171}
172
npujar1d86a522019-11-14 17:11:16 +0530173// GetNumONUPerOLT returns number of ONUs per OLT
khenaidooab1f7bd2019-11-14 14:00:27 -0500174func (oltA *OLTAdapter) GetNumONUPerOLT() int {
175 return numONUPerOLT
176}
177
khenaidoo67b22152020-03-02 16:01:25 -0500178// Returns the starting UNI port number
179func (oltA *OLTAdapter) GetStartingUNIPortNo() int {
180 return startingUNIPortNo
181}
182
npujar1d86a522019-11-14 17:11:16 +0530183// Disable_device disables device
184func (oltA *OLTAdapter) Disable_device(device *voltha.Device) error { // nolint
khenaidooab1f7bd2019-11-14 14:00:27 -0500185 go func() {
186 if d := oltA.getDevice(device.Id); d == nil {
187 log.Fatalf("device-not-found-%s", device.Id)
188 }
189
190 cloned := proto.Clone(device).(*voltha.Device)
191 // Update the all ports state on that device to disable
192 if err := oltA.coreProxy.PortsStateUpdate(context.TODO(), cloned.Id, voltha.OperStatus_UNKNOWN); err != nil {
193 log.Fatalf("updating-ports-failed", log.Fields{"deviceId": device.Id, "error": err})
194 }
195
196 //Update the device state
197 cloned.ConnectStatus = voltha.ConnectStatus_UNREACHABLE
198 cloned.OperStatus = voltha.OperStatus_UNKNOWN
199
200 if err := oltA.coreProxy.DeviceStateUpdate(context.TODO(), cloned.Id, cloned.ConnectStatus, cloned.OperStatus); err != nil {
201 log.Fatalf("device-state-update-failed", log.Fields{"deviceId": device.Id, "error": err})
202 }
203
204 if err := oltA.updateDevice(cloned); err != nil {
205 log.Fatalf("saving-device-failed-%s", err)
206 }
207
208 // Tell the Core that all child devices have been disabled (by default it's an action already taken by the Core
209 if err := oltA.coreProxy.ChildDevicesLost(context.TODO(), cloned.Id); err != nil {
210 log.Fatalf("lost-notif-of-child-devices-failed", log.Fields{"deviceId": device.Id, "error": err})
211 }
212 }()
213 return nil
214}
215
npujar1d86a522019-11-14 17:11:16 +0530216// Reenable_device reenables device
217func (oltA *OLTAdapter) Reenable_device(device *voltha.Device) error { // nolint
khenaidooab1f7bd2019-11-14 14:00:27 -0500218 go func() {
219 if d := oltA.getDevice(device.Id); d == nil {
220 log.Fatalf("device-not-found-%s", device.Id)
221 }
222
223 cloned := proto.Clone(device).(*voltha.Device)
224 // Update the all ports state on that device to enable
225 if err := oltA.coreProxy.PortsStateUpdate(context.TODO(), cloned.Id, voltha.OperStatus_ACTIVE); err != nil {
226 log.Fatalf("updating-ports-failed", log.Fields{"deviceId": device.Id, "error": err})
227 }
228
229 //Update the device state
230 cloned.ConnectStatus = voltha.ConnectStatus_REACHABLE
231 cloned.OperStatus = voltha.OperStatus_ACTIVE
232
233 if err := oltA.coreProxy.DeviceStateUpdate(context.TODO(), cloned.Id, cloned.ConnectStatus, cloned.OperStatus); err != nil {
234 log.Fatalf("device-state-update-failed", log.Fields{"deviceId": device.Id, "error": err})
235 }
236
237 // Tell the Core that all child devices have been enabled
238 if err := oltA.coreProxy.ChildDevicesDetected(context.TODO(), cloned.Id); err != nil {
239 log.Fatalf("detection-notif-of-child-devices-failed", log.Fields{"deviceId": device.Id, "error": err})
240 }
241 }()
242 return nil
243}
kesavandbc2d1622020-01-21 00:42:01 -0500244
245// Enable_port -
246func (oltA *OLTAdapter) Enable_port(deviceId string, Port *voltha.Port) error { //nolint
247 go func() {
248
249 if Port.Type == voltha.Port_PON_OLT {
250 if err := oltA.coreProxy.PortStateUpdate(context.TODO(), deviceId, voltha.Port_PON_OLT, Port.PortNo, voltha.OperStatus_ACTIVE); err != nil {
251 log.Fatalf("updating-ports-failed", log.Fields{"device-id": deviceId, "error": err})
252 }
253 }
254
255 }()
256 return nil
257}
258
259// Disable_port -
260func (oltA *OLTAdapter) Disable_port(deviceId string, Port *voltha.Port) error { //nolint
261 go func() {
262
263 if Port.Type == voltha.Port_PON_OLT {
264 if err := oltA.coreProxy.PortStateUpdate(context.TODO(), deviceId, voltha.Port_PON_OLT, Port.PortNo, voltha.OperStatus_DISCOVERED); err != nil {
265 log.Fatalf("updating-ports-failed", log.Fields{"device-id": deviceId, "error": err})
266 }
267 }
268 }()
269 return nil
270}
Chaitrashree G S543df3e2020-02-24 22:36:54 -0500271
272// Child_device_lost deletes ONU and its references
273func (oltA *OLTAdapter) Child_device_lost(deviceID string, pPortNo uint32, onuID uint32) error { // nolint
274 return nil
275}
khenaidoo67b22152020-03-02 16:01:25 -0500276
277// Update_flows_incrementally mocks the incremental flow update
278func (oltA *OLTAdapter) Update_flows_incrementally(device *voltha.Device, flows *of.FlowChanges, groups *of.FlowGroupChanges, flowMetadata *voltha.FlowMetadata) error { // nolint
279 oltA.lock.Lock()
280 defer oltA.lock.Unlock()
281
282 if flows.ToAdd != nil {
283 for _, f := range flows.ToAdd.Items {
284 oltA.flows[f.Id] = f
285 }
286 }
287 if flows.ToRemove != nil {
288 for _, f := range flows.ToRemove.Items {
289 delete(oltA.flows, f.Id)
290 }
291 }
292 return nil
293}
294
295// GetFlowCount returns the total number of flows presently under this adapter
296func (oltA *OLTAdapter) GetFlowCount() int {
297 oltA.lock.Lock()
298 defer oltA.lock.Unlock()
299
300 return len(oltA.flows)
301}
302
303// ClearFlows removes all flows in this adapter
304func (oltA *OLTAdapter) ClearFlows() {
305 oltA.lock.Lock()
306 defer oltA.lock.Unlock()
307
308 oltA.flows = map[uint64]*voltha.OfpFlowStats{}
309}