The FreeRADIUS server $Id: 15bac2a4c627c01d1aa2047687b3418955ac7f00 $
|
#include <freeradius-devel/radius/defs.h>
#include <freeradius-devel/util/packet.h>
#include <freeradius-devel/util/rand.h>
#include <freeradius-devel/util/log.h>
#include <freeradius-devel/util/dbuff.h>
#include <freeradius-devel/io/test_point.h>
Go to the source code of this file.
Data Structures | |
struct | fr_radius_attr_flags_t |
struct | fr_radius_ctx_t |
struct | fr_radius_decode_ctx_t |
struct | fr_radius_encode_ctx_t |
struct | fr_radius_tag_ctx_t |
Functions | |
void | _fr_packet_log_hex (fr_log_t const *log, fr_packet_t const *packet, char const *file, int line) |
ssize_t | fr_packet_encode (fr_packet_t *packet, fr_pair_list_t *list, fr_packet_t const *original, char const *secret)) |
Encode a packet. | |
bool | fr_packet_ok (fr_packet_t *packet, uint32_t max_attributes, bool require_message_authenticator, fr_radius_decode_fail_t *reason)) |
See if the data pointed to by PTR is a valid RADIUS packet. | |
fr_packet_t * | fr_packet_recv (TALLOC_CTX *ctx, int fd, int flags, uint32_t max_attributes, bool require_message_authenticator) |
Receive UDP client requests, and fill in the basics of a fr_packet_t structure. | |
int | fr_packet_send (fr_packet_t *packet, fr_pair_list_t *list, fr_packet_t const *original, char const *secret)) |
Reply to the request. | |
int | fr_packet_sign (fr_packet_t *packet, fr_packet_t const *original, char const *secret)) |
Sign a previously encoded packet. | |
int | fr_packet_verify (fr_packet_t *packet, fr_packet_t *original, char const *secret)) |
Verify the Request/Response Authenticator (and Message-Authenticator if present) of a packet. | |
int | fr_radius_allow_reply (int code, bool allowed[static FR_RADIUS_CODE_MAX]) |
ssize_t | fr_radius_ascend_secret (fr_dbuff_t *dbuff, uint8_t const *in, size_t inlen, char const *secret, uint8_t const *vector) |
Do Ascend-Send / Recv-Secret calculation. | |
static fr_radius_attr_flags_t const * | fr_radius_attr_flags (fr_dict_attr_t const *da) |
Return RADIUS-specific flags for a given attribute. | |
ssize_t | fr_radius_decode (TALLOC_CTX *ctx, fr_pair_list_t *out, uint8_t *packet, size_t packet_len, fr_radius_decode_ctx_t *decode_ctx) |
ssize_t | fr_radius_decode_abinary (fr_pair_t *vp, uint8_t const *data, size_t data_len) |
Print an Ascend binary filter attribute to a string,. | |
ssize_t | fr_radius_decode_foreign (TALLOC_CTX *ctx, fr_pair_list_t *out, uint8_t const *data, size_t data_len) |
ssize_t | fr_radius_decode_pair (TALLOC_CTX *ctx, fr_pair_list_t *list, uint8_t const *data, size_t data_len, fr_radius_decode_ctx_t *packet_ctx) |
Create a "normal" fr_pair_t from the given data. | |
ssize_t | fr_radius_decode_pair_value (TALLOC_CTX *ctx, fr_pair_list_t *list, fr_dict_attr_t const *parent, uint8_t const *data, size_t const attr_len, void *packet_ctx) |
Create any kind of VP from the attribute contents. | |
ssize_t | fr_radius_decode_simple (TALLOC_CTX *ctx, fr_pair_list_t *out, uint8_t *packet, size_t packet_len, uint8_t const *vector, char const *secret)) |
Simple wrapper for callers who just need a shared secret. | |
ssize_t | fr_radius_decode_tlv (TALLOC_CTX *ctx, fr_pair_list_t *list, fr_dict_attr_t const *parent, uint8_t const *data, size_t data_len, fr_radius_decode_ctx_t *packet_ctx) |
Convert TLVs to one or more VPs. | |
int | fr_radius_decode_tlv_ok (uint8_t const *data, size_t length, size_t dv_type, size_t dv_length) |
Check if a set of RADIUS formatted TLVs are OK. | |
ssize_t | fr_radius_encode (fr_dbuff_t *dbuff, fr_pair_list_t *vps, fr_radius_encode_ctx_t *packet_ctx) |
ssize_t | fr_radius_encode_abinary (fr_pair_t const *vp, fr_dbuff_t *dbuff) |
Encode a string to abinary. | |
ssize_t | fr_radius_encode_foreign (fr_dbuff_t *dbuff, fr_pair_list_t const *list) |
ssize_t | fr_radius_encode_pair (fr_dbuff_t *dbuff, fr_dcursor_t *cursor, void *encode_ctx) |
Encode a data structure into a RADIUS attribute. | |
static bool | fr_radius_flag_extended (fr_dict_attr_t const *da) |
void | fr_radius_global_free (void) |
int | fr_radius_global_init (void) |
bool | fr_radius_ok (uint8_t const *packet, size_t *packet_len_p, uint32_t max_attributes, bool require_message_authenticator, fr_radius_decode_fail_t *reason)) |
See if the data pointed to by PTR is a valid RADIUS packet. | |
void | fr_radius_packet_header_log (fr_log_t const *log, fr_packet_t *packet, bool received) |
void | fr_radius_packet_log (fr_log_t const *log, fr_packet_t *packet, fr_pair_list_t *list, bool received) |
ssize_t | fr_radius_recv_header (int sockfd, fr_ipaddr_t *src_ipaddr, uint16_t *src_port, unsigned int *code) |
Basic validation of RADIUS packet header. | |
int | fr_radius_sign (uint8_t *packet, uint8_t const *vector, uint8_t const *secret, size_t secret_len)) |
Sign a previously encoded packet. | |
int | fr_radius_verify (uint8_t *packet, uint8_t const *vector, uint8_t const *secret, size_t secret_len, bool require_message_authenticator, bool limit_proxy_state)) |
Verify a request / response packet. | |
struct fr_radius_attr_flags_t |
Data Fields | ||
---|---|---|
unsigned int | abinary: 1 | Attribute is in "abinary" format. |
unsigned int | concat: 1 | Attribute is concatenated. |
fr_radius_attr_flags_encrypt_t | encrypt | Attribute is encrypted. |
unsigned int | extended: 1 | Attribute is an extended attribute. |
unsigned int | has_tag: 1 | Attribute has a tag. |
unsigned int | long_extended: 1 | Attribute is a long extended attribute. |
struct fr_radius_ctx_t |
struct fr_radius_decode_ctx_t |
Data Fields | ||
---|---|---|
fr_radius_ctx_t const * | common | |
uint8_t const * | end | end of the packet |
bool | limit_proxy_state | Don't allow Proxy-State in requests. |
uint8_t const * | request_authenticator | |
uint8_t | request_code | original code for the request. |
bool | require_message_authenticator | |
fr_pair_list_t * | tag_root | Where to insert tag attributes. |
TALLOC_CTX * | tag_root_ctx | Where to allocate new tag attributes. |
fr_radius_tag_ctx_t ** | tags | for decoding tagged attributes |
TALLOC_CTX * | tmp_ctx | for temporary things cleaned up during decoding |
bool | tunnel_password_zeros | check for trailing zeros on decode |
bool | verify | can skip verify for dynamic clients |
struct fr_radius_encode_ctx_t |
Data Fields | ||
---|---|---|
bool | add_proxy_state | do we add a Proxy-State? |
uint8_t | code | |
fr_radius_ctx_t const * | common | |
bool | disallow_tunnel_passwords | not all packets can have tunnel passwords |
uint8_t | id | |
fr_fast_rand_t | rand_ctx | for tunnel passwords |
uint8_t const * | request_authenticator | |
uint8_t | request_code | |
int | salt_offset | for tunnel passwords |
bool | seen_message_authenticator | |
uint8_t | tag | current tag for encoding |
struct fr_radius_tag_ctx_t |
#define AUTH_PASS_LEN (RADIUS_AUTH_VECTOR_LENGTH) |
#define fr_packet_log_hex | ( | _log, | |
_packet | |||
) | _fr_packet_log_hex(_log, _packet, __FILE__, __LINE__) |
#define fr_radius_flag_abinary | ( | _da | ) | fr_radius_attr_flags(_da)->abinary |
#define fr_radius_flag_concat | ( | _da | ) | fr_radius_attr_flags(_da)->concat |
#define fr_radius_flag_encrypted | ( | _da | ) | fr_radius_attr_flags(_da)->encrypt |
#define fr_radius_flag_has_tag | ( | _da | ) | fr_radius_attr_flags(_da)->has_tag |
#define fr_radius_flag_long_extended | ( | _da | ) | fr_radius_attr_flags(_da)->long_extended |
#define FR_RADIUS_PACKET_CODE_VALID | ( | _x | ) | ((_x > 0) && (_x < FR_RADIUS_CODE_MAX)) |
Failure reasons.
Control whether Proxy-State is allowed in Access-Requests.
Control whether Message-Authenticator is required in Access-Requests.
void _fr_packet_log_hex | ( | fr_log_t const * | log, |
fr_packet_t const * | packet, | ||
char const * | file, | ||
int | line | ||
) |
ssize_t fr_packet_encode | ( | fr_packet_t * | packet, |
fr_pair_list_t * | list, | ||
fr_packet_t const * | original, | ||
char const * | secret | ||
) |
bool fr_packet_ok | ( | fr_packet_t * | packet, |
uint32_t | max_attributes, | ||
bool | require_message_authenticator, | ||
fr_radius_decode_fail_t * | reason | ||
) |
See if the data pointed to by PTR is a valid RADIUS packet.
Packet is not 'const * const' because we may update data_len, if there's more data in the UDP packet than in the RADIUS packet.
[in] | packet | to check. |
[in] | max_attributes | to decode. |
[in] | require_message_authenticator | to require Message-Authenticator. |
[out] | reason | if not NULL, will have the failure reason written to where it points. |
Definition at line 119 of file packet.c.
fr_packet_t * fr_packet_recv | ( | TALLOC_CTX * | ctx, |
int | fd, | ||
int | flags, | ||
uint32_t | max_attributes, | ||
bool | require_message_authenticator | ||
) |
Receive UDP client requests, and fill in the basics of a fr_packet_t structure.
Definition at line 205 of file packet.c.
int fr_packet_send | ( | fr_packet_t * | packet, |
fr_pair_list_t * | list, | ||
fr_packet_t const * | original, | ||
char const * | secret | ||
) |
int fr_packet_sign | ( | fr_packet_t * | packet, |
fr_packet_t const * | original, | ||
char const * | secret | ||
) |
int fr_packet_verify | ( | fr_packet_t * | packet, |
fr_packet_t * | original, | ||
char const * | secret | ||
) |
int fr_radius_allow_reply | ( | int | code, |
bool | allowed[static FR_RADIUS_CODE_MAX] | ||
) |
ssize_t fr_radius_ascend_secret | ( | fr_dbuff_t * | dbuff, |
uint8_t const * | in, | ||
size_t | inlen, | ||
char const * | secret, | ||
uint8_t const * | vector | ||
) |
Do Ascend-Send / Recv-Secret calculation.
The secret is hidden by xoring with a MD5 digest created from the RADIUS shared secret and the authentication vector. We put them into MD5 in the reverse order from that used when encrypting passwords to RADIUS.
Definition at line 247 of file base.c.
|
inlinestatic |
ssize_t fr_radius_decode | ( | TALLOC_CTX * | ctx, |
fr_pair_list_t * | out, | ||
uint8_t * | packet, | ||
size_t | packet_len, | ||
fr_radius_decode_ctx_t * | decode_ctx | ||
) |
Print an Ascend binary filter attribute to a string,.
Grrr... Ascend makes the server do this work, instead of doing it on the NAS.
[in,out] | vp | Where the decoded string will be stored. |
[in] | data | binary data to decodee |
[in] | data_len | length of the binary data to decodee |
Definition at line 1316 of file abinary.c.
ssize_t fr_radius_decode_foreign | ( | TALLOC_CTX * | ctx, |
fr_pair_list_t * | out, | ||
uint8_t const * | data, | ||
size_t | data_len | ||
) |
ssize_t fr_radius_decode_pair | ( | TALLOC_CTX * | ctx, |
fr_pair_list_t * | list, | ||
uint8_t const * | data, | ||
size_t | data_len, | ||
fr_radius_decode_ctx_t * | packet_ctx | ||
) |
ssize_t fr_radius_decode_pair_value | ( | TALLOC_CTX * | ctx, |
fr_pair_list_t * | out, | ||
fr_dict_attr_t const * | parent, | ||
uint8_t const * | data, | ||
size_t const | attr_len, | ||
void * | decode_ctx | ||
) |
Create any kind of VP from the attribute contents.
"length" is AT LEAST the length of this attribute, as we expect the caller to have verified the data with fr_packet_ok(). "length" may be up to the length of the packet.
This function will ONLY return -1 on programmer error or OOM. If there's anything wrong with the attribute, it will ALWAYS create a "raw" attribute.
Definition at line 1475 of file decode.c.
ssize_t fr_radius_decode_simple | ( | TALLOC_CTX * | ctx, |
fr_pair_list_t * | out, | ||
uint8_t * | packet, | ||
size_t | packet_len, | ||
uint8_t const * | vector, | ||
char const * | secret | ||
) |
ssize_t fr_radius_decode_tlv | ( | TALLOC_CTX * | ctx, |
fr_pair_list_t * | list, | ||
fr_dict_attr_t const * | parent, | ||
uint8_t const * | data, | ||
size_t | data_len, | ||
fr_radius_decode_ctx_t * | packet_ctx | ||
) |
ssize_t fr_radius_encode | ( | fr_dbuff_t * | dbuff, |
fr_pair_list_t * | vps, | ||
fr_radius_encode_ctx_t * | packet_ctx | ||
) |
ssize_t fr_radius_encode_abinary | ( | fr_pair_t const * | vp, |
fr_dbuff_t * | dbuff | ||
) |
Encode a string to abinary.
This routine will call routines to parse entries from an ASCII format to a binary format recognized by the Ascend boxes.
vp | VP to encode |
dbuff | where to write the VP data |
Definition at line 1192 of file abinary.c.
ssize_t fr_radius_encode_foreign | ( | fr_dbuff_t * | dbuff, |
fr_pair_list_t const * | list | ||
) |
ssize_t fr_radius_encode_pair | ( | fr_dbuff_t * | dbuff, |
fr_dcursor_t * | cursor, | ||
void * | encode_ctx | ||
) |
Encode a data structure into a RADIUS attribute.
This is the main entry point into the encoder. It sets up the encoder array we use for tracking our TLV/VSA nesting and then calls the appropriate dispatch function.
[out] | dbuff | Where to write encoded data. |
[in] | cursor | Specifying attribute to encode. |
[in] | encode_ctx | Additional data such as the shared secret to use. |
Definition at line 1515 of file encode.c.
|
static |
void fr_radius_global_free | ( | void | ) |
int fr_radius_global_init | ( | void | ) |
bool fr_radius_ok | ( | uint8_t const * | packet, |
size_t * | packet_len_p, | ||
uint32_t | max_attributes, | ||
bool | require_message_authenticator, | ||
fr_radius_decode_fail_t * | reason | ||
) |
See if the data pointed to by PTR is a valid RADIUS packet.
[in] | packet | to check. |
[in,out] | packet_len_p | The size of the packet data. |
[in] | max_attributes | to allow in the packet. |
[in] | require_message_authenticator | whether we require Message-Authenticator. |
[in] | reason | if not NULL, will have the failure reason written to where it points. |
Definition at line 515 of file base.c.
void fr_radius_packet_header_log | ( | fr_log_t const * | log, |
fr_packet_t * | packet, | ||
bool | received | ||
) |
void fr_radius_packet_log | ( | fr_log_t const * | log, |
fr_packet_t * | packet, | ||
fr_pair_list_t * | list, | ||
bool | received | ||
) |
ssize_t fr_radius_recv_header | ( | int | sockfd, |
fr_ipaddr_t * | src_ipaddr, | ||
uint16_t * | src_port, | ||
unsigned int * | code | ||
) |
Basic validation of RADIUS packet header.
[in] | sockfd | we're reading from. |
[out] | src_ipaddr | of the packet. |
[out] | src_port | of the packet. |
[out] | code | Pointer to where to write the packet code. |
Definition at line 285 of file base.c.
int fr_radius_sign | ( | uint8_t * | packet, |
uint8_t const * | vector, | ||
uint8_t const * | secret, | ||
size_t | secret_len | ||
) |
Sign a previously encoded packet.
Calculates the request/response authenticator for packets which need it, and fills in the message-authenticator value if the attribute is present in the encoded packet.
[in,out] | packet | (request or response). |
[in] | vector | original packet vector to use |
[in] | secret | to sign the packet with. |
[in] | secret_len | The length of the secret. |
Definition at line 358 of file base.c.
int fr_radius_verify | ( | uint8_t * | packet, |
uint8_t const * | vector, | ||
uint8_t const * | secret, | ||
size_t | secret_len, | ||
bool | require_message_authenticator, | ||
bool | limit_proxy_state | ||
) |
Verify a request / response packet.
This function does its work by calling fr_radius_sign(), and then comparing the signature in the packet with the one we calculated. If they differ, there's a problem.
[in] | packet | the raw RADIUS packet (request or response) |
[in] | vector | the original packet vector |
[in] | secret | the shared secret |
[in] | secret_len | the length of the secret |
[in] | require_message_authenticator | whether we require Message-Authenticator. |
[in] | limit_proxy_state | whether we allow Proxy-State without Message-Authenticator. |
Definition at line 778 of file base.c.
|
extern |
|
extern |
|
extern |
|
extern |