blob: a05ab38eb459faea2c5d888fbef46f868f368e75 [file] [log] [blame]
Matteo Scandolocedde462021-03-09 17:37:16 -08001/*
Joey Armstrong14628cd2023-01-10 08:38:31 -05002 * Copyright 2018-2023 Open Networking Foundation (ONF) and the ONF Contributors
Matteo Scandolocedde462021-03-09 17:37:16 -08003
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
17package omci
18
19import (
20 "encoding/hex"
21 "errors"
Holger Hildebrandt96382572022-05-31 09:41:38 +000022 "strconv"
23
Matteo Scandolocedde462021-03-09 17:37:16 -080024 "github.com/google/gopacket"
Andrea Campanella10426e22021-10-15 17:58:04 +020025 "github.com/opencord/omci-lib-go/v2"
26 me "github.com/opencord/omci-lib-go/v2/generated"
Matteo Scandolocedde462021-03-09 17:37:16 -080027 log "github.com/sirupsen/logrus"
Holger Hildebrandt96382572022-05-31 09:41:38 +000028)
29
30const (
31 cOmciDownloadSectionSizeBaseLine = 31 //in bytes
32 cOmciDownloadSectionSizeExtLine = 1965 //in bytes
Matteo Scandolocedde462021-03-09 17:37:16 -080033)
34
35func ParseStartSoftwareDownloadRequest(omciPkt gopacket.Packet) (*omci.StartSoftwareDownloadRequest, error) {
36 msgLayer := omciPkt.Layer(omci.LayerTypeStartSoftwareDownloadRequest)
37 if msgLayer == nil {
38 err := "omci Msg layer could not be detected for LayerTypeStartSoftwareDownloadRequest"
39 omciLogger.Error(err)
40 return nil, errors.New(err)
41 }
42 msgObj, msgOk := msgLayer.(*omci.StartSoftwareDownloadRequest)
43 if !msgOk {
44 err := "omci Msg layer could not be assigned for LayerTypeStartSoftwareDownloadRequest"
45 omciLogger.Error(err)
46 return nil, errors.New(err)
47 }
48 return msgObj, nil
49}
50
51func ParseDownloadSectionRequest(omciPkt gopacket.Packet) (*omci.DownloadSectionRequest, error) {
52 msgLayer := omciPkt.Layer(omci.LayerTypeDownloadSectionRequest)
53 if msgLayer == nil {
54 err := "omci Msg layer could not be detected for LayerTypeDownloadSectionRequest"
55 omciLogger.Error(err)
56 return nil, errors.New(err)
57 }
58 msgObj, msgOk := msgLayer.(*omci.DownloadSectionRequest)
59 if !msgOk {
60 err := "omci Msg layer could not be assigned for LayerTypeDownloadSectionRequest"
61 omciLogger.Error(err)
62 return nil, errors.New(err)
63 }
64 return msgObj, nil
65}
66
67func ParseEndSoftwareDownloadRequest(omciPkt gopacket.Packet) (*omci.EndSoftwareDownloadRequest, error) {
68 msgLayer := omciPkt.Layer(omci.LayerTypeEndSoftwareDownloadRequest)
69 if msgLayer == nil {
70 err := "omci Msg layer could not be detected for LayerTypeEndSoftwareDownloadRequest"
71 omciLogger.Error(err)
72 return nil, errors.New(err)
73 }
74 msgObj, msgOk := msgLayer.(*omci.EndSoftwareDownloadRequest)
75 if !msgOk {
76 err := "omci Msg layer could not be assigned for LayerTypeEndSoftwareDownloadRequest"
77 omciLogger.Error(err)
78 return nil, errors.New(err)
79 }
80 return msgObj, nil
81}
82
83func ParseActivateSoftwareRequest(omciPkt gopacket.Packet) (*omci.ActivateSoftwareRequest, error) {
84 msgLayer := omciPkt.Layer(omci.LayerTypeActivateSoftwareRequest)
85 if msgLayer == nil {
86 err := "omci Msg layer could not be detected for LayerTypeActivateSoftwareRequest"
87 omciLogger.Error(err)
88 return nil, errors.New(err)
89 }
90 msgObj, msgOk := msgLayer.(*omci.ActivateSoftwareRequest)
91 if !msgOk {
92 err := "omci Msg layer could not be assigned for LayerTypeActivateSoftwareRequest"
93 omciLogger.Error(err)
94 return nil, errors.New(err)
95 }
96 return msgObj, nil
97}
98
99func ParseCommitSoftwareRequest(omciPkt gopacket.Packet) (*omci.CommitSoftwareRequest, error) {
100 msgLayer := omciPkt.Layer(omci.LayerTypeCommitSoftwareRequest)
101 if msgLayer == nil {
102 err := "omci Msg layer could not be detected for LayerTypeCommitSoftwareRequest"
103 omciLogger.Error(err)
104 return nil, errors.New(err)
105 }
106 msgObj, msgOk := msgLayer.(*omci.CommitSoftwareRequest)
107 if !msgOk {
108 err := "omci Msg layer could not be assigned for LayerTypeCommitSoftwareRequest"
109 omciLogger.Error(err)
110 return nil, errors.New(err)
111 }
112 return msgObj, nil
113}
114
115func CreateStartSoftwareDownloadResponse(omciPkt gopacket.Packet, omciMsg *omci.OMCI) ([]byte, error) {
Holger Hildebrandt96382572022-05-31 09:41:38 +0000116
Matteo Scandolocedde462021-03-09 17:37:16 -0800117 responeCode := me.Success
118 msgObj, err := ParseStartSoftwareDownloadRequest(omciPkt)
119 if err != nil {
120 responeCode = me.ProcessingError
121 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000122 isExtended := false
123 if omciMsg.DeviceIdentifier == omci.ExtendedIdent {
124 isExtended = true
125 }
Matteo Scandolocedde462021-03-09 17:37:16 -0800126 omciLogger.WithFields(log.Fields{
127 "OmciMsgType": omciMsg.MessageType,
128 "TransCorrId": omciMsg.TransactionID,
Holger Hildebrandt96382572022-05-31 09:41:38 +0000129 "DeviceIdentifier": omciMsg.DeviceIdentifier,
Matteo Scandolocedde462021-03-09 17:37:16 -0800130 "EntityInstance": msgObj.EntityInstance,
131 "WindowSize": msgObj.WindowSize,
132 "ImageSize": msgObj.ImageSize,
133 "NumberOfCircuitPacks": msgObj.NumberOfCircuitPacks,
134 "CircuitPacks": msgObj.CircuitPacks,
135 }).Debug("received-start-software-download-request")
136
137 response := &omci.StartSoftwareDownloadResponse{
138 MeBasePacket: omci.MeBasePacket{
139 EntityClass: msgObj.EntityClass,
140 EntityInstance: msgObj.EntityInstance,
Holger Hildebrandt96382572022-05-31 09:41:38 +0000141 Extended: isExtended,
Matteo Scandolocedde462021-03-09 17:37:16 -0800142 },
143 WindowSize: msgObj.WindowSize,
144 Result: responeCode,
145 NumberOfInstances: 0, // NOTE this can't be bigger than 0 this we can populate downloadResults
146 MeResults: []omci.DownloadResults{}, // FIXME downloadResults is not exported
147 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000148 omciLayer := &omci.OMCI{
149 TransactionID: omciMsg.TransactionID,
150 MessageType: omci.StartSoftwareDownloadResponseType,
151 DeviceIdentifier: omciMsg.DeviceIdentifier,
152 }
153 var options gopacket.SerializeOptions
154 options.FixLengths = true
Matteo Scandolocedde462021-03-09 17:37:16 -0800155
Holger Hildebrandt96382572022-05-31 09:41:38 +0000156 buffer := gopacket.NewSerializeBuffer()
157 err = gopacket.SerializeLayers(buffer, options, omciLayer, response)
Matteo Scandolocedde462021-03-09 17:37:16 -0800158 if err != nil {
159 omciLogger.WithFields(log.Fields{
Holger Hildebrandt96382572022-05-31 09:41:38 +0000160 "Err": err,
161 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
162 }).Error("cannot-Serialize-StartSoftwareDownloadResponse")
Matteo Scandolocedde462021-03-09 17:37:16 -0800163 return nil, err
164 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000165 pkt := buffer.Bytes()
Matteo Scandolocedde462021-03-09 17:37:16 -0800166
167 log.WithFields(log.Fields{
168 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
169 "pkt": hex.EncodeToString(pkt),
170 }).Trace("omci-start-software-download-response")
171
172 return pkt, nil
173}
174
175func CreateDownloadSectionResponse(omciPkt gopacket.Packet, omciMsg *omci.OMCI) ([]byte, error) {
176
177 msgObj, err := ParseDownloadSectionRequest(omciPkt)
178
179 if err != nil {
180 return nil, err
181 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000182 isExtended := false
183 if omciMsg.DeviceIdentifier == omci.ExtendedIdent {
184 isExtended = true
185 }
Matteo Scandolocedde462021-03-09 17:37:16 -0800186 omciLogger.WithFields(log.Fields{
Holger Hildebrandt96382572022-05-31 09:41:38 +0000187 "OmciMsgType": omciMsg.MessageType,
188 "TransCorrId": omciMsg.TransactionID,
189 "DeviceIdentifier": omciMsg.DeviceIdentifier,
190 "EntityInstance": msgObj.EntityInstance,
191 "SectionNumber": msgObj.SectionNumber,
Matteo Scandolocedde462021-03-09 17:37:16 -0800192 }).Debug("received-download-section-request")
193
194 response := &omci.DownloadSectionResponse{
195 MeBasePacket: omci.MeBasePacket{
196 EntityClass: msgObj.EntityClass,
197 EntityInstance: msgObj.EntityInstance,
Holger Hildebrandt96382572022-05-31 09:41:38 +0000198 Extended: isExtended,
Matteo Scandolocedde462021-03-09 17:37:16 -0800199 },
200 Result: me.Success,
201 SectionNumber: msgObj.SectionNumber,
202 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000203 omciLayer := &omci.OMCI{
204 TransactionID: omciMsg.TransactionID,
205 MessageType: omci.DownloadSectionResponseType,
206 DeviceIdentifier: omciMsg.DeviceIdentifier,
207 }
208 var options gopacket.SerializeOptions
209 options.FixLengths = true
Matteo Scandolocedde462021-03-09 17:37:16 -0800210
Holger Hildebrandt96382572022-05-31 09:41:38 +0000211 buffer := gopacket.NewSerializeBuffer()
212 err = gopacket.SerializeLayers(buffer, options, omciLayer, response)
Matteo Scandolocedde462021-03-09 17:37:16 -0800213 if err != nil {
Holger Hildebrandt96382572022-05-31 09:41:38 +0000214 omciLogger.WithFields(log.Fields{
215 "Err": err,
216 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
217 }).Error("cannot-Serialize-DownloadSectionResponse")
Matteo Scandolocedde462021-03-09 17:37:16 -0800218 return nil, err
219 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000220 pkt := buffer.Bytes()
Matteo Scandolocedde462021-03-09 17:37:16 -0800221
222 log.WithFields(log.Fields{
223 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
224 "pkt": hex.EncodeToString(pkt),
225 }).Trace("omci-download-section-with-response-response")
226
227 return pkt, nil
228}
229
230func CreateEndSoftwareDownloadResponse(omciPkt gopacket.Packet, omciMsg *omci.OMCI, status me.Results) ([]byte, error) {
231
232 msgObj, err := ParseEndSoftwareDownloadRequest(omciPkt)
233
234 if err != nil {
235 return nil, err
236 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000237 isExtended := false
238 if omciMsg.DeviceIdentifier == omci.ExtendedIdent {
239 isExtended = true
240 }
Matteo Scandolocedde462021-03-09 17:37:16 -0800241 omciLogger.WithFields(log.Fields{
242 "OmciMsgType": omciMsg.MessageType,
243 "TransCorrId": omciMsg.TransactionID,
Holger Hildebrandt96382572022-05-31 09:41:38 +0000244 "DeviceIdentifier": omciMsg.DeviceIdentifier,
Matteo Scandolocedde462021-03-09 17:37:16 -0800245 "EntityInstance": msgObj.EntityInstance,
246 "Crc32": msgObj.CRC32,
247 "ImageSize": msgObj.ImageSize,
248 "NumberOfInstances": msgObj.NumberOfInstances,
249 "ImageInstances": msgObj.ImageInstances,
250 }).Debug("received-end-software-download-request")
251
252 response := &omci.EndSoftwareDownloadResponse{
253 MeBasePacket: omci.MeBasePacket{
254 EntityClass: msgObj.EntityClass,
255 EntityInstance: msgObj.EntityInstance,
Holger Hildebrandt96382572022-05-31 09:41:38 +0000256 Extended: isExtended,
Matteo Scandolocedde462021-03-09 17:37:16 -0800257 },
258 Result: status,
259 NumberOfInstances: 0, // NOTE this can't be bigger than 0 this we can populate downloadResults
260 //MeResults: []omci.downloadResults{}, // FIXME downloadResults is not exported
261 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000262 omciLayer := &omci.OMCI{
263 TransactionID: omciMsg.TransactionID,
264 MessageType: omci.EndSoftwareDownloadResponseType,
265 DeviceIdentifier: omciMsg.DeviceIdentifier,
266 }
267 var options gopacket.SerializeOptions
268 options.FixLengths = true
Matteo Scandolocedde462021-03-09 17:37:16 -0800269
Holger Hildebrandt96382572022-05-31 09:41:38 +0000270 buffer := gopacket.NewSerializeBuffer()
271 err = gopacket.SerializeLayers(buffer, options, omciLayer, response)
Matteo Scandolocedde462021-03-09 17:37:16 -0800272 if err != nil {
Holger Hildebrandt96382572022-05-31 09:41:38 +0000273 omciLogger.WithFields(log.Fields{
274 "Err": err,
275 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
276 }).Error("cannot-Serialize-EndSoftwareDownloadResponse")
Matteo Scandolocedde462021-03-09 17:37:16 -0800277 return nil, err
278 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000279 pkt := buffer.Bytes()
Matteo Scandolocedde462021-03-09 17:37:16 -0800280
281 log.WithFields(log.Fields{
282 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
283 "pkt": hex.EncodeToString(pkt),
284 }).Trace("omci-end-software-download-response")
285
286 return pkt, nil
287}
288
289func CreateActivateSoftwareResponse(omciPkt gopacket.Packet, omciMsg *omci.OMCI) ([]byte, error) {
290
291 msgObj, err := ParseActivateSoftwareRequest(omciPkt)
292
293 if err != nil {
294 return nil, err
295 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000296 isExtended := false
297 if omciMsg.DeviceIdentifier == omci.ExtendedIdent {
298 isExtended = true
299 }
Matteo Scandolocedde462021-03-09 17:37:16 -0800300 omciLogger.WithFields(log.Fields{
Holger Hildebrandt96382572022-05-31 09:41:38 +0000301 "OmciMsgType": omciMsg.MessageType,
302 "TransCorrId": omciMsg.TransactionID,
303 "DeviceIdentifier": omciMsg.DeviceIdentifier,
304 "EntityInstance": msgObj.EntityInstance,
305 "ActivateFlags": msgObj.ActivateFlags,
Matteo Scandolocedde462021-03-09 17:37:16 -0800306 }).Debug("received-activate-software-request")
307
308 response := &omci.ActivateSoftwareResponse{
309 MeBasePacket: omci.MeBasePacket{
310 EntityClass: msgObj.EntityClass,
311 EntityInstance: msgObj.EntityInstance,
Holger Hildebrandt96382572022-05-31 09:41:38 +0000312 Extended: isExtended,
Matteo Scandolocedde462021-03-09 17:37:16 -0800313 },
314 Result: me.Success,
315 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000316 omciLayer := &omci.OMCI{
317 TransactionID: omciMsg.TransactionID,
318 MessageType: omci.ActivateSoftwareResponseType,
319 DeviceIdentifier: omciMsg.DeviceIdentifier,
320 }
321 var options gopacket.SerializeOptions
322 options.FixLengths = true
Matteo Scandolocedde462021-03-09 17:37:16 -0800323
Holger Hildebrandt96382572022-05-31 09:41:38 +0000324 buffer := gopacket.NewSerializeBuffer()
325 err = gopacket.SerializeLayers(buffer, options, omciLayer, response)
Matteo Scandolocedde462021-03-09 17:37:16 -0800326 if err != nil {
Holger Hildebrandt96382572022-05-31 09:41:38 +0000327 omciLogger.WithFields(log.Fields{
328 "Err": err,
329 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
330 }).Error("cannot-Serialize-ActivateSoftwareResponse")
Matteo Scandolocedde462021-03-09 17:37:16 -0800331 return nil, err
332 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000333 pkt := buffer.Bytes()
Matteo Scandolocedde462021-03-09 17:37:16 -0800334
335 log.WithFields(log.Fields{
336 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
337 "pkt": hex.EncodeToString(pkt),
338 }).Trace("omci-activate-software-response")
339
340 return pkt, nil
341}
342
343func CreateCommitSoftwareResponse(omciPkt gopacket.Packet, omciMsg *omci.OMCI) ([]byte, error) {
344
345 msgObj, err := ParseCommitSoftwareRequest(omciPkt)
346
347 if err != nil {
348 return nil, err
349 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000350 isExtended := false
351 if omciMsg.DeviceIdentifier == omci.ExtendedIdent {
352 isExtended = true
353 }
Matteo Scandolocedde462021-03-09 17:37:16 -0800354 omciLogger.WithFields(log.Fields{
Holger Hildebrandt96382572022-05-31 09:41:38 +0000355 "OmciMsgType": omciMsg.MessageType,
356 "TransCorrId": omciMsg.TransactionID,
357 "DeviceIdentifier": omciMsg.DeviceIdentifier,
358 "EntityInstance": msgObj.EntityInstance,
Matteo Scandolocedde462021-03-09 17:37:16 -0800359 }).Debug("received-commit-software-request")
360
361 response := &omci.CommitSoftwareResponse{
362 MeBasePacket: omci.MeBasePacket{
363 EntityClass: msgObj.EntityClass,
364 EntityInstance: msgObj.EntityInstance,
Holger Hildebrandt96382572022-05-31 09:41:38 +0000365 Extended: isExtended,
Matteo Scandolocedde462021-03-09 17:37:16 -0800366 },
367 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000368 omciLayer := &omci.OMCI{
369 TransactionID: omciMsg.TransactionID,
370 MessageType: omci.CommitSoftwareResponseType,
371 DeviceIdentifier: omciMsg.DeviceIdentifier,
372 }
373 var options gopacket.SerializeOptions
374 options.FixLengths = true
Matteo Scandolocedde462021-03-09 17:37:16 -0800375
Holger Hildebrandt96382572022-05-31 09:41:38 +0000376 buffer := gopacket.NewSerializeBuffer()
377 err = gopacket.SerializeLayers(buffer, options, omciLayer, response)
Matteo Scandolocedde462021-03-09 17:37:16 -0800378 if err != nil {
Holger Hildebrandt96382572022-05-31 09:41:38 +0000379 omciLogger.WithFields(log.Fields{
380 "Err": err,
381 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
382 }).Error("cannot-Serialize-CommitSoftwareResponse")
Matteo Scandolocedde462021-03-09 17:37:16 -0800383 return nil, err
384 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000385 pkt := buffer.Bytes()
Matteo Scandolocedde462021-03-09 17:37:16 -0800386
387 log.WithFields(log.Fields{
388 "TxID": strconv.FormatInt(int64(omciMsg.TransactionID), 16),
389 "pkt": hex.EncodeToString(pkt),
390 }).Trace("omci-commit-software-response")
391
392 return pkt, nil
393}
394
Holger Hildebrandt96382572022-05-31 09:41:38 +0000395func ComputeDownloadSectionsCount(pkt gopacket.Packet) uint32 {
Matteo Scandolocedde462021-03-09 17:37:16 -0800396 msgObj, err := ParseStartSoftwareDownloadRequest(pkt)
397 if err != nil {
398 omciLogger.Error("cannot-parse-start-software-download-request")
399 }
Holger Hildebrandt96382572022-05-31 09:41:38 +0000400 var omciDownloadSectionSize uint32
401 if msgObj.Extended {
402 omciDownloadSectionSize = cOmciDownloadSectionSizeExtLine
403 } else {
404 omciDownloadSectionSize = cOmciDownloadSectionSizeBaseLine
405 }
406 noOfSections := msgObj.ImageSize / omciDownloadSectionSize
407 if msgObj.ImageSize%omciDownloadSectionSize > 0 {
408 noOfSections++
409 }
410 return noOfSections
Matteo Scandolocedde462021-03-09 17:37:16 -0800411}