# xApp Development: Colosseum Near RT RIC and ns-o-ran [TOC] --- ## Architecture ![image](https://hackmd.io/_uploads/H1gQmYy_xl.png) ## Callflow ![kpimon bwxapp callflow](https://hackmd.io/_uploads/BkxkiiXeuex.png) ## Near-RT RIC Setup ### Colosseum Near RT RIC To install and setup the Near RT RIC environment, you can follow this tutorial: [Colosseum Near RT RIC Installation](https://hackmd.io/@nomaden/BJAxCtKOxl) ### Deploy ns-o-ran to Docker ```bash cd ~/colosseum-near-rt-ric/ ./build-ns-o-ran.sh ``` ## How bw-xapp Works My implementation `bw-xapp` is that I only modify the `sample-xapp` and the `xapp.cc` in `xapp-sm-connector` to be able to fetch data from Shared Data Layer (SDL). The connection of the intended system is like this: ![image](https://hackmd.io/_uploads/H1Ednrguge.png) `kpimon` can retrieve KPM Data and **stored it to the `DBAAS` (SDL)**. And the `xapp-sm-connector` fetch the KPM Data **from the SDL**. However, due to the mismatched of `kpimon` with `ns-o-ran`. The connection is instead like this: ![image](https://hackmd.io/_uploads/BkJ26Hg_le.png) Since the SDL is not filled with any KPM data, I modify the `xapp-sm-connector` to generate ***dummy KPM data*** and sends the data to the `bw-xapp`. First, we need to take a look at the modified code for generating KPM data ([Code](https://github.com/den-dimas/colosseum-near-rt-ric/blob/main/setup/xapp-sm-connector/src/xapp.cc): `Line 228`): ```cc! std::string Xapp::get_kpm_data() { mdclog_write(MDCLOG_INFO, "Attempting to retrieve KPM data from SDL..."); bool sdl_data_available = false; rapidjson::Document kpm_data; kpm_data.SetObject(); if (sdl_data_available) { kpm_data.AddMember("cell_load", 0.75, kpm_data.GetAllocator()); kpm_data.AddMember("packet_drop_rate", 0.05, kpm_data.GetAllocator()); } else { mdclog_write(MDCLOG_INFO, "SDL data not available. Using dummy data."); // Dummy KPM data kpm_data.AddMember("cell_load", 0.85, kpm_data.GetAllocator()); kpm_data.AddMember("packet_drop_rate", 0.02, kpm_data.GetAllocator()); } rapidjson::StringBuffer buffer; rapidjson::Writer<rapidjson::StringBuffer> writer(buffer); kpm_data.Accept(writer); return buffer.GetString(); } ``` As you can see on the code above, I didn't check the connection to the SDL. The `xapp-sm-connector` does have a function to communicate to SDL. But I only used *dummy data* because of the `kpimon` issue. I generate the *dummy* KPM data and format it with JSON. Then, in order to send it to the `bw-xapp`. It is done by the `handle_rx_msg_agent()` function ([Code](https://github.com/den-dimas/colosseum-near-rt-ric/blob/main/setup/xapp-sm-connector/src/xapp.cc): `Line 256`). The `bw-xapp`, creates a strategy from this ([Code](https://github.com/den-dimas/colosseum-near-rt-ric/blob/main/setup/bw-xapp/run_xapp.py): `Line 19`): ```python! # 1. Receive data from socket opened by xapp-sm-connector data = receive_from_socket(control_sck) # 2. Wait for the KPM Data being sent from the xapp-sm-connector if not data: logging.warning("No data received. Waiting for KPM data from xapp-sm-connector...") continue # 3. Loads the KPM data and kpm_data_str = data logging.info("Received KPM data from xapp-sm-connector: %s", kpm_data_str) # parse it with JSON kpm_data = json.loads(kpm_data_str) # Get the cell load parameter cell_load = kpm_data.get('cell_load', 0) bandwidth_adjustment = 0 # This is just an assumption and with no consideration of parameters # Adjust the bandwidth adjustment from cell_load KPM if cell_load > 0.8: logging.info("High cell load detected (%.2f). Suggesting to increase bandwidth.", cell_load) bandwidth_adjustment = 10 else: logging.info("Low cell load detected (%.2f). Suggesting to decrease bandwidth.", cell_load) bandwidth_adjustment = -5 # 4. Formulate the message to send control_message_params = { "bandwidth_adjustment": bandwidth_adjustment, "target_gnb": "gnb:131-133-31000000" } control_message_json = json.dumps(control_message_params) # 5. Send the byte encoded JSON message back to the xapp-sm-connector bytes_num = control_sck.send(control_message_json.encode("utf-8")) logging.info("Socket sent %d bytes with JSON payload: %s", bytes_num, control_message_json) ``` Like I've mentioned in the code, the bandwidth parameter right now is just a simple instruction with no consideration of the E2AP and E2SM parameters. The JSON message will be **encoded as an RIC-Control-Message Payload** by the `xapp-sm-connector` ## Deploy and Run bw-xapp To deploy and run the `bw-xapp` to the enviroment: ```bash cd ~/colosseum-near-rt-ric/setup-scripts ./start-xapp-ns-o-ran.sh ``` ## Deploy and Run kpimon xApp ### Clone the repository ```bash cd ~ git clone https://github.com/den-dimas/ric-app-kpimon.git kpimon ``` ### Deploy the xApp ```bash cd ~/kpimon ./redeploy.sh ``` ## Testing After finishing the environment and xApp setup, at the end you can see the docker containers: ```bash! docker ps ``` ![image](https://hackmd.io/_uploads/HyLk8Ykdxx.png) ### Setup - Open three terminal and login to the VM in each terminal. - Terminal A for **ns-o-ran** ```bash! docker exec -it ns-o-ran /bin/bash ``` - Terminal B for **kpimon** ```bash! docker exec -it kpimon /bin/bash ``` - Terminal C for **bw-xapp** ```bash! docker exec -it bw-xapp-24 /bin/bash ``` - **Terminal A** ```bash! cd ns3-mmwave-oran/ ./ns3 run scratch/scenario-zero.cc ``` :::spoiler **Result** ![image](https://hackmd.io/_uploads/Bky4vFydgg.png =600x) ::: - **Terminal B** ```bash! ./kpimon -f /opt/config-file.json ``` :::spoiler **Result** ![image](https://hackmd.io/_uploads/SJJKPt1Oll.png =600x) ::: - **Terminal C** ```bash! /home/bw-xapp/run_xapp.sh ``` :::spoiler **Result** ![image](https://hackmd.io/_uploads/By5ADtkule.png =600x) ::: >[!Important] Notes >Note that all three simulation needs to be executed simultaneously! ### Testing Result **ns-o-ran Simulation:** :::spoiler **RIC-INDICATION** ```bash! [DEBUG] data.len is 193 [DEBUG] after getting sent_len <E2AP-PDU> <initiatingMessage> <procedureCode>5</procedureCode> <criticality><ignore/></criticality> <value> <RICindication> <protocolIEs> <RICindication-IEs> <id>29</id> <criticality><reject/></criticality> <value> <RICrequestID> <ricRequestorID>1001</ricRequestorID> <ricInstanceID>0</ricInstanceID> </RICrequestID> </value> </RICindication-IEs> <RICindication-IEs> <id>5</id> <criticality><reject/></criticality> <value> <RANfunctionID>200</RANfunctionID> </value> </RICindication-IEs> <RICindication-IEs> <id>15</id> <criticality><reject/></criticality> <value> <RICactionID>0</RICactionID> </value> </RICindication-IEs> <RICindication-IEs> <id>27</id> <criticality><reject/></criticality> <value> <RICindicationSN>1</RICindicationSN> </value> </RICindication-IEs> <RICindication-IEs> <id>28</id> <criticality><reject/></criticality> <value> <RICindicationType><report/></RICindicationType> </value> </RICindication-IEs> <RICindication-IEs> <id>25</id> <criticality><reject/></criticality> <value> <RICindicationHeader> 00 00 00 01 98 7A 76 E9 23 60 31 31 31 00 31 00 00 </RICindicationHeader> </value> </RICindication-IEs> <RICindication-IEs> <id>26</id> <criticality><reject/></criticality> <value> <RICindicationMessage> 10 98 00 0B 00 00 08 4E 52 43 65 6C 6C 43 55 00 0B 40 05 30 30 30 30 37 00 40 05 30 30 30 31 32 00 40 05 30 30 30 30 31 00 40 05 30 30 30 30 35 00 40 05 30 30 30 30 34 00 40 05 30 30 30 30 33 00 40 05 30 30 30 30 32 00 40 05 30 30 30 31 30 00 40 05 30 30 30 31 31 00 40 05 30 30 30 30 39 00 40 05 30 30 30 30 38 00 40 05 30 30 30 30 36 00 </RICindicationMessage> </value> </RICindication-IEs> <RICindication-IEs> <id>20</id> <criticality><reject/></criticality> <value> <RICcallProcessID>63 70 69 64</RICcallProcessID> </value> </RICindication-IEs> </protocolIEs> </RICindication> </value> </initiatingMessage> </E2AP-PDU> [DEBUG] [E2AP ASN] Encoded succesfully, encoded size = 188 [INFO ] Send data to client_fd 3 [DEBUG] in sctp send data func [DEBUG] data.len is 188 [DEBUG] after getting sent_len ``` ::: :::spoiler **RIC-CONTROL-REQUEST** ```bash! [DEBUG] [SCTP] Received new data of size 35 [DEBUG] in e2ap_handle_sctp_data() [DEBUG] [E2AP ASN] Decoded successfully <E2AP-PDU> <initiatingMessage> <procedureCode>4</procedureCode> <criticality><ignore/></criticality> <value> <RICcontrolRequest> <protocolIEs> <RICcontrolRequest-IEs> <id>29</id> <criticality><reject/></criticality> <value> <RICrequestID> <ricRequestorID>1</ricRequestorID> <ricInstanceID>0</ricInstanceID> </RICrequestID> </value> </RICcontrolRequest-IEs> <RICcontrolRequest-IEs> <id>5</id> <criticality><reject/></criticality> <value> <RANfunctionID>0</RANfunctionID> </value> </RICcontrolRequest-IEs> <RICcontrolRequest-IEs> <id>22</id> <criticality><reject/></criticality> <value> <RICcontrolHeader></RICcontrolHeader> </value> </RICcontrolRequest-IEs> <RICcontrolRequest-IEs> <id>23</id> <criticality><reject/></criticality> <value> <RICcontrolMessage>31 30 00</RICcontrolMessage> </value> </RICcontrolRequest-IEs> </protocolIEs> </RICcontrolRequest> </value> </initiatingMessage> </E2AP-PDU> [DEBUG] [INFO ] [E2AP] Received RIC-CONTROL-REQUEST [INFO ] %%we are getting the e2sm callback for func id 300 ``` ::: :::spoiler **RIC-CONTROL-ACKNOWLEDGE** ```bash! [DEBUG] Calling callback function [DEBUG] [E2AP] Created E2-RIC-CONTROL-ACKNOWLEDGE <E2AP-PDU> <successfulOutcome> <procedureCode>4</procedureCode> <criticality><reject/></criticality> <value> <RICcontrolAcknowledge> <protocolIEs> <RICcontrolAcknowledge-IEs> <id>29</id> <criticality><reject/></criticality> <value> <RICrequestID> <ricRequestorID>0</ricRequestorID> <ricInstanceID>0</ricInstanceID> </RICrequestID> </value> </RICcontrolAcknowledge-IEs> <RICcontrolAcknowledge-IEs> <id>5</id> <criticality><reject/></criticality> <value> <RANfunctionID>0</RANfunctionID> </value> </RICcontrolAcknowledge-IEs> <RICcontrolAcknowledge-IEs> <id>24</id> <criticality><reject/></criticality> <value> <RICcontrolStatus><success/></RICcontrolStatus> </value> </RICcontrolAcknowledge-IEs> </protocolIEs> </RICcontrolAcknowledge> </value> </successfulOutcome> </E2AP-PDU> [DEBUG] [DEBUG] er encoded is 1457 [DEBUG] in sctp send data func [DEBUG] data.len is 1457 [DEBUG] after getting sent_len [INFO ] [SCTP] Sent E2-SERVICE-UPDATE ``` ::: --- **kpimon xApp:** :::spoiler **Sub-Request** ```bash! {"ts":1754401282838,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"Using config file: /opt/config-file.json"} Starting new control. Ran list is gnb:131-133-31000000,gnb:131-133-32000000,gnb:131-133-33000000,gnb:131-133-34000000,gnb:131-133-35000000 ---- [KPIMON] Successfully creating new xApp control. {"ts":1754401282855,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"===========\nRunning the xApp..."} {"ts":1754401282855,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"===========\nCheck xApp ready..."} 1754401282 119/RMR [INFO] ric message routing library on SI95/g mv=3 flg=00 (f1d10cd 4.0.5 built: May 7 2020) {"ts":1754401282856,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"Register new counter with opts: {ricxapp RMR Transmitted The total number of transmited RMR messages map[]}"} {"ts":1754401282856,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"Register new counter with opts: {ricxapp RMR Received The total number of received RMR messages map[]}"} {"ts":1754401282856,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"Register new counter with opts: {ricxapp RMR TransmitError The total number of RMR transmission errors map[]}"} {"ts":1754401282856,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"Register new counter with opts: {ricxapp RMR ReceiveError The total number of RMR receive errors map[]}"} {"ts":1754401282856,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"Xapp started, listening on: "} {"ts":1754401282857,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"Connection to database established!"} {"ts":1754401282857,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:22"},"msg":"rmrClient: Waiting for RMR to be ready ..."} {"ts":1754401283857,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:23"},"msg":"rmrClient: RMR is ready after 1 seconds waiting..."} {"ts":1754401283857,"crit":"INFO","id":"kpimon","mdc":{"time":"2025-08-05T13:41:23"},"msg":"rmrClient: 'worker-0': receiving messages on [tcp:4560]"} {"ts":1754401283857,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:23"},"msg":"=============\nSub request done."} {"ts":1754401283857,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:23"},"msg":"===========Starting KPIMON control loop."} {"ts":1754401283857,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:23"},"msg":"===========Receiving from socket channel."} 1754401283 119/RMR [INFO] sends: ts=1754401283 src=ec5698187287:4560 target=10.0.2.11:3801 open=0 succ=0 fail=0 (hard=0 soft=0) 1754401283 119/RMR [INFO] sends: ts=1754401283 src=ec5698187287:4560 target=service-ricplt-a1mediator-rmr.ricplt:4562 open=0 succ=0 fail=0 (hard=0 soft=0) 1754401283 119/RMR [INFO] sends: ts=1754401283 src=ec5698187287:4560 target=10.0.2.11:4801 open=0 succ=0 fail=0 (hard=0 soft=0) 1754401283 119/RMR [INFO] sends: ts=1754401283 src=ec5698187287:4560 target=10.0.2.10:38000 open=0 succ=0 fail=0 (hard=0 soft=0) RMR is ready now ... {"ts":1754401285863,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:25"},"msg":"send RIC_SUB_REQ to gNodeB with cnt=1"} {"ts":1754401285865,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:25"},"msg":"The RMR message to be sent is 12010 with SubId=1001"} {"ts":1754401285865,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:25"},"msg":"RIC_SUB_REQ succesfully being sent."} {"ts":1754401285865,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:25"},"msg":"RIC_SUB_REQ[gnb:131-133-31000000]: Waiting for RIC_SUB_RESP..."} {"ts":1754401285869,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:25"},"msg":"Received message type: 12011"} {"ts":1754401285869,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:25"},"msg":"The params: {\n \"Mtype\": 12011,\n \"Payload\": \"IAgAHQAAAwAdAAUAA+kAAAAFAAIAAAARAAcAAA4AAgAA\",\n \"PayloadLen\": 33,\n \"Meid\": {\n \"PlmnID\": \"\",\n \"EnbID\": \"\",\n \"RanName\": \"gnb:131-133-31000000\"\n },\n \"Xid\": \" 733560319369\",\n \"SubId\": -1,\n \"Src\": \"ca5b5399ccc3:38000\",\n \"Mbuf\": {},\n \"Whid\": 0,\n \"Callid\": 0,\n \"Timeout\": 0\n}"} {"ts":1754401285869,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:25"},"msg":"The SubId in RIC_SUB_RESP is -1"} ``` ::: :::spoiler **RIC-INDICATION** ```bash! {"ts":1754401285870,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:25"},"msg":"===========Receiving from socket channel."} {"ts":1754401286072,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:26"},"msg":"Received message type: 12050"} {"ts":1754401286072,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:26"},"msg":"The params: {\n \"Mtype\": 12050,\n \"Payload\": \"AAVAgLwAAAgAHQAFAAPpAAAABQACAMgADwABAAAbAAIAAQAcAAEAABkAEhEAAAABmHp25/dgMTExADEAAAAaAHd2EKAAIDExMQAAYAAgAhN0AAAAAAAAC0AFMDAwMDkAQAUwMDAwNwBABTAwMDExAEAFMDAwMDQAQAUwMDAwMwBABTAwMDEwAEAFMDAwMDgAQAUwMDAxMgBABTAwMDAxAEAFMDAwMDYAQAUwMDAwMgBABTAwMDA1AAAUAAUEY3BpZA==\",\n \"PayloadLen\": 193,\n \"Meid\": {\n \"PlmnID\": \"\",\n \"EnbID\": \"\",\n \"RanName\": \"gnb:131-133-31000000\"\n },\n \"Xid\": \" 733560319370\",\n \"SubId\": 1001,\n \"Src\": \"ca5b5399ccc3:38000\",\n \"Mbuf\": {},\n \"Whid\": 0,\n \"Callid\": 0,\n \"Timeout\": 0\n}"} {"ts":1754401286072,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:26"},"msg":"RIC Indication Header decoded!"} {"ts":1754401286073,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:26"},"msg":"RIC Indication Message: &{0 0 <nil>}"} {"ts":1754401286073,"crit":"ERROR","id":"kpimon","mdc":{"time":"2025-08-05T13:41:26"},"msg":"Failed to decode RIC Indication Message: e2sm wrapper is unable to get IndicationMessage due to wrong or invalid input"} {"ts":1754401286073,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:26"},"msg":"===========Receiving from socket channel."} {"ts":1754401286073,"crit":"DEBUG","id":"kpimon","mdc":{"time":"2025-08-05T13:41:26"},"msg":"Received message type: 12050"} ``` ::: --- **bw-xapp:** :::spoiler **Sub-Request** ```bash! Waiting for xApp connection on port 4200 Xapp Name is: hwxapp {"ts":1754401292107,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Starting thread 132578989082432"} {"ts":1754401292107,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Xapp Name set to hwxapp from environment variable"} {"ts":1754401292107,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Xapp ID set to hwxapp from environment variable"} {"ts":1754401292107,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Ports set to 4560 from environment variable"} 1754401292 157/RMR [INFO] ric message routing library on SI95/g mv=3 flg=00 (f1d10cd 4.0.5 built: May 7 2020) {"ts":1754401292107,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":">>> waiting for RMR, file= xapp-utils/xapp_rmr.cc, line=59"} {"ts":1754401293108,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"RMR Context is Ready, file= xapp-utils/xapp_rmr.cc, line=63"} {"ts":1754401293108,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Created Hello World Xapp Instance"} 1754401293 157/RMR [INFO] sends: ts=1754401293 src=65eacd91577f:4560 target=service-ricplt-a1mediator-rmr.ricplt:4562 open=0 succ=0 fail=0 (hard=0 soft=0) 1754401293 157/RMR [INFO] sends: ts=1754401293 src=65eacd91577f:4560 target=10.0.2.10:38000 open=0 succ=0 fail=0 (hard=0 soft=0) {"ts":1754401294108,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Starting Listener Threads. Number of Workers = 1"} {"ts":1754401294108,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Receiver Thread file= xapp.cc, line=179"} {"ts":1754401294108,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Starting receiver thread 132578560423680"} {"ts":1754401294108,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Listening at Thread: 132578560423680"} gNB read: gnb:131-133-31000000 gNB read: gnb:131-133-32000000 gNB read: gnb:131-133-33000000 gNB read: gnb:131-133-34000000 gNB read: gnb:131-133-35000000 Opening control socket with host 127.0.0.1:4200 Opened control socket server on port 7000 {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Preparing to send subscription in file= xapp.cc, line=487"} Sending subscriptions to: gnb:131-133-31000000 xApp connected: 127.0.0.1:59360 Opening RX thread with agent 127.0.0.1 {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Sending subscription in file= xapp.cc, line=538 for MEID gnb:131-133-31000000"} {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Sending subscription in file= xapp.cc, line=538 for MEID gnb:131-133-31000000"} ``` ::: :::spoiler **KPM Data** ```bash! {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Attempting to retrieve KPM data from SDL..."} {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Sending subscription in file= xapp.cc, line=538 for MEID gnb:131-133-31000000"} {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"SDL data not available. Using dummy data."} add_request_entry gnb:131-133-31000000 Added status pending to request gnb:131-133-31000000 {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Sending thread 132578989082432"} {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Sent KPM data to Python xApp."} {"ts":1754401295109,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Message Sent: RMR State = RMR_OK"} ``` ::: :::spoiler **RIC-Control** ```bash! 2025-08-05 13:41:35,109 INFO Received KPM data from xapp-sm-connector: {"cell_load":0.85,"packet_drop_rate":0.02} 2025-08-05 13:41:35,110 INFO High cell load detected (0.85). Suggesting to increase bandwidth. Received message from Python xApp: {"bandwidth_adjustment": 10, "target_gnb": "gnb:131-133-31000000"} Sending RIC Control Request {"ts":1754401295110,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Preparing to send control in file= xapp.cc, line=432"} RIC Control Request, gNB gnb:131-133-31000000 {"ts":1754401295110,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Size of msg 3"} 2025-08-05 13:41:35,110 INFO Socket sent 66 bytes with JSON payload: {"bandwidth_adjustment": 10, "target_gnb": "gnb:131-133-31000000"} {"ts":1754401295110,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Sending CTRL REQ in file= xapp.cc, line=471 for MEID gnb:131-133-31000000"} {"ts":1754401295110,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Sending thread 132578543638272"} {"ts":1754401295110,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"Message Sent: RMR State = RMR_OK"} {"ts":1754401295110,"crit":"INFO","id":"hw_xapp_main","mdc":{},"msg":"CTRL REQ SUCCESSFUL in file= xapp.cc, line=475 for MEID gnb:131-133-31000000"} 2025-08-05 13:41:35,110 INFO ==================================== {"ts":1754401295110,"crit":"DEBUG","id":"hw_xapp_main","mdc":{},"msg":"Freeing E2AP Control Request object memory"} {"ts":1754401295110,"crit":"DEBUG","id":"hw_xapp_main","mdc":{},"msg":"Freed E2AP Control Request object mempory"} {"ts":1754401295110,"crit":"DEBUG","id":"hw_xapp_main","mdc":{},"msg":"Freeing E2AP Control Request object memory"} {"ts":1754401295110,"crit":"DEBUG","id":"hw_xapp_main","mdc":{},"msg":"Freed E2AP Control Request object mempory"} 2025-08-05 13:41:35,110 INFO Control cycle complete. 2025-08-05 13:41:35,110 INFO ==================================== ``` ::: ## Conclusion - All components have been integrated in the Docker environment - kpimon couldnt decode RIC-Indication message because of the mismatched type between ns3 and kpimon E2AP and E2SM ASN.1 encoding - bw-xapp could create strategy based on KPM data and sends RIC-Control message to the gnb - bw-xapp couldn't retrieve the real KPM information from SDL since the kpimon xApp is not working