From: Alan T. DeKok Date: Fri, 1 Sep 2023 12:47:08 +0000 (-0400) Subject: add packet to Net.* and Net.* to packet functions X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=9ff19ff299a5dfc02488a43f27dd3b47711d2b25;p=thirdparty%2Ffreeradius-server.git add packet to Net.* and Net.* to packet functions --- diff --git a/src/lib/server/base.c b/src/lib/server/base.c index 2421c331578..9a254d62fff 100644 --- a/src/lib/server/base.c +++ b/src/lib/server/base.c @@ -96,6 +96,11 @@ int server_init(CONF_SECTION *cs) */ if (xlat_instantiate() < 0) return -1; + /* + * load the 'Net.' packet attributes. + */ + if (packet_global_init() < 0) return -1; + return 0; } @@ -105,6 +110,10 @@ int server_init(CONF_SECTION *cs) */ void server_free(void) { + /* + * Free any resources used by 'Net.' packet + */ + packet_global_free(); /* * Free xlat instance data, and call any detach methods diff --git a/src/lib/server/base.h b/src/lib/server/base.h index 37e11fb50eb..67f709a1112 100644 --- a/src/lib/server/base.h +++ b/src/lib/server/base.h @@ -47,6 +47,7 @@ RCSIDH(base_h, "$Id$") #include #include #include +#include #include #include #include diff --git a/src/lib/server/libfreeradius-server.mk b/src/lib/server/libfreeradius-server.mk index ce71e18d7d3..0ed6e925387 100644 --- a/src/lib/server/libfreeradius-server.mk +++ b/src/lib/server/libfreeradius-server.mk @@ -23,6 +23,7 @@ SOURCES := \ map_proc.c \ module.c \ module_rlm.c \ + packet.c \ paircmp.c \ pairmove.c \ password.c \ diff --git a/src/lib/server/packet.c b/src/lib/server/packet.c new file mode 100644 index 00000000000..f0204c61435 --- /dev/null +++ b/src/lib/server/packet.c @@ -0,0 +1,149 @@ +/* + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +/** fr_radius_packet_t alloc/free functions + * + * @file src/lib/server/packet.c + * + * @copyright 2023 Network RADIUS SAS (legal@networkradius.com) + */ +RCSID("$Id$") + +#include + +static fr_dict_t const *dict_freeradius; + +extern fr_dict_autoload_t util_packet_dict[]; +fr_dict_autoload_t util_packet_dict[] = { + { .out = &dict_freeradius, .proto = "freeradius" }, + { NULL } +}; + +static fr_dict_attr_t const *attr_net_tlv; +static fr_dict_attr_t const *attr_net_src_ip; +static fr_dict_attr_t const *attr_net_src_port; +static fr_dict_attr_t const *attr_net_dst_ip; +static fr_dict_attr_t const *attr_net_dst_port; +static fr_dict_attr_t const *attr_net_timestamp; + +extern fr_dict_attr_autoload_t util_packet_dict_attr[]; +fr_dict_attr_autoload_t util_packet_dict_attr[] = { + { .out = &attr_net_tlv, .name = "Net", .type = FR_TYPE_TLV, .dict = &dict_freeradius }, + { .out = &attr_net_src_ip, .name = "Net.Src.IP", .type = FR_TYPE_COMBO_IP_ADDR, .dict = &dict_freeradius }, + { .out = &attr_net_src_port, .name = "Net.Src.Port", .type = FR_TYPE_UINT16, .dict = &dict_freeradius }, + { .out = &attr_net_dst_ip, .name = "Net.Dst.IP", .type = FR_TYPE_COMBO_IP_ADDR, .dict = &dict_freeradius }, + { .out = &attr_net_dst_port, .name = "Net.Dst.Port", .type = FR_TYPE_UINT16, .dict = &dict_freeradius }, + { .out = &attr_net_timestamp, .name = "Net.Timestamp", .type = FR_TYPE_DATE, .dict = &dict_freeradius }, + + { NULL } +}; + +/** Allocate a "Net." struct with src/dst host and port. + * + * @param ctx The context in which the packet is allocated. + * @param[in] list #fr_pair_list_t value to resolve to #fr_radius_packet_t. + * @param[out] packet The request packet. + * + * @return + * - 0 on success + * - -1 on error. + */ +int fr_packet_pairs_from_packet(TALLOC_CTX *ctx, fr_pair_list_t *list, fr_radius_packet_t const *packet) +{ + fr_pair_t *vp; + + /* + * @todo - create nested ones! + * + * We can't call main_config_migrate_option_get(), as this file is also included in radclient. :( + */ + vp = fr_pair_afrom_da(ctx, attr_net_src_ip); + if (!vp) return -1; + fr_value_box_ipaddr(&vp->data, attr_net_src_ip, &packet->socket.inet.src_ipaddr, true); + fr_pair_append(list, vp); + + vp = fr_pair_afrom_da(ctx, attr_net_src_port); + if (!vp) return -1; + vp->vp_uint32 = packet->socket.inet.src_port; + fr_pair_append(list, vp); + + vp = fr_pair_afrom_da(ctx, attr_net_dst_ip); + if (!vp) return -1; + fr_value_box_ipaddr(&vp->data, attr_net_dst_ip, &packet->socket.inet.dst_ipaddr, true); + fr_pair_append(list, vp); + + vp = fr_pair_afrom_da(ctx, attr_net_dst_port); + if (!vp) return -1; + vp->vp_uint32 = packet->socket.inet.dst_port; + fr_pair_append(list, vp); + + vp = fr_pair_afrom_da(ctx, attr_net_timestamp); + if (!vp) return -1; + vp->vp_date = fr_time_to_unix_time(packet->timestamp); + fr_pair_append(list, vp); + + return 0; +} + +int fr_packet_pairs_to_packet(fr_radius_packet_t *packet, fr_pair_list_t const *list) +{ + fr_pair_t *vp; + + /* + * @todo - create nested ones! + */ + vp = fr_pair_find_by_da(list, NULL, attr_net_src_ip); + if (vp) packet->socket.inet.src_ipaddr = vp->vp_ip; + + vp = fr_pair_find_by_da(list, NULL, attr_net_src_port); + if (vp) packet->socket.inet.src_port = vp->vp_uint16; + + vp = fr_pair_find_by_da(list, NULL, attr_net_dst_ip); + if (vp) packet->socket.inet.dst_ipaddr = vp->vp_ip; + + vp = fr_pair_find_by_da(list, NULL, attr_net_dst_port); + if (vp) packet->socket.inet.dst_port = vp->vp_uint16; + + vp = fr_pair_find_by_da(list, NULL, attr_net_timestamp); + if (vp) packet->timestamp = fr_time_add(packet->timestamp, vp->vp_time_delta); + + return 0; +} + +/** Initialises the Net. packet attributes. + * + * @note Call log free when the server is done to fix any spurious memory leaks. + * @return + * - 0 on success. + * - -1 on failure. + */ +int packet_global_init(void) +{ + if (fr_dict_autoload(util_packet_dict) < 0) { + error: + fr_perror("packet_global_init"); + return -1; + } + + if (fr_dict_attr_autoload(util_packet_dict_attr) < 0) goto error; + + return 0; +} + +void packet_global_free(void) +{ + fr_dict_autofree(util_packet_dict); +} diff --git a/src/lib/server/packet.h b/src/lib/server/packet.h new file mode 100644 index 00000000000..f107d252e7a --- /dev/null +++ b/src/lib/server/packet.h @@ -0,0 +1,41 @@ +#pragma once +/* + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +/** Structures and functions for packet manipulation + * + * @file src/lib/server/packet.h + * + * copyright 2023 Network RADIUS SAS (legal@networkradius.com) + */ +RCSIDH(server_packet_h, "$Id$") + +#ifdef __cplusplus +extern "C" { +#endif + +#include +#include + +int fr_packet_pairs_from_packet(TALLOC_CTX *ctx, fr_pair_list_t *list, fr_radius_packet_t const *packet); +int fr_packet_pairs_to_packet(fr_radius_packet_t *packet, fr_pair_list_t const *list); + +int packet_global_init(void); +void packet_global_free(void); + +#ifdef __cplusplus +} +#endif