Updating DHCP flow checks according to VOL-3212

Change-Id: Ia4ef31c8dfb196be29a76a099698c4cbf73debe4
diff --git a/internal/bbsim/devices/onu.go b/internal/bbsim/devices/onu.go
index 583a5a6..14103c7 100644
--- a/internal/bbsim/devices/onu.go
+++ b/internal/bbsim/devices/onu.go
@@ -644,11 +644,10 @@
 		}
 	} else if msg.Flow.Classifier.EthType == uint32(layers.EthernetTypeIPv4) &&
 		msg.Flow.Classifier.SrcPort == uint32(68) &&
-		msg.Flow.Classifier.DstPort == uint32(67) &&
-		(msg.Flow.Classifier.OPbits == 0 || msg.Flow.Classifier.OPbits == 255) {
+		msg.Flow.Classifier.DstPort == uint32(67) {
 
 		for _, s := range o.Services {
-			s.HandleDhcp(int(msg.Flow.Classifier.OVid))
+			s.HandleDhcp(uint8(msg.Flow.Classifier.OPbits), int(msg.Flow.Classifier.OVid))
 		}
 	}
 }
diff --git a/internal/bbsim/devices/service_test.go b/internal/bbsim/devices/service_test.go
index 0c4ab2b..a2b720d 100644
--- a/internal/bbsim/devices/service_test.go
+++ b/internal/bbsim/devices/service_test.go
@@ -37,7 +37,7 @@
 	s.HandleAuthCallCount = s.HandleAuthCallCount + 1
 }
 
-func (s *mockService) HandleDhcp(cTag int) {
+func (s *mockService) HandleDhcp(pbit uint8, cTag int) {
 	s.HandleDhcpCallCount = s.HandleDhcpCallCount + 1
 }
 
@@ -59,7 +59,7 @@
 	onu.PonPort.Olt.enableContext = enableContext
 	return NewService("testService", mac, onu, 900, 900,
 		needsEapol, needsDchp, false, 64, 0, false,
-		0, 0, 0, 0)
+		7, 7, 7, 7)
 }
 
 // test the internalState transitions
@@ -143,7 +143,7 @@
 	}
 	s.Initialize(stream)
 
-	s.HandleDhcp(900)
+	s.HandleDhcp(7, 900)
 	time.Sleep(1 * time.Second)
 
 	assert.Equal(t, stream.CallCount, 0)
@@ -165,7 +165,7 @@
 	s.Initialize(stream)
 
 	// NOTE that the c_tag is different from the one configured in the service
-	s.HandleDhcp(800)
+	s.HandleDhcp(7, 800)
 	time.Sleep(1 * time.Second)
 
 	assert.Equal(t, stream.CallCount, 0)
@@ -174,6 +174,47 @@
 	assert.Equal(t, s.DHCPState.Current(), "created")
 }
 
+// when we receive a DHCP flow we call HandleDhcp an all the ONU Services
+// each service device whether the tag matches it's own configuration
+func TestService_HandleDhcp_different_pbit(t *testing.T) {
+	s, err := createTestService(false, true)
+
+	assert.Nil(t, err)
+
+	stream := &mockStream{
+		Calls: make(map[int]*openolt.Indication),
+	}
+	s.Initialize(stream)
+
+	// NOTE that the c_tag is different from the one configured in the service
+	s.HandleDhcp(5, 900)
+	time.Sleep(1 * time.Second)
+
+	assert.Equal(t, stream.CallCount, 0)
+
+	// state should not change
+	assert.Equal(t, s.DHCPState.Current(), "created")
+}
+
+// if PBIT is 255 it means all of them, so start DHCP if the C_TAG matches
+func TestService_HandleDhcp_pbit_255(t *testing.T) {
+	s, err := createTestService(false, true)
+
+	assert.Nil(t, err)
+
+	stream := &mockStream{
+		Calls: make(map[int]*openolt.Indication),
+	}
+	s.Initialize(stream)
+
+	// NOTE that the c_tag is different from the one configured in the service
+	s.HandleDhcp(255, 900)
+	time.Sleep(1 * time.Second)
+
+	assert.Equal(t, 1, stream.CallCount)
+	assert.Equal(t, s.DHCPState.Current(), "dhcp_discovery_sent")
+}
+
 // make sure that if the service does need DHCP we're sending any packet
 func TestService_HandleDhcp_needed(t *testing.T) {
 	s, err := createTestService(false, true)
@@ -185,7 +226,7 @@
 	}
 	s.Initialize(stream)
 
-	s.HandleDhcp(900)
+	s.HandleDhcp(7, 900)
 	time.Sleep(1 * time.Second)
 
 	assert.Equal(t, 1, stream.CallCount)
diff --git a/internal/bbsim/devices/services.go b/internal/bbsim/devices/services.go
index 4b82e98..95661c8 100644
--- a/internal/bbsim/devices/services.go
+++ b/internal/bbsim/devices/services.go
@@ -39,9 +39,9 @@
 var dhcpWaitTime = 60 * time.Second
 
 type ServiceIf interface {
-	HandlePackets()      // start listening on the PacketCh
-	HandleAuth()         // Sends the EapoStart packet
-	HandleDhcp(cTag int) // Sends the DHCPDiscover packet
+	HandlePackets()                  // start listening on the PacketCh
+	HandleAuth()                     // Sends the EapoStart packet
+	HandleDhcp(pbit uint8, cTag int) // Sends the DHCPDiscover packet
 
 	Initialize(stream bbsimTypes.Stream)
 	Disable()
@@ -292,9 +292,9 @@
 }
 
 // HandleDhcp is used to start DHCP for a particular Service when the corresponding flow is received
-func (s *Service) HandleDhcp(cTag int) {
+func (s *Service) HandleDhcp(pbit uint8, cTag int) {
 
-	if s.CTag != cTag {
+	if s.CTag != cTag || (s.UsPonCTagPriority != pbit && pbit != 255) {
 		serviceLogger.WithFields(log.Fields{
 			"OnuId":  s.Onu.ID,
 			"IntfId": s.Onu.PonPortID,