Browse code

modules/ims_charging: added access-network-information data to CCR -allows OCS to know location of UE when charge was made -tested with 3GPP EUTRAN FDD using utran-cell-id-3gpp as base station id

Jason Penton authored on 26/02/2015 19:57:33
Showing 8 changed files
... ...
@@ -87,7 +87,7 @@ out_of_memory:
87 87
 }
88 88
 
89 89
 ims_information_t * new_ims_information(event_type_t * event_type, time_stamps_t * time_stamps, str * user_session_id, str * outgoing_session_id, str * calling_party, 
90
-	str * called_party, str * icid, str * orig_ioi, str * term_ioi, int node_role, str *incoming_trunk_id, str *outgoing_trunk_id) {
90
+	str * called_party, str * icid, str * orig_ioi, str * term_ioi, int node_role, str *incoming_trunk_id, str *outgoing_trunk_id, str* pani) {
91 91
 
92 92
     str_list_slot_t *sl = 0;
93 93
     ims_information_t *x = 0;
... ...
@@ -123,6 +123,10 @@ ims_information_t * new_ims_information(event_type_t * event_type, time_stamps_t
123 123
     
124 124
     if (outgoing_trunk_id && outgoing_trunk_id->s)
125 125
         str_dup_ptr(x->outgoing_trunk_id, *outgoing_trunk_id, pkg);
126
+    
127
+    if (pani && pani->s) {
128
+		str_dup_ptr(x->access_network_info, *pani, pkg);
129
+    }
126 130
 
127 131
     //WL_FREE_ALL(&(x->called_asserted_identity),str_list_t,pkg);
128 132
     //str_free_ptr(x->requested_party_address,pkg);
... ...
@@ -239,6 +243,7 @@ void ims_information_free(ims_information_t *x) {
239 239
     
240 240
     str_free_ptr(x->incoming_trunk_id, pkg);
241 241
     str_free_ptr(x->outgoing_trunk_id, pkg);
242
+    str_free_ptr(x->access_network_info, pkg);
242 243
 
243 244
     time_stamps_free(x->time_stamps);
244 245
 
... ...
@@ -271,7 +271,8 @@ typedef struct {
271 271
     str_list_t calling_party_address;
272 272
     str *called_party_address;
273 273
     str_list_t called_asserted_identity;
274
-    str * requested_party_address;
274
+    str *requested_party_address;
275
+    str *access_network_info;
275 276
 
276 277
     time_stamps_t *time_stamps;
277 278
 
... ...
@@ -398,7 +399,8 @@ ims_information_t * new_ims_information(event_type_t * event_type,
398 398
         str * term_ioi,
399 399
         int node_role,
400 400
 	str *incoming_trunk_id,
401
-	str *outgoing_trunk_id);
401
+	str *outgoing_trunk_id,
402
+        str *pani);
402 403
 
403 404
 void event_type_free(event_type_t *x);
404 405
 void time_stamps_free(time_stamps_t *x);
... ...
@@ -108,6 +108,10 @@ int Ro_write_ims_information_avps(AAA_AVP_LIST * avp_list, ims_information_t* x)
108 108
 	cdp_avp->cdp->AAAFreeAVPList(&aList);
109 109
         aList.head = aList.tail = 0;
110 110
     }
111
+    
112
+    if (x->access_network_info) {
113
+		cdp_avp->imsapp.add_Access_Network_Information(&aList2, *(x->access_network_info), 0);
114
+    }
111 115
 
112 116
     for (sl = x->called_asserted_identity.head; sl; sl = sl->next) {
113 117
         if (!cdp_avp->epcapp.add_Called_Asserted_Identity(&aList2, sl->data, 0))
... ...
@@ -380,7 +380,7 @@ int get_timestamps(struct sip_msg * req, struct sip_msg * reply, time_t * req_ti
380 380
  */
381 381
 
382 382
 Ro_CCR_t * dlg_create_ro_session(struct sip_msg * req, struct sip_msg * reply, AAASession ** authp, int dir, str asserted_identity,
383
-	str called_asserted_identity, str subscription_id, int subscription_id_type, str* incoming_trunk_id, str *outgoing_trunk_id) {
383
+	str called_asserted_identity, str subscription_id, int subscription_id_type, str* incoming_trunk_id, str *outgoing_trunk_id, str* pani) {
384 384
 
385 385
     Ro_CCR_t * ro_ccr_data = 0;
386 386
     AAASession * auth = NULL;
... ...
@@ -419,7 +419,7 @@ Ro_CCR_t * dlg_create_ro_session(struct sip_msg * req, struct sip_msg * reply, A
419 419
 	goto error;
420 420
 
421 421
     if (!(ims_info = new_ims_information(event_type, time_stamps, &callid, &callid, &asserted_identity, &called_asserted_identity, &icid,
422
-	    &orig_ioi, &term_ioi, dir, incoming_trunk_id, outgoing_trunk_id)))
422
+	    &orig_ioi, &term_ioi, dir, incoming_trunk_id, outgoing_trunk_id, pani)))
423 423
 	goto error;
424 424
     event_type = 0;
425 425
     time_stamps = 0;
... ...
@@ -467,13 +467,13 @@ out_of_memory:
467 467
 }
468 468
 
469 469
 int sip_create_ro_ccr_data(struct sip_msg * msg, int dir, Ro_CCR_t ** ro_ccr_data, AAASession ** auth, str asserted_identity, str called_asserted_identity,
470
-	str subscription_id, int subscription_id_type, str* incoming_trunk_id, str* outgoing_trunk_id) {
470
+	str subscription_id, int subscription_id_type, str* incoming_trunk_id, str* outgoing_trunk_id, str* pani) {
471 471
 
472 472
     if (msg->first_line.type == SIP_REQUEST) {
473 473
 	/*end of session*/
474 474
 	if (strncmp(msg->first_line.u.request.method.s, "INVITE", 6) == 0) {
475 475
 	    if (!(*ro_ccr_data = dlg_create_ro_session(msg, NULL, auth, dir, asserted_identity, called_asserted_identity, subscription_id,
476
-		    subscription_id_type, incoming_trunk_id, outgoing_trunk_id)))
476
+		    subscription_id_type, incoming_trunk_id, outgoing_trunk_id, pani)))
477 477
 		goto error;
478 478
 	}
479 479
     } else {
... ...
@@ -526,7 +526,7 @@ void send_ccr_interim(struct ro_session* ro_session, unsigned int used, unsigned
526 526
 	goto error;
527 527
 
528 528
     if (!(ims_info = new_ims_information(event_type, time_stamps, &ro_session->callid, &ro_session->callid, &ro_session->asserted_identity,
529
-	    &ro_session->called_asserted_identity, 0, 0, 0, ro_session->direction, &ro_session->incoming_trunk_id, &ro_session->outgoing_trunk_id)))
529
+	    &ro_session->called_asserted_identity, 0, 0, 0, ro_session->direction, &ro_session->incoming_trunk_id, &ro_session->outgoing_trunk_id, 0)))
530 530
 	goto error;
531 531
 
532 532
     LM_DBG("Created IMS information\n");
... ...
@@ -760,7 +760,7 @@ void send_ccr_stop(struct ro_session *ro_session) {
760 760
 	goto error0;
761 761
 
762 762
     if (!(ims_info = new_ims_information(event_type, time_stamps, &ro_session->callid, &ro_session->callid, &ro_session->asserted_identity,
763
-	    &ro_session->called_asserted_identity, 0, 0, 0, ro_session->direction, &ro_session->incoming_trunk_id, &ro_session->outgoing_trunk_id)))
763
+	    &ro_session->called_asserted_identity, 0, 0, 0, ro_session->direction, &ro_session->incoming_trunk_id, &ro_session->outgoing_trunk_id, 0)))
764 764
 	goto error0;
765 765
 
766 766
     event_type = 0;
... ...
@@ -926,7 +926,7 @@ error:
926 926
  * @returns #CSCF_RETURN_BREAK if OK, #CSCF_RETURN_ERROR on error
927 927
  */
928 928
 int Ro_Send_CCR(struct sip_msg *msg, struct dlg_cell *dlg, int dir, int reservation_units, str* incoming_trunk_id, str* outgoing_trunk_id,
929
-	cfg_action_t* action, unsigned int tindex, unsigned int tlabel) {
929
+	str* pani, cfg_action_t* action, unsigned int tindex, unsigned int tlabel) {
930 930
     str session_id = {0, 0},
931 931
     called_asserted_identity = {0, 0},
932 932
     subscription_id = {0, 0},
... ...
@@ -1044,7 +1044,7 @@ int Ro_Send_CCR(struct sip_msg *msg, struct dlg_cell *dlg, int dir, int reservat
1044 1044
     //create a session object without auth and diameter session id - we will add this later.
1045 1045
     new_session = build_new_ro_session(dir, 0, 0, &session_id, &dlg->callid,
1046 1046
 	    &asserted_identity, &called_asserted_identity, &mac, dlg->h_entry, dlg->h_id,
1047
-	    reservation_units, 0, active_rating_group, active_service_identifier, incoming_trunk_id, outgoing_trunk_id);
1047
+	    reservation_units, 0, active_rating_group, active_service_identifier, incoming_trunk_id, outgoing_trunk_id, pani);
1048 1048
 
1049 1049
     if (!new_session) {
1050 1050
 	LM_ERR("Couldn't create new Ro Session - this is BAD!\n");
... ...
@@ -1056,7 +1056,7 @@ int Ro_Send_CCR(struct sip_msg *msg, struct dlg_cell *dlg, int dir, int reservat
1056 1056
     ssd->tlabel = tlabel;
1057 1057
     ssd->ro_session = new_session;
1058 1058
 
1059
-    if (!sip_create_ro_ccr_data(msg, dir, &ro_ccr_data, &cc_acc_session, asserted_identity, called_asserted_identity, subscription_id, subscription_id_type, incoming_trunk_id, outgoing_trunk_id))
1059
+    if (!sip_create_ro_ccr_data(msg, dir, &ro_ccr_data, &cc_acc_session, asserted_identity, called_asserted_identity, subscription_id, subscription_id_type, incoming_trunk_id, outgoing_trunk_id, pani))
1060 1060
 	goto error;
1061 1061
 
1062 1062
     if (!ro_ccr_data)
... ...
@@ -1096,7 +1096,7 @@ int Ro_Send_CCR(struct sip_msg *msg, struct dlg_cell *dlg, int dir, int reservat
1096 1096
 	LM_ERR("Problem adding Multiple Service Credit Control data\n");
1097 1097
 	goto error;
1098 1098
     }
1099
-
1099
+    
1100 1100
     /* before we send, update our session object with CC App session ID and data */
1101 1101
     new_session->auth_appid = cc_acc_session->application_id;
1102 1102
     new_session->auth_session_type = cc_acc_session->type;
... ...
@@ -15,7 +15,7 @@ struct interim_ccr {
15 15
 void credit_control_session_callback(int event, void* session);
16 16
 void remove_aaa_session(str *session_id);
17 17
 int Ro_Send_CCR(struct sip_msg *msg, struct dlg_cell *dlg, int dir, int reservation_units, 
18
-	    str *incoming_trunk_id, str *outgoing_trunk_id, cfg_action_t* action, unsigned int tindex, unsigned int tlabel);
18
+	    str *incoming_trunk_id, str *outgoing_trunk_id, str *enb_cell_id, cfg_action_t* action, unsigned int tindex, unsigned int tlabel);
19 19
 void send_ccr_interim(struct ro_session* ro_session, unsigned int used, unsigned int reserve);
20 20
 void send_ccr_stop(struct ro_session *ro_session);
21 21
 int get_direction_as_int(str* direction);
... ...
@@ -325,6 +325,7 @@ static int w_ro_ccr(struct sip_msg *msg, char* c_route_name, char* c_direction,
325 325
 	int ret = RO_RETURN_TRUE;
326 326
 	int dir = 0;
327 327
 	str identity = {0, 0},
328
+	pani = {0,0},
328 329
 	contact = {0, 0};
329 330
 	struct hdr_field *h=0;
330 331
 	
... ...
@@ -393,6 +394,7 @@ static int w_ro_ccr(struct sip_msg *msg, char* c_route_name, char* c_direction,
393 393
 			goto send_ccr;
394 394
 		}
395 395
 		
396
+		pani = cscf_get_access_network_info(msg, &h);
396 397
 	} else if (dir == RO_TERM_DIRECTION){
397 398
 		//get callee IMPU from called part id - if not present then skip this
398 399
 		if ((identity = cscf_get_public_identity_from_called_party_id(msg, &h)).len == 0) {
... ...
@@ -503,7 +505,7 @@ send_ccr:
503 503
 		goto done;
504 504
 	}
505 505
 	
506
-	ret = Ro_Send_CCR(msg, dlg, dir, reservation_units, &s_incoming_trunk_id, &s_outgoing_trunk_id, cfg_action, tindex, tlabel);
506
+	ret = Ro_Send_CCR(msg, dlg, dir, reservation_units, &s_incoming_trunk_id, &s_outgoing_trunk_id, &pani, cfg_action, tindex, tlabel);
507 507
 	
508 508
 	if(ret < 0){
509 509
 	    LM_ERR("Failed to send CCR\n");
... ...
@@ -177,7 +177,7 @@ void destroy_dlg_table(void) {
177 177
 
178 178
 struct ro_session* build_new_ro_session(int direction, int auth_appid, int auth_session_type, str *session_id, str *callid, str *asserted_identity, 
179 179
 	str* called_asserted_identity, str* mac, unsigned int dlg_h_entry, unsigned int dlg_h_id, unsigned int requested_secs, unsigned int validity_timeout,
180
-	int active_rating_group, int active_service_identifier, str *incoming_trunk_id, str *outgoing_trunk_id){
180
+	int active_rating_group, int active_service_identifier, str *incoming_trunk_id, str *outgoing_trunk_id, str *pani){
181 181
     LM_DBG("Building Ro Session **********");
182 182
     char *p;
183 183
     unsigned int len = session_id->len + callid->len + asserted_identity->len + called_asserted_identity->len + mac->len + incoming_trunk_id->len + outgoing_trunk_id->len + sizeof (struct ro_session);
... ...
@@ -192,6 +192,11 @@ struct ro_session* build_new_ro_session(int direction, int auth_appid, int auth_
192 192
     LM_DBG("New Ro Session given memory at address [%p]\n", new_ro_session);
193 193
 
194 194
     memset(new_ro_session, 0, len);
195
+    
196
+    if (pani->len < MAX_PANI_LEN) {
197
+		p = new_ro_session->pani;
198
+		memcpy(p, pani->s, pani->len);
199
+    }
195 200
 
196 201
     new_ro_session->direction = direction;
197 202
     new_ro_session->auth_appid = auth_appid;
... ...
@@ -20,6 +20,8 @@
20 20
 #define RO_SESSION_FLAG_CHANGED      (1<<2) /*!< ro session has been updated */
21 21
 #define RO_SESSION_FLAG_DELETED      (1<<3) /*!< ro session has been deleted */
22 22
 
23
+#define MAX_PANI_LEN 100
24
+
23 25
 enum ro_session_event_type {
24 26
     pending,
25 27
     answered,
... ...
@@ -50,6 +52,7 @@ struct ro_session {
50 50
     str called_asserted_identity;
51 51
     str incoming_trunk_id;
52 52
     str outgoing_trunk_id;
53
+    char pani[MAX_PANI_LEN];
53 54
     unsigned int hop_by_hop;
54 55
     struct ro_tl ro_tl;
55 56
     unsigned int reserved_secs;
... ...
@@ -191,7 +194,7 @@ void remove_aaa_session(str *session_id);
191 191
 
192 192
 struct ro_session* build_new_ro_session(int direction, int auth_appid, int auth_session_type, str *session_id, str *callid, str *asserted_identity, str* called_asserted_identity, 
193 193
 	str* mac, unsigned int dlg_h_entry, unsigned int dlg_h_id, unsigned int requested_secs, unsigned int validity_timeout,
194
-	int active_rating_group, int active_service_identifier, str *incoming_trunk_id, str *outgoing_trunk_id);
194
+	int active_rating_group, int active_service_identifier, str *incoming_trunk_id, str *outgoing_trunk_id, str *pani);
195 195
 
196 196
 /*!
197 197
  * \brief Refefence a ro_session with locking