freeradius/freeradius-no-antora-docs.patch
Antonio Torres 58d6a6708a
Rebase to FreeRADIUS 3.2.5
Resolves: RHEL-46784
Signed-off-by: Antonio Torres <antorres@redhat.com>
2024-07-10 11:00:08 +02:00

9268 lines
308 KiB
Diff
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

From: Antonio Torres <antorres@redhat.com>
Date: Tue, 2 Apr 2024
Subject: Remove Antora docs from sources
These files are meant to be used for upstream web documentation, so we don't need them for
distribution in RHEL.
Generated by removing doc/antora directory in FreeRADIUS repo, and requesting the diff:
git diff --patch --stat
Binary files such as *.png might need to be removed manually from patch.
Resolves: https://issues.redhat.com/browse/RHEL-31184
Signed-off-by: Antonio Torres <antorres@redhat.com>
---
doc/antora/antora.yml | 18 -
doc/antora/modules/ROOT/assets/images/favicon.svg | 104 ---
doc/antora/modules/ROOT/nav.adoc | 1 -
doc/antora/modules/ROOT/pages/directories.adoc | 69 --
doc/antora/modules/ROOT/pages/index.adoc | 137 ----
doc/antora/modules/concepts/nav.adoc | 6 -
doc/antora/modules/concepts/pages/aaa.adoc | 60 --
doc/antora/modules/concepts/pages/index.adoc | 8 -
.../pages/modules/ldap/authentication.adoc | 203 -----
doc/antora/modules/developers/nav.adoc | 7 -
doc/antora/modules/developers/pages/bugs.adoc | 194 -----
.../modules/developers/pages/coding-methods.adoc | 235 ------
.../modules/developers/pages/contributing.adoc | 126 ---
doc/antora/modules/developers/pages/coverage.adoc | 11 -
doc/antora/modules/developers/pages/index.adoc | 18 -
doc/antora/modules/developers/pages/profile.adoc | 41 -
.../modules/developers/pages/release-method.adoc | 55 --
doc/antora/modules/howto/nav.adoc | 22 -
doc/antora/modules/howto/pages/index.adoc | 17 -
.../modules/howto/pages/monitoring/index.adoc | 67 --
.../modules/howto/pages/monitoring/statistics.adoc | 336 --------
.../modules/howto/pages/protocols/dhcp/enable.adoc | 213 -----
.../modules/howto/pages/protocols/dhcp/index.adoc | 35 -
.../modules/howto/pages/protocols/dhcp/policy.adoc | 14 -
.../protocols/dhcp/policy_common_options.adoc | 80 --
.../protocols/dhcp/policy_device_options.adoc | 310 -------
.../pages/protocols/dhcp/policy_ippool_access.adoc | 54 --
.../protocols/dhcp/policy_ippool_creation.adoc | 112 ---
.../protocols/dhcp/policy_network_options.adoc | 237 ------
.../protocols/dhcp/policy_subnet_options.adoc | 184 -----
.../howto/pages/protocols/dhcp/prepare.adoc | 59 --
.../modules/howto/pages/protocols/dhcp/test.adoc | 143 ----
.../protocols/proxy/enable_proxy_protocol.adoc | 114 ---
.../howto/pages/protocols/proxy/enable_radsec.adoc | 188 -----
.../modules/howto/pages/protocols/proxy/index.adoc | 126 ---
.../howto/pages/protocols/proxy/radsec_client.adoc | 181 -----
.../pages/protocols/proxy/radsec_with_haproxy.adoc | 134 ----
.../pages/protocols/proxy/radsec_with_traefik.adoc | 128 ---
.../modules/howto/pages/simultaneous_use.adoc | 78 --
doc/antora/modules/installation/nav.adoc | 5 -
.../modules/installation/pages/dependencies.adoc | 35 -
doc/antora/modules/installation/pages/index.adoc | 15 -
.../modules/installation/pages/packages.adoc | 22 -
doc/antora/modules/installation/pages/source.adoc | 199 -----
doc/antora/modules/installation/pages/upgrade.adoc | 737 -----------------
doc/antora/modules/unlang/.gitignore | 1 -
doc/antora/modules/unlang/nav.adoc | 51 --
doc/antora/modules/unlang/pages/attr.adoc | 77 --
doc/antora/modules/unlang/pages/break.adoc | 28 -
doc/antora/modules/unlang/pages/case.adoc | 44 -
doc/antora/modules/unlang/pages/condition/and.adoc | 21 -
doc/antora/modules/unlang/pages/condition/cmp.adoc | 104 ---
doc/antora/modules/unlang/pages/condition/eq.adoc | 30 -
.../modules/unlang/pages/condition/index.adoc | 85 --
doc/antora/modules/unlang/pages/condition/not.adoc | 19 -
.../modules/unlang/pages/condition/operands.adoc | 37 -
doc/antora/modules/unlang/pages/condition/or.adoc | 21 -
.../modules/unlang/pages/condition/para.adoc | 19 -
.../modules/unlang/pages/condition/regex.adoc | 180 -----
.../unlang/pages/condition/return_codes.adoc | 35 -
doc/antora/modules/unlang/pages/default.adoc | 47 --
doc/antora/modules/unlang/pages/else.adoc | 30 -
doc/antora/modules/unlang/pages/elsif.adoc | 43 -
doc/antora/modules/unlang/pages/foreach.adoc | 40 -
doc/antora/modules/unlang/pages/group.adoc | 39 -
doc/antora/modules/unlang/pages/if.adoc | 29 -
doc/antora/modules/unlang/pages/index.adoc | 162 ----
doc/antora/modules/unlang/pages/keywords.adoc | 78 --
doc/antora/modules/unlang/pages/list.adoc | 72 --
doc/antora/modules/unlang/pages/load-balance.adoc | 32 -
doc/antora/modules/unlang/pages/module.adoc | 86 --
.../modules/unlang/pages/module_builtin.adoc | 42 -
doc/antora/modules/unlang/pages/module_method.adoc | 27 -
.../unlang/pages/redundant-load-balance.adoc | 39 -
doc/antora/modules/unlang/pages/redundant.adoc | 42 -
doc/antora/modules/unlang/pages/return.adoc | 36 -
doc/antora/modules/unlang/pages/return_codes.adoc | 17 -
doc/antora/modules/unlang/pages/switch.adoc | 83 --
.../modules/unlang/pages/type/all_types.adoc | 80 --
doc/antora/modules/unlang/pages/type/double.adoc | 39 -
doc/antora/modules/unlang/pages/type/index.adoc | 117 ---
doc/antora/modules/unlang/pages/type/ip.adoc | 15 -
doc/antora/modules/unlang/pages/type/numb.adoc | 11 -
.../unlang/pages/type/string/backticks.adoc | 38 -
.../modules/unlang/pages/type/string/double.adoc | 68 --
.../modules/unlang/pages/type/string/escaping.adoc | 14 -
.../modules/unlang/pages/type/string/single.adoc | 19 -
.../modules/unlang/pages/type/string/unquoted.adoc | 21 -
doc/antora/modules/unlang/pages/update.adoc | 160 ----
.../modules/unlang/pages/xlat/alternation.adoc | 24 -
.../modules/unlang/pages/xlat/attribute.adoc | 54 --
doc/antora/modules/unlang/pages/xlat/builtin.adoc | 891 ---------------------
.../modules/unlang/pages/xlat/character.adoc | 80 --
doc/antora/modules/unlang/pages/xlat/index.adoc | 56 --
doc/antora/modules/unlang/pages/xlat/module.adoc | 18 -
.../modules/unlang/partials/rcode_table.adoc | 39 -
98 files changed, 8578 deletions(-)
diff --git a/doc/antora/antora.yml b/doc/antora/antora.yml
deleted file mode 100644
index 263945a943..0000000000
--- a/doc/antora/antora.yml
+++ /dev/null
@@ -1,18 +0,0 @@
-#
-# Metadata for the freeradius-server component
-# Examples of other components are the PAM module,
-# apache module, and the client library.
-#
-name: freeradius-server
-title: The FreeRADIUS Server
-version: '3.2.5'
-start_page: ROOT:index.adoc
-nav:
-- modules/ROOT/nav.adoc
-- modules/installation/nav.adoc
-- modules/concepts/nav.adoc
-- modules/howto/nav.adoc
-- modules/tutorials/nav.adoc
-- modules/unlang/nav.adoc
-- modules/developers/nav.adoc
-- modules/raddb/nav.adoc
diff --git a/doc/antora/modules/ROOT/assets/images/favicon.svg b/doc/antora/modules/ROOT/assets/images/favicon.svg
deleted file mode 100644
index 7476355932..0000000000
--- a/doc/antora/modules/ROOT/assets/images/favicon.svg
+++ /dev/null
@@ -1,104 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Generator: Adobe Illustrator 19.2.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
-<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
- viewBox="0 0 160 160" style="enable-background:new 0 0 160 160;" xml:space="preserve">
-<style type="text/css">
- .st0{fill:none;stroke:#FFD62B;stroke-width:3;stroke-miterlimit:10;}
- .st1{fill:#B0C3C6;}
- .st2{fill:none;stroke:#DEE7E8;stroke-miterlimit:10;}
- .st3{fill:#00A6E2;}
- .st4{fill:none;stroke:#B0C3C6;stroke-width:2;stroke-miterlimit:10;}
- .st5{fill:#666666;}
- .st6{fill:none;stroke:#B0C3C6;stroke-width:2;stroke-linejoin:round;stroke-miterlimit:10;}
- .st7{fill:#00C9ED;}
- .st8{fill:#FFFFFF;stroke:#B0C3C6;stroke-width:2;stroke-linejoin:round;stroke-miterlimit:10;}
- .st9{fill:#303030;}
- .st10{opacity:0.4;fill:#F6F6F6;}
- .st11{fill:none;stroke:#999999;stroke-width:2;stroke-miterlimit:10;}
- .st12{fill:#999999;}
- .st13{fill:#FFFFFF;}
- .st14{clip-path:url(#SVGID_2_);fill:#2F3537;}
- .st15{opacity:0.3;fill:none;stroke:#9FB1B3;stroke-width:2;stroke-miterlimit:10;}
- .st16{fill:none;stroke:#FFFFFF;stroke-miterlimit:10;}
- .st17{fill:#FFFFFF;stroke:#FFFFFF;stroke-miterlimit:10;}
- .st18{fill:none;stroke:#303030;stroke-miterlimit:10;}
- .st19{opacity:0.8;fill:#B0C3C6;}
- .st20{opacity:0.7;}
- .st21{opacity:0.8;clip-path:url(#SVGID_4_);fill:#00A6E2;}
- .st22{opacity:0.8;fill:#00A6E2;}
- .st23{opacity:0.8;clip-path:url(#SVGID_6_);fill:#00A6E2;}
- .st24{clip-path:url(#SVGID_8_);}
- .st25{clip-path:url(#SVGID_10_);}
- .st26{fill:none;stroke:#B0C3C6;stroke-width:3;stroke-linejoin:round;stroke-miterlimit:10;}
- .st27{opacity:0.3;fill:none;stroke:#9FB1B3;stroke-width:3;stroke-miterlimit:10;}
- .st28{fill:#FFFFFF;stroke:#B0C3C6;stroke-width:3;stroke-linejoin:round;stroke-miterlimit:10;}
- .st29{clip-path:url(#SVGID_12_);fill:#2F3537;}
- .st30{clip-path:url(#SVGID_14_);fill:#B0C3C6;}
- .st31{fill:#33B8E8;}
- .st32{fill:#238DB4;}
- .st33{fill:#E2E7E8;}
- .st34{clip-path:url(#SVGID_16_);}
- .st35{fill:#FFFFFF;stroke:#B0C3C6;stroke-width:2;stroke-miterlimit:10;}
- .st36{fill:#B4CBCE;}
- .st37{fill:#003147;}
- .st38{fill:#FFD62B;}
- .st39{fill:#00B78E;}
- .st40{fill:#FF7824;}
- .st41{fill:#FF3223;}
- .st42{fill:#7955DF;}
- .st43{fill:none;stroke:#FF3223;stroke-width:2;stroke-miterlimit:10;}
- .st44{fill:none;stroke:#00A6E2;stroke-width:2;stroke-miterlimit:10;}
- .st45{clip-path:url(#SVGID_18_);fill:#303030;}
- .st46{fill:#F5C81F;}
- .st47{fill:#F49F90;}
- .st48{fill:#F3EEDE;}
- .st49{fill-rule:evenodd;clip-rule:evenodd;fill:#FFFFFF;}
- .st50{fill:#00131F;}
- .st51{clip-path:url(#SVGID_20_);fill:#303030;}
- .st52{fill:none;stroke:#FFFFFF;stroke-width:2;stroke-miterlimit:10;}
- .st53{clip-path:url(#SVGID_22_);fill:#303030;}
- .st54{clip-path:url(#SVGID_24_);fill:#303030;}
-</style>
-<path class="st0" d="M72.3,25.6c0,0-2.3-3.2-6-2.3"/>
-<g>
- <polygon class="st50" points="79.2,73 20.3,37.9 86.2,19.3 145.1,54.4 "/>
- <g>
- <g>
- <g>
- <g>
- <path class="st3" d="M126.2,113.6c-4.4,0-8.2-3-9.3-7.1c2.8,1,5.7,1.6,8.8,1.6c4.4,0,7.9-3.5,7.9-7.9c0-4.4-3.5-7.9-7.9-7.9
- c-5.3,0-9.9-4.3-9.9-9.6c0-0.7,0-2.1,0-2.1v-6.1c0-19.4-15.7-35.2-35.2-35.2c-19.4,0-35.2,15.7-35.2,35.2v6.1c0,0,0,1.3,0,2.1
- c0,5.3-4.6,9.6-9.9,9.6c-4.4,0-7.9,3.5-7.9,7.9c0,4.4,3.5,7.9,7.9,7.9c3.5,0,6.8-0.7,9.8-2c-1,4.3-4.8,7.5-9.4,7.5
- c-4.4,0-7.9,3.5-7.9,7.9c0,4.4,3.5,7.9,7.9,7.9c6.9,0,13.2-2.8,17.8-7.3v10.4c0,4.4,3.5,7.9,7.9,7.9c4.4,0,7.9-3.5,7.9-7.9
- v-14.8h3.1v18.7c0,4.4,3.5,7.9,7.9,7.9c4.4,0,7.9-3.5,7.9-7.9v-18.7h3.1v14.8c0,4.4,3.5,7.9,7.9,7.9c4.4,0,7.9-3.5,7.9-7.9
- v-11.4c4.7,5.1,11.3,8.2,18.7,8.2c4.4,0,7.9-3.5,7.9-7.9C134.1,117.1,130.5,113.6,126.2,113.6z"/>
- <g>
- <circle class="st13" cx="80" cy="76.9" r="17.5"/>
- <g>
- <defs>
- <circle id="SVGID_19_" cx="80" cy="76.9" r="17.5"/>
- </defs>
- <use xlink:href="#SVGID_19_" style="overflow:visible;fill:#FFFFFF;"/>
- <clipPath id="SVGID_2_">
- <use xlink:href="#SVGID_19_" style="overflow:visible;"/>
- </clipPath>
- <path style="clip-path:url(#SVGID_2_);fill:#303030;" d="M73.3,85.5c-6.7,0-12.2-5.5-12.2-12.2c0-6.7,5.5-12.2,12.2-12.2
- s12.2,5.5,12.2,12.2C85.5,80,80.1,85.5,73.3,85.5z"/>
- </g>
- </g>
- </g>
- </g>
- </g>
- </g>
- <g>
- <path class="st50" d="M46,65.8c0-19.1,15.5-29.7,34.6-29.7s34.6,10.6,34.6,29.7c0,0-9.6-9.8-34.2-9.8S46,65.8,46,65.8z"/>
- </g>
- <g>
- <path class="st0" d="M66.3,23.3c0,0-10.7,2.8-10.2,9.7v20.8"/>
- <line class="st0" x1="56" y1="53.7" x2="59.3" y2="66"/>
- <line class="st0" x1="56" y1="53.7" x2="54" y2="64.7"/>
- <line class="st0" x1="56" y1="53.7" x2="62" y2="59.2"/>
- <line class="st0" x1="56" y1="53.7" x2="50.8" y2="60.4"/>
- </g>
-</g>
-</svg>
diff --git a/doc/antora/modules/ROOT/nav.adoc b/doc/antora/modules/ROOT/nav.adoc
deleted file mode 100644
index 3d924122c1..0000000000
--- a/doc/antora/modules/ROOT/nav.adoc
+++ /dev/null
@@ -1 +0,0 @@
-* xref:index.adoc[Introduction]
diff --git a/doc/antora/modules/ROOT/pages/directories.adoc b/doc/antora/modules/ROOT/pages/directories.adoc
deleted file mode 100644
index 9b16249044..0000000000
--- a/doc/antora/modules/ROOT/pages/directories.adoc
+++ /dev/null
@@ -1,69 +0,0 @@
-= Directories
-
-The directories in the server source are laid out ad follows:
-
-== Documentation
-
-[width="100%",cols="50%,50%",options="header",]
-|===
-| Directory | Description
-| `doc/` | Various snippets of documentation.
-| `doc/introduction/` | Concepts and introduction to FreeRADIUS.
-| `doc/raddb/` | HTML versions of the configuration files.
-| `doc/developers/` | Developer documentation for internal APIs
-| `doc/unlang/` | The unlang processing language.
-| `doc/upgrade/` | How to upgrade from version 3 to version 4.
-| `doc/rfc/` | Copies of the RFCs. If you have Perl, do a `make` in
- that directory, and look at the HTML output.
-| `doc/antora/` | Metadata and documentation source files to build
- an Antora based documentation site.
-| `doc/doxygen/` | Files to build a Doxygen site from the source code.
-| `man/` | Unix Manual pages for the server, configuration files,
- and associated utilities.
-|===
-
-== Utility
-
-[cols=",",options="header",]
-|===
-|Directory | Description
-| `mibs/` | SNMP Mibs for the server.
-| `scripts/` | Sample scripts for startup and maintenance.
-|===
-
-== Configuration
-
-[width="100%",cols="50%,50%",options="header",]
-|===
-| Directory | Description
-| `raddb/` | Sample configuration files for the server.
-| `raddb/mods-available` | Module configuration files.
-| `raddb/mods-enabled` | Directory containing symlinks to `raddb/mods-available`.
- Controls which modules are enabled.
-| `raddb/sites-available` | Virtual servers.
-| `raddb/sites-enabled` | Directory containing symlinks to `raddb/sites-available`.
- Control which virtual servers are enabled.
-|===
-
-== Packaging
-
-[cols=",",options="header",]
-|===
-|Directory | Description
-| `debian/` | Files to build a `freeradius` Debian Linux package.
-| `redhat/` | Additional files for a RedHat Linux system.
-| `suse/` | Additional files for a SuSE (UnitedLinux) system.
-|===
-
-== Source
-
-[cols=",",options="header",]
-|===
-|Directory | Description
-| `src/` | Source code.
-| `src/bin/` | Source code for the daemon and associated utilities.
-| `src/lib/` | Source code for various utility libraries.
-| `src/include/` | Header files.
-| `src/protocols/` | Dynamic frontend plug-in modules.
-| `src/modules/` | Dynamic backend plug-in modules.
-|===
diff --git a/doc/antora/modules/ROOT/pages/index.adoc b/doc/antora/modules/ROOT/pages/index.adoc
deleted file mode 100644
index e9bc7a0954..0000000000
--- a/doc/antora/modules/ROOT/pages/index.adoc
+++ /dev/null
@@ -1,137 +0,0 @@
-= Introduction
-
-This is the documentation for FreeRADIUS, version 3. The documentation
-is available under the Creative Commons Non-Commercial license, as given
-in the `LICENSE` file in this directory.
-
-FreeRADIUS is a complex piece of software with many configuration
-options. However, we have taken great care to make the default
-configuration work in most circumstances. The result is that for most
-simple systems, it is trivial to install and configure the server. For
-those situations, this documentation will serve to answer basic
-questions about functionality, configuration, etc.
-
-For more complex requirements, FreeRADIUS can be difficult to
-configure. The reason for this difficulty is that the server can do
-almost anything, which means that there are a near-infinite number of
-ways to configure it. The question for an administrator, then, is what
-piece of the configuration to change, and how to change it.
-
-This documentation will answer those questions. The FreeRADIUS team has
-put substantial effort into writing the documentation for this release.
-Everything in the server is fully documented, and there are many
-`how-to` guides available.
-
-The documentation is split into sections by subject area, oganized by
-desired outcome. At a high level, the subject areas describe:
-
-* xref:concepts:index.adoc[Concepts] and introduction for newcomers.
-* xref:installation:index.adoc[Installing] and xref:installation:upgrade.adoc[upgrading] FreeRADIUS.
-* The syntax of the xref:unlang:index.adoc[unlang] processing language.
-* The xref:raddb:index.adoc[configuration files] located in `/etc/raddb/`, or `/etc/freeradius/`
-* Various xref:howto:index.adoc[how-to] guides.
-* xref:developers:index.adoc[Developer documentation].
-
-This organization means that for example, the `ldap` module will have
-documention located in multiple places. We feel that organizing the
-documentation by desired _goal_ is better than the alternatives.
-
-Within each section, the documentation is split into small pages, which
-are generally no more than a few screens worth of information. We feel
-that having multiple small pages with cross-links is more helpful than
-having a smaller number of enormous pages. This division ensures that
-(for example) the `how-to` guides are split into a series of small
-steps, each of which can be performed quickly.
-
-We hope that this extended documentation will address any lingering
-concerns about the quality of the FreeRADIUS documentation.
-
-== Changes From Earlier Versions
-
-Administrators who have version 2 and wish to upgrade to version 3
-should read the xref:installation:upgrade.adoc[upgrading] documentation.
-That documentation explains the differences between the two versions, and
-how an existing configuration can be reproduced in the latest
-release. We do _not_ recommend using version 2 configuration files
-with version 3. The configuration files are _not_ compatible across a
-major version upgrade.
-
-== Getting Started with FreeRADIUS
-
-FreeRADIUS can be installed using the pre-built packages available
-from http://packages.networkradius.com[Network RADIUS,
-window="_blank"]. That page contains packages for all common OS
-distributions. New packages are available as soon as a new version
-has been released. Packages for older releases are also available for
-historical purposes.
-
-FreeRADIUS can also be installed from the source code. Please see the
-xref:installation:index.adoc[installation guide] for instructions.
-
-WARNING: Many Operating System distributions ship versions of FreeRADIUS
-which are years out of date. Those versions may contain bugs which have
-been fixed in newer releases. We recommend using the
-http://packages.networkradius.com[Network RADIUS, window="_blank"] packages where
-possible.
-
-Administrators who are new to FreeRADIUS should read the
-xref:concepts:index.adoc[concepts section] as it describes the concepts behind
-FreeRADIUS. It is vital for newcomers to understand these concepts, as the rest
-of the documentation assumes familiarity with them.
-
-A detailed xref:unlang:index.adoc[unlang] reference guide is also available.
-This section describes the syntax and functionality of the keywords,
-data types, etc. used in the `unlang` processing language.
-
-All of the xref:raddb:index.adoc[configuration files] are available in
-hypertext format. In can often be easier to read the configuration files
-in a nicely formatted version, instead of as a fixed-width font in a
-text editor.
-
-For specific problem solving, we recommend the xref:howto:index.adoc[how-to]
-guides. These guides give instructions for reaching high-level goals, or
-for configuring and testing individual xref:howto:modules/index.adoc[modules].
-
-There is also xref:developers:index.adoc[developer documentation]. This section
-documents the APIs for developers. Most people can ignore it.
-
-== Debugging
-
-If you have ANY problems, concerns, or surprises when running the
-server, the the server should be run in debugging mode as root, from the
-command line:
-
-```
-# radiusd -X
-```
-
-It will produce a large number of messages. The answers to many
-questions, and the solution to many problems, can usually be found in
-these messages. When run in a terminal window, error messages will be
-shown in red text, and warning messages will be shown in yellow text.
-
-For other use-cases, please look for `ERROR` or `WARNING` in the
-debug output. In many cases, those messages describe exactly what is
-going wrong, and how to fix it.
-
-For further details, about the debug output see the
-http://wiki.freeradius.org/radiusd-X[radiusd-X, window="_blank"] page on the
-http://wiki.freeradius.org[wiki, window="_blank"].
-
-== Getting Help
-
-We also recommend joining the
-http://lists.freeradius.org/mailman/listinfo/freeradius-users[mailing
-list] in order to ask questions and receive answers. The developers are
-not on Stack Overflow, IRC, or other web sites. While the FreeRADIUS
-source is available on
-https://github.com/FreeRADIUS/freeradius-server/[GitHub, window="_blank"], questions
-posted there will not be answered.
-
-Before posting to the list, please read the
-http://wiki.freeradius.org/list-help[list help, window="_blank"] page. That page explains
-how to run the server in debugging mode; how to understand the debug
-output; and what information to post to the list.
-
-Commercial support for FreeRADIUS is available from
-https://networkradius.com/freeradius-support/[Network RADIUS, window="_blank"].
diff --git a/doc/antora/modules/concepts/nav.adoc b/doc/antora/modules/concepts/nav.adoc
deleted file mode 100644
index 493b956641..0000000000
--- a/doc/antora/modules/concepts/nav.adoc
+++ /dev/null
@@ -1,6 +0,0 @@
-* xref:index.adoc[Concepts]
-** General
-*** xref:aaa.adoc[AAA]
-** Modules
-*** LDAP
-**** xref:modules/ldap/authentication.adoc[Authentication]
diff --git a/doc/antora/modules/concepts/pages/aaa.adoc b/doc/antora/modules/concepts/pages/aaa.adoc
deleted file mode 100644
index 294305cb5b..0000000000
--- a/doc/antora/modules/concepts/pages/aaa.adoc
+++ /dev/null
@@ -1,60 +0,0 @@
-= AAA
-
-== Authorization, Authentication, and Accounting request handling
-
-There are a lot of questions about misconfigured FreeRADIUS servers
-because of misunderstanding of FreeRADIUS operations. This document
-explains how the server operates.
-
-Normally there are two steps in processing an authentication request
-coming from a NAS in FreeRADIUS: authorization and authentication.
-If we use FreeRADIUS as a proxy to re-send the request to another
-RADIUS server there will be additional steps.
-
-=== Authorization
-
-Authorization is the process of finding and returning information
-about what the user is allowed to do. For example, finding out what
-kind of authentication methods they are allowed to run, and what VLAN
-the user should be placed into.
-
-Authorization modules generally "get data" from somewhere,
-e.g. `ldap`, `sql`, `files`, etc.
-
-The authentication method is usually determined when the server gets
-the users credentials from a database. Once the credentials are
-available, the server can authenticate the user.
-
-=== Authentication
-
-Authentication is simply a process of comparing users credentials in
-request with the "known good" credentials retrieved from a
-database. Authentication usually deals with password
-encryption. The modules `pap`, `chap`, `mschap`, etc. do authentication.
-
-Some modules do both authentication and limited authorization. For
-example, the `mschap` module authenticates MS-CHAP credentials, but it
-may also be used as an authorization module, which verifies that
-request contains `MS-CHAP` related attribute. If so, the module
-instructs the server to use `mschap` for authentication, too
-
-These dual modules are usually related to protocol-specific
-attributes, such as the `pap` module for the `User-Password`
-attribute, `chap` for `CHAP-Password`, `mschap` for `MS-CHAP-*`, etc.
-
-=== Request Processing
-
-When the server processes requests, it manages four
-xref:unlang:list.adoc[attribute lists]:
-
-`request`:: attributes taken from the received packet
-
-`reply`:: attributes which will be sent in the reply
-
-`control`:: attributes used to control how the server operates. These are never sent in a packet
-
-`session-state`:: attributes which are saved and restroed across multiple request / reply exchanges.
-
-All of these lists are available to all modules. All of these
-lists are available in xref:unlang:index.adoc[Unlang].
-
diff --git a/doc/antora/modules/concepts/pages/index.adoc b/doc/antora/modules/concepts/pages/index.adoc
deleted file mode 100644
index f2bc25f36f..0000000000
--- a/doc/antora/modules/concepts/pages/index.adoc
+++ /dev/null
@@ -1,8 +0,0 @@
-= Concepts
-
-This section documents concerning the protocols and modules used by the
-FreeRADIUS server.
-
-It intended to provide more theoretical information about particular subjects
-than would be appropriate to include inline in module configurations or as
-sidebars in howto guides.
diff --git a/doc/antora/modules/concepts/pages/modules/ldap/authentication.adoc b/doc/antora/modules/concepts/pages/modules/ldap/authentication.adoc
deleted file mode 100644
index edc553e80a..0000000000
--- a/doc/antora/modules/concepts/pages/modules/ldap/authentication.adoc
+++ /dev/null
@@ -1,203 +0,0 @@
-== Authenticating Users with LDAP
-
-Please be aware the FreeRADIUS is an AAA server, and LDAP
-is a _database_. This separation of roles means that FreeRADIUS
-supports multiple kinds of authentication protocols such as `PAP`,
-`CHAP`, `MS-CHAP`, etc. An LDAP database supports only one
-authentication method: "bind as user". This authentication method is
-compatible only with PAP.
-
-Our recommendation is to use LDAP as a database. FreeRADIUS should
-read the "known good" password from LDAP, and then use that
-information to authenticate the user. It is almost always wrong to
-use the LDAP "bind as user" method for authenticating users.
-
-The only caveat to the above recommendation is Active Directory. For
-"security" reasons, Active Directory will not return the "known good"
-password to FreeRADIUS over a standard LDAP query. Therefore when
-Active Directory is used, the choices are:
-
-PAP::
-Use "bind as user"
-
-MS-CHAP::
-Use xref:raddb:mods-available/ntlm_auth.adoc[`ntlm`] or xref:raddb:mods-available/winbind.adoc[`winbind`].
-
-Due to the limitations of Active Directory, There are unfortunately no
-other possible choices.
-
-== LDAP Security Recommendations
-
-The credentials (username *and* password) for FreeRADIUS to use to
-connect to your LDAP server(s) should be secure. We make the
-following recommendations for LDAP "best practices" security.
-
-* Create a dedicated account for use by FreeRADIUS
-
-* Ensure that this account does not have administrator access
-
-* Ensure that this account is read-only, and has no write permissions
-
-* Start by using 'simple authentication' instead of
- https://en.wikipedia.org/wiki/Simple_Authentication_and_Security_Layer[SASL].
- The SASL protocol should be attempted only after 'simple
- authentication' has been verified to work.
-
-* Use TLS for connecting between FreeRADIUS and the LDAP server. See
- the `tls` sub-section of the default `ldap` module for instructions
-
-* When storing RADIUS user profiles (quotas, `Simultaneous-Use` flags,
- access time restrictions, etc) in LDAP, the LDAP schema
- `doc/schemas/ldap/openldap/freeradius-radius.schema` must first be imported
- into the LDAP server.
-
-== Authentication method compatibility
-
-The LDAP module is compatible a few different kinds of authentication
-methods. Note that we say _compatible_, and not _supports_. LDAP
-servers are databases, and do not support authentication protocols
-such as CHAP, MS-CHAP, or EAP.
-
-PAP::
-The user supplies a `User-Password` (plaintext or EAP-TTLS/PAP)
-+
-FreeRADIUS reads the "known good" password from LDAP, and compares
-that to what the user entered.
-
-Bind as user::
-The user supplies a `User-Password` (plaintext or EAP-TTLS/PAP)
-+
-FreeRADIUS uses that password to "bind as the user" to LDAP, using the
-supplied `User-Name` and `User-Password. If the bind is successfull,
-the user is authenticated. Otherwise, authentication fails.
-
-CHAP::
-The user supplies a `CHAP` password attribute.
-+
-FreeRADIUS reads the "known good" password from LDAP in cleartext, and
-compares that to what the user entered.
-
-MS-CHAP::
-The user supplies a `MS-CHAP` password attribute. Either as
-MS-CHAPv2, or as PEAP/MSCHAPv2, or as EAP-TTLS/MS-CHAPv2.
-+
-FreeRADIUS reads the "known good" password from LDAP in cleartext, or
-as an NT hash, and compares that to what the user entered.
-
-All of above authentication methods other than "bind as user" require
-that FreeRADIUS obtain the `userPassword` field from LDAP. If that
-field is not returned to FreeRADIUS, then normal authentication is
-impossible. Either FreeRADIUS has to be configured to use "bind as
-user" for authentication, or the LDAP database has to be updated to
-return the `userPassword` field to FreeRADIUS. This change usually
-involves giving the FreeRADIUS "read-only" user permission to read the
-`userPassword` field.
-
-Again, the best method is to test authentication is with the
-xref:howto:modules/ldap/ldapsearch/index.adoc[ldapsearch] tool.
-These tests *must* be run prior to configuring FreeRADIUS. We strongly
-recommend having the LDAP database return the `userPassword` field to
-FreeRADIUS, so that FreeRADIUS can authenticate the user.
-
-We also strongly recommend that the passwords be stored in LDAP as
-cleartext. Otherwise, the only authentication methods that will work
-are PAP and EAP-TTLS/PAP. The next section explains these issues in
-more detail.
-
-== Password Storage Methods
-
-If the `userPassword` field is returned from LDAP to FreeRADIUS, that
-information can be stored in a number of different formats:
-
-* the value can be cleartext
-* the value can be prepended with a string enclosed by braces, such as with `{crypt}` or `{ssha3}`.
-* the value can be have a suffix of `::`, in which case the password is generally a https://en.wikipedia.org/wiki/Base64[base64] encoded version of the real password
-
-TIP: Base64 values can be decoded via the command: `printf "%s"
-"VALUE" | base64 -d`
-
-FreeRADIUS is capable of understanding and parsing all of the above
-formats. There is sufficient information in the password values to
-determine what format it is in (base64, binary, or text), and what
-password "encryption" mechanism has been used (crypt, MD5, SHA, SSHA2,
-SHA3, etc). All that is necessary is that the
-xref:raddb:mods-available/ldap.adoc[ldap module] be configured to map
-the `userPassword` LDAP field to the `&control.Password.With-Header`
-attribute in FreeRADIUS. FreeRADIUS will then "do the right thing" to
-authenticate the user.
-
-This mapping is done in the default module configuration. There are
-no additional changes required for FreeRADIUS to correctly read and
-decode the `userPassword` field from LDAP. Please see the
-xref:raddb:mods-available/pap.adoc[pap module] for a full list of
-supported password "encryption" formats.
-
-== Additional Considerations
-
-There are some major caveats with the above authentication methods.
-The first is that we *strongly recommend* against using "bind as
-user". This process is slow, and causes unnecessary churn in the
-connections used to contact the LDAP server. Further, the "bind as
-user" process works _only_ when a `User-Password attribute exists in
-the request. If any other authentication type is used in the request,
-then the "bind as user" _will not work_. There is no amount of
-"fixing" things or configuration changes which will make it work.
-
-The second caveat is that the `CHAP` authentication type works _only_
-when a "clear text" password is stored in the LDAP database. The
-`CHAP` calclulations are designed around having access to the "clear
-text" password. It is impossible to use any "encrypted" or "hashed"
-passwords with `CHAP`.
-
-The third caveat is that the `MS-CHAP` authentication type works
-_only_ when a "clear text" password or "NT hashed" passwords which are
-stored in the LDAP database. The `MS-CHAP` calculations are designed
-around having access to "known good" passwords in those formats. It
-is impossible to use any other kind of "encrypted" or "hashed"
-passwords with `MS-CHAP`.
-
-The final caveat is that when the LDAP database contains "encrypted"
-or "hashed" passwords, the _only_ authentication type which is
-compatible with those passwords is PAP. i.e. when the `User-Password`
-is supplied to FreeRADIUS.
-
-For recommendations on password storage methods in LDAP, please see
-the LDAP
-https://openldap.org/doc/admin24/security.html#Password%20Storage[password
-storage] page. Please note that the recommendations there are made
-for LDAP security, and pay no attention to the caveats described
-above. When both RADIUS and LDAP are used together, then the
-requirements of _both_ systems must be met in order for them to work
-together. In many cases, a naive approach to LDAP security will
-prevent RADIUS from working.
-
-The issue of a database storing passwords in clear-text has to be
-balanced against the users sending clear-text passwords in
-authentication protocols. While those passwords are protected by TLS
-(EAP-TTLS) or by RADIUS (in it's own "encryption" mechanism), it is
-generally better to use a stronger authentication method than just
-PAP.
-
-In the end, there is no perfect solution to security requirements.
-The choice may be either to give up on using a particular
-authentication method, or to relax the security requirements on LDAP
-and on password storage. The final decision as to which choice is
-best can only be made by a local administrator.
-
-== Integrating Novell eDirectory with FreeRADIUS
-
-You can integrate Novell eDirectoryTM 8.7.1 or later with FreeRADIUS
-1.0.2 onwards to allow wireless authentication for eDirectory users. By
-integrating eDirectory with FreeRADIUS, you can do the following:
-
-* Use universal password for RADIUS authentication. Universal password
-provides single login and authentication for eDirectory users.
-Therefore, the users need not have a separate password for RADIUS and
-eDirectory authentication.
-* Enforce eDirectory account policies for users. The existing eDirectory
-policies on the user accounts can still be applied even after
-integrating with RADIUS. Also, you can make use of the intruder lockout
-facility of eDirectory by logging the failed logins into eDirectory.
-
-For configuration information please refer to the Novell documentation
-https://www.netiq.com/documentation/edir_radius/
diff --git a/doc/antora/modules/developers/nav.adoc b/doc/antora/modules/developers/nav.adoc
deleted file mode 100644
index ed6962a734..0000000000
--- a/doc/antora/modules/developers/nav.adoc
+++ /dev/null
@@ -1,7 +0,0 @@
-* xref:index.adoc[Developers]
-** xref:bugs.adoc[Bugs]
-** xref:coding-methods.adoc[Coding Methods]
-** xref:coverage.adoc[Code Coverage]
-** xref:profile.adoc[Profiling]
-** xref:contributing.adoc[Contributing]
-** xref:release-method.adoc[Release Method]
diff --git a/doc/antora/modules/developers/pages/bugs.adoc b/doc/antora/modules/developers/pages/bugs.adoc
deleted file mode 100644
index b63329c0bb..0000000000
--- a/doc/antora/modules/developers/pages/bugs.adoc
+++ /dev/null
@@ -1,194 +0,0 @@
-= Bugs
-
-== Introduction
-
-The FreeRADIUS web site is at https://freeradius.org/, and most
-information referenced in this document can be found there.
-
-This document is primarily for non-developers of the FreeRADIUS
-server. If you are able to patch the code to work correctly, then
-we invite you to join the development list to discuss it. If
-youre the type who know little about how to code, then this is
-the place for you!
-
-== You found a bug
-
-Where the server terminates ungracefully due to a bus error,
-segmentation violation, or other memory error, you should create a new
-issue in the issue tracker https://bugs.freeradius.org/, including
-information from the debugging sections below.
-
-For any other issues, you should first discuss them on the
-https://freeradius.org/support/[FreeRADIUS users list], to
-see if anyone can reproduce them. Often theres a simple explanation of
-why the server behaves as it does, and its not necessarily a bug in the
-code, so browse the lists archives of the last two months, and if you
-dont see messages about it, ask!
-
-If the behavior is correct but confusing, we think thats a bug too, and
-you should file a bug against our documentation.
-
-For more information about the users list, the lists archives and the
-faq, please visit https://www.freeradius.org/list/users.html Please make
-sure to READ and RESPECT the house-rules. You will get much better
-response and much faster if you do!
-
-== Core dumps
-
-If the server (or one of the accompanying programs) core dumps, then you
-should rebuild the server as follows:
-
-```
-$ ./configure --enable-developer
-$ make
-$ make install
-```
-
-and then run the program again. You may have to to enable core dumps,
-via:
-
-```
-$ ulimit -c unlimited
-```
-
-When it core dumps, do:
-
-```
-$ gdb /path/to/executable /path/to/core/file
-```
-
-Enable logging in `gdb` via the following commands:
-
-```
-(gdb) set logging file gdb-radiusd.log
-(gdb) set logging on
-```
-
-and follow the instructions in the proceeding section.
-
-You can also enable the `panic_action` given in
-`raddb/radiusd.conf`. See the comments in that file for more details
-about automatically collecting gdb debugging information when the server
-crashes.
-
-== Debugging a live server
-
-If you cant get a core dump, or the problem doesnt result in a core
-dump, you may have to run the server under gdb. To do this, ensure that
-you have symbols in the binaries (i.e. a 'non-stripped' binary) by
-re-building the server as described in the previous section. Then, run
-the server under gdb as follows:
-
-```
-$ gdb radiusd
-```
-
-Enable logging in `gdb` via the following commands:
-
-```
-(gdb) set logging file gdb-radiusd.log
-(gdb) set logging on
-```
-
-Tell `gdb` to pass any necessary command-line arguments to the server:
-
-```
-(gdb) set args ...
-```
-
-Where the ``…'' are the command-line arguments you normally pass to
-radiusd. For debugging, you probably want to do:
-
-```
-(gdb) set args -fxx
-```
-
-Then, do:
-
-```
-(gdb) run
-```
-
-When something interesting happens, you can hit CTRL-C in the window,
-and you should be back at the gdb prompt:
-
-```
-(gdb)
-```
-
-And follow the instructions in the next section.
-
-== Obtaining useful information
-
-Once you have a core dump loaded into gdb, or FreeRADIUS running under
-gdb, you may use the commands below to get useful information about the
-state of the server.
-
-If the server was built with threads, you can do:
-
-```
-(gdb) info threads
-```
-
-Which will give you information about the threads. If the server isnt
-threaded, that command-line will print a message saying so.
-
-Then, do:
-
-```
-(gdb) thread apply all bt full
-```
-
-If the server isnt threaded, the `thread apply` section isnt
-necessary
-
-The output should be printed to the screen, and also sent to the
-`gdb-radiusd.log` file.
-
-You should then submit the information from the log file, along with any
-server output, the output of `radiusd -xv`, and information about your
-operating system to:
-
-https://bugs.freeradius.org/
-
-Submitting it to the bug database ensures that the bug report wont get
-forgotten, and that it will be dealt with in due course.
-
-You should provide the issue number in any mail sent to the users list.
-
-== Valgrind
-
-On Linux systems, `valgrind` is a useful tool that can catch certain
-classes of bugs. To use it, run the server via:
-
-```
-$ valgrind --tool=memcheck --leak-check=full radiusd -Xm
-```
-
-It will print out certain kinds of errors to the screen. There may be a
-number of errors related to OpenSSL, dlopen(), or libtldl. We cannot do
-anything about those problems. However, any errors that are inside of
-the FreeRADIUS source should be brought to our attention.
-
-== Running with `screen`
-
-If the bug is a crash of the server, and it takes a long time for the
-crash to happen, perform the following steps:
-
-* Log in as root.
-* Open a https://www.gnu.org/software/screen/[screen] session: `$ screen bash`.
-* Make sure FreeRADIUS is not running.
-* Make sure you have all the debug symbols about, or a debugable version
-of the server installed (one built with `--enable-developer` as above).
-* Configure screen to log to a file by pressing `Ctrl+a`, then `h`.
-* Type `gdb /path/to/radiusd` (or /path/to/freeradius on Debian).
-* At the `(gdb)` prompt, type `run -X`.
-* Detach from screen with `Ctrl+a`, `d`.
-* When you notice FreeRADIUS has died, reconnect to your screen session
-`$ screen -D -r`.
-* At the `(gdb)` prompt type `where` or for _lots_ of info try
-`thread apply all bt full`.
-* Tell screen to stop logging, `Ctrl+a`, `h`.
-* Logout from screen.
-
-FreeRADIUS Project, copyright 2019
diff --git a/doc/antora/modules/developers/pages/coding-methods.adoc b/doc/antora/modules/developers/pages/coding-methods.adoc
deleted file mode 100644
index 3de92c460e..0000000000
--- a/doc/antora/modules/developers/pages/coding-methods.adoc
+++ /dev/null
@@ -1,235 +0,0 @@
-= Coding Methods
-
-The following is a short set of guidelines to follow while programming. It does
-not address coding styles, function naming methods, or debugging methods.
-Rather, it describes the processes which should go on in the programmers mind
-while they are programming.
-
-Coding standards apply to function names, the look of the code, and coding
-consistency. Coding methods apply to the daily practices used by the programmer
-to write code.
-
-== Comment your code
-
-If you dont, youll be forced to debug it six months later, when you have no clue
-as to what its doing.
-
-If someone _really_ hates you, youll be forced to debug un-commented code that
-someone else wrote. You dont want to do that.
-
-For FreeRADIUS, use doxygen `@`-style comments so you get the
-benefits of the developer documentation site, https://doc.freeradius.org/.
-
-== Give things reasonable names
-
-Variables and functions should have names. Calling them `x`, `xx`,
-and `xxx` makes your life hell. Even `foo` and `i` are
-problematic.
-
-Avoid smurfs. Dont re-use struct names in field names, i. e.
-
-[source,c]
-----
-struct smurf {
- char *smurf_pappa_smurf;
-}
-----
-
-If your code reads as full English sentences, youre doing it right.
-
-== Check input parameters in the functions you write
-
-Your function _cannot_ do anything right if the user passed in garbage
-and you were too lazy to check for garbage input.
-
-`assert()` (`fr_assert()`) is ugly. Use it.
-
-[NOTE]
-====
-GIGO, "Garbage In, Garbage Out," is wrong. If your function gets
-garbage input, it should complain loudly and with great
-descriptiveness.
-====
-
-== Write useful error messages
-
-"Function failed" is useless as an error message. It makes debugging the code
-impossible without source-level instrumentation.
-
-If youre going to instrument the code at source level for error messages, leave
-the error messages there, so the next sucker wont have to do the same work all
-over again.
-
-== Check error conditions from the functions you call
-
-Your function _cannot_ do anything right if you called another function, and
-they gave you garbage output.
-
-One of the most common mistakes is:
-
-[source,c]
-----
-fp = fopen(...);
-fgetc(fp); /* core dumps! */
-----
-
-If the programmer had bothered to check for a `NULL` fp (error
-condition), then they could have produced a descriptive error message
-instead of having the program core dump.
-
-== Core dumps are for weenies
-
-If your program core dumps accidentally, youre a bad programmer. You dont know
-what your program is doing, or what its supposed to be doing when anything goes
-wrong.
-
-If it hits an `assert()` and calls `abort()`, youre a genius. Youve thought
-ahead to what _might_ go wrong, and put in an assertion to ensure that it fails
-in a _known manner_ when something _does_ go wrong. (As it usually does…)
-
-== Initialize your variables
-
-`memset()` (`talloc_zero()`) is your friend. `ptr = NULL` is nice,
-too.
-
-Having variables containing garbage values makes it easy for the code to do
-garbage things. The contents of local variables are inputs to your function. See
-xref:#_check_input_parameters_in_the_functions_you_write[#3].
-
-Its also nearly impossible for you to debug any problems, as you cant tell the
-variables with garbage values from the real ones.
-
-== Dont allow buffer over-runs
-
-Theyre usually accidental, but they cause core dumps. `strcpy()` and `strcat()`
-are ugly. Use them under duress.
-
-`sizeof()` is your friend.
-
-== `const` is your friend
-
-If you dont mean to modify an input structure to your function, declare it
-`const`. Declare string constants `const`. It cant hurt, and it allows more
-errors to be found at compile time.
-
-Use `const` everywhere. Once you throw a few into your code, and have it save
-you from stupid bugs, youll blindly throw in `const` everywhere. Its a
-life-saver.
-
-== Use C compiler warnings
-
-Turn on all of the C compiler warnings possible. You might have to turn some off
-due to broken system header files, though. But the more warnings the merrier.
-
-Getting error messages at compile time is much preferable to getting core dumps
-at run time. See xref:#_initialize_your_variables[#7].
-
-Notice that the C compiler error messages are helpful? You should write error
-messages like this, too. See xref:#_write_useful_error_messages[#4].
-
-== Avoid UNIXisms and ASCIIisms and visualisms
-
-You dont know under what system someone will try to run your code. Dont demand
-that others use the same OS or character set as you use.
-
-Never assign numbers to pointers. If foo is a `char*`, and you want it to be be
-`NULL`, assign `NULL`, not `0`. The zeroth location is perfectly as addressable
-as any other on plenty of OSes. Not all the world runs on Unix (though it should
-:) ).
-
-Another common mistake is to assume that the zeroth character in the character
-set is the string terminator. Instead of terminating a string with `0`, use
-`'\0'`, which is always right. Similarly, `memset()` with the appropriate value:
-`NULL`, `'\0'`, or `0` for pointers, chars, and numbers.
-
-Dont put tabs in string constants, either. Always use `'\t'` to represent a
-tab, instead of ASCII 9. Literal tabs are presented to readers of your code as
-arbitrary whitespace, and its easy to mess up.
-
-== Make conditionals explicit
-
-Though its legal to test `if (foo) {}` if you test against the appropriate
-value (like `NULL` or `'\0'`), your code is prettier and easier for others to
-read without having to eyeball your prototypes continuously to figure out what
-youre doing (especially if your variables arent well-named). See
-xref:#_give_things_reasonable_names[#2].
-
-== Test your code
-
-Even Donald Knuth writes buggy code. Youll never find all of the bugs in your
-code. But writing a test program definitely helps.
-
-This means that youll have to write your code so that it will be easily
-testable. As a result, it will look better and be easier to debug.
-
-== Hints, Tips, and Tricks
-
-This section lists many of the common `rules` associated with code submitted to
-the project. There are always exceptions… but you must have a really good reason
-for doing so.
-
-== Read the Documentation and follow the CodingStyle
-
-The FreeRADIUS server has a common coding style. Use real tabs to indent. There
-is whitespace in variable assignments (`i = 1`, not `i=1`).
-
-When in doubt, format your code to look the same as code already in the server.
-If your code deviates too much from the current style, it is likely to be
-rejected without further review, and without comment.
-
-== #ifdefs are ugly
-
-Code cluttered with `#ifdef` s is difficult to read and maintain. Dont do it.
-Instead, put your `#ifdef` s in a header, and conditionally define `static
-inline` functions, or macros, which are used in the code. Let the compiler
-optimize away the 'no-op' case.
-
-Simple example, of poor code:
-
-[source,c]
-----
-#ifdef CONFIG_MY_FUNKINESS
- init_my_stuff(foo);
-#endif
-----
-
-Cleaned-up example:
-
-(in header):
-
-[source,c]
-----
-#ifndef CONFIG_MY_FUNKINESS
- static inline void init_my_stuff(char *foo) {}
-#endif
-----
-
-(in the code itself):
-
-[source,c]
-----
-init_my_stuff(dev);
-----
-
-== `static inline` is better than a macro
-
-Static inline functions are greatly preferred over macros. They provide type
-safety, have no length limitations, no formatting limitations, and under gcc
-they are as cheap as macros.
-
-Macros should only be used for cases where a static inline is clearly suboptimal
-(there a few, isolated cases of this in fast paths), or where it is impossible
-to use a static inline function (such as string-izing).
-
-`static inline` is preferred over `$$static __inline__$$`, `extern inline`, and
-`$$extern __inline__$$`.
-
-== Dont over-design
-
-Dont try to anticipate nebulous future cases which may or may not be useful:
-_Make it as simple as you can, and no simpler._
-
-Split up functionality as much as possible. If your code needs to do two
-unrelated things, write two functions. Mashing two kinds of work into one
-function makes the server difficult to debug and maintain.
-
diff --git a/doc/antora/modules/developers/pages/contributing.adoc b/doc/antora/modules/developers/pages/contributing.adoc
deleted file mode 100644
index e4a4b0a1c5..0000000000
--- a/doc/antora/modules/developers/pages/contributing.adoc
+++ /dev/null
@@ -1,126 +0,0 @@
-= Contributing
-
-== Submitting patches or diffs to the FreeRADIUS project
-
-For a person or company wishing to submit a change to the FreeRADIUS
-project the process can sometimes be daunting if youre not familiar
-with "the system." This text is a collection of suggestions which can
-greatly increase the chances of your change being accepted.
-
-Note: Only trivial patches will be accepted via email. Large patches, or
-patches that modify a number of files MUST be submitted as a
-https://github.com/FreeRADIUS/freeradius-server/pulls[pull-request via GitHub].
-
-== Hints and tips
-
-=== 1. Describe your changes
-
-Describe the technical detail of the change(s) your patch or commit
-includes.
-
-Be as specific as possible. The WORST descriptions possible include
-things like "update file X", "bug fix for file X", or "this patch
-includes updates for subsystem X. Please apply."
-
-If your description starts to get long, thats a sign that you probably
-need to split up your commit. See the next point.
-
-=== 2. Separate your changes
-
-Separate each logical change into its own commit.
-
-For example, if your changes include both bug fixes and performance
-enhancements for a single module, separate those changes into two or
-more patches.
-
-On the other hand, if you make a single change to numerous files, group
-those changes into a single commit. Thus a single LOGICAL change is
-contained within a single commit.
-
-If one commit depends on another commit in order for a change to be
-complete, that is OK. Simply note "this commit depends on commit X" in
-the extended commit description.
-
-If your commit includes significant whitespace changes these should also
-be broken out into another, separate, commit.
-
-== Submitting patches via GitHub
-
-See the following links for more details about submitting via github:
-
-* https://help.github.com/articles/fork-a-repo
-* http://wiki.freeradius.org/contributing/GitHub
-
-== Submitting patches via email
-
-=== 1. diff -u
-
-Use `diff -u` or `diff -urN` to create patches.
-
-All changes to the source occur in the form of patches, as generated by
-diff(1). When creating your patch, make sure to create it in unified
-diff format, as supplied by the `-u` argument to diff(1). Patches
-should be based in the root source directory, not in any lower
-subdirectory.
-
-To create a patch for a single file, it is often sufficient to do::
-
-```
-SRCTREE=/home/user/src/freeradiusd/
-MYFILE=src/modules/rlm_foo/foo.c
-
-cd $SRCTREE
-cp $MYFILE $MYFILE.orig
-vi $MYFILE # make your change
-diff -u $MYFILE.orig $MYFILE > /tmp/patch
-```
-
-To create a patch for multiple files, you should unpack a `vanilla`,
-or unmodified source tree, and generate a diff against your own source
-tree. For example:
-
-```
-MYSRC=/home/user/src/freeradiusd-feature/
-
-gunzip freeradiusd-version.tar.gz
-tar xvf freeradiusd-version.tar
-diff -urN freeradiusd-version $MYSRC > ~/feature-version.patch
-```
-
-=== 2. Select e-mail destination
-
-If you are on the developers mailing list, send the patch there.
-mailto:freeradius-devel@lists.freeradius.org[freeradius-devel@lists.freeradius.org]
-
-Otherwise, send the patch to
-mailto:patches@freeradius.org[patches@freeradius.org]
-
-=== 3. No MIME, no links, no compression, no attachments. Just plain text
-
-The developers need to be able to read and comment on the changes you
-are submitting. It is important for a developer to be able to `quote`
-your changes, using standard e-mail tools, so that they may comment on
-specific portions of your code.
-
-For this reason, all patches should be submitting e-mail `inline`.
-
-Do not attach the patch as a MIME attachment, compressed or not. Many
-popular e-mail applications will not always transmit a MIME attachment
-as plain text, making it impossible to comment on your code. A MIME
-attachment also takes a bit more time to process, decreasing the
-likelihood of your MIME-attached change being accepted.
-
-Compressed patches are generally rejected outright. If the developer has
-to do additional work to read your patch, the odds are that it will be
-ignored completely.
-
-=== 4. E-mail size
-
-Large changes are not appropriate for mailing lists, and some
-maintainers. If your patch, exceeds 5Kb in size, you must submit the
-patch via GitHub instead.
-
-=== 5. Name the version of the server
-
-It is important to note, either in the subject line or in the patch
-description, the server version to which this patch applies.
diff --git a/doc/antora/modules/developers/pages/coverage.adoc b/doc/antora/modules/developers/pages/coverage.adoc
deleted file mode 100644
index af6048e39e..0000000000
--- a/doc/antora/modules/developers/pages/coverage.adoc
+++ /dev/null
@@ -1,11 +0,0 @@
-= Code Coverage
-
-We use the link:https://gcc.gnu.org/onlinedocs/gcc/Gcov-Intro.html#Gcov-Intro[gcov] tool to know our tests coverage.
-
-[source,shell]
-----
-$ make clean
-$ make coverage
-----
-
-If completed with success, a pretty report will be available in `${source_tree}/build/coverage/index.html`
diff --git a/doc/antora/modules/developers/pages/index.adoc b/doc/antora/modules/developers/pages/index.adoc
deleted file mode 100644
index e66ef61382..0000000000
--- a/doc/antora/modules/developers/pages/index.adoc
+++ /dev/null
@@ -1,18 +0,0 @@
-= FreeRADIUS Development
-
-List with some usual howtos for FreeRADIUS.
-
-Programming reference documentation can be found at the
-https://doc.freeradius.org/[Doxygen] site.
-
-== Topics
-
-* xref:bugs.adoc[Bugs]
-* xref:coding-methods.adoc[Coding Methods]
-* xref:coverage.adoc[Code Coverage]
-* xref:profile.adoc[Profiling]
-* xref:contributing.adoc[Contributing]
-* xref:release-method.adoc[Release Method]
-
-Also see the xref:installation:dependencies.adoc[build
-dependencies] page.
diff --git a/doc/antora/modules/developers/pages/profile.adoc b/doc/antora/modules/developers/pages/profile.adoc
deleted file mode 100644
index ca94f53a40..0000000000
--- a/doc/antora/modules/developers/pages/profile.adoc
+++ /dev/null
@@ -1,41 +0,0 @@
-= Profiling
-
-Build with gperftools, and ensure that it's built:
-
-[source,shell]
-----
-$ grep profile Make.inc
-GPERFTOOLS_LIBS = -lprofiler
-----
-
-Run your test using the profiling tools. One signal will start the
-profiling, another will stop it.
-
-[source,shell]
-----
-env CPUPROFILE=/tmp/freeradius.prof CPUPROFILESIGNAL=12 freeradius ...
-killall -12 freeradius
- ... wait ...
-killall -12 freeradius
-----
-
-View the results
-
-[source,shell]
-----
-pprof --text /path/to/freeradius /tmp/freeradius.prof
-----
-
-or as a graph
-
-[source,shell]
-----
-pprof --gv /path/to/freeradius /tmp/freeradius.prof
-----
-
-or as cachgrind output
-
-[source,shell]
-----
-pprof --cachegrind /path/to/freeradius /tmp/freeradius.prof
-----
diff --git a/doc/antora/modules/developers/pages/release-method.adoc b/doc/antora/modules/developers/pages/release-method.adoc
deleted file mode 100644
index 1de9e2dc17..0000000000
--- a/doc/antora/modules/developers/pages/release-method.adoc
+++ /dev/null
@@ -1,55 +0,0 @@
-= Release Method
-
-== Topics
-
-[arabic]
-. As of 2.0, the release process is much simpler. Edit the Changelog
-with the version number and any last updates.
-
-```
-# vi doc/ChangeLog
-# git commit doc/ChangeLog
-```
-
-[arabic, start=2]
-. Change version numbers in the VERSION file:
-
-```
-# vi VERSION
-# git commit VERSION
-```
-
-[arabic, start=3]
-. Make the files
-
-NOTE: It also does `make dist-check`, which checks the build rules for
-various packages.
-
-```
-# make dist
-```
-
-[arabic, start=4]
-. Validate that the packages are OK. If so, tag the release.
-
-NOTE: This does NOT actually do the tagging! You will have to run the
-command it prints out yourself.
-
-```
-# make dist-tag
-```
-
-[arabic, start=5]
-. Sign the packages. You will need the correct GPG key for this to work.
-
-```
-# make dist-sign
-```
-
-[arabic, start=6]
-. Push to the FTP site. You will need write access to the FTP site for
-this to work.
-
-```
-# make dist-publish
-```
diff --git a/doc/antora/modules/howto/nav.adoc b/doc/antora/modules/howto/nav.adoc
deleted file mode 100644
index dab23f80d6..0000000000
--- a/doc/antora/modules/howto/nav.adoc
+++ /dev/null
@@ -1,22 +0,0 @@
-* xref:index.adoc[Howto Guides]
-** Protocols
-**** xref:protocols/dhcp/index.adoc[DHCP]
-***** xref:protocols/dhcp/prepare.adoc[Preparation]
-***** xref:protocols/dhcp/enable.adoc[Enabling the DHCP service]
-***** xref:protocols/dhcp/test.adoc[Testing the DHCP service]
-***** xref:protocols/dhcp/policy.adoc[Defining the DHCP policy]
-****** xref:protocols/dhcp/policy_ippool_creation.adoc[IP pool creation]
-****** xref:protocols/dhcp/policy_common_options.adoc[Common options]
-****** xref:protocols/dhcp/policy_network_options.adoc[Network options and IP pool selection]
-****** xref:protocols/dhcp/policy_subnet_options.adoc[Subnet options]
-****** xref:protocols/dhcp/policy_device_options.adoc[Device, class and group options]
-****** xref:protocols/dhcp/policy_ippool_access.adoc[IP pool access restriction]
-**** xref:protocols/proxy/index.adoc[PROXY Protocol]
-***** xref:protocols/proxy/enable_radsec.adoc[Enabling RadSec]
-***** xref:protocols/proxy/radsec_client.adoc[Configuring a test RadSec client]
-***** xref:protocols/proxy/radsec_with_haproxy.adoc[Proxying RadSec with HAproxy]
-***** xref:protocols/proxy/radsec_with_traefik.adoc[Proxying RadSec with Traefik]
-***** xref:protocols/proxy/enable_proxy_protocol.adoc[Enabling PROXY Protocol for RadSec]
-** xref:monitoring/index.adoc[Monitoring]
-*** xref:monitoring/statistics.adoc[Server statistics]
-** xref:simultaneous_use.adoc[Simultaneous-Use]
diff --git a/doc/antora/modules/howto/pages/index.adoc b/doc/antora/modules/howto/pages/index.adoc
deleted file mode 100644
index 47a51460c1..0000000000
--- a/doc/antora/modules/howto/pages/index.adoc
+++ /dev/null
@@ -1,17 +0,0 @@
-= Howto Guides
-
-The documents in this section describe how to perform various common tasks with
-FreeRADIUS. They also provide worked examples on using the various modules in
-common deployment scenarions.
-
-If you have a topic you'd like to see included in the list of howtos, contact
-the developers on the
-link:http://lists.freeradius.org/mailman/listinfo/freeradius-users[User's
-mailing list].
-
-Some of the documents here started life as pages on
-link:http://wiki.freeradius.org[wiki.freeradius.org]. If you've just been
-through a particularly arduous service configuration and deployment, and would
-like to help your fellow users, then please create a new how to on the wiki.
-If it's popular enough, we'll include it in the official documentation for the
-next release.
diff --git a/doc/antora/modules/howto/pages/monitoring/index.adoc b/doc/antora/modules/howto/pages/monitoring/index.adoc
deleted file mode 100644
index a08ffb4194..0000000000
--- a/doc/antora/modules/howto/pages/monitoring/index.adoc
+++ /dev/null
@@ -1,67 +0,0 @@
-= Monitoring
-
-Any good systems administrator will want to know how well
-their systems are operating, both to catch issues before they
-become a serious problem, or for long term analysis.
-The term "monitoring" can encompass all kinds of watching how the
-system is working, from generating and watching logs, gathering
-statistics or ensuring that the service daemon is still running
-and serving requests.
-
-We break the different types of monitoring down into the following
-sections.
-
-== Service checking
-
-Checking the running service can include the following:
-
-* Ensuring the daemon is still running, i.e. process monitoring
-* Sending regular RADIUS authentication or accounting requests and checking they are correctly responded to
-* Sending Status-Server RADIUS requests
-
-Within a proxy environment FreeRADIUS needs to know if upstream
-proxies are available. It can do this itself using the latter two
-options above.
-
-== Logging
-
-System logs are often the most critical part of a RADIUS system.
-They are necessary for the administrator to know who has logged in
-and when, for debugging purposes such as when an end user cannot
-connect, and often for regulatory or compliance purposes.
-
-RADIUS server logs are also often used as a basic form of
-recording accounting requests, which are in and of themselves a
-form of logging by the NAS. Getting correct logging systems
-operational is key to running an efficient and easy to maintain
-RADIUS server.
-
-FreeRADIUS has many options for being able to generate and store
-logs, including the following:
-
-* Main daemon logging, configured in `radiusd.conf`
-* Line-based text logging, using `rlm_linelog`
-* Detailed RADIUS packet logs, using `rlm_detail`
-
-As well as recording direct to disk, the above can be sent via a
-local syslog server, which opens up many opportunities for central
-logging.
-
-It is possible to integrate FreeRADIUS into other more complicated
-logging systems, some options may include:
-
-* To CSV files, for example via `rlm_linelog`
-* Writing entries to an SQL database using `rlm_sql`
-* Into a log management system such as Elasticsearch or Graylog
-
-
-== Statistics gathering
-
-It is often useful to collect statistics from a running RADIUS
-server. These are often plotted on graphs to show current load or
-for trend analysis, as well as an indication of system operation.
-
-Statistics are usually gathered in two ways:
-
-* FreeRADIUS xref:monitoring/statistics.adoc[internal statistics]
-* Analysing logs with some external tool
diff --git a/doc/antora/modules/howto/pages/monitoring/statistics.adoc b/doc/antora/modules/howto/pages/monitoring/statistics.adoc
deleted file mode 100644
index 0583f0adc0..0000000000
--- a/doc/antora/modules/howto/pages/monitoring/statistics.adoc
+++ /dev/null
@@ -1,336 +0,0 @@
-= Server statistics
-
-FreeRADIUS collects statistics internally about certain operations
-it is doing, such as the number of authentication and accounting
-requests, how many accepts and failures, and server queue lengths.
-These can be queried by sending a specially-crafted RADIUS
-`Status-Server` packet to a "status" virtual server.
-
-== Configuring the status virtual server
-
-The `status` virtual server is present in the default
-configuration, but needs to be enabled before it can be used. To
-do this, create a symlink from `sites-enabled/status` to
-`../sites-available/status`:
-
-[source,shell]
-----
-# cd raddb/sites-enabled
-# ln -s ../sites-available/status
-----
-
-[NOTE]
-====
-If you are not starting from the default configuration, check that
-`status_server` is still set to `yes` in `raddb/radiusd.conf` as
-well.
-====
-
-While the default configuration will work for most setups, you may
-edit the virtual server configuration in `sites-enabled/status`.
-No major changes are necessary here, though the default secret,
-`adminsecret`, should be changed. Other possible changes may be
-the listening IP address and port, and the clients that are
-allowed to connect. By default, connections are restricted to the
-local host only.
-
-Having enabled and configured the status server, restart
-FreeRADIUS to make it active.
-
-== Querying the server
-
-To get the current statistics from the server, send a RADIUS
-request of type `Status-Server` to the status port. Unless edited
-above, the request must come from the same server that FreeRADIUS
-is running on, and be sent to port 18121 with the secret
-'adminsecret' . At a minimum, the `FreeRADIUS-Statistics-Type`
-attribute must be set. For example:
-
- $ cat <<EOF | radclient -x localhost:18121 status adminsecret
- > FreeRADIUS-Statistics-Type = 0x01
- > Message-Authenticator = 0x00
- > EOF
- Sent Status-Server Id 145 from 0.0.0.0:b852 to 127.0.0.1:18121 length 62
- FreeRADIUS-Statistics-Type = Authentication
- Message-Authenticator = 0x00
- Received Access-Accept Id 145 from 127.0.0.1:46c9 to 127.0.0.1:47186 length 152
- FreeRADIUS-Total-Access-Requests = 27
- FreeRADIUS-Total-Access-Accepts = 20
- FreeRADIUS-Total-Access-Rejects = 1
- FreeRADIUS-Total-Access-Challenges = 0
- FreeRADIUS-Total-Auth-Responses = 5
- FreeRADIUS-Total-Auth-Duplicate-Requests = 0
- FreeRADIUS-Total-Auth-Malformed-Requests = 0
- FreeRADIUS-Total-Auth-Invalid-Requests = 0
- FreeRADIUS-Total-Auth-Dropped-Requests = 0
- FreeRADIUS-Total-Auth-Unknown-Types = 0
- FreeRADIUS-Total-Auth-Conflicts = 0
-
-The `FreeRADIUS-Statistics-Type` attribute is a bitmask - add
-together the following numbers to select the statistics required.
-Some options are mutually exclusive, so it might be necessary to
-send multiple requests to collect all information.
-
-[%header,cols="2,1,1,5"]
-|===
-|Name|Hex value|Decimal value|Description
-
-|Authentication
-|0x01
-|1
-|Stats about authentications
-
-|Accounting
-|0x02
-|2
-|Stats about accounting
-
-|Proxy Auth
-|0x04
-|4
-|Proxied authentication requests
-
-|Proxy Accounting
-|0x08
-|8
-|Proxied accounting requests
-
-|Internal
-|0x10
-|16
-|Queue lengths, thread information etc.
-
-|Client
-|0x20
-|32
-|Statistics about RADIUS clients e.g. defined in `clients.conf`
-
-|Server
-|0x40
-|64
-|Statistics about server 'listen' sockets e.g. in `sites-enabled/*`
-
-|Home Server
-|0x80
-|128
-|Statistics about a proxy home servers e.g. in `proxy.conf`
-|===
-
-== Worked examples
-
-To show the statistics available, a few examples follow.
-
-=== Global server authentications
-
-Using `FreeRADIUS-Statistics-Type = 0x01` requests stats about
-authentications. Because, for example, no "Client" qualifier has
-been added (`0x20`) the numbers are global to the server.
-
-[source,shell]
-----
-# cat <<EOF | radclient -x localhost:18121 status adminsecret
-FreeRADIUS-Statistics-Type = 0x01
-Message-Authenticator=0x00
-EOF
-Sent Status-Server Id 90 from 0.0.0.0:e008 to 127.0.0.1:18121 length 50
- FreeRADIUS-Statistics-Type = Authentication
- Message-Authenticator = 0x00
-Received Access-Accept Id 90 from 127.0.0.1:46c9 to 127.0.0.1:57352 length 152
- FreeRADIUS-Total-Access-Requests = 133
- FreeRADIUS-Total-Access-Accepts = 114
- FreeRADIUS-Total-Access-Rejects = 13
- FreeRADIUS-Total-Access-Challenges = 0
- FreeRADIUS-Total-Auth-Responses = 127
- FreeRADIUS-Total-Auth-Duplicate-Requests = 0
- FreeRADIUS-Total-Auth-Malformed-Requests = 0
- FreeRADIUS-Total-Auth-Invalid-Requests = 0
- FreeRADIUS-Total-Auth-Dropped-Requests = 0
- FreeRADIUS-Total-Auth-Unknown-Types = 0
- FreeRADIUS-Total-Auth-Conflicts = 0
-----
-
-=== Global server authentication and accounting requests
-
-Sending `0x01` requests authentication statistics, and `0x02`
-requests accounting stats. To get both in one result, add them
-together, so we requst `0x03`. In this example we send decimal
-rather than hexadecimal.
-
-[source,shell]
-----
-# cat <<EOF | radclient -x localhost:18121 status adminsecret
-FreeRADIUS-Statistics-Type = 3
-Message-Authenticator=0x00
-EOF
-Sent Status-Server Id 216 from 0.0.0.0:ce7b to 127.0.0.1:18121 length 50
- FreeRADIUS-Statistics-Type = Auth-Acct
- Message-Authenticator = 0x00
-Received Access-Accept Id 216 from 127.0.0.1:46c9 to 127.0.0.1:52859 length 248
- FreeRADIUS-Total-Access-Requests = 542
- FreeRADIUS-Total-Access-Accepts = 451
- FreeRADIUS-Total-Access-Rejects = 81
- FreeRADIUS-Total-Access-Challenges = 0
- FreeRADIUS-Total-Auth-Responses = 532
- FreeRADIUS-Total-Auth-Duplicate-Requests = 0
- FreeRADIUS-Total-Auth-Malformed-Requests = 0
- FreeRADIUS-Total-Auth-Invalid-Requests = 0
- FreeRADIUS-Total-Auth-Dropped-Requests = 0
- FreeRADIUS-Total-Auth-Unknown-Types = 0
- FreeRADIUS-Total-Auth-Conflicts = 0
- FreeRADIUS-Total-Accounting-Requests = 0
- FreeRADIUS-Total-Accounting-Responses = 0
- FreeRADIUS-Total-Acct-Duplicate-Requests = 0
- FreeRADIUS-Total-Acct-Malformed-Requests = 0
- FreeRADIUS-Total-Acct-Invalid-Requests = 0
- FreeRADIUS-Total-Acct-Dropped-Requests = 0
- FreeRADIUS-Total-Acct-Unknown-Types = 0
- FreeRADIUS-Total-Acct-Conflicts = 0
-----
-
-=== Internal server stats
-
-The value `0x10` requests information about the server such as queue
-lengths and thread state.
-
-[source,shell]
-----
-# cat <<EOF | radclient -x localhost:18121 status adminsecret
-FreeRADIUS-Statistics-Type = 0x10
-Message-Authenticator=0x00
-EOF
-Sent Status-Server Id 158 from 0.0.0.0:a090 to 127.0.0.1:18121 length 50
- FreeRADIUS-Statistics-Type = Internal
- Message-Authenticator = 0x00
-Received Access-Accept Id 158 from 127.0.0.1:46c9 to 127.0.0.1:41104 length 164
- FreeRADIUS-Stats-Start-Time = "Aug 3 2023 13:36:24 UTC"
- FreeRADIUS-Stats-HUP-Time = "Aug 3 2023 13:36:24 UTC"
- FreeRADIUS-Queue-Len-Internal = 0
- FreeRADIUS-Queue-Len-Proxy = 0
- FreeRADIUS-Queue-Len-Auth = 0
- FreeRADIUS-Queue-Len-Acct = 0
- FreeRADIUS-Queue-Len-Detail = 0
- FreeRADIUS-Queue-PPS-In = 0
- FreeRADIUS-Queue-PPS-Out = 0
- FreeRADIUS-Stats-Threads-Active = 0
- FreeRADIUS-Stats-Threads-Total = 0
- FreeRADIUS-Stats-Threads-Max = 0
-----
-
-=== Complete global server information
-
-A useful common request is all information about the server on a
-global basis: internal stats (16 / `0x10`) plus authentications (1
-/ `0x01`), accounting (2 / `0x02`), proxy authentications (4 /
-`0x04`) and proxy accounting (8 / `0x08`). The value `All` is
-defined in the dictionary as `0x1f` (decimal 31) to cover
-this common eventuality, and is what we demonstrate here.
-
-[source,shell]
-----
-# cat <<EOF | radclient -x localhost:18121 status adminsecret
-FreeRADIUS-Statistics-Type = All
-Message-Authenticator=0x00
-EOF
-Sent Status-Server Id 4 from 0.0.0.0:9ee4 to 127.0.0.1:18121 length 50
- FreeRADIUS-Statistics-Type = All
- Message-Authenticator = 0x00
-Received Access-Accept Id 4 from 127.0.0.1:46c9 to 127.0.0.1:40676 length 596
- FreeRADIUS-Total-Access-Requests = 792
- FreeRADIUS-Total-Access-Accepts = 659
- FreeRADIUS-Total-Access-Rejects = 122
- FreeRADIUS-Total-Access-Challenges = 0
- FreeRADIUS-Total-Auth-Responses = 781
- FreeRADIUS-Total-Auth-Duplicate-Requests = 0
- FreeRADIUS-Total-Auth-Malformed-Requests = 0
- FreeRADIUS-Total-Auth-Invalid-Requests = 0
- FreeRADIUS-Total-Auth-Dropped-Requests = 0
- FreeRADIUS-Total-Auth-Unknown-Types = 0
- FreeRADIUS-Total-Auth-Conflicts = 0
- FreeRADIUS-Total-Accounting-Requests = 0
- FreeRADIUS-Total-Accounting-Responses = 0
- FreeRADIUS-Total-Acct-Duplicate-Requests = 0
- FreeRADIUS-Total-Acct-Malformed-Requests = 0
- FreeRADIUS-Total-Acct-Invalid-Requests = 0
- FreeRADIUS-Total-Acct-Dropped-Requests = 0
- FreeRADIUS-Total-Acct-Unknown-Types = 0
- FreeRADIUS-Total-Acct-Conflicts = 0
- FreeRADIUS-Total-Proxy-Access-Requests = 0
- FreeRADIUS-Total-Proxy-Access-Accepts = 0
- FreeRADIUS-Total-Proxy-Access-Rejects = 0
- FreeRADIUS-Total-Proxy-Access-Challenges = 0
- FreeRADIUS-Total-Proxy-Auth-Responses = 0
- FreeRADIUS-Total-Proxy-Auth-Duplicate-Requests = 0
- FreeRADIUS-Total-Proxy-Auth-Malformed-Requests = 0
- FreeRADIUS-Total-Proxy-Auth-Invalid-Requests = 0
- FreeRADIUS-Total-Proxy-Auth-Dropped-Requests = 0
- FreeRADIUS-Total-Proxy-Auth-Unknown-Types = 0
- FreeRADIUS-Total-Proxy-Accounting-Requests = 0
- FreeRADIUS-Total-Proxy-Accounting-Responses = 0
- FreeRADIUS-Total-Proxy-Acct-Duplicate-Requests = 0
- FreeRADIUS-Total-Proxy-Acct-Malformed-Requests = 0
- FreeRADIUS-Total-Proxy-Acct-Invalid-Requests = 0
- FreeRADIUS-Total-Proxy-Acct-Dropped-Requests = 0
- FreeRADIUS-Total-Proxy-Acct-Unknown-Types = 0
- FreeRADIUS-Stats-Start-Time = "Aug 3 2023 13:36:24 UTC"
- FreeRADIUS-Stats-HUP-Time = "Aug 3 2023 13:36:24 UTC"
- FreeRADIUS-Queue-Len-Internal = 0
- FreeRADIUS-Queue-Len-Proxy = 0
- FreeRADIUS-Queue-Len-Auth = 0
- FreeRADIUS-Queue-Len-Acct = 0
- FreeRADIUS-Queue-Len-Detail = 0
- FreeRADIUS-Queue-PPS-In = 0
- FreeRADIUS-Queue-PPS-Out = 0
- FreeRADIUS-Stats-Threads-Active = 0
- FreeRADIUS-Stats-Threads-Total = 0
- FreeRADIUS-Stats-Threads-Max = 0
-----
-
-=== Client statistics
-
-Data can be provided about each RADIUS client defined in the
-server. Note that this is for the client definition, not for each
-client that connects - if a client definition has a wide netmask
-and permits multiple clients to connect, the statistics will be
-aggregate for all clients using that definition.
-
-[NOTE]
-====
-It is not possible to request global server statistics
-concurrently with client statistics as both use the same reply
-attributes.
-====
-
-Here we request accounting data for one particular client by IP
-address.
-
-[source,shell]
-----
-# cat <<EOF | radclient -x localhost:18121 status adminsecret
-FreeRADIUS-Statistics-Type = 0x2f
-FreeRADIUS-Stats-Client-IP-Address = 172.16.0.10
-Message-Authenticator=0x00
-EOF
-Sent Status-Server Id 194 from 0.0.0.0:d897 to 127.0.0.1:18121 length 62
- FreeRADIUS-Statistics-Type = 47
- FreeRADIUS-Stats-Client-IP-Address = 172.16.0.10
- Message-Authenticator = 0x00
-Received Access-Accept Id 194 from 127.0.0.1:46c9 to 127.0.0.1:55447 length 236
- FreeRADIUS-Stats-Client-IP-Address = 172.16.0.10
- FreeRADIUS-Total-Access-Requests = 1491
- FreeRADIUS-Total-Access-Accepts = 1240
- FreeRADIUS-Total-Access-Rejects = 246
- FreeRADIUS-Total-Access-Challenges = 0
- FreeRADIUS-Total-Auth-Responses = 1486
- FreeRADIUS-Total-Auth-Duplicate-Requests = 0
- FreeRADIUS-Total-Auth-Malformed-Requests = 0
- FreeRADIUS-Total-Auth-Invalid-Requests = 0
- FreeRADIUS-Total-Auth-Dropped-Requests = 0
- FreeRADIUS-Total-Auth-Unknown-Types = 0
- FreeRADIUS-Total-Accounting-Requests = 0
- FreeRADIUS-Total-Accounting-Responses = 0
- FreeRADIUS-Total-Acct-Duplicate-Requests = 0
- FreeRADIUS-Total-Acct-Malformed-Requests = 0
- FreeRADIUS-Total-Acct-Invalid-Requests = 0
- FreeRADIUS-Total-Acct-Dropped-Requests = 0
- FreeRADIUS-Total-Acct-Unknown-Types = 0
-----
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/enable.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/enable.adoc
deleted file mode 100644
index 2824bd0f48..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/enable.adoc
+++ /dev/null
@@ -1,213 +0,0 @@
-== Enabling the DHCP service
-
-A major difference between configuring FreeRADIUS as a DHCP server versus most
-other DHCP software such as ISC DHCP is that other software typically uses a
-single monolithic configuration file whereas FreeRADIUS has a collection of
-configuration files. This reflects the modularity of FreeRADIUS; attempting to
-put the entire configuration in a single file would result in a very difficult
-to read configuration.
-
-The root of the FreeRADIUS configuration may be in a different location on the
-filesystem depending on how FreeRADIUS has been installed. This directory will
-be referred to as `<raddb>` below. The sample configuration files are well
-commented describing what each configuration option does.
-
-FreeRADIUS compiled from source will default to `/usr/local/etc/raddb`.
-Pre-built packages will default to either `/etc/raddb` or
-`/etc/freeradius`.
-
-
-=== Enable the DHCP virtual server
-
-The FreeRADIUS configuration separates each network service that it provides
-into "virtual servers". A number of sample virtual server definitions are
-provided in `<raddb>/sites-available`, one of which is the sample
-configuration for a DHCP service.
-
-Sites may be added to the working configuration by either creating a symlink to
-them or copying them to `<conf>/sites-enabled` depending on how you wish to
-manage future upgrades.
-
-[TIP]
-====
-As with other package-managed configuration files, package upgrades will not
-automatically replace files that you have edited but you will need to resolve
-any local differences. Creating copies avoids the need to resolve conflicts
-during a package upgrade.
-====
-
-Add the DHCP virtual server to the active configuration:
-
-[source,shell]
-----
-cd <raddb>/sites-enabled
-ln -s ../sites-available/dhcp .
-----
-
-or:
-
-[source,shell]
-----
-cd <raddb>/sites-enabled
-cp ../sites-available/dhcp .
-----
-
-The sample configuration has been set up in such a way that it is initially
-safe. It will not actually take over live DHCP serving on the network when it
-is simply enabled until it is configured to do so. Rather is set up for testing
-prior to going live.
-
-The virtual server begins with a `listen` section. In this section your need to
-modify the following configuration items:
-
-`ipaddr`:: The IP address to listen on.
-`src_ipaddr`:: The source IP for unicast packets.
-`port`:: The port to listen on. Setting this to `67` will make the DHCP service live on the network.
-`interface`:: The network interface to listen on.
-`broadcast`:: Allow broadcast packets. For most live systems this will need to be set to `yes`.
-
-Below the `listen` section, there are sections that define how to respond to
-each of the DHCP packet types. Most installations will require that you review
-the settings for `DHCP-Discover` and `DHCP-Request`.
-
-Their contents contain directives in the FreeRADIUS policy language, "unlang".
-Many examples are provided which have been carefully described.
-
-
-=== Enable SQL and IP pool modules
-
-FreeRADIUS has many modules to support different aspects of the functionality
-required for the network protocols it can process. The two of most significance
-for DHCP are `dhcp_sql` and `dhcp_sqlippool`. As with virtual servers, a
-number of example module configurations are available in
-`<raddb>/mods-available`.
-These should be symlinked or copied into `<raddb>/mods-enabled` in order to
-enable them.
-
-
-==== Configure the `dhcp_sql` module
-
-Add the `dhcp_sql` module to the active configuration:
-
-[source,shell]
-----
-cd <raddb>/mods-enabled
-ln -s ../mods-available/dhcp_sql .
-----
-
-or:
-
-[source,shell]
-----
-cd <raddb>/mods-enabled
-cp ../mods-available/dhcp_sql .
-----
-
-The `dhcp_sql` module should be configured with the connection parameters for
-whichever database is to be used. The key configuration items are:
-
-`dialect`:: Which SQL dialect is in use.
-`driver`:: Which driver to use to access the database. For most databases this
- is `rlm_sql_<dialect>`, however Microsoft SQL Server has a choice of
- drivers.
-
-Then, there are configuration options that are unique to each database,
-including connection details. For most databases these are:
-
-`server`:: The host name or IP address of the database server.
-`port`:: The port to connect to the database server on.
-`login`:: The user name used to connect to the database.
-`password`:: The password for authenticating to the database.
-`radius_db`:: The name of the database.
-
-[NOTE]
-====
-SQLite does not use these connection options, rather the `filename`
-option within the `sqlite` section is used to determine where the database
-will be stored.
-====
-
-
-==== Configure the `dhcp_sqlippool` module
-
-Add the `dhcp_sqlippool` module to the active configuration:
-
-[source,shell]
-----
-cd <raddb>/mods-enabled
-ln -s ../mods-available/dhcp_sqlippool .
-----
-
-or
-
-[source,shell]
-----
-cd <raddb>/mods-enabled
-cp ../mods-available/dhcp_sqlippool .
-----
-
-The `dhcp_sqlippool` module must be configured. The key configuration
-items are:
-
-`dialect`:: Set this to the same SQL dialect as in the `sql` module.
-`offer_duration`:: How long an IP is offered to the client in a DHCP OFFER.
-`lease_duration`:: How long an IP is leased to the client in a DHCP ACK.
-
-
-=== Provision the database
-
-You should provision your database by creating a user for FreeRADIUS (matching
-the configuration that you have previously provided) and then loading the
-schema. The procedure for doing this will vary according to the database
-server.
-
-The schema, stored procedure definition and any additional setup scripts for
-your database are in `<raddb>/mods-config/sql/ippool-dhcp/{dialect}/`.
-
-=== Test FreeRADIUS startup
-
-Once you have provisioned your schema, created a user account and granted
-access to the user, you should be able to start FreeRADIUS.
-
-If FreeRADIUS has been configured correctly then the output of `ss` will
-contain a line showing that FreeRADIUS is listening for DHCP packets on the
-designated interface on port 67:
-
-.Example of FreeRADIUS listening on `<interface>` for DHCP packets
-==================================================================
- # ss -lunp
- Netid Recv-Q Send-Q Local Address:Port ...
- udp 0 0 0.0.0.0%<interface>:67 ... users:(("radiusd",...))
-==================================================================
-
-Note that if the database is inaccessible then FreeRADIUS will normally refuse
-to start.
-
-The FreeRADIUS wiki contains extensive information about debugging FreeRADIUS
-startup issues that we do not repeat in any detail here.
-
-Essentially, stop your init system from repeatedly trying to launch FreeRADIUS:
-
-[source,shell]
-----
-service radiusd stop
-----
-
-Then start FreeRADIUS manually in debug mode:
-
-[source,shell]
-----
-radiusd -X
-----
-
-Carefully read the output since this will tell you why FreeRADIUS was unable to
-start.
-
-Once you have fixed the issue start FreeRADIUS as normal:
-
-[source,shell]
-----
-service radiusd start
-----
-
-Now xref:protocols/dhcp/test.adoc[test the DHCP service] to ensure that it is responding to requests.
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/index.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/index.adoc
deleted file mode 100644
index fde22024f0..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/index.adoc
+++ /dev/null
@@ -1,35 +0,0 @@
-= FreeRADIUS DHCP server
-
-This guide describes how FreeRADIUS can be used in place of ISC DHCP or ISC Kea
-to provide a significantly more performant and, above all, more flexible DHCP
-server.
-
-This guide provides a suggested configuration that should be somewhat familiar
-to anyone who has previously implemented DHCP using the most frequently used
-features of other DHCP server software.
-
-The modular design of FreeRADIUS means that there is no one "right" way to
-implement the DHCP service. FreeRADIUS allows you to put together a "mix and
-match" approach.
-
-For example you can manage the leases in an SQL database. You might then hard
-code certain DHCP reply parameters within configuration and then look up
-additional parameters using a datastore such as:
-
- * a local file such as a structured text file or an SQLite database
- * an organisational LDAP directory
- * an SQL or "no SQL" database
- * a remote endpoint such as a RESTful HTTP API
-
-The policy language and modular configuration of FreeRADIUS is sufficiently
-powerful and that almost any aspect of the server's behaviour can be customised
-to implement even the most sophisticated DHCP configurations.
-
-== Sections in this guide
-
-This guide is organised into four parts that should be read in order:
-
-1. xref:protocols/dhcp/prepare.adoc[Preparation]
-2. xref:protocols/dhcp/enable.adoc[Enabling the DHCP service]
-3. xref:protocols/dhcp/test.adoc[Testing the DHCP service]
-4. xref:protocols/dhcp/policy.adoc[Defining the DHCP policy]
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/policy.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/policy.adoc
deleted file mode 100644
index d8f1bcb79a..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/policy.adoc
+++ /dev/null
@@ -1,14 +0,0 @@
-== Defining the DHCP policy
-
-Now that FreeRADIUS is successfully running as a DHCP server it is necessary to
-configure a DHCP policy so that it returns correctly formed responses to the DHCP
-requests that it receives.
-
-This involves a number of steps:
-
- * xref:protocols/dhcp/policy_ippool_creation.adoc[Defining the IP address pools.]
- * xref:protocols/dhcp/policy_common_options.adoc[Defining the options that are common to all replies.]
- * xref:protocols/dhcp/policy_network_options.adoc[Defining the options for the network from which the request originates and ensuring that IP addresses are allocated from the correct pool.]
- * xref:protocols/dhcp/policy_subnet_options.adoc[Defining the options for the subnet to which this issued IP address belongs.]
- * xref:protocols/dhcp/policy_device_options.adoc[Defining the device, class and group based options specific to the device.]
- * xref:protocols/dhcp/policy_ippool_access.adoc[Using device properties to restrict access to certain pools.]
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/policy_common_options.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/policy_common_options.adoc
deleted file mode 100644
index ca4d98fee5..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/policy_common_options.adoc
+++ /dev/null
@@ -1,80 +0,0 @@
-== Configure common reply options
-
-FreeRADIUS includes a powerful xref:index.adoc[policy language] called
-"unlang".
-
-Statements in unlang may be used to call further policies, update attribute
-lists and invoke modules. There are also control flow statements (if,
-switch, etc.) typical of most imperative languages.
-
-FreeRADIUS has a number attribute lists that it maintains as it processes
-packets within the virtual server sections. Most relevant to DHCP are
-`request`, `control` and `reply`.
-
-The DHCP options from the current request packet are provided in the
-`request` list. This includes fixed DHCP parameters such as
-`DHCP-Client-Hardware-Address`, optional parameters such as
-`DHCP-Requested-IP-Address`, and parameters synthesised by FreeRADIUS such as
-`DHCP-Message-Type` and `DHCP-Network-Subnet`.
-
-DHCP options can be set by updating their value in the `reply` list. This
-forms the basis of the packet returned to the client.
-
-In the default DHCP server configuration, a "policy" (akin to a subroutine) is
-used to set common options for reply packets. The policy is found in
-`<raddb>/policy.d/dhcp`.
-
-Look at the contents of the `dhcp_common` section and set any global options
-applicable to all clients in this policy.
-
-[source,unlang]
-----
-dhcp_common {
- update reply {
- &DHCP-Domain-Name-Server := 8.8.8.8
- &DHCP-Domain-Name-Server += 8.8.4.4
- &DHCP-Subnet-Mask := 255.255.255.0
- &DHCP-Router-Address := 192.0.2.1
- ...
- }
-}
-----
-
-Note, FreeRADIUS has four main operators for assigning values to attributes:
-
-`=`:: Add the attribute to the list, if and only if an attribute of the same
- name is not already present in that list.
-`:=`:: Add the attribute to the list. If any attribute of the same name is
- already present in that list it is replaced with the new one.
-`+=`:: Add the attribute to the tail of the list, even if attributes of the
- same name are already present in the list.
-`^=`:: Add the attribute to the head of the list, even if attributes of the
- same name are already present in the list.
-
-These operators allow for attributes to be set to default values and then
-overwritten, e.g. setting a default lease time, but then overwriting it for
-a particular group of clients.
-
-Attributes in the `control` list are not returned in the DHCP reply packets
-but instead govern aspects of server's behaviour.
-
-To use an SQL backend for either static or dynamic IP allocation, un-comment
-the block:
-
-[source,unlang]
-----
-update control {
- &Pool-Name := "local"
-}
-dhcp_sqlippool
-----
-
-The `Pool-Name` control attribute is used in looking up addresses in the
-database. The line containing `dhcp_sqlippool` is a call to invoke an
-instance of a module with that name. This module is responsible for assigning a
-free IP address into the `DHCP-Your-IP-Address` reply attribute from the pool
-identified by `Pool-Name`.
-
-Here `Pool-Name` is being set to a constant value (`local`) indicating
-that a single pool is to be used. If you have multiple pools, then replace this
-`update` block with logic to map clients to the correct pool, as described below.
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/policy_device_options.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/policy_device_options.adoc
deleted file mode 100644
index 05845ea893..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/policy_device_options.adoc
+++ /dev/null
@@ -1,310 +0,0 @@
-== Configure "device", "class" and "group" options
-
-Beyond the global, network and subnet options already described, most sites
-will have a number of group or class based options, and have a requirement for
-setting reply parameters against individual devices.
-
-In general, FreeRADIUS does not differentiate between "classes" (memberships
-defined by some attribute of the DHCP request) and "groups" (memberships
-defined by some manually aggregation related devices, typically based on lists
-of MAC address).
-
-The sample DHCP configuration provided with FreeRADIUS makes use of an internal
-attribute `DHCP-Group-Name` to support the setting of different options for
-different groups of devices.
-
-In general the groups to which a device belongs is determined during the
-processing of a request and these are added as instances of the
-`DHCP-Group-Name` attribute. This may be by performing a test on one or more
-request parameters (akin to a "class"), hash-based lookup of up all of part of
-an attribute in a local list (akin to a "subclass"), or doing the same using a
-remote datastore (SQL, LDAP, REST API, etc).
-
-FreeRADIUS can then iterate over `DHCP-Group-Name` to set group-specific
-options.
-
-We describe some of these options in more detail.
-
-=== Directly in Policy
-
-Simple class options can be written directly into policy. This is most
-suited to those options that rarely change and are based on attributes in the
-request such as the `User-Class`.
-
-Consider the ISC DHCP configuration snippet:
-
-[source,iscdhcp]
-----
-filename "undionly.kpxe";
-class "pxeclient" {
- match option substring(user-class,0,4);
-}
-subclass "pxeclient" "iPXE" {
- filename "http://my.web.server/boot_script.php";
-}
-----
-
-Or the equivalent Kea configuration:
-
-[source,isckea]
-----
-"Dhcp4": {
- "option-data": [
- { "name": "boot-file-name", "data": "undionly.kpxe" }
- ],
- "client-classes": [
- {
- "name": "pxeclient",
- "test": "substring(option[77],0,4) == 'iPXE'",
- "option-data": [
- {
- "name": "boot-file-name",
- "data": "http://my.web.server/boot_script.php"
- }
- ]
- }
- ]
- ...
-}
-----
-
-These define the "filename" DHCP option differently based on whether or not the
-supplied "user-class" option begins with "iPXE".
-
-FreeRADIUS provides multiple ways for this to be configured.
-
-For example, the following "unlang" policy implements the class options defined
-above:
-
-[source,unlang]
-----
-if (&DHCP-User-Class && "%{substring:&DHCP-User-Class 0 4}" == "iPXE") {
- update reply {
- &DHCP-Boot-Filename := "http://my.web.server/boot_script.php"
- }
-} else {
- update reply {
- &DHCP-Boot-Filename := "undionly.kpxe"
- }
-}
-----
-
-Policy-based configuration of DHCP options is also useful for complex matching.
-For example, the following Unlang sets the DHCP-Boot-Filename parameter based
-on the request's DHCP-Client-Identifier using regular expression captures,
-provided that it matches the given format:
-
-[source,unlang]
-----
-if (&DHCP-Client-Identifier && \
- "%{string:DHCP-Client-Identifier}" =~ /^RAS([0-9])-site([A-Z])$/) {
- update reply {
- &DHCP-Boot-Filename := "rasboot-%{1}-%{2}.kpxe"
- }
-}
-----
-
-=== In Text Files
-
-The `files` module that has already been described for global, network and
-subnet options can also be used to apply options to groups of clients.
-
-Firstly we must defined a mapping from a set of clients clients to their
-respective groups. One option for this is to use the `passwd` module, for
-which a sample configuration is included.
-
-Firstly symlink or copy the module configuration
-`<raddb>/mods-available/dhcp_passwd` into `<raddb>/mods-enabled/`. The
-suggested configuration expects the group membership file to be in
-`<raddb>/mods-config/files/dhcp_groups` and take the form of:
-
-[source,config]
-----
-<group1 name>|<hardware address>,<hardware address>,<hardware address>
-<group2 name>|<hardware address>,<hardware address>
-----
-
-i.e. one line for each group starting with the group name followed by a pipe
-character and then a comma-separated list of hardware addresses.
-
-The `allow_multiple_keys` option allows for a host to be a member of
-more than one group.
-
-Sample configuration for looking up group options is contained in
-`<raddb>/policy.d/dhcp` in the `dhcp_group_options` policy and in
-`<raddb>/mods-available/dhcp_files` as the `dhcp_set_group_options` instance.
-
-The same data file `<raddb>/mods-config/files/dhcp` is used to lookup
-group options as was used for global and network options. In this instance,
-add entries with the group name as the key such as:
-
-[source,config]
-----
-group1
- DHCP-Log-Server := 10.10.0.100,
- DHCP-LPR-Server := 10.10.0.200
-
-group2
- DHCP-LPR-Server := 192.168.20.200
-----
-
-=== In the SQL Database
-
-Policy and files are both read during startup and editing them while
-FreeRADIUS is running will not result in any changes in behaviour. If
-you require regular changes to DHCP options, then storing them in
-an SQL database provides greater flexibility since the queries will be run in
-response to each DHCP packet rather than requiring the server to be restarted.
-
-DHCP reply options for devices (including network-specific options) can be
-fetched from SQL using an arbitrary lookup key. This can be performed multiple
-times as necessary using different contexts, for example to first set
-subnet-specific options and then to set group-specific options.
-
-The default schema contains three tables to support this:
-
-"dhcpreply" contains reply options for a given identifier (e.g. MAC Address):
-
-.dhcpreply table
-|===
-|Identifier |Attribute |Op |Value |Context
-
-|`02:01:aa:bb:cc:dd` |`DHCP-Log-Server` |`:=` |`192.0.2.10` |`by-mac`
-|`02:01:aa:bb:cc:dd` |`DHCP-LPR-Server` |`:=` |`192.0.2.11` |`by-mac`
-|`02:01:aa:bb:cc:dd` |`Fall-Through` |`:=` |`Yes` |`by-mac`
-|===
-
-"dhcpgroup" maps identifiers to a group of options that can be shared:
-
-.dhcpgroup table
-|===
-|Identifier |GroupName |Priority |Context
-
-|`02:01:aa:bb:cc:dd` |`salesdept` |`10` |`by-mac`
-|===
-
-"dhcpgroupreply" contains reply options for each group:
-
-.dhcpgroupreply table
-|===
-|GroupName |Attribute |Op |Value |Context
-
-|`salesdept` |`DHCP-NTP-Servers` |`:=` |`192.0.2.20` |`by-mac`
-|`salesdept` |`DHCP-Log-Server` |`+=` |`192.0.2.21` |`by-mac`
-|`salesdept` |`DHCP-LPR-Server` |`^=` |`192.0.2.22` |`by-mac`
-|===
-
-Within the context of assigning options directly to devices, as well as to
-manually-curated groups of devices keyed by their MAC address:
-
- - Place device-specific options in the "dhcpreply" table.
- - Add `Fall-Through := Yes` to the options in the "dhcpreply" table in order
- to trigger group lookups, which are disabled by default.
- - Place entries in the "dhcpgroup" `identifier = <MAC-Address>, groupname = <group>, priority =
- <priority>` in the "dhcpgroup" table to map a device to its groups by
- priority.
- - Place the grouped options in the "dhcpgroupreply" table.
- - For each of the above, set `Context` to something by which the option
- lookup is referred to in the policy, for example `Context = 'by-mac'`.
-
-For the above example you would add the following to the DHCP virtual server to
-perform reply option lookup using the device's MAC address against the `by-mac`
-context:
-
-[source,unlang]
-----
-update control {
- &DHCP-SQL-Option-Context := "by-mac"
- &DHCP-SQL-Option-Identifier := &request:DHCP-Client-Hardware-Address
-}
-dhcp_sql.authorize
-----
-
-In the above, the DHCP reply options would be assigned to a device with MAC
-address 02:01:aa:bb:cc:dd as follows:
-
- - Firstly, the `DHCP-Log-Server` option would be set to `192.0.2.10` and the
- `DHCP-LPR-Server` option set to `192.0.2.11`.
- - `Fall-Through` is set, so the group mapping is then queried which
- determines that the device belongs to a single `salesdept` group.
- - Finally, the options for the `salesdept` group are now merged, setting a
- `DHCP-NTP-Servers` option to `192.0.2.20`, appending an additional
- `DHCP-Log-Server` option set to `192.0.2.21`, and prepending an additional
- `DHCP-LPR-Server` option set to `192.0.2.22`.
-
-If instead you wanted to perform a "subclass" lookup based on the first three
-octets of the device's MAC address then with tables containing the following
-sample data you could invoke an SQL lookup as shown:
-
-."dhcpreply" table:
-|===
-|Identifier |Attribute |Op |Value |Context
-
-|`000393` |`Fall-Through` |`:=` |`Yes` |`class-vendor`
-|`000a27` |`Fall-Through` |`:=` |`Yes` |`class-vendor`
-|`f40304` |`Fall-Through` |`:=` |`Yes` |`class-vendor`
-|===
-
-."dhcpgroup" table:
-|===
-|Identifier |GroupName |Priority |Context
-
-|`000393` |`apple` |`10` |`class-vendor`
-|`000a27` |`apple` |`10` |`class-vendor`
-|`f40304` |`google` |`10` |`class-vendor`
-|===
-
-."dhcpgroupreply" table:
-|===
-|GroupName |Attribute |Op |Value |Context
-
-|`apple` |`DHCP-Boot-Filename` |`:=` |`apple.efi` |`class-vendor`
-|`google` |`DHCP-Boot-Filename` |`:=` |`google.efi` |`class-vendor`
-|===
-
-
-[source,unlang]
-----
-update control {
- &DHCP-SQL-Option-Context := "class-vendor"
- &DHCP-SQL-Option-Identifier := \
- "%{substring:%{hex:&DHCP-Client-Hardware-Address} 0 6}"
-}
-dhcp_sql.authorize
-----
-
-The file `policy.d/dhcp` contains a policy named `dhcp_policy_sql` which
-provides further worked examples for different types of option lookups.
-
-=== Testing "device", "class" and "group" options
-
-You should now test that any device-related options that you have configured
-using the various methods available are applied successfully by generating
-packets containing those parameters based upon which the reply options are set.
-
-For example, to test the iPXE user class example above you might want to
-generate a request as follows:
-
-[source,shell]
-----
-cat <<EOF > dhcp-packet-ipxe-boot.txt
-DHCP-Message-Type := DHCP-Discover
-DHCP-Client-Hardware-Address := 02:01:aa:bb:cc:dd
-DHCP-User-Class := "iPXE-class-abc"
-EOF
-----
-
-To which you would expect to see a response such as:
-
-.Example output from dhcpclient
-===============================
- dhcpclient: ...
- ----------------------------------------------------------------------
- Waiting for DHCP replies for: 5.000000
- ----------------------------------------------------------------------
- ...
- DHCP-Message-Type = DHCP-Offer
- DHCP-Your-IP-Address = 1.2.3.4
- DHCP-Boot-Filename := "http://my.web.server/boot_script.php"
- ...
-===============================
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/policy_ippool_access.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/policy_ippool_access.adoc
deleted file mode 100644
index 40b8e3094a..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/policy_ippool_access.adoc
+++ /dev/null
@@ -1,54 +0,0 @@
-== Configure access restrictions for pools
-
-We can combine what we have learned in the preceeding sections to provide pools
-whose access is restricted in some way, for example to a particular class.
-
-Consider the ISC DHCP configuration snippet:
-
-[source,iscdhcp]
-----
-subnet 10.99.99.0 netmask 255.255.255.0 {
- pool {
- range 10.99.99.200 10.99.99.250;
- allow members of "printers";
- }
- option routers 10.99.99.1;
-}
-----
-
-Or the equivalent Kea configuration:
-
-[source,isckea]
-----
-"Dhcp4": {
- "subnet4": [{
- "subnet": "10.99.99.0/24",
- "pools": [
- {
- "pool": "10.99.99.200 - 10.99.99.250",
- "client-class": "printers"
- }
- ],
- "option-data": [
- { "name": "routers", "data": "10.10.0.1" }
- ]
- }],
- ...
-}
-----
-
-These define a subnet containing a single pool that is restricted to members of
-the "printers" class. (The definition for this class is omitted.)
-
-In FreeRADIUS, to filter access to this pool entries such as the following
-should included in the `<raddb>/mods-config/files/dhcp` configuration file:
-
-[source,config]
-----
-network DHCP-Network-Subnet < 10.99.99.0/24, \
- DHCP-Group-Name == "printers", Pool-Name := "printers-pool"
- DHCP-Router-Address := 10.99.99.1
-----
-
-Note that any number of additional filters can be added to the initial "check"
-line to restrict matches to the network block.
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/policy_ippool_creation.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/policy_ippool_creation.adoc
deleted file mode 100644
index e976873c12..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/policy_ippool_creation.adoc
+++ /dev/null
@@ -1,112 +0,0 @@
-=== Determine the IP pool plan
-
-Except for cases where all IP allocation is performed using a mapping from the
-device MAC address to a fixed IP address, the DHCP configuration will involve
-the use of one or more IP address pools.
-
-FreeRADIUS stores all the IP addresses in its pools in whichever database has
-been chosen. An instance of the `sqlippools` module is used to manage all pools
-within a single table (normally `dhcpippool`). Each row of this table
-corresponds to an IP address that is a member of some pool. The pools are
-distinguished by name, so the table has a column (`pool_name`) that denotes
-this.
-
-Each pool in this table should be composed of a set of equally valid IP
-addresses for the devices that are designated to be members of the pool.
-
-Firstly, consider the network locations to which distinct ranges of IP
-addresses must be allocated and provisionally assign a pool to each.
-
-Next, consider that many networks support multiple co-existing subnets without
-VLAN separation. We will call this a "shared-network" to use the original ISC
-DHCP parlance. In Microsoft DHCP contexts this is often referred to as a
-"multinet".
-
-Often in a shared-network the policy has no regard for which of the network's
-devices is allocated to which subnet. In this case we must create a single,
-combined pool containing all of the IP addresses from each subnet in that
-network. Since all addresses in a pool are treated equally this will mean that
-any IP address may be allocated to a device that is making a DHCP request from
-that network. The appropriate DHCP parameters for the subnet to which the IP
-address belongs is determined after allocation.
-
-There are sometimes shared-networks (or even single subnets) for which IP
-addresses belonging to any subnet may be technically suitable for any device,
-however some local policy wants to assigning them to a particular subnet, for
-example to provide loose segregation between classes of device. In this case we
-define multiple pools, one for each range of IP addresses whose devices needs to
-be differentiated.
-
-The choice of pool is ordinarily determined based on the network from which the
-request originates using a mapping from Layer 2 networks to the pool name
-provided by the user. The indicator for the originating network can be
-overridden when this alone is insufficient to implement the required pool
-selection policy such as when you need to differentiate the pool's users with
-more granularity that their Layer 2 network, such as by considering device
-attributes ("class" membership in ISC parlance) or Option 82 circuit data.
-
-
-=== Populate the IP Pools
-
-By this stage you should have derived a list of pools, the IP address ranges
-contained therein, and the means of selecting the pool to use based on the
-originating network and/or some additional criteria from the request.
-
-A helper Perl script is provided with FreeRADIUS that can be used to populate
-the pools provide that you are using the default schema.
-
-[source,shell]
-----
-rlm_sqlippool_tool -p <pool_name> -s <range_start> -e <range_end> \
- -t <table_name> (-d <sql_dialect> | -f <raddb_dir> [ -i <instance> ]) \
- [ -c <capacity> ] [ -x <existing_ips_file> ]
-----
-
-If, for example, you had a range configured in ISC DHCP as:
-
-[source,iscdhcp]
-----
-range 10.0.0.5 10.0.0.199
-----
-
-and you are using PostgreSQL as your database, and you wish to refer to this pool
-using the name `local`, this could be prepared with:
-
-[source,shell]
-----
-rlm_sqlippool_tool -p local -s 10.0.0.5 -e 10.0.0.199 -t dhcpippool -d postgresql
-----
-
-If the SQL module of FreeRADIUS is already configured then this can
-be referenced so that the tool is able to use the configured connection
-parameters to connect to the database and populate the pool:
-
-[source,shell]
-----
-rlm_sqlippool_tool -p local -s 10.0.0.5 -e 10.0.0.199 -t dhcpippool -f /etc/raddb
-----
-
-For installations that require multiple pools, `rlm_sqlippool_tool` can
-be called referencing a YAML file defining the pools. Comments at the
-head of `rlm_sqlippool_tool` explain the options in more detail.
-
-If static leases are required then these should be set up in the database
-such that the MAC address of the client should be set as the `pool_key`
-against the corresponding address and the `status` column of the row
-representing the address set to `static`. A helper perl script,
-`rlm_iscfixed2ippool` can be used to read an ISC DHCP config file and produce
-SQL to perform these changes or directly update the database:
-
-[source,shell]
-----
-rlm_iscfixed2ippool -c <dhcpd.<raddb> -t <table_name> -k <mac|id> \
- (-d <sql_dialect> | -f <raddb_dir> [-i <instance>])
-----
-
-For example, to read /etc/dhcp/dhcpd.conf and populate the configured
-FreeRADIUS database, using the mac as the identifier:
-
-[source,shell]
-----
-rlm_iscfixed2ippool -c /etc/dhcp/dhcpd.conf -t dhcpippool -k mac -f /usr/local/etc/raddb
-----
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/policy_network_options.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/policy_network_options.adoc
deleted file mode 100644
index e2657a8cfe..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/policy_network_options.adoc
+++ /dev/null
@@ -1,237 +0,0 @@
-== Configure network-specific options and IP pool selection
-
-In an environment where multiple networks (often VLANs) are in use, it is
-necessary to identify which network a client belongs to in order to assign an
-address from the correct pool.
-
-Consider the ISC DHCP configuration snippet:
-
-[source,iscdhcp]
-----
-option domain-name "example.org";
-
-subnet 10.10.0.0 netmask 255.255.0.0 {
- range 10.10.1.10 10.10.10.254;
- range 10.10.100.10 10.10.110.254;
- option routers 10.10.0.1;
- option domain-name-servers 10.10.0.2, 10.10.0.3;
- default-lease-time 7200;
-}
-----
-
-Or the equivalent Kea configuration:
-
-[source,isckea]
-----
-"Dhcp4": {
- "option-data": [
- { "name": "domain-name", "data": "example.org" }
- ],
- "subnet4": [{
- "subnet": "10.10.0.0/16",
- "pools": [ { "pool": "10.10.1.10 - 10.10.10.254" },
- { "pool": "10.10.100.10 - 10.10.110.254" }
- ],
- "option-data": [
- { "name": "routers", "data": "10.10.0.1" },
- { "name": "domain-name-servers", "data": "10.10.0.2, 10.10.0.3" }
- ],
- "valid-lifetime": 7200
- }],
- ...
-}
-----
-
-These define a network consisting of a single subnet 10.10.0.0/16 containing two
-IP address pools 10.10.1.10 - 10.10.10.254 and 10.10.100.10 - 10.10.110.254.
-Requests that are determined to have originated from this network (e.g. because
-their `giaddr` belongs within the subnet) will be assigned the specified DHCP
-parameters and allocated an address from one of its ranges.
-
-To provide equivalent functionality, FreeRADIUS must identify the correct DHCP
-reply parameters as well as the name of the pool to be used for IP address
-assignment, based on the originating network of the request.
-
-The definition for this pool (the addresses contained within it, corresponding
-to the `range` statement in ISC DHCP and Kea) is specified entirely in the
-database: It is precisely the rows in the `dhcpippool` table with a particular
-`pool_name`.
-
-[TIP]
-====
-As described previously, in FreeRADIUS a pool is a set of IP addresses that are
-equally valid with respect to the network policy; therefore, unlike ISC DHCP
-and ISC Kea, FreeRADIUS does not differentiate between the two `range`s.
-Instead we should have previously populated a single pool containing all of the
-IP addresses from both ranges.
-====
-
-FreeRADIUS derives a request attribute called `DHCP-Network-Subnet` which
-honours the standard DHCP process for designating the choice of network, in
-order of preference:
-
- 1. Link Selection Suboption of Option 82
- 2. IPv4 Subnet Selection Option
- 3. Gateway IP Address ("giaddr")
- 4. Client IP Address ("ciaddr", only set for unicast packets)
-
-If `DHCP-Network-Subnet` contains an IP address then this should be used as
-the basis of choosing a network. When there is no address in this attribute it
-can be assumed that the packet has been received from a client on the local
-LAN.
-
-The `files` module in FreeRADIUS provides a simple method to map
-`DHCP-Network-Subnet` to the corresponding pool based on its network
-membership, setting the appropriate options to return to clients. It can also
-set the global options.
-
-[TIP]
-====
-In the case where an instance of the `files` module is used to get global
-default parameters, the `dhcp_common` policy becomes redundant so the
-statement calling the policy (by name) can be commented out in
-`<raddb>/sites-enabled/dhcp`.
-====
-
-To use the provided example `files` module instance for DHCP, symlink or copy
-`<raddb>/mods-available/dhcp_files` into `<raddb>/mods-enabled/` and then
-uncomment the calls to `dhcp_network` in `<raddb>/sites-enabled/dhcp`.
-
-A template configuration file `<raddb>/mods-config/files/dhcp` is also
-provided which should be adapted to suit your network topology.
-
-For the configuration above you may deduce the following configuration, which
-has been extended to include an initial default section for requests originating
-from directly-connected clients on the local LAN (192.168.20/24):
-
-[source,config]
-----
-network Pool-Name := "local"
- DHCP-Domain-Name := "example.org",
- DHCP-Subnet-Mask := 255.255.255.0,
- DHCP-Router-Address := 192.168.20.1,
- DHCP-Domain-Name-Server := 192.168.20.2,
- Fall-Through := yes
-
-network DHCP-Network-Subnet < 10.10.0.0/16, Pool-Name := "remote"
- DHCP-Subnet-Mask := 255.0.0.0,
- DHCP-Router-Address := 10.10.0.1,
- DHCP-Domain-Name-Server := 10.10.0.2,
- DHCP-Domain-Name-Server += 10.10.0.3,
- DHCP-IP-Address-Lease-Time := 7200
-----
-
-Each block in the file starts with a line beginning with the key to be matched.
-In this case the keyword of `network` (defined earlier in `dhcp_networks`
-configuration) is used for each block, so each of the above blocks is a
-candidate during the search.
-
-There may be further filtering of the candidates in the form of `<Attribute>
-<op> <Value>`. In the case of the second block we match the
-`DHCP-Network-Subnet` to an enclosing subnet with
-`DHCP-Network-Subnet < <subnet>`. Additional filters could be added as
-required, comma separated.
-
-Following the filters on the first line, attributes in the `control` list can
-be set using the syntax of `<Attribute> := <Value>`. In this example this is
-used to specify the `Pool-Name` for choosing the appropriate IP pool to
-allocate an address from.
-
-Subsequent indented lines are attribute assignments for values in the `reply`
-list. Note that, apart from the last line, they are all terminated with a
-comma.
-
-The special option `Fall-Through` determines whether, following a match,
-other records are checked for a match. All lookups will match the entry
-with a key of `network` and no further filtering, so `Fall-Through`
-is set on that record in order that the other records will be tested
-to find subnet matches.
-
-=== Example packet processing
-
-For our example, we consider a request arriving from a DHCP relay within
-10.10.0.0/16. In the absence of any specific DHCP subnet selection options in
-the request, the `DHCP-Network-Subnet` attribute is calculated to be the
-relay's IP address, say 10.10.0.1.
-
-The request is matched against the first block, setting an initial pool name to
-"local", domain name to "example.org" and setting some additional global
-default parameters. By virtue of `Fall-Through` being set, the next block is
-considered.
-
-Since the network identifier is within the specified subnet (i.e. `10.10.0.1 <
-10.10.0.0/16`) this second block is matched. This block overrides the pool name
-setting it to "remote", overrides some other global defaults and sets the lease
-time to 7200 seconds. `Fall-Through` is not set, so we are now done with
-deriving the pool name and network options.
-
-When the `dhcp_sqlippool` module is called during DHCP DISCOVER processing (in
-`<raddb>/sites-enabled/dhcp`) the `remote` pool will be used for IP address
-allocation.
-
-The assigned IP address and network parameters will subsequently be returned in
-the DHCP reply.
-
-=== Testing the pool operation and network-specific options
-
-Before proceeding further, you should test the operation of the IP pools and
-ensure that any network-specific reply attributes that you have configured are
-correctly set in replies.
-
-For example, if you have a single, flat pool you should test using sample
-packets for devices with different MAC addresses and/or Client Identifiers.
-
-[source,shell]
-----
-cat <<EOF > dhcp-packet-1.txt
-DHCP-Message-Type := DHCP-Discover
-DHCP-Client-Hardware-Address := 02:01:11:11:11:11
-DHCP-Client-Identifier := device1
-EOF
-----
-
-[source,shell]
-----
-cat <<EOF > dhcp-packet-2.txt
-DHCP-Message-Type := DHCP-Discover
-DHCP-Client-Hardware-Address := 02:01:22:22:22:22
-DHCP-Client-Identifier := device2
-EOF
-----
-
-Generate these packets as show previously using the dhcpclient tool and look
-for `DHCP-Your-IP-Address` in the DHCP responses to determine the IP address
-that has been offered.
-
-Ensure that the DHCP Offer responses contain unique IP addresses. Ensure that
-when these requests are resent within the lifetime of the initial offer that
-the reponses to the subsequent replies contain the original IP address that was
-in the initial offer to the device.
-
-Additionally, ensure that the DHCP Offers contain any network-specific
-parameters that you have specified.
-
-In the case that the policy contains multiple IP pools and network definitions
-for clients belonging to different Layer 2 networks (or indeed belonging to the
-same network but segregated according to some local policy) you should ensure
-that the devices are being mapped to the correct definition.
-
-For a typical policy that selects the IP pool and network options based on the
-originating network for the DHCP packet, explicitly specifying a network by
-including a `DHCP-Subnet-Selection-Option` parameter may avoid the need to test
-from a host within each individual network:
-
-[source,shell]
-----
-cat <<EOF > dhcp-packet-network-10.10.10.0.txt
-DHCP-Message-Type := DHCP-Discover
-DHCP-Client-Hardware-Address := 02:01:aa:bb:cc:dd
-DHCP-Client-Identifier := abc123
-DHCP-Subnet-Selection-Option := 10.10.10.0
-EOF
-----
-
-For policies where the IP pool and network option selection is based on some
-custom criteria it is necessary to include different variations for the
-parameters on which the policy makes the decision. The testing example for the
-class-specific options later in this document provides such an example.
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/policy_subnet_options.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/policy_subnet_options.adoc
deleted file mode 100644
index 1980e89cd0..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/policy_subnet_options.adoc
+++ /dev/null
@@ -1,184 +0,0 @@
-== Configure subnet-specific options for shared networks
-
-In the case that shared-networks are in use, with the pool containing
-equally-valid IP addresses from multiple subnets, it is necessary to set the
-subnet-specific parameters such as `DHCP-Router-Address`, `DHCP-Subnet-Mask`
-and `DHCP-Broadcast-Address` based on the IP address that has been allocated.
-
-Consider the ISC DHCP configuration snippet:
-
-[source,iscdhcp]
-----
-option domain-name "example.org";
-
-shared-network bigdept {
-
- option domain-name-servers 10.10.0.2, 10.10.0.3;
- default-lease-time 7200;
-
- subnet 10.30.10.0 netmask 255.255.255.0 {
- option routers 10.30.10.1;
- }
- subnet 10.30.20.0 netmask 255.255.255.0 {
- option routers 10.30.20.1;
- }
- range 10.30.10.10 10.30.10.254;
- range 10.30.20.10 10.30.20.254;
-
-}
-----
-
-Or the equivalent Kea configuration:
-
-[source,kea]
-----
-"Dhcp4": {
- "option-data": [
- { "name": "domain-name", "data": "example.org" }
- ],
- "shared-networks": [{
- "name": "bigdept",
- "option-data": [
- { "name": "domain-name-servers", "data": "10.10.0.2, 10.10.0.3" }
- ],
- "valid-lifetime": 7200,
- "subnet4": [{
- "subnet": "10.30.10.0/24",
- "pools": [ { "pool": "10.30.10.10 - 10.30.10.254" } ],
- "option-data": [
- { "name": "routers", "data": "10.30.10.1" }
- ]
- }],
- "subnet4": [{
- "subnet": "10.30.20.0/24",
- "pools": [ { "pool": "10.30.20.10 - 10.30.20.254" } ],
- "option-data": [
- { "name": "routers", "data": "10.30.20.1" }
- ]
- }]
- }],
- ...
-}
-----
-
-As with the network to pool lookup, an instance of the `files` modules can be
-employed (this time after the allocation of an IP address) to set the correct
-reply parameters based on the subnet membership of the assigned address.
-
-To do this, we can use this section of `<raddb>/mods-available/dhcp_files`:
-
-[source,config]
-----
-files dhcp_subnets {
- filename = ${modconfdir}/files/dhcp
- key = "subnet"
-}
-----
-
-Additionally, uncomment the `dhcp_subnets` policy in `<raddb>/policy.d/dhcp`.
-This policy wraps the call to the `dhcp_subnets` files module with code that
-"tightens" the `DHCP-Network-Subnet` attribute by setting it to the
-just-allocated IP address.
-
-The relevant entries in the `<raddb>/mods-config/files/dhcp` configuration
-file might then look something like this:
-
-[source,config]
-----
-network
- DHCP-Domain-Name := "example.org",
- Fall-Through := yes
-
-network DHCP-Network-Subnet < 10.30.0.0/16, Pool-Name := "bigdept"
- DHCP-Domain-Name-Server := 10.10.0.2,
- DHCP-Domain-Name-Server += 10.10.0.3,
- DHCP-IP-Address-Lease-Time := 7200
-
-subnet DHCP-Network-Subnet < 10.30.10.0/24
- DHCP-Router-Address := 10.30.10.1
-
-subnet DHCP-Network-Subnet < 10.30.20.0/24
- DHCP-Router-Address := 10.30.20.1
-----
-
-=== Example packet processing
-
-For our example, we consider a request arriving from a DHCP relay within
-10.30.10.0/24. In the absence of any specific DHCP subnet selection options in
-the request, the `DHCP-Network-Subnet` attribute is calculated to be the
-relay's IP address, say 10.30.10.1.
-
-The request is matched against the first "network" block, setting the domain
-name to "example.org". By virtue of `Fall-Through` being set, the next "network"
-block is considered.
-
-Since the network identifier is within the specified subnet (i.e. `10.30.10.1 <
-10.30.0.0/16`) this second "network" block is matched. This block sets the pool
-name to "bigdept", sets some network-specific DNS resolvers and sets the lease
-time to 7200 seconds. `Fall-Through` is not set, so we are now done with
-deriving the pool name and network options.
-
-When the `dhcp_sqlippool` module is called during DHCP DISCOVER processing (in
-`<raddb>/sites-enabled/dhcp`) the `bigdept` pool will be used for IP address
-allocation.
-
-After IP allocation the `dhcp_subnet` policy and files instance are called.
-Before the subnet options are looked up the `DHCP-Network-Subnet`
-attribute is tightened to match the assigned IP address, say 10.30.20.123.
-
-The request does not match the first subnet block since 10.30.20.123 is not
-within 10.30.10.0/24. However, the request does match the second subnet block
-since `10.30.20.123 < 10.30.20.0/24`. This block sets the default gateway
-reply parameter. `Fall-Through` is not set, so we are now done with deriving
-the pool name and network options.
-
-The assigned IP address, network and subnet parameters will subsequently be
-returned in the DHCP reply.
-
-=== Testing the subnet-specific options
-
-If you have set any subnet-specific reply parameters then you should test these
-before proceeding further.
-
-For example, in the case that you have a single, large pool spanning two IP
-subnets you might want to test by repeatedly allocating addresses using sample
-packets with different MAC addresses, each time checking to ensure that the
-DHCP parameters correspond to the IP address that has been offered.
-
-.Example output from dhcpclient showing a response
-==================================================
- dhcpclient: ...
- ...
- ----------------------------------------------------------------------
- Waiting for DHCP replies for: 5.000000
- ----------------------------------------------------------------------
- ...
- DHCP-Your-IP-Address = 10.0.10.50
- DHCP-Router-Address = 10.0.10.1
- DHCP-Broadcast-Address = 10.0.10.255
- DHCP-Subnet-Mask = 255.255.255.255
-==================================================
-
-
-.Example output from dhcpclient showing a response
-==================================================
- dhcpclient: ...
- ...
- ----------------------------------------------------------------------
- Waiting for DHCP replies for: 5.000000
- ----------------------------------------------------------------------
- ...
- DHCP-Your-IP-Address = 10.99.99.50
- DHCP-Router-Address = 10.99.99.1
- DHCP-Broadcast-Address = 10.99.99.255
- DHCP-Subnet-Mask = 255.255.255.255
-==================================================
-
-
-[TIP]
-====
-If the subnets are large then you might want to temporarily reduce their
-size by setting the `status` field of the majority of the rows for each subnet
-to "`disabled`" to cause offers to be made more readily with IP addresses in
-different subnets.
-====
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/prepare.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/prepare.adoc
deleted file mode 100644
index aa43530a66..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/prepare.adoc
+++ /dev/null
@@ -1,59 +0,0 @@
-== Preparation
-
-It is necessary to consider the requirements for the installation in order to
-devise an efficient and manageable set up.
-
-=== Understand the network topology
-
-When multiple networks (VLANs) are in use consideration must be given to how
-the correct "pool" (IP address ranges) from which to allocate addresses is
-identified.
-
-The policy for setting specific DHCP options (e.g. lease time, default gateway,
-time server and vendor-specific parameters) for different groups of hosts,
-based on their network or some device attributes either supplied in the DHCP
-requests or determined by dynamic lookup, should be well defined and
-understood.
-
-Other DHCP servers may implement implicit assumptions about the requirement of
-your network topology and silently define particular behaviours, such as the
-selection of IP address pool for a request based on a relay address. Some of
-these behaviours must be specifed explicitly when using FreeRADIUS.
-
-=== Choose a database backend
-
-FreeRADIUS stores its leases in an SQL database, so one of the key decisions to
-make is which database to use.
-
-FreeRADIUS supports:
-
- * SQLite
- * PostgreSQL
- * MySQL / MariaDB
- * Microsoft SQL Server
- * Oracle
-
-In most configurations the SQL database is likely to be the limiting component
-that restricts the IP allocation throughput of the overall system. Each
-database server has its own performance characteristics and unique approach to
-features such as high-availability.
-
-The choice of database should be made carefully based on the performance and
-high-availability requirements of the system, as well as any prior experience.
-
-[TIP]
-====
-SQLite is an in-process database that uses the local file system, is simple to
-configure and is suitable for smaller installations. However, users with larger
-address pools or high availability requirements should choose one of the other
-standalone databases based on criteria such as performance, features,
-familiarity and your need for commercial support.
-====
-
-FreeRADIUS ships with a default database schema and set of queries for each
-supported database. These are sufficient for most DHCP deployments but can be
-reviewed and modified as required to suit a particular situation, for example
-to customise the IP allocation policy such as by disabling address
-"stickiness".
-
-Now xref:protocols/dhcp/enable.adoc[enable the DHCP service].
diff --git a/doc/antora/modules/howto/pages/protocols/dhcp/test.adoc b/doc/antora/modules/howto/pages/protocols/dhcp/test.adoc
deleted file mode 100644
index 322de08fa9..0000000000
--- a/doc/antora/modules/howto/pages/protocols/dhcp/test.adoc
+++ /dev/null
@@ -1,143 +0,0 @@
-== Testing the DHCP service
-
-We can verify that FreeRADIUS is providing a DHCP service using the
-`dhcpclient` tool that is included with the FreeRADIUS distribution.
-
-Temporarily configure FreeRADIUS to issue a single static IP address to all
-clients by updating the `dhcp DHCP-Discover` section in the `dhcp` virtual
-server to include the following:
-
-[source,unlang]
-----
-update reply {
- &DHCP-Your-IP-Address := 1.2.3.4
-}
-----
-
-Define a sample DHCP packet as follows:
-
-[source,shell]
-----
-cat <<EOF > dhcp-packet.txt
-DHCP-Message-Type := DHCP-Discover
-DHCP-Client-Hardware-Address := 02:01:aa:bb:cc:dd
-DHCP-Client-Identifier := abc123
-EOF
-----
-
-We can now generate this packet by invoking one of the following commands based
-on the current circumstances...
-
-From the host that is running the FreeRADIUS DHCP server:
-
-[source,shell]
-----
-dhcpclient -i lo 255.255.255.255 -f dhcp-packet.txt -x auto
-----
-
-From a different host with an interface (eth0) in the same broadcast domain
-as the FreeRADIUS DHCP server:
-
-[source,shell]
-----
-dhcpclient -i eth0 255.255.255.255 -f dhcp-packet.txt -x auto
-----
-
-If all of the DHCP broadcast traffic in other Layer 2 networks is converted to
-unicast by DHCP relay agents then it is not necessary for FreeRADIUS to listen
-on a broadcast address. In this case you can test DHCP using a unicast request:
-
-[source,shell]
-----
-dhcpclient 192.0.2.10 -f dhcp-packet.txt -x auto
-----
-
-[NOTE]
-====
-In order for the returned, unicast DHCP OFFER to be received it is necessary to
-ensure that the `DHCP-Your-IP-Address` parameter set by FreeRADIUS matches an
-address on the interface used by the dhcpclient tool to send the Discover
-packet.
-====
-
-When one of the above commands is run, the tool with generate output such as
-the following which shows that the packet was sent and that it is now waiting
-for replies:
-
-.Example output from dhcpclient showing the request
-===================================================
- dhcpclient: ...
- ----------------------------------------------------------------------
- DHCP-Opcode = 0x01
- DHCP-Hardware-Type = 0x01
- DHCP-Hardware-Address-Length = 0x06
- DHCP-Hop-Count = 0x00
- DHCP-Transaction-Id = 0x5e0bbfab
- DHCP-Number-of-Seconds = 0x0000
- DHCP-Flags = 0x0000
- DHCP-Client-IP-Address = 0x00000000
- DHCP-Your-IP-Address = 0x00000000
- DHCP-Server-IP-Address = 0x00000000
- DHCP-Gateway-IP-Address = 0x00000000
- ...
- ----------------------------------------------------------------------
- Waiting for DHCP replies for: 5.000000
- ----------------------------------------------------------------------
-===================================================
-
-
-Each received DHCP response will generate output such as the following:
-
-.Example output from dhcpclient showing a response
-==================================================
- ...
- ----------------------------------------------------------------------
- DHCP-Opcode = Server-Message
- DHCP-Hardware-Type = Ethernet
- DHCP-Hardware-Address-Length = 6
- DHCP-Hop-Count = 0
- DHCP-Transaction-Id = 1577828267
- DHCP-Number-of-Seconds = 0
- DHCP-Flags = 0
- DHCP-Client-IP-Address = 0.0.0.0
- DHCP-Your-IP-Address = 1.2.3.4
- DHCP-Server-IP-Address = 192.0.2.10
- DHCP-Gateway-IP-Address = 0.0.0.0
- DHCP-Client-Hardware-Address = 02:42:0a:00:00:0b
- DHCP-Message-Type = DHCP-Offer
- DHCP-Client-Identifier = 0x616263313233
- Waiting for additional DHCP replies for: 4.999429
- ...
-==================================================
-
-Examine the DHCP response to ensure that it has the correct message type
-(`DHCP-Offer`, in this case), contains the temporary IP address that you
-configured earlier, i.e. `DHCP-Your-IP-Address = 1.2.3.4`, and any other
-expected reply parameters (which we configure later). You should also carefully
-examine the output of a FreeRADIUS debug session (`radius -X`) to ensure that
-the policy is being executed in the way that you expect and that no warnings
-are being generated.
-
-You can now change the content of the sample DHCP request by editing the
-`dhcp-packet.txt` file and re-run the above command to see the server's reply.
-You should examine the DHCP dictionary distrubuted with FreeRADIUS (usually
-`/usr/share/freeradius/dictionary.dhcp`) which provides the list of all of the
-DHCP parameters ("attributes") understood by FreeRADIUS.
-
-[WARNING]
-====
-When you are done **remember** to remove the temporary edit that was made to
-the `dhcp` virtual server that provides the static IP assignment.
-====
-
-=== Testing the DHCP policy
-
-The remainder of this guide describes how to configure the IP address plan,
-setup the IP pools and define a DHCP policy. You should develop your policy by
-making small, incremental changes to the provided configuration and then test
-those changes with the approach described above, using `dhcpclient` and `radius -X`,
-modifying the sample DHCP packet as required. If you break the policy then
-revert the last change, attempt to understand what went wrong, and try
-something else.
-
-Now xref:protocols/dhcp/policy.adoc[define the DHCP policy].
diff --git a/doc/antora/modules/howto/pages/protocols/proxy/enable_proxy_protocol.adoc b/doc/antora/modules/howto/pages/protocols/proxy/enable_proxy_protocol.adoc
deleted file mode 100644
index a4ab3dbada..0000000000
--- a/doc/antora/modules/howto/pages/protocols/proxy/enable_proxy_protocol.adoc
+++ /dev/null
@@ -1,114 +0,0 @@
-== Enabling PROXY Protocol
-
-Now that we have a working configuration which used RadSec and HAproxy
-or Traefik, we are finally ready to enable PROXY Protocol.
-
-Configure FreeRADIUS on the `radsecsvr` host to expect the PROXY
-Protocol for RadSec connections. This is done by editing the `listen
-{}` section of the `tls` virtual server to include a reference to the
-proxy protocol:
-
-.Enabling PROXY Protocol in a FreeRADIUS virtual server
-=======================================================
-
- listen {
- ...
- proxy_protocol = true
- ...
- }
-
-=======================================================
-
-Now restart the debugging session:
-[source,shell]
-----
-radiusd -fxxl /dev/stdout
-----
-
-
-For HAproxy, you should enable the PROXY Protocol on connections to
-the RadSec backend, by editing the `backend` definition to add a
-`send-proxy` argument:
-
-.Example HAproxy backend configuration with PROXY Protocol
-==========================================================
-
- backend radsec_be
- mode tcp
- balance roundrobin
- server radsecsvr 172.23.0.3:2083 send-proxy
-
-==========================================================
-
-Note the `send-proxy` argument in the `server` definition.
-
-Now reload the HAproxy service:
-
-[source,shell]
-----
-service haproxy reload
-----
-
-
-For Traefik, enable the PROXY Protocol on connections to the RadSec
-backend by editing the `radsec-service` definition to add a reference
-to the proxy protocol"
-
-.Example Traefik service configuration with PROXY Protocol
-==========================================================
-
- radsec-service:
- loadBalancer:
- servers:
- - address: "172.23.0.3:2083"
- proxyProtocol:
- version: 1
-
-==========================================================
-
-Note the `proxyProtocol` and `version: 1` directives.
-
-Traefik should automatically detect the updates and reconfigure the
-service.
-
-
-=== Testing RadSec connectivity via a proxy using PROXY Protocol
-
-Finally, with your test client configured to use the proxy, perform a
-test authentication:
-
-[source,shell]
-----
-echo "User-Name = bob" | radclient 127.0.0.1 auth testing123
-----
-
-You should expect to see the familiar output:
-
-.Example output from radclient
-==============================
-
- Sent Access-Request Id 252 from 0.0.0.0:50118 to 127.0.0.1:1812 length 27
- Received Access-Accept Id 252 from 127.0.0.1:1812 to 127.0.0.1:50118 length 39
-
-==============================
-
-Now examine the FreeRADIUS debug output on the RadSec server:
-
-.Expected output from `radiusd -X` with PROXY Protocol
-======================================================
-
- ...
- (0) (TLS) Received PROXY protocol connection from client \
- 172.23.0.2:55343 -> 172.23.0.4:2083, via proxy 172.23.0.4:40268 -> 0.0.0.0:2083
- ...
- (0) Received Access-Request Id 227 from 172.23.0.2:55343 to 172.23.0.4:2083 length 49
- (0) Sent Access-Accept Id 227 from 172.23.0.4:2083 to 172.23.0.2:55343 length 0
- ...
-
-======================================================
-
-The output indicates that FreeRADIUS is receiving the originating
-connection information from the PROXY Protocol. FreeRADIUS then
-handles the RadSec requests as though they have been received directly
-from the originating client.
-
diff --git a/doc/antora/modules/howto/pages/protocols/proxy/enable_radsec.adoc b/doc/antora/modules/howto/pages/protocols/proxy/enable_radsec.adoc
deleted file mode 100644
index f5e7603c10..0000000000
--- a/doc/antora/modules/howto/pages/protocols/proxy/enable_radsec.adoc
+++ /dev/null
@@ -1,188 +0,0 @@
-== Enabling RadSec with FreeRADIUS
-
-Our first task is to set up a RadSec server by configuring an instance of
-FreeRADIUS to accept RADIUS over TLS requests.
-
-The following steps should be performed on the host which will be the
-RadSec server, we will call it `radsecsvr`.
-
-You can install FreeRADIUS using the NetworkRADIUS packages by
-following the instructions provided here:
-
-<https://networkradius.com/packages/>
-
-Before making any configuration changes, you should stop the radiusd
-service:
-
-[source,shell]
-----
- service radiusd stop
-----
-
-Then, enable the `tls` virtual server:
-
-[source,shell]
-----
-cd /etc/raddb/sites-enabled
-ln -s ../sites-available/tls
-----
-
-The FreeRADIUS distribution contains an example Certificate Authority
-that will have generated the necessary CA, server and client
-certificates and keys during package installation. You can use this
-CA, or you can use your own CA and certificates.
-
-[TIP]
-====
-If the example certificates are not present (for example if FreeRADIUS was
-installed from source) then FreeRADIUS will fail to start. The files can be
-regenerated by running `make` in the `/etc/raddb/certs` directory.
-====
-
-Edit the `tls` virtual server configuration, in order to add
-definitions for the clients by extending the `clients radsec {}` section:
-
-.Example radsec client definitions in `/etc/raddb/sites-available/tls`
-====
-
- clients radsec {
- ...
- # Direct connections from the test client
- client radseccli {
- ipaddr = 172.23.0.2
- proto = tls
- virtual_server = default
- }
- # Connections via HAproxy
- client haproxy {
- ipaddr = 172.23.0.4
- proto = tls
- virtual_server = default
- }
- # Connections via Traefik
- client traefik {
- ipaddr = 172.23.0.5
- proto = tls
- virtual_server = default
- }
- }
-
-====
-
-The client `ipaddr` configuration item is used to match the source IP
-address of incoming connections. You must add client definitions for
-each of the clients which will connect.
-
-For RadSec, you can just list the IP address of the RadSec client.
-This client definition is used for processing RADIUS packets from the
-RadSec client.
-
-[NOTE]
-====
-A `secret` does not have to be specified for RadSec clients, as the
-default is `radsec`. If you specify a secret, then that will be used
-instead of `radsec`.
-====
-
-When the PROXY protocol is used, you must _also_ define a client which
-matches the IP address of the proxy (haproxy, etc). This client is
-only used to check that the source IP is permitted to connect to the
-server. Fields other than `ipaddr` can be specified (and in some
-cases may be required). However, all other fields will be ignored.
-
-For testing purposes, we want to amend the `default` virtual server so
-that it accepts all authentication reqeusts and immediately responds
-to accounting requests.
-
-Edit the `/etc/raddb/sites-enabled/default` file so that the beginning of
-the `authorize` and `preacct` sections looks as follows:
-
-.Example default virtual server modification to unconditionally accept Access-Requests
-====
-
- authorize {
- accept
- ...
- }
- ...
- preacct {
- handled
- ...
- }
-
-====
-
-This change makes the `authorize` section always "accept" the user,
-and makes the `preacct` section always say "we handled the accounting
-request". These changes are only for testing, and should never be
-used in production.
-
-Start the FreeRADIUS service in the foreground with debugging enabled:
-
-[source,shell]
-----
-radiusd -fxxl /dev/stdout
-----
-
-Examine the output from FreeRADIUS to ensure that it is now listening for
-RadSec connection on TCP/2083:
-
-.Example output from running `radiusd -fxxl /dev/stdout`
-====
-
- FreeRADIUS Version 3.0.24
- Copyright (C) 1999-2021 The FreeRADIUS server project and contributors
- ...
- ... : Debug: Listening on auth+acct proto tcp address * port 2083 (TLS) bound to server default
- ... : Debug: Listening on auth address * port 1812 bound to server default
- ... : Debug: Listening on acct address * port 1813 bound to server default
- ... : Debug: Listening on auth address :: port 1812 bound to server default
- ... : Debug: Listening on acct address :: port 1813 bound to server default
- ...
- ... : Info: Ready to process requests
-
-====
-
-FreeRADIUS is now ready to process RadSec traffic.
-
-For testing, we first test normal RADIUS over UDP functionality, then
-the RadSec connection using a test client, then introduce a proxy
-server, and finally we enable PROXY Protocol. Doing the tests in this
-way ensures that we know that all previous steps work before trying
-the next step. This process allows us to quickly narrow down
-problems, and gets us to the final goal _faster_ than just "doing
-everything all at once".
-
-=== Testing the RADIUS policy
-
-Before moving on, verify that the FreeRADIUS policy is able to
-authenticate a local test RADIUS Access-Request over UDP:
-
-[source,shell]
-----
-echo "User-Name = terry" | radclient 127.0.0.1 auth testing123
-----
-
-Due to the `accept` we added in the `authorize` section, the expected
-output should be an Access-Accept:
-
-.Expected output from radclient
-===============================
-
- Sent Access-Request Id 157 from 0.0.0.0:36850 to 127.0.0.1:1812 length 27
- Received Access-Accept Id 157 from 127.0.0.1:1812 to 127.0.0.1:36850 length 20
-
-===============================
-
-Any other output indicates that there is a problem with the FreeRADIUS
-configuration which *must* be solved before testing RadSec. Carefully verify that
-you have carried out each of the above steps correctly and examine the debug
-output from FreeRADIUS, which will usually tell you what is wrong.
-
-See [how to read the debug
-output](http://wiki.freeradius.org/radiusd-X) for instructions on
-reading amd understanding the debug output.
-
-The next step is to xref:protocols/proxy/radsec_client.adoc[configure
-FreeRADIUS as a RadSec test client] so that we can verify that our
-RadSec server is working.
diff --git a/doc/antora/modules/howto/pages/protocols/proxy/index.adoc b/doc/antora/modules/howto/pages/protocols/proxy/index.adoc
deleted file mode 100644
index 5100635921..0000000000
--- a/doc/antora/modules/howto/pages/protocols/proxy/index.adoc
+++ /dev/null
@@ -1,126 +0,0 @@
-= Proxying RadSec and enabling PROXY Protocol
-
-This guide shows how to set up FreeRADIUS to serve RadSec connections, fronted
-by either HAproxy or Traefik as Layer 4 proxies that pass on the original
-client connection information using PROXY Protocol.
-
-It is not a comprehensive guide to using RadSec with FreeRADIUS. It presents a
-basic configuration that uses an example CA and does not validate certificate
-attributes or perform revokation status.
-
-
-== Introduction
-
-FreeRADIUS supports receiving RADIUS requests over TLS-enabled TCP connections
-and supports proxying of requests over TCP connections to another TLS-enabled
-homeserver. The protocol for RADIUS over TLS is called "RadSec" and is defined
-in RFC 6614.
-
-FreeRADIUS is a capable and performant application-aware ("Layer 7") proxy /
-load-balancer for RadSec and other forms of RADIUS traffic.
-
-
-=== Layer 4 proxying
-
-Rather than use an application-aware proxy it is sometimes better to reduce the
-performance impact incurred by re-encoding an application protocol by using a
-"Layer 4" proxy that operates at the level of individual connections without
-regard for the application protocol. Such a proxy is more of a "bump in the
-wire" than a request buffer and minimises the latency incurred due to proxying.
-
-It is common to see software such as HAproxy and Traefik used in Layer 4 mode
-in place of FreeRADIUS for purposes such as connection load balancing. In
-addition to improved performance, these tools have the benefit that they
-typically support dynamic service discovery and "hitless" reloads to
-automatically adapt their connection routing based on changes to backend
-services such as the introduction of new nodes with even a momentary loss of
-service.
-
-
-=== Loss of connection information
-
-When TCP connections are relayed through Layer 4 proxies the information
-about the originating source of the connection is no longer known to the
-backend service, unless it is otherwise made available. Identifying the
-originator of connections is often necessary for security purposes and for
-request processing.
-
-Whilst many application protcols support headers that allow proxies to preserve
-connection information these are not helpful in the context of Layer 4
-proxying: The process of populating headers requires knowledge of the
-application protocol to re-encode requests as they are transmitted between the
-frontend and backend connections.
-
-
-=== PROXY Protocol
-
-PROXY Protocol overcomes this limitation by allowing the original connection
-information to be provided to the backend at the start of the TCP connection.
-After this initial data is encoded the remainder of the conversation then
-proceeds as normal. However now that the connection information is known to the
-backend server it is able to process requests made on the connection as though
-the connection were being made directly by the client and not via the proxy.
-
-PROXY Protocol is specified in this document:
-http://www.haproxy.org/download/1.8/doc/proxy-protocol.txt
-
-
-== Requirements
-
-PROXY Protocol Version 1 is supported by FreeRADIUS v3.0.24 and later versions.
-
-You will require the following set of VMs or containers, each with their own
-IP address:
-
-[cols="1,1,1"]
-|===
-|Hostname|IP address|Purpose
-
-|radseccli
-|172.23.0.2
-|FreeRADIUS configured to provide a RadSec test client
-
-|radsecsvr
-|172.23.0.3
-|FreeRADIUS configured as a RadSec server
-
-|haproxy
-|172.23.0.4
-|HAproxy in Layer 4 mode to the FreeRADIUS RadSec backend
-|===
-
-Optionally you may want to configure a host to run Traefik within a Docker
-container using host mode networking, perhaps configured by Docker Compose,
-however the installation is beyond the scope of this guide:
-
-[cols="1,1,1"]
-|===
-|traefik
-|172.23.0.5
-|Traefik configured as a TCP router with TLS passthrough to the FreeRADIUS RadSec backend
-|===
-
-The hostnames and IP addresses provided above are for examples purposes and are
-used throughout the remainder of this guide. This guide provides commands and
-output for CentOS. Other distributions will have minor differences, including
-the location of the FreeRADIUS configuration (the "raddb").
-
-[NOTE]
-====
-You can choose to use your own hostname, IP addresses and OS distribution. You
-could also use official Docker images provided by the respecitive projects,
-however these prescribe methods for configuring and managing the services
-that are not typical for a normal package installation which would provide a
-distraction if used for by guide.
-====
-
-
-== Sections in this guide
-
-This guide is organised into four parts that should be read in order:
-
-1. xref:protocols/proxy/enable_radsec.adoc[Enabling RadSec]
-2. xref:protocols/proxy/radsec_client.adoc[Configuring a test RadSec client]
-3. xref:protocols/proxy/radsec_with_haproxy.adoc[Proxying RadSec with HAproxy]
-4. xref:protocols/proxy/radsec_with_traefik.adoc[Proxying RadSec with Traefik]
-5. xref:protocols/proxy/enable_proxy_protocol.adoc[Enabling PROXY Protocol for RadSec]
diff --git a/doc/antora/modules/howto/pages/protocols/proxy/radsec_client.adoc b/doc/antora/modules/howto/pages/protocols/proxy/radsec_client.adoc
deleted file mode 100644
index d92345e9e8..0000000000
--- a/doc/antora/modules/howto/pages/protocols/proxy/radsec_client.adoc
+++ /dev/null
@@ -1,181 +0,0 @@
-== Configuring FreeRADIUS as a RadSec test client
-
-Unfortunately, the `radclient` program does not support RadSec. We
-must therefore configure an instance of FreeRADIUS as a "transport
-converter" which proxies UDP-based RADIUS requests to a RadSec
-destination of our choice.
-
-The following steps should be performed on a client system, which we
-will call `radseccli`. This system should be a new system, with a
-different IP address. That is, you shoudl not edit the configuration
-on the `radsecsvr` host. Doing so will break the RadSec configuration.
-
-Install FreeRADIUS using the NetworkRADIUS packages by following the
-instructions provided here:
-
-<https://networkradius.com/packages/>
-
-Before making any configuration changes, you should stop the radiusd
-service:
-
-[source,shell]
-----
- service radiusd stop
-----
-
-Add a new `tls` home server definition, which will point to the RadSec
-server. We do this by creating a file
-`/etc/raddb/sites-enabled/radsec-homeserver` with the following
-contents:
-
-.Example homeserver, pool and realm definitions for the RadSec service
-====
-
- home_server tls {
- ipaddr = 172.23.0.3 # IP address of our RadSec server
- port = 2083
- type = auth+acct
- proto = tcp
- tls {
- private_key_password = whatever
- private_key_file = ${certdir}/client.pem
- certificate_file = ${certdir}/client.pem
- ca_file = ${cadir}/ca.pem
- }
- }
- home_server_pool tls {
- type = fail-over
- home_server = tls
- }
- realm tls {
- auth_pool = tls
- acct_pool = tls
- }
-
-====
-
-[TIP]
-====
-Complete descriptions of each of the above configuration items can be found in the
-`[raddb]/sites-available/tls` example configuration file. For simple tests, however,
-we can omit all of the comments from the file.
-====
-
-To use this `tls` home server, we change the `default` virtual server to proxy
-all authentication and accounting requests to it.
-
-Edit the `/etc/raddb/sites-enabled/default` file so that the beginning of
-the `authorize` and `preacct` sections looks as follows:
-
-.Example default virtual server modification to proxy requests to a RadSec proxy server
-====
-
- authorize {
- update control {
- &Proxy-To-Realm := tls
- }
- handled
- ...
- }
- ...
- preacct {
- update control {
- &Proxy-To-Realm := tls
- }
- handled
- ...
- }
-
-====
-
-These changes make the `tls` virtual server always proxy packets.
-These changes are only for testing, and should never be used in
-production.
-
-We must now copy the example CA certificate as well as the client
-certificate and key files which are on the `radsecsrv` host to this
-test client.
-
-Replace the following files on `radseccli` with the equivalent files from
-`radsecsrv`:
-
-[cols="1,1,1"]
-|===
-|File|Corresponding configuration item|Purpose
-
-|/etc/raddb/certs/ca.pem
-|`ca_file`
-|CA certificate which is used to authenticate the server certificate presented by the RadSec server to the client.
-
-|/etc/raddb/certs/client.pem
-|`certificate_file`
-|Client certificate (signed by the CA certificate) that is presented by the test client to the RadSec server.
-
-|/etc/raddb/certs/client.pem
-|`private_key_file` and `private_key_password`
-|Private key corresponding to the client certificate
-|===
-
-Note that the client certificate and key are typically bundled into a single file.
-
-[CAUTION]
-====
-If you do not correctly replace the CA, client certificate, and key
-material on the test client then the RadSec client and RadSec server
-will fail to mutually authenticate each other as they do not share a
-trusted CA. If you see messages like `unknown CA`, then you know that
-the certificates have not been set up correctly.
-====
-
-Start the FreeRADIUS service in debug mode:
-
-[source,shell]
-----
-radiusd -X
-----
-
-
-=== Testing RadSec connectivity
-
-At this stage you should be able to cause the test client to send RadSec
-requests directly to the RadSec server.
-
-Run the following to send a RADUS (UDP) Access-Request to the local FreeRADIUS
-instance. It should then proxy the request over RadSec connection to
-the remote RadSec server:
-
-[source,shell]
-----
- echo "User-Name = bob" | radclient 127.0.0.1 auth testing123
-----
-
-If the test client is able to successfully establish the RadSec
-connection, and the RadSec server replies with an Access-Accept
-response, then the output will be as follows:
-
-.Expected output from radclient
-===============================
-
- Sent Access-Request Id 252 from 0.0.0.0:50118 to 127.0.0.1:1812 length 27
- Received Access-Accept Id 252 from 127.0.0.1:1812 to 127.0.0.1:50118 length 39
-
-===============================
-
-Lack of response or an Access-Reject response indicates that the RadSec
-connection is not being established successfully.
-
-There may be serveral reasons for broken connectivity including:
-
- * The client not accepting the certificate presented by the server.
- * The server not accepting the certificate presented by the client.
-
-Look at the debug output generated by both the test client and the RadSec
-server. In many cases it will tell you exactly what the problem is.
-
-Do not proceed with any further steps until direct connections between the
-RadSec client and Radsec Server are working properly.
-
-Once things are working we are ready to
-xref:protocols/proxy/radsec_with_haproxy.adoc[configure HAproxy to proxy RadSec
-connections] or to xref:protocols/proxy/radsec_with_traefik.adoc[configure
-Traefik to proxy RadSec connections].
diff --git a/doc/antora/modules/howto/pages/protocols/proxy/radsec_with_haproxy.adoc b/doc/antora/modules/howto/pages/protocols/proxy/radsec_with_haproxy.adoc
deleted file mode 100644
index e58abfe53b..0000000000
--- a/doc/antora/modules/howto/pages/protocols/proxy/radsec_with_haproxy.adoc
+++ /dev/null
@@ -1,134 +0,0 @@
-== Proxying RadSec with HAproxy
-
-This section shows how to configure HAproxy to proxy RadSec connections.
-
-The following steps should be performed on the `haproxy` host, unless otherwise
-stated.
-
-Install the HAproxy package supplied with the OS distribution:
-
-[source,shell]
-----
- yum install haproxy
-----
-
-Stop the haproxy service:
-
-[source,shell]
-----
- service haproxy stop
-----
-
-Modify the haproxy configuration (typically `/etc/haproxy/haproxy.conf`) so
-that it includes new frontend and backend configuration for the radsec service:
-
-.Example minimal HAproxy configuration
-======================================
-
- global
- maxconn 100
- defaults
- mode tcp
- timeout connect 10s
- timeout client 30s
- timeout server 30s
- frontend radsec_fe
- bind *:2083
- default_backend radsec_be
- backend radsec_be
- balance roundrobin
- server radsecsvr 172.23.0.3:2083
-
-======================================
-
-Note the `mode tcp` directive which tells HAproxy to act as a Layer 4
-proxy, so that it doesn't attempt to perform SSL termination or
-decode the RADIUS protocol.
-
-[NOTE]
-====
-The above example is a minimal configuration. In practise you will want to
-retain many of the HAproxy configuration items already present in the
-configuration (e.g. `log`, `chroot`, `user`, `group`), but these vary across
-distributions. Other HTTP-related options that may already exist in the
-configuration will conflict with `mode tcp` (Layer 4 proxying) and should be
-removed if HAproxy complains about them.
-
-However, you should first get things working with the minimal
-configuration which is known to work, and then make customisations.
-If you start off with a complex configuration, then there may be a
-large number of things which are broken, and debugging them all will
-be difficult. Start simple, and then add complexity!
-====
-
-Restart the haproxy service in foreground mode for debugging purposes:
-
-[source,shell]
-----
-haproxy -f /etc/haproxy/haproxy.cfg -db
-----
-
-
-=== Testing RadSec connectivity via HAproxy
-
-Now edit the test RadSec client, so that instead of making connections directly
-to the RadSec server it makes connections to the HAproxy server.
-
-On `radseccli` edit the `/etc/raddb/sites-enabled/tls` file, and set
-the IP address to the address of the `haproxy` host.
-
-.Example updated test client homeserver configuration
-=====================================================
-
- home_server tls {
- ipaddr = 172.23.0.4 # Updated from radsecsvr to haproxy
- ...
- }
-
-=====================================================
-
-Restart the debug mode session:
-
-[source,shell]
-----
-radiusd -X
-----
-
-Perform a test authentication:
-
-[source,shell]
-----
- echo "User-Name = bob" | radclient 127.0.0.1 auth testing123
-----
-
-If the test client is able to successfully establish the RadSec
-connection via HAproxy, and the RadSec server replies with an
-Access-Accept response, then the output will be as follows:
-
-.Expected output from radclient
-===============================
-
- Sent Access-Request Id 252 from 0.0.0.0:50118 to 127.0.0.1:1812 length 27
- Received Access-Accept Id 252 from 127.0.0.1:1812 to 127.0.0.1:50118 length 39
-
-===============================
-
-HAproxy should also log a message that indicates that the connection was
-proxied, such as the following:
-
-.Expected output from HAproxy
-=============================
-
- <150>...: Connect from 172.23.0.2:50087 to 172.23.0.4:2083 (radius_fr/TCP)
-
-=============================
-
-Any other output from radclient or HAproxy indicates that there is a
-problem with the HAproxy configuration, or that FreeRADIUS is not
-accepting connection from the `haproxy` host, which must be solved
-before continuing.
-
-Once proxied connections are working we are ready to
-xref:protocols/proxy/enable_proxy_protocol.adoc[enable the PROXY
-Protocol] on both HAproxy and the RadSec server.
-
diff --git a/doc/antora/modules/howto/pages/protocols/proxy/radsec_with_traefik.adoc b/doc/antora/modules/howto/pages/protocols/proxy/radsec_with_traefik.adoc
deleted file mode 100644
index 11030e92fd..0000000000
--- a/doc/antora/modules/howto/pages/protocols/proxy/radsec_with_traefik.adoc
+++ /dev/null
@@ -1,128 +0,0 @@
-== Proxying RadSec with Traefik
-
-This section shows how to configure Traefik to proxy RadSec connections. You
-should skip this section if you are not using Traefik as your proxy.
-
-Installing Traefik is beyond the scope of this guide. It is typically installed
-as a service mesh router within a Docker or Kubernetes environment using
-offical Docker images.
-
-Traefik configuration has two components of interest:
-
- * Static configuration: Defines "entrypoints" on which Traefik listens for connections.
- * Dynamic configuration: Defines backend service components and the routing policy.
-
-Traefik supports a number of providers of dynamic configuration data for the
-router and service definitions. For demonstration purposes the files provider
-is used here, however you can switch to another provide once you have things
-working using this method.
-
-The static configuration can be provided by starting Traefik with the following
-arguments:
-
-.Example Traefik static configuration
-=====================================
-
- traefik \
- --log.level=DEBUG \
- --providers.file.filename=/etc/traefik/dynamic_config.yml
- --providers.file.watch=true
- --entryPoints.radsec.address=:2083
-
-=====================================
-
-Note that a `radsec` entrypoint is defined to listen on port 2083 and that a
-static `file` provider is used to defined the dynamic services.
-
-The backend for RadSec should be defined in this file as follows:
-
-.Example Traefik dynamic configuration
-======================================
-
- tcp:
- routers:
- radsec-router:
- entryPoints:
- - radsec
- rule: "HostSNI(`*`)"
- service: "radsec-service"
- tls:
- passthrough: true
- services:
- radsec-service:
- loadBalancer:
- servers:
- - address: "172.23.0.3:2083"
-
-======================================
-
-Note the `passthrough: true` directive under `tls:` which tells Treafik not to
-attempt TLS termination which it would otherwise perform for all incoming TLS
-connections. We require that the connection is passed through from the RadSec
-client to the RadSec server without being reterminated since the end client's
-certificate is authenticated by the RadSec server and many be used for
-policy decisions.
-
-
-=== Testing RadSec connectivity via Traefik
-
-Now amend the test RadSec client so that instead of making connections directly
-to the RadSec server it makes them via Traefik.
-
-On `radseccli` amend `/etc/raddb/sites-enabled/tls` and set the IP address to
-that of the `traefik` host.
-
-.Example updated test client homeserver configuration
-=====================================================
-
- home_server tls {
- ipaddr = 172.23.0.5 # Updated from radsecsvr to traefik
- ...
- }
-
-=====================================================
-
-Restart the debug mode session:
-
-[source,shell]
-----
-radiusd -X
-----
-
-Perform a test authentication:
-
-[source,shell]
-----
- echo "User-Name = bob" | radclient 127.0.0.1 auth testing123
-----
-
-If the test client is able to successfully establish the RadSec connection via
-Traefik and the RadSec server replies with an Access-Accept response then the
-output will be as follows:
-
-.Example output from radclient
-==============================
-
- Sent Access-Request Id 252 from 0.0.0.0:50118 to 127.0.0.1:1812 length 27
- Received Access-Accept Id 252 from 127.0.0.1:1812 to 127.0.0.1:50118 length 39
-
-==============================
-
-Traefik should also log a message that indicates that the connection was
-proxied, such as the following:
-
-.Example output from Traefik
-============================
-
- time="..." level=debug msg="Handling connection from 172.23.0.2:57367"
-
-============================
-
-Any other output from radclient or Traefik indicates that there is a problem
-with the Traefik configuration or that FreeRADIUS is not accepting connection
-from the `traefik` host, which must be solved before continuing.
-
-Once proxied connections are working we are ready to
-xref:protocols/proxy/enable_proxy_protocol.adoc[enable the PROXY Protocol] on
-both Traefik and the RadSec server.
-
diff --git a/doc/antora/modules/howto/pages/simultaneous_use.adoc b/doc/antora/modules/howto/pages/simultaneous_use.adoc
deleted file mode 100644
index b4a97abb91..0000000000
--- a/doc/antora/modules/howto/pages/simultaneous_use.adoc
+++ /dev/null
@@ -1,78 +0,0 @@
-= Simultaneous-Use checking
-
-There are a whole lot of pieces which have to work together for
-`Simultaneous-Use` to work. In this guide, we assume that user
-sessions are stored in SQL.
-
-For `Simultaneous-Use` to work. the server needs to know who is
-online, which means that accounting must be configured and working.
-Start off by checking the basics, independent of `Simultaneous-Use`.
-
-As always, start off with reading the debug output, and use that
-information to answer a few questions.
-
-== Did the user get Access-Accept?
-
-*No* - Fix that. Make sure that the user can be authenticated!
-
-*Yes* - FreeRADIUS told the NAS to allow the user online. This usually
- works, but perhaps the NAS disagreed, and still dropped the user. It happens.
-
-The only way you know that a user is actually online is to check the
-accounting data. So we will do that next.
-
-== Did the server then get an Accounting-Request for that user?
-
-*No* - The NAS isn't sending accounting packets, Simultaneous-Use will never work.
-
-Go fix the NAS so that it sends accounting packets.
-
-*Yes* - The NAS is telling FreeRADIUS that it allowed the user online,
- and the user has an active session. We now have to see where that data is stored.
-
-== Did the accounting data go into the radacct table?
-
-As always, Read the debug output.
-
-*No* - There is nothing in the debug output about radacct? Configure the server to write accounting data to SQL
-
-ou can use `radclient` to send fake accounting packets for testing.
-Use a real accounting packet as a template for input to `radclient`,
-but change the `User-Name` so that the tests don't affect real users.
-
-
-*Yes* - You see successful `INSERT` or `UPDATE` lines in `radacct`. That's good!
-
-== One last check
-
-Double-check the radacct database using an SQL client. Just to be sure that the data is really there.
-
-== It is now set up correctly to track user sessions
-
-If all that works, then the server is set up correctly to authenticate
-users, and to store their data in SQL. This is the foundation for
-`Simultaneous-Use`.
-
-== Set Simultaneous-Use
-
-Then, configure the server to set `Simultaneous-Use=1`. That tells the server to enforce `Simultaneous-Use`. That configuration can go into the `files` module, `sql`, or whereever else you want.
-
-You will also need to configure the `default` virtual server to check session data in SQL. Look for `Simultaneous-Use` in `sites-available/default`. Uncomment the line containing `sql`
-
-== Double check that a user can still log in!
-
-Go through all of the above steps _again_, checking that the user can
-log in, and that the server is receiving accounting packets.
-
-This time, also look for the debug output to contain:
-
-```
-# Executing section session from file ...
-session {
-```
-
-That shows it is checking the `session` database. If all goes well, the next few lines after that should show that it is checking `sql`.
-
-If the above text doesn't appear, then the server isn't getting told to set `Simultaneous-Use = 1`. You will have to fix that before going to the next step.
-
-If the user has not logged in yet, you will see an `Access-Accept`. Otherwise, if the user already has an active session, the server should say that the user is being rejected due to multiple logins.
diff --git a/doc/antora/modules/installation/nav.adoc b/doc/antora/modules/installation/nav.adoc
deleted file mode 100644
index 26ce32e54e..0000000000
--- a/doc/antora/modules/installation/nav.adoc
+++ /dev/null
@@ -1,5 +0,0 @@
-* xref:index.adoc[Installing and upgrading]
-** xref:packages.adoc[Install from packages]
-** xref:dependencies.adoc[Dependencies]
-** xref:source.adoc[Build from source]
-** xref:upgrade.adoc[Upgrading to v3]
diff --git a/doc/antora/modules/installation/pages/dependencies.adoc b/doc/antora/modules/installation/pages/dependencies.adoc
deleted file mode 100644
index 3fb366796a..0000000000
--- a/doc/antora/modules/installation/pages/dependencies.adoc
+++ /dev/null
@@ -1,35 +0,0 @@
-= FreeRADIUS Dependencies
-
-Some external dependencies must be installed before building or
-running FreeRADIUS. For version 3, the core depends on one
-mandatory library: `libtalloc` for memory management.
-
-Many of the modules also have optional dependencies. For example,
-the LDAP module requires LDAP client libraries to be installed
-and database modules need their respective database client
-libraries.
-
-If building from source code, the configure stage will check for
-the optional dependencies. Any missing libraries will cause that
-particular module to be skipped.
-
-== Libraries
-
-=== libtalloc
-
-Talloc is a memory allocation library available at
-https://talloc.samba.org/talloc/doc/html/index.html
-
-*OSX*
-
-`# brew install talloc`
-
-*Debian, Ubuntu and `dpkg`-based systems*
-
-`# apt-get install libtalloc-dev`
-
-*RedHat, CentOS, Rocky Linux or equivalent*
-
-```
-# yum install libtalloc-devel
-```
diff --git a/doc/antora/modules/installation/pages/index.adoc b/doc/antora/modules/installation/pages/index.adoc
deleted file mode 100644
index b810078083..0000000000
--- a/doc/antora/modules/installation/pages/index.adoc
+++ /dev/null
@@ -1,15 +0,0 @@
-== Installation
-
-FreeRADIUS is available from multiple sources:
-
-* Official xref:packages.adoc[Network RADIUS packages]
-* xref:source.adoc[Source code]
-* Many Operating System distributions
-
-We highly recommend using the official packages from Network
-RADIUS, where available.
-
-The documents in this section cover details of the above
-installation methods, as well as instructions on building
-packages locally.
-
diff --git a/doc/antora/modules/installation/pages/packages.adoc b/doc/antora/modules/installation/pages/packages.adoc
deleted file mode 100644
index ffc52cd8f3..0000000000
--- a/doc/antora/modules/installation/pages/packages.adoc
+++ /dev/null
@@ -1,22 +0,0 @@
-== Install from packages
-
-Network RADIUS provide pre-built binary packages of FreeRADIUS for
-common Linux distributions. This is the recommended installation
-method when packages are available for your system.
-
-The official http://packages.networkradius.com[Network RADIUS
-packages] page contains recent FreeRADIUS packages and
-installation instructions.
-
-=== Distribution-supplied packages
-
-While many Operating System distributions ship FreeRADIUS
-packages, the versions they include are often years out of date.
-As well as missing out on the latest bug fixes and features, this
-also means that it is very hard to know if an issue encountered is
-still a problem or if it is fixed in the latest release.
-
-Therefore, whilst the distribution-supplied packages can often be
-the most convenient to install, we do not usually recommend using
-them.
-
diff --git a/doc/antora/modules/installation/pages/source.adoc b/doc/antora/modules/installation/pages/source.adoc
deleted file mode 100644
index cf40a792f4..0000000000
--- a/doc/antora/modules/installation/pages/source.adoc
+++ /dev/null
@@ -1,199 +0,0 @@
-== Building from Source
-
-We recommend xref:packages.adoc[installing from packages] if
-possible. Full instructions on building and installing from source
-code follow.
-
-The mandatory xref:installation:dependencies.adoc[dependencies]
-must be installed before FreeRADIUS can be built. These dependencies
-are `libtalloc` and `libkqueue`, which FreeRADIUS uses for memory
-management, and platform-independent event handling.
-
-Per-module dependencies that enable support for external services
-such as LDAP, SQL, etc, are optional. They must be installed for
-any modules that are to be used. The FreeRADIUS `./configure` step
-will automatically detect if each module has its dependencies met
-and automatically enable support for them. If the features you
-require are not enabled you should inspect the configure script
-output to figure out which additional development libraries need
-to be installed.
-
-The FreeRADIUS source may be obtained from a number of locations:
-
-* Download the latest version of the FreeRADIUS source from
- https://www.freeradius.org/releases/[the FreeRADIUS web site]; or
-* download directly from the
- ftp://ftp.freeradius.org/pub/freeradius/[FreeRADIUS FTP site]; or
-* download from
- https://github.com/FreeRADIUS/freeradius-server/[GitHub].
-
-The file wil be name something like: `freeradius-server-3.0.22.tar.gz`.
-Later versions will be `3.0.23`, or `4.0.0`, etc. PGP signatures are
-also provided for official releases from the FTP site; these are
-named e.g. `freeradius-server-3.0.22.tar.gz.sig`.
-
-Un-tar the file, and change to the FreeRADIUS directory (where
-`VERSION` below is the version of the server that you have
-downloaded).
-
-[source,shell]
-----
-tar -zxf freeradius-server-VERSION.tar.gz
-cd freeradius-server-VERSION
-----
-
-Take the following steps to build and install the server from source:
-
-[source,shell]
-----
-./configure
-make
-sudo make install
-----
-
-=== Custom build
-
-FreeRADIUS has GNU autoconf support. This means you have to run
-`./configure`, and then run `make`. To see which configuration
-options are supported, run `./configure --help`, and read its output.
-
-The `make install` stage will install the binaries, the "man" pages,
-and _may_ install the configuration files. If you have not installed a
-RADIUS server before, then the configuration files for FreeRADIUS will
-be installed.
-
-If you already have a RADIUS server installed, then *FreeRADIUS
-WILL NOT over-write your current configuration.*
-
-The `make install` process will warn you about the files it could not
-install.
-
-If you see a warning message about files that could not be
-installed, then you *must* ensure that the new server is using the
-new configuration files and not the old configuration files, as
-this may cause undesired behavior and failure to operate correctly.
-
-The initial output from running in debugging mode (`radiusd -X`)
-will tell you which configuration files are being used. See
-xref:installation:upgrade.adoc[Upgrading] for information about
-upgrading from older versions. There _may_ be changes in the
-dictionary files which are required for a new version of the
-software. These files will not be installed over your current
-configuration, so you *must* verify and install any problem files by
-hand, for example using `diff(1)` to check for changes.
-
-When installing from source, it is _extremely_ helpful to read the
-output of `./configure`, `make`, and `make install`. If a
-particular module you expected to be installed was not installed,
-then the output will tell you why that module was not installed.
-The most likely reason is that required libraries (including their
-development header files) are not available.
-
-Please do _not_ post questions to the FreeRADIUS users list
-without first carefully reading the output of this process as it
-often contains the information needed to resolve a problem.
-
-== Upgrading To A New Minor Release
-
-The installation process will not over-write your existing configuration
-files. It will, however, warn you about the files it did not install.
-These will require manual integration with the existing files.
-
-It is not possible to re-use configurations between different major
-versions of the server.
-
-For details on what has changed between the version, see the
-xref:installation:upgrade.adoc[upgrade] guide.
-
-We _strongly_ recommend that new major versions be installed in a
-different location than any existing installations. Any local policies
-can then be migrated gradually to the configuration format of the new
-major version. The number of differences in the new configuration mean
-that is is both simpler and safer to migrate your configurations rather
-than to try and just get the old configuration to work.
-
-== Running the server
-
-If the server builds and installs, but doesnt run correctly, then
-you should first use debugging mode (`radiusd -X`) to figure out
-the problem.
-
-This is your best hope for understanding the problem. Read _all_
-of the messages which are printed to the screen, the answer to
-your problem will often be in a warning or error message.
-
-We really cannot emphasize that last sentence enough. Configuring
-a RADIUS server for complex local authentication isnt a trivial
-task. Your _best_ and _only_ method for debugging it is to read
-the debug messages, where the server will tell you exactly what
-its doing, and why. You should then compare its behaviour to what
-you intended, and edit the configuration files as appropriate.
-
-If you dont use debugging mode, and ask questions on the mailing
-list, then the responses will all tell you to use debugging mode.
-The server prints out a lot of information in this mode, including
-suggestions for fixes to common problems. Look especially for
-`WARNING` and `ERROR` messages in the output, and read the related
-messages.
-
-Since the main developers of FreeRADIUS use debugging mode to
-track down their configuration problems with the server, its a
-good idea for you to use it, too. If you dont, there is little
-hope for you to solve any configuration problem related to the
-server.
-
-To start the server in debugging mode, do:
-
-[source,shell]
-----
-radiusd -X
-----
-
-You should see a lot of text printed on the screen as it starts up. If
-you dont, or if you see error messages, please read the FAQ:
-
-https://wiki.freeradius.org/guide/FAQ
-
-If the server says `Ready to process requests.`, then it is running
-properly. From another shell (or another window), type
-
-[source,shell]
-----
-radtest test test localhost 0 testing123
-----
-
-You should see the server print out more messages as it receives the
-request, and responds to it. The `radtest` program should receive the
-response within a few seconds. It doesnt matter if the authentication
-request is accepted or rejected, what matters is that the server
-received the request, and responded to it.
-
-You can now edit the configuration files for your local system. You will
-usually want to start with `sites-enabled/default` for main
-configurations. To set which NASes (clients) can communicate with this
-server, edit `raddb/clients.conf`. Please read the configuration files
-carefully, as many configuration options are only documented in comments
-in the file.
-
-Note that is is _highly_ recommended that you use some sort of version
-control system to manage your configuration, such as git or Subversion.
-You should then make small changes to the configuration, checking in and
-testing as you go. When a config change causes the server to stop
-working, you will be able to easily step back and find out what update
-broke the configuration.
-
-It is also considered a best practice to maintain a staging or
-development environment. This allows you to test and integrate your
-changes without impacting your active production environment. You should
-make the appropirate investment in order to properly support a critical
-resource such as your authentication servers.
-
-Configuring and running the server MAY be complicated. Many modules have
-`man` pages. See `man rlm_pap`, or `man rlm_*` for information.
-Please read the documentation in the doc/ directory. The comments in the
-configuration files also contain a lot of documentation.
-
-If you have any additional issues, the FAQ is also a good place to
-start.
-
-https://wiki.freeradius.org/guide/FAQ
diff --git a/doc/antora/modules/installation/pages/upgrade.adoc b/doc/antora/modules/installation/pages/upgrade.adoc
deleted file mode 100644
index 67874c859a..0000000000
--- a/doc/antora/modules/installation/pages/upgrade.adoc
+++ /dev/null
@@ -1,737 +0,0 @@
-= Upgrading from v2 to v3
-
-The configuration for 3.0 is *largely* compatible with the 2.x.x
-configuration. However, it is NOT possible to simply use the 2.x.x
-configuration as-is. Instead, you should re-create it.
-
-== Security
-
-A number of configuration items have moved into the "security" subsection of
-radiusd.conf. If you use these, you should move them. Otherwise, they can
-be ignored.
-
-The list of moved options is:
-
-* chroot
-* user
-* group
-* allow_core_dumps
-* reject_delay
-* status_server
-
-These entries should be moved from "radiusd.conf" to the "security"
-subsection of that file.
-
-== Naming
-
-Many names used by configuration items were inconsistent in earlier
-versions of the server. These names have been unified in version 3.0.
-
-If a file is being referenced or created the config item `filename`
-is used.
-
-If a file is being created, the initial permissions are set by the
-`permissions` config item.
-
-If a directory hierarchy needs to be created, the permissions are set
-by `dir_permissions`.
-
-If an external host is referenced in the context of a module the
-`server` config item is used.
-
-Unless the config item is a well recognised portmanteau
-(as `filename` is for example), it must be written as multiple
-distinct words separated by underscores `_`.
-
-The configuration items `file`, `script_file`, `module`,
-`detail`, `detailfile`, `attrsfile`, `perm`, `dirperm`,
-`detailperm`, and `hostname` are deprecated. As well as any false
-portmanteaus, and configuration items that used hyphens as word
-delimiters. e.g. `foo-bar` has been changed to `foo_bar`. Please
-update your module configuration to use the new syntax.
-
-In most cases the server will tell you the replacement config item to
-use. As always, run the server in debugging mode to see these
-messages.
-
-== Modules Directory
-
-As of version 3.0, the `modules/` directory no longer exists.
-
-Instead, all "example" modules have been put into the
-`mods-available/` directory. Modules which can be loaded by the
-server are placed in the `mods-enabled/` directory. All of the
-modules in that directory will be loaded. This means that the
-`instantiate` section of radiusd.conf is less important. The only
-reason to list a module in the `instantiate` section is to force
-ordering when the modules are loaded.
-
-Modules can be enabled by creating a soft link. For module `foo`, do:
-
-[source,shell]
-----
-cd raddb/mods-enabled
-ln -s ../mods-available/foo
-----
-
-To create "local" versions of the modules, we suggest copying the file
-instead. This leaves the original file (with documentation) in the
-`mods-available/` directory. Local changes should go into the
-`mods-enabled/` directory.
-
-Module-specific configuration files are now in the `mods-config/`
-directory. This change allows for better organization, and means that
-there are fewer files in the main `raddb` directory. See
-`mods-config/README.rst` for more details.
-
-== Changed Modules
-
-The following modules have been changed in this version.
-
-=== rlm_sql
-
-The SQL configuration has been moved from `sql.conf` to
-`mods-available/sql`. The `sqlippool.conf` file has also been
-moved to `mods-available/sqlippool`.
-
-The SQL module configuration has been changed. The old connection
-pool options are no longer accepted:
-
-----
-num_sql_socks
-connect_failure_retry_delay
-lifetime
-max_queries
-----
-
-Instead, a connection pool configuration is used. This configuration
-contains all of the functionality of the previous configuration, but
-in a more generic form. It also is used in multiple modules, meaning
-that there are fewer different configuration items. The mapping
-between the configuration items is:
-
-----
-num_sql_socks -> pool { max }
-connect_failure_retry_delay -> pool { retry_delay }
-lifetime -> pool { lifetime }
-max_queries -> pool { uses }
-----
-
-The pool configuration adds a number of new configuration options,
-which allow the administrator to better control how FreeRADIUS uses
-SQL connection pools.
-
-The following parameters have been changed:
-
-----
-trace -> removed
-tracefile -> logfile
-----
-
-The logfile is intended to log SQL queries performed. If you need to
-debug the server, use debugging mode. If `logfile` is set, then
-*all* SQL queries will go to `logfile`.
-
-You can now use a NULL SQL database:
-
-.Example
-----
-driver = rlm_sql_null
-----
-
-This is an empty driver which will always return "success". It is
-intended to be used to replace the `sql_log` module, and to work in
-conjunction with the `radsqlrelay` program. Simply take your normal
-configuration for raddb/mods-enabled/sql, and set:
-
-.Example
-----
-driver = rlm_sql_null
-...
-logfile = ${radacctdir}/sql.log
-----
-
-All of the SQL queries will be logged to that file. The connection
-pool does not need to be configured for the `null` SQL driver. It
-can be left as-is, or deleted from the SQL configuration file.
-
-
-=== rlm_sql_sybase
-
-The `rlm_sql_sybase` module has been renamed to `rlm_sql_freetds`
-and the old `rlm_sql_freetds` module has been removed.
-
-`rlm_sql_sybase` used the newer ct-lib API, and `rlm_sql_freetds`
-used an older API and was incomplete.
-
-The new `rlm_sql_freetds` module now also supports database
-selection on connection startup so `use` statements no longer
-have to be included in queries.
-
-
-=== sql/dialup.conf
-
-Queries for post-auth and accounting calls have been re-arranged. The
-SQL module will now expand the 'reference' configuration item in the
-appropriate sub-section, and resolve this to a configuration
-item. This behaviour is similar to rlm_linelog. This dynamic
-expansion allows for a dynamic mapping between accounting types and
-SQL queries. Previously, the mapping was fixed. Any "new" accounting
-type was ignored by the module. Now, support for any accounting type
-can be added by just adding a new target, as below.
-
-Queries from v2.x.x may be manually copied to the new v3.0
-`dialup.conf` file (`raddb/sql/main/<dialect>/queries.conf`).
-When doing this you may also need to update references to the
-accounting tables, as their definitions will now be outside of
-the subsection containing the query.
-
-The mapping from old "fixed" query to new "dynamic" query is as follows:
-
-----
-accounting_onoff_query -> accounting.type.accounting-on.query
-accounting_update_query -> accounting.type.interim-update.query
-accounting_update_query_alt +> accounting.type.interim-update.query
-accounting_start_query -> accounting.type.start.query
-accounting_start_query_alt +> accounting.type.start.query
-accounting_stop_query -> accounting.type.stop.query
-accounting_stop_query_alt +> accounting.type.stop.query
-postauth_query -> post-auth.query
-----
-
-Alternatively a 2.x.x config may be patched to work with the
-3.0 module by adding the following:
-
-.Example
-[source,unlang]
-----
- accounting {
- reference = "%{tolower:type.%{Acct-Status-Type}.query}"
- type {
- accounting-on {
- query = "${....accounting_onoff_query}"
- }
- accounting-off {
- query = "${....accounting_onoff_query}"
- }
- start {
- query = "${....accounting_start_query}"
- query = "${....accounting_start_query_alt}"
- }
- interim-update {
- query = "${....accounting_update_query}"
- query = "${....accounting_update_query_alt}"
- }
- stop {
- query = "${....accounting_stop_query}"
- query = "${....accounting_stop_query_alt}"
- }
- }
- }
- post-auth {
- query = "${..postauth_query}"
- }
-----
-
-In general, it is safer to migrate the configuration rather than
-trying to "patch" it, to make it look like a v2 configuration.
-
-Note that the sub-sections holding the queries are labelled
-`accounting-on`, and not `accounting_on`. The reason is that the
-names of these sections are taken directly from the
-`Accounting-Request` packet, and the `Acct-Status-Type` field.
-The `sql` module looks at the value of that field, and then looks
-for a section of that name, in order to find the query to use.
-
-That process means that the server can be extended to support any new
-value of `Acct-Status-Type`, simply by adding a named sub-section,
-and a query. This behavior is preferable to that of v2, which had
-hard-coded queries for certain `Acct-Status-Type` values, and was
-ignored all other values.
-
-=== rlm_ldap
-
-The LDAP module configuration has been substantially changed. Please
-read `raddb/mods-available/ldap`. It now uses a connection pool,
-just like the SQL module.
-
-Many of the configuration items remain the same, but they have been
-moved into subsections. This change is largely cosmetic, but it makes
-the configuration clearer. Instead of having a large set of random
-configuration items, they are now organized into logical groups.
-
-You will need to read your old LDAP configuration, and migrate it
-manually to the new configuration. Simply copying the old
-configuration WILL NOT WORK.
-
-Users upgrading from 2.x.x who used to call the ldap module in
-`post-auth` should now set `edir_autz = yes`, and remove the `ldap`
-module from the `post-auth` section.
-
-=== rlm_ldap and LDAP-Group
-
-In 2.x.x the registration of the `LDAP-Group` pair comparison was done
-by the last instance of rlm_ldap to be instantiated. In 3.0 this has
-changed so that only the default `ldap {}` instance registers
-`LDAP-Group`.
-
-If `<instance>-LDAP-Group` is already used throughout your configuration
-no changes will be needed.
-
-=== rlm_ldap authentication
-
-In 2.x.x the LDAP module had a `set_auth_type` configuration item,
-which forced `Auth-Type := ldap`. This was removed in 3.x.x as it
-often did not work, and was not consistent with the rest of the
-server. We generally recommend that LDAP should be used as a
-database, and that FreeRADIUS should do authentication.
-
-The only reason to use `Auth-Type := ldap` is when the LDAP server
-will not supply the "known good" password to FreeRADIUS, *and* where
-the Access-Request contains User-Password. This situation happens
-only for Active Directory. If you think you need to force `Auth-Type
-:= ldap` in other situations, you are very likely to be wrong.
-
-The following is an example of what should be inserted into the
-`authorize {}` and `authenticate {}` sections of the relevant
-virtual-servers, to get functionality equivalent to v2.x:
-
-.Example
-[source,unlang]
-----
-authorize {
- ...
- ldap
- if ((ok || updated) && User-Password) {
- update control {
- Auth-Type := ldap
- }
-...
-}
-authenticate {
- ...
- Auth-Type ldap {
- ldap
- }
-...
-}
-----
-
-=== rlm_eap
-
-The EAP configuration has been moved from `eap.conf` to
-`mods-available/eap`. A new `pwd` subsection has been added for
-EAP-PWD.
-
-
-=== rlm_expiration & rlm_logintime
-
-The rlm_expiration and rlm_logintime modules no longer add a `Reply-Message`,
-the same behaviour can be achieved checking the return code of the module and
-adding the `Reply-Message` with unlang:
-
-.Example
-[source,unlang]
-----
-expiration
-if (userlock) {
- update reply {
- Reply-Message := "Your account has expired"
- }
-}
-----
-
-
-=== rlm_unix
-
-The `unix` module does not have an `authenticate` section. So you
-cannot set `Auth-Type := System`. The `unix` module has also been
-deleted from the examples in `sites-available/`. Listing it there
-has been deprecated for many years.
-
-The PAP module can do crypt authentication. It should be used instead
-of Unix authentication.
-
-The Unix module still can pull the passwords from `/etc/passwd`, or
-`/etc/shadow`. This is done by listing it in the `authorize`
-section, as is done in the examples in `sites-available/`. However,
-some systems using NIS or NSS will not supply passwords to the
-`unix` module. For those systems, we recommend putting users and
-passwords into a database, instead of relying on `/etc/passwd`.
-
-
-=== rlm_preprocess
-
-In 2.x.x `huntroups` and `users` files were loaded from default locations
-without being configured explicitly. Since 3.x.x you need to set
-`huntgroups` and `users` configuration item(s) in module section in order
-to get them being processed.
-
-
-== New Modules
-
-=== rlm_date
-
-Instances of rlm_date register an xlat method which can translate
-integer and date values to an arbitrarily formatted date time
-string, or an arbitrarily formated time string to an integer,
-depending on the attribute type passed.
-
-
-=== rlm_rest
-
-The `rest` module is used to translate RADIUS requests into
-RESTfull HTTP requests. Currently supported body types are JSON
-and POST.
-
-
-=== rlm_unpack
-
-The `unpack` module is used to turn data buried inside of binary
-attributes. e.g. if we have `Class = 0x00000001020304` then:
-
-.Example
-[source,unlang]
-----
-Tmp-Integer-0 := "%{unpack:&Class 4 short}"
-----
-
-will unpack octets 4 and 5 as a "short", which has value 0x0304.
-All integers are assumed to be in network byte order.
-
-
-=== rlm_yubikey
-
-The `yubikey` module can be used to forward yubikey OTP token
-values to a Yubico validation server, or decrypt the token
-using a PSK.
-
-
-== Deleted Modules
-
-The following modules have been deleted, and are no longer supported
-in Version 3. If you are using one of these modules, your
-configuration can probably be changed to not need it. Otherwise email
-the freeradius-devel list, and ask about the module.
-
-
-=== rlm_acct_unique
-
-This module has been replaced by the "acct_unique" policy. See
-raddb/policy.d/accounting.
-
-The method for calculating the value of acct_unique has changed.
-However, as this method was configurable, this change should not
-matter. The only issue is in having a v2 and v3 server writing to the
-same database at the same time. They will calculate different values
-for Acct-Unique-Id.
-
-
-=== rlm_acctlog
-
-You should use rlm_linelog instead. That module has a superset of the
-acctlog functionality.
-
-
-=== rlm_attr_rewrite
-
-The attr_rewrite module looked for an attribute, and then re-wrote it,
-or created a new attribute. All of that can be done in "unlang".
-
-A sample configuration in "unlang" is:
-
-.Example
-[source,unlang]
-----
-if (request:Calling-Station-Id) {
- update request {
- Calling-Station-Id := "...."
- }
-}
-----
-
-We suggest updating all uses of attr_rewrite to use unlang instead.
-
-
-=== rlm_checkval
-
-The checkval module compared two attributes. All of that can be done in "unlang":
-
-.Example
-[source,unlang]
-----
-if (&request:Calling-Station-Id == &control:Calling-Station-Id) {
- ok
-}
-----
-
-We suggest updating all uses of checkval to use unlang instead.
-
-
-=== rlm_dbm
-
-No one seems to use it. There is no sample configuration for it.
-There is no speed advantage to using it over the "files" module.
-Modern systems are fast enough that 10K entries can be read from the
-"users" file in about 10ms. If you need more users than that, use a
-real database such as SQL.
-
-
-=== rlm_fastusers
-
-No one seems to use it. It has been deprecated since Version 2.0.0.
-The "files" module was rewritten so that the "fastusers" module was no
-longer necessary.
-
-
-=== rlm_policy
-
-No one seems to use it. Almost all of its functionality is available
-via `unlang`.
-
-
-=== rlm_sim_files
-
-The rlm_sim_files module has been deleted. It was never marked "stable",
-and was never used in a production environment. There are better ways
-to test EAP.
-
-If you want similar functionality, see rlm_passwd. It can read CSV
-files, and create attributes from them.
-
-
-=== rlm_sql_log
-
-This has been replaced with the "null" sql driver. See
-`raddb/mods-available/sql` for an example configuration.
-
-The main SQL module has more functionality than rlm_sql_log, and
-results in less code in the server.
-
-== Other Functionality
-
-The following is a list of new / changed functionality.
-
-=== RadSec
-
-RadSec (or RADIUS over TLS) is now supported. RADIUS over bare TCP
-is also supported, but is recommended only for secure networks.
-
-See `sites-available/tls` for complete details on using TLS. The server
-can both receive incoming TLS connections, and also originate outgoing
-TLS connections.
-
-The TLS configuration is taken from the old EAP-TLS configuration. It
-is largely identical to the old EAP-TLS configuration, so it should be
-simple to use and configure. It re-uses much of the EAP-TLS code,
-so it is well-tested and reliable.
-
-Once RadSec is enabled, normal debugging mode will not work. This is
-because the TLS code requires threading to work properly. Instead of doing:
-
-.Example
-[source,shell]
-----
-radiusd -X
-----
-
-you will need to do:
-
-.Example
-[source,shell]
-----
-radiusd -fxx -l stdout
-----
-
-That's the price to pay for using RadSec. This limitation may be
-lifted in a future version of the server.
-
-
-=== PAP and User-Password
-
-From version 3.0 onwards the server no longer supports authenticating
-against a cleartext password in the 'User-Password' attribute. Any
-occurences of this (for instance, in the users file) should now be changed
-to 'Cleartext-Password' instead.
-
-e.g. change entries like this:
-
-----
-bob User-Password == "hello"
-----
-
-to ones like this:
-
-----
-bob Cleartext-Password := "hello"
-----
-
-If this is not done, authentication will likely fail. The server will
-also print a helpful message in debugging mode.
-
-If it really is impossible to do this, the following unlang inserted above
-the call to the pap module may be used to copy User-Password to the correct
-attribute:
-
-.Example
-[source,unlang]
-----
-if (!control:Cleartext-Password && control:User-Password) {
- update control {
- Cleartext-Password := "%{control:User-Password}"
- }
-}
-----
-
-However, this should only be seen as a temporary, not permanent, fix.
-It is better to fix your databases to use the correct configuration.
-
-
-== Unlang
-
-
-The unlang policy language is compatible with v2, but has a number of
-new features. See `man unlang` for complete documentation.
-
-
-=== Errors
-
-Many more errors are caught when the server is starting up. Syntax
-errors in `unlang` are caught, and a helpful error message is
-printed. The error message points to the exact place where the error
-occurred:
-
-----
- ./raddb/sites-enabled/default[230]: Parse error in condition
- ERROR: if (User-Name ! "bob") {
- ERROR: ^ Invalid operator
-----
-
-`update` sections are more generic. Instead of doing `update
-reply`, you can do the following:
-
-.Example
-[source,unlang]
-----
-update {
- reply:Class := 0x0000
- control:Cleartext-Password := "hello"
-}
-----
-
-This change means that you need fewer `update` sections.
-
-
-=== Comparisons
-
-Attribute comparisons can be done via the `&` operator. When you
-needed to compare two attributes, the old comparison style was:
-
-.Example
-[source,unlang]
-----
-if (User-Name == "%{control:Tmp-String-0}") {
-----
-
-This syntax is inefficient, as the `Tmp-String-0` attribute would be
-printed to an intermediate string, causing unnecessary work. You can
-now instead compare the two attributes directly:
-
-.Example
-[source,unlang]
-----
-if (&User-Name == &control:Tmp-String-0) {
-----
-
-See `man unlang` for more details.
-
-=== Casts
-
-Casts are now permitted. This allows you to force type-specific
-comparisons:
-
-.Example
-[source,unlang]
-----
-if (<ipaddr>"%{sql: SELECT...}" == 127.0.0.1) {
-----
-
-This forces the string returned by the SELECT to be treated as an IP
-address, and compare to `127.0.0.1`. Previously, the comparison
-would have been done as a simple string comparison.
-
-
-=== Networks
-
-IP networks are now supported:
-
- if (127.0.0.1/32 == 127.0.0.1) {
-
-Will be `true`. The various comparison operators can be used to
-check IP network membership::
-
-.Example
-[source,unlang]
-----
-if (127/8 > 127.0.0.1) {
-----
-
-Returns `true`, because `127.0.0.1` is within the `127/8`
-network. However, the following comparison will return `false`::
-
-.Example
-[source,unlang]
-----
-if (127/8 > 192.168.0.1) {
-----
-
-because `192.168.0.1` is outside of the `127/8` network.
-
-
-=== Optimization
-
-As `unlang` is now pre-compiled, many compile-time optimizations are
-done. This means that the debug output may not be exactly the same as
-what is in the configuration files:
-
- if (0 && (User-Name == "bob')) {
-
-The result will always be `false`, as the `if 0` prevents the
-following `&& ...` from being evaluated.
-
-Not only that, but the entire contents of that section will be ignored
-entirely:
-
-.Example
-[source,unlang]
-----
-if (0) {
- this_module_does_not_exist
- and_this_one_does_not_exist_either
-}
-----
-
-In v2, that configuration would result in a parse error, as there is
-no module called `this_module_does_not_exist`. In v3, that text is
-ignored. This ability allows you to have dynamic configurations where
-certain parts are used (or not) depending on compile-time configuration.
-
-Similarly, conditions which always evaluate to `true` will be
-optimized away:
-
-
-.Example
-[source,unlang]
-----
-if (1) {
- files
-}
-----
-
-That configuration will never show the `if (1)` output in debugging mode.
-
-=== Dialup_admin
-
-The dialup_admin directory has been removed. No one stepped forward
-to maintain it, and the code had not been changed in many years.
-
diff --git a/doc/antora/modules/unlang/.gitignore b/doc/antora/modules/unlang/.gitignore
deleted file mode 100644
index c5722d7c54..0000000000
--- a/doc/antora/modules/unlang/.gitignore
+++ /dev/null
@@ -1 +0,0 @@
-!*.adoc
diff --git a/doc/antora/modules/unlang/nav.adoc b/doc/antora/modules/unlang/nav.adoc
deleted file mode 100644
index e2d68b30e0..0000000000
--- a/doc/antora/modules/unlang/nav.adoc
+++ /dev/null
@@ -1,51 +0,0 @@
-* xref:index.adoc[Unlang Policy Language]
-
-** xref:list.adoc[Attribute Lists]
-** xref:attr.adoc[Attribute References]
-** xref:return_codes.adoc[Return Codes]
-
-** xref:keywords.adoc[Keywords]
-*** xref:break.adoc[break]
-*** xref:case.adoc[case]
-*** xref:else.adoc[else]
-*** xref:elsif.adoc[elsif]
-*** xref:foreach.adoc[foreach]
-*** xref:group.adoc[group]
-*** xref:if.adoc[if]
-*** xref:load-balance.adoc[load-balance]
-*** xref:redundant-load-balance.adoc[redundant-load-balance]
-*** xref:redundant.adoc[redundant]
-*** xref:return.adoc[return]
-*** xref:switch.adoc[switch]
-*** xref:update.adoc[update]
-
-** xref:module.adoc[Modules]
-*** xref:module_method.adoc[Module Methods]
-*** xref:module_builtin.adoc[Built-in Modules]
-
-** xref:type/index.adoc[Data Types]
-*** xref:type/index.adoc[List of Data Types]
-*** xref:type/ip.adoc[IP Addresses]
-*** xref:type/numb.adoc[Numbers]
-*** xref:type/string/single.adoc[Single Quoted Strings]
-*** xref:type/string/double.adoc[Double Quoted Strings]
-*** xref:type/string/backticks.adoc[Backtick-quoted string]
-*** xref:type/string/unquoted.adoc[Unquoted Strings]
-
-** xref:condition/index.adoc[Conditional Expressions]
-*** xref:condition/cmp.adoc[Comparisons]
-*** xref:condition/operands.adoc[Operands]
-*** xref:condition/return_codes.adoc[The Return Code Operator]
-*** xref:condition/eq.adoc[The '==' Operator]
-*** xref:condition/and.adoc[The '&&' Operator]
-*** xref:condition/or.adoc[The '||' Operator]
-*** xref:condition/not.adoc[The '!' Operator]
-*** xref:condition/para.adoc[The '( )' Operator]
-*** xref:condition/regex.adoc[Regular Expressions]
-
-** xref:xlat/index.adoc[String Expansion]
-*** xref:xlat/alternation.adoc[Alternation Syntax]
-*** xref:xlat/builtin.adoc[Built-in Expansions]
-*** xref:xlat/character.adoc[Single Letter Expansions]
-*** xref:xlat/attribute.adoc[Attribute References]
-*** xref:xlat/module.adoc[Module References]
diff --git a/doc/antora/modules/unlang/pages/attr.adoc b/doc/antora/modules/unlang/pages/attr.adoc
deleted file mode 100644
index 70afce41af..0000000000
--- a/doc/antora/modules/unlang/pages/attr.adoc
+++ /dev/null
@@ -1,77 +0,0 @@
-= &Attribute References
-
-.Syntax
-[source,unlang]
-----
-[&]Attribute-Name
-----
-
-The `&Attribute-Name` operator returns a reference to the named
-attribute.
-
-When used as an existence check in a condition, the condition
-evaluates to `true` if the attribute exists. Otherwise, the condition
-evaluates to `false`.
-
-When used elsewhere, such as in xref:switch.adoc[switch], it returns
-the value of the named attribute.
-
-.Examples
-[source,unlang]
-----
-&User-Name
-&NAS-IP-Address
-----
-
-== Lists
-
-The attribute reference can also be qualified with a
-xref:list.adoc[list] reference. When no list is given, the server
-looks in the input packet list for the named attribute.
-
-.Examples
-
-[source,unlang]
-----
-&request:User-Name
-&reply:NAS-IP-Address
-----
-
-== Array References
-
-.Syntax
-[source,unlang]
-----
-&Attribute-Name[<integer>]
-----
-
-When an attribute appears multiple times in a list, this syntax allows
-you to address the attributes as if they were array entries. The
-`<integer>` value defines which attribute to address. The `[0]` value
-refers to the first attributes, `[1]` refers to the second attribute,
-etc.
-
-.Examples
-[source,unlang]
-----
-&EAP-Message[1]
-&reply:NAS-IP-Address[2]
-----
-
-== Removing ambuguity from the configuration files
-
-The server does not use the `&` character to distinguish attribute names
-from other strings.
-
-Without the `&`, it is more difficult to parse the configuration file
-clearly. You could interpret a string as `hello-there`
-either as a literal string "hello-there", or as a reference to an
-attribute named `hello-there`.
-
-Adding the leading `&` character means that attribute references are
-now easily distinguishable from literal strings. The use of the leading
-`&` character is highly recommended.
-
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/break.adoc b/doc/antora/modules/unlang/pages/break.adoc
deleted file mode 100644
index 01783ea8f2..0000000000
--- a/doc/antora/modules/unlang/pages/break.adoc
+++ /dev/null
@@ -1,28 +0,0 @@
-= The break statement
-
-.Syntax
-[source,unlang]
-----
-break
-----
-
-The `break` statement is used to exit an enclosing
-xref:foreach.adoc[foreach] loop. The `break` statement only be used
-inside of a xref:foreach.adoc[foreach] loop.
-
-.Example
-[source,unlang]
-----
-foreach &Class {
- if (&Foreach-Variable-0 == 0xabcdef) {
- break
- }
-
- update reply {
- Reply-Message += "Contains %{Foreach-Variable-0}"
- }
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/case.adoc b/doc/antora/modules/unlang/pages/case.adoc
deleted file mode 100644
index 2d5749dd8e..0000000000
--- a/doc/antora/modules/unlang/pages/case.adoc
+++ /dev/null
@@ -1,44 +0,0 @@
-= The case Statement
-
-.Syntax
-[source,unlang]
-----
-case [ <match> ] {
- [ statements ]
-}
-----
-
-The `case` statement is used to match data inside of a
-xref:switch.adoc[switch] statement. The `case` statement cannot be used
-outside of a xref:switch.adoc[switch] statement.
-
-
-The `<match>` text can be an attribute reference such as `&User-Name`,
-or it can be a xref:type/index.adoc[string]. If the match
-text is a dynamically expanded string, then the match is performed on
-the output of the string expansion.
-
-If no `<match>` text is given, it means that the `case` statement is
-the "default" and will match all which is not matched by another
-`case` statement inside of the same xref:switch.adoc[switch].
-
-.Example
-[source,unlang]
-----
-switch &User-Name {
- case "bob" {
- reject
- }
-
- case &Filter-Id {
- reject
- }
-
- case {
- ok
- }
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/and.adoc b/doc/antora/modules/unlang/pages/condition/and.adoc
deleted file mode 100644
index 50b3deb2e0..0000000000
--- a/doc/antora/modules/unlang/pages/condition/and.adoc
+++ /dev/null
@@ -1,21 +0,0 @@
-= The && Operator
-
-.Syntax
-[source,unlang]
-----
-(condition-1 && condition-2)
-----
-
-The `&&` operator performs a short-circuit "and" evaluation of the
-two conditions. This operator evaluates _condition-1_ and returns
-`false` if _condition-1_ returns `false`. Only if _condition-1_
-returns `true` is _condition-2_ evaluated and its result returned.
-
-.Examples
-[source,unlang]
-----
-if (&User-Name && &EAP-Message) { ...
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/cmp.adoc b/doc/antora/modules/unlang/pages/condition/cmp.adoc
deleted file mode 100644
index 4138b869ae..0000000000
--- a/doc/antora/modules/unlang/pages/condition/cmp.adoc
+++ /dev/null
@@ -1,104 +0,0 @@
-= Comparisons
-
-.Syntax
-[source,unlang]
-----
-lhs OP rhs
-----
-
-The most common use-case for conditions is to perform comparisons.
-The `lhs` and `rhs` of a conditional comparison can be
-xref:attr.adoc[&Attribute-Name] or xref:type/index.adoc[data]. The
-the `OP` is an operator, commonly `==` or `\<=`. It is used to
-control how the two other portions of the condition are compared.
-
-== The Comparison Operators
-
-The comparison operators are given below.
-
-[options="header"]
-|=====
-| Operator | Description
-| < | less than
-| \<= | less than or equals
-| == | equals
-| != | not equals
-| >= | greater than or equals
-| > | greater than
-| xref:condition/regex.adoc[=~] | regular expression matches
-| xref:condition/regex.adoc[!~] | regular expression does not match
-|=====
-
-The comparison operators perform _type-specific_ comparisons. The
-only exceptions are the xref:condition/regex.adoc[regular expression] operators,
-which interpret the `lhs` as a printable string, and the `rhs` as a
-regular expression.
-
-== IP Address Comparisons
-
-The type-specific comparisons operate as expected for most data types.
-The only exception is data types that are IP addresses or IP address
-prefixes. For those data types, the comparisons are done via the
-following rules:
-
-* Any unqualified IP address is assumed to have a /32 prefix (IPv4)
- or a /128 prefix (IPv6).
-
-* If the prefixes of the left and right sides are equal, then the comparisons
- are performed on the IP address portion.
-
-* If the prefixes of the left and right sides are not equal, then the
- comparisons are performed as _set membership checks_.
-
-The syntax allows conditions such as `192.0.2.1 < 192.0.2/24`. This
-condition will return `true`, as the IP address `192.0.2.1' is within
-the network `192.0.2/24`.
-
-== Casting
-
-In some situations, it is useful to force the left side to be
-interpreted as a particular data type.
-
-[NOTE]
-The data types used by the cast *must* be a type taken from the RADIUS
-dictionaries, e.g., `ipaddr`, `integer`, etc. These types are not the
-same as the xref:type/index.adoc[data types] used in the
-configuration files.
-
-.Syntax
-[source,unlang]
-----
-<cast>lhs OP rhs
-----
-
-The `cast` text can be any one of the standard RADIUS dictionary data
-types, as with the following example:
-
-.Example
-[source,unlang]
-----
-<ipaddr>&Class == 127.0.0.1
-----
-
-In this example, the `Class` attribute is treated as if it was an IPv4
-address and is compared to the address `127.0.0.1`
-
-Casting is most useful when the left side of a comparison is a
-dynamically expanded string. The cast ensures that the comparison is
-done in a type-safe manner, instead of performing a string comparison.
-
-.Example
-[source,unlang]
-----
-<integer>`/bin/echo 00` == 0
-----
-
-In this example, the string output of the `echo` program is interpreted as an
-integer. It is then compared to the right side via integer
-comparisons. Since the integer `00` is equivalent to the integer `0`,
-the comparison will match. If the comparison had been performed via
-string equality checks, then the comparison would fail, because the
-strings `00` and `0` are different.
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/eq.adoc b/doc/antora/modules/unlang/pages/condition/eq.adoc
deleted file mode 100644
index d9e51f3f13..0000000000
--- a/doc/antora/modules/unlang/pages/condition/eq.adoc
+++ /dev/null
@@ -1,30 +0,0 @@
-= The == Operator
-
-.Syntax
-`(data-1 == data-2)`
-
-The `==` operator compares the result of evaluating `data-1` and
-`data-2`. As discussed in xref:type/index.adoc[Data Types], the `data-1`
-field may be interpreted as a reference to an attribute.
-
-The `data-2` field is interpreted in a type-specific manner. For
-example, if `data-1` refers to an attribute of type `ipaddr`, then
-`data-2` is evaluated as an IP address. If `data-1` refers to an
-attribute of type `integer`, then `data-2` is evaluated as an integer
-or as a named enumeration defined by a `VALUE` statement in a
-dictionary. Similarly, if `data-1` refers to an attribute of type
-`date`, then `data-2` will be interpreted as a date string.
-
-If the resulting data evaluates to be the same, then the operator
-returns `true`; otherwise, it returns `false`.
-
-.Example
-[source,unlang]
-----
-if (User-Name == "bob") {
- ...
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/index.adoc b/doc/antora/modules/unlang/pages/condition/index.adoc
deleted file mode 100644
index 10a84c8485..0000000000
--- a/doc/antora/modules/unlang/pages/condition/index.adoc
+++ /dev/null
@@ -1,85 +0,0 @@
-= Conditional Expressions
-
-Conditions are evaluated when parsing xref:if.adoc[if] and
-xref:elsif.adoc[elsif] statements. These conditions allow the server to
-make complex decisions based on one of a number of possible criteria.
-
-.Syntax
-[source,unlang]
-----
-if ( condition ) { ...
-
-elsif ( condition ) { ...
-----
-
-Conditions are expressed using the following syntax:
-
-[options="header"]
-|=====
-| Syntax | Description
-| xref:attr.adoc[&Attribute-Name] | Check for attribute existence.
-| xref:condition/return_codes.adoc[rcode] | Check return code of a previous module.
-| xref:condition/operands.adoc[data] | Check value of data.
-| xref:condition/cmp.adoc[lhs OP rhs] | Compare two kinds of data.
-| xref:condition/para.adoc[( condition )] | Check sub-condition
-| xref:condition/not.adoc[! condition] | Negate a conditional check
-| xref:condition/and.adoc[( condition ) && ...] | Check a condition AND the next one
-| xref:condition/or.adoc[( condition ) \|\| ...] | Check a condition OR the next one
-|=====
-
-
-.Examples
-[source,unlang]
-----
-if ( &User-Name == "bob" ) {
- ...
-}
-
-if ( &Framed-IP-Address == 127.0.0.1 ) {
- ...
-}
-
-if ( &Calling-Station-Id == "%{sql:SELECT ...}" ) {
- ...
-}
-----
-
-== Load-time Syntax Checks
-
-The server performs a number of checks when it loads the configuration
-files. Unlike version 2, all of the conditions are syntax checked
-when the server loads. This checking greatly aids in creating
-configurations that are correct. Where the configuration is
-incorrect, a descriptive error is produced.
-
-This error contains the filename and line number of the syntax error.
-In addition, it will print out a portion of the line that caused the
-error and will point to the exact character where the error was seen.
-These descriptive messages mean that most errors are easy to find and fix.
-
-== Load-time Optimizations
-
-The server performs a number of optimizations when it loads the
-configuration files. Conditions that have static values are
-evaluated and replaced with the result of the conditional comparison.
-
-.Example
-[source,unlang]
-----
-if ( 0 == 1 ) {
- ...
-}
-----
-
-The condition `0 == 1` is static and will evaluate to `false`. Since
-it evaluates to `false`, the configuration inside of the `if`
-statement is ignored. Any modules referenced inside of the `if`
-statement will not be loaded.
-
-This optimization is most useful for creating configurations that
-selectively load (or not) certain policies. If the condition above
-was used in version 2, then the configuration inside of the `if` statement
-would be loaded, even though it would never be used.
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/not.adoc b/doc/antora/modules/unlang/pages/condition/not.adoc
deleted file mode 100644
index bde038e2de..0000000000
--- a/doc/antora/modules/unlang/pages/condition/not.adoc
+++ /dev/null
@@ -1,19 +0,0 @@
-= The ! Operator
-
-.Syntax
-[source,unlang]
-----
-! condition
-----
-
-The `!` operator negates the result of the following condition. It
-returns `true` when _condition_ returns `false`. It returns `false`
-when _condition_ returns `true`.
-
-.Examples
-
-`(! (foo == bar))` +
-`! &User-Name`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/operands.adoc b/doc/antora/modules/unlang/pages/condition/operands.adoc
deleted file mode 100644
index 5b19af32f0..0000000000
--- a/doc/antora/modules/unlang/pages/condition/operands.adoc
+++ /dev/null
@@ -1,37 +0,0 @@
-= Operands
-
-.Syntax
-[source,unlang]
-----
-string
-integer
-"double-quoted string"
-'single-quoted string'
-`back-quoted string`
-----
-
-Any text not matching xref:attr.adoc[&Attribute-Name] or
-xref:condition/return_codes.adoc[Return Code] is interpreted as a value for a
-particular xref:type/index.adoc[data type].
-
-Double-quoted strings and back-quoted strings are dynamically expanded
-before the condition is evaluated. Single-quoted strings are static
-literals and are not dynamically expanded.
-
-When used as an existence check, the condition evaluates to `true` if
-the data is non-zero. Otherwise, the condition evaluates to `false`.
-
-For integer existence checks, `0` is `false`; all other values are `true`.
-
-For string existence checks, an empty string is `false`. All other
-strings are `true`.
-
-All other data types are disallowed in existence checks.
-
-.Examples
-
-`"hello there"` +
-`5`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/or.adoc b/doc/antora/modules/unlang/pages/condition/or.adoc
deleted file mode 100644
index 80c2cb45a8..0000000000
--- a/doc/antora/modules/unlang/pages/condition/or.adoc
+++ /dev/null
@@ -1,21 +0,0 @@
-= The || Operator
-
-.Syntax
-[source,unlang]
-----
-(expression-1 || expression-2)
-----
-
-The `||` operator performs a short-circuit "or" evaluation of the two
-expressions. This operator evaluates _condition-1_ and returns `true`
-if _condition-1_ returns true. Only if _condition-1_ returns `false`
-is _condition-2_ evaluated and its result returned.
-
-.Examples
-[source,unlang]
-----
-if (&User-Name || &NAS-IP-Address) { ...
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/para.adoc b/doc/antora/modules/unlang/pages/condition/para.adoc
deleted file mode 100644
index bdb3f013c3..0000000000
--- a/doc/antora/modules/unlang/pages/condition/para.adoc
+++ /dev/null
@@ -1,19 +0,0 @@
-= The ( ) Operator
-
-.Syntax
-[source,unlang]
-----
-( condition )
-----
-
-The `( )` operator returns the result of evaluating the given
-`condition`. It is used to clarify policies or to explicitly define
-conditional precedence.
-
-.Examples
-
-`(foo)` +
-`(bar || (baz && dub))`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/regex.adoc b/doc/antora/modules/unlang/pages/condition/regex.adoc
deleted file mode 100644
index 038faa647f..0000000000
--- a/doc/antora/modules/unlang/pages/condition/regex.adoc
+++ /dev/null
@@ -1,180 +0,0 @@
-= Regular Expressions
-
-.Syntax
-====
-[source,unlang]
-----
-(<subject> =~ /<pattern>/)
-(<subject> =~ /<pattern>/[imsux])
-
-(<subject> !~ /<pattern>/)
-(<subject> !~ /<pattern>/[imsux])
-----
-====
-
-== Matching
-The regular expression operators perform regular expression matching
-on the data. The `<subject>` field can be an attribute reference or data,
-as with the other xref:condition/cmp.adoc[comparison] operators. The `/<pattern>/`
-field must be a valid regular expression.
-
-The `=~` operator evaluates to `true` when `data` matches the
-`/<pattern>/`. Otherwise, it evaluates to `false`.
-
-The `!~` operator evaluates to `true` when `data` does not match the
-`/<pattern>/`. Otherwise, it evaluates to `true`.
-
-The regular expression comparison is performed on the _string representation_
-of the left side of the comparison. That is, if the left side is an
-xref:type/numb.adoc[integer], the regular expression will behave is if the
-value `0` was the literal string `"0"`. Similarly, if the left side is an
-xref:attr.adoc[&Attribute-Name], then the regular expression will behave is if
-the attribute was printed to a string, and the match was performed on the
-resulting string.
-
-.Checking if the `User-Name` attribute contains a realm of example.com
-====
-[source,unlang]
-----
-if (&User-Name =~ /@example\.com$/) {
- ...
-}
-----
-====
-
-== Dialects
-
-The syntax of the regular expression is defined by the regular
-expression library available on the local system.
-
-FreeRADIUS currently supports:
-
-* link:https://www.pcre.org/original/doc/html/[libpcre] and
-link:https://www.pcre.org/current/doc/html/[libpcre2] both of which
-provide
-link:https://en.wikipedia.org/wiki/Perl_Compatible_Regular_Expressions[Perl
-Compatible Regular expressions].
-* Regex support provided by the local libc implementation, usually
-link:http://en.wikipedia.org/wiki/Regular_expression#POSIX_basic_and_extended[
-Posix regular expressions].
-
-[TIP]
-====
-Use the output of `radiusd -Xxv` to determine which regular expression library is in use.
-
-....
-...
-Debug : regex-pcre : no
-Debug : regex-pcre2 : yes
-Debug : regex-posix : no
-Debug : regex-posix-extended : no
-Debug : regex-binsafe : yes
-...
-Debug : pcre2 : 10.33 (2019-04-16) - retrieved at build time
-....
-====
-
-[WARNING]
-====
-Depending on the regular expression library or libc implementation the server
-was built against, the pattern matching function available may not be binary
-safe (see `regex-binsafe` in the output of `radiusd -Xxv`).
-
-If a binary safe regex match function is not available, and a match is
-attempted against a subject that contains one or more `NUL` ('\0') bytes, the
-match will be aborted, any condition that uses the result will evaluate to false,
-and a warning will be emitted.
-====
-
-== Flags
-
-The regular expression `/<pattern>/` may be followed by one or more flag
-characters. Again, which flags are available depends on the regular expression
-library the server was built with. Multiple flags may be specified per
-`/pattern/`.
-
-.Flags and their uses
-
-[options="header"]
-|=====
-| Flag Character | Available with | Effect
-| `i` | All | Enable case-insensitive matching.
-| `m` | All | '^' and '$' match newlines within the subject.
-| `s` | libpcre[2] | '.' matches anything, including newlines.
-| `u` | libpcre[2] | Treats subjects as UTF8. Invalid UTF8
- sequences will result in the match failing.
- |`x` | libpcre[2] | Allows comments in expressions by ignoring
- whitespace, and text between '#' and the next
- newline character.
-|=====
-
-== Subcapture groups
-
-When the `=~` or `!~` operators are used, then parentheses in the regular
-expression will sub capture groups, which contain part of the subject string.
-
-The special expansion `%{0}` expands to the portion of the subject that
-matched. The expansions +
-`%{1}`..`%{32}` expand to the contents of any subcapture groups.
-
-When using libpcre[2], named capture groups may also be accessed using the
-built-in expansion +
-`%{regex:<named capture group>}`.
-
-Please see the xref:xlat/builtin.adoc#_0_32[xlat documentation] for
-more information on regular expression matching.
-
-.Extracting the 'user' portion of a realm qualified string
-====
-[source,unlang]
-----
-if (&User-Name =~ /^(.*)@example\.com$/) {
- update reply {
- Reply-Message := "Hello %{1}"
- }
-}
-----
-====
-
-== Pre-Compiled vs Runtime Compiled
-
-When the server starts any regular expressions comparisons it finds will be
-pre-compiled, and if support is available, JIT'd (converted to machine code)
-to ensure fast execution.
-
-If a pattern contains a xref:xlat/index.adoc[string expansion], the pattern
-cannot be compiled on startup, and will be compiled at runtime each time the
-expression is evaluated. The server will also turn off JITing for runtime
-compiled expressions, as the overhead is greater than the time that would be
-saved during evaluation.
-
-.A runtime compiled regular expression
-====
-[source,unlang]
-----
-if (&User-Name =~ /^@%{Tmp-String-0}$/) {
- ...
-}
-----
-====
-
-To ensure optimal performance you should limit the number of patterns
-containing xref:xlat/index.adoc[string expansions], and if using PCRE, combine
-multiple expressions operating on the same subject into a single expression
-using the PCRE alternation '|' operator.
-
-.Using multiple string expansions and the PCRE alternation operator
-====
-[source,unlang]
-----
-if (&User-Name =~ /^@(%{Tmp-String-0}|%{Tmp-String-1})$/) {
- ...
-}
-----
-====
-
-
-// Licenced under CC-by-NC 4.0.
-// Copyright (C) 2020 Network RADIUS SAS.
-// Copyright (C) 2019 Arran Cudbard-Bell <a.cudbardb@freeradius.org>
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/condition/return_codes.adoc b/doc/antora/modules/unlang/pages/condition/return_codes.adoc
deleted file mode 100644
index ebc49ed5c7..0000000000
--- a/doc/antora/modules/unlang/pages/condition/return_codes.adoc
+++ /dev/null
@@ -1,35 +0,0 @@
-= The return code Operator
-
-.Syntax
-[source,unlang]
-----
-rcode
-----
-
-The Unlang interpreter tracks the return code of any module, string expansion
-or keyword that has been called.
-
-This return code can be checked in any condition. If the saved return code
-matches the `code` given here, then the condition evaluates to `true`.
-Otherwise, it evaluates to `false`.
-
-rcodes cannot be set in a condition. rcodes cannot be compared with anything else.
-
-The list of valid return codes is as follows:
-
-.Return Codes
-
-include::partial$rcode_table.adoc[]
-
-.Examples
-
-[source,unlang]
-----
-sql
-if (notfound) {
- ...
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/default.adoc b/doc/antora/modules/unlang/pages/default.adoc
deleted file mode 100644
index 30912ef40a..0000000000
--- a/doc/antora/modules/unlang/pages/default.adoc
+++ /dev/null
@@ -1,47 +0,0 @@
-= The case Statement
-
-.Syntax
-[source,unlang]
-----
-case [ <match> ] {
- [ statements ]
-}
-----
-
-The `case` statement is used to match data inside of a
-xref:switch.adoc[switch] statement. The `case` statement cannot be used
-outside of a xref:switch.adoc[switch] statement.
-
-
-The `<match>` text can be an attribute reference such as `&User-Name`,
-or it can be a xref:type/index.adoc[string]. If the match
-text is a dynamically expanded string, then the match is performed on
-the output of the string expansion.
-
-The keyword `default` can be used to specify the default action to
-take inside of a xref:switch.adoc[switch] statement.
-
-If no `<match>` text is given, it means that the `case` statement is
-the "default" and will match all which is not matched by another
-`case` statement inside of the same xref:switch.adoc[switch].
-
-.Example
-[source,unlang]
-----
-switch &User-Name {
- case "bob" {
- reject
- }
-
- case &Filter-Id {
- reject
- }
-
- default {
- ok
- }
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/else.adoc b/doc/antora/modules/unlang/pages/else.adoc
deleted file mode 100644
index a795d0e12c..0000000000
--- a/doc/antora/modules/unlang/pages/else.adoc
+++ /dev/null
@@ -1,30 +0,0 @@
-= The else Statement
-
-.Syntax
-[source,unlang]
-----
-if (condition) {
- [ statements ]
-}
-else {
- [ statements ]
-}
-----
-
-An xref:if.adoc[if] statement can have an `else` clause. If _condition_
-evaluates to `false`, the statements in the xref:if.adoc[if] subsection are skipped
-and the statements within the `else` subsection are executed.
-
-.Example
-[source,unlang]
-----
-if (&User-Name == "bob") {
- reject
-}
-else {
- ok
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/elsif.adoc b/doc/antora/modules/unlang/pages/elsif.adoc
deleted file mode 100644
index ff5799c791..0000000000
--- a/doc/antora/modules/unlang/pages/elsif.adoc
+++ /dev/null
@@ -1,43 +0,0 @@
-= The elsif Statement
-
-.Syntax
-[source,unlang]
-----
-if (condition-1) {
- [ statements-1 ]
-}
-elsif (condition-2) {
- [ statements-2 ]
-}
-else {
- [ statements-3 ]
-}
-----
-
-An `elsif` statement is used to evaluate a subsequent
-xref:condition/index.adoc[condition] after a preceding xref:if.adoc[if] statement
-evaluates to `false`. In the example above, when _condition-1_
-evaluates to false, then _statements-1_ are skipped and _condition-2_
-is checked. When _condition-2_ evaluates true, then _statements-2_
-are executed. When _condition-2_ evaluates false, then
-_statements-2_ are skipped and _statements-3_ are executed.
-
-As with xref:if.adoc[if], an `elsif` clause does not need to be followed by
-an xref:else.adoc[else] statement. However, any xref:else.adoc[else] statement
-must be the last statement in an `elsif` chain. An arbitrary number of
-`elsif` statements can be chained together to create a series of
-conditional checks and statements.
-
-.Example
-[source,unlang]
-----
-if (&User-Name == "bob") {
- reject
-}
-elsif (&User-Name == "doug") {
- ok
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/foreach.adoc b/doc/antora/modules/unlang/pages/foreach.adoc
deleted file mode 100644
index 6ed3ddff67..0000000000
--- a/doc/antora/modules/unlang/pages/foreach.adoc
+++ /dev/null
@@ -1,40 +0,0 @@
-= The foreach Statement
-
-.Syntax
-[source,unlang]
-----
-foreach <attribute-reference> {
- [ statements ]
-}
-----
-
-The `foreach` statement loops over a set of attributes as given by
-`<attribute-reference>`. The loop can be exited early by using the
-xref:break.adoc[break] keyword.
-
-<attribute-reference>::
-
-The xref:attr.adoc[attribute reference] which will will be looped
-over. The reference can be to one attribute, to an array, a child, or
-be a subset.
-
-Inside of the `foreach` block, the attribute that is being looped over
-can be referenced as `Foreach-Variable-0`, through
-`Foreach-Variable-9`. The last digit is the depth of the loop,
-starting at "0". The loops can be nested up to eight (8) deep, though
-this is not recommended.
-
-The attributes being looped over cannot be modified or deleted.
-
-.Example
-[source,unlang]
-----
-foreach &Class {
- update reply {
- Reply-Message += "Contains %{Foreach-Variable-0}"
- }
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/group.adoc b/doc/antora/modules/unlang/pages/group.adoc
deleted file mode 100644
index 98801fd280..0000000000
--- a/doc/antora/modules/unlang/pages/group.adoc
+++ /dev/null
@@ -1,39 +0,0 @@
-= The group Statement
-
-.Syntax
-[source,unlang]
-----
-group {
- [ statements ]
-}
-----
-
-The `group` statement collects a series of statements into a list.
-The default processing sections of the server (`authorize`,
-`accounting`, etc.) are also `group` statements. Those sections are
-given different name for management reasons, but they behave
-internally exactly like a `group`.
-
-[ statements ]:: The `unlang` commands which will be executed.
-
-All of the statements inside of the `group` are executed in sequence.
-The `group` statement is not normally used, as the statements within
-it can just be placed inside of the enclosing section. However, the
-`group` statement is included in the `unlang` syntax for completeness.
-
-.Examples
-
-[source,unlang]
-----
-group {
- sql
- ldap
- file
- if (updated) {
- ...
- }
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/if.adoc b/doc/antora/modules/unlang/pages/if.adoc
deleted file mode 100644
index ea549efb52..0000000000
--- a/doc/antora/modules/unlang/pages/if.adoc
+++ /dev/null
@@ -1,29 +0,0 @@
-= The if Statement
-
-.Syntax
-[source,unlang]
-----
-if (condition) {
- [ statements ]
-}
-----
-
-.Description
-The `if` statement evaluates a xref:condition/index.adoc[condition]. When the
-_condition_ evaluates to `true`, the statements within the subsection
-are executed. When the _condition_ evaluates to `false`, those
-statements are skipped.
-
-An `if` statement can optionally be followed by an xref:else.adoc[else] or
-an xref:elsif.adoc[elsif] statement.
-
-.Example
-[source,unlang]
-----
-if (&User-Name == "bob") {
- reject
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/index.adoc b/doc/antora/modules/unlang/pages/index.adoc
deleted file mode 100644
index fc812f873d..0000000000
--- a/doc/antora/modules/unlang/pages/index.adoc
+++ /dev/null
@@ -1,162 +0,0 @@
-= Unlang Policy Language
-
-The server supports a simple processing language called "Unlang",
-which is short for "un-language". The original intention of using an
-"un-language" was to avoid creating yet another programming language.
-Instead, the `unlang` syntax allows for simple _if / then / else_
-checks, and attribute editing. It does not support recursion,
-subroutines, or more complex flow controls.
-
-Where more complicated functionality is required, we recommend using
-the `lua`, `perl` or `python` modules. Those modules allow the insertion of
-full-featured scripts at any point in the packet processing.
-
-NOTE: The documentation is this directory is _reference_
-documentation. That is, it describes the syntax of `unlang` keywords,
-using minimal examples. The reference documentation does not,
-however, describe _when_ to use the keywords, or _how_ to create
-policies. Please see the xref:howto:index.adoc[howto] directory for
-more in-depth "how to" guides.
-
-The documentation is organized so that each item is on its own page.
-The page beings with a description of the item, followed by some text
-explaining what the item does. The page concludes with one or more
-examples of using the item in `unlang` policies.
-
-The `unlang` processing can be split into some high-level concepts.
-
-== Keywords
-
-xref:keywords.adoc[Keywords], which are the basic statements of the
-language, e.g., xref:load-balance.adoc[load-balance],
-xref:if.adoc[if], xref:else.adoc[else], etc.
-
-.Example
-[source,unlang]
-----
-load-balance {
- sql1
- sql2
- sql3
-}
-----
-
-== Conditional Expressions
-
-xref:condition/index.adoc[Conditional expressions], which are used to check
-if conditions evaluate to _true_ or _false_. Conditional expressions
-can be used to control the flow of processing.
-
-.Example
-[source,unlang]
-----
-if ((&User-Name == "bob") && (&Calling-Station-Id == "00:01:03:04:05")) {
- ...
-}
-----
-
-== Update Statements
-
-xref:update.adoc[update] statements are used to edit attributes and
-lists of attributes.
-
-Most request packets will result in reply packets that contain
-additional information for the requestor. The `update` section allows
-policies to add attributes to requests, replies, or to other places.
-
-.Example
-[source,unlang]
-----
-update reply {
- &Session-Timeout := 3600
- &Framed-IP-Address := 192.0.2.4
-}
-----
-
-== String Expansions
-
-xref:xlat/index.adoc[String expansion] Using `%{...}` to perform dynamic
-string expansions. (also known as xref:xlat/index.adoc[xlat])
-
-String expansions are usually performed in order to get additional
-information which is not immediately available to the policy. This
-information can be taken from almost any source, including other
-attributes, databases, and scripts.
-
-.Example
-[source,unlang]
-----
-update reply {
- &Framed-IP-Address := "%{sql:SELECT static_ip from table WHERE user = '%{User-Name}'}"
-}
-----
-
-== Data Types
-
-Each attribute used by the server has an associated
-xref:type/index.adoc[data type]. The `unlang` interpreter enforces
-restrictions on assignments, so that only valid data types can be
-assigned to an attribute. Invalid assignments result in a run-time
-error.
-
-.Example
-[source,unlang]
-----
-update reply {
- &Framed-IP-Address := 192.0.2.4
- &Session-Timeout := 5
- &Reply-Message := "hello"
-}
-----
-
-== Design Goals of Unlang
-
-The goal of `unlang` is to allow simple policies to be written with
-minimal effort. Conditional checks can be performed by the policies,
-which can then update the request or response attributes based on the
-results of those checks. `unlang` can only be used in a processing
-section, it cannot be used anywhere else, including in configuration
-sections for a client or a module. The reason for this limitation is
-that the language is intended to perform specific actions on requests
-and responses. The client and module sections contain definitions for
-a client or module; they do not define how a request is processed.
-
-`unlang` uses the same the basic syntax as the configuration files.
-The syntax of the configuration file for lines, comments, sections,
-sub-section, etc., all apply to `unlang`.
-
-Where `unlang` differs from the basic configuration file format is in
-complexity and operation. The normal configuration files are
-_declarative_ and they are _static_. That is, they declare variables
-and values for those variables. Those values do not change when the
-server is running.
-
-In contrast, `unlang` performs run-time processing of requests.
-Conditional statements such as xref:if.adoc[if] are evaluated for every
-packet that is received. Attribute editing statements such as
-xref:update.adoc[update] can be used to edit attribute contents or lists
-of attributes.
-
-.Example
-[source,unlang]
-----
-# First, the keyword 'if'
-
-# followed by condition which checks that the User-Name
-# attribute has value "bob"
-
-if (&User-Name == "bob") {
- # keyword "update"
-
- # followed by instructions to add the Reply-Message
- # attribute to the "reply" list, with contents
- # "Hello, bob"
-
- update reply {
- Reply-Message := "Hello, bob"
- }
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/keywords.adoc b/doc/antora/modules/unlang/pages/keywords.adoc
deleted file mode 100644
index e6411ea984..0000000000
--- a/doc/antora/modules/unlang/pages/keywords.adoc
+++ /dev/null
@@ -1,78 +0,0 @@
-= Keywords
-
-The following tables list the keywords used in `Unlang`. These keywords
-implement the "flow control" of the policies.
-
-== Flow Control Keywords
-
-The _flow control_ keywords allow _if / then / else_ checks, simple
-looping, etc.
-
-.Flow Control
-[options="header"]
-[cols="30%,70%"]
-|=====
-| Keyword | Description
-| xref:break.adoc[break] | Exit early from a `foreach` loop.
-| xref:case.adoc[case] | Match inside of a `switch`.
-| xref:else.adoc[else] | Do something when an `if` does not match.
-| xref:elsif.adoc[elsif] | Check for condition when a previous `if` does not match.
-| xref:foreach.adoc[foreach] | Loop over a list of attributes.
-| xref:if.adoc[if] | Check for a condition, and execute a sub-policy if it matches.
-| xref:return.adoc[return] | Immediately stop processing a section.
-| xref:switch.adoc[switch] | Check for multiple values.
-|=====
-
-== Attribute Editing Keywords
-
-The _attribute editing_ keywords allow policies to add, delete, and
-modify attributes in any list or packet.
-
-.Attribute Editing
-[options="header"]
-[cols="30%,70%"]
-|=====
-| Keyword | Description
-| xref:update.adoc[update] | Add or filter attributes to a list
-|=====
-
-== Grouping Keywords
-
-The _grouping_ keywords allow policies to be organized into groups,
-including load-balancing.
-
-.Grouping
-[options="header"]
-[cols="30%,70%"]
-|=====
-| Keyword | Description
-| xref:group.adoc[group] | Group a series of statements.
-| xref:load-balance.adoc[load-balance] | Define a load balancing group without fail-over.
-| xref:redundant.adoc[redundant] | Define a redundant group with fail-over.
-| xref:redundant-load-balance.adoc[redundant-load-balance] | Define a redundant group with fail-over and load balancing.
-|=====
-
-== Module Keywords
-
-The _module_ keywords refer pre-packaged libraries that implement
-specific functionality, such as connecting to SQL, LDAP, etc. The
-name used here is not the literal string `module`. Instead, it is the
-name of an instance of a pre-packaged module such as `sql`, or `ldap`, or
-`eap`.
-
-The documentation below describes how to reference modules. That is,
-how to use `sql`, etc. in the policies. Please see
-`raddb/mods-available/` for configuration examples for each module.
-
-.Modules
-[options="header"]
-[cols="30%,70%"]
-|=====
-| Keyword | Description
-| xref:module.adoc[<module>] | Execute a named module, e.g., `sql`.
-| xref:module_method.adoc[<module>.<method>] | Execute a particular method of a named module, e.g., `pap.authorize`
-| xref:module_builtin.adoc[reject] | Built-in modules, e.g., `reject`, or `ok`, etc.
-|=====
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/list.adoc b/doc/antora/modules/unlang/pages/list.adoc
deleted file mode 100644
index a55a54f992..0000000000
--- a/doc/antora/modules/unlang/pages/list.adoc
+++ /dev/null
@@ -1,72 +0,0 @@
-= Attribute Lists
-
-An attribute list contains a set of attributes. The allowed lists
-are:
-
-`request`:: Attributes in the incoming request packet.
-
-`reply`:: Attributes in the outgoing reply packet.
-
-`control`:: Attributes in the internal "control" list that is
-associated with the request.
-+
-The `control` attributes are used to manage how the request is
-processed. These attributes are never sent in any packet.
-
-`session-state`:: Attributes which are maintained across multi-packet
-exchanges.
-
-`proxy-request`:: Attributes in the proxied request packet to a home server.
-
-`proxy-reply`:: Attributes in the reply packet from the home server.
-
-`coa`:: Attributes in a CoA-Request packet which is sent to a home server.
-
-`disconnect`:: Attributes in a Disconnect-Request packet which is sent to a home server.
-
-There must be a colon `:` after the list name and before the attribute name.
-This syntax helps the server to distinguish between list names and attribute
-names.
-
-With the exception of `session-state`, all of the above lists are
-ephemeral. That is, they exist for one packet exchange, and only one
-packet exchange. When a reply is sent for a request, the above lists
-and all attributes are deleted. There is no way to reference an
-attribute from a previous packet. We recommend using a database to
-track complex state.
-
-The `coa` and `disconnect` lists can only be used when the server
-receives an Access-Request or Accounting-Request. Use `request` and
-`reply` instead of `coa` when the server receives a CoA-Request or
-Disconnect-Request packet.
-
-Adding one or more attributes to either of the `coa` or `disconnect`
-list causes server to originate a CoA-Request or Disconnect-Request
-packet. That packet is sent when the current Access-Request or
-Accounting-Request has been finished, and a reply sent to the NAS.
-See `raddb/sites-available/originate-coa` for additional information.
-
-In some cases, requests are associated a multi-packet exchange. For
-those situations, the `session-state` list is automatically saved when
-a reply is sent, and it is automatically restored when the next packet
-in sequence comes in. Once the packet exchange has been finished, the
-`session-state` list is deleted.
-
-In some cases, there is a parent-child relationship between requests.
-In those situations, it is possible for the policy rules in the child
-to refer to attributes in the parent. This reference can be made by
-prefixing the _<list>_ name with the `parent` qualifier. The key word
-`outer` is also a synonym for `parent`. If there are multiple
-parent-child relationships, the `parent` qualifier can be repeated.
-
-There is, however, no way for the parent to refer to the child. When
-the child is running, the parent is suspended. Once the child
-finishes, it is deleted, and is no longer accessible to the parent.
-
-.Examples
-`&parent.request.User-Name` +
-`&parent.reply.Reply-Message` +
-`&parent.parent.session-state.Filter-Id`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/load-balance.adoc b/doc/antora/modules/unlang/pages/load-balance.adoc
deleted file mode 100644
index d64b161590..0000000000
--- a/doc/antora/modules/unlang/pages/load-balance.adoc
+++ /dev/null
@@ -1,32 +0,0 @@
-= The load-balance Statement
-
-.Syntax
-[source,unlang]
-----
-load-balance {
- [ statements ]
-}
-----
-
-The `load-balance` section is similar to the `redundant` section
-except that only one module in the subsection is ever called.
-
-In general, the
-xref:redundant-load-balance.adoc[redundant-load-balance] statement is
-more useful than this one.
-
-[ statements ]:: One or more `unlang` commands. Only one of the
-statements is executed.
-
-.Examples
-
-[source,unlang]
-----
-load-balance &User-Name {
- sql1
- sql2
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/module.adoc b/doc/antora/modules/unlang/pages/module.adoc
deleted file mode 100644
index fd18f2f4ba..0000000000
--- a/doc/antora/modules/unlang/pages/module.adoc
+++ /dev/null
@@ -1,86 +0,0 @@
-= Modules
-
-.Syntax
-[source,unlang]
-----
-<module>
-----
-
-The `<module>` statement is a reference to the named module. Common
-module names include `pap`, `chap`, `files`, `eap`, and `sql`. The
-`modules { ... }` subsection of `radiusd.conf` contains all of the
-valid modules.
-
-When processing reaches a named module, the pre-compiled module is
-called. The module may succeed or fail and will return a status code
-to the `unlang` interpreter detailing success or failure.
-
-.Example
-[source,unlang]
-----
-chap
-sql
-----
-
-== Module Return Codes
-
-When a module is called, it returns one of the following codes to
-the interpreter; the meaning of each code is detailed to the right of
-the source, below:
-
-.Module Return Codes
-
-The below table describes the purpose of the rcodes that may be returned
-by a module call. In this case the 'operation' referenced in the table is
-the current module call.
-
-include::partial$rcode_table.adoc[]
-
-These return codes can be used in a subsequent
-xref:condition/index.adoc[conditional expression] thus allowing policies to
-perform different actions based on the behaviour of the modules.
-
-.Example
-[source,unlang]
-----
-sql
-if (notfound) {
- update reply {
- Reply-Message = "We don't know who you are"
- }
- reject
-}
-----
-
-== Module Return Code priority overrides
-
-In the case of modules, rcodes can be modified on a per-call basis.
-
-Module priority overrides are specified in a block inline with the module call.
-The format of an override is `<rcode> = (0+|<rcode>|return)` - That is,
-a number greater than or equal to 0, the priority of another rcode, or the special
-priority `return` which causes the current section to immediately exit.
-
-[source, unlang]
-----
-ldap { <1>
- fail = 1 <2>
- ok = handled <3>
- reject = return <4>
-}
-----
-
-<1> Call to the `ldap` module.
-<2> Sets the priority of the `fail` rcode to be `1`. If the priority
- of the rcode for the request is `0`, then the request request rcode
- will be set to `fail` if the module returns `fail`.
-<3> Sets the priority of the `ok` rcode to be whatever the default is for
- `handled` in this section. As the default for `handled` is usually
- `return`. If `ok` is returned, the current section will immediately
- exit.
-<4> Sets the priority of `reject` to be `return`. If the module returns
- `reject`, the current section will immediately exit.
-
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/module_builtin.adoc b/doc/antora/modules/unlang/pages/module_builtin.adoc
deleted file mode 100644
index f21a128953..0000000000
--- a/doc/antora/modules/unlang/pages/module_builtin.adoc
+++ /dev/null
@@ -1,42 +0,0 @@
-= Built-in Modules
-
-In some cases, it is useful to reject a request immediately or perform another
-action on it. The built-in modules can be used to perform these actions. These
-modules are named for the return codes given in the xref:module.adoc[module]
-section.
-
-In practice, these modules are implemented by the `always` module and
-exist so that a success or failure can be forced during the processing
-of a policy.
-
-The names and behaviours of these modules are given below:
-
-`fail`::
-Causes the request to be treated as if a database failure had
-occurred.
-
-`noop`::
-Do nothing. This also serves as an instruction to the
-configurable failover tracking that nothing was done in the current
-section.
-
-`ok`::
-Instructs the server that the request was processed properly. This keyword can be used to over-ride earlier failures if the local
-administrator determines that the failures are not catastrophic.
-
-`reject`::
-Causes the request to be immediately rejected.
-
-.Example
-[source,unlang]
-----
-if (!&User-Name) {
- update reply {
- Reply-Message := "We don't know who you are"
- }
- reject
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/module_method.adoc b/doc/antora/modules/unlang/pages/module_method.adoc
deleted file mode 100644
index 98cd37582e..0000000000
--- a/doc/antora/modules/unlang/pages/module_method.adoc
+++ /dev/null
@@ -1,27 +0,0 @@
-= Module methods
-
-.Syntax
-[source,unlang]
-----
-<module>.<method>
-----
-
-This variant of xref:module.adoc[<module>] is used in one processing
-section. It calls a module using the method of another processing
-section. For example, it can be used to call a module's `authorize`
-method while processing the `post-auth` section.
-
-The `<module>` portion must refer to an existing module; the
-`<method>` portion must refer to processing method supported by that
-module. Typically, the names of the processing method will be the
-same as the processing sections.
-
-.Example
-[source,unlang]
-----
-sql.recv.Accounting-Request
-files.recv.Access-Request
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/redundant-load-balance.adoc b/doc/antora/modules/unlang/pages/redundant-load-balance.adoc
deleted file mode 100644
index 2322f726fd..0000000000
--- a/doc/antora/modules/unlang/pages/redundant-load-balance.adoc
+++ /dev/null
@@ -1,39 +0,0 @@
-= The redundant-load-balance Statement
-
-.Syntax
-[source,unlang]
-----
-redundant-load-balance {
- [ statements ]
-}
-----
-
-The `redundant-load-balance` section operates as a combination of the
-xref:redundant.adoc[redundant] and xref:load-balance.adoc[load-balance]
-sections.
-
-[ statements ]:: One or more `unlang` commands.
-+
-If the selected statement succeeds, then the server stops processing
-the `redundant-load-balance` section. If, however, that statement fails,
-then the next statement in the list is chosen (wrapping around to the
-top). This process continues until either one statement succeeds or all
-of the statements have failed.
-+
-All of the statements in the list should be modules, and of the same
-type (e.g., `ldap` or `sql`). All of the statements in the list should
-behave identically, otherwise different requests will be processed
-through different modules and will give different results.
-
-.Example
-[source,unlang]
-----
-redundant-load-balance &User-Name {
- sql1
- sql2
- sql3
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/redundant.adoc b/doc/antora/modules/unlang/pages/redundant.adoc
deleted file mode 100644
index e837d1f369..0000000000
--- a/doc/antora/modules/unlang/pages/redundant.adoc
+++ /dev/null
@@ -1,42 +0,0 @@
-= The redundant Statement
-
-.Syntax
-[source,unlang]
-----
-redundant {
- [ statements ]
-}
-----
-
-The `redundant` section executes a series of statements in sequence.
-As soon as one statement succeeds, the rest of the section is skipped.
-
-[ statements ]:: One or more `unlang` commands. Processing starts
-from the first statement in the list.
-+
-If the selected statement succeeds, then the server stops processing
-the `redundant` section. If, however, that statement fails, then the
-next statement in the list is chosen. This process continues until
-either one statement succeeds or all of the statements have failed.
-+
-All of the statements in the list should be modules, and of the same
-type (e.g., `ldap` or `sql`). All of the statements in the list should
-behave identically, otherwise different requests will be processed
-through different modules and will give different results.
-
-In general, we recommend using the
-xref:redundant-load-balance.adoc[redundant-load-balance] statement
-instead of `redundant`.
-
-.Example
-[source,unlang]
-----
-redundant {
- sql1
- sql2
- sql3
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/return.adoc b/doc/antora/modules/unlang/pages/return.adoc
deleted file mode 100644
index aea1bc2ab2..0000000000
--- a/doc/antora/modules/unlang/pages/return.adoc
+++ /dev/null
@@ -1,36 +0,0 @@
-= The return Statement
-
-.Syntax
-[source,unlang]
-----
-return
-----
-
-The `return` statement is used to exit a processing section such as
-`authorize`. It behaves similarly to the
-xref:break.adoc[break] statement, except that it is not limited to
-being used inside of a xref:foreach.adoc[foreach] loop.
-
-The `return` statement is not strictly necessary. It is mainly used
-to simplify the layout of `unlang` policies. If the `return`
-statement did not exist, then every xref:if.adoc[if] statement might need
-to have a matching xref:else.adoc[else] statement.
-
-The `return` statement will also exit a policy which is defined in the
-`policy { ... } ` subsection. This behavior allows policies to be
-treated as a function call. Any `return` inside of the policy section
-will only return from that policy. The `return` will _not_ return
-from the enclosing processing section which called the policy.
-
-.Example
-[source,unlang]
-----
-sql
-if (&reply.Filter-Id == "hello") {
- return
-}
-...
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/return_codes.adoc b/doc/antora/modules/unlang/pages/return_codes.adoc
deleted file mode 100644
index 3b09c2dc52..0000000000
--- a/doc/antora/modules/unlang/pages/return_codes.adoc
+++ /dev/null
@@ -1,17 +0,0 @@
-= Return codes
-
-Many operations in the server produce a return code (rcode).
-The different rcodes give a course indication of whether a particular operation
-(a module call, string expansion, or keyword) was successful.
-
-Unlike return values in other languages, FreeRADIUS' rcodes are are always taken
-from a fixed compiled-in set.
-
-include::partial$rcode_table.adoc[]
-
-Return codes propagate through nested unlang sections based on their priority.
-If a rcode returned by an operation has a higher priority than the current rcode
-associated with the request, then the request rcode is overwritten.
-
-Return code priorities are assigned by the section the module call, expansion or
-keyword was used in.
diff --git a/doc/antora/modules/unlang/pages/switch.adoc b/doc/antora/modules/unlang/pages/switch.adoc
deleted file mode 100644
index deff7032bd..0000000000
--- a/doc/antora/modules/unlang/pages/switch.adoc
+++ /dev/null
@@ -1,83 +0,0 @@
-= The switch Statement
-
-.Syntax
-[source,unlang]
-----
-switch <expansion> {
- case <match-1> {
- [ statements-1 ]
- }
- case <match-2> {
- [ statements-2 ]
- }
- case {
- [ statements-3 ]
- }
-}
-----
-
-A `switch` statement causes the server to evaluate _expansion_, which
-can be an xref:attr.adoc[&Attribute-Name] or
-xref:condition/operands.adoc[data]. The result is compared against _match-1_
-and _match-2_ to find a match. If no string matches, then the server
-looks for the default xref:case.adoc[case] statement, which has no
-associated match.
-
-The matching is done via equality. The `switch` statement is mostly
-syntactic sugar and is used to simplify the visual form of the
-configuration. It is mostly equivalent to the following use of
-xref:if.adoc[if] statements:
-
-.Nearly equivalent syntax
-[source,unlang]
-----
-if (<expansion> == <match-1>) {
- [ statements-1 ]
-}
-elsif (<expansion> == <match-2>) {
- [ statements-2 ]
-}
-else {
- [ statements-3 ]
-}
-----
-
-The only difference between the two forms is that for a `switch`
-statement, the _expansion_ is evaluated only once. For the equivalent
-xref:if.adoc[if] statement, the _expansion_ is evaluated again for every
-xref:if.adoc[if].
-
-If a matching xref:case.adoc[case] is found, the statements within
-that xref:case.adoc[case] are evaluated. If no matching
-xref:case.adoc[case] is found, the `case` section with no "match" is
-evaluated. If there is no such `case { ...}` subsection, then the
-`switch` statement behaves as if the `case {...}` section was empty.
-
-////
-For compatibility with version 3, and empty `case` statement can also
-be used instead of `default`.
-////
-
-The _match_ text for the xref:case.adoc[case] statement can be an
-xref:attr.adoc[&Attribute-Name] or xref:type/index.adoc[data].
-
-No statement other than xref:case.adoc[case] can appear in a `switch`
-statement, and the xref:case.adoc[case] statement cannot appear outside of a
-`switch` statement.
-
-.Example
-[source,unlang]
-----
-switch &User-Name {
- case "bob" {
- reject
- }
-
- case {
- ok
- }
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/type/all_types.adoc b/doc/antora/modules/unlang/pages/type/all_types.adoc
deleted file mode 100644
index 0bace01354..0000000000
--- a/doc/antora/modules/unlang/pages/type/all_types.adoc
+++ /dev/null
@@ -1,80 +0,0 @@
-= List of Data Types
-
-The server support a wide range of data types, both in `unlang` and in
-the dictionaries. This page outlines the names and functionality of
-those data types.
-
-== Basic Data Types
-
-There are a number of "basic" data types. These data types are
-fixed-size, and encapsulate simple concepts such as "integer" or "IP
-address".
-
-Basic data types can be used in `unlang`, as they contain simple
-values which can be compared, or assigned to one attribute. In most
-cases, it is not necessary to know the name of the data type. It is
-possible to write values in the format you expect, The server will do
-"the right thing" when interpreting the values.
-
-.Basic Data Types
-[options="header"]
-[cols="15%,85%"]
-|=====
-| Data Type | Description
-| bool | boolean
-| date | calendar date
-| ethernet | Ethernet address
-| float32 | 32-bit floating point number
-| float64 | 64-bit floating point number
-| ifid | interface ID
-| int8 | 8-bit signed integer
-| int16 | 16-bit signed integer
-| int32 | 32-bit signed integer
-| int64 | 64-bit signed integer
-| ipaddr | IPv4 address
-| ipv6addr | IPv6 address
-| ipv4prefix | IPv4 network with address and prefix length
-| ipv6prefix | IPv6 network with address and prefix length
-| octets | raw binary, printed as hex strings
-| string | printable strings
-| time_delta | difference between two calendar dates
-| uint8 | 8-bit unsigned integer
-| uint16 | 16-bit unsigned integer
-| uint32 | 32-bit unsigned integer
-| uint64 | 64-bit unsigned integer
-|=====
-
-=== Structural Data Types
-
-The following data types are "structural", in that they form
-parent-child relationships between attributes. These data types can
-only be used in the dictionaries. They cannot be used in `unlang`
-statements.
-
-.Structural Data Types
-[options="header"]
-[cols="15%,85%"]
-|=====
-| Data Type | Description
-| struct | structure which contains fixed-width fields
-| tlv | type-length-value which contains other attributes
-| vsa | Encapsulation of vendor-specific attributes
-|=====
-
-=== Protocol-Specific Data Types
-
-The following data types are used only in certain protocols. These
-data types can be used only in the dictionaries. They cannot be used
-in `unlang` statements.
-
-.Protocol Specific Data Types
-[options="header"]
-[cols="15%,15%,70%"]
-|=====
-| Data Type | Protocol | Description
-| abinary | RADIUS | Ascend binary filters
-| extended | RADIUS | attributes which "extend" the number space
-|=====
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS
diff --git a/doc/antora/modules/unlang/pages/type/double.adoc b/doc/antora/modules/unlang/pages/type/double.adoc
deleted file mode 100644
index 6c3e708eaa..0000000000
--- a/doc/antora/modules/unlang/pages/type/double.adoc
+++ /dev/null
@@ -1,39 +0,0 @@
-= Double-Quoted Strings
-
-.Syntax
-`"string"`
-
-A double-quoted string is interpreted via the usual rules in
-programming languages for double quoted strings. The double-quote
-character can be placed in a string by escaping it with a backslash.
-Carriage returns and line-feeds can also be used via the usual `\r` and
-`\n` syntax.
-
-The main difference between the single and double quoted strings is
-that the double quoted strings can be dynamically expanded. The syntax
-`${...}` is used for parse-time expansion and `%{...}` is used for
-run-time expansion. The difference between the two methods is that the
-`${...}` form is expanded when the server loads the configuration
-files and is valid anywhere in the configuration files. The `%{...}`
-link:xlat.adoc[string expansion] form is valid only in conditional
-expressions and attribute assignments.
-
-The output of the dynamic expansion can be interpreted as a string,
-a number, or an IP address, depending on its context.
-
-Note that the interpretation of text _strongly_ depends on the
-context. The text `"0000"` can be interpreted as a data type
-"integer", having value zero, or a data type "string", having value
-`"0000"`. In general when a particular piece of text is used, it is
-used with the context of a known attribute. That attribute has a
-link:data.adoc[data type], and the text will be interpreted as that
-data type.
-
-.Examples
-
-`"word"` +
-`"a string"` +
-`"this has embedded\ncharacters"`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/type/index.adoc b/doc/antora/modules/unlang/pages/type/index.adoc
deleted file mode 100644
index f26489b179..0000000000
--- a/doc/antora/modules/unlang/pages/type/index.adoc
+++ /dev/null
@@ -1,117 +0,0 @@
-= Data Types
-
-Unlang supports a number of data types. These data types are used in
-conditional expressions or when assigning a value to an attribute.
-
-== Using Data Types
-
-The server support a wide range of data types, as given in the
-xref:type/all_types.adoc[list of data types] page. The choice
-of which data type applies is determined by the context in which that
-data type is used. This context is usually taken from an attribute
-which is being assigned a value.
-
-The `unlang` interpreter uses pre-defined attributes which are defined
-in dictionaries. The dictionaries define both a name, and a data type
-for the attributes. In the interpreter, then, attributes can be
-assigned a value or compared to a value, without specifying the data
-type. The interpreter knows how to parse the value by using the data
-type assigned to the attribute.
-
-The result is that in most cases, it is not necessary to know the name
-of the data types. It is possible to write values in the format you
-expect, and he server will do "the right thing" when interpreting the
-values.
-
-.Attributes with Different Data Types
-[source,unlang]
-----
-Framed-IP-Address = 192.0.2.1
-Framed-IPv6-Address = 2001:db8::
-Reply-Message = "This is a reply"
-Port-Limit = 5
-Boolean = true
-Octets-Thing = 0xabcdef0102030405
-MAC-Address = 00:01:02:03:04:05
-----
-
-== Parsing Data Types
-
-The interpreter is flexible when parsing data types. So long as the
-value can be parsed as the given data type without error, the value
-will be accepted.
-
-For example, a particular attribute may be of data type `ipaddr` in
-order to store IPv4 addresses. The interpreter will then accept the
-following strings as valid IPv4 addresses:
-
-`192.168.0.2`:: xref:type/string/unquoted.adoc[Unquoted text], interpreted as the data type
-
-`'192.168.0.2'`:: xref:type/string/single.adoc[Single-quoted string], the contents of the string are parsed as the data type.
-+
-The single-quoted string form is most useful when the data type
-contains special characters that may otherwise confuse the parser.
-
-`"192.168.0.2"`:: xref:type/string/double.adoc[Double-quoted string].
-+
-The contents of the string are dynamically expanded as described in
-the xref:xlat/index.adoc[dynamic expansion] page. The
-resulting output is then interpreted as the given data type.
-
-`{backtick}/bin/echo 192.168.0.2{backtick}`:: xref:type/string/backticks.adoc[backtick-quoted string].
-Run a script, and parse the resulting string as the data type.
-
-Similar processing rules are applied when parsing assignments and
-comparisons, for all attributes and data types.
-
-=== Casting Data Types
-
-In some cases, it is necessary to parse values which do not refer to
-attributes. This situation usually occurs when two values need to be
-compared, as in the following example:
-
-[source,unlang]
-----
-if ("%{sql:SELECT ipaddress FROM table WHERE user=%{User-Name}}" == 192.0.2.1) }
- ....
-}
-----
-
-Since there is no attribute on either side of the `==` operator, the
-interpreter has no way of knowing that the string `192.0.2.1` is an IP
-address. There is unfortunately no way of automatically parsing
-strings in order to determine the data type to use. Any such
-automatic parsing would work most of the time, but it would have
-error cases where the parsing was incorrect.
-
-The solution is to resolve these ambiguities by allowing the values to
-be cast to a particular type. Casting a value to a type tells the
-interpreter how that value should be parsed. Casting is done by
-prefixing a value with the type name, surrounded by angle brackets;
-`<...>`.
-
-.Syntax
-----
-<...>value
-----
-
-We can add a cast to the above example, as follows:
-
-[source,unlang]
-----
-if ("%{sql:SELECT ipaddress FROM table WHERE user=%{User-Name}}" == <ipaddr>192.0.2.1) }
- ....
-}
-----
-
-In this example, we prefix the IP address with the string `<ipaddr>`.
-The interpreter then knows that the value `192.0.2.` should be
-interpreted as the data type `ipaddr`, and not as the literal string
-`"192.0.2."`.
-
-For a full list of data types which can be used in a cast, please see
-the xref:type/all_types.adoc[list of data types] page, and the
-"Basic Type Types" section.
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/type/ip.adoc b/doc/antora/modules/unlang/pages/type/ip.adoc
deleted file mode 100644
index fc25ae8eb2..0000000000
--- a/doc/antora/modules/unlang/pages/type/ip.adoc
+++ /dev/null
@@ -1,15 +0,0 @@
-= IP Addresses
-
-.Examples
-
-`192.0.2.16` +
-`::1` +
-`example.com`
-
-Depending on the context, a "simple word", as above, may be
-interpreted as an IPv4 or an IPv6 address. This interpretation is
-usually done when the string is used in the context of an attribute,
-or to compare two addresses or assign an address to an attribute.
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/type/numb.adoc b/doc/antora/modules/unlang/pages/type/numb.adoc
deleted file mode 100644
index 284cf819c1..0000000000
--- a/doc/antora/modules/unlang/pages/type/numb.adoc
+++ /dev/null
@@ -1,11 +0,0 @@
-= Numbers
-
-.Examples
-
-`0` +
-`563`
-
-Numbers are unsigned integers that are composed of decimal digits.
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/type/string/backticks.adoc b/doc/antora/modules/unlang/pages/type/string/backticks.adoc
deleted file mode 100644
index 9372b4c736..0000000000
--- a/doc/antora/modules/unlang/pages/type/string/backticks.adoc
+++ /dev/null
@@ -1,38 +0,0 @@
-= Backtick-quoted string
-
-.Syntax
-`{backtick}string{backtick}`
-
-The backtick operator is used to perform a run-time expansion
-similar to what is done with the Unix shell. The contents of the string
-are split into one or more sub-strings, based on intermediate
-whitespace. Each substring is then expanded as described above for
-double quoted strings. The resulting set of strings is used to execute a
-program with the associated arguments.
-
-The output of the program is recorded, and the resulting data is
-used in place of the input string value. Where the output is composed of
-multiple lines, any carriage returns and line feeds are replaced by
-spaces.
-
-For safety reasons, the full path to the executed program should be
-given. In addition, the string is split into arguments _before_ the
-substrings are dynamically expanded. This step is done both to allow
-the substrings to contain spaces, and to prevent spaces in the
-expanded substrings from affecting the number of command-line
-arguments.
-
-For performance reasons, we recommend that the use of back-quoted
-strings be kept to a minimum. Executing external programs is
-relatively expensive, and executing a large number of programs for
-every request can quickly use all of the CPU time in a server. If many
-programs need to be executed, it is suggested that alternative ways to
-achieve the same result be found. In some cases, using a real
-programming language such as `lua`, `perl` or `python` may be better.
-
-.Examples
-
-`{backtick}/bin/echo hello{backtick}`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/type/string/double.adoc b/doc/antora/modules/unlang/pages/type/string/double.adoc
deleted file mode 100644
index ea87bc5c45..0000000000
--- a/doc/antora/modules/unlang/pages/type/string/double.adoc
+++ /dev/null
@@ -1,68 +0,0 @@
-= Double Quoted Strings
-
-.Syntax
-`"string"`
-
-A double-quoted string allows escape sequences and xref:xlat/index.adoc[dynamic
-expansions]. As with xref:type/string/single.adoc[single-quoted strings], text
-within double quotes can include spaces.
-
-The main difference between the single and double quoted strings is
-that the double quoted strings can be dynamically expanded. The syntax
-`${...}` is used for parse-time expansion and `%{...}` is used for
-run-time expansion. The difference between the two methods is that the
-`${...}` form is expanded when the server loads the configuration
-files and is valid anywhere in the configuration files. The `%{...}`
-xref:xlat/index.adoc[string expansion] form is valid only in conditional
-expressions and attribute assignments.
-
-The output of the dynamic expansion can be interpreted as a string,
-a number, or an IP address, depending on its context.
-
-Note that the interpretation of text _strongly_ depends on the
-context. The text `"0000"` can be interpreted as a data type
-"integer", having value zero, or a data type "string", having value
-`"0000"`. In general when a particular piece of text is used, it is
-used with the context of a known attribute. That attribute has a
-xref:type/index.adoc[data type], and the text will be interpreted as that
-data type.
-
-NOTE: Most values retrieved from external datastores will be treated implicitly
-as double-quoted strings.
-
-== Escape sequences
-
-Escape sequences allow the inclusion of characters that may be difficult to
-represent in datastores, or the FreeRADIUS configuration files.
-
-.Escape sequences and their descriptions
-[options="header", cols="15%,85%"]
-|=====
-| Escape sequence | Character represented
-| `\\` | Literal backslash (0x5c)
-| `\r` | Carriage return (0x0d)
-| `\n` | Line feed (0x0a)
-| `\t` | Horizontal tab (0x09)
-| `\"` | Double quote (0x22)
-| `\x<hex><hex>` | A byte whose numerical value is given by `<hex><hex>` interpreted as a hexadecimal number.
-| `\x<oct><oct><oct>` | A byte whose numerical value is given by `<oct><oct><oct>` interpreted as an octal number.
-|=====
-
-.Examples
-
-`"word"` +
-`"a string"' +
-`"foo\"bar\""` +
-`"this is a long string"` +
-`"this has embedded\ncharacters"` +
-`"attribute\tvalue\nusername\t%{User-Name}\nreply-message\t%{reply.Reply-Message}"`
-`"The result of 'SELECT * FROM foo WHERE 1' is: %{sql:SELECT * FROM foo WHERE 1}"`
-
-// Licenced under CC-by-NC 4.0.
-// Copyright (C) 2019 Arran Cudbard-Bell <a.cudbardb@freeradius.org>
-// Copyright (C) 2019 The FreeRADIUS project.
-// Copyright (C) 2020 Network RADIUS SAS.
-
-
-
-
diff --git a/doc/antora/modules/unlang/pages/type/string/escaping.adoc b/doc/antora/modules/unlang/pages/type/string/escaping.adoc
deleted file mode 100644
index e63a498ce0..0000000000
--- a/doc/antora/modules/unlang/pages/type/string/escaping.adoc
+++ /dev/null
@@ -1,14 +0,0 @@
-= Character Escaping
-
-The quotation characters in the above string data types can be
-escaped by using the backslash, or `\,` character. The backslash
-character itself can be created by using `\\`. Carriage returns and
-line feeds can be created by using `\n` and `\r`.
-
-.Examples
-
-`"I say \"hello\" to you"` +
-`"This is split\nacross two lines"`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/type/string/single.adoc b/doc/antora/modules/unlang/pages/type/string/single.adoc
deleted file mode 100644
index fa2ac05255..0000000000
--- a/doc/antora/modules/unlang/pages/type/string/single.adoc
+++ /dev/null
@@ -1,19 +0,0 @@
-= Single Quoted Strings
-
-.Syntax
-`'string'`
-
-A single-quoted string is interpreted without any dynamic string
-expansion. The quotes allow the string to contain spaces, among other
-special characters. The single quote character can be placed in such a
-string by escaping it with a backslash.
-
-.Examples
-
-`'hello'` +
-`'foo bar`' +
-`'foo\\'bar'` +
-`'this is a long string'`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/type/string/unquoted.adoc b/doc/antora/modules/unlang/pages/type/string/unquoted.adoc
deleted file mode 100644
index 9dd6e557b7..0000000000
--- a/doc/antora/modules/unlang/pages/type/string/unquoted.adoc
+++ /dev/null
@@ -1,21 +0,0 @@
-= Unquoted Strings
-
-Where a series of characters cannot be parsed as a decimal number,
-they are interpreted as a simple string composed of one word. This
-word is delimited by spaces, or by other tokens, such as `)` in
-conditional expressions.
-
-This unquoted text is interpreted as simple strings and are generally
-equivalent to placing the string in single quotes.
-
-The interpretation of the text depends on the context, which is
-usually defined by an attribute which has a xref:type/index.adoc[data type].
-
-.Examples
-
-`Hello` +
-`192.168.0.1` +
-`00:01:02:03:04:05`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/update.adoc b/doc/antora/modules/unlang/pages/update.adoc
deleted file mode 100644
index 645f4d8aba..0000000000
--- a/doc/antora/modules/unlang/pages/update.adoc
+++ /dev/null
@@ -1,160 +0,0 @@
-= The update Statement
-
-.Syntax
-[source,unlang]
-----
-update [ <list> ] {
- <server-attribute> <op> <value>
- ...
-}
-----
-
-The `update` statement adds attributes to, or edits the attributes in,
-the named _<list>_.
-
-The `update` statement consists of the following syntax elements:
-
-<list>:: The attribute list which will be updated. The list is
-usually `request`, `reply`, or `control`.
-+
-If the _<list>_ qualifier is omitted, then each entry inside of the
-`update` section *must* be prefixed with a list name. For example,
-`&request.User-Name ...`
-
-<server-attribute>:: The server attribute which is assigned the
-_<value>_.
-
-<op>:: The operator such as `=`, `:=`, etc.
-
-<value>:: The value which is assigned to the attribute. If the field
-is a double-quoted string, it undergoes xref:xlat/index.adoc[string
-expansion], and the resulting value is assigned to the attribute.
-
-The update process is atomic, in that either all of the attributes are
-modified, or none of them are modified. If the `update` fails for any
-reason, then all of the results are discarded, and the `update` does
-not affect any server attributes.
-
-.Example
-[source,unlang]
-----
-update reply {
- &Reply-Message := "Hello!"
- &Framed-IP-Address := 192.0.2.4
-}
-----
-
-== Lists
-
-The _<list>_ field sets the attribute list that will be updated. If
-the _<list>_ qualifier is omitted, then each entry inside of the
-`update` section *must* be prefixed with a list name. For example,
-`&request.User-Name ...`
-
-Please see the xref:list.adoc[list] page for valid list names.
-
-== Server Attributes
-
-The _<server-attribute>_ field is an attribute name, such as
-`&Reply-Message`. The attribute name may also be prefixed with a
-_<list>_ qualifier, which overrides the _<list>_ given at the start
-of the `update` section.
-
-NOTE: In version 3, the leading `&` is optional but recommended.
-
-== Editing Operators
-
-The `<op>` field is used to define how the attribute is processed.
-Different operators allow attributes to be added, deleted, or
-replaced, as defined below.
-
-.Editing Operators
-[options="header"]
-[cols="10%,90%"]
-|=====
-| Operator | Description
-| = | Add the attribute to the list, if and only if an attribute of
-the same name is not already present in that list.
-| := | Add the attribute to the list. If any attribute of the same
-name is already present in that list, its value is replaced with the
-value of the current attribute.
-| += | Add the attribute to the tail of the list, even if attributes
-of the same name are already present in the list.
-| ^= | Add the attribute to the head of the list, even if attributes
-of the same name are already present in the list.
-| -= | Remove all attributes from the list that match _<value>_.
-| !* | Delete all occurances of the attribute, no matter what the value.
-|=====
-
-== Filtering Operators
-
-The following operators may also be used in addition to the ones
-listed above. These operators use the _<server-attribute>_ and
-_<value>_ fields to enforce limits on all attributes in the given
-_<list>_, and to edit attributes which have a matching
-_<server-attribute>_ name. All other attributes are ignored.
-
-.Filtering Operators
-[options="header]
-[cols="10%,90%"]
-|=====
-| Operator | Description
-| == | Keep only the attributes in the list that match _<value>_
-| < | Keep only the attributes in the list that have values less than _<value>_.
-| \<= | Keep only the attributes in the list that have values less than or equal to _<value>_.
-| > | Keep only the attributes in the list that have values greater than _<value>_.
-| >= | Keep only the attributes in the list that have values greater than or equal to _<value>_.
-| =~ | Keep only the attributes in the list which match the regular expression given in _<value>_.
-| !~ | Keep only the attributes in the list which do not match the regular expression given in _<value>_.
-|=====
-
-The `==` operator is very different from the `=` operator listed
-above. The `=` operator is used to add new attributes to the list,
-while the `==` operator removes all attributes that do not match the
-given value.
-
-The comparison operators `<`, `<=`, `>`, and `>=` have some additional
-side effects. Any non-matching value is replaced by the _<value>_
-given here. If no attribute exists, it is created with the given
-_<value>_.
-
-For IP addresses, the operators `>`, `>=`, `<`, and `\<=` check for
-membership in a network. The _<value>_ field should then be a IP
-network, given in `address/mask` format.
-
-.Example
-[source,unlang]
-----
-update reply {
- &Session-timeout := 86400
-}
-----
-
-.Example
-[source,unlang]
-----
-update reply {
- &Reply-Message += "Rejected: Also, realm does not end with ac.uk"
-}
-----
-
-== Values
-
-The _<value>_ field is the value which is assigned to the
-_<server-attribute>_. The interpretation of the _<value>_ field
-depends on the data type of the contents. For example, if the string
-`"192.0.2.1"` is assigned to an attribute of the `string` data type,
-then the result is an ASCII string containing that value. However, if
-the same string is assigned to an attribute of the `ipaddr` data type,
-then the result is a 32-bit IPv4 address, with binary value `0xc0000201`.
-
-.Example
-[source,unlang]
-----
-update reply {
- &Session-Timeout <= 3600
-}
-----
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/xlat/alternation.adoc b/doc/antora/modules/unlang/pages/xlat/alternation.adoc
deleted file mode 100644
index adb76043dd..0000000000
--- a/doc/antora/modules/unlang/pages/xlat/alternation.adoc
+++ /dev/null
@@ -1,24 +0,0 @@
-= Alternation Syntax
-
-Alternation syntax similar to that used in Unix shells may also be
-used:
-
-`%{%{Foo}:-bar}`
-
-This code returns the value of `%{Foo}`, if it has a value.
-Otherwise, it returns a literal string bar.
-
-`%{%{Foo}:-%{Bar}}`
-
-This code returns the value of `%{Foo}`, if it has a value.
-Otherwise, it returns the expansion of `%{Bar}`.
-
-These conditional expansions can be nested to almost any depth, such
-as with `%{%{One}:-%{%{Two}:-%{Three}}}`.
-
-.Examples
-`%{%{Stripped-User-Name}:-%{User-Name}}` +
-`%{%{Framed-IP-Address}:-<none>}`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/xlat/attribute.adoc b/doc/antora/modules/unlang/pages/xlat/attribute.adoc
deleted file mode 100644
index a3ee29bb06..0000000000
--- a/doc/antora/modules/unlang/pages/xlat/attribute.adoc
+++ /dev/null
@@ -1,54 +0,0 @@
-= Attribute References
-
-Attributes in a list may be referenced via one of the following two
-syntaxes:
-
-`%{Attribute-Name}` +
-`%{<list>:Attribute-Name}`
-
-The `<list>:` prefix is optional. If given, it must be a valid
-reference to an xref:list.adoc[attribute list].
-
-If the `<list>:` prefix is omitted, then the `request` list is
-assumed.
-
-For EAP methods with tunneled authentication sessions (i.e. PEAP and
-EAP-TTLS), the inner tunnel session can refer to a list for the outer
-session by prefixing the list name with `outer.` ; for example,
-`outer.request`.
-
-When a reference is encountered, the given list is examined for an
-attribute of the given name. If found, the variable reference in the
-string is replaced with the value of that attribute. Otherwise, the
-reference is replacedd with an empty string.
-
-.Examples
-
-`%{User-Name}` +
-`%{request.User-Name} # same as above` +
-`%{reply.User-Name}` +
-`%{outer.request.User-Name} # from inside of a TTLS/PEAP tunnel`
-
-Examples of using references inside of a string:
-
-`"Hello %{User-Name}"` +
-`"You, %{User-Name} are not allowed to use %{NAS-IP-Address}"`
-
-== Additional Variations
-
-`%{Attribute-Name[#]}`::
-Returns an integer containing the number of named attributes
-
-`%{Attribute-Name[0]}`::
-
-When an attribute appears multiple times in a list, this syntax allows
-you to address the attributes as with array entries. `[0]` refers to
-the first attributes, `[1]` refers to the second attribute, etc.
-
-`%{Attribute-Name[*]}`::
-
-Returns a comma-separated string containing all values for the named
-attributes.
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/xlat/builtin.adoc b/doc/antora/modules/unlang/pages/xlat/builtin.adoc
deleted file mode 100644
index 10d31482fc..0000000000
--- a/doc/antora/modules/unlang/pages/xlat/builtin.adoc
+++ /dev/null
@@ -1,891 +0,0 @@
-= Built-In Expansions
-
-In addition to storing attribute references, the server has a number
-of built-in expansions. These expansions act largely as functions
-which operate on inputs, and produce an output.
-
-
-
-== Attribute Manipulation
-
-=== %{length: ... }
-
-The `length` expansion returns the size of the input as an integer.
-When the input is a string, then the output is identical to the
-`strlen` expansion.
-
-When the input is an attribute reference, the output is the size of
-the attributes data as encoded "on the wire".
-
-.Return: _size_
-
-.Determining the length of fixed and variable length attributes
-====
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "Caipirinha"
- &Framed-IP-Address := 192.0.2.1
-}
-
-update reply {
- &Reply-Message := "The length of %{control:Tmp-String-0} is %{length:&control:Tmp-String-0}"
- &Reply-Message += "The length of %{control:Framed-IP-Address} is %{length:&control:Framed-IP-Address}"
-}
-----
-
-.Output
-....
-The length of Caipirinha is 10
-The length of 192.168.0.2 is 4
-....
-====
-
-`length` is built in to the server core.
-
-
-
-=== %{integer:<&ref>}
-
-Print the value of the attribute an integer.
-
-In normal operation, `integer` attributes are printed using the name
-given by a `VALUE` statement in a dictionary. Similarly, date
-attributes are printed as dates, i.e., "January 1 2010.
-
-The `integer` expansion applies only to attributes which can be
-converted to an integer. For all other inputs, it returns `0`.
-
-A common usage is to find the difference between two dates.
-
-For example, if a request contains `Service-Type = Login-User`, the
-expansion of `%{integer:&Service-Type}` will yield `1`, which is the
-value associated with the `Login-User` name. Using
-`%{integer:&Event-Timestamp}` will return the event timestamp as an
-unsigned 32-bit number.
-
-.Return: _string_
-
-.Determining the integer value of an enumerated attribute
-====
-[source,unlang]
-----
-update {
- &control:Service-Type := Login-User
-}
-update reply {
- &Reply-Message := "The value of Service-Type is %{integer:&control:Service-Type}"
-}
-----
-
-.Output
-
-```
-The value of Service-Type is 1
-```
-====
-
-`integer` is built in to the server core.
-
-
-
-=== %{rand:<number>}
-
-Generate random number from `0` to `<number>-1`.
-
-.Return: _uint64_
-
-.Generating a random number between 0 and 511
-====
-[source,unlang]
-----
-update reply {
- &Reply-Message := "The random number is %{rand:512}"
-}
-----
-
-.Output
-
-```
-The random number is 347
-```
-====
-
-`rand` is provided by the `rlm_expr` module.
-
-
-
-=== %{tag:<attribute ref>}
-
-CAUTION: This expansion is deprecated and will likely be removed.
-
-Returns a list of tags for any attributes found using ``<attribute ref>``.
-
-.Return: _int8_
-
-.Determining the tag value of the second instance of the `radius.Tunnel-Server-Endpoint` attribute
-====
-[source,unlang]
-----
-update request {
- &Tunnel-Server-Endpoint := '192.0.1.1'
- &Tunnel-Server-Endpoint:1 := '192.0.5.2'
- &Tunnel-Server-Endpoint:1 += '192.0.3.8'
- &Tunnel-Server-Endpoint:2 := '192.0.2.1'
- &Tunnel-Server-Endpoint:2 += '192.0.3.4'
-}
-
-update reply {
- &Reply-Message := "The tag value of the second instance of Tunnel-Server-Enpoint is %{request:Tunnel-Server-Endpoint[1]}"
-}
-----
-
-.Output
-
-```
-The tag value of the second instance of Tunnel-Server-Enpoint is 192.0.5.2
-```
-====
-
-`tag` is built in to the server core.
-
-
-
-=== %{string:<data>}
-
-Convert input to a string (if possible). For _octets_ type attributes, this
-means interpreting the data as a UTF8 string, and inserting octal escape
-sequences where appropriate.
-
-For other types, this means printing the value in its _presentation_ format,
-i.e. dotted quads for IPv4 addresses, link:https://en.wikipedia.org/wiki/ISO_8601[ISO 8601]
-time for date types, enumeration values for attributes such as `radius.Service-Type` etc.
-
-.Return: _string_
-
-.String interpolation using the raw octets value of Tmp-Octets-0, and the stringified version
-====
-[source,unlang]
-----
-update control {
- &Tmp-Octets-0 := 0x7465737431
-}
-update reply {
- &Reply-Message := "The string value of %{control:Tmp-Octets-0} is %{string:%{control:Tmp-Octets-0}}"
-}
-----
-====
-
-.Output
-
-```
-The string value of 0x7465737431 is test1
-```
-
-`string` is built in to the server core.
-
-
-
-== Server Manipulation
-
-=== %{config:<key>}
-
-Refers to a variable in the configuration file. See the documentation
-on configuration file references.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-"Server installed in %{config:prefix}"
-"Module rlm_exec.shell_escape = %{config:modules.exec.shell_escape}"
-----
-
-.Output
-
-```
-Server installed in /opt/freeradius
-Module rlm_exec.shell_escape = yes
-```
-
-`config` is built in to the server core.
-
-
-
-=== %{client:<key>}
-
-Refers to a variable that was defined in the client section for the
-current client. See the sections `client { ... }` in `clients.conf`.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-"The client ipaddr is %{client:ipaddr}"
-----
-
-.Output
-
-```
-The client ipaddr is 192.168.5.9
-```
-
-`client` is built in to the server core.
-
-
-
-=== %{debug:<level>}
-
-Dynamically change the debug level to something high, recording the old level.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-authorize {
- if (&request:User-Name == "bob") {
- "%{debug:4}"
- } else {
- "%{debug:0}"
- }
- ...
-}
-----
-
-.Output (_extra informations only for that condition_)
-
-```
-...
-(0) authorize {
-(0) if (&request:User-Name == "bob") {
-(0) EXPAND %{debug:4}
-(0) --> 2
-(0) } # if (&request:User-Name == "bob") (...)
-(0) filter_username {
-(0) if (&State) {
-(0) ...
-(0) }
-...
-```
-
-`debug` is built in to the server core.
-
-
-
-=== %{debug_attr:<list:[index]>}
-
-Print to debug output all instances of current attribute, or all attributes in a list.
-expands to a zero-length string.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-authorize {
- if (&request:User-Name == "bob") {
- "%{debug_attr:request[*]}"
- }
- ...
-}
-----
-
-.Output
-
-```
-...
-(0) authorize {
-(0) if (&request:User-Name == "bob") {
-(0) Attributes matching "request[*]"
-(0) &request:User-Name = bob
-(0) &request:User-Password = hello
-(0) &request:NAS-IP-Address = 127.0.1.1
-(0) &request:NAS-Port = 1
-(0) &request:Message-Authenticator = 0x9210ee447a9f4c522f5300eb8fc15e14
-(0) EXPAND %{debug_attr:request[*]}
-(0) } # if (&request:User-Name == "bob") (...)
-...
-```
-
-`debug_attr` is built in to the server core.
-
-
-
-== String manipulation
-
-=== %{lpad:<&ref> <val> <char>}
-
-Left-pad a string.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "123"
-}
-update reply {
- &Reply-Message := "Maximum should be %{lpad:&control:Tmp-String-0 11 0}"
-}
-----
-
-.Output
-
-```
-Maximum should be 00000000123
-```
-
-`lpad` is provided by the `rlm_expr` module.
-
-
-
-=== %{rpad:<&ref> <val> <char>}
-
-Right-pad a string.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "123"
-}
-update reply {
- &Reply-Message := "Maximum should be %{rpad:&control:Tmp-String-0 11 0}"
-}
-----
-
-.Output
-
-```
-Maximum should be 12300000000
-```
-
-`rpad` is provided by the `rlm_expr` module.
-
-
-
-=== %{pairs:<&list:[*]>}
-
-Serialize attributes as comma-delimited string.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update {
- &control:Tmp-String-0 := "This is a string"
- &control:Tmp-String-0 += "This is another one"
-}
-
-update reply {
- &Reply-Message := "Serialize output: %{pairs:&control[*]}"
-}
-----
-
-.Output
-
-```
-Serialize output: Tmp-String-0 = \"This is a string\"Tmp-String-0 = \"This is another one\"
-```
-
-`pairs` is provided by the `rlm_expr` module.
-
-
-
-=== %{randstr: ...}
-
-Get random string built from character classes.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update reply {
- &Reply-Message := "The random string output is %{randstr:aaaaaaaa}"
-}
-----
-
-.Output
-
-```
-The random string output is 4Uq0gPyG
-```
-
-`randstr` is provided by the `rlm_expr` module.
-
-
-
-=== %{strlen: ... }
-
-Length of given string.
-
-.Return: _integer_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "Caipirinha"
-}
-update reply {
- &Reply-Message := "The length of %{control:Tmp-String-0} is %{strlen:&control:Tmp-String-0}"
-}
-----
-
-.Output
-
-```
-The length of Caipirinha is 21
-```
-
-`strlen` is built in to the server core.
-
-
-
-=== %{tolower: ... }
-
-Dynamically expands the string and returns the lowercase version of
-it. This definition is only available in version 2.1.10 and later.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "CAIPIRINHA"
-}
-update reply {
- &Reply-Message := "tolower of %{control:Tmp-String-0} is %{tolower:%{control:Tmp-String-0}}"
-}
-----
-
-.Output
-
-```
-tolower of CAIPIRINHA is caipirinha
-```
-
-`tolower` is provided by the `rlm_expr` module.
-
-
-
-=== %{toupper: ... }
-
-Dynamically expands the string and returns the uppercase version of
-it. This definition is only available in version 2.1.10 and later.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "caipirinha"
-}
-update reply {
- &Reply-Message := "toupper of %{control:Tmp-String-0} is %{toupper:%{control:Tmp-String-0}}"
-}
-----
-
-.Output
-
-```
-toupper of caipirinha is CAIPIRINHA
-```
-
-`toupper` is provided by the `rlm_expr` module.
-
-
-
-== String Conversion
-
-=== %{base64: ... }
-
-Encode a string using Base64.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "Caipirinha"
-}
-update reply {
- &Reply-Message := "The base64 of %{control:Tmp-String-0} is %{base64:%{control:Tmp-String-0}}"
-}
-----
-
-.Output
-
-```
-The base64 of foo is Q2FpcGlyaW5oYQ==
-```
-
-`base64` is provided by the `rlm_expr` module.
-
-
-
-=== %{base64tohex: ... }
-
-Decode a base64 string (e.g. previously encoded using `base64`) to
-hex.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "Q2FpcGlyaW5oYQ=="
-}
-update reply {
- &Reply-Message := "The base64tohex of %{control:Tmp-String-0} is %{base64tohex:%{control:Tmp-String-0}}"
-}
-----
-
-.Output
-
-```
-The base64decode of Q2FpcGlyaW5oYQ== is 436169706972696e6861
-```
-
-`base64tohex` is provided by the `rlm_expr` module.
-
-
-
-=== %{hex: ... }
-
-Convert to hex.
-
-.Return: _string_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "12345"
-}
-update reply {
- &Reply-Message := "The value of %{control:Tmp-String-0} in hex is %{hex:%{control:Tmp-String-0}}"
-}
-----
-
-.Output
-
-```
-The value of 12345 in hex is 3132333435
-```
-
-`hex` is built in to the server core.
-
-
-
-=== %{urlquote: ... }
-
-Quote URL special characters.
-
-.Return: _string_.
-
-.Example
-
-[source,unlang]
-----
-update {
- &control:Tmp-String-0 := "http://example.org/"
-}
-update reply {
- &Reply-Message += "The urlquote of %{control:Tmp-String-0} is %{urlquote:%{control:Tmp-String-0}}"
-}
-----
-
-.Output
-
-```
-The urlquote of http://example.org/ is http%3A%2F%2Fexample.org%2F
-```
-
-`urlquote` is provided by the `rlm_expr` module.
-
-
-
-=== %{urlunquote: ... }
-
-Unquote URL special characters.
-
-.Return: _string_.
-
-.Example
-
-[source,unlang]
-----
-update {
- &control:Tmp-String-0 := "http%%3A%%2F%%2Fexample.org%%2F" # Attention for the double %.
-}
-update reply {
- &Reply-Message += "The urlunquote of %{control:Tmp-String-0} is %{urlunquote:%{control:Tmp-String-0}}"
-}
-----
-
-.Output
-
-```
-The urlunquote of http%3A%2F%2Fexample.org%2F is http://example.org/
-```
-
-`urlunquote` is provided by the `rlm_expr` module.
-
-
-
-== Hashing and Encryption
-
-=== %{hmacmd5:<shared_key> <string>}
-
-Generate `HMAC-MD5` of string.
-
-.Return: _octal_
-
-.Example
-
-[source,unlang]
-----
-update {
- &control:Tmp-String-0 := "mykey"
- &control:Tmp-String-1 := "Caipirinha"
-}
-update {
- &control:Tmp-Octets-0 := "%{hmacmd5:%{control:Tmp-String-0} %{control:Tmp-String-1}}"
-}
-
-update reply {
- &Reply-Message := "The HMAC-MD5 of %{control:Tmp-String-1} in octets is %{control:Tmp-Octets-0}"
- &Reply-Message += "The HMAC-MD5 of %{control:Tmp-String-1} in hex is %{hex:control:Tmp-Octets-0}"
-}
-----
-
-.Output
-
-```
-The HMAC-MD5 of Caipirinha in octets is \317}\264@K\216\371\035\304\367\202,c\376\341\203
-The HMAC-MD5 of Caipirinha in hex is 636f6e74726f6c3a546d702d4f63746574732d30
-```
-
-`hmacmd5` is provided by the `rlm_expr` module.
-
-
-
-=== %{hmacsha1:<shared_key> <string>}
-
-Generate `HMAC-SHA1` of string.
-
-.Return: _octal_
-
-.Example
-
-[source,unlang]
-----
-update {
- &control:Tmp-String-0 := "mykey"
- &control:Tmp-String-1 := "Caipirinha"
-}
-update {
- &control:Tmp-Octets-0 := "%{hmacsha1:%{control:Tmp-String-0} %{control:Tmp-String-1}}"
-}
-
-update reply {
- &Reply-Message := "The HMAC-SHA1 of %{control:Tmp-String-1} in octets is %{control:Tmp-Octets-0}"
- &Reply-Message += "The HMAC-SHA1 of %{control:Tmp-String-1} in hex is %{hex:control:Tmp-Octets-0}"
-}
-----
-
-.Output
-
-```
-The HMAC-SHA1 of Caipirinha in octets is \311\007\212\234j\355\207\035\225\256\372ʙ>R\"\341\351O)
-The HMAC-SHA1 of Caipirinha in hex is 636f6e74726f6c3a546d702d4f63746574732d30
-```
-
-`hmacsha1` is provided by the `rlm_expr` module.
-
-
-
-=== %{md5: ... }
-
-Dynamically expands the string and performs an MD5 hash on it. The
-result is binary data.
-
-.Return: _binary data_
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "Caipirinha"
-}
-update reply {
- &Reply-Message := "md5 of %{control:Tmp-String-0} is octal=%{md5:%{control:Tmp-String-0}}"
- &Reply-Message := "md5 of %{control:Tmp-String-0} is hex=%{hex:%{md5:%{control:Tmp-String-0}}}"
-}
-----
-
-.Output
-
-```
-md5 of Caipirinha is octal=\024\204\013md||\230\243\3472\3703\330n\251
-md5 of Caipirinha is hex=14840b6d647c7c98a3e732f833d86ea9
-```
-
-`md5` is provided by the `rlm_expr` module.
-
-
-
-== Miscellaneous Expansions
-
-=== +%{0}+..+%{32}+
-
-`%{0}` expands to the portion of the subject that matched the last regular
-expression evaluated. `%{1}`..`%{32}` expand to the contents of any capture
-groups in the pattern.
-
-Every time a regular expression is evaluated, whether it matches or not,
-the numbered capture group values will be cleared.
-
-
-
-=== +%{regex:<named capture group>}+
-
-Return named subcapture value from the last regular expression evaluated.
-
-Results of named capture groups are available using the `%{regex:<named capture
-group>}` expansion. They will also be accessible using the numbered expansions
-described xref:#_0_32[above].
-
-Every time a regular expression is evaluated, whether it matches or not,
-the named capture group values will be cleared.
-
-[NOTE]
-====
-This expansion is only available if the server is built with libpcre or libpcre2.
-Use the output of `radiusd -Xxv` to determine which regular expression library in use.
-
-....
-...
-Debug : regex-pcre : no
-Debug : regex-pcre2 : yes
-Debug : regex-posix : no
-Debug : regex-posix-extended : no
-Debug : regex-binsafe : yes
-...
-Debug : pcre2 : 10.33 (2019-04-16) - retrieved at build time
-....
-====
-
-`regex` is built in to the server core.
-
-
-
-=== +%{nexttime:<time>}+
-
-Calculate number of seconds until next n hour(`s`), day(`s`), week(`s`), year(`s`).
-
-.Return: _string_
-
-.Example:
-
-With the current time at 16:18, `%{nexttime:1h}` will expand to `2520`.
-
-[source,unlang]
-----
-update reply {
- &Reply-Message := "You should wait for %{nexttime:1h}s"
-}
-----
-
-.Output
-
-```
-You should wait for 2520s
-```
-
-`nexttime` is provided by the `rlm_expr` module.
-
-
-
-=== +%{Packet-Type}+
-
-The packet type (`Access-Request`, etc.)
-
-
-
-=== +%{Packet-Src-IP-Address} and %{Packet-Src-IPv6-Address}+
-
-The source IPv4 or IPv6 address of the packet. See also the expansions
-`%{client:ipaddr}` and `%{client:ipv6addr}`. The two expansions
-should be identical, unless `%{client:ipaddr}` contains a DNS hostname.
-
-
-
-=== +%{Packet-Dst-IP-Address} and %{Packet-Dst-IPv6-Address}+
-
-The destination IPv4 or IPv6 address of the packet. See also the
-expansions `%{listen:ipaddr}` and `%{listen:ipv6addr}`. If the socket
-is listening on a "wildcard" address, then these two expansions will be
-different, as follows: the `%{listen:ipaddr}` will be the wildcard
-address and `%{Packet-DST-IP-Address}` will be the unicast address to
-which the packet was sent.
-
-
-
-=== +%{Packet-Src-Port} and %{Packet-Dst-Port}+
-
-The source/destination ports associated with the packet.
-
-.Return: _string_.
-
-.Example
-
-[source,unlang]
-----
-update control {
- &Tmp-String-0 := "user@example.com"
-}
-
-if (&control:Tmp-String-0 =~ /^(?<login>(.*))@(?<domain>(.*))$/) {
- update reply {
- &Reply-Message := "The %{control:Tmp-String-0} { login=%{regex:login}, domain=%{regex:domain} }"
- }
-}
-----
-
-.Output
-
-```
-The user@example.com { login=user, domain=example.com }
-```
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/xlat/character.adoc b/doc/antora/modules/unlang/pages/xlat/character.adoc
deleted file mode 100644
index 84a148cf1b..0000000000
--- a/doc/antora/modules/unlang/pages/xlat/character.adoc
+++ /dev/null
@@ -1,80 +0,0 @@
-= Single Letter Expansions
-
-The following are single letter expansions. These expansions do not
-use the typical `%{...}` format. Instead, they are short-cuts for
-simple, common cases.
-
-== Miscellaneous
-
-`%%`::
-
-Returns `%`.
-
-
-== Current Time
-
-`%c`::
-
-The current Unix epoch time in seconds. This is an unsigned decimal number.
-It should be used with time-based calculations.
-
-`%C`::
-
-The microsecond component of the current epoch time. This is an unsigned
-decimal number. It should be used with time-based calculations.
-
-
-== Request Time
-
-`%l`::
-
-The Unix timestamp of when the request was received. This is an unsigned
-decimal number. It should be used with time-based calculations.
-
-`%Y`::
-
-Four-digit year when the request was received.
-
-`%m`::
-
-Numeric month when the request was received.
-
-`%d`::
-
-Numeric day of the month when the request was received.
-
-`%H`::
-
-Hour of the day when the request was received.
-
-`%G`::
-
-Minute component of the time when the request was received.
-
-`%e`::
-
-Second component of the time when the request was received.
-
-`%M`::
-
-Microsecond component of the time when the request was received.
-
-`%D`::
-
-Request date in the format `YYYYMMDD`.
-
-`%S`::
-
-Request timestamp in SQL format, `YYYY-mmm-ddd HH:MM:SS`.
-
-`%t`::
-
-Request timestamp in _ctime_ format, `Www Mmm dd HH:MM:SS YYYY`.
-
-`%T`::
-
-Request timestamp in ISO format, `YYYY-mm-ddTHH:MM:SS.000`.
-
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/xlat/index.adoc b/doc/antora/modules/unlang/pages/xlat/index.adoc
deleted file mode 100644
index b42f725e6e..0000000000
--- a/doc/antora/modules/unlang/pages/xlat/index.adoc
+++ /dev/null
@@ -1,56 +0,0 @@
-= String Expansion
-
-String expansion is a feature that allows strings to dynamically
-define their value at run time. For historical reasons, these string
-expansions are called "xlats".
-
-String expansion is performed via the following syntax:
-
-`%{...}`
-
-Where the `%{` signals the start of a dynamic expansion, and `}`
-signals the end of the dynamic expansion. The contents of the
-expansion can be many things:
-
-.String Expansions
-[options="header"]
-|=====
-| Keyword | Description
-| xref:xlat/attribute.adoc[attributes] | Expand the value of a named attribute.
-| xref:xlat/character.adoc[single character] | Single character expansions.
-| xref:xlat/module.adoc[modules] | Pass a string to a module such as `sql`.
-| xref:xlat/alternation.adoc[condition] | Conditionally expand a string.
-| xref:xlat/builtin.adoc[built-in expansions] | Such as string length, tolower, etc...
-|=====
-
-This feature is used to create policies which refer to concepts rather
-than to specific values. For example, a policy can be created that
-refers to the User-Name in a request, via:
-
-`%{User-Name}`
-
-This string expansion is done only for double-quoted strings and for
-the back-tick operator.
-
-== Caveats
-
-Unlike other languages, there is no way to define new variables. All
-of the string expansions must refer to attributes that already exist,
-or to modules that will return a string value.
-
-== Character Escaping
-
-Some characters need to be escaped within a dynamically expanded
-string `%{...}`. The `%` character is used for variable expansion, so a
-literal `%` character can be created by using `%%`.
-
-Other than within a dynamically expanded string, very little
-character escaping is needed. The rules of the enclosing string context
-determine whether or not a space or " character needs to be escaped.
-
-.Example
-
-`Reply-Message := "%{User-Name} with a literal %%`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/pages/xlat/module.adoc b/doc/antora/modules/unlang/pages/xlat/module.adoc
deleted file mode 100644
index 3ce43228b1..0000000000
--- a/doc/antora/modules/unlang/pages/xlat/module.adoc
+++ /dev/null
@@ -1,18 +0,0 @@
-= Module References
-
-Individual modules may be referenced via the following syntax:
-
-`%{module:string}`
-
-These references are allowed only by a small number of modules that
-usually perform database lookups. The module name is the actual name of
-the module, as described earlier. The string portion is specific to each
-module and is not documented here. It is, however, usually dynamically
-expanded to allow for additional flexibility.
-
-.Examples
-
-`%{sql:SELECT name FROM mytable WHERE username = %{User-Name}}`
-
-// Copyright (C) 2020 Network RADIUS SAS. Licenced under CC-by-NC 4.0.
-// Development of this documentation was sponsored by Network RADIUS SAS.
diff --git a/doc/antora/modules/unlang/partials/rcode_table.adoc b/doc/antora/modules/unlang/partials/rcode_table.adoc
deleted file mode 100644
index e114e74507..0000000000
--- a/doc/antora/modules/unlang/partials/rcode_table.adoc
+++ /dev/null
@@ -1,39 +0,0 @@
-[options="header"]
-[cols="15%,85%"]
-|=====
-| Return code | Description
-| `fail` | The operation failed. Usually as a result of an
- external dependency like a database being unavailable
- or an internal error.
-| `handled` | The request has been "handled", no further policies
- in the current section should be called, and the section
- should immediately exit.
-| `invalid` | The request, or operation, was invalid. In the case of
- requests this usually indicates absent or malformed
- attribute values.
-| `noop` | The operation did nothing.
-| `notfound` | A 'lookup' operation returned no results.
-| `ok` | Operation completed successfully but did not change any
- attributes in the request.
-| `reject` | The operation indicates the current request should be
- 'rejected'. What this actually means is different from
- protocol to protocol. It usually means that access to
- the requested resource should be denied, or that the
- current request should be NAKd. Usually returned when
- provided credentials were invalid.
-| `updated` | The operation completed successfully and updated one
- or more attributes in the request.
-| `disallow` | Access to a particular resource is
- denied. This is similar to `reject` but is the result
- of an authorizational check failing, as opposed to
- credentials being incorrect.
-| `yield` | Returned by an operation when execution of a request should
- be suspended.
-|=====
-
-[NOTE]
-====
-In versions ≤ v3.0.x the `disallow` rcode was called `userlock`. `disallow` and
-`userlock` have an identical meaning. `disallow` will be returned in any
-instance where `userlock` was returned in v3.0.x
-====