/*
 * Copyright (c) 2018 - present.  Boling Consulting Solutions (bcsw.net)
 * 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.
 */
/*
 * NOTE: This file was generated, manual edits will be overwritten!
 *
 * Generated by 'goCodeGenerator.py':
 *              https://github.com/cboling/OMCI-parser/README.md
 */

package generated

import "github.com/deckarep/golang-set"

// EfmBondingGroupClassID is the 16-bit ID for the OMCI
// Managed entity EFM bonding group
const EfmBondingGroupClassID = ClassID(418) // 0x01a2

var efmbondinggroupBME *ManagedEntityDefinition

// EfmBondingGroup (Class ID: #418 / 0x01a2)
//	The EFM bonding group represents a group of links that are bonded. In [IEEE 802.3], a bonding
//	group is known as a PAF [physical medium entity (PME) aggregation function] and a link is known
//	as a PME instance of this ME are created and deleted by the OLT.
//
//	Relationships
//		An instance of this ME may be associated with zero or more instances of an EFM bonding link.
//
//	Attributes
//		Managed Entity Id
//			This attribute uniquely identifies each instance of this ME. The value 0 is reserved. (R,
//			setbycreate) (mandatory) (2-bytes)
//
//		Group Id
//			This attribute is the unique number representing this bonding group. See clause C.3.1.1 of
//			[ITU-T G.998.2]. (R,-W, setbycreate) (mandatory) (6-bytes)
//
//		Minimum Upstream Group Rate
//			This attribute sets the minimum upstream group rate, in bits per second, for this EFM Group.
//			This attribute is used to determine the group US rate low alarm status. The group US rate low
//			alarm means that the aggregate upstream rate of all active links associated with this group is
//			less than the minimum upstream group rate. The default value for this rate is zero. (R,-W)
//			(mandatory, setbycreate) (4-bytes)
//
//		Minimum Downstream Group Rate
//			This attribute sets the minimum downstream group rate, in bits per second, for this EFM Group.
//			This attribute is used to determine the group DS rate low alarm status. The group DS rate low
//			alarm means that the aggregate downstream rate of all active links associated with this group is
//			less than the minimum downstream group rate. The default value for this rate is zero. (R,-W)
//			(mandatory) (4-bytes, setbycreate)
//
//		Group Alarm Enable
//			This bit mapped attribute enables the various group alarms. A bit value of 1 means "enable".
//
//			Bit	Meaning
//
//			1 (LSB)	Group down
//
//			2	Group partial
//
//			3	Group US rate low
//
//			4	Group DS rate low
//
//			5	4x rate ratio
//
//			6-8	Reserved
//
//			(R,-W, setbycreate) (mandatory) (1-byte)
//
type EfmBondingGroup struct {
	ManagedEntityDefinition
	Attributes AttributeValueMap
}

// Attribute name constants

const EfmBondingGroup_GroupId = "GroupId"
const EfmBondingGroup_MinimumUpstreamGroupRate = "MinimumUpstreamGroupRate"
const EfmBondingGroup_MinimumDownstreamGroupRate = "MinimumDownstreamGroupRate"
const EfmBondingGroup_GroupAlarmEnable = "GroupAlarmEnable"

func init() {
	efmbondinggroupBME = &ManagedEntityDefinition{
		Name:    "EfmBondingGroup",
		ClassID: EfmBondingGroupClassID,
		MessageTypes: mapset.NewSetWith(
			Create,
			Delete,
			Get,
			Set,
		),
		AllowedAttributeMask: 0xf000,
		AttributeDefinitions: AttributeDefinitionMap{
			0: Uint16Field(ManagedEntityID, PointerAttributeType, 0x0000, 0, mapset.NewSetWith(Read, SetByCreate), false, false, false, 0),
			1: MultiByteField(EfmBondingGroup_GroupId, OctetsAttributeType, 0x8000, 6, toOctets("AAAAAAAA"), mapset.NewSetWith(Read, SetByCreate, Write), false, false, false, 1),
			2: Uint32Field(EfmBondingGroup_MinimumUpstreamGroupRate, UnsignedIntegerAttributeType, 0x4000, 0, mapset.NewSetWith(Read, Write), false, false, false, 2),
			3: Uint32Field(EfmBondingGroup_MinimumDownstreamGroupRate, UnsignedIntegerAttributeType, 0x2000, 0, mapset.NewSetWith(Read, Write), false, false, false, 3),
			4: ByteField(EfmBondingGroup_GroupAlarmEnable, UnsignedIntegerAttributeType, 0x1000, 0, mapset.NewSetWith(Read, SetByCreate, Write), false, false, false, 4),
		},
		Access:  CreatedByOlt,
		Support: UnknownSupport,
		Alarms: AlarmMap{
			0: "Group down",
			1: "Group partial",
			2: "Group US rate low",
			3: "Group DS rate low",
			4: "4x rate ratio",
		},
	}
}

// NewEfmBondingGroup (class ID 418) creates the basic
// Managed Entity definition that is used to validate an ME of this type that
// is received from or transmitted to the OMCC.
func NewEfmBondingGroup(params ...ParamData) (*ManagedEntity, OmciErrors) {
	return NewManagedEntity(*efmbondinggroupBME, params...)
}
