/*
 *	A lie!  It always returns!
 */
static rlm_rcode_t sometimes_return(void *instance, RADIUS_PACKET *packet,
				    RADIUS_PACKET *reply)
{
	uint32_t hash;
	int value;
	rlm_sometimes_t *inst = instance;
	VALUE_PAIR *vp;

	/*
	 *	Set it to NOOP and the module will always do nothing
	 */
	if (inst->rcode == RLM_MODULE_NOOP) return inst->rcode;

	/*
	 *	Hash based on the given key.  Usually User-Name.
	 */
	vp = pairfind(packet->vps, inst->da->attr, inst->da->vendor, TAG_ANY);
	if (!vp) return RLM_MODULE_NOOP;

	hash = fr_hash(&vp->data, vp->length);
	hash &= 0xff;		/* ensure it's 0..255 */
	value = hash;

	/*
	 *	Ranges are INCLUSIVE.
	 *	[start,end] returns "rcode"
	 *	Everything else returns "noop"
	 */
	if (value < inst->start) return RLM_MODULE_NOOP;
	if (value > inst->end) return RLM_MODULE_NOOP;

	/*
	 *	If we're returning "handled", then set the packet
	 *	code in the reply, so that the server responds.
	 */
	if ((inst->rcode == RLM_MODULE_HANDLED) && reply) {
		switch (packet->code) {
		case PW_AUTHENTICATION_REQUEST:
			reply->code = PW_AUTHENTICATION_ACK;
			break;

		case PW_ACCOUNTING_REQUEST:
			reply->code = PW_ACCOUNTING_RESPONSE;
			break;

		case PW_COA_REQUEST:
			reply->code = PW_COA_ACK;
			break;

		case PW_DISCONNECT_REQUEST:
			reply->code = PW_DISCONNECT_ACK;
			break;

		default:
			break;
		}
	}

	return inst->rcode;
}
Exemple #2
0
static uint32_t dict_value_value_hash(const void *data)
{
	uint32_t hash;
	const DICT_VALUE *dval = data;

	hash = fr_hash(&dval->attr, sizeof(dval->attr));
	return fr_hash_update(&dval->value, sizeof(dval->value), hash);
}
Exemple #3
0
static uint32_t dict_attr_value_hash(const void *data)
{
	uint32_t hash;
	const DICT_ATTR *attr = data;

	hash = fr_hash(&attr->vendor, sizeof(attr->vendor));
	return fr_hash_update(&attr->attr, sizeof(attr->attr), hash);
}
Exemple #4
0
/*
 *	Take the key fields of a request packet, and convert it to a
 *	hash.
 */
uint32_t fr_request_packet_hash(const RADIUS_PACKET *packet)
{
	uint32_t hash;

	if (packet->hash) return packet->hash;

	hash = fr_hash(&packet->sockfd, sizeof(packet->sockfd));
	hash = fr_hash_update(&packet->src_port, sizeof(packet->src_port),
				hash);
	hash = fr_hash_update(&packet->dst_port,
				sizeof(packet->dst_port), hash);
	hash = fr_hash_update(&packet->src_ipaddr.af,
				sizeof(packet->src_ipaddr.af), hash);

	/*
	 *	The caller ensures that src & dst AF are the same.
	 */
	switch (packet->src_ipaddr.af) {
	case AF_INET:
		hash = fr_hash_update(&packet->src_ipaddr.ipaddr.ip4addr,
					sizeof(packet->src_ipaddr.ipaddr.ip4addr),
					hash);
		hash = fr_hash_update(&packet->dst_ipaddr.ipaddr.ip4addr,
					sizeof(packet->dst_ipaddr.ipaddr.ip4addr),
					hash);
		break;
	case AF_INET6:
		hash = fr_hash_update(&packet->src_ipaddr.ipaddr.ip6addr,
					sizeof(packet->src_ipaddr.ipaddr.ip6addr),
					hash);
		hash = fr_hash_update(&packet->dst_ipaddr.ipaddr.ip6addr,
					sizeof(packet->dst_ipaddr.ipaddr.ip6addr),
					hash);
		break;
	default:
		break;
	}

	return fr_hash_update(&packet->id, sizeof(packet->id), hash);
}
Exemple #5
0
static uint32_t packet_dst2id_hash(const void *data)
{
	uint32_t hash;
	const fr_packet_dst2id_t *pd = data;

	hash = fr_hash(&pd->dst_port, sizeof(pd->dst_port));

	switch (pd->dst_ipaddr.af) {
	case AF_INET:
		hash = fr_hash_update(&pd->dst_ipaddr.ipaddr.ip4addr,
					sizeof(pd->dst_ipaddr.ipaddr.ip4addr),
					hash);
		break;
	case AF_INET6:
		hash = fr_hash_update(&pd->dst_ipaddr.ipaddr.ip6addr,
					sizeof(pd->dst_ipaddr.ipaddr.ip6addr),
					hash);
		break;
	default:
		break;
	}

	return hash;
}
Exemple #6
0
static uint32_t pid_hash(const void *data)
{
	const thread_fork_t *tf = data;

	return fr_hash(&tf->pid, sizeof(tf->pid));
}
Exemple #7
0
static uint32_t dict_vendor_value_hash(const void *data)
{
	return fr_hash(&(((const DICT_VENDOR *)data)->vendorpec),
			 sizeof(((const DICT_VENDOR *)data)->vendorpec));
}
Exemple #8
0
static uint32_t detail_hash(void const *data)
{
	DICT_ATTR const *da = data;
	return fr_hash(&da, sizeof(da));
}
Exemple #9
0
uint32_t hash_state(const void *data)
{
	const struct radius_state_node *p = data;
	return fr_hash(p->data, p->datalen);
}
/*
 *	A lie!  It always returns!
 */
static rlm_rcode_t sometimes_return(void const *instance, REQUEST *request, RADIUS_PACKET *packet, RADIUS_PACKET *reply)
{
	uint32_t		hash;
	uint32_t		value;
	rlm_sometimes_t const	*inst = instance;
	VALUE_PAIR		*vp;

	/*
	 *	Set it to NOOP and the module will always do nothing
	 */
	if (inst->rcode == RLM_MODULE_NOOP) return inst->rcode;

	/*
	 *	Hash based on the given key.  Usually User-Name.
	 */
	tmpl_find_vp(&vp, request, inst->key);
	if (!vp) return RLM_MODULE_NOOP;

	switch (vp->vp_type) {
	case FR_TYPE_OCTETS:
	case FR_TYPE_STRING:
		hash = fr_hash(vp->data.datum.ptr, vp->vp_length);
		break;

	case FR_TYPE_ABINARY:
		hash = fr_hash(vp->vp_filter, vp->vp_length);
		break;

	case FR_TYPE_STRUCTURAL:
		return RLM_MODULE_FAIL;

	default:
		hash = fr_hash(&vp->data.datum, fr_value_box_field_sizes[vp->vp_type]);
		break;
	}
	hash &= 0xff;		/* ensure it's 0..255 */
	value = hash;

	/*
	 *	Ranges are INCLUSIVE.
	 *	[start,end] returns "rcode"
	 *	Everything else returns "noop"
	 */
	if (value < inst->start) return RLM_MODULE_NOOP;
	if (value > inst->end) return RLM_MODULE_NOOP;

	/*
	 *	If we're returning "handled", then set the packet
	 *	code in the reply, so that the server responds.
	 */
	if ((inst->rcode == RLM_MODULE_HANDLED) && reply) {
		switch (packet->code) {
		case FR_CODE_ACCESS_REQUEST:
			reply->code = FR_CODE_ACCESS_ACCEPT;
			break;

		case FR_CODE_ACCOUNTING_REQUEST:
			reply->code = FR_CODE_ACCOUNTING_RESPONSE;
			break;

		case FR_CODE_COA_REQUEST:
			reply->code = FR_CODE_COA_ACK;
			break;

		case FR_CODE_DISCONNECT_REQUEST:
			reply->code = FR_CODE_DISCONNECT_ACK;
			break;

		default:
			break;
		}
	}

	return inst->rcode;
}