From 7bf791816c7e6dbae19149ac6c31c49095d4b9b0 Mon Sep 17 00:00:00 2001 From: Samuel Thibault Date: Sun, 26 Mar 2023 18:01:00 +0200 Subject: [PATCH] Fix the password used when acting as LAC When acting as LNS, we have to answer challenges with our own secret, but when acting as LAC, we have to answer challenges with the LNS secret, not ours. --- l2tplac.c | 15 +++++++++++++++ l2tplac.h | 1 + l2tpns.c | 40 ++++++++++++++++++++++++++++------------ 3 files changed, 44 insertions(+), 12 deletions(-) diff --git a/l2tplac.c b/l2tplac.c index 4140258..8be2261 100644 --- a/l2tplac.c +++ b/l2tplac.c @@ -451,6 +451,21 @@ void lac_calc_rlns_auth(tunnelidt t, uint8_t id, uint8_t *out) MD5_Final(out, &ctx); } +// Calcul our LNS auth +void lac_calc_our_auth(tunnelidt t, uint8_t *challenge, uint8_t id, uint16_t challenge_length, uint8_t *out) +{ + MD5_CTX ctx; + confrlnsidt idrlns; + + idrlns = tunnel[t].isremotelns; + + MD5_Init(&ctx); + MD5_Update(&ctx, &id, 1); + MD5_Update(&ctx, pconfigrlns[idrlns].l2tp_secret, strlen(pconfigrlns[idrlns].l2tp_secret)); + MD5_Update(&ctx, challenge, challenge_length); + MD5_Final(out, &ctx); +} + // Forward session to LAC or Remote LNS int lac_session_forward(uint8_t *buf, int len, sessionidt sess, uint16_t proto, in_addr_t s_addr, int sin_port, uint16_t indexudpfd) { diff --git a/l2tplac.h b/l2tplac.h index a7ae905..b755bdb 100644 --- a/l2tplac.h +++ b/l2tplac.h @@ -15,6 +15,7 @@ void lac_initremotelnsdata(); int lac_session_forward(uint8_t *buf, int len, sessionidt sess, uint16_t proto, in_addr_t s_addr, int sin_port, uint16_t indexudpfd); int lac_conf_forwardtoremotelns(sessionidt s, char * puser); void lac_calc_rlns_auth(tunnelidt t, uint8_t id, uint8_t *out); +void lac_calc_our_auth(tunnelidt t, uint8_t *challenge, uint8_t id, uint16_t challenge_length, uint8_t *out); int lac_addremotelns(char *mask, char *IP_RemoteLNS, char *Port_RemoteLNS, char *SecretRemoteLNS); /* Function for Tunnels creating from radius responses */ diff --git a/l2tpns.c b/l2tpns.c index 3d722e5..44b8cfc 100644 --- a/l2tpns.c +++ b/l2tpns.c @@ -249,7 +249,7 @@ static void dump_acct_info(int all); static void sighup_handler(int sig); static void shutdown_handler(int sig); static void sigchild_handler(int sig); -static void build_chap_response(uint8_t *challenge, uint8_t id, uint16_t challenge_length, uint8_t **challenge_response); +static void build_chap_response(uint16_t t, uint8_t *challenge, uint8_t id, uint16_t challenge_length, int we_are_lac, uint8_t **challenge_response); static void update_config(void); static void read_config_file(void); static void initplugins(void); @@ -2887,11 +2887,18 @@ void processudp(uint8_t *buf, int len, struct sockaddr_in *addr, uint16_t indexu break; case 11: // Request Challenge { - LOG(4, s, t, " LAC requested CHAP authentication for tunnel\n"); if (message == 1) - build_chap_response(b, 2, n, &sendchalresponse); + { + LOG(4, s, t, " LAC requested CHAP authentication for tunnel\n"); + // We are LNS + build_chap_response(t, b, 2, n, 0, &sendchalresponse); + } else if (message == 2) - build_chap_response(b, 3, n, &sendchalresponse); + { + LOG(4, s, t, " LNS requested CHAP authentication for tunnel\n"); + // We are LAC + build_chap_response(t, b, 3, n, 1, &sendchalresponse); + } } break; case 13: // receive challenge Response @@ -5306,14 +5313,14 @@ static void sigchild_handler(int sig) ; } -static void build_chap_response(uint8_t *challenge, uint8_t id, uint16_t challenge_length, uint8_t **challenge_response) +static void build_chap_response(uint16_t t, uint8_t *challenge, uint8_t id, uint16_t challenge_length, int we_are_lac, uint8_t **challenge_response) { MD5_CTX ctx; *challenge_response = NULL; - if (!*config->l2tp_secret) + if (!we_are_lac && !*config->l2tp_secret) { - LOG(0, 0, 0, "LNS requested CHAP authentication, but no l2tp secret is defined\n"); + LOG(0, 0, 0, "LAC requested CHAP authentication, but no l2tp secret is defined\n"); return; } @@ -5321,11 +5328,20 @@ static void build_chap_response(uint8_t *challenge, uint8_t id, uint16_t challen *challenge_response = calloc(17, 1); - MD5_Init(&ctx); - MD5_Update(&ctx, &id, 1); - MD5_Update(&ctx, config->l2tp_secret, strlen(config->l2tp_secret)); - MD5_Update(&ctx, challenge, challenge_length); - MD5_Final(*challenge_response, &ctx); + if (we_are_lac) + { + // Use the LNS secret + lac_calc_our_auth(t, challenge, id, challenge_length, *challenge_response); + } + else + { + // Use our LNS secret + MD5_Init(&ctx); + MD5_Update(&ctx, &id, 1); + MD5_Update(&ctx, config->l2tp_secret, strlen(config->l2tp_secret)); + MD5_Update(&ctx, challenge, challenge_length); + MD5_Final(*challenge_response, &ctx); + } return; }