/**
 * Creates and adds a Vendor-Specifig-Application-ID AVP.
 * @param msg - the Diameter message to add to.
 * @param vendor_id - the value of the vendor_id,
 * @param auth_id - the authorization application id
 * @param acct_id - the accounting application id
 * @returns 1 on success or 0 on error
 */
inline int Ro_add_vendor_specific_appid(AAAMessage *msg, unsigned int vendor_id, unsigned int auth_id, unsigned int acct_id) {
    AAA_AVP_LIST list;
    str group;
    char x[4];

    list.head = 0;
    list.tail = 0;

    set_4bytes(x, vendor_id);
    Ro_add_avp_list(&list, x, 4, AVP_Vendor_Id, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);

    if (auth_id) {
        set_4bytes(x, auth_id);
        Ro_add_avp_list(&list, x, 4, AVP_Auth_Application_Id, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);
    }
    if (acct_id) {
        set_4bytes(x, acct_id);
        Ro_add_avp_list(&list, x, 4, AVP_Acct_Application_Id, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);
    }

    group = cdpb.AAAGroupAVPS(list);

    cdpb.AAAFreeAVPList(&list);

    return Ro_add_avp(msg, group.s, group.len, AVP_Vendor_Specific_Application_Id, AAA_AVP_FLAG_MANDATORY, 0, AVP_FREE_DATA, __FUNCTION__);
}
Beispiel #2
0
/**
 * Send a Capability Exchange Request.
 * \note Must be called with a lock on the peer.
 * @param p - the peer to send to
 */
void I_Snd_CER(peer *p)
{
	AAAMessage *cer=0;
//	AAA_AVP *avp;
	unsigned long ip;
	struct sockaddr_in addr;
	socklen_t addrlen;
	char x[6];
	
	cer = AAANewMessage(Code_CE,0,0,0);
	if (!cer) return;
	cer->hopbyhopId = next_hopbyhop();
	cer->endtoendId = next_endtoend();
	addrlen = sizeof(struct sockaddr_in);
	if (getsockname(p->I_sock,(struct sockaddr*) &addr, &addrlen) == -1) { 
		LOG(L_ERR,"ERROR:I_Snd_CER(): Error on finding local host address > %s\n",strerror(errno));
	}else{
		set_2bytes(x,1);
		ip = htonl(addr.sin_addr.s_addr);
		set_4bytes(x+2,ip);
		AAACreateAndAddAVPToMessage(cer,AVP_Host_IP_Address,AAA_AVP_FLAG_MANDATORY,0,x,6);
	}

	set_4bytes(x,config->vendor_id);
	AAACreateAndAddAVPToMessage(cer,AVP_Vendor_Id,AAA_AVP_FLAG_MANDATORY,0,x,4);
			
	AAACreateAndAddAVPToMessage(cer,AVP_Product_Name,AAA_AVP_FLAG_MANDATORY,0,config->product_name.s,config->product_name.len);

	Snd_CE_add_applications(cer,p);
//	peer_send(p,p->I_sock,cer,1);
	peer_send_msg(p,cer);
}
Beispiel #3
0
/**
 * Send a Capabilities Exchange Answer.
 * Checks whether there are common applications.
 * \note Must be called with a lock on the peer.
 * @param p - peer identification
 * @param cer - the CER message
 * @param result_code - the Result-Code to send
 * @param sock - socket to send through
 */
void Snd_CEA(peer *p,AAAMessage *cer,int result_code,int sock)
{
	AAAMessage *cea;
	unsigned int ip;
	struct sockaddr_in addr;
	socklen_t addrlen;
	char x[6];
	
	cea = AAANewMessage(Code_CE,0,0,cer);	
	if (!cea) goto done;
	
	addrlen = sizeof(struct sockaddr_in);
	if (getsockname(sock,(struct sockaddr*) &addr, &addrlen) == -1) { 
		LOG(L_ERR,"ERROR:Snd_CEA(): Error on finding local host address > %s\n",strerror(errno));
	}else{
		set_2bytes(x,1);
		ip = htonl(addr.sin_addr.s_addr);
		set_4bytes(x+2,ip);
		AAACreateAndAddAVPToMessage(cea,AVP_Host_IP_Address,AAA_AVP_FLAG_MANDATORY,0,x,6);
	}

	set_4bytes(x,config->vendor_id);
	AAACreateAndAddAVPToMessage(cea,AVP_Vendor_Id,AAA_AVP_FLAG_MANDATORY,0,x,4);
			
	AAACreateAndAddAVPToMessage(cea,AVP_Product_Name,AAA_AVP_FLAG_MANDATORY,0,config->product_name.s,config->product_name.len);

	set_4bytes(x,result_code);
	AAACreateAndAddAVPToMessage(cea,AVP_Result_Code,AAA_AVP_FLAG_MANDATORY,0,x,4);

	Snd_CE_add_applications(cea,p);

	peer_send(p,sock,cea,1);
done:	
	AAAFreeMessage(&cer);
}
int AAAAVPBuildBuffer(AAA_AVP *avp, unsigned char *dest)  {
  unsigned char* p = dest;

  if (!avp || !dest) {
    ERROR("trying to build msg buffer from/to NULL avp");
    return 0;
  }
  /* AVP HEADER */
  /* avp code */
  set_4bytes(p,avp->code);
  p +=4;
  /* flags */
  (*p++) = (unsigned char)avp->flags;
  /* avp length */
  set_3bytes(p, (AVP_HDR_SIZE(avp->flags)+avp->data.len) );
  p += 3;
  /* vendor id */
  if ((avp->flags&0x80)!=0) {
    set_4bytes(p,avp->vendorId);
    p +=4;
  }
  /* data */
  memcpy( p, avp->data.s, avp->data.len);
  p += to_32x_len( avp->data.len );  

  return p-dest;
}
void Send_ASR(cdp_session_t* s, AAAMessage* msg) {
    AAAMessage *asr = 0;
    AAA_AVP *avp = 0;
    peer *p = 0;
    char x[4];
    LM_DBG("Send_ASR() : sending ASR\n");
    asr = AAACreateRequest(s->application_id, IMS_ASR, Flag_Proxyable, s);

    if (!asr) {
        LM_ERR("Send_ASR(): error creating ASR!\n");
        return;
    }

    set_4bytes(x, s->application_id);
    avp = AAACreateAVP(AVP_Auth_Application_Id, AAA_AVP_FLAG_MANDATORY, 0, x, 4, AVP_DUPLICATE_DATA);
    AAAAddAVPToMessage(asr, avp, asr->avpList.tail);

    set_4bytes(x, 3); // Not specified
    avp = AAACreateAVP(AVP_IMS_Abort_Cause, AAA_AVP_FLAG_MANDATORY, 0, x, 4, AVP_DUPLICATE_DATA);
    AAAAddAVPToMessage(asr, avp, asr->avpList.tail);
    //todo - add all the other avps

    p = get_routing_peer(s, asr);
    if (!p) {
        LM_ERR("unable to get routing peer in Send_ASR \n");
        if (asr) AAAFreeMessage(&asr); //needed in frequency
    }

    if (!peer_send_msg(p, asr)) {
        if (asr) AAAFreeMessage(&asr); //needed in frequency
    } else
        LM_DBG("success sending ASR\n");
}
inline int Ro_add_cc_request(AAAMessage *msg, unsigned int cc_request_type, unsigned int cc_request_number) {
    char x[4];
    set_4bytes(x, cc_request_type);
    int success = Ro_add_avp(msg, x, 4, AVP_CC_Request_Type, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);

    char y[4];
    set_4bytes(y, cc_request_number);

    return success && Ro_add_avp(msg, y, 4, AVP_CC_Request_Number, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);

}
Beispiel #7
0
/**
 * Groups a list of avps into a data buffer
 * @param avps
 */
str AAAGroupAVPS(AAA_AVP_LIST avps)
{
	AAA_AVP *avp;
	unsigned char *p;
	str buf={0,0};

	/* count and add the avps */
	for(avp=avps.head;avp;avp=avp->next) {
		buf.len += AVP_HDR_SIZE(avp->flags)+ to_32x_len( avp->data.len );
	}

	if (!buf.len) return buf;
	/* allocate some memory */
	buf.s = (char*)shm_malloc( buf.len );
	if (!buf.s) {
		LM_ERR("hss3g_group_avps: no more free memory!\n");
		buf.len=0;
		return buf;
	}
	memset(buf.s, 0, buf.len);
	/* fill in the buffer */
	p = (unsigned char*) buf.s;
	for(avp=avps.head;avp;avp=avp->next) {
		/* AVP HEADER */
		/* avp code */
		set_4bytes(p,avp->code);
		p +=4;
		/* flags */
		(*p++) = (unsigned char)avp->flags;
		/* avp length */
		set_3bytes(p, (AVP_HDR_SIZE(avp->flags)+avp->data.len) );
		p += 3;
		/* vendor id */
		if ((avp->flags&0x80)!=0) {
			set_4bytes(p,avp->vendorId);
			p +=4;
		}
		/* data */
		memcpy( p, avp->data.s, avp->data.len);
		p += to_32x_len( avp->data.len );
	}
	if ((char*)p-buf.s!=buf.len) {
		LM_ERR("BUG:hss3g_group_avps: mismatch between len and buf!\n");
		shm_free( buf.s );
		buf.s = 0;
		buf.len = 0;
		return buf;
	}
	return buf;
}
Beispiel #8
0
/**
 * Send a Capabilities Exchange Answer.
 * Checks whether there are common applications.
 * \note Must be called with a lock on the peer.
 * @param p - peer identification
 * @param cer - the CER message
 * @param result_code - the Result-Code to send
 * @param sock - socket to send through
 */
void Snd_CEA(peer *p,AAAMessage *cer,int result_code,int sock)
{
	AAAMessage *cea;
	unsigned int ip;
	union {
		struct sockaddr addr;
		struct sockaddr_in in;
		struct sockaddr_in6 in6;
	} addr_u ;
	socklen_t addrlen;
	char x[18];
	
	cea = AAANewMessage(Code_CE,0,0,cer);	
	if (!cea) goto done;
	
	addrlen = sizeof(addr_u);
	if (getsockname(sock, &(addr_u.addr), &addrlen) == -1) { 
		LM_ERR("Snd_CEA(): Error on finding local host address > %s\n",strerror(errno));
	}else{
		switch(addr_u.addr.sa_family){
			case AF_INET:
				set_2bytes(x,1);
				ip = htonl(addr_u.in.sin_addr.s_addr);
				set_4bytes(x+2,ip);
				AAACreateAndAddAVPToMessage(cea,AVP_Host_IP_Address,AAA_AVP_FLAG_MANDATORY,0,x,6);
				break;
			case AF_INET6:
				set_2bytes(x,2);
				memcpy(x+2,addr_u.in6.sin6_addr.s6_addr,16);
				AAACreateAndAddAVPToMessage(cea,AVP_Host_IP_Address,AAA_AVP_FLAG_MANDATORY,0,x,18);
				break;
			default:
				LM_ERR("Snd_CEA(): unknown address type with family %d\n",addr_u.addr.sa_family);
		}
	}

	set_4bytes(x,config->vendor_id);
	AAACreateAndAddAVPToMessage(cea,AVP_Vendor_Id,AAA_AVP_FLAG_MANDATORY,0,x,4);
			
	AAACreateAndAddAVPToMessage(cea,AVP_Product_Name,AAA_AVP_FLAG_MANDATORY,0,config->product_name.s,config->product_name.len);

	set_4bytes(x,result_code);
	AAACreateAndAddAVPToMessage(cea,AVP_Result_Code,AAA_AVP_FLAG_MANDATORY,0,x,4);

	Snd_CE_add_applications(cea,p);

	peer_send(p,sock,cea,1);
done:	
	AAAFreeMessage(&cer);
}
void Send_STR(cdp_session_t* s, AAAMessage* msg)
{
	AAAMessage *str=0;
	AAA_AVP *avp=0;
	peer *p=0;
	char x[4];
	LOG(L_DBG, "sending STR\n");
	//if (msg) LOG(L_DBG,"Send_STR() : sending STR for %d, flags %#1x endtoend %u hopbyhop %u\n",msg->commandCode,msg->flags,msg->endtoendId,msg->hopbyhopId);
	//else LOG(L_DBG,"Send_STR() called from AAATerminateAuthSession or some other event\n");
	str = AAACreateRequest(s->application_id,IMS_STR,Flag_Proxyable,s);
	
	if (!str) {
		LOG(L_ERR,"ERR:Send_STR(): error creating STR!\n");
		return;
	}
	if(!dup_routing_avps(msg, str)){
		LOG(L_ERR,"ERR:Send_STR(): error duplicating routing AVPs!\n");
		AAAFreeMessage(&str);
		return;
	}
	if(s->vendor_id!=0 && !add_vendor_specific_application_id_group(str,s->vendor_id,s->application_id)){ 
		LOG(L_ERR,"ERR:Send_STR(): error adding Vendor-Id-Specific-Application-Id Group!\n");
		AAAFreeMessage(&str);
		return;
	}
	
	set_4bytes(x,s->application_id);
	avp = AAACreateAVP(AVP_Auth_Application_Id,AAA_AVP_FLAG_MANDATORY,0,x,4,AVP_DUPLICATE_DATA);
	AAAAddAVPToMessage(str,avp,str->avpList.tail);
	
	set_4bytes(x,4); // Diameter_administrative
	avp = AAACreateAVP(AVP_Termination_Cause,AAA_AVP_FLAG_MANDATORY,0,x,4,AVP_DUPLICATE_DATA);
	AAAAddAVPToMessage(str,avp,str->avpList.tail);
	//todo - add all the other avps

	p = get_routing_peer(str);
	if (!p) {
		LOG(L_ERR,"unable to get routing peer in Send_STR \n");
		if (str) AAAFreeMessage(&str); //needed in frequency
		return;
	}
	//if (str) LOG(L_CRIT,"Send_STR() : sending STR  %d, flags %#1x endtoend %u hopbyhop %u\n",str->commandCode,str->flags,str->endtoendId,str->hopbyhopId);
	if (!peer_send_msg(p,str))
	{
		LOG(L_DBG,"Send_STR peer_send_msg return error!\n");
		if (str) AAAFreeMessage(&str); //needed in frequency	
	} else { 
		LOG(L_DBG,"success sending STR\n");
	}
}
Beispiel #10
0
AAAMessage *send_unknown_request_answer(AAAMessage *req)
{
        AAAMessage *ans=0;
        char x[4];
        AAA_AVP *avp;


        /* UAA header is created based on the UAR */
        ans = AAANewMessage(req->commandCode,req->applicationId,0,req);

        if (!ans) return 0;

        set_4bytes(x,(unsigned int) DIAMETER_UNABLE_TO_COMPLY);

        avp = AAACreateAVP(AVP_Result_Code,AAA_AVP_FLAG_MANDATORY,0,x,4,AVP_DUPLICATE_DATA);
        if (!avp) {
                LOG(L_ERR,"ERR: Failed creating avp for result code\n");
                AAAFreeMessage(&ans);
                return 0;
        }
        if (AAAAddAVPToMessage(ans,avp,ans->avpList.tail)!=AAA_ERR_SUCCESS) {
                LOG(L_ERR,"ERR: Failed adding avp to message\n");
                AAAFreeAVP(&avp);
                AAAFreeMessage(&ans);
                return 0;
        }
        return ans;
}
inline AAA_AVP *cdp_avp_new_Integer32(int avp_code,int avp_flags,int avp_vendorid,int32_t data)
{
	char x[4];
	str s={x,4};
	set_4bytes(x,data);
	return cdp_avp_new(avp_code,avp_flags,avp_vendorid,s,AVP_DUPLICATE_DATA);
}
Beispiel #12
0
/**
 * Send a Capability Exchange Request.
 * \note Must be called with a lock on the peer.
 * @param p - the peer to send to
 */
void I_Snd_CER(peer *p)
{
	AAAMessage *cer=0;
//	AAA_AVP *avp;
	unsigned long ip;
	union {
		struct sockaddr addr;
		struct sockaddr_in in;
		struct sockaddr_in6 in6;
	} addr_u ;
	socklen_t addrlen;
	char x[18];
	
	cer = AAANewMessage(Code_CE,0,0,0);
	if (!cer) return;
	cer->hopbyhopId = next_hopbyhop();
	cer->endtoendId = next_endtoend();
	addrlen = sizeof(addr_u);
	if (getsockname(p->I_sock,&(addr_u.addr), &addrlen) == -1) { 
		LM_ERR("I_Snd_CER(): Error on finding local host address > %s\n",strerror(errno));
	}else{
		switch(addr_u.addr.sa_family){
			case AF_INET:
				set_2bytes(x,1);
				ip = htonl(addr_u.in.sin_addr.s_addr);
				set_4bytes(x+2,ip);
				AAACreateAndAddAVPToMessage(cer,AVP_Host_IP_Address,AAA_AVP_FLAG_MANDATORY,0,x,6);
				break;
			case AF_INET6:
				set_2bytes(x,2);
				memcpy(x+2,addr_u.in6.sin6_addr.s6_addr,16);
				AAACreateAndAddAVPToMessage(cer,AVP_Host_IP_Address,AAA_AVP_FLAG_MANDATORY,0,x,18);
				break;
			default:
				LM_ERR("I_Snd_CER(): unknown address type with family %d\n",addr_u.addr.sa_family);
		}
	}

	set_4bytes(x,config->vendor_id);
	AAACreateAndAddAVPToMessage(cer,AVP_Vendor_Id,AAA_AVP_FLAG_MANDATORY,0,x,4);
			
	AAACreateAndAddAVPToMessage(cer,AVP_Product_Name,AAA_AVP_FLAG_MANDATORY,0,config->product_name.s,config->product_name.len);

	Snd_CE_add_applications(cer,p);
//	peer_send(p,p->I_sock,cer,1);
	peer_send_msg(p,cer);
}
inline int Ro_add_multiple_service_credit_Control(AAAMessage *msg, unsigned int requested_unit, int used_unit, int active_rating_group, int active_service_identifier) {
    // Add Multiple-Services AVP Indicator
    char x[4];
    set_4bytes(x, 1);
    Ro_add_avp(msg, x, 4, AVP_Multiple_Services_Indicator, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);

    AAA_AVP_LIST list, used_list, mscc_list;
    str group, used_group;

    list.head = 0;
    list.tail = 0;
    used_list.head = 0;
    used_list.tail = 0;
    mscc_list.head = 0;
    mscc_list.tail = 0;

    set_4bytes(x, requested_unit);
    Ro_add_avp_list(&list, x, 4, AVP_CC_Time, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);
    group = cdpb.AAAGroupAVPS(list);
    cdpb.AAAFreeAVPList(&list);

    Ro_add_avp_list(&mscc_list, group.s, group.len, AVP_Requested_Service_Unit, AAA_AVP_FLAG_MANDATORY, 0, AVP_FREE_DATA, __FUNCTION__);

    set_4bytes(x, active_service_identifier);
    Ro_add_avp_list(&mscc_list, x, 4, AVP_Service_Identifier, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);

    // Rating Group = -1 => omit Rating group
    if (active_rating_group >= 0) {
      set_4bytes(x, active_rating_group);
      Ro_add_avp_list(&mscc_list, x, 4, AVP_Rating_Group, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);
    }

    /* if we must Used-Service-Unit */
    if (used_unit >= 0) {
        set_4bytes(x, used_unit);
        Ro_add_avp_list(&used_list, x, 4, AVP_CC_Time, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);
        used_group = cdpb.AAAGroupAVPS(used_list);
        cdpb.AAAFreeAVPList(&used_list);
        Ro_add_avp_list(&mscc_list, used_group.s, used_group.len, AVP_Used_Service_Unit, AAA_AVP_FLAG_MANDATORY, 0, AVP_FREE_DATA, __FUNCTION__);
    }

    group = cdpb.AAAGroupAVPS(mscc_list);
    cdpb.AAAFreeAVPList(&mscc_list);

    return Ro_add_avp(msg, group.s, group.len, AVP_Multiple_Services_Credit_Control, AAA_AVP_FLAG_MANDATORY, 0, AVP_FREE_DATA, __FUNCTION__);
}
void Send_ASA(cdp_session_t* s, AAAMessage* msg)
{
	AAAMessage *asa;
	char x[4];
	AAA_AVP *avp;	
	LOG(L_INFO,"Send_ASA():  sending ASA\n");
	if (!s) {
	//send an ASA for UNKNOWN_SESSION_ID - use AAASendMessage()
	// msg is the ASR received
		asa = AAANewMessage(IMS_ASA,0,0,msg);
		if (!asa) return;	
	
		set_4bytes(x,AAA_SUCCESS);
		AAACreateAndAddAVPToMessage(asa,AVP_Result_Code,AAA_AVP_FLAG_MANDATORY,0,x,4);
	
		AAASendMessage(asa,0,0);
	}else{
		// send... many cases... maybe not needed.
		// for now we do the same
		asa = AAANewMessage(IMS_ASA,0,0,msg);
		if (!asa) return;	
	
		set_4bytes(x,AAA_SUCCESS);
		AAACreateAndAddAVPToMessage(asa,AVP_Result_Code,AAA_AVP_FLAG_MANDATORY,0,x,4);
				
		avp = AAAFindMatchingAVP(msg,0,AVP_Origin_Host,0,0);	
		if (avp) {
				// This is because AAASendMessage is not going to find a route to the 
				// the PCRF because TS 29.214 says no Destination-Host and no Auth-Application-Id
				// in the ASA
			LOG(L_INFO,"sending ASA to peer %.*s\n",avp->data.len,avp->data.s); 
			peer *p;
			p = get_peer_by_fqdn(&avp->data);
			if (!peer_send_msg(p,asa)) {
				if (asa) AAAFreeMessage(&asa);	//needed in frequency
			} else  
				LOG(L_INFO,"success sending ASA\n");
		}else if (!AAASendMessage(asa,0,0)) {
			LOG(L_ERR,"Send_ASA() : error sending ASA\n");
		}	
	}	
}
/* called only when building stop record AVPS */
inline int Ro_add_multiple_service_credit_Control_stop(AAAMessage *msg, int used_unit, int active_rating_group, int active_service_identifier) {
    char x[4];
    AAA_AVP_LIST used_list, mscc_list;
    str used_group;

    // Add Multiple-Services AVP Indicator
    set_4bytes(x, 1);
    Ro_add_avp(msg, x, 4, AVP_Multiple_Services_Indicator, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);

    //unsigned int service_id = 1000; //Removed these are now configurable config file params

    //unsigned int rating_group = 500; //Removed these are now configurable config file params

    used_list.head = 0;
    used_list.tail = 0;
    mscc_list.head = 0;
    mscc_list.tail = 0;

    /* if we must Used-Service-Unit */
    if (used_unit >= 0) {
        set_4bytes(x, used_unit);
        Ro_add_avp_list(&used_list, x, 4, AVP_CC_Time, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);
        used_group = cdpb.AAAGroupAVPS(used_list);
        cdpb.AAAFreeAVPList(&used_list);
        Ro_add_avp_list(&mscc_list, used_group.s, used_group.len, AVP_Used_Service_Unit, AAA_AVP_FLAG_MANDATORY, 0, AVP_FREE_DATA, __FUNCTION__);
    }

    set_4bytes(x, active_service_identifier);
    Ro_add_avp_list(&mscc_list, x, 4, AVP_Service_Identifier, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);

    // Rating Group = -1 => omit Rating group
    if (active_rating_group >= 0) {
        set_4bytes(x, active_rating_group);
        Ro_add_avp_list(&mscc_list, x, 4, AVP_Rating_Group, AAA_AVP_FLAG_MANDATORY, 0, AVP_DUPLICATE_DATA, __FUNCTION__);
    }

    used_group = cdpb.AAAGroupAVPS(mscc_list);
    cdpb.AAAFreeAVPList(&mscc_list);

    return Ro_add_avp(msg, used_group.s, used_group.len, AVP_Multiple_Services_Credit_Control, AAA_AVP_FLAG_MANDATORY, 0, AVP_FREE_DATA, __FUNCTION__);
}
Beispiel #16
0
/**
 * Adds the Applications to a Capability Exchange message.
 * \note Must be called with a lock on the peer.
 * @param msg - the message to add to (request/answer)
 * @param p - the peer to add applications from
 */
static inline void Snd_CE_add_applications(AAAMessage *msg,peer *p)
{
	int i;
	app_config *app;
	char x[4];
	AAA_AVP *avp1,*avp2;
	AAA_AVP_LIST list;
	str group;
	list.head=0;list.tail=0;
	
	for(i=0;i<config->applications_cnt;i++){
		app = config->applications+i;
		if (app->vendor==0){
			set_4bytes(x,app->id);
			AAACreateAndAddAVPToMessage(msg,
				(app->type==DP_AUTHORIZATION?AVP_Auth_Application_Id:AVP_Acct_Application_Id),
				AAA_AVP_FLAG_MANDATORY,0,x,4);
		}else{
			set_4bytes(x,app->vendor);
			avp1 = AAACreateAVP(AVP_Vendor_Id,AAA_AVP_FLAG_MANDATORY,0,x,4, AVP_DUPLICATE_DATA);			
			AAAAddAVPToList(&list,avp1);
			
			set_4bytes(x,app->id);
			avp2 = AAACreateAVP((app->type==DP_AUTHORIZATION?AVP_Auth_Application_Id:AVP_Acct_Application_Id),
				AAA_AVP_FLAG_MANDATORY,0,x,4,AVP_DUPLICATE_DATA);			
			AAAAddAVPToList(&list,avp2);
		
			group = AAAGroupAVPS(list);	
			AAAFreeAVPList(&list);
			
			AAACreateAndAddAVPToMessage(msg,
				AVP_Vendor_Specific_Application_Id,
				AAA_AVP_FLAG_MANDATORY,0,group.s,group.len);
			shm_free(group.s);
		}
	}
	for(i=0;i<config->supported_vendors_cnt;i++){
		set_4bytes(x,config->supported_vendors[i]);
		AAACreateAndAddAVPToMessage(msg,AVP_Supported_Vendor_Id,AAA_AVP_FLAG_MANDATORY,0,x,4);					
	}		
}
Beispiel #17
0
/**
 * Creates and adds a Result-Code AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 */
inline int cxdx_add_result_code(AAAMessage *msg,unsigned int data)
{
	char x[4];
	set_4bytes(x,data);
	return 
	cxdx_add_avp(msg,x,4,
		AVP_Result_Code,
		AAA_AVP_FLAG_MANDATORY,
		0,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
}
Beispiel #18
0
/**
 * Creates and adds a Auth-Session-State AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 */
inline int cxdx_add_auth_session_state(AAAMessage *msg,unsigned int data)
{
	char x[4];
	set_4bytes(x,data);
	return 
	cxdx_add_avp(msg,x,4,
		AVP_Auth_Session_State,
		AAA_AVP_FLAG_MANDATORY,
		0,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
}
Beispiel #19
0
/**
 * Creates and adds a SIP-Number-Auth-Items AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 */
inline int cxdx_add_sip_number_auth_items(AAAMessage *msg,unsigned int data)
{
	char x[4];
	set_4bytes(x,data);
	return 
	cxdx_add_avp(msg,x,4,
		AVP_IMS_SIP_Number_Auth_Items,
		AAA_AVP_FLAG_MANDATORY|AAA_AVP_FLAG_VENDOR_SPECIFIC,
		IMS_vendor_id_3GPP,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
}
Beispiel #20
0
/**
 * Creates and adds a Server-Assignment-Type AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 */
inline int cxdx_add_server_assignment_type(AAAMessage *msg,unsigned int data)
{
	char x[4];
	set_4bytes(x,data);
	return 
	cxdx_add_avp(msg,x,4,
		AVP_IMS_Server_Assignment_Type,
		AAA_AVP_FLAG_MANDATORY|AAA_AVP_FLAG_VENDOR_SPECIFIC,
		IMS_vendor_id_3GPP,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
}
Beispiel #21
0
/**
 * Creates and adds Userdata-Available AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 */
inline int cxdx_add_userdata_available(AAAMessage *msg,unsigned int data)
{
	char x[4];
	set_4bytes(x,data);
	return 
	cxdx_add_avp(msg,x,4,
		AVP_IMS_User_Data_Already_Available,
		AAA_AVP_FLAG_MANDATORY|AAA_AVP_FLAG_VENDOR_SPECIFIC,
		IMS_vendor_id_3GPP,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
}
Beispiel #22
0
/**
 * Creates and adds a Authorization-Type AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 */
inline int Cx_add_authorization_type(AAAMessage *msg,unsigned int data)
{
	char x[4];
	set_4bytes(x,data);
	return 
	Cx_add_avp(msg,x,4,
		AVP_IMS_User_Authorization_Type,
		AAA_AVP_FLAG_MANDATORY|AAA_AVP_FLAG_VENDOR_SPECIFIC,
		IMS_vendor_id_3GPP,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
}
Beispiel #23
0
/**
 * Creates and adds a perMbyte_credit AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 */
inline int Rf_add_Credit_perMbyte(AAAMessage *msg, unsigned int data)
{
	char x[4];
	set_4bytes(x,data);
	return 
	Rf_add_avp(msg,x,4,
		AVP_Credit_perMbyte,
		AAA_AVP_FLAG_MANDATORY,
		0,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
	
}
Beispiel #24
0
/**
 * Creates and adds an Acct-Application-Id AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @return 1 on success or 0 on error
 */
inline int Gq_add_auth_application_id(AAAMessage *msg, unsigned int data)
{
	char x[4];
	set_4bytes(x, data);	

	return
	Gq_add_avp(msg, x, 4,
			AVP_Auth_Application_Id,
			AAA_AVP_FLAG_MANDATORY,
			0,
			AVP_DUPLICATE_DATA,
			__FUNCTION__);
}
Beispiel #25
0
/**
 * Creates and adds a Accounting-Number-Type AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 * 
 * TODO should be added by base protocol
 */
inline int Rf_add_accounting_record_number(AAAMessage* msg, unsigned int data)
{
	char x[4];
	set_4bytes(x,data);
	
	return
	Rf_add_avp(msg, x, 4,
		AVP_Accounting_Record_Number,
		AAA_AVP_FLAG_MANDATORY,
		0,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
}
Beispiel #26
0
/**
 * Creates and adds a Experimental-Result-Code AVP.
 * @param msg - the Diameter message to add to.
 * @param data - the value for the AVP payload
 * @returns 1 on success or 0 on error
 */
inline int Cx_add_experimental_result_code(AAAMessage *msg,unsigned int data)
{
	AAA_AVP_LIST list;
	str group;
	char x[4];
	list.head=0;list.tail=0;
		
	set_4bytes(x,data);
	Cx_add_avp_list(&list,
		x,4,
		AVP_IMS_Experimental_Result_Code,
		AAA_AVP_FLAG_MANDATORY,
		0,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
	
	set_4bytes(x,IMS_vendor_id_3GPP);
	Cx_add_avp_list(&list,
		x,4,
		AVP_IMS_Vendor_Id,
		AAA_AVP_FLAG_MANDATORY,
		0,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
	
	
	group = cdpb.AAAGroupAVPS(list);
	
	cdpb.AAAFreeAVPList(&list);
	
	return 
	Cx_add_avp(msg,group.s,group.len,
		AVP_IMS_Experimental_Result,
		AAA_AVP_FLAG_MANDATORY,
		0,
		AVP_FREE_DATA,
		__FUNCTION__);
}
/**
 * Add Session-Timeout, Auth-Lifetime and Auth-Grace-Period AVPs to outgoing messages in case they are missing
 * @param x
 * @param msg
 */
void add_auth_session_timers(cdp_auth_session_t *x,AAAMessage *msg)
{
	AAA_AVP *avp;
	char data[4];
	uint32_t v;
	
	avp = AAAFindMatchingAVP(msg,0,AVP_Authorization_Lifetime,0,0);
	if (!avp){ 
		if (x->lifetime==-1) v=0xFFFFFFFF;
		else {
			v = x->lifetime-time(0);
			if (v<0) v = 0;
		}
		set_4bytes(data,v);
		avp = AAACreateAVP(AVP_Authorization_Lifetime,AAA_AVP_FLAG_MANDATORY,0,data,4,AVP_DUPLICATE_DATA);
		if (avp) AAAAddAVPToMessage(msg,avp,0);
	}
	if (x->lifetime!=-1){
		avp = AAAFindMatchingAVP(msg,0,AVP_Auth_Grace_Period,0,0);
		if (!avp){ 
			v = x->grace_period;
			set_4bytes(data,v);
			avp = AAACreateAVP(AVP_Auth_Grace_Period,AAA_AVP_FLAG_MANDATORY,0,data,4,AVP_DUPLICATE_DATA);
			if (avp) AAAAddAVPToMessage(msg,avp,0);
		}
	}
	avp = AAAFindMatchingAVP(msg,0,AVP_Session_Timeout,0,0);
	if (!avp){ 
		if (x->timeout==-1) v=0xFFFFFFFF;
		else {
			v = x->timeout-time(0);
			if (v<0) v = 0;
		}
		set_4bytes(data,v);
		avp = AAACreateAVP(AVP_Session_Timeout,AAA_AVP_FLAG_MANDATORY,0,data,4,AVP_DUPLICATE_DATA);
		if (avp) AAAAddAVPToMessage(msg,avp,0);
	}
}
Beispiel #28
0
int add_vendor_specific_application_id_group(AAAMessage * msg, unsigned int vendor_id, unsigned int auth_app_id) {
    char x[4];
    AAA_AVP_LIST list_grp = {0, 0};
    AAA_AVP *avp;
    str group = {0, 0};

    set_4bytes(x, vendor_id);
    if (!(avp = AAACreateAVP(AVP_Vendor_Id, AAA_AVP_FLAG_MANDATORY, 0,
            x, 4, AVP_DUPLICATE_DATA))) goto error;
    AAAAddAVPToList(&list_grp, avp);

    set_4bytes(x, auth_app_id);
    if (!(avp = AAACreateAVP(AVP_Auth_Application_Id, AAA_AVP_FLAG_MANDATORY, 0,
            x, 4, AVP_DUPLICATE_DATA))) goto error;
    AAAAddAVPToList(&list_grp, avp);

    group = AAAGroupAVPS(list_grp);
    if (!group.s || !group.len) goto error;

    if (!(avp = AAACreateAVP(AVP_Vendor_Specific_Application_Id, AAA_AVP_FLAG_MANDATORY, 0,
            group.s, group.len, AVP_DUPLICATE_DATA))) goto error;

    if (AAAAddAVPToMessage(msg, avp, msg->avpList.tail) != AAA_ERR_SUCCESS) goto error;

    AAAFreeAVPList(&list_grp);
    shm_free(group.s);
    group.s = NULL;

    return 1;

error:

    AAAFreeAVPList(&list_grp);
    if (group.s) shm_free(group.s);
    return 0;
}
Beispiel #29
0
/** 
 * Creates and adds Expires AVP to an AVP list 
 * @param list - the AVP list to add to.
 * @param data - the value for the AVP payload. 
 * @return 1 on successs or 0 on error
 */
inline int Rf_add_expires(AAA_AVP_LIST* list, unsigned int data)
{
	char x[4];
	set_4bytes(x, data);
	
	
	return
	Rf_add_avp_list(list,
		x,4,
		AVP_IMS_Expires,
		AAA_AVP_FLAG_MANDATORY,
		IMS_vendor_id_3GPP,
		AVP_DUPLICATE_DATA,
		__FUNCTION__);
}
Beispiel #30
0
/**
 * Sends a Diameter Watch-dog Answer.
 * \note Must be called with a lock on the peer.
 * @param p - the peer that the DWR was received from
 * @param dwr - the DWR message
 * @param result_code - the Result-Code to attach to DWA
 * @param sock - socket to send on
 */	
void Snd_DWA(peer *p,AAAMessage *dwr,int result_code,int sock)
{
	AAAMessage *dwa;
	char x[4];	

	dwa = AAANewMessage(Code_DW,0,0,dwr);
	if (!dwa) goto done;	

	set_4bytes(x,result_code);
	AAACreateAndAddAVPToMessage(dwa,AVP_Result_Code,AAA_AVP_FLAG_MANDATORY,0,x,4);
	
	peer_send_msg(p,dwa);
done:	
	AAAFreeMessage(&dwr);
}