Add version 0.5.0
Change-Id: Ic052ea806f728c7e437038b1809f84a47af90011
Signed-off-by: Peter Szilagyi <peter.3.szilagyi@nokia.com>
diff --git a/pkg/control/control.go b/pkg/control/control.go
index d213c65..9a5022f 100644
--- a/pkg/control/control.go
+++ b/pkg/control/control.go
@@ -27,69 +27,97 @@
*/
import "C"
-
import (
- "gerrit.o-ran-sc.org/r/ric-plt/xapp-frame/pkg/xapp"
- "errors"
- "strconv"
+ "errors"
+ "gerrit.o-ran-sc.org/r/ric-plt/xapp-frame/pkg/xapp"
+ "github.com/spf13/viper"
+ "math/rand"
+ "strconv"
+ "time"
)
type Control struct {
- e2ap *E2ap
- registry *Registry
+ e2ap *E2ap
+ registry *Registry
+}
+
+var SEEDSN uint16
+
+func init() {
+ viper.AutomaticEnv()
+ viper.SetEnvPrefix("submgr")
+ viper.AllowEmptyEnv(true)
+ SEEDSN = uint16(viper.GetInt("seed_sn"))
+ if SEEDSN == 0 {
+ rand.Seed(time.Now().UnixNano())
+ SEEDSN = uint16(rand.Intn(65535))
+ }
+ if SEEDSN > 65535 {
+ SEEDSN = 0
+ }
+ xapp.Logger.Info("SUBMGR: Initial Sequence Number: %v", SEEDSN)
}
func NewControl() Control {
- return Control{new(E2ap),new(Registry)}
+ registry := new(Registry)
+ registry.Initialize(SEEDSN)
+ return Control{new(E2ap), registry}
}
func (c *Control) Run() {
- xapp.Run(c)
+ xapp.Run(c)
}
func (c *Control) Consume(mtype, sub_id int, len int, payload []byte) (err error) {
- switch mtype {
- case C.RIC_SUB_REQ:
- err = c.handleSubscriptionRequest(&RmrDatagram{mtype, sub_id, payload})
- case C.RIC_SUB_RESP:
- err = c.handleSubscriptionResponse(&RmrDatagram{mtype, sub_id, payload})
- default:
- err = errors.New("Message Type "+strconv.Itoa(mtype)+" discarded")
- }
- return
+ switch mtype {
+ case C.RIC_SUB_REQ:
+ err = c.handleSubscriptionRequest(&RmrDatagram{mtype, uint16(sub_id), payload})
+ case C.RIC_SUB_RESP:
+ err = c.handleSubscriptionResponse(&RmrDatagram{mtype, uint16(sub_id), payload})
+ default:
+ err = errors.New("Message Type " + strconv.Itoa(mtype) + " is discarded")
+ }
+ return
}
func (c *Control) rmrSend(datagram *RmrDatagram) (err error) {
- if !xapp.Rmr.Send(datagram.MessageType, datagram.SubscriptionId, len(datagram.Payload), datagram.Payload) {
- err = errors.New("rmr.Send() failed")
- }
- return
+ if !xapp.Rmr.Send(datagram.MessageType, int(datagram.SubscriptionId), len(datagram.Payload), datagram.Payload) {
+ err = errors.New("rmr.Send() failed")
+ }
+ return
}
-func (c *Control) handleSubscriptionRequest(datagram *RmrDatagram) ( err error) {
- /* TODO: removed to being able to integrate with UEMGR
- content, err := c.e2ap.GetPayloadContent(datagram.Payload)
- */
- xapp.Logger.Info("Subscription Request Message received with ID: %v", datagram.SubscriptionId)
- new_sub_id := c.registry.GetSubscriptionId()
- /* TODO: removed to being able to integrate with UEMGR
- payload, err := c.e2ap.SetSubscriptionSequenceNumber(datagram.Payload, new_sub_id)
- if err != nil {
- xapp.Logger.Error("Unable to set Subscription Sequence Number in Payload due to: "+ err.Error())
- return
- }
- */
- xapp.Logger.Info("New Subscription Registered, forwarding to E2T")
- c.rmrSend(&RmrDatagram{C.RIC_SUB_REQ , new_sub_id, datagram.Payload})
- return
+func (c *Control) handleSubscriptionRequest(datagram *RmrDatagram) (err error) {
+ payload_seq_num, err := c.e2ap.GetSubscriptionRequestSequenceNumber(datagram.Payload)
+ if err != nil {
+ err = errors.New("Unable to get Subscription Sequence Number from Payload due to: " + err.Error())
+ return
+ }
+ xapp.Logger.Info("Subscription Request Received. RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", datagram.SubscriptionId, payload_seq_num)
+ new_sub_id := c.registry.ReserveSequenceNumber()
+ payload, err := c.e2ap.SetSubscriptionRequestSequenceNumber(datagram.Payload, new_sub_id)
+ if err != nil {
+ err = errors.New("Unable to set Subscription Sequence Number in Payload due to: " + err.Error())
+ return
+ }
+ xapp.Logger.Info("Generated ID: %v. Forwarding to E2 Termination...", int(new_sub_id))
+ c.rmrSend(&RmrDatagram{C.RIC_SUB_REQ, new_sub_id, payload})
+ return
}
-func (c *Control) handleSubscriptionResponse(datagram *RmrDatagram) ( err error) {
- /* TODO: removed to being able to integrate with UEMGR
- content, err := c.e2ap.GetPayloadContent(datagram.Payload)
- */
- xapp.Logger.Info("Subscription Response Message received with ID: %v", datagram.SubscriptionId)
- xapp.Logger.Info("Subscription Response Registered, forwarding to Requestor")
- c.rmrSend(&RmrDatagram{C.RIC_SUB_RESP , datagram.SubscriptionId, datagram.Payload})
- return
-}
\ No newline at end of file
+func (c *Control) handleSubscriptionResponse(datagram *RmrDatagram) (err error) {
+ payload_seq_num, err := c.e2ap.GetSubscriptionResponseSequenceNumber(datagram.Payload)
+ if err != nil {
+ err = errors.New("Unable to get Subscription Sequence Number from Payload due to: " + err.Error())
+ return
+ }
+ xapp.Logger.Info("Subscription Response Received. RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", datagram.SubscriptionId, payload_seq_num)
+ if !c.registry.IsValidSequenceNumber(payload_seq_num) {
+ err = errors.New("Unknown Subscription ID: " + strconv.Itoa(int(payload_seq_num)) + " in Subscritpion Response. Message discarded.")
+ return
+ }
+ c.registry.setSubscriptionToConfirmed(payload_seq_num)
+ xapp.Logger.Info("Subscription Response Registered. Forwarding to Requestor...")
+ c.rmrSend(&RmrDatagram{C.RIC_SUB_RESP, payload_seq_num, datagram.Payload})
+ return
+}
diff --git a/pkg/control/e2ap.go b/pkg/control/e2ap.go
index ff9c778..c6b5e28 100644
--- a/pkg/control/e2ap.go
+++ b/pkg/control/e2ap.go
@@ -19,66 +19,57 @@
package control
+/*
+#include <wrapper.h>
+
+#cgo LDFLAGS: -lwrapper
+*/
+import "C"
+
import (
- "encoding/gob"
- "bytes"
- "errors"
+ "errors"
+ "unsafe"
)
type E2ap struct {
}
-func (c *E2ap) GetSubscriptionSequenceNumber(payload []byte) (int, error) {
- asn1 := new(Asn1)
- message, err := asn1.Decode(payload)
- if err != nil {
- return 0, errors.New("Unable to decode payload due to "+ err.Error())
- }
- return message.SubscriptionId, nil
+func (c *E2ap) GetSubscriptionRequestSequenceNumber(payload []byte) (sub_id uint16, err error) {
+ cptr := unsafe.Pointer(&payload[0])
+ cret := C.e2ap_get_ric_subscription_request_sequence_number(cptr, C.size_t(len(payload)))
+ if cret < 0 {
+ return 0, errors.New("e2ap wrapper is unable to get Subscirption Request Sequence Number due to wrong or invalid payload")
+ }
+ sub_id = uint16(cret)
+ return
}
-func (c *E2ap) SetSubscriptionSequenceNumber(payload []byte, newSubscriptionid int) ([]byte ,error) {
- asn1 := new(Asn1)
- message, err := asn1.Decode(payload)
- if err != nil {
- return make([]byte,0), errors.New("Unable to decode payload due to "+ err.Error())
- }
- message.SubscriptionId = newSubscriptionid
- payload, err = asn1.Encode(message)
- if err != nil {
- return make([]byte,0), errors.New("Unable to encode message due to "+ err.Error())
- }
- return payload, nil
+func (c *E2ap) SetSubscriptionRequestSequenceNumber(payload []byte, newSubscriptionid uint16) (new_payload []byte, err error) {
+ cptr := unsafe.Pointer(&payload[0])
+ size := C.e2ap_set_ric_subscription_request_sequence_number(cptr, C.size_t(len(payload)), C.long(newSubscriptionid))
+ if size < 0 {
+ return make([]byte, 0), errors.New("e2ap wrapper is unable to set Subscirption Request Sequence Number due to wrong or invalid payload")
+ }
+ new_payload = C.GoBytes(cptr, C.int(size))
+ return
}
-
-func (c *E2ap) GetPayloadContent(payload []byte) (content string, err error) {
- asn1 := new(Asn1)
- message, err := asn1.Decode(payload)
- content = message.Content
- return
-}
-/*
-Serialize and Deserialize message using this until real ASN1 GO wrapper is not in place
-*/
-type Asn1 struct {
+func (c *E2ap) GetSubscriptionResponseSequenceNumber(payload []byte) (sub_id uint16, err error) {
+ cptr := unsafe.Pointer(&payload[0])
+ cret := C.e2ap_get_ric_subscription_response_sequence_number(cptr, C.size_t(len(payload)))
+ if cret < 0 {
+ return 0, errors.New("e2ap wrapper is unable to get Subscirption Response Sequence Number due to wrong or invalid payload")
+ }
+ sub_id = uint16(cret)
+ return
}
-func (a *Asn1) Encode(message RmrPayload) ([]byte, error) {
- buffer := new(bytes.Buffer)
- asn1 := gob.NewEncoder(buffer)
- if err := asn1.Encode(message); err != nil {
- return nil, err
- }
- return buffer.Bytes(), nil
-}
-
-func (a *Asn1) Decode(data []byte) (RmrPayload, error) {
- message := new(RmrPayload)
- buffer := bytes.NewBuffer(data)
- asn1 := gob.NewDecoder(buffer)
- if err := asn1.Decode(message); err != nil {
- return RmrPayload{}, err
- }
- return *message, nil
+func (c *E2ap) SetSubscriptionResponseSequenceNumber(payload []byte, newSubscriptionid uint16) (new_payload []byte, err error) {
+ cptr := unsafe.Pointer(&payload[0])
+ size := C.e2ap_set_ric_subscription_response_sequence_number(cptr, C.size_t(len(payload)), C.long(newSubscriptionid))
+ if size < 0 {
+ return make([]byte, 0), errors.New("e2ap wrapper is unable to set Subscirption Reponse Sequence Number due to wrong or invalid payload")
+ }
+ new_payload = C.GoBytes(cptr, C.int(size))
+ return
}
diff --git a/pkg/control/registry.go b/pkg/control/registry.go
index 8f52f97..d182b3e 100644
--- a/pkg/control/registry.go
+++ b/pkg/control/registry.go
@@ -19,15 +19,45 @@
package control
+import "gerrit.o-ran-sc.org/r/ric-plt/xapp-frame/pkg/xapp"
+
type Registry struct {
- counter int
+ register map[uint16]bool
+ counter uint16
}
-func (r *Registry) GetSubscriptionId() int {
- return r.generateId()
+// This method should run as a constructor
+func (r *Registry) Initialize(seedsn uint16) {
+ r.register = make(map[uint16]bool)
+ r.counter = seedsn
}
-func (r *Registry) generateId() int {
- r.counter += 1
- return r.counter
+// Reserves and returns the next free sequence number
+func (r *Registry) ReserveSequenceNumber() uint16 {
+ sequenceNumber := r.counter
+ r.register[sequenceNumber] = false
+ r.shift()
+ return sequenceNumber
+}
+
+// This function checks the validity of the given subscription id
+func (r *Registry) IsValidSequenceNumber(sn uint16) bool {
+ xapp.Logger.Debug("Registry map: %v", r.register)
+ if _, ok := r.register[sn]; ok {
+ return true
+ }
+ return false
+}
+
+// This function sets the give id as confirmed in the register
+func (r *Registry) setSubscriptionToConfirmed(sn uint16) {
+ r.register[sn] = true
+}
+
+func (r *Registry) shift() {
+ if r.counter == 65535 {
+ r.counter = 0
+ } else {
+ r.counter++
+ }
}
diff --git a/pkg/control/types.go b/pkg/control/types.go
index 5f46e65..2a4e9d5 100644
--- a/pkg/control/types.go
+++ b/pkg/control/types.go
@@ -19,14 +19,8 @@
package control
-type RmrPayload struct {
- MessageType int
- SubscriptionId int
- Content string
-}
-
type RmrDatagram struct {
- MessageType int
- SubscriptionId int
- Payload []byte
+ MessageType int
+ SubscriptionId uint16
+ Payload []byte
}