summaryrefslogtreecommitdiff
path: root/accel-pppd/auth
diff options
context:
space:
mode:
authorDmitry Kozlov <xeb@mail.ru>2014-09-20 12:18:49 +0400
committerDmitry Kozlov <xeb@mail.ru>2014-09-20 12:18:49 +0400
commit62e89248160d3592c2d754fcaa15e37586a5b091 (patch)
treea6513cfd1e8ef6c6079ea2436e8573b122cc1ec6 /accel-pppd/auth
parent0a58c20b44136c1fba996becea18696b3f67a1f9 (diff)
downloadaccel-ppp-62e89248160d3592c2d754fcaa15e37586a5b091.tar.gz
accel-ppp-62e89248160d3592c2d754fcaa15e37586a5b091.zip
rewrite of authentication/accounting procedures
This patch gets rid of synchronuos style of authentication/accounting. Synchronous style of authentication/accounting produced sleeping threads which becomes a problem when lots of sessions started/stopped and all they want authorization/accounting.
Diffstat (limited to 'accel-pppd/auth')
-rw-r--r--accel-pppd/auth/auth_chap_md5.c101
-rw-r--r--accel-pppd/auth/auth_mschap_v1.c126
-rw-r--r--accel-pppd/auth/auth_mschap_v2.c142
-rw-r--r--accel-pppd/auth/auth_pap.c91
4 files changed, 330 insertions, 130 deletions
diff --git a/accel-pppd/auth/auth_chap_md5.c b/accel-pppd/auth/auth_chap_md5.c
index 9a52581c..5be8b875 100644
--- a/accel-pppd/auth/auth_chap_md5.c
+++ b/accel-pppd/auth/auth_chap_md5.c
@@ -30,39 +30,39 @@
#define MSG_FAILURE "Authentication failed"
#define MSG_SUCCESS "Authentication succeeded"
-#define HDR_LEN (sizeof(struct chap_hdr_t)-2)
+#define HDR_LEN (sizeof(struct chap_hdr)-2)
static int conf_timeout = 5;
static int conf_interval = 0;
static int conf_max_failure = 3;
static int conf_any_login = 0;
-struct chap_hdr_t {
+struct chap_hdr {
uint16_t proto;
uint8_t code;
uint8_t id;
uint16_t len;
} __attribute__((packed));
-struct chap_challenge_t {
- struct chap_hdr_t hdr;
+struct chap_challenge {
+ struct chap_hdr hdr;
uint8_t val_size;
uint8_t val[VALUE_SIZE];
char name[0];
} __attribute__((packed));
-struct chap_failure_t {
- struct chap_hdr_t hdr;
+struct chap_failure {
+ struct chap_hdr hdr;
char message[sizeof(MSG_FAILURE)];
} __attribute__((packed));
-struct chap_success_t {
- struct chap_hdr_t hdr;
+struct chap_success {
+ struct chap_hdr hdr;
char message[sizeof(MSG_SUCCESS)];
} __attribute__((packed));
-struct chap_auth_data_t {
+struct chap_auth_data {
struct auth_data_t auth;
struct ppp_handler_t h;
struct ppp_t *ppp;
@@ -71,10 +71,12 @@ struct chap_auth_data_t {
struct triton_timer_t timeout;
struct triton_timer_t interval;
int failure;
+ char *name;
+ char *mschap_error;
int started:1;
};
-static void chap_send_challenge(struct chap_auth_data_t *ad, int new);
+static void chap_send_challenge(struct chap_auth_data *ad, int new);
static void chap_recv(struct ppp_handler_t *h);
static void chap_timeout_timer(struct triton_timer_t *t);
static void chap_restart_timer(struct triton_timer_t *t);
@@ -94,7 +96,7 @@ static void print_str(const char *buf, int size)
static struct auth_data_t* auth_data_init(struct ppp_t *ppp)
{
- struct chap_auth_data_t *d = _malloc(sizeof(*d));
+ struct chap_auth_data *d = _malloc(sizeof(*d));
memset(d, 0, sizeof(*d));
d->auth.proto = PPP_CHAP;
@@ -105,7 +107,7 @@ static struct auth_data_t* auth_data_init(struct ppp_t *ppp)
static void auth_data_free(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
if (d->timeout.tpd)
triton_timer_del(&d->timeout);
@@ -118,7 +120,7 @@ static void auth_data_free(struct ppp_t *ppp, struct auth_data_t *auth)
static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
d->h.proto = PPP_CHAP;
d->h.recv = chap_recv;
@@ -127,6 +129,7 @@ static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
d->interval.expire = chap_restart_timer;
d->interval.period = conf_interval * 1000;
d->id = 1;
+ d->name = NULL;
ppp_register_chan_handler(ppp, &d->h);
@@ -137,13 +140,16 @@ static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
static int chap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
if (d->timeout.tpd)
triton_timer_del(&d->timeout);
if (d->interval.tpd)
triton_timer_del(&d->interval);
+
+ if (d->name)
+ _free(d->name);
ppp_unregister_handler(ppp, &d->h);
@@ -152,7 +158,7 @@ static int chap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
static void chap_timeout_timer(struct triton_timer_t *t)
{
- struct chap_auth_data_t *d = container_of(t, typeof(*d), timeout);
+ struct chap_auth_data *d = container_of(t, typeof(*d), timeout);
if (conf_ppp_verbose)
log_ppp_warn("chap-md5: timeout\n");
@@ -168,7 +174,7 @@ static void chap_timeout_timer(struct triton_timer_t *t)
static void chap_restart_timer(struct triton_timer_t *t)
{
- struct chap_auth_data_t *d = container_of(t, typeof(*d), interval);
+ struct chap_auth_data *d = container_of(t, typeof(*d), interval);
chap_send_challenge(d, 1);
}
@@ -186,9 +192,9 @@ static int lcp_recv_conf_req(struct ppp_t *ppp, struct auth_data_t *d, uint8_t *
return LCP_OPT_NAK;
}
-static void chap_send_failure(struct chap_auth_data_t *ad)
+static void chap_send_failure(struct chap_auth_data *ad)
{
- struct chap_failure_t msg = {
+ struct chap_failure msg = {
.hdr.proto = htons(PPP_CHAP),
.hdr.code = CHAP_FAILURE,
.hdr.id = ad->id,
@@ -202,9 +208,9 @@ static void chap_send_failure(struct chap_auth_data_t *ad)
ppp_chan_send(ad->ppp, &msg, ntohs(msg.hdr.len) + 2);
}
-static void chap_send_success(struct chap_auth_data_t *ad, int id)
+static void chap_send_success(struct chap_auth_data *ad, int id)
{
- struct chap_success_t msg = {
+ struct chap_success msg = {
.hdr.proto = htons(PPP_CHAP),
.hdr.code = CHAP_SUCCESS,
.hdr.id = id,
@@ -218,9 +224,9 @@ static void chap_send_success(struct chap_auth_data_t *ad, int id)
ppp_chan_send(ad->ppp, &msg, ntohs(msg.hdr.len) + 2);
}
-static void chap_send_challenge(struct chap_auth_data_t *ad, int new)
+static void chap_send_challenge(struct chap_auth_data *ad, int new)
{
- struct chap_challenge_t msg = {
+ struct chap_challenge msg = {
.hdr.proto = htons(PPP_CHAP),
.hdr.code = CHAP_CHALLENGE,
.hdr.id = ad->id,
@@ -245,14 +251,45 @@ static void chap_send_challenge(struct chap_auth_data_t *ad, int new)
triton_timer_add(ad->ppp->ses.ctrl->ctx, &ad->timeout, 0);
}
-static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *hdr)
+static void auth_result(struct chap_auth_data *ad, int res)
+{
+ char *name = ad->name;
+
+ ad->name = NULL;
+
+ if (res == PWDB_DENIED) {
+ chap_send_failure(ad);
+ if (ad->started)
+ ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
+ else
+ ppp_auth_failed(ad->ppp, name);
+ } else {
+ if (ppp_auth_succeeded(ad->ppp, name)) {
+ chap_send_failure(ad);
+ ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
+ } else {
+ chap_send_success(ad, ad->id);
+ ad->started = 1;
+ if (conf_interval)
+ triton_timer_add(ad->ppp->ses.ctrl->ctx, &ad->interval, 0);
+ name = NULL;
+ }
+ }
+
+ ad->id++;
+
+ if (name)
+ _free(name);
+}
+
+static void chap_recv_response(struct chap_auth_data *ad, struct chap_hdr *hdr)
{
MD5_CTX md5_ctx;
uint8_t md5[MD5_DIGEST_LENGTH];
char *passwd;
char *name;
int r;
- struct chap_challenge_t *msg = (struct chap_challenge_t*)hdr;
+ struct chap_challenge *msg = (struct chap_challenge*)hdr;
if (ad->timeout.tpd)
triton_timer_del(&ad->timeout);
@@ -270,6 +307,9 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
return;
}
+ if (ad->name)
+ return;
+
if (msg->hdr.id != ad->id) {
if (conf_ppp_verbose)
log_ppp_warn("chap-md5: id mismatch\n");
@@ -301,7 +341,12 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
return;
}
- r = pwdb_check(&ad->ppp->ses, name, PPP_CHAP, CHAP_MD5, ad->id, ad->val, VALUE_SIZE, msg->val);
+ r = pwdb_check(&ad->ppp->ses, (pwdb_callback)auth_result, ad, name, PPP_CHAP, CHAP_MD5, ad->id, ad->val, VALUE_SIZE, msg->val);
+
+ if (r == PWDB_WAIT) {
+ ad->name = name;
+ return;
+ }
if (r == PWDB_NO_IMPL) {
passwd = pwdb_get_passwd(&ad->ppp->ses, name);
@@ -383,7 +428,7 @@ static int chap_check(uint8_t *ptr)
static int chap_restart(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
chap_send_challenge(d, 1);
@@ -405,8 +450,8 @@ static struct ppp_auth_handler_t chap=
static void chap_recv(struct ppp_handler_t *h)
{
- struct chap_auth_data_t *d = container_of(h, typeof(*d), h);
- struct chap_hdr_t *hdr = (struct chap_hdr_t *)d->ppp->buf;
+ struct chap_auth_data *d = container_of(h, typeof(*d), h);
+ struct chap_hdr *hdr = (struct chap_hdr *)d->ppp->buf;
if (d->ppp->buf_size < sizeof(*hdr) || ntohs(hdr->len) < HDR_LEN || ntohs(hdr->len) > d->ppp->buf_size - 2) {
log_ppp_warn("chap-md5: short packet received\n");
diff --git a/accel-pppd/auth/auth_mschap_v1.c b/accel-pppd/auth/auth_mschap_v1.c
index 1576c837..d9232cc9 100644
--- a/accel-pppd/auth/auth_mschap_v1.c
+++ b/accel-pppd/auth/auth_mschap_v1.c
@@ -29,7 +29,7 @@
#define VALUE_SIZE 8
#define RESPONSE_VALUE_SIZE (24+24+1)
-#define HDR_LEN (sizeof(struct chap_hdr_t)-2)
+#define HDR_LEN (sizeof(struct chap_hdr)-2)
static int conf_timeout = 5;
static int conf_interval = 0;
@@ -38,22 +38,22 @@ static int conf_any_login = 0;
static char *conf_msg_failure = "E=691 R=0";
static char *conf_msg_success = "Authentication succeeded";
-struct chap_hdr_t {
+struct chap_hdr {
uint16_t proto;
uint8_t code;
uint8_t id;
uint16_t len;
} __attribute__((packed));
-struct chap_challenge_t {
- struct chap_hdr_t hdr;
+struct chap_challenge {
+ struct chap_hdr hdr;
uint8_t val_size;
uint8_t val[VALUE_SIZE];
char name[0];
} __attribute__((packed));
-struct chap_response_t {
- struct chap_hdr_t hdr;
+struct chap_response {
+ struct chap_hdr hdr;
uint8_t val_size;
uint8_t lm_hash[24];
uint8_t nt_hash[24];
@@ -61,7 +61,7 @@ struct chap_response_t {
char name[0];
} __attribute__((packed));
-struct chap_auth_data_t {
+struct chap_auth_data {
struct auth_data_t auth;
struct ppp_handler_t h;
struct ppp_t *ppp;
@@ -70,15 +70,17 @@ struct chap_auth_data_t {
struct triton_timer_t timeout;
struct triton_timer_t interval;
int failure;
+ char *name;
+ char *mschap_error;
int started:1;
};
-static void chap_send_challenge(struct chap_auth_data_t *ad, int new);
+static void chap_send_challenge(struct chap_auth_data *ad, int new);
static void chap_recv(struct ppp_handler_t *h);
-static int chap_check_response(struct chap_auth_data_t *ad, struct chap_response_t *res, const char *name);
+static int chap_check_response(struct chap_auth_data *ad, struct chap_response *res, const char *name);
static void chap_timeout_timer(struct triton_timer_t *t);
static void chap_restart_timer(struct triton_timer_t *t);
-static void set_mppe_keys(struct chap_auth_data_t *ad, uint8_t *z_hash);
+static void set_mppe_keys(struct chap_auth_data *ad, uint8_t *z_hash);
static void print_buf(const uint8_t *buf,int size)
{
@@ -95,7 +97,7 @@ static void print_str(const char *buf, int size)
static struct auth_data_t* auth_data_init(struct ppp_t *ppp)
{
- struct chap_auth_data_t *d = _malloc(sizeof(*d));
+ struct chap_auth_data *d = _malloc(sizeof(*d));
memset(d, 0, sizeof(*d));
d->auth.proto = PPP_CHAP;
@@ -106,7 +108,7 @@ static struct auth_data_t* auth_data_init(struct ppp_t *ppp)
static void auth_data_free(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
if (d->timeout.tpd)
triton_timer_del(&d->timeout);
@@ -119,7 +121,7 @@ static void auth_data_free(struct ppp_t *ppp, struct auth_data_t *auth)
static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
d->h.proto = PPP_CHAP;
d->h.recv = chap_recv;
@@ -128,6 +130,7 @@ static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
d->interval.expire = chap_restart_timer;
d->interval.period = conf_interval * 1000;
d->id = 1;
+ d->name = NULL;
ppp_register_chan_handler(ppp, &d->h);
@@ -138,7 +141,7 @@ static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
static int chap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
if (d->timeout.tpd)
triton_timer_del(&d->timeout);
@@ -146,6 +149,9 @@ static int chap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
if (d->interval.tpd)
triton_timer_del(&d->interval);
+ if (d->name)
+ _free(d->name);
+
ppp_unregister_handler(ppp, &d->h);
return 0;
@@ -153,7 +159,7 @@ static int chap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
static void chap_timeout_timer(struct triton_timer_t *t)
{
- struct chap_auth_data_t *d = container_of(t, typeof(*d), timeout);
+ struct chap_auth_data *d = container_of(t, typeof(*d), timeout);
if (conf_ppp_verbose)
log_ppp_warn("mschap-v1: timeout\n");
@@ -169,7 +175,7 @@ static void chap_timeout_timer(struct triton_timer_t *t)
static void chap_restart_timer(struct triton_timer_t *t)
{
- struct chap_auth_data_t *d = container_of(t, typeof(*d), interval);
+ struct chap_auth_data *d = container_of(t, typeof(*d), interval);
chap_send_challenge(d, 1);
}
@@ -187,9 +193,9 @@ static int lcp_recv_conf_req(struct ppp_t *ppp, struct auth_data_t *d, uint8_t *
return LCP_OPT_NAK;
}
-static void chap_send_failure(struct chap_auth_data_t *ad, char *mschap_error)
+static void chap_send_failure(struct chap_auth_data *ad, char *mschap_error)
{
- struct chap_hdr_t *hdr = _malloc(sizeof(*hdr) + strlen(mschap_error) + 1);
+ struct chap_hdr *hdr = _malloc(sizeof(*hdr) + strlen(mschap_error) + 1);
hdr->proto = htons(PPP_CHAP);
hdr->code = CHAP_FAILURE;
hdr->id = ad->id;
@@ -204,9 +210,9 @@ static void chap_send_failure(struct chap_auth_data_t *ad, char *mschap_error)
_free(hdr);
}
-static void chap_send_success(struct chap_auth_data_t *ad, int id)
+static void chap_send_success(struct chap_auth_data *ad, int id)
{
- struct chap_hdr_t *hdr = _malloc(sizeof(*hdr) + strlen(conf_msg_success) + 1);
+ struct chap_hdr *hdr = _malloc(sizeof(*hdr) + strlen(conf_msg_success) + 1);
hdr->proto = htons(PPP_CHAP);
hdr->code = CHAP_SUCCESS;
hdr->id = id;
@@ -221,9 +227,9 @@ static void chap_send_success(struct chap_auth_data_t *ad, int id)
_free(hdr);
}
-static void chap_send_challenge(struct chap_auth_data_t *ad, int new)
+static void chap_send_challenge(struct chap_auth_data *ad, int new)
{
- struct chap_challenge_t msg = {
+ struct chap_challenge msg = {
.hdr.proto = htons(PPP_CHAP),
.hdr.code = CHAP_CHALLENGE,
.hdr.id = ad->id,
@@ -248,11 +254,46 @@ static void chap_send_challenge(struct chap_auth_data_t *ad, int new)
triton_timer_add(ad->ppp->ses.ctrl->ctx, &ad->timeout, 0);
}
-static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *hdr)
+static void auth_result(struct chap_auth_data *ad, int res)
+{
+ char *name = ad->name;
+
+ ad->name = NULL;
+
+ if (res == PWDB_DENIED) {
+ chap_send_failure(ad, ad->mschap_error);
+ if (ad->started)
+ ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
+ else
+ ppp_auth_failed(ad->ppp, name);
+ } else {
+ if (ppp_auth_succeeded(ad->ppp, name)) {
+ chap_send_failure(ad, ad->mschap_error);
+ ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
+ } else {
+ chap_send_success(ad, ad->id);
+ ad->started = 1;
+ if (conf_interval)
+ triton_timer_add(ad->ppp->ses.ctrl->ctx, &ad->interval, 0);
+ name = NULL;
+ }
+ }
+
+ ad->id++;
+
+ if (ad->mschap_error != conf_msg_failure) {
+ _free(ad->mschap_error);
+ ad->mschap_error = conf_msg_failure;
+ }
+
+ if (name)
+ _free(name);
+}
+
+static void chap_recv_response(struct chap_auth_data *ad, struct chap_hdr *hdr)
{
- struct chap_response_t *msg = (struct chap_response_t*)hdr;
+ struct chap_response *msg = (struct chap_response*)hdr;
char *name;
- char *mschap_error = conf_msg_failure;
int r;
if (ad->timeout.tpd)
@@ -273,6 +314,9 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
return;
}
+ if (ad->name)
+ return;
+
if (msg->hdr.id != ad->id) {
if (conf_ppp_verbose)
log_ppp_warn("mschap-v1: id mismatch\n");
@@ -300,7 +344,7 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
if (conf_any_login) {
if (ppp_auth_succeeded(ad->ppp, name)) {
- chap_send_failure(ad, mschap_error);
+ chap_send_failure(ad, ad->mschap_error);
ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
_free(name);
return;
@@ -311,24 +355,34 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
return;
}
- r = pwdb_check(&ad->ppp->ses, name, PPP_CHAP, MSCHAP_V1, ad->id, ad->val, VALUE_SIZE, msg->lm_hash, msg->nt_hash, msg->flags, &mschap_error);
+ ad->mschap_error = conf_msg_failure;
+
+ r = pwdb_check(&ad->ppp->ses, (pwdb_callback)auth_result, ad, name, PPP_CHAP, MSCHAP_V1, ad->id, ad->val, VALUE_SIZE, msg->lm_hash, msg->nt_hash, msg->flags, &ad->mschap_error);
+
+ if (r == PWDB_WAIT) {
+ ad->name = name;
+ return;
+ }
+
if (r == PWDB_NO_IMPL)
if (chap_check_response(ad, msg, name))
r = PWDB_DENIED;
if (r == PWDB_DENIED) {
- chap_send_failure(ad, mschap_error);
+ chap_send_failure(ad, ad->mschap_error);
if (ad->started)
ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
else
ppp_auth_failed(ad->ppp, name);
_free(name);
- if (mschap_error != conf_msg_failure)
- _free(mschap_error);
+ if (ad->mschap_error != conf_msg_failure) {
+ _free(ad->mschap_error);
+ ad->mschap_error = conf_msg_failure;
+ }
} else {
if (!ad->started) {
if (ppp_auth_succeeded(ad->ppp, name)) {
- chap_send_failure(ad, mschap_error);
+ chap_send_failure(ad, ad->mschap_error);
ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
_free(name);
} else {
@@ -375,7 +429,7 @@ static void des_encrypt(const uint8_t *input, const uint8_t *key, uint8_t *outpu
memcpy(output, res, 8);
}
-static int chap_check_response(struct chap_auth_data_t *ad, struct chap_response_t *msg, const char *name)
+static int chap_check_response(struct chap_auth_data *ad, struct chap_response *msg, const char *name)
{
MD4_CTX md4_ctx;
uint8_t z_hash[21];
@@ -420,7 +474,7 @@ static int chap_check(uint8_t *ptr)
return *ptr == MSCHAP_V1;
}
-static void set_mppe_keys(struct chap_auth_data_t *ad, uint8_t *z_hash)
+static void set_mppe_keys(struct chap_auth_data *ad, uint8_t *z_hash)
{
MD4_CTX md4_ctx;
SHA_CTX sha_ctx;
@@ -450,7 +504,7 @@ static void set_mppe_keys(struct chap_auth_data_t *ad, uint8_t *z_hash)
static int chap_restart(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
chap_send_challenge(d, 1);
@@ -471,8 +525,8 @@ static struct ppp_auth_handler_t chap = {
static void chap_recv(struct ppp_handler_t *h)
{
- struct chap_auth_data_t *d = container_of(h, typeof(*d), h);
- struct chap_hdr_t *hdr = (struct chap_hdr_t *)d->ppp->buf;
+ struct chap_auth_data *d = container_of(h, typeof(*d), h);
+ struct chap_hdr *hdr = (struct chap_hdr *)d->ppp->buf;
if (d->ppp->buf_size < sizeof(*hdr) || ntohs(hdr->len) < HDR_LEN || ntohs(hdr->len) > d->ppp->buf_size - 2) {
log_ppp_warn("mschap-v1: short packet received\n");
diff --git a/accel-pppd/auth/auth_mschap_v2.c b/accel-pppd/auth/auth_mschap_v2.c
index 29f37495..0235ddf0 100644
--- a/accel-pppd/auth/auth_mschap_v2.c
+++ b/accel-pppd/auth/auth_mschap_v2.c
@@ -29,7 +29,7 @@
#define VALUE_SIZE 16
#define RESPONSE_VALUE_SIZE (16+8+24+1)
-#define HDR_LEN (sizeof(struct chap_hdr_t)-2)
+#define HDR_LEN (sizeof(struct chap_hdr)-2)
static int conf_timeout = 5;
static int conf_interval = 0;
@@ -38,7 +38,7 @@ static char *conf_msg_failure = "E=691 R=0 V=3";
static char *conf_msg_failure2 = "Authentication failure";
static char *conf_msg_success = "Authentication succeeded";
-struct chap_hdr_t {
+struct chap_hdr {
uint16_t proto;
uint8_t code;
uint8_t id;
@@ -46,14 +46,14 @@ struct chap_hdr_t {
} __attribute__((packed));
struct chap_challenge_t {
- struct chap_hdr_t hdr;
+ struct chap_hdr hdr;
uint8_t val_size;
uint8_t val[VALUE_SIZE];
char name[0];
} __attribute__((packed));
-struct chap_response_t {
- struct chap_hdr_t hdr;
+struct chap_response {
+ struct chap_hdr hdr;
uint8_t val_size;
uint8_t peer_challenge[16];
uint8_t reserved[8];
@@ -62,7 +62,7 @@ struct chap_response_t {
char name[0];
} __attribute__((packed));
-struct chap_auth_data_t {
+struct chap_auth_data {
struct auth_data_t auth;
struct ppp_handler_t h;
struct ppp_t *ppp;
@@ -71,16 +71,19 @@ struct chap_auth_data_t {
struct triton_timer_t timeout;
struct triton_timer_t interval;
char authenticator[41];
+ char *name;
+ char *mschap_error;
+ char *reply_msg;
int failure;
int started:1;
};
-static void chap_send_challenge(struct chap_auth_data_t *ad, int new);
+static void chap_send_challenge(struct chap_auth_data *ad, int new);
static void chap_recv(struct ppp_handler_t *h);
-static int chap_check_response(struct chap_auth_data_t *ad, struct chap_response_t *msg, const char *name);
+static int chap_check_response(struct chap_auth_data *ad, struct chap_response *msg, const char *name);
static void chap_timeout_timer(struct triton_timer_t *t);
static void chap_restart_timer(struct triton_timer_t *t);
-static void set_mppe_keys(struct chap_auth_data_t *ad, uint8_t *z_hash, uint8_t *nt_hash);
+static void set_mppe_keys(struct chap_auth_data *ad, uint8_t *z_hash, uint8_t *nt_hash);
static void print_buf(const uint8_t *buf, int size)
{
@@ -98,7 +101,7 @@ static void print_str(const char *buf, int size)
static struct auth_data_t* auth_data_init(struct ppp_t *ppp)
{
- struct chap_auth_data_t *d = _malloc(sizeof(*d));
+ struct chap_auth_data *d = _malloc(sizeof(*d));
memset(d, 0, sizeof(*d));
d->auth.proto = PPP_CHAP;
@@ -109,7 +112,7 @@ static struct auth_data_t* auth_data_init(struct ppp_t *ppp)
static void auth_data_free(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
if (d->timeout.tpd)
triton_timer_del(&d->timeout);
@@ -122,7 +125,7 @@ static void auth_data_free(struct ppp_t *ppp, struct auth_data_t *auth)
static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
d->h.proto = PPP_CHAP;
d->h.recv = chap_recv;
@@ -131,6 +134,7 @@ static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
d->interval.expire = chap_restart_timer;
d->interval.period = conf_interval * 1000;
d->id = 1;
+ d->name = NULL;
ppp_register_chan_handler(ppp, &d->h);
@@ -141,7 +145,7 @@ static int chap_start(struct ppp_t *ppp, struct auth_data_t *auth)
static int chap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
if (d->timeout.tpd)
triton_timer_del(&d->timeout);
@@ -156,7 +160,7 @@ static int chap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
static void chap_timeout_timer(struct triton_timer_t *t)
{
- struct chap_auth_data_t *d = container_of(t, typeof(*d), timeout);
+ struct chap_auth_data *d = container_of(t, typeof(*d), timeout);
if (conf_ppp_verbose)
log_ppp_warn("mschap-v2: timeout\n");
@@ -172,7 +176,7 @@ static void chap_timeout_timer(struct triton_timer_t *t)
static void chap_restart_timer(struct triton_timer_t *t)
{
- struct chap_auth_data_t *d = container_of(t, typeof(*d), interval);
+ struct chap_auth_data *d = container_of(t, typeof(*d), interval);
chap_send_challenge(d, 1);
}
@@ -190,9 +194,9 @@ static int lcp_recv_conf_req(struct ppp_t *ppp, struct auth_data_t *d, uint8_t *
return LCP_OPT_NAK;
}
-static void chap_send_failure(struct chap_auth_data_t *ad, char *mschap_error, char *reply_msg)
+static void chap_send_failure(struct chap_auth_data *ad, char *mschap_error, char *reply_msg)
{
- struct chap_hdr_t *hdr = _malloc(sizeof(*hdr) + strlen(mschap_error) + strlen(reply_msg) + 4);
+ struct chap_hdr *hdr = _malloc(sizeof(*hdr) + strlen(mschap_error) + strlen(reply_msg) + 4);
hdr->proto = htons(PPP_CHAP);
hdr->code = CHAP_FAILURE;
hdr->id = ad->id;
@@ -208,9 +212,9 @@ static void chap_send_failure(struct chap_auth_data_t *ad, char *mschap_error, c
_free(hdr);
}
-static void chap_send_success(struct chap_auth_data_t *ad, int id, const char *authenticator)
+static void chap_send_success(struct chap_auth_data *ad, int id, const char *authenticator)
{
- struct chap_hdr_t *hdr = _malloc(sizeof(*hdr) + strlen(conf_msg_success) + 1 + 45);
+ struct chap_hdr *hdr = _malloc(sizeof(*hdr) + strlen(conf_msg_success) + 1 + 45);
hdr->proto = htons(PPP_CHAP),
hdr->code = CHAP_SUCCESS,
hdr->id = id,
@@ -226,7 +230,7 @@ static void chap_send_success(struct chap_auth_data_t *ad, int id, const char *a
_free(hdr);
}
-static int generate_response(struct chap_auth_data_t *ad, struct chap_response_t *msg, const char *name, char *authenticator)
+static int generate_response(struct chap_auth_data *ad, struct chap_response *msg, const char *name, char *authenticator)
{
MD4_CTX md4_ctx;
SHA_CTX sha_ctx;
@@ -296,7 +300,7 @@ static int generate_response(struct chap_auth_data_t *ad, struct chap_response_t
return 0;
}
-static void chap_send_challenge(struct chap_auth_data_t *ad, int new)
+static void chap_send_challenge(struct chap_auth_data *ad, int new)
{
struct chap_challenge_t msg = {
.hdr.proto = htons(PPP_CHAP),
@@ -323,14 +327,54 @@ static void chap_send_challenge(struct chap_auth_data_t *ad, int new)
triton_timer_add(ad->ppp->ses.ctrl->ctx, &ad->timeout, 0);
}
-static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *hdr)
+static void auth_result(struct chap_auth_data *ad, int res)
+{
+ char *name = ad->name;
+
+ ad->name = NULL;
+
+ if (res == PWDB_DENIED) {
+ chap_send_failure(ad, ad->mschap_error, ad->reply_msg);
+ if (ad->started)
+ ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
+ else
+ ppp_auth_failed(ad->ppp, name);
+ } else {
+ if (ppp_auth_succeeded(ad->ppp, name)) {
+ chap_send_failure(ad, ad->mschap_error, ad->reply_msg);
+ ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
+ } else {
+ chap_send_success(ad, ad->id, ad->authenticator);
+ ad->started = 1;
+ if (conf_interval)
+ triton_timer_add(ad->ppp->ses.ctrl->ctx, &ad->interval, 0);
+ name = NULL;
+ }
+ }
+
+ ad->id++;
+
+ if (ad->mschap_error != conf_msg_failure) {
+ _free(ad->mschap_error);
+ ad->mschap_error = conf_msg_failure;
+ }
+
+ if (ad->reply_msg != conf_msg_failure2) {
+ _free(ad->reply_msg);
+ ad->reply_msg = conf_msg_failure2;
+ }
+
+ if (name)
+ _free(name);
+}
+
+
+static void chap_recv_response(struct chap_auth_data *ad, struct chap_hdr *hdr)
{
- struct chap_response_t *msg = (struct chap_response_t*)hdr;
+ struct chap_response *msg = (struct chap_response*)hdr;
char *name;
- char authenticator[41];
+ char *authenticator = ad->authenticator;
int r;
- char *mschap_error = conf_msg_failure;
- char *reply_msg = conf_msg_failure2;
authenticator[40] = 0;
@@ -352,6 +396,12 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
return;
}
+ if (ad->name)
+ return;
+
+ ad->mschap_error = conf_msg_failure;
+ ad->reply_msg = conf_msg_failure2;
+
if (msg->hdr.id != ad->id) {
if (conf_ppp_verbose)
log_ppp_warn("mschap-v2: id mismatch\n");
@@ -360,7 +410,7 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
if (msg->val_size != RESPONSE_VALUE_SIZE) {
log_ppp_error("mschap-v2: incorrect value-size (%i)\n", msg->val_size);
- chap_send_failure(ad, mschap_error, reply_msg);
+ chap_send_failure(ad, ad->mschap_error, ad->reply_msg);
if (ad->started)
ap_session_terminate(&ad->ppp->ses, TERM_USER_ERROR, 0);
else
@@ -378,7 +428,12 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
return;
}
- r = pwdb_check(&ad->ppp->ses, name, PPP_CHAP, MSCHAP_V2, ad->id, ad->val, msg->peer_challenge, msg->reserved, msg->nt_hash, msg->flags, authenticator, &mschap_error, &reply_msg);
+ r = pwdb_check(&ad->ppp->ses, (pwdb_callback)auth_result, ad, name, PPP_CHAP, MSCHAP_V2, ad->id, ad->val, msg->peer_challenge, msg->reserved, msg->nt_hash, msg->flags, authenticator, &ad->mschap_error, &ad->reply_msg);
+
+ if (r == PWDB_WAIT) {
+ ad->name = name;
+ return;
+ }
if (r == PWDB_NO_IMPL) {
r = chap_check_response(ad, msg, name);
@@ -389,20 +444,27 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
}
if (r == PWDB_DENIED) {
- chap_send_failure(ad, mschap_error, reply_msg);
+ chap_send_failure(ad, ad->mschap_error, ad->reply_msg);
if (ad->started)
ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
else
ppp_auth_failed(ad->ppp, name);
+
_free(name);
- if (mschap_error != conf_msg_failure)
- _free(mschap_error);
- if (reply_msg != conf_msg_failure2)
- _free(reply_msg);
+
+ if (ad->mschap_error != conf_msg_failure) {
+ _free(ad->mschap_error);
+ ad->mschap_error = conf_msg_failure;
+ }
+
+ if (ad->reply_msg != conf_msg_failure2) {
+ _free(ad->reply_msg);
+ ad->reply_msg = conf_msg_failure2;
+ }
} else {
if (!ad->started) {
if (ppp_auth_succeeded(ad->ppp, name)) {
- chap_send_failure(ad, mschap_error, reply_msg);
+ chap_send_failure(ad, ad->mschap_error, ad->reply_msg);
ap_session_terminate(&ad->ppp->ses, TERM_AUTH_ERROR, 0);
_free(name);
} else {
@@ -416,8 +478,6 @@ static void chap_recv_response(struct chap_auth_data_t *ad, struct chap_hdr_t *h
_free(name);
}
- memcpy(ad->authenticator, authenticator, 41);
-
ad->id++;
}
}
@@ -451,7 +511,7 @@ static void des_encrypt(const uint8_t *input, const uint8_t *key, uint8_t *outpu
memcpy(output,res,8);
}
-static int chap_check_response(struct chap_auth_data_t *ad, struct chap_response_t *msg, const char *name)
+static int chap_check_response(struct chap_auth_data *ad, struct chap_response *msg, const char *name)
{
MD4_CTX md4_ctx;
SHA_CTX sha_ctx;
@@ -499,7 +559,7 @@ static int chap_check_response(struct chap_auth_data_t *ad, struct chap_response
return memcmp(nt_hash, msg->nt_hash, 24);
}
-static void set_mppe_keys(struct chap_auth_data_t *ad, uint8_t *z_hash, uint8_t *nt_hash)
+static void set_mppe_keys(struct chap_auth_data *ad, uint8_t *z_hash, uint8_t *nt_hash)
{
MD4_CTX md4_ctx;
SHA_CTX sha_ctx;
@@ -591,7 +651,7 @@ static int chap_check(uint8_t *ptr)
static int chap_restart(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct chap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct chap_auth_data *d = container_of(auth, typeof(*d), auth);
chap_send_challenge(d, 1);
@@ -613,8 +673,8 @@ static struct ppp_auth_handler_t chap=
static void chap_recv(struct ppp_handler_t *h)
{
- struct chap_auth_data_t *d = container_of(h, typeof(*d), h);
- struct chap_hdr_t *hdr = (struct chap_hdr_t *)d->ppp->buf;
+ struct chap_auth_data *d = container_of(h, typeof(*d), h);
+ struct chap_hdr *hdr = (struct chap_hdr *)d->ppp->buf;
if (d->ppp->buf_size < sizeof(*hdr) || ntohs(hdr->len) < HDR_LEN || ntohs(hdr->len) > d->ppp->buf_size - 2) {
log_ppp_warn("mschap-v2: short packet received\n");
diff --git a/accel-pppd/auth/auth_pap.c b/accel-pppd/auth/auth_pap.c
index 5f073370..9aab3775 100644
--- a/accel-pppd/auth/auth_pap.c
+++ b/accel-pppd/auth/auth_pap.c
@@ -15,12 +15,14 @@
#define MSG_FAILED "Authentication failed"
#define MSG_SUCCESSED "Authentication succeeded"
-#define HDR_LEN (sizeof(struct pap_hdr_t)-2)
+#define HDR_LEN (sizeof(struct pap_hdr)-2)
#define PAP_REQ 1
#define PAP_ACK 2
#define PAP_NAK 3
+struct pap_auth_data;
+
static int conf_timeout = 5;
static int conf_any_login = 0;
@@ -32,33 +34,32 @@ static int pap_start(struct ppp_t*, struct auth_data_t*);
static int pap_finish(struct ppp_t*, struct auth_data_t*);
static void pap_recv(struct ppp_handler_t*h);
static void pap_timeout(struct triton_timer_t *t);
+static void pap_auth_result(struct pap_auth_data *, int);
-struct pap_auth_data_t
-{
+struct pap_auth_data {
struct auth_data_t auth;
struct ppp_handler_t h;
struct ppp_t *ppp;
- int started:1;
struct triton_timer_t timeout;
+ char *peer_id;
+ int req_id;
+ int started:1;
};
-struct pap_hdr_t
-{
+struct pap_hdr {
uint16_t proto;
uint8_t code;
uint8_t id;
uint16_t len;
} __attribute__((packed));
-struct pap_ack_t
-{
- struct pap_hdr_t hdr;
+struct pap_ack {
+ struct pap_hdr hdr;
uint8_t msg_len;
char msg[0];
} __attribute__((packed));
-static struct ppp_auth_handler_t pap=
-{
+static struct ppp_auth_handler_t pap= {
.name = "PAP",
.init = auth_data_init,
.free = auth_data_free,
@@ -70,7 +71,7 @@ static struct ppp_auth_handler_t pap=
static struct auth_data_t* auth_data_init(struct ppp_t *ppp)
{
- struct pap_auth_data_t *d = _malloc(sizeof(*d));
+ struct pap_auth_data *d = _malloc(sizeof(*d));
memset(d, 0, sizeof(*d));
d->auth.proto = PPP_PAP;
@@ -81,14 +82,14 @@ static struct auth_data_t* auth_data_init(struct ppp_t *ppp)
static void auth_data_free(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct pap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct pap_auth_data *d = container_of(auth, typeof(*d), auth);
_free(d);
}
static int pap_start(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct pap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct pap_auth_data *d = container_of(auth, typeof(*d), auth);
d->h.proto = PPP_PAP;
d->h.recv = pap_recv;
@@ -103,10 +104,13 @@ static int pap_start(struct ppp_t *ppp, struct auth_data_t *auth)
}
static int pap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
{
- struct pap_auth_data_t *d = container_of(auth, typeof(*d), auth);
+ struct pap_auth_data *d = container_of(auth, typeof(*d), auth);
if (d->timeout.tpd)
triton_timer_del(&d->timeout);
+
+ if (d->peer_id)
+ _free(d->peer_id);
ppp_unregister_handler(ppp, &d->h);
@@ -115,7 +119,7 @@ static int pap_finish(struct ppp_t *ppp, struct auth_data_t *auth)
static void pap_timeout(struct triton_timer_t *t)
{
- struct pap_auth_data_t *d = container_of(t, typeof(*d), timeout);
+ struct pap_auth_data *d = container_of(t, typeof(*d), timeout);
if (conf_ppp_verbose)
log_ppp_warn("pap: timeout\n");
@@ -133,10 +137,10 @@ static int lcp_recv_conf_req(struct ppp_t *ppp, struct auth_data_t *d, uint8_t *
return LCP_OPT_ACK;
}
-static void pap_send_ack(struct pap_auth_data_t *p, int id)
+static void pap_send_ack(struct pap_auth_data *p, int id)
{
uint8_t buf[128];
- struct pap_ack_t *msg = (struct pap_ack_t*)buf;
+ struct pap_ack *msg = (struct pap_ack*)buf;
msg->hdr.proto = htons(PPP_PAP);
msg->hdr.code = PAP_ACK;
msg->hdr.id = id;
@@ -150,10 +154,10 @@ static void pap_send_ack(struct pap_auth_data_t *p, int id)
ppp_chan_send(p->ppp, msg, ntohs(msg->hdr.len) + 2);
}
-static void pap_send_nak(struct pap_auth_data_t *p, int id)
+static void pap_send_nak(struct pap_auth_data *p, int id)
{
uint8_t buf[128];
- struct pap_ack_t *msg = (struct pap_ack_t*)buf;
+ struct pap_ack *msg = (struct pap_ack*)buf;
msg->hdr.proto = htons(PPP_PAP);
msg->hdr.code = PAP_NAK;
msg->hdr.id = id;
@@ -167,7 +171,33 @@ static void pap_send_nak(struct pap_auth_data_t *p, int id)
ppp_chan_send(p->ppp, msg, ntohs(msg->hdr.len) + 2);
}
-static int pap_recv_req(struct pap_auth_data_t *p, struct pap_hdr_t *hdr)
+static void pap_auth_result(struct pap_auth_data *p, int res)
+{
+ char *peer_id = p->peer_id;
+
+ p->peer_id = NULL;
+
+ if (res == PWDB_DENIED) {
+ pap_send_nak(p, p->req_id);
+ if (p->started)
+ ap_session_terminate(&p->ppp->ses, TERM_AUTH_ERROR, 0);
+ else
+ ppp_auth_failed(p->ppp, peer_id);
+ } else {
+ if (ppp_auth_succeeded(p->ppp, peer_id)) {
+ pap_send_nak(p, p->req_id);
+ ap_session_terminate(&p->ppp->ses, TERM_AUTH_ERROR, 0);
+ } else {
+ pap_send_ack(p, p->req_id);
+ p->started = 1;
+ return;
+ }
+ }
+
+ _free(peer_id);
+}
+
+static int pap_recv_req(struct pap_auth_data *p, struct pap_hdr *hdr)
{
int ret, r;
char *peer_id;
@@ -182,17 +212,21 @@ static int pap_recv_req(struct pap_auth_data_t *p, struct pap_hdr_t *hdr)
if (conf_ppp_verbose)
log_ppp_info2("recv [PAP AuthReq id=%x]\n", hdr->id);
-
+
if (p->started) {
pap_send_ack(p, hdr->id);
return 0;
}
+ if (p->peer_id)
+ return 0;
+
peer_id_len = *(uint8_t*)ptr; ptr++;
if (peer_id_len > ntohs(hdr->len) - sizeof(*hdr) + 2 - 1) {
log_ppp_warn("PAP: short packet received\n");
return -1;
}
+
peer_id = (char*)ptr; ptr += peer_id_len;
passwd_len = *(uint8_t*)ptr; ptr++;
@@ -217,7 +251,14 @@ static int pap_recv_req(struct pap_auth_data_t *p, struct pap_hdr_t *hdr)
passwd = _strndup((const char*)ptr, passwd_len);
- r = pwdb_check(&p->ppp->ses, peer_id, PPP_PAP, passwd);
+ r = pwdb_check(&p->ppp->ses, (pwdb_callback)pap_auth_result, p, peer_id, PPP_PAP, passwd);
+ if (r == PWDB_WAIT) {
+ p->peer_id = peer_id;
+ p->req_id = hdr->id;
+ _free(passwd);
+ return 0;
+ }
+
if (r == PWDB_NO_IMPL) {
passwd2 = pwdb_get_passwd(&p->ppp->ses, peer_id);
if (!passwd2) {
@@ -268,8 +309,8 @@ failed:
static void pap_recv(struct ppp_handler_t *h)
{
- struct pap_auth_data_t *d = container_of(h, typeof(*d), h);
- struct pap_hdr_t *hdr = (struct pap_hdr_t *)d->ppp->buf;
+ struct pap_auth_data *d = container_of(h, typeof(*d), h);
+ struct pap_hdr *hdr = (struct pap_hdr *)d->ppp->buf;
if (d->ppp->buf_size < sizeof(*hdr) || ntohs(hdr->len) < HDR_LEN || ntohs(hdr->len) < d->ppp->buf_size - 2) {
log_ppp_warn("PAP: short packet received\n");