diff --git a/internal/pkg/mib/onu_device_entry.go b/internal/pkg/mib/onu_device_entry.go
new file mode 100755
index 0000000..ebf8de8
--- /dev/null
+++ b/internal/pkg/mib/onu_device_entry.go
@@ -0,0 +1,992 @@
+/*
+ * Copyright 2020-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+//Package mib provides the utilities for managing the onu mib
+package mib
+
+import (
+	"context"
+	"encoding/json"
+	"errors"
+	"fmt"
+	"sync"
+	"time"
+
+	"github.com/looplab/fsm"
+	"github.com/opencord/omci-lib-go"
+	me "github.com/opencord/omci-lib-go/generated"
+	"github.com/opencord/voltha-lib-go/v7/pkg/db"
+	"github.com/opencord/voltha-lib-go/v7/pkg/db/kvstore"
+	vgrpc "github.com/opencord/voltha-lib-go/v7/pkg/grpc"
+
+	"github.com/opencord/voltha-lib-go/v7/pkg/log"
+
+	cmn "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/common"
+	devdb "github.com/opencord/voltha-openonu-adapter-go/internal/pkg/devdb"
+	"github.com/opencord/voltha-openonu-adapter-go/internal/pkg/swupg"
+)
+
+// events of MibUpload FSM
+const (
+	UlEvStart              = "UlEvStart"
+	UlEvResetMib           = "UlEvResetMib"
+	UlEvGetVendorAndSerial = "UlEvGetVendorAndSerial"
+	UlEvGetEquipmentID     = "UlEvGetEquipmentId"
+	UlEvGetFirstSwVersion  = "UlEvGetFirstSwVersion"
+	UlEvGetSecondSwVersion = "UlEvGetSecondSwVersion"
+	UlEvGetMacAddress      = "UlEvGetMacAddress"
+	UlEvGetMibTemplate     = "UlEvGetMibTemplate"
+	UlEvUploadMib          = "UlEvUploadMib"
+	UlEvExamineMds         = "UlEvExamineMds"
+	UlEvSuccess            = "UlEvSuccess"
+	UlEvMismatch           = "UlEvMismatch"
+	UlEvAuditMib           = "UlEvAuditMib"
+	UlEvForceResync        = "UlEvForceResync"
+	UlEvDiffsFound         = "UlEvDiffsFound"
+	UlEvTimeout            = "UlEvTimeout"
+	UlEvStop               = "UlEvStop"
+)
+
+// states of MibUpload FSM
+const (
+	UlStDisabled               = "UlStDisabled"
+	UlStStarting               = "UlStStarting"
+	UlStResettingMib           = "UlStResettingMib"
+	UlStGettingVendorAndSerial = "UlStGettingVendorAndSerial"
+	UlStGettingEquipmentID     = "UlStGettingEquipmentID"
+	UlStGettingFirstSwVersion  = "UlStGettingFirstSwVersion"
+	UlStGettingSecondSwVersion = "UlStGettingSecondSwVersion"
+	UlStGettingMacAddress      = "UlStGettingMacAddress"
+	UlStGettingMibTemplate     = "UlStGettingMibTemplate"
+	UlStUploading              = "UlStUploading"
+	UlStUploadDone             = "UlStUploadDone"
+	UlStInSync                 = "UlStInSync"
+	UlStExaminingMds           = "UlStExaminingMds"
+	UlStResynchronizing        = "UlStResynchronizing"
+	UlStExaminingMdsSuccess    = "UlStExaminingMdsSuccess"
+	UlStAuditing               = "UlStAuditing"
+	UlStReAuditing             = "UlStReAuditing"
+	UlStOutOfSync              = "UlStOutOfSync"
+)
+
+// CMibUlFsmIdleState - TODO: add comment
+const CMibUlFsmIdleState = UlStInSync
+
+// events of MibDownload FSM
+const (
+	DlEvStart         = "DlEvStart"
+	DlEvCreateGal     = "DlEvCreateGal"
+	DlEvRxGalResp     = "DlEvRxGalResp"
+	DlEvRxOnu2gResp   = "DlEvRxOnu2gResp"
+	DlEvRxBridgeResp  = "DlEvRxBridgeResp"
+	DlEvTimeoutSimple = "DlEvTimeoutSimple"
+	DlEvTimeoutBridge = "DlEvTimeoutBridge"
+	DlEvReset         = "DlEvReset"
+	DlEvRestart       = "DlEvRestart"
+)
+
+// states of MibDownload FSM
+const (
+	DlStDisabled     = "DlStDisabled"
+	DlStStarting     = "DlStStarting"
+	DlStCreatingGal  = "DlStCreatingGal"
+	DlStSettingOnu2g = "DlStSettingOnu2g"
+	DlStBridgeInit   = "DlStBridgeInit"
+	DlStDownloaded   = "DlStDownloaded"
+	DlStResetting    = "DlStResetting"
+)
+
+// CMibDlFsmIdleState - TODO: add comment
+const CMibDlFsmIdleState = DlStDisabled
+
+const (
+	// NOTE that this hardcoded to service/voltha as the MIB template is shared across stacks
+	cBasePathMibTemplateKvStore = "service/voltha/omci_mibs/go_templates"
+	cSuffixMibTemplateKvStore   = "%s/%s/%s"
+	cBasePathOnuKVStore         = "%s/openonu"
+)
+
+const cEmptyMacAddrString = "000000000000"
+const cEmptySerialNumberString = "0000000000000000"
+
+type uniPersConfig struct {
+	PersUniID      uint8                   `json:"uni_id"`
+	PersTpPathMap  map[uint8]string        `json:"PersTpPathMap"` // tp-id to tp-path map
+	PersFlowParams []cmn.UniVlanFlowParams `json:"flow_params"`   //as defined in omci_ani_config.go
+}
+
+type onuPersistentData struct {
+	PersOnuID              uint32            `json:"onu_id"`
+	PersIntfID             uint32            `json:"intf_id"`
+	PersSerialNumber       string            `json:"serial_number"`
+	PersMacAddress         string            `json:"mac_address"`
+	PersVendorID           string            `json:"vendor_id"`
+	PersEquipmentID        string            `json:"equipment_id"`
+	PersActiveSwVersion    string            `json:"active_sw_version"`
+	PersAdminState         string            `json:"admin_state"`
+	PersOperState          string            `json:"oper_state"`
+	PersUniUnlockDone      bool              `json:"uni_unlock_done"`
+	PersUniDisableDone     bool              `json:"uni_disable_done"`
+	PersMibAuditInterval   time.Duration     `json:"mib_audit_interval"`
+	PersMibLastDbSync      uint32            `json:"mib_last_db_sync"`
+	PersMibDataSyncAdpt    uint8             `json:"mib_data_sync_adpt"`
+	PersUniConfig          []uniPersConfig   `json:"uni_config"`
+	PersAlarmAuditInterval time.Duration     `json:"alarm_audit_interval"`
+	PersTcontMap           map[uint16]uint16 `json:"tcont_map"` //alloc-id to me-instance-id map
+}
+
+// OnuDeviceEntry - ONU device info and FSM events.
+type OnuDeviceEntry struct {
+	deviceID                   string
+	baseDeviceHandler          cmn.IdeviceHandler
+	pOpenOnuAc                 cmn.IopenONUAC
+	pOnuTP                     cmn.IonuUniTechProf
+	coreClient                 *vgrpc.Client
+	PDevOmciCC                 *cmn.OmciCC
+	pOnuDB                     *devdb.OnuDeviceDB
+	mibTemplateKVStore         *db.Backend
+	MutexPersOnuConfig         sync.RWMutex
+	SOnuPersistentData         onuPersistentData
+	reconcilingFlows           bool
+	mutexReconcilingFlowsFlag  sync.RWMutex
+	chReconcilingFlowsFinished chan bool //channel to indicate that reconciling of flows has been finished
+	mibTemplatePath            string
+	mutexOnuKVStore            sync.RWMutex
+	onuKVStore                 *db.Backend
+	onuKVStorePath             string
+	mutexOnuKVStoreProcResult  sync.RWMutex
+	onuKVStoreProcResult       error //error indication of processing
+	chOnuKvProcessingStep      chan uint8
+	mutexOnuSwImageIndications sync.RWMutex
+	onuSwImageIndications      cmn.SswImageIndications
+	MutexOnuImageStatus        sync.RWMutex
+	POnuImageStatus            *swupg.OnuImageStatus
+	//lockDeviceEntries           sync.RWMutex
+	mibDbClass    func(context.Context) error
+	supportedFsms cmn.OmciDeviceFsms
+	devState      cmn.OnuDeviceEvent
+	// Audit and MDS
+	mibAuditInterval   time.Duration
+	alarmAuditInterval time.Duration
+	// TODO: periodical mib resync will be implemented with story VOL-3792
+	//mibNextDbResync uint32
+
+	// for mibUpload
+	PMibUploadFsm          *cmn.AdapterFsm //could be handled dynamically and more general as pcmn.AdapterFsm - perhaps later
+	mutexLastTxParamStruct sync.RWMutex
+	lastTxParamStruct      sLastTxMeParameter
+	// for mibDownload
+	PMibDownloadFsm *cmn.AdapterFsm //could be handled dynamically and more general as pcmn.AdapterFsm - perhaps later
+	//remark: general usage of pAdapterFsm would require generalization of CommChan  usage and internal event setting
+	//  within the FSM event procedures
+	mutexPLastTxMeInstance           sync.RWMutex
+	pLastTxMeInstance                *me.ManagedEntity
+	omciMessageReceived              chan bool        //seperate channel needed by DownloadFsm
+	omciRebootMessageReceivedChannel chan cmn.Message // channel needed by reboot request
+
+	mutexTcontMap sync.RWMutex
+}
+
+//NewOnuDeviceEntry returns a new instance of a OnuDeviceEntry
+//mib_db (as well as not inluded alarm_db not really used in this code? VERIFY!!)
+func NewOnuDeviceEntry(ctx context.Context, cc *vgrpc.Client, dh cmn.IdeviceHandler,
+	openonu cmn.IopenONUAC) *OnuDeviceEntry {
+	var onuDeviceEntry OnuDeviceEntry
+	onuDeviceEntry.deviceID = dh.GetDeviceID()
+	logger.Debugw(ctx, "init-onuDeviceEntry", log.Fields{"device-id": onuDeviceEntry.deviceID})
+	onuDeviceEntry.baseDeviceHandler = dh
+	onuDeviceEntry.pOpenOnuAc = openonu
+	onuDeviceEntry.coreClient = cc
+	onuDeviceEntry.devState = cmn.DeviceStatusInit
+	onuDeviceEntry.SOnuPersistentData.PersUniConfig = make([]uniPersConfig, 0)
+	onuDeviceEntry.SOnuPersistentData.PersTcontMap = make(map[uint16]uint16)
+	onuDeviceEntry.chReconcilingFlowsFinished = make(chan bool)
+	onuDeviceEntry.reconcilingFlows = false
+	onuDeviceEntry.chOnuKvProcessingStep = make(chan uint8)
+	onuDeviceEntry.omciRebootMessageReceivedChannel = make(chan cmn.Message, 2048)
+	//openomciagent.lockDeviceHandlersMap = sync.RWMutex{}
+	//OMCI related databases are on a per-agent basis. State machines and tasks
+	//are per ONU Vendor
+	//
+	// MIB Synchronization Database - possible overloading from arguments
+	supportedFsms := onuDeviceEntry.pOpenOnuAc.GetSupportedFsms()
+	if supportedFsms != nil {
+		onuDeviceEntry.supportedFsms = *supportedFsms
+	} else {
+		// This branch is currently not used and is for potential future usage of alternative MIB Sync FSMs only!
+		//var mibSyncFsm = NewMibSynchronizer()
+		// use some internal defaults, if not defined from outside
+		onuDeviceEntry.supportedFsms = cmn.OmciDeviceFsms{
+			"mib-synchronizer": {
+				//mibSyncFsm,        // Implements the MIB synchronization state machine
+				DatabaseClass: onuDeviceEntry.mibDbVolatileDict, // Implements volatile ME MIB database
+				//true,                             // Advertise events on OpenOMCI event bus
+				AuditInterval: dh.GetAlarmAuditInterval(), // Time to wait between MIB audits.  0 to disable audits.
+				// map[string]func() error{
+				// 	"mib-upload":    onuDeviceEntry.MibUploadTask,
+				// 	"mib-template":  onuDeviceEntry.MibTemplateTask,
+				// 	"get-mds":       onuDeviceEntry.GetMdsTask,
+				// 	"mib-audit":     onuDeviceEntry.GetMdsTask,
+				// 	"mib-resync":    onuDeviceEntry.MibResyncTask,
+				// 	"mib-reconcile": onuDeviceEntry.MibReconcileTask,
+				// },
+			},
+		}
+	}
+	onuDeviceEntry.mibDbClass = onuDeviceEntry.supportedFsms["mib-synchronizer"].DatabaseClass
+	logger.Debug(ctx, "access2mibDbClass")
+	go onuDeviceEntry.mibDbClass(ctx)
+	if !dh.IsReconciling() {
+		onuDeviceEntry.mibAuditInterval = onuDeviceEntry.supportedFsms["mib-synchronizer"].AuditInterval
+		onuDeviceEntry.SOnuPersistentData.PersMibAuditInterval = onuDeviceEntry.mibAuditInterval
+		onuDeviceEntry.alarmAuditInterval = dh.GetAlarmAuditInterval()
+		onuDeviceEntry.SOnuPersistentData.PersAlarmAuditInterval = onuDeviceEntry.alarmAuditInterval
+	} else {
+		logger.Debugw(ctx, "reconciling - take audit interval from persistent data", log.Fields{"device-id": onuDeviceEntry.deviceID})
+		// TODO: This is a preparation for VOL-VOL-3811 to preserve config history in case of
+		// vendor- or deviceID-specific configurations via voltctl-commands
+		onuDeviceEntry.mibAuditInterval = onuDeviceEntry.SOnuPersistentData.PersMibAuditInterval
+		onuDeviceEntry.alarmAuditInterval = onuDeviceEntry.SOnuPersistentData.PersAlarmAuditInterval
+	}
+	logger.Debugw(ctx, "MibAuditInterval and AlarmAuditInterval is set to", log.Fields{"mib-audit-interval": onuDeviceEntry.mibAuditInterval,
+		"alarm-audit-interval": onuDeviceEntry.alarmAuditInterval})
+	// TODO: periodical mib resync will be implemented with story VOL-3792
+	//onuDeviceEntry.mibNextDbResync = 0
+
+	// Omci related Mib upload sync state machine
+	mibUploadChan := make(chan cmn.Message, 2048)
+	onuDeviceEntry.PMibUploadFsm = cmn.NewAdapterFsm("MibUpload", onuDeviceEntry.deviceID, mibUploadChan)
+	onuDeviceEntry.PMibUploadFsm.PFsm = fsm.NewFSM(
+		UlStDisabled,
+		fsm.Events{
+
+			{Name: UlEvStart, Src: []string{UlStDisabled}, Dst: UlStStarting},
+
+			{Name: UlEvResetMib, Src: []string{UlStStarting}, Dst: UlStResettingMib},
+			{Name: UlEvGetVendorAndSerial, Src: []string{UlStResettingMib}, Dst: UlStGettingVendorAndSerial},
+			{Name: UlEvGetEquipmentID, Src: []string{UlStGettingVendorAndSerial}, Dst: UlStGettingEquipmentID},
+			{Name: UlEvGetFirstSwVersion, Src: []string{UlStGettingEquipmentID}, Dst: UlStGettingFirstSwVersion},
+			{Name: UlEvGetSecondSwVersion, Src: []string{UlStGettingFirstSwVersion}, Dst: UlStGettingSecondSwVersion},
+			{Name: UlEvGetMacAddress, Src: []string{UlStGettingSecondSwVersion}, Dst: UlStGettingMacAddress},
+			{Name: UlEvGetMibTemplate, Src: []string{UlStGettingMacAddress}, Dst: UlStGettingMibTemplate},
+
+			{Name: UlEvUploadMib, Src: []string{UlStGettingMibTemplate}, Dst: UlStUploading},
+			{Name: UlEvExamineMds, Src: []string{UlStStarting}, Dst: UlStExaminingMds},
+
+			{Name: UlEvSuccess, Src: []string{UlStGettingMibTemplate}, Dst: UlStUploadDone},
+			{Name: UlEvSuccess, Src: []string{UlStUploading}, Dst: UlStUploadDone},
+
+			{Name: UlEvSuccess, Src: []string{UlStUploadDone}, Dst: UlStInSync},
+			//{Name: UlEvSuccess, Src: []string{UlStExaminingMds}, Dst: UlStInSync},
+			{Name: UlEvSuccess, Src: []string{UlStExaminingMds}, Dst: UlStExaminingMdsSuccess},
+			// TODO: As long as mib-resynchronizing is not implemented, failed MDS-examination triggers
+			// mib-reset and new provisioning at this point
+			//{Name: UlEvMismatch, Src: []string{UlStExaminingMds}, Dst: UlStResynchronizing},
+			{Name: UlEvMismatch, Src: []string{UlStExaminingMds}, Dst: UlStResettingMib},
+
+			{Name: UlEvSuccess, Src: []string{UlStExaminingMdsSuccess}, Dst: UlStInSync},
+			{Name: UlEvMismatch, Src: []string{UlStExaminingMdsSuccess}, Dst: UlStResettingMib},
+
+			{Name: UlEvAuditMib, Src: []string{UlStInSync}, Dst: UlStAuditing},
+
+			{Name: UlEvSuccess, Src: []string{UlStOutOfSync}, Dst: UlStInSync},
+			{Name: UlEvAuditMib, Src: []string{UlStOutOfSync}, Dst: UlStAuditing},
+
+			{Name: UlEvSuccess, Src: []string{UlStAuditing}, Dst: UlStInSync},
+			{Name: UlEvMismatch, Src: []string{UlStAuditing}, Dst: UlStReAuditing},
+			{Name: UlEvForceResync, Src: []string{UlStAuditing}, Dst: UlStResynchronizing},
+
+			{Name: UlEvSuccess, Src: []string{UlStReAuditing}, Dst: UlStInSync},
+			{Name: UlEvMismatch, Src: []string{UlStReAuditing}, Dst: UlStResettingMib},
+
+			{Name: UlEvSuccess, Src: []string{UlStResynchronizing}, Dst: UlStInSync},
+			{Name: UlEvDiffsFound, Src: []string{UlStResynchronizing}, Dst: UlStOutOfSync},
+
+			{Name: UlEvTimeout, Src: []string{UlStResettingMib, UlStGettingVendorAndSerial, UlStGettingEquipmentID, UlStGettingFirstSwVersion,
+				UlStGettingSecondSwVersion, UlStGettingMacAddress, UlStGettingMibTemplate, UlStUploading, UlStResynchronizing, UlStExaminingMds,
+				UlStUploadDone, UlStInSync, UlStOutOfSync, UlStAuditing, UlStReAuditing}, Dst: UlStStarting},
+
+			{Name: UlEvStop, Src: []string{UlStStarting, UlStResettingMib, UlStGettingVendorAndSerial, UlStGettingEquipmentID, UlStGettingFirstSwVersion,
+				UlStGettingSecondSwVersion, UlStGettingMacAddress, UlStGettingMibTemplate, UlStUploading, UlStResynchronizing, UlStExaminingMds,
+				UlStUploadDone, UlStInSync, UlStOutOfSync, UlStAuditing, UlStReAuditing}, Dst: UlStDisabled},
+		},
+
+		fsm.Callbacks{
+			"enter_state":                         func(e *fsm.Event) { onuDeviceEntry.PMibUploadFsm.LogFsmStateChange(ctx, e) },
+			"enter_" + UlStStarting:               func(e *fsm.Event) { onuDeviceEntry.enterStartingState(ctx, e) },
+			"enter_" + UlStResettingMib:           func(e *fsm.Event) { onuDeviceEntry.enterResettingMibState(ctx, e) },
+			"enter_" + UlStGettingVendorAndSerial: func(e *fsm.Event) { onuDeviceEntry.enterGettingVendorAndSerialState(ctx, e) },
+			"enter_" + UlStGettingEquipmentID:     func(e *fsm.Event) { onuDeviceEntry.enterGettingEquipmentIDState(ctx, e) },
+			"enter_" + UlStGettingFirstSwVersion:  func(e *fsm.Event) { onuDeviceEntry.enterGettingFirstSwVersionState(ctx, e) },
+			"enter_" + UlStGettingSecondSwVersion: func(e *fsm.Event) { onuDeviceEntry.enterGettingSecondSwVersionState(ctx, e) },
+			"enter_" + UlStGettingMacAddress:      func(e *fsm.Event) { onuDeviceEntry.enterGettingMacAddressState(ctx, e) },
+			"enter_" + UlStGettingMibTemplate:     func(e *fsm.Event) { onuDeviceEntry.enterGettingMibTemplateState(ctx, e) },
+			"enter_" + UlStUploading:              func(e *fsm.Event) { onuDeviceEntry.enterUploadingState(ctx, e) },
+			"enter_" + UlStUploadDone:             func(e *fsm.Event) { onuDeviceEntry.enterUploadDoneState(ctx, e) },
+			"enter_" + UlStExaminingMds:           func(e *fsm.Event) { onuDeviceEntry.enterExaminingMdsState(ctx, e) },
+			"enter_" + UlStResynchronizing:        func(e *fsm.Event) { onuDeviceEntry.enterResynchronizingState(ctx, e) },
+			"enter_" + UlStExaminingMdsSuccess:    func(e *fsm.Event) { onuDeviceEntry.enterExaminingMdsSuccessState(ctx, e) },
+			"enter_" + UlStAuditing:               func(e *fsm.Event) { onuDeviceEntry.enterAuditingState(ctx, e) },
+			"enter_" + UlStReAuditing:             func(e *fsm.Event) { onuDeviceEntry.enterReAuditingState(ctx, e) },
+			"enter_" + UlStOutOfSync:              func(e *fsm.Event) { onuDeviceEntry.enterOutOfSyncState(ctx, e) },
+			"enter_" + UlStInSync:                 func(e *fsm.Event) { onuDeviceEntry.enterInSyncState(ctx, e) },
+		},
+	)
+	// Omci related Mib download state machine
+	mibDownloadChan := make(chan cmn.Message, 2048)
+	onuDeviceEntry.PMibDownloadFsm = cmn.NewAdapterFsm("MibDownload", onuDeviceEntry.deviceID, mibDownloadChan)
+	onuDeviceEntry.PMibDownloadFsm.PFsm = fsm.NewFSM(
+		DlStDisabled,
+		fsm.Events{
+
+			{Name: DlEvStart, Src: []string{DlStDisabled}, Dst: DlStStarting},
+
+			{Name: DlEvCreateGal, Src: []string{DlStStarting}, Dst: DlStCreatingGal},
+			{Name: DlEvRxGalResp, Src: []string{DlStCreatingGal}, Dst: DlStSettingOnu2g},
+			{Name: DlEvRxOnu2gResp, Src: []string{DlStSettingOnu2g}, Dst: DlStBridgeInit},
+			// the bridge state is used for multi ME config for alle UNI related ports
+			// maybe such could be reflected in the state machine as well (port number parametrized)
+			// but that looks not straightforward here - so we keep it simple here for the beginning(?)
+			{Name: DlEvRxBridgeResp, Src: []string{DlStBridgeInit}, Dst: DlStDownloaded},
+
+			{Name: DlEvTimeoutSimple, Src: []string{DlStCreatingGal, DlStSettingOnu2g}, Dst: DlStStarting},
+			{Name: DlEvTimeoutBridge, Src: []string{DlStBridgeInit}, Dst: DlStStarting},
+
+			{Name: DlEvReset, Src: []string{DlStStarting, DlStCreatingGal, DlStSettingOnu2g,
+				DlStBridgeInit, DlStDownloaded}, Dst: DlStResetting},
+			// exceptional treatment for all states except DlStResetting
+			{Name: DlEvRestart, Src: []string{DlStStarting, DlStCreatingGal, DlStSettingOnu2g,
+				DlStBridgeInit, DlStDownloaded, DlStResetting}, Dst: DlStDisabled},
+		},
+
+		fsm.Callbacks{
+			"enter_state":               func(e *fsm.Event) { onuDeviceEntry.PMibDownloadFsm.LogFsmStateChange(ctx, e) },
+			"enter_" + DlStStarting:     func(e *fsm.Event) { onuDeviceEntry.enterDLStartingState(ctx, e) },
+			"enter_" + DlStCreatingGal:  func(e *fsm.Event) { onuDeviceEntry.enterCreatingGalState(ctx, e) },
+			"enter_" + DlStSettingOnu2g: func(e *fsm.Event) { onuDeviceEntry.enterSettingOnu2gState(ctx, e) },
+			"enter_" + DlStBridgeInit:   func(e *fsm.Event) { onuDeviceEntry.enterBridgeInitState(ctx, e) },
+			"enter_" + DlStDownloaded:   func(e *fsm.Event) { onuDeviceEntry.enterDownloadedState(ctx, e) },
+			"enter_" + DlStResetting:    func(e *fsm.Event) { onuDeviceEntry.enterResettingState(ctx, e) },
+		},
+	)
+	if onuDeviceEntry.PMibDownloadFsm == nil || onuDeviceEntry.PMibDownloadFsm.PFsm == nil {
+		logger.Errorw(ctx, "MibDownloadFsm could not be instantiated", log.Fields{"device-id": onuDeviceEntry.deviceID})
+		// TODO some specific error treatment - or waiting for crash ?
+	}
+
+	onuDeviceEntry.mibTemplateKVStore = onuDeviceEntry.baseDeviceHandler.SetBackend(ctx, cBasePathMibTemplateKvStore)
+	if onuDeviceEntry.mibTemplateKVStore == nil {
+		logger.Errorw(ctx, "Can't access mibTemplateKVStore - no backend connection to service",
+			log.Fields{"device-id": onuDeviceEntry.deviceID, "service": cBasePathMibTemplateKvStore})
+	}
+
+	onuDeviceEntry.onuKVStorePath = onuDeviceEntry.deviceID
+	baseKvStorePath := fmt.Sprintf(cBasePathOnuKVStore, dh.GetBackendPathPrefix())
+	onuDeviceEntry.onuKVStore = onuDeviceEntry.baseDeviceHandler.SetBackend(ctx, baseKvStorePath)
+	if onuDeviceEntry.onuKVStore == nil {
+		logger.Errorw(ctx, "Can't access onuKVStore - no backend connection to service",
+			log.Fields{"device-id": onuDeviceEntry.deviceID, "service": baseKvStorePath})
+	}
+
+	// Alarm Synchronization Database
+
+	//self._alarm_db = None
+	//self._alarm_database_cls = support_classes['alarm-synchronizer']['database']
+	return &onuDeviceEntry
+}
+
+//Start starts (logs) the omci agent
+func (oo *OnuDeviceEntry) Start(ctx context.Context) error {
+	logger.Debugw(ctx, "OnuDeviceEntry-starting", log.Fields{"for device-id": oo.deviceID})
+	if oo.PDevOmciCC == nil {
+		oo.PDevOmciCC = cmn.NewOmciCC(ctx, oo.deviceID, oo.baseDeviceHandler, oo, oo.baseDeviceHandler.GetOnuAlarmManager(), oo.coreClient)
+		if oo.PDevOmciCC == nil {
+			logger.Errorw(ctx, "Could not create devOmciCc - abort", log.Fields{"for device-id": oo.deviceID})
+			return fmt.Errorf("could not create devOmciCc %s", oo.deviceID)
+		}
+	}
+	return nil
+}
+
+//Stop stops/resets the omciCC
+func (oo *OnuDeviceEntry) Stop(ctx context.Context, abResetOmciCC bool) error {
+	logger.Debugw(ctx, "OnuDeviceEntry-stopping", log.Fields{"for device-id": oo.deviceID})
+	if abResetOmciCC && (oo.PDevOmciCC != nil) {
+		_ = oo.PDevOmciCC.Stop(ctx)
+	}
+	//to allow for all event notifications again when re-using the device and omciCC
+	oo.devState = cmn.DeviceStatusInit
+	return nil
+}
+
+// Reboot - TODO: add comment
+func (oo *OnuDeviceEntry) Reboot(ctx context.Context) error {
+	logger.Debugw(ctx, "OnuDeviceEntry-rebooting", log.Fields{"for device-id": oo.deviceID})
+	if oo.PDevOmciCC != nil {
+		if err := oo.PDevOmciCC.SendReboot(ctx, oo.baseDeviceHandler.GetOmciTimeout(), true, oo.omciRebootMessageReceivedChannel); err != nil {
+			logger.Errorw(ctx, "onu didn't reboot", log.Fields{"for device-id": oo.deviceID})
+			return err
+		}
+	}
+	return nil
+}
+
+// WaitForRebootResponse - TODO: add comment
+func (oo *OnuDeviceEntry) WaitForRebootResponse(ctx context.Context, responseChannel chan cmn.Message) error {
+	select {
+	case <-time.After(oo.PDevOmciCC.GetMaxOmciTimeoutWithRetries() * time.Second): //3s was detected to be to less in 8*8 bbsim test with debug Info/Debug
+		logger.Warnw(ctx, "reboot timeout", log.Fields{"for device-id": oo.deviceID})
+		return fmt.Errorf("rebootTimeout")
+	case data := <-responseChannel:
+		switch data.Data.(cmn.OmciMessage).OmciMsg.MessageType {
+		case omci.RebootResponseType:
+			{
+				msgLayer := (*data.Data.(cmn.OmciMessage).OmciPacket).Layer(omci.LayerTypeRebootResponse)
+				if msgLayer == nil {
+					return fmt.Errorf("omci Msg layer could not be detected for RebootResponseType")
+				}
+				msgObj, msgOk := msgLayer.(*omci.RebootResponse)
+				if !msgOk {
+					return fmt.Errorf("omci Msg layer could not be assigned for RebootResponseType %s", oo.deviceID)
+				}
+				logger.Debugw(ctx, "RebootResponse data", log.Fields{"device-id": oo.deviceID, "data-fields": msgObj})
+				if msgObj.Result != me.Success {
+					logger.Errorw(ctx, "Omci RebootResponse result error", log.Fields{"device-id": oo.deviceID, "Error": msgObj.Result})
+					// possibly force FSM into abort or ignore some errors for some messages? store error for mgmt display?
+					return fmt.Errorf("omci RebootResponse result error indication %s for device %s",
+						msgObj.Result, oo.deviceID)
+				}
+				return nil
+			}
+		}
+		logger.Warnw(ctx, "Reboot response message type error", log.Fields{"for device-id": oo.deviceID})
+		return fmt.Errorf("unexpected OmciResponse type received %s", oo.deviceID)
+	}
+}
+
+//Relay the InSync message via Handler to Rw core - Status update
+func (oo *OnuDeviceEntry) transferSystemEvent(ctx context.Context, devEvent cmn.OnuDeviceEvent) {
+	logger.Debugw(ctx, "relaying system-event", log.Fields{"Event": devEvent})
+	// decouple the handler transfer from further processing here
+	// TODO!!! check if really no synch is required within the system e.g. to ensure following steps ..
+	if devEvent == cmn.MibDatabaseSync {
+		if oo.devState < cmn.MibDatabaseSync { //devState has not been synced yet
+			oo.devState = cmn.MibDatabaseSync
+			go oo.baseDeviceHandler.DeviceProcStatusUpdate(ctx, devEvent)
+			//TODO!!! device control: next step: start MIB capability verification from here ?!!!
+		} else {
+			logger.Debugw(ctx, "mibinsync-event in some already synced state - ignored", log.Fields{"state": oo.devState})
+		}
+	} else if devEvent == cmn.MibDownloadDone {
+		if oo.devState < cmn.MibDownloadDone { //devState has not been synced yet
+			oo.devState = cmn.MibDownloadDone
+			go oo.baseDeviceHandler.DeviceProcStatusUpdate(ctx, devEvent)
+		} else {
+			logger.Debugw(ctx, "mibdownloaddone-event was already seen - ignored", log.Fields{"state": oo.devState})
+		}
+	} else {
+		logger.Warnw(ctx, "device-event not yet handled", log.Fields{"state": devEvent})
+	}
+}
+
+// RestoreDataFromOnuKvStore - TODO: add comment
+func (oo *OnuDeviceEntry) RestoreDataFromOnuKvStore(ctx context.Context) error {
+	if oo.onuKVStore == nil {
+		logger.Debugw(ctx, "onuKVStore not set - abort", log.Fields{"device-id": oo.deviceID})
+		return fmt.Errorf(fmt.Sprintf("onuKVStore-not-set-abort-%s", oo.deviceID))
+	}
+	oo.MutexPersOnuConfig.Lock()
+	defer oo.MutexPersOnuConfig.Unlock()
+	oo.SOnuPersistentData =
+		onuPersistentData{0, 0, "", "", "", "", "", "", "", false, false, oo.mibAuditInterval, 0, 0, make([]uniPersConfig, 0), oo.alarmAuditInterval, make(map[uint16]uint16)}
+	oo.mutexOnuKVStore.RLock()
+	Value, err := oo.onuKVStore.Get(ctx, oo.onuKVStorePath)
+	oo.mutexOnuKVStore.RUnlock()
+	if err == nil {
+		if Value != nil {
+			logger.Debugw(ctx, "ONU-data read",
+				log.Fields{"Key": Value.Key, "device-id": oo.deviceID})
+			tmpBytes, _ := kvstore.ToByte(Value.Value)
+
+			if err = json.Unmarshal(tmpBytes, &oo.SOnuPersistentData); err != nil {
+				logger.Errorw(ctx, "unable to unmarshal ONU-data", log.Fields{"error": err, "device-id": oo.deviceID})
+				return fmt.Errorf(fmt.Sprintf("unable-to-unmarshal-ONU-data-%s", oo.deviceID))
+			}
+			logger.Debugw(ctx, "ONU-data", log.Fields{"SOnuPersistentData": oo.SOnuPersistentData,
+				"device-id": oo.deviceID})
+		} else {
+			logger.Debugw(ctx, "no ONU-data found", log.Fields{"path": oo.onuKVStorePath, "device-id": oo.deviceID})
+			return fmt.Errorf("no-ONU-data-found")
+		}
+	} else {
+		logger.Errorw(ctx, "unable to read from KVstore", log.Fields{"device-id": oo.deviceID})
+		return fmt.Errorf(fmt.Sprintf("unable-to-read-from-KVstore-%s", oo.deviceID))
+	}
+	return nil
+}
+
+// DeleteDataFromOnuKvStore - TODO: add comment
+func (oo *OnuDeviceEntry) DeleteDataFromOnuKvStore(ctx context.Context, wg *sync.WaitGroup) {
+	defer wg.Done()
+
+	if oo.onuKVStore == nil {
+		logger.Debugw(ctx, "onuKVStore not set - abort", log.Fields{"device-id": oo.deviceID})
+		oo.setKvProcessingErrorIndication(errors.New("onu-data delete aborted: onuKVStore not set"))
+		return
+	}
+	var processingStep uint8 = 1 // used to synchronize the different processing steps with chOnuKvProcessingStep
+	go oo.deletePersistentData(ctx, processingStep)
+	if !oo.waitForTimeoutOrCompletion(ctx, oo.chOnuKvProcessingStep, processingStep) {
+		//timeout or error detected
+		logger.Debugw(ctx, "ONU-data not deleted - abort", log.Fields{"device-id": oo.deviceID})
+		oo.setKvProcessingErrorIndication(errors.New("onu-data delete aborted: during kv-access"))
+		return
+	}
+}
+
+func (oo *OnuDeviceEntry) deletePersistentData(ctx context.Context, aProcessingStep uint8) {
+
+	logger.Debugw(ctx, "delete and clear internal persistency data", log.Fields{"device-id": oo.deviceID})
+
+	oo.MutexPersOnuConfig.Lock()
+	defer oo.MutexPersOnuConfig.Unlock()
+
+	oo.SOnuPersistentData.PersUniConfig = nil //releasing all UniConfig entries to garbage collector default entry
+	oo.SOnuPersistentData =
+		onuPersistentData{0, 0, "", "", "", "", "", "", "", false, false, oo.mibAuditInterval, 0, 0, make([]uniPersConfig, 0), oo.alarmAuditInterval, make(map[uint16]uint16)}
+	logger.Debugw(ctx, "delete ONU-data from KVStore", log.Fields{"device-id": oo.deviceID})
+	oo.mutexOnuKVStore.Lock()
+	err := oo.onuKVStore.Delete(ctx, oo.onuKVStorePath)
+	oo.mutexOnuKVStore.Unlock()
+	if err != nil {
+		logger.Errorw(ctx, "unable to delete in KVstore", log.Fields{"device-id": oo.deviceID, "err": err})
+		oo.chOnuKvProcessingStep <- 0 //error indication
+		return
+	}
+	oo.chOnuKvProcessingStep <- aProcessingStep //done
+}
+
+// UpdateOnuKvStore - TODO: add comment
+func (oo *OnuDeviceEntry) UpdateOnuKvStore(ctx context.Context, wg *sync.WaitGroup) {
+	defer wg.Done()
+
+	if oo.onuKVStore == nil {
+		logger.Debugw(ctx, "onuKVStore not set - abort", log.Fields{"device-id": oo.deviceID})
+		oo.setKvProcessingErrorIndication(errors.New("onu-data update aborted: onuKVStore not set"))
+		return
+	}
+	var processingStep uint8 = 1 // used to synchronize the different processing steps with chOnuKvProcessingStep
+	go oo.storeDataInOnuKvStore(ctx, processingStep)
+	if !oo.waitForTimeoutOrCompletion(ctx, oo.chOnuKvProcessingStep, processingStep) {
+		//timeout or error detected
+		logger.Debugw(ctx, "ONU-data not written - abort", log.Fields{"device-id": oo.deviceID})
+		oo.setKvProcessingErrorIndication(errors.New("onu-data update aborted: during writing process"))
+		return
+	}
+}
+
+func (oo *OnuDeviceEntry) storeDataInOnuKvStore(ctx context.Context, aProcessingStep uint8) {
+
+	oo.MutexPersOnuConfig.Lock()
+	defer oo.MutexPersOnuConfig.Unlock()
+	//assign values which are not already present when NewOnuDeviceEntry() is called
+	onuIndication := oo.baseDeviceHandler.GetOnuIndication()
+	oo.SOnuPersistentData.PersOnuID = onuIndication.OnuId
+	oo.SOnuPersistentData.PersIntfID = onuIndication.IntfId
+	//TODO: verify usage of these values during restart UC
+	oo.SOnuPersistentData.PersAdminState = onuIndication.AdminState
+	oo.SOnuPersistentData.PersOperState = onuIndication.OperState
+
+	logger.Debugw(ctx, "Update ONU-data in KVStore", log.Fields{"device-id": oo.deviceID, "SOnuPersistentData": oo.SOnuPersistentData})
+
+	Value, err := json.Marshal(oo.SOnuPersistentData)
+	if err != nil {
+		logger.Errorw(ctx, "unable to marshal ONU-data", log.Fields{"SOnuPersistentData": oo.SOnuPersistentData,
+			"device-id": oo.deviceID, "err": err})
+		oo.chOnuKvProcessingStep <- 0 //error indication
+		return
+	}
+	oo.pOpenOnuAc.RLockMutexDeviceHandlersMap()
+	if _, exist := oo.pOpenOnuAc.GetDeviceHandler(oo.deviceID); !exist {
+		logger.Debugw(ctx, "delete_device in progress - skip write request", log.Fields{"device-id": oo.deviceID})
+		oo.chOnuKvProcessingStep <- aProcessingStep
+		oo.pOpenOnuAc.RUnlockMutexDeviceHandlersMap()
+		return
+	}
+	oo.baseDeviceHandler.RLockMutexDeletionInProgressFlag()
+	if oo.baseDeviceHandler.GetDeletionInProgress() {
+		logger.Debugw(ctx, "delete_device in progress - skip write request", log.Fields{"device-id": oo.deviceID})
+		oo.chOnuKvProcessingStep <- aProcessingStep
+		oo.pOpenOnuAc.RUnlockMutexDeviceHandlersMap()
+		oo.baseDeviceHandler.RUnlockMutexDeletionInProgressFlag()
+		return
+	}
+	oo.pOpenOnuAc.RUnlockMutexDeviceHandlersMap()
+	oo.baseDeviceHandler.RUnlockMutexDeletionInProgressFlag()
+
+	oo.mutexOnuKVStore.Lock()
+	err = oo.onuKVStore.Put(ctx, oo.onuKVStorePath, Value)
+	oo.mutexOnuKVStore.Unlock()
+	if err != nil {
+		logger.Errorw(ctx, "unable to write ONU-data into KVstore", log.Fields{"device-id": oo.deviceID, "err": err})
+		oo.chOnuKvProcessingStep <- 0 //error indication
+		return
+	}
+	oo.chOnuKvProcessingStep <- aProcessingStep //done
+}
+
+// UpdateOnuUniTpPath - TODO: add comment
+func (oo *OnuDeviceEntry) UpdateOnuUniTpPath(ctx context.Context, aUniID uint8, aTpID uint8, aPathString string) bool {
+	/* within some specific InterAdapter processing request write/read access to data is ensured to be sequentially,
+	   as also the complete sequence is ensured to 'run to completion' before some new request is accepted
+	   no specific concurrency protection to SOnuPersistentData is required here
+	*/
+	oo.MutexPersOnuConfig.Lock()
+	defer oo.MutexPersOnuConfig.Unlock()
+
+	for k, v := range oo.SOnuPersistentData.PersUniConfig {
+		if v.PersUniID == aUniID {
+			existingPath, ok := oo.SOnuPersistentData.PersUniConfig[k].PersTpPathMap[aTpID]
+			logger.Debugw(ctx, "PersUniConfig-entry exists", log.Fields{"device-id": oo.deviceID, "uniID": aUniID,
+				"tpID": aTpID, "path": aPathString, "existingPath": existingPath, "ok": ok})
+			if !ok {
+				logger.Debugw(ctx, "tp-does-not-exist", log.Fields{"device-id": oo.deviceID, "uniID": aUniID, "tpID": aTpID, "path": aPathString})
+			}
+			if existingPath != aPathString {
+				if aPathString == "" {
+					//existing entry to be deleted
+					logger.Debugw(ctx, "UniTp delete path value", log.Fields{"device-id": oo.deviceID, "uniID": aUniID, "path": aPathString})
+					oo.SOnuPersistentData.PersUniConfig[k].PersTpPathMap[aTpID] = ""
+				} else {
+					//existing entry to be modified
+					logger.Debugw(ctx, "UniTp modify path value", log.Fields{"device-id": oo.deviceID, "uniID": aUniID, "path": aPathString})
+					oo.SOnuPersistentData.PersUniConfig[k].PersTpPathMap[aTpID] = aPathString
+				}
+				return true
+			}
+			//entry already exists
+			if aPathString == "" {
+				//no active TechProfile
+				logger.Debugw(ctx, "UniTp path has already been removed - no AniSide config to be removed", log.Fields{
+					"device-id": oo.deviceID, "uniID": aUniID})
+			} else {
+				//the given TechProfile already exists and is assumed to be active - update devReason as if the config has been done here
+				//was needed e.g. in voltha POD Tests:Validate authentication on a disabled ONU
+				//  (as here the TechProfile has not been removed with the disable-device before the new enable-device)
+				logger.Debugw(ctx, "UniTp path already exists - TechProfile supposed to be active", log.Fields{
+					"device-id": oo.deviceID, "uniID": aUniID, "path": aPathString})
+				//no deviceReason update (DeviceProcStatusUpdate) here to ensure 'omci_flows_pushed' state within disable/enable procedure of ATT scenario
+				//  (during which the flows are removed/re-assigned but the techProf is left active)
+				//and as the TechProfile is regarded as active we have to verify, if some flow configuration still waits on it
+				//  (should not be the case, but should not harm or be more robust ...)
+				// and to be sure, that for some reason the corresponding TpDelete was lost somewhere in history
+				//  we also reset a possibly outstanding delete request - repeated TpConfig is regarded as valid for waiting flow config
+				if oo.pOnuTP != nil {
+					oo.pOnuTP.SetProfileToDelete(aUniID, aTpID, false)
+				}
+				go oo.baseDeviceHandler.VerifyVlanConfigRequest(ctx, aUniID, aTpID)
+			}
+			return false //indicate 'no change' - nothing more to do, TechProf inter-adapter message is return with success anyway here
+		}
+	}
+	//no entry exists for uniId
+
+	if aPathString == "" {
+		//delete request in non-existing state , accept as no change
+		logger.Debugw(ctx, "UniTp path already removed", log.Fields{"device-id": oo.deviceID, "uniID": aUniID})
+		return false
+	}
+	//new entry to be created
+	logger.Debugw(ctx, "New UniTp path set", log.Fields{"device-id": oo.deviceID, "uniID": aUniID, "path": aPathString})
+	perSubTpPathMap := make(map[uint8]string)
+	perSubTpPathMap[aTpID] = aPathString
+	oo.SOnuPersistentData.PersUniConfig =
+		append(oo.SOnuPersistentData.PersUniConfig, uniPersConfig{PersUniID: aUniID, PersTpPathMap: perSubTpPathMap, PersFlowParams: make([]cmn.UniVlanFlowParams, 0)})
+	return true
+}
+
+// UpdateOnuUniFlowConfig - TODO: add comment
+func (oo *OnuDeviceEntry) UpdateOnuUniFlowConfig(aUniID uint8, aUniVlanFlowParams *[]cmn.UniVlanFlowParams) {
+
+	oo.MutexPersOnuConfig.Lock()
+	defer oo.MutexPersOnuConfig.Unlock()
+
+	for k, v := range oo.SOnuPersistentData.PersUniConfig {
+		if v.PersUniID == aUniID {
+			oo.SOnuPersistentData.PersUniConfig[k].PersFlowParams = make([]cmn.UniVlanFlowParams, len(*aUniVlanFlowParams))
+			copy(oo.SOnuPersistentData.PersUniConfig[k].PersFlowParams, *aUniVlanFlowParams)
+			return
+		}
+	}
+	//flow update was faster than tp-config - create PersUniConfig-entry
+	//TODO!!: following activity to 'add' some new uni entry might not be quite correct if this function is called to clear the data
+	//  (e.g after flow removal from RemoveUniFlowParams()).
+	//  This has the effect of misleading indication that there is still some active UNI entry, even though there might be only some nil flow entry
+	//  The effect of this flaw is that at TechProfile removal there is an additional attempt to remove the entry even though no techProfile exists anymore
+	//  The code is not changed here because of the current release lane, changes might have unexpected secondary effects, perhaps later with more elaborate tests
+	tmpConfig := uniPersConfig{PersUniID: aUniID, PersTpPathMap: make(map[uint8]string), PersFlowParams: make([]cmn.UniVlanFlowParams, len(*aUniVlanFlowParams))}
+	copy(tmpConfig.PersFlowParams, *aUniVlanFlowParams)
+	oo.SOnuPersistentData.PersUniConfig = append(oo.SOnuPersistentData.PersUniConfig, tmpConfig)
+}
+
+func (oo *OnuDeviceEntry) waitForTimeoutOrCompletion(
+	ctx context.Context, aChOnuProcessingStep <-chan uint8, aProcessingStep uint8) bool {
+	select {
+	case <-ctx.Done():
+		logger.Warnw(ctx, "processing not completed in-time!",
+			log.Fields{"device-id": oo.deviceID, "error": ctx.Err()})
+		return false
+	case rxStep := <-aChOnuProcessingStep:
+		if rxStep == aProcessingStep {
+			return true
+		}
+		//all other values are not accepted - including 0 for error indication
+		logger.Warnw(ctx, "Invalid processing step received: abort!",
+			log.Fields{"device-id": oo.deviceID,
+				"wantedStep": aProcessingStep, "haveStep": rxStep})
+		return false
+	}
+}
+
+// ResetKvProcessingErrorIndication - TODO: add comment
+func (oo *OnuDeviceEntry) ResetKvProcessingErrorIndication() {
+	oo.mutexOnuKVStoreProcResult.Lock()
+	oo.onuKVStoreProcResult = nil
+	oo.mutexOnuKVStoreProcResult.Unlock()
+}
+
+// GetKvProcessingErrorIndication - TODO: add comment
+func (oo *OnuDeviceEntry) GetKvProcessingErrorIndication() error {
+	oo.mutexOnuKVStoreProcResult.RLock()
+	value := oo.onuKVStoreProcResult
+	oo.mutexOnuKVStoreProcResult.RUnlock()
+	return value
+}
+
+func (oo *OnuDeviceEntry) setKvProcessingErrorIndication(value error) {
+	oo.mutexOnuKVStoreProcResult.Lock()
+	oo.onuKVStoreProcResult = value
+	oo.mutexOnuKVStoreProcResult.Unlock()
+}
+
+// IncrementMibDataSync - TODO: add comment
+func (oo *OnuDeviceEntry) IncrementMibDataSync(ctx context.Context) {
+	oo.MutexPersOnuConfig.Lock()
+	defer oo.MutexPersOnuConfig.Unlock()
+	if oo.SOnuPersistentData.PersMibDataSyncAdpt < 255 {
+		oo.SOnuPersistentData.PersMibDataSyncAdpt++
+	} else {
+		// per G.984 and G.988 overflow starts over at 1 given 0 is reserved for reset
+		oo.SOnuPersistentData.PersMibDataSyncAdpt = 1
+	}
+	logger.Debugf(ctx, "mibDataSync updated - mds: %d - device-id: %s", oo.SOnuPersistentData.PersMibDataSyncAdpt, oo.deviceID)
+}
+
+// ModifySwImageInactiveVersion - updates the inactive SW image version stored
+func (oo *OnuDeviceEntry) ModifySwImageInactiveVersion(ctx context.Context, aImageVersion string) {
+	oo.mutexOnuSwImageIndications.Lock()
+	defer oo.mutexOnuSwImageIndications.Unlock()
+	logger.Debugw(ctx, "software-image set inactive version", log.Fields{
+		"device-id": oo.deviceID, "version": aImageVersion})
+	oo.onuSwImageIndications.InActiveEntityEntry.Version = aImageVersion
+	//inactive SW version is not part of persistency data (yet) - no need to update that
+}
+
+// ModifySwImageActiveCommit - updates the active SW commit flag stored
+func (oo *OnuDeviceEntry) ModifySwImageActiveCommit(ctx context.Context, aCommitted uint8) {
+	oo.mutexOnuSwImageIndications.Lock()
+	defer oo.mutexOnuSwImageIndications.Unlock()
+	logger.Debugw(ctx, "software-image set active entity commit flag", log.Fields{
+		"device-id": oo.deviceID, "committed": aCommitted})
+	oo.onuSwImageIndications.ActiveEntityEntry.IsCommitted = aCommitted
+	//commit flag is not part of persistency data (yet) - no need to update that
+}
+
+// GetActiveImageVersion - returns the active SW image version stored
+func (oo *OnuDeviceEntry) GetActiveImageVersion(ctx context.Context) string {
+	oo.mutexOnuSwImageIndications.RLock()
+	if oo.onuSwImageIndications.ActiveEntityEntry.Valid {
+		value := oo.onuSwImageIndications.ActiveEntityEntry.Version
+		oo.mutexOnuSwImageIndications.RUnlock()
+		return value
+	}
+	oo.mutexOnuSwImageIndications.RUnlock()
+	logger.Debugw(ctx, "Active Image is not valid", log.Fields{"device-id": oo.deviceID})
+	return ""
+}
+
+// GetInactiveImageVersion - TODO: add comment
+func (oo *OnuDeviceEntry) GetInactiveImageVersion(ctx context.Context) string {
+	oo.mutexOnuSwImageIndications.RLock()
+	if oo.onuSwImageIndications.InActiveEntityEntry.Valid {
+		value := oo.onuSwImageIndications.InActiveEntityEntry.Version
+		oo.mutexOnuSwImageIndications.RUnlock()
+		return value
+	}
+	oo.mutexOnuSwImageIndications.RUnlock()
+	logger.Debugw(ctx, "Inactive Image is not valid", log.Fields{"device-id": oo.deviceID})
+	return ""
+}
+
+func (oo *OnuDeviceEntry) buildMibTemplatePath() string {
+	oo.MutexPersOnuConfig.RLock()
+	defer oo.MutexPersOnuConfig.RUnlock()
+	return fmt.Sprintf(cSuffixMibTemplateKvStore, oo.SOnuPersistentData.PersVendorID, oo.SOnuPersistentData.PersEquipmentID, oo.SOnuPersistentData.PersActiveSwVersion)
+}
+
+// AllocateFreeTcont - TODO: add comment
+func (oo *OnuDeviceEntry) AllocateFreeTcont(ctx context.Context, allocID uint16) (uint16, bool, error) {
+	logger.Debugw(ctx, "allocate-free-tcont", log.Fields{"device-id": oo.deviceID, "allocID": allocID,
+		"allocated-instances": oo.SOnuPersistentData.PersTcontMap})
+
+	oo.mutexTcontMap.Lock()
+	defer oo.mutexTcontMap.Unlock()
+	if entityID, ok := oo.SOnuPersistentData.PersTcontMap[allocID]; ok {
+		//tcont already allocated before, return the used instance-id
+		return entityID, true, nil
+	}
+	//First allocation of tcont. Find a free instance
+	if tcontInstKeys := oo.pOnuDB.GetSortedInstKeys(ctx, me.TContClassID); len(tcontInstKeys) > 0 {
+		logger.Debugw(ctx, "allocate-free-tcont-db-keys", log.Fields{"device-id": oo.deviceID, "keys": tcontInstKeys})
+		for _, instID := range tcontInstKeys {
+			instExist := false
+			//If this instance exist in map, it means it is not  empty. It is allocated before
+			for _, v := range oo.SOnuPersistentData.PersTcontMap {
+				if v == instID {
+					instExist = true
+					break
+				}
+			}
+			if !instExist {
+				oo.SOnuPersistentData.PersTcontMap[allocID] = instID
+				return instID, false, nil
+			}
+		}
+	}
+	return 0, false, fmt.Errorf(fmt.Sprintf("no-free-tcont-left-for-device-%s", oo.deviceID))
+
+}
+
+// FreeTcont - TODO: add comment
+func (oo *OnuDeviceEntry) FreeTcont(ctx context.Context, allocID uint16) {
+	logger.Debugw(ctx, "free-tcont", log.Fields{"device-id": oo.deviceID, "alloc": allocID})
+	oo.mutexTcontMap.Lock()
+	defer oo.mutexTcontMap.Unlock()
+	delete(oo.SOnuPersistentData.PersTcontMap, allocID)
+}
+
+// GetDevOmciCC - TODO: add comment
+func (oo *OnuDeviceEntry) GetDevOmciCC() *cmn.OmciCC {
+	return oo.PDevOmciCC
+}
+
+// GetOnuDB - TODO: add comment
+func (oo *OnuDeviceEntry) GetOnuDB() *devdb.OnuDeviceDB {
+	return oo.pOnuDB
+}
+
+// GetPersSerialNumber - TODO: add comment
+func (oo *OnuDeviceEntry) GetPersSerialNumber() string {
+	value := oo.SOnuPersistentData.PersSerialNumber
+	return value
+}
+
+// GetPersVendorID - TODO: add comment
+func (oo *OnuDeviceEntry) GetPersVendorID() string {
+	value := oo.SOnuPersistentData.PersVendorID
+	return value
+}
+
+// GetPersEquipmentID - TODO: add comment
+func (oo *OnuDeviceEntry) GetPersEquipmentID() string {
+	value := oo.SOnuPersistentData.PersEquipmentID
+	return value
+}
+
+// GetMibUploadFsmCommChan - TODO: add comment
+func (oo *OnuDeviceEntry) GetMibUploadFsmCommChan() chan cmn.Message {
+	return oo.PMibUploadFsm.CommChan
+}
+
+// GetMibDownloadFsmCommChan - TODO: add comment
+func (oo *OnuDeviceEntry) GetMibDownloadFsmCommChan() chan cmn.Message {
+	return oo.PMibDownloadFsm.CommChan
+}
+
+// GetOmciRebootMsgRevChan - TODO: add comment
+func (oo *OnuDeviceEntry) GetOmciRebootMsgRevChan() chan cmn.Message {
+	return oo.omciRebootMessageReceivedChannel
+}
+
+// LockMutexOnuSwImageIndications - TODO: add comment
+func (oo *OnuDeviceEntry) LockMutexOnuSwImageIndications() {
+	oo.mutexOnuSwImageIndications.Lock()
+}
+
+// UnlockMutexOnuSwImageIndications - TODO: add comment
+func (oo *OnuDeviceEntry) UnlockMutexOnuSwImageIndications() {
+	oo.mutexOnuSwImageIndications.Unlock()
+}
+
+// GetOnuSwImageIndications - TODO: add comment
+func (oo *OnuDeviceEntry) GetOnuSwImageIndications() cmn.SswImageIndications {
+	return oo.onuSwImageIndications
+}
+
+// SetOnuSwImageIndications - TODO: add comment
+func (oo *OnuDeviceEntry) SetOnuSwImageIndications(value cmn.SswImageIndications) {
+	oo.onuSwImageIndications = value
+}
+
+// LockMutexPersOnuConfig - TODO: add comment
+func (oo *OnuDeviceEntry) LockMutexPersOnuConfig() {
+	oo.MutexPersOnuConfig.Lock()
+}
+
+// UnlockMutexPersOnuConfig - TODO: add comment
+func (oo *OnuDeviceEntry) UnlockMutexPersOnuConfig() {
+	oo.MutexPersOnuConfig.Unlock()
+}
+
+// GetPersActiveSwVersion - TODO: add comment
+func (oo *OnuDeviceEntry) GetPersActiveSwVersion() string {
+	return oo.SOnuPersistentData.PersActiveSwVersion
+}
+
+// SetPersActiveSwVersion - TODO: add comment
+func (oo *OnuDeviceEntry) SetPersActiveSwVersion(value string) {
+	oo.SOnuPersistentData.PersActiveSwVersion = value
+}
+
+// SetReconcilingFlows - TODO: add comment
+func (oo *OnuDeviceEntry) SetReconcilingFlows(value bool) {
+	oo.mutexReconcilingFlowsFlag.Lock()
+	oo.reconcilingFlows = value
+	oo.mutexReconcilingFlowsFlag.Unlock()
+}
+
+// SetChReconcilingFlowsFinished - TODO: add comment
+func (oo *OnuDeviceEntry) SetChReconcilingFlowsFinished(value bool) {
+	oo.chReconcilingFlowsFinished <- value
+}
+
+// IsReconcilingFlows - TODO: add comment
+func (oo *OnuDeviceEntry) IsReconcilingFlows() bool {
+	oo.mutexReconcilingFlowsFlag.RLock()
+	value := oo.reconcilingFlows
+	oo.mutexReconcilingFlowsFlag.RUnlock()
+	return value
+}
