ngap_gNB_context_management_procedures.c 11.5 KB
Newer Older
zhenghuangkun's avatar
zhenghuangkun committed
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
/*
 * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The OpenAirInterface Software Alliance licenses this file to You under
 * the OAI Public License, Version 1.1  (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.openairinterface.org/?page_id=698
 *
 * 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.
 *-------------------------------------------------------------------------------
 * For more information about the OpenAirInterface (OAI) Software Alliance:
 *      contact@openairinterface.org
 */

/*! \file ngap_gNB_context_management_procedures.c
 * \brief NGAP context management procedures
zhenghuangkun's avatar
zhenghuangkun committed
24 25 26
 * \author  Yoshio INOUE, Masayuki HARADA
 * \date 2020
 * \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
zhenghuangkun's avatar
zhenghuangkun committed
27 28 29
 * \version 1.0
 * @ingroup _ngap
 */
zhenghuangkun's avatar
zhenghuangkun committed
30 31
 

zhenghuangkun's avatar
zhenghuangkun committed
32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>

#include "assertions.h"
#include "conversions.h"

#include "intertask_interface.h"

#include "ngap_common.h"
#include "ngap_gNB_defs.h"

#include "ngap_gNB_itti_messaging.h"

#include "ngap_gNB_encoder.h"
#include "ngap_gNB_nnsf.h"
#include "ngap_gNB_ue_context.h"
#include "ngap_gNB_nas_procedures.h"
#include "ngap_gNB_management_procedures.h"
#include "ngap_gNB_context_management_procedures.h"
yaojie's avatar
yaojie committed
52
#include "NGAP_PDUSessionResourceItemCxtRelReq.h"
zhenghuangkun's avatar
zhenghuangkun committed
53 54 55 56 57 58
#include "msc.h"


int ngap_ue_context_release_complete(instance_t instance,
                                     ngap_ue_release_complete_t *ue_release_complete_p)
{
59

zhenghuangkun's avatar
zhenghuangkun committed
60 61 62 63 64 65 66 67 68 69 70 71 72 73 74
  ngap_gNB_instance_t                 *ngap_gNB_instance_p = NULL;
  struct ngap_gNB_ue_context_s        *ue_context_p        = NULL;
  NGAP_NGAP_PDU_t                      pdu;
  NGAP_UEContextReleaseComplete_t     *out;
  NGAP_UEContextReleaseComplete_IEs_t *ie;
  uint8_t  *buffer;
  uint32_t length;

  /* Retrieve the NGAP gNB instance associated with Mod_id */
  ngap_gNB_instance_p = ngap_gNB_get_instance(instance);

  DevAssert(ue_release_complete_p != NULL);
  DevAssert(ngap_gNB_instance_p != NULL);

  /*RB_FOREACH(ue_context_p, ngap_ue_map, &ngap_gNB_instance_p->ngap_ue_head) {
zhenghuangkun's avatar
zhenghuangkun committed
75 76
    NGAP_WARN("in ngap_ue_map: UE context gNB_ue_ngap_id %u amf_ue_ngap_id %u state %u\n",
        ue_context_p->gNB_ue_ngap_id, ue_context_p->amf_ue_ngap_id,
zhenghuangkun's avatar
zhenghuangkun committed
77 78 79 80 81 82 83 84 85 86 87 88 89
        ue_context_p->ue_state);
  }*/
  if ((ue_context_p = ngap_gNB_get_ue_context(ngap_gNB_instance_p,
                      ue_release_complete_p->gNB_ue_ngap_id)) == NULL) {
    /* The context for this gNB ue ngap id doesn't exist in the map of gNB UEs */
    NGAP_WARN("Failed to find ue context associated with gNB ue ngap id: %u\n",
              ue_release_complete_p->gNB_ue_ngap_id);
    return -1;
  }

  /* Prepare the NGAP message to encode */
  memset(&pdu, 0, sizeof(pdu));
  pdu.present = NGAP_NGAP_PDU_PR_successfulOutcome;
90 91 92 93 94
  pdu.choice.successfulOutcome = CALLOC(1, sizeof(struct NGAP_SuccessfulOutcome));
  pdu.choice.successfulOutcome->procedureCode = NGAP_ProcedureCode_id_UEContextRelease;
  pdu.choice.successfulOutcome->criticality = NGAP_Criticality_reject;
  pdu.choice.successfulOutcome->value.present = NGAP_SuccessfulOutcome__value_PR_UEContextReleaseComplete;
  out = &pdu.choice.successfulOutcome->value.choice.UEContextReleaseComplete;
zhenghuangkun's avatar
zhenghuangkun committed
95 96 97

  /* mandatory */
  ie = (NGAP_UEContextReleaseComplete_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseComplete_IEs_t));
zhenghuangkun's avatar
zhenghuangkun committed
98
  ie->id = NGAP_ProtocolIE_ID_id_AMF_UE_NGAP_ID;
zhenghuangkun's avatar
zhenghuangkun committed
99
  ie->criticality = NGAP_Criticality_ignore;
zhenghuangkun's avatar
zhenghuangkun committed
100
  ie->value.present = NGAP_UEContextReleaseComplete_IEs__value_PR_AMF_UE_NGAP_ID;
101
  asn_uint642INTEGER(&ie->value.choice.AMF_UE_NGAP_ID, ue_context_p->amf_ue_ngap_id);
zhenghuangkun's avatar
zhenghuangkun committed
102 103 104 105
  ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);

  /* mandatory */
  ie = (NGAP_UEContextReleaseComplete_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseComplete_IEs_t));
106
  ie->id = NGAP_ProtocolIE_ID_id_RAN_UE_NGAP_ID;
zhenghuangkun's avatar
zhenghuangkun committed
107
  ie->criticality = NGAP_Criticality_ignore;
108 109
  ie->value.present = NGAP_UEContextReleaseComplete_IEs__value_PR_RAN_UE_NGAP_ID;
  ie->value.choice.RAN_UE_NGAP_ID = ue_release_complete_p->gNB_ue_ngap_id;
zhenghuangkun's avatar
zhenghuangkun committed
110 111 112 113 114 115 116 117 118 119 120
  ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);


  if (ngap_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
    /* Encode procedure has failed... */
    NGAP_ERROR("Failed to encode UE context release complete\n");
    return -1;
  }

  MSC_LOG_TX_MESSAGE(
    MSC_NGAP_GNB,
zhenghuangkun's avatar
zhenghuangkun committed
121
    MSC_NGAP_AMF,
zhenghuangkun's avatar
zhenghuangkun committed
122 123
    buffer,
    length,
124
    MSC_AS_TIME_FMT" UEContextRelease successfulOutcome gNB_ue_ngap_id %u amf_ue_ngap_id %lu",
zhenghuangkun's avatar
zhenghuangkun committed
125 126
    0,0, //MSC_AS_TIME_ARGS(ctxt_pP),
    ue_release_complete_p->gNB_ue_ngap_id,
zhenghuangkun's avatar
zhenghuangkun committed
127
    ue_context_p->amf_ue_ngap_id);
zhenghuangkun's avatar
zhenghuangkun committed
128 129 130

  /* UE associated signalling -> use the allocated stream */
  ngap_gNB_itti_send_sctp_data_req(ngap_gNB_instance_p->instance,
zhenghuangkun's avatar
zhenghuangkun committed
131
                                   ue_context_p->amf_ref->assoc_id, buffer,
zhenghuangkun's avatar
zhenghuangkun committed
132 133 134
                                   length, ue_context_p->tx_stream);

  //LG ngap_gNB_itti_send_sctp_close_association(ngap_gNB_instance_p->instance,
zhenghuangkun's avatar
zhenghuangkun committed
135
  //                                             ue_context_p->amf_ref->assoc_id);
zhenghuangkun's avatar
zhenghuangkun committed
136 137 138 139 140 141 142 143 144 145 146 147 148
  // release UE context
  struct ngap_gNB_ue_context_s *ue_context2_p = NULL;

  if ((ue_context2_p = RB_REMOVE(ngap_ue_map, &ngap_gNB_instance_p->ngap_ue_head, ue_context_p))
      != NULL) {
    NGAP_WARN("Removed UE context gNB_ue_ngap_id %u\n",
              ue_context2_p->gNB_ue_ngap_id);
    ngap_gNB_free_ue_context(ue_context2_p);
  } else {
    NGAP_WARN("Removing UE context gNB_ue_ngap_id %u: did not find context\n",
              ue_context_p->gNB_ue_ngap_id);
  }
  /*RB_FOREACH(ue_context_p, ngap_ue_map, &ngap_gNB_instance_p->ngap_ue_head) {
zhenghuangkun's avatar
zhenghuangkun committed
149 150
    NGAP_WARN("in ngap_ue_map: UE context gNB_ue_ngap_id %u amf_ue_ngap_id %u state %u\n",
        ue_context_p->gNB_ue_ngap_id, ue_context_p->amf_ue_ngap_id,
zhenghuangkun's avatar
zhenghuangkun committed
151 152
        ue_context_p->ue_state);
  }*/
153

zhenghuangkun's avatar
zhenghuangkun committed
154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184
  return 0;
}


int ngap_ue_context_release_req(instance_t instance,
                                ngap_ue_release_req_t *ue_release_req_p)
{
  ngap_gNB_instance_t                *ngap_gNB_instance_p           = NULL;
  struct ngap_gNB_ue_context_s       *ue_context_p                  = NULL;
  NGAP_NGAP_PDU_t                     pdu;
  NGAP_UEContextReleaseRequest_t     *out;
  NGAP_UEContextReleaseRequest_IEs_t *ie;
  uint8_t                            *buffer                        = NULL;
  uint32_t                            length;
  /* Retrieve the NGAP gNB instance associated with Mod_id */
  ngap_gNB_instance_p = ngap_gNB_get_instance(instance);

  DevAssert(ue_release_req_p != NULL);
  DevAssert(ngap_gNB_instance_p != NULL);

  if ((ue_context_p = ngap_gNB_get_ue_context(ngap_gNB_instance_p,
                      ue_release_req_p->gNB_ue_ngap_id)) == NULL) {
    /* The context for this gNB ue ngap id doesn't exist in the map of gNB UEs */
    NGAP_WARN("Failed to find ue context associated with gNB ue ngap id: %u\n",
              ue_release_req_p->gNB_ue_ngap_id);
    return -1;
  }

  /* Prepare the NGAP message to encode */
  memset(&pdu, 0, sizeof(pdu));
  pdu.present = NGAP_NGAP_PDU_PR_initiatingMessage;
185 186 187 188 189
  pdu.choice.initiatingMessage = CALLOC(1, sizeof(struct NGAP_InitiatingMessage));
  pdu.choice.initiatingMessage->procedureCode = NGAP_ProcedureCode_id_UEContextReleaseRequest;
  pdu.choice.initiatingMessage->criticality = NGAP_Criticality_ignore;
  pdu.choice.initiatingMessage->value.present = NGAP_InitiatingMessage__value_PR_UEContextReleaseRequest;
  out = &pdu.choice.initiatingMessage->value.choice.UEContextReleaseRequest;
zhenghuangkun's avatar
zhenghuangkun committed
190 191 192

  /* mandatory */
  ie = (NGAP_UEContextReleaseRequest_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseRequest_IEs_t));
zhenghuangkun's avatar
zhenghuangkun committed
193
  ie->id = NGAP_ProtocolIE_ID_id_AMF_UE_NGAP_ID;
zhenghuangkun's avatar
zhenghuangkun committed
194
  ie->criticality = NGAP_Criticality_reject;
zhenghuangkun's avatar
zhenghuangkun committed
195
  ie->value.present = NGAP_UEContextReleaseRequest_IEs__value_PR_AMF_UE_NGAP_ID;
196
  asn_uint642INTEGER(&ie->value.choice.AMF_UE_NGAP_ID, ue_context_p->amf_ue_ngap_id);
zhenghuangkun's avatar
zhenghuangkun committed
197 198 199 200
  ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);

  /* mandatory */
  ie = (NGAP_UEContextReleaseRequest_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseRequest_IEs_t));
201
  ie->id = NGAP_ProtocolIE_ID_id_RAN_UE_NGAP_ID;
zhenghuangkun's avatar
zhenghuangkun committed
202
  ie->criticality = NGAP_Criticality_reject;
203 204
  ie->value.present = NGAP_UEContextReleaseRequest_IEs__value_PR_RAN_UE_NGAP_ID;
  ie->value.choice.RAN_UE_NGAP_ID = ue_release_req_p->gNB_ue_ngap_id;
zhenghuangkun's avatar
zhenghuangkun committed
205 206
  ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);

yaojie's avatar
yaojie committed
207 208 209
  /* optional */
  if (ue_release_req_p->nb_of_pdusessions > 0) {
    ie = (NGAP_UEContextReleaseRequest_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseRequest_IEs_t));
yaojie's avatar
yaojie committed
210
    ie->id = NGAP_ProtocolIE_ID_id_PDUSessionResourceListCxtRelReq;
yaojie's avatar
yaojie committed
211 212 213 214 215 216 217 218 219 220 221
    ie->criticality = NGAP_Criticality_reject;
    ie->value.present = NGAP_UEContextReleaseRequest_IEs__value_PR_PDUSessionResourceListCxtRelReq;
    for (int i = 0; i < ue_release_req_p->nb_of_pdusessions; i++) {
      NGAP_PDUSessionResourceItemCxtRelReq_t     *item;
      item = (NGAP_PDUSessionResourceItemCxtRelReq_t *)calloc(1,sizeof(NGAP_PDUSessionResourceItemCxtRelReq_t));
      item->pDUSessionID = ue_release_req_p->pdusessions[i].pdusession_id;
      ASN_SEQUENCE_ADD(&ie->value.choice.PDUSessionResourceListCxtRelReq.list, item);
    }
    ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
  }

zhenghuangkun's avatar
zhenghuangkun committed
222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271
  /* mandatory */
  ie = (NGAP_UEContextReleaseRequest_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseRequest_IEs_t));
  ie->id = NGAP_ProtocolIE_ID_id_Cause;
  ie->criticality = NGAP_Criticality_ignore;
  ie->value.present = NGAP_UEContextReleaseRequest_IEs__value_PR_Cause;

  switch (ue_release_req_p->cause) {
    case NGAP_Cause_PR_radioNetwork:
      ie->value.choice.Cause.present = NGAP_Cause_PR_radioNetwork;
      ie->value.choice.Cause.choice.radioNetwork = ue_release_req_p->cause_value;
      break;

    case NGAP_Cause_PR_transport:
      ie->value.choice.Cause.present = NGAP_Cause_PR_transport;
      ie->value.choice.Cause.choice.transport = ue_release_req_p->cause_value;
      break;

    case NGAP_Cause_PR_nas:
      ie->value.choice.Cause.present = NGAP_Cause_PR_nas;
      ie->value.choice.Cause.choice.nas = ue_release_req_p->cause_value;
      break;

    case NGAP_Cause_PR_protocol:
      ie->value.choice.Cause.present = NGAP_Cause_PR_protocol;
      ie->value.choice.Cause.choice.protocol = ue_release_req_p->cause_value;
      break;

    case NGAP_Cause_PR_misc:
      ie->value.choice.Cause.present = NGAP_Cause_PR_misc;
      ie->value.choice.Cause.choice.misc = ue_release_req_p->cause_value;
      break;

    case NGAP_Cause_PR_NOTHING:
    default:
      ie->value.choice.Cause.present = NGAP_Cause_PR_NOTHING;
      break;
  }

  ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);



  if (ngap_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
    /* Encode procedure has failed... */
    NGAP_ERROR("Failed to encode UE context release complete\n");
    return -1;
  }

  MSC_LOG_TX_MESSAGE(
    MSC_NGAP_GNB,
zhenghuangkun's avatar
zhenghuangkun committed
272
    MSC_NGAP_AMF,
zhenghuangkun's avatar
zhenghuangkun committed
273 274
    buffer,
    length,
275
    MSC_AS_TIME_FMT" UEContextReleaseRequest initiatingMessage gNB_ue_ngap_id %u amf_ue_ngap_id %lu",
zhenghuangkun's avatar
zhenghuangkun committed
276 277
    0,0,//MSC_AS_TIME_ARGS(ctxt_pP),
    ue_release_req_p->gNB_ue_ngap_id,
zhenghuangkun's avatar
zhenghuangkun committed
278
    ue_context_p->amf_ue_ngap_id);
zhenghuangkun's avatar
zhenghuangkun committed
279 280 281

  /* UE associated signalling -> use the allocated stream */
  ngap_gNB_itti_send_sctp_data_req(ngap_gNB_instance_p->instance,
zhenghuangkun's avatar
zhenghuangkun committed
282
                                   ue_context_p->amf_ref->assoc_id, buffer,
zhenghuangkun's avatar
zhenghuangkun committed
283
                                   length, ue_context_p->tx_stream);
284

zhenghuangkun's avatar
zhenghuangkun committed
285 286 287
  return 0;
}