[VOL-4723] openonuAdapterGo: OMCI extended message set - support alarm data retrieval

Change-Id: I3c5c3a9e8126b4e7b44ffc1a7fd9e10694c6e2d6
diff --git a/VERSION b/VERSION
index 3263355..276cbf9 100755
--- a/VERSION
+++ b/VERSION
@@ -1 +1 @@
-2.3.0-dev287
+2.3.0
diff --git a/go.mod b/go.mod
index d6f2212..fd7e3ba 100644
--- a/go.mod
+++ b/go.mod
@@ -15,7 +15,7 @@
 	github.com/golang/protobuf v1.5.2
 	github.com/google/gopacket v1.1.17
 	github.com/looplab/fsm v0.2.0
-	github.com/opencord/omci-lib-go/v2 v2.2.0
+	github.com/opencord/omci-lib-go/v2 v2.2.1
 	github.com/opencord/voltha-lib-go/v7 v7.1.8
 	github.com/opencord/voltha-protos/v5 v5.2.2
 	github.com/stretchr/testify v1.7.0
diff --git a/go.sum b/go.sum
index fb49fc2..b70e58c 100644
--- a/go.sum
+++ b/go.sum
@@ -198,8 +198,8 @@
 github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo=
 github.com/onsi/gomega v1.14.0 h1:ep6kpPVwmr/nTbklSx2nrLNSIO62DoYAhnPNIMhK8gI=
 github.com/onsi/gomega v1.14.0/go.mod h1:cIuvLEne0aoVhAgh/O6ac0Op8WWw9H6eYCriF+tEHG0=
-github.com/opencord/omci-lib-go/v2 v2.2.0 h1:9eawwD1+oWHTzEv9Q/JeSN12N/3YSGKoj1dr2Pm434g=
-github.com/opencord/omci-lib-go/v2 v2.2.0/go.mod h1:o1S/jhDLHNikFU7uG2TR5UOM5KmKlqwLlVncXi0FBYQ=
+github.com/opencord/omci-lib-go/v2 v2.2.1 h1:Eai3feaixdQ7ZT8zgqIa94QlJ4tfQCgL0sTM8Q6/rkI=
+github.com/opencord/omci-lib-go/v2 v2.2.1/go.mod h1:o1S/jhDLHNikFU7uG2TR5UOM5KmKlqwLlVncXi0FBYQ=
 github.com/opencord/voltha-lib-go/v7 v7.1.8 h1:5k+1Ul+T+gmvM7GONbK1/+YrX4tizAc3REgHoFvug0I=
 github.com/opencord/voltha-lib-go/v7 v7.1.8/go.mod h1:lnwlFfhDVMBg2siCv1CajB1fvfAU9Cs8VbB64LQ8zVg=
 github.com/opencord/voltha-protos/v5 v5.2.2 h1:1Bcgl+Fmp00ZxlDrHZdcbjpMgOwX6TnZmOTrYm9SbR8=
diff --git a/internal/pkg/almgr/alarm_manager.go b/internal/pkg/almgr/alarm_manager.go
index 159736b..cfdaa7b 100755
--- a/internal/pkg/almgr/alarm_manager.go
+++ b/internal/pkg/almgr/alarm_manager.go
@@ -111,8 +111,9 @@
 	onuDBCopy                  alarmBitMapDB
 	bufferedNotifications      []*omci.AlarmNotificationMsg
 	alarmUploadSeqNo           uint16
-	alarmUploadNoOfCmds        uint16
+	alarmUploadNoOfCmdsOrMEs   uint16
 	StopAlarmAuditTimer        chan struct{}
+	isExtendedOmci             bool
 }
 
 // NewAlarmManager - TODO: add comment
@@ -231,7 +232,7 @@
 		}
 	}
 	if err := am.pOnuDeviceEntry.GetDevOmciCC().SendGetAllAlarm(log.WithSpanFromContext(context.TODO(), ctx), 0,
-		am.pDeviceHandler.GetOmciTimeout(), true); err != nil {
+		am.pDeviceHandler.GetOmciTimeout(), true, am.isExtendedOmci); err != nil {
 		// Transition to failure so that alarm sync can be restarted again
 		go failureTransition()
 	}
@@ -366,7 +367,7 @@
 			am.processMessage = false
 			am.activeAlarms = nil
 			am.alarmBitMapDB = nil
-			am.alarmUploadNoOfCmds = 0
+			am.alarmUploadNoOfCmdsOrMEs = 0
 			am.alarmUploadSeqNo = 0
 			am.onuAlarmManagerLock.Unlock()
 			return
@@ -406,7 +407,7 @@
 		return
 	}
 	am.onuAlarmManagerLock.Lock()
-	am.alarmUploadNoOfCmds = msgObj.NumberOfCommands
+	am.alarmUploadNoOfCmdsOrMEs = msgObj.NumberOfCommands
 	am.onuAlarmManagerLock.Unlock()
 	failureTransition := func() {
 		if err := am.AlarmSyncFsm.PFsm.Event(AsEvFailure); err != nil {
@@ -414,7 +415,7 @@
 		}
 	}
 	am.onuAlarmManagerLock.Lock()
-	if am.alarmUploadSeqNo < am.alarmUploadNoOfCmds {
+	if am.alarmUploadSeqNo < am.alarmUploadNoOfCmdsOrMEs {
 		// Reset Onu Alarm Sequence
 		am.resetAlarmSequence()
 		// Get a copy of the alarm bit map db.
@@ -423,11 +424,11 @@
 		}
 		am.onuAlarmManagerLock.Unlock()
 		if err := am.pOnuDeviceEntry.GetDevOmciCC().SendGetAllAlarmNext(
-			log.WithSpanFromContext(context.TODO(), ctx), am.pDeviceHandler.GetOmciTimeout(), true); err != nil {
+			log.WithSpanFromContext(context.TODO(), ctx), am.pDeviceHandler.GetOmciTimeout(), true, am.isExtendedOmci); err != nil {
 			// Transition to failure
 			go failureTransition()
 		}
-	} else if am.alarmUploadNoOfCmds == 0 {
+	} else if am.alarmUploadNoOfCmdsOrMEs == 0 {
 		// Reset Onu Alarm Sequence
 		am.resetAlarmSequence()
 		// Get a copy of the alarm bit map db.
@@ -452,7 +453,7 @@
 		}
 	} else {
 		logger.Errorw(ctx, "invalid-number-of-commands-received", log.Fields{"device-id": am.deviceID,
-			"upload-no-of-cmds": am.alarmUploadNoOfCmds, "upload-seq-no": am.alarmUploadSeqNo})
+			"upload-no-of-cmds": am.alarmUploadNoOfCmdsOrMEs, "upload-seq-no": am.alarmUploadSeqNo})
 		am.onuAlarmManagerLock.Unlock()
 		go failureTransition()
 	}
@@ -487,11 +488,30 @@
 			logger.Debugw(ctx, "alarm-sync-fsm-cannot-go-to-state-failure", log.Fields{"device-id": am.deviceID, "err": err})
 		}
 	}
+	if msg.OmciMsg.DeviceIdentifier == omci.ExtendedIdent {
+		logger.Debugw(ctx, "get-all-alarms-next-response-additional-data",
+			log.Fields{"device-id": am.deviceID, "additional-data": msgObj.AdditionalAlarms})
+
+		for _, additionalAlarmReport := range msgObj.AdditionalAlarms {
+			meClassID := additionalAlarmReport.AlarmEntityClass
+			meEntityID := additionalAlarmReport.AlarmEntityInstance
+			meAlarmBitMap := additionalAlarmReport.AlarmBitMap
+
+			am.onuAlarmManagerLock.Lock()
+			am.onuDBCopy[meAlarmKey{
+				classID:    meClassID,
+				instanceID: meEntityID,
+			}] = meAlarmBitMap
+			am.onuAlarmManagerLock.Unlock()
+
+			am.IncrementAlarmUploadSeqNo()
+		}
+	}
 	am.onuAlarmManagerLock.RLock()
-	if am.alarmUploadSeqNo < am.alarmUploadNoOfCmds {
+	if am.alarmUploadSeqNo < am.alarmUploadNoOfCmdsOrMEs {
 		am.onuAlarmManagerLock.RUnlock()
 		if err := am.pOnuDeviceEntry.GetDevOmciCC().SendGetAllAlarmNext(
-			log.WithSpanFromContext(context.TODO(), ctx), am.pDeviceHandler.GetOmciTimeout(), true); err != nil {
+			log.WithSpanFromContext(context.TODO(), ctx), am.pDeviceHandler.GetOmciTimeout(), true, am.isExtendedOmci); err != nil {
 			// Transition to failure
 			go failureTransition()
 		} //TODO: needs to handle timeouts
@@ -524,6 +544,8 @@
 		am.activeAlarms = make(map[alarmInfo]struct{})
 	}
 	am.alarmBitMapDB = make(map[meAlarmKey][alarmBitMapSizeBytes]byte)
+	// when instantiating alarm manager it was too early, but now we can check for ONU's extended OMCI support
+	am.isExtendedOmci = am.pOnuDeviceEntry.GetPersIsExtOmciSupported()
 	am.onuAlarmManagerLock.Unlock()
 	am.flushAlarmSyncChannels(ctx) // Need to do this first as there might be stale data on the channels and the start state waits on same channels
 
@@ -778,7 +800,7 @@
 func (am *OnuAlarmManager) ResetAlarmUploadCounters() {
 	am.onuAlarmManagerLock.Lock()
 	am.alarmUploadSeqNo = 0
-	am.alarmUploadNoOfCmds = 0
+	am.alarmUploadNoOfCmdsOrMEs = 0
 	am.onuAlarmManagerLock.Unlock()
 }
 
diff --git a/internal/pkg/common/omci_cc.go b/internal/pkg/common/omci_cc.go
index ef7711b..a47ca1a 100755
--- a/internal/pkg/common/omci_cc.go
+++ b/internal/pkg/common/omci_cc.go
@@ -959,55 +959,99 @@
 }
 
 // SendGetAllAlarm gets all alarm ME instances
-func (oo *OmciCC) SendGetAllAlarm(ctx context.Context, alarmRetreivalMode uint8, timeout int, highPrio bool) error {
+func (oo *OmciCC) SendGetAllAlarm(ctx context.Context, alarmRetreivalMode uint8, timeout int, highPrio bool, isExtendedOmci bool) error {
 	logger.Debugw(ctx, "send GetAllAlarms-msg to:", log.Fields{"device-id": oo.deviceID})
+
+	tid := oo.GetNextTid(highPrio)
+	omciLayer := &omci.OMCI{
+		TransactionID: tid,
+		MessageType:   omci.GetAllAlarmsRequestType,
+		// DeviceIdentifier: omci.BaselineIdent,		// Optional, defaults to Baseline
+	}
+	if isExtendedOmci {
+		omciLayer.DeviceIdentifier = omci.ExtendedIdent
+	}
 	request := &omci.GetAllAlarmsRequest{
 		MeBasePacket: omci.MeBasePacket{
 			EntityClass: me.OnuDataClassID,
+			Extended:    isExtendedOmci,
 		},
 		AlarmRetrievalMode: byte(alarmRetreivalMode),
 	}
-	tid := oo.GetNextTid(highPrio)
-	pkt, err := Serialize(ctx, omci.GetAllAlarmsRequestType, request, tid)
+	var options gopacket.SerializeOptions
+	options.FixLengths = true
+	buffer := gopacket.NewSerializeBuffer()
+	err := gopacket.SerializeLayers(buffer, options, omciLayer, request)
 	if err != nil {
-		logger.Errorw(ctx, "Cannot serialize GetAllAlarmsRequest", log.Fields{
-			"Err": err, "device-id": oo.deviceID})
+		logger.Errorw(ctx, "Cannot serialize GetAllAlarmsRequest", log.Fields{"Err": err,
+			"device-id": oo.deviceID})
 		return err
 	}
+	outgoingPacket := buffer.Bytes()
+
 	oo.pOnuAlarmManager.ResetAlarmUploadCounters()
 
 	omciRxCallbackPair := CallbackPair{
 		CbKey:   tid,
 		CbEntry: CallbackPairEntry{oo.pOnuAlarmManager.GetAlarmMgrEventChannel(), oo.receiveOmciResponse, true},
 	}
-	return oo.Send(ctx, pkt, timeout, CDefaultRetries, highPrio, omciRxCallbackPair)
+	err = oo.Send(ctx, outgoingPacket, timeout, CDefaultRetries, highPrio, omciRxCallbackPair)
+	if err != nil {
+		logger.Errorw(ctx, "Cannot send GetAllAlarmsRequest", log.Fields{"Err": err,
+			"device-id": oo.deviceID})
+		return err
+	}
+	logger.Debug(ctx, "send GetAllAlarmsRequest done")
+	return nil
 }
 
 // SendGetAllAlarmNext gets next alarm ME instance
-func (oo *OmciCC) SendGetAllAlarmNext(ctx context.Context, timeout int, highPrio bool) error {
+func (oo *OmciCC) SendGetAllAlarmNext(ctx context.Context, timeout int, highPrio bool, isExtendedOmci bool) error {
 	alarmUploadSeqNo := oo.pOnuAlarmManager.GetAlarmUploadSeqNo()
 	logger.Debugw(ctx, "send SendGetAllAlarmNext-msg to:", log.Fields{"device-id": oo.deviceID,
 		"alarmUploadSeqNo": alarmUploadSeqNo})
+
+	tid := oo.GetNextTid(highPrio)
+	omciLayer := &omci.OMCI{
+		TransactionID: tid,
+		MessageType:   omci.GetAllAlarmsNextRequestType,
+		// DeviceIdentifier: omci.BaselineIdent,		// Optional, defaults to Baseline
+	}
+	if isExtendedOmci {
+		omciLayer.DeviceIdentifier = omci.ExtendedIdent
+	}
 	request := &omci.GetAllAlarmsNextRequest{
 		MeBasePacket: omci.MeBasePacket{
 			EntityClass: me.OnuDataClassID,
+			Extended:    isExtendedOmci,
 		},
 		CommandSequenceNumber: alarmUploadSeqNo,
 	}
-	tid := oo.GetNextTid(highPrio)
-	pkt, err := Serialize(ctx, omci.GetAllAlarmsNextRequestType, request, tid)
+	var options gopacket.SerializeOptions
+	options.FixLengths = true
+	buffer := gopacket.NewSerializeBuffer()
+	err := gopacket.SerializeLayers(buffer, options, omciLayer, request)
 	if err != nil {
-		logger.Errorw(ctx, "Cannot serialize GetAllAlarmsNextRequest", log.Fields{
-			"Err": err, "device-id": oo.deviceID})
+		logger.Errorw(ctx, "Cannot serialize GetAllAlarmsNextRequest", log.Fields{"Err": err,
+			"device-id": oo.deviceID})
 		return err
 	}
+	outgoingPacket := buffer.Bytes()
+
 	oo.pOnuAlarmManager.IncrementAlarmUploadSeqNo()
 
 	omciRxCallbackPair := CallbackPair{
 		CbKey:   tid,
 		CbEntry: CallbackPairEntry{oo.pOnuAlarmManager.GetAlarmMgrEventChannel(), oo.receiveOmciResponse, true},
 	}
-	return oo.Send(ctx, pkt, timeout, CDefaultRetries, highPrio, omciRxCallbackPair)
+	err = oo.Send(ctx, outgoingPacket, timeout, CDefaultRetries, highPrio, omciRxCallbackPair)
+	if err != nil {
+		logger.Errorw(ctx, "Cannot send GetAllAlarmsNextRequest", log.Fields{"Err": err,
+			"device-id": oo.deviceID})
+		return err
+	}
+	logger.Debug(ctx, "send GetAllAlarmsNextRequest done")
+	return nil
 }
 
 // SendCreateGalEthernetProfile creates GalEthernetProfile ME instance
diff --git a/vendor/github.com/opencord/omci-lib-go/v2/VERSION b/vendor/github.com/opencord/omci-lib-go/v2/VERSION
index ccbccc3..c043eea 100644
--- a/vendor/github.com/opencord/omci-lib-go/v2/VERSION
+++ b/vendor/github.com/opencord/omci-lib-go/v2/VERSION
@@ -1 +1 @@
-2.2.0
+2.2.1
diff --git a/vendor/github.com/opencord/omci-lib-go/v2/alarms.go b/vendor/github.com/opencord/omci-lib-go/v2/alarms.go
index 2bf61b5..2bb163c 100644
--- a/vendor/github.com/opencord/omci-lib-go/v2/alarms.go
+++ b/vendor/github.com/opencord/omci-lib-go/v2/alarms.go
@@ -21,6 +21,7 @@
 	"encoding/binary"
 	"errors"
 	"fmt"
+
 	"github.com/google/gopacket"
 	me "github.com/opencord/omci-lib-go/v2/generated"
 )
@@ -513,7 +514,7 @@
 		contentLength += 2 // Length field
 		if omci.AdditionalAlarms != nil {
 			extraMEs = len(omci.AdditionalAlarms)
-			contentLength += extraMEs*4 + 28
+			contentLength += extraMEs * (4 + 28)
 		}
 	}
 	if contentLength > maxLength {
diff --git a/vendor/modules.txt b/vendor/modules.txt
index c2c7606..80eff4a 100644
--- a/vendor/modules.txt
+++ b/vendor/modules.txt
@@ -133,7 +133,7 @@
 # github.com/looplab/fsm v0.2.0
 ## explicit
 github.com/looplab/fsm
-# github.com/opencord/omci-lib-go/v2 v2.2.0
+# github.com/opencord/omci-lib-go/v2 v2.2.1
 ## explicit
 github.com/opencord/omci-lib-go/v2
 github.com/opencord/omci-lib-go/v2/generated