On Thu, Mar 02, 2023 at 09:31:57AM -0700, Theo de Raadt wrote:
> Using a global variable like that is poor style.
OK, I'm gonna give it one more attempt:
In RFC 2865 there is no auth code for discarding a message but there is a
255 reserved value which we may be able to use as a hack. Refer to page
14 of RFC 2865.
The updated patch then returns from rad_recv() with that 255 and is caught
in the switch/case, and executes with a following goto retry.
Again I don't have a test network for this.
Best Regards,
-peter
Index: raddauth.c
===================================================================
RCS file: /cvs/src/libexec/login_radius/raddauth.c,v
retrieving revision 1.30
diff -u -p -u -r1.30 raddauth.c
--- raddauth.c 28 Jun 2019 13:32:53 -0000 1.30
+++ raddauth.c 2 Mar 2023 16:46:37 -0000
@@ -105,6 +105,7 @@
#define PW_CLIENT_PORT_ID 5
#define PW_PORT_MESSAGE 18
#define PW_STATE 24
+#define PW_SILENT_DISCARD 255 /* Reserved in RFC 2865 */
#ifndef RADIUS_DIR
#define RADIUS_DIR "/etc/raddb"
@@ -324,6 +325,10 @@ retry:
passwd = "";
break;
+ case PW_SILENT_DISCARD:
+ goto retry;
+ break;
+
default:
if (timedout)
goto retry;
@@ -451,17 +456,22 @@ rad_recv(char *state, char *challenge, u
struct sockaddr_in sin;
u_char recv_vector[AUTH_VECTOR_LEN], test_vector[AUTH_VECTOR_LEN];
MD5_CTX context;
+ ssize_t total_length;
salen = sizeof(sin);
alarm(timeout);
- if ((recvfrom(sockfd, &auth, sizeof(auth), 0,
- (struct sockaddr *)&sin, &salen)) < AUTH_HDR_LEN) {
+ total_length = recvfrom(sockfd, &auth, sizeof(auth), 0,
+ (struct sockaddr *)&sin, &salen);
+ alarm(0);
+ if (total_length < AUTH_HDR_LEN) {
if (timedout)
return(-1);
errx(1, "bogus auth packet from server");
}
- alarm(0);
+ if (ntohs(auth.length) > total_length) {
+ return (PW_SILENT_DISCARD);
+ }
if (sin.sin_addr.s_addr != auth_server)
errx(1, "bogus authentication server");