Skip to content
This repository has been archived by the owner on Oct 20, 2024. It is now read-only.

Commit

Permalink
feat: Adds PDI UE IP address
Browse files Browse the repository at this point in the history
  • Loading branch information
gruyaume committed Jan 20, 2024
1 parent 51c4b26 commit 666ef9c
Show file tree
Hide file tree
Showing 4 changed files with 148 additions and 5 deletions.
8 changes: 4 additions & 4 deletions ie/create_pdr_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -53,8 +53,8 @@ func TestGivenCorrectParametersWhenNewCreatePDRThenFieldsSetCorrectly(t *testing
t.Errorf("Expected CreatePDR Precedence %v, got %v", precedence, createPDR.Precedence)
}

if createPDR.PDI != pdi {
t.Errorf("Expected CreatePDR PDI %v, got %v", pdi, createPDR.PDI)
if createPDR.PDI.SourceInterface != pdi.SourceInterface {
t.Errorf("Expected CreatePDR PDI SourceInterface %v, got %v", pdi.SourceInterface, createPDR.PDI.SourceInterface)
}
}

Expand Down Expand Up @@ -113,7 +113,7 @@ func TestGivenSerializedWhenDeserializeCreatePDRThenFieldsSetCorrectly(t *testin
t.Errorf("Expected CreatePDR Precedence %v, got %v", precedence, deserialized.Precedence)
}

if deserialized.PDI != pdi {
t.Errorf("Expected CreatePDR PDI %v, got %v", pdi, deserialized.PDI)
if deserialized.PDI.SourceInterface != pdi.SourceInterface {
t.Errorf("Expected CreatePDR PDI SourceInterface %v, got %v", pdi.SourceInterface, deserialized.PDI.SourceInterface)
}
}
1 change: 1 addition & 0 deletions ie/ie.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ const (
PDRIDIEType IEType = 56
FSEIDIEType IEType = 57
NodeIDIEType IEType = 60
UEIPAddressIEType IEType = 93
RecoveryTimeStampIEType IEType = 96
NodeReportTypeIEType IEType = 101
FARIDIEType IEType = 108
Expand Down
3 changes: 2 additions & 1 deletion ie/pdi.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,8 @@ import (

type PDI struct {
Header Header
SourceInterface SourceInterface
SourceInterface SourceInterface // Mandatory
UEIPAddress UEIPAddress // Optional
}

func NewPDI(sourceInterface SourceInterface) (PDI, error) {
Expand Down
141 changes: 141 additions & 0 deletions ie/ue_ip_address.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,141 @@
package ie

import (
"bytes"
"errors"
"net"
)

type UEIPAddress struct {
Header Header
IP6PL bool
CHV6 bool
CHV4 bool
IPv6D bool
SD bool
V4 bool
V6 bool
IPv4Address []byte
IPv6Address []byte
IPv6PrefixDelegationBits uint8
IPv6PrefixLength uint8
}

type SourceDestination struct {
Source bool
Destination bool
}

func NewUEIPAddress(ipv4CIDR string, ipv6CIDR string, sd SourceDestination, ipv6PrefixDelegationBits uint8) (UEIPAddress, error) {
var ipv4Address, ipv6Address []byte
var ipv6PrefixLength uint8
var length uint16 = 1

if ipv4CIDR != "" {
ip, _, err := net.ParseCIDR(ipv4CIDR)
if err != nil {
return UEIPAddress{}, err
}
ipv4Address = ip.To4()
if ipv4Address == nil {
return UEIPAddress{}, errors.New("invalid IPv4 address")
}
length += 4
}

if ipv6CIDR != "" {
ip, ipv6Network, err := net.ParseCIDR(ipv6CIDR)
if err != nil {
return UEIPAddress{}, err
}
ipv6Address = ip.To16()
if ipv6Address == nil {
return UEIPAddress{}, errors.New("invalid IPv6 address")
}
ones, _ := ipv6Network.Mask.Size()
ipv6PrefixLength = uint8(ones)
length += 18
}

var sourceDestination bool
if sd.Source {
sourceDestination = false
} else if sd.Destination {
sourceDestination = true
}

ieHeader := Header{
Type: UEIPAddressIEType,
Length: length,
}

return UEIPAddress{
Header: ieHeader,
IP6PL: ipv6PrefixLength != 0,
CHV6: ipv6Address == nil,
CHV4: ipv4Address == nil,
IPv6D: ipv6PrefixDelegationBits != 0,
SD: sourceDestination,
V4: ipv4Address != nil,
V6: ipv6Address != nil,
IPv4Address: ipv4Address,
IPv6Address: ipv6Address,
IPv6PrefixDelegationBits: ipv6PrefixDelegationBits,
IPv6PrefixLength: ipv6PrefixLength,
}, nil
}

func (ueIPaddress *UEIPAddress) Serialize() []byte {
buf := new(bytes.Buffer)

// Octets 1 to 4: Header
buf.Write(ueIPaddress.Header.Serialize())

// Octet 5: Bit 1: V6, Bit 2: V4, Bit 3: S/D, Bit 4: IPv6D, Bit 5: CHV4, Bit 6: CHV6, Bit 7: IP6PL, Bit 8: Spare
var octet5 byte
if ueIPaddress.IP6PL {
octet5 |= 1 << 7
}
if ueIPaddress.CHV6 {
octet5 |= 1 << 6
}
if ueIPaddress.CHV4 {
octet5 |= 1 << 5
}
if ueIPaddress.IPv6D {
octet5 |= 1 << 4
}
if ueIPaddress.SD {
octet5 |= 1 << 3
}
if ueIPaddress.V4 {
octet5 |= 1 << 2
}
if ueIPaddress.V6 {
octet5 |= 1 << 1
}
buf.WriteByte(octet5)

// Octet m to (m+3): IPv4 Address
if ueIPaddress.V4 {
buf.Write(ueIPaddress.IPv4Address)
}

// Octet p to (p+15): IPv6 Address
if ueIPaddress.V6 {
buf.Write(ueIPaddress.IPv6Address)
}

// Octet r: IPv6 Delegation Bits
if ueIPaddress.IPv6D {
buf.WriteByte(ueIPaddress.IPv6PrefixDelegationBits)
}

// Octet s: IPv6 Prefix Length
if ueIPaddress.IPv6D {
buf.WriteByte(ueIPaddress.IPv6PrefixLength)
}

return buf.Bytes()

}

0 comments on commit 666ef9c

Please sign in to comment.