summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorbrian <brian@FreeBSD.org>1997-12-03 10:23:54 +0000
committerbrian <brian@FreeBSD.org>1997-12-03 10:23:54 +0000
commit4c9568e05af003a85ca40c896b5041fc8286221f (patch)
tree86301631e3a842883c7e61e9c2f1feab23a39e23
parent185fb48052f903a80b31786784cbb82fb059c35c (diff)
downloadFreeBSD-src-4c9568e05af003a85ca40c896b5041fc8286221f.zip
FreeBSD-src-4c9568e05af003a85ca40c896b5041fc8286221f.tar.gz
Abstract the CCP layer a level.
Add DEFLATE support.
-rw-r--r--usr.sbin/ppp/Makefile10
-rw-r--r--usr.sbin/ppp/ccp.c214
-rw-r--r--usr.sbin/ppp/ccp.h37
-rw-r--r--usr.sbin/ppp/deflate.c499
-rw-r--r--usr.sbin/ppp/deflate.h5
-rw-r--r--usr.sbin/ppp/fsm.c9
-rw-r--r--usr.sbin/ppp/fsm.h3
-rw-r--r--usr.sbin/ppp/hdlc.c57
-rw-r--r--usr.sbin/ppp/hdlc.h3
-rw-r--r--usr.sbin/ppp/ipcp.c41
-rw-r--r--usr.sbin/ppp/lcp.c228
-rw-r--r--usr.sbin/ppp/lcp.h18
-rw-r--r--usr.sbin/ppp/main.c79
-rw-r--r--usr.sbin/ppp/mbuf.h3
-rw-r--r--usr.sbin/ppp/os.c3
-rw-r--r--usr.sbin/ppp/ppp.833
-rw-r--r--usr.sbin/ppp/ppp.8.m433
-rw-r--r--usr.sbin/ppp/pred.c147
-rw-r--r--usr.sbin/ppp/pred.h6
-rw-r--r--usr.sbin/ppp/server.c3
-rw-r--r--usr.sbin/ppp/vars.c17
-rw-r--r--usr.sbin/ppp/vars.h24
-rw-r--r--usr.sbin/ppp/vjcomp.c20
-rw-r--r--usr.sbin/ppp/vjcomp.h3
24 files changed, 1209 insertions, 286 deletions
diff --git a/usr.sbin/ppp/Makefile b/usr.sbin/ppp/Makefile
index d3c5e2d..67cff18 100644
--- a/usr.sbin/ppp/Makefile
+++ b/usr.sbin/ppp/Makefile
@@ -1,14 +1,14 @@
-# $Id: Makefile,v 1.31 1997/11/18 14:52:03 brian Exp $
+# $Id: Makefile,v 1.32 1997/11/22 03:37:21 brian Exp $
PROG= ppp
-SRCS= arp.c async.c auth.c ccp.c chap.c chat.c \
- command.c defs.c filter.c fsm.c hdlc.c id.c ip.c ipcp.c lcp.c \
+SRCS= arp.c async.c auth.c ccp.c chap.c chat.c command.c deflate.c \
+ defs.c filter.c fsm.c hdlc.c id.c ip.c ipcp.c lcp.c \
log.c lqr.c main.c mbuf.c modem.c os.c pap.c phase.c \
pred.c route.c server.c sig.c slcompress.c systems.c throughput.c \
timer.c tun.c vars.c vjcomp.c
CFLAGS+=-Wall
-LDADD+= -lmd -lcrypt -lutil
-DPADD+= ${LIBMD} ${LIBCRYPT} ${LIBUTIL}
+LDADD+= -lmd -lcrypt -lutil -lz
+DPADD+= ${LIBMD} ${LIBCRYPT} ${LIBUTIL} ${LIBZ}
MAN8= ppp.8
BINMODE=4550
BINOWN= root
diff --git a/usr.sbin/ppp/ccp.c b/usr.sbin/ppp/ccp.c
index 6fbee99..a72ad5c 100644
--- a/usr.sbin/ppp/ccp.c
+++ b/usr.sbin/ppp/ccp.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: ccp.c,v 1.19 1997/11/14 15:39:14 brian Exp $
+ * $Id: ccp.c,v 1.20 1997/11/22 03:37:25 brian Exp $
*
* TODO:
* o Support other compression protocols
@@ -41,6 +41,7 @@
#include "loadalias.h"
#include "vars.h"
#include "pred.h"
+#include "deflate.h"
struct ccpstate CcpInfo;
@@ -54,8 +55,6 @@ static void CcpLayerUp(struct fsm *);
static void CcpLayerDown(struct fsm *);
static void CcpInitRestartCounter(struct fsm *);
-#define REJECTED(p, x) (p->his_reject & (1<<x))
-
struct fsm CcpFsm = {
"CCP",
PROTO_CCP,
@@ -92,11 +91,31 @@ static char const *cftypes[] = {
"MSPPC", /* 18: Microsoft PPC */
"GAND", /* 19: Gandalf FZA */
"V42BIS", /* 20: ARG->DATA.42bis compression */
- "BSD", /* BSD LZW Compress */
+ "BSD", /* 21: BSD LZW Compress */
+ "???",
+ "???",
+ "DEFLATE", /* 24: PPP Deflate */
};
#define NCFTYPES (sizeof(cftypes)/sizeof(char *))
+static const char *
+protoname(int proto)
+{
+ if (proto < 0 || proto > NCFTYPES)
+ return "none";
+ return cftypes[proto];
+}
+
+static const struct ccp_algorithm *algorithm[] = {
+ &Pred1Algorithm,
+ &DeflateAlgorithm
+};
+
+static int in_algorithm = -1;
+static int out_algorithm = -1;
+#define NALGORITHMS (sizeof(algorithm)/sizeof(algorithm[0]))
+
int
ReportCcpStatus(struct cmdargs const *arg)
{
@@ -105,10 +124,10 @@ ReportCcpStatus(struct cmdargs const *arg)
if (VarTerm) {
fprintf(VarTerm, "%s [%s]\n", fp->name, StateNames[fp->state]);
- fprintf(VarTerm, "myproto = %s, hisproto = %s\n",
- cftypes[icp->want_proto], cftypes[icp->his_proto]);
- fprintf(VarTerm, "Input: %ld --> %ld, Output: %ld --> %ld\n",
- icp->orgin, icp->compin, icp->orgout, icp->compout);
+ fprintf(VarTerm, "My protocol = %s, His protocol = %s\n",
+ protoname(icp->my_proto), protoname(icp->his_proto));
+ fprintf(VarTerm, "Output: %ld --> %ld, Input: %ld --> %ld\n",
+ icp->uncompout, icp->compout, icp->compin, icp->uncompin);
}
return 0;
}
@@ -120,8 +139,15 @@ CcpInit()
FsmInit(&CcpFsm);
memset(icp, '\0', sizeof(struct ccpstate));
- if (Enabled(ConfPred1))
- icp->want_proto = TY_PRED1;
+ icp->his_proto = icp->my_proto = -1;
+ if (in_algorithm >= 0 && in_algorithm < NALGORITHMS) {
+ (*algorithm[in_algorithm]->i.Term)();
+ in_algorithm = -1;
+ }
+ if (out_algorithm >= 0 && out_algorithm < NALGORITHMS) {
+ (*algorithm[out_algorithm]->o.Term)();
+ out_algorithm = -1;
+ }
CcpFsm.maxconfig = 10;
}
@@ -137,13 +163,22 @@ CcpSendConfigReq(struct fsm *fp)
{
u_char *cp;
struct ccpstate *icp = &CcpInfo;
+ int f;
- cp = ReqBuff;
LogPrintf(LogCCP, "CcpSendConfigReq\n");
- if (icp->want_proto && !REJECTED(icp, TY_PRED1)) {
- *cp++ = TY_PRED1;
- *cp++ = 2;
- }
+ cp = ReqBuff;
+ CcpInfo.my_proto = -1;
+ out_algorithm = -1;
+ for (f = 0; f < NALGORITHMS; f++)
+ if (Enabled(algorithm[f]->Conf) && !REJECTED(icp, algorithm[f]->id)) {
+ struct lcp_opt o;
+
+ (*algorithm[f]->o.Get)(&o);
+ cp += LcpPutConf(LogCCP, cp, &o, cftypes[o.id],
+ (*algorithm[f]->Disp)(&o));
+ CcpInfo.my_proto = o.id;
+ out_algorithm = f;
+ }
FsmOutput(fp, CODE_CONFIGREQ, fp->reqid++, ReqBuff, cp - ReqBuff);
}
@@ -170,7 +205,8 @@ CcpSendTerminateAck(struct fsm *fp)
void
CcpRecvResetReq(struct fsm *fp)
{
- Pred1Init(2); /* Initialize Output part */
+ if (out_algorithm >= 0 && out_algorithm < NALGORITHMS)
+ (*algorithm[out_algorithm]->o.Reset)();
}
static void
@@ -183,24 +219,44 @@ static void
CcpLayerFinish(struct fsm *fp)
{
LogPrintf(LogCCP, "CcpLayerFinish.\n");
+ if (in_algorithm >= 0 && in_algorithm < NALGORITHMS) {
+ (*algorithm[in_algorithm]->i.Term)();
+ in_algorithm = -1;
+ }
+ if (out_algorithm >= 0 && out_algorithm < NALGORITHMS) {
+ (*algorithm[out_algorithm]->o.Term)();
+ out_algorithm = -1;
+ }
}
static void
CcpLayerDown(struct fsm *fp)
{
LogPrintf(LogCCP, "CcpLayerDown.\n");
+ if (in_algorithm >= 0 && in_algorithm < NALGORITHMS) {
+ (*algorithm[in_algorithm]->i.Term)();
+ in_algorithm = -1;
+ }
+ if (out_algorithm >= 0 && out_algorithm < NALGORITHMS) {
+ (*algorithm[out_algorithm]->o.Term)();
+ out_algorithm = -1;
+ }
}
/*
- * Called when CCP has reached to OPEN state
+ * Called when CCP has reached the OPEN state
*/
static void
CcpLayerUp(struct fsm *fp)
{
LogPrintf(LogCCP, "CcpLayerUp(%d).\n", fp->state);
- LogPrintf(LogCCP, "myproto = %d, hisproto = %d\n",
- CcpInfo.want_proto, CcpInfo.his_proto);
- Pred1Init(3); /* Initialize Input and Output */
+ LogPrintf(LogCCP, "Out = %s[%d], In = %s[%d]\n",
+ protoname(CcpInfo.my_proto), CcpInfo.my_proto,
+ protoname(CcpInfo.his_proto), CcpInfo.his_proto);
+ if (in_algorithm >= 0 && in_algorithm < NALGORITHMS)
+ (*algorithm[in_algorithm]->i.Init)();
+ if (out_algorithm >= 0 && out_algorithm < NALGORITHMS)
+ (*algorithm[out_algorithm]->o.Init)();
}
void
@@ -213,15 +269,29 @@ CcpUp()
void
CcpOpen()
{
- if (Enabled(ConfPred1))
- FsmOpen(&CcpFsm);
+ int f;
+
+ for (f = 0; f < NALGORITHMS; f++)
+ if (Enabled(algorithm[f]->Conf)) {
+ CcpFsm.open_mode = OPEN_ACTIVE;
+ FsmOpen(&CcpFsm);
+ break;
+ }
+
+ if (f == NALGORITHMS)
+ for (f = 0; f < NALGORITHMS; f++)
+ if (Acceptable(algorithm[f]->Conf)) {
+ CcpFsm.open_mode = OPEN_PASSIVE;
+ FsmOpen(&CcpFsm);
+ break;
+ }
}
static void
CcpDecodeConfig(u_char *cp, int plen, int mode_type)
{
int type, length;
- char tbuff[100];
+ int f;
ackp = AckBuff;
nakp = NakBuff;
@@ -233,42 +303,74 @@ CcpDecodeConfig(u_char *cp, int plen, int mode_type)
type = *cp;
length = cp[1];
if (type < NCFTYPES)
- snprintf(tbuff, sizeof(tbuff), " %s[%d] ", cftypes[type], length);
+ LogPrintf(LogCCP, " %s[%d]\n", cftypes[type], length);
else
- snprintf(tbuff, sizeof(tbuff), " ");
-
- LogPrintf(LogCCP, "%s\n", tbuff);
+ LogPrintf(LogCCP, " ???[%d]\n", length);
+
+ for (f = NALGORITHMS-1; f > -1; f--)
+ if (algorithm[f]->id == type)
+ break;
+
+ if (f == -1) {
+ /* Don't understand that :-( */
+ if (mode_type == MODE_REQ) {
+ CcpInfo.my_reject |= (1 << type);
+ memcpy(rejp, cp, length);
+ rejp += length;
+ }
+ } else {
+ struct lcp_opt o;
- switch (type) {
- case TY_PRED1:
switch (mode_type) {
case MODE_REQ:
- if (Acceptable(ConfPred1)) {
- memcpy(ackp, cp, length);
- ackp += length;
- CcpInfo.his_proto = type;
+ if (Acceptable(algorithm[f]->Conf) && in_algorithm == -1) {
+ memcpy(&o, cp, length);
+ switch ((*algorithm[f]->i.Set)(&o)) {
+ case MODE_REJ:
+ memcpy(rejp, &o, o.len);
+ rejp += o.len;
+ break;
+ case MODE_NAK:
+ memcpy(nakp, &o, o.len);
+ nakp += o.len;
+ break;
+ case MODE_ACK:
+ memcpy(ackp, cp, length);
+ ackp += length;
+ CcpInfo.his_proto = type;
+ in_algorithm = f; /* This one'll do ! */
+ break;
+ }
} else {
memcpy(rejp, cp, length);
rejp += length;
}
break;
case MODE_NAK:
+ memcpy(&o, cp, length);
+ if ((*algorithm[f]->o.Set)(&o) == MODE_ACK)
+ CcpInfo.my_proto = algorithm[f]->id;
+ else {
+ CcpInfo.his_reject |= (1 << type);
+ CcpInfo.my_proto = -1;
+ }
+ break;
case MODE_REJ:
CcpInfo.his_reject |= (1 << type);
- CcpInfo.want_proto = 0;
+ CcpInfo.my_proto = -1;
break;
}
- break;
- case TY_BSD:
- default:
- CcpInfo.my_reject |= (1 << type);
- memcpy(rejp, cp, length);
- rejp += length;
- break;
}
+
plen -= length;
cp += length;
}
+
+ if (rejp != RejBuff) {
+ ackp = AckBuff; /* let's not send both ! */
+ CcpInfo.his_proto = -1;
+ in_algorithm = -1;
+ }
}
void
@@ -282,3 +384,33 @@ CcpInput(struct mbuf *bp)
pfree(bp);
}
}
+
+void
+CcpResetInput()
+{
+ if (in_algorithm >= 0 && in_algorithm < NALGORITHMS)
+ (*algorithm[in_algorithm]->i.Reset)();
+}
+
+int
+CcpOutput(int pri, u_short proto, struct mbuf *m)
+{
+ if (out_algorithm >= 0 && out_algorithm < NALGORITHMS)
+ return (*algorithm[out_algorithm]->o.Write)(pri, proto, m);
+ return 0;
+}
+
+struct mbuf *
+CompdInput(u_short *proto, struct mbuf *m)
+{
+ if (in_algorithm >= 0 && in_algorithm < NALGORITHMS)
+ return (*algorithm[in_algorithm]->i.Read)(proto, m);
+ return NULL;
+}
+
+void
+CcpDictSetup(u_short proto, struct mbuf *m)
+{
+ if (in_algorithm >= 0 && in_algorithm < NALGORITHMS)
+ (*algorithm[in_algorithm]->i.DictSetup)(proto, m);
+}
diff --git a/usr.sbin/ppp/ccp.h b/usr.sbin/ppp/ccp.h
index 8585f17..a9e7e8f 100644
--- a/usr.sbin/ppp/ccp.h
+++ b/usr.sbin/ppp/ccp.h
@@ -15,7 +15,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: ccp.h,v 1.8 1997/10/26 01:02:12 brian Exp $
+ * $Id: ccp.h,v 1.9 1997/11/22 03:37:25 brian Exp $
*
* TODO:
*/
@@ -32,19 +32,44 @@
#define TY_GAND 19 /* Gandalf FZA */
#define TY_V42BIS 20 /* V.42bis compression */
#define TY_BSD 21 /* BSD LZW Compress */
+#define TY_DEFLATE 24 /* Deflate (gzip) */
struct ccpstate {
u_long his_proto; /* peer's compression protocol */
- u_long want_proto; /* my compression protocol */
+ u_long my_proto; /* our compression protocol */
u_long his_reject; /* Request codes rejected by peer */
u_long my_reject; /* Request codes I have rejected */
- u_long orgout, compout;
- u_long orgin, compin;
+ u_long uncompout, compout;
+ u_long uncompin, compin;
};
extern struct ccpstate CcpInfo;
+
+struct ccp_algorithm {
+ int id;
+ int Conf; /* A Conf value from vars.h */
+ const char *(*Disp)(struct lcp_opt *);
+ struct {
+ void (*Get)(struct lcp_opt *);
+ int (*Set)(struct lcp_opt *);
+ int (*Init)(void);
+ void (*Term)(void);
+ void (*Reset)(void);
+ struct mbuf *(*Read)(u_short *, struct mbuf *);
+ void (*DictSetup)(u_short, struct mbuf *);
+ } i;
+ struct {
+ void (*Get)(struct lcp_opt *);
+ int (*Set)(struct lcp_opt *);
+ int (*Init)(void);
+ void (*Term)(void);
+ void (*Reset)(void);
+ int (*Write)(int, u_short, struct mbuf *);
+ } o;
+};
+
extern struct fsm CcpFsm;
extern void CcpRecvResetReq(struct fsm *);
@@ -54,3 +79,7 @@ extern void CcpUp(void);
extern void CcpOpen(void);
extern void CcpInit(void);
extern int ReportCcpStatus(struct cmdargs const *);
+extern void CcpResetInput(void);
+extern int CcpOutput(int, u_short, struct mbuf *);
+extern struct mbuf *CompdInput(u_short *, struct mbuf *);
+extern void CcpDictSetup(u_short, struct mbuf *);
diff --git a/usr.sbin/ppp/deflate.c b/usr.sbin/ppp/deflate.c
new file mode 100644
index 0000000..a759288
--- /dev/null
+++ b/usr.sbin/ppp/deflate.c
@@ -0,0 +1,499 @@
+/*
+ * $Id$
+ */
+
+#include <sys/param.h>
+#include <netinet/in.h>
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <zlib.h>
+
+#include "command.h"
+#include "mbuf.h"
+#include "log.h"
+#include "defs.h"
+#include "loadalias.h"
+#include "vars.h"
+#include "hdlc.h"
+#include "lcp.h"
+#include "ccp.h"
+#include "lcpproto.h"
+#include "timer.h"
+#include "fsm.h"
+#include "deflate.h"
+
+/* Our state */
+struct deflate_state {
+ u_short seqno;
+ z_stream cx;
+};
+
+static int iWindowSize = 15;
+static int oWindowSize = 15;
+static struct deflate_state InputState, OutputState;
+static char garbage[10];
+static u_char EMPTY_BLOCK[4] = { 0x00, 0x00, 0xff, 0xff };
+
+#define DEFLATE_CHUNK_LEN 1024 /* Allocate mbufs this size */
+
+static void
+DeflateResetOutput(void)
+{
+ OutputState.seqno = 0;
+ deflateReset(&OutputState.cx);
+ LogPrintf(LogCCP, "Deflate: Output channel reset\n");
+}
+
+static int
+DeflateOutput(int pri, u_short proto, struct mbuf *mp)
+{
+ u_char *wp, *rp;
+ int olen, ilen, len, res, flush;
+ struct mbuf *mo_head, *mo, *mi_head, *mi;
+
+ ilen = plength(mp);
+ LogPrintf(LogDEBUG, "DeflateOutput: Proto %02x (%d bytes)\n", proto, ilen);
+ LogDumpBp(LogDEBUG, "DeflateOutput: Compress packet:", mp);
+
+ /* Stuff the protocol in front of the input */
+ mi_head = mi = mballoc(2, MB_HDLCOUT);
+ mi->next = mp;
+ rp = MBUF_CTOP(mi);
+ if (proto < 0x100) { /* Compress the protocol */
+ rp[0] = proto & 0377;
+ mi->cnt = 1;
+ } else { /* Don't compress the protocol */
+ rp[0] = proto >> 8;
+ rp[1] = proto & 0377;
+ mi->cnt = 2;
+ }
+
+ /* Allocate the initial output mbuf */
+ mo_head = mo = mballoc(DEFLATE_CHUNK_LEN, MB_HDLCOUT);
+ mo->cnt = 2;
+ wp = MBUF_CTOP(mo);
+ *wp++ = OutputState.seqno >> 8;
+ *wp++ = OutputState.seqno & 0377;
+ LogPrintf(LogDEBUG, "DeflateOutput: Seq %d\n", OutputState.seqno);
+ OutputState.seqno++;
+
+ /* Set up the deflation context */
+ OutputState.cx.next_out = wp;
+ OutputState.cx.avail_out = DEFLATE_CHUNK_LEN - 2;
+ OutputState.cx.next_in = MBUF_CTOP(mi);
+ OutputState.cx.avail_in = mi->cnt;
+ flush = Z_NO_FLUSH;
+
+ olen = 0;
+ while (1) {
+ if ((res = deflate(&OutputState.cx, flush)) != Z_OK) {
+ if (res == Z_STREAM_END)
+ break; /* Done */
+ LogPrintf(LogERROR, "DeflateOutput: deflate returned %d (%s)\n",
+ res, OutputState.cx.msg ? OutputState.cx.msg : "");
+ pfree(mo_head);
+ mbfree(mi_head);
+ OutputState.seqno--;
+ return 1; /* packet dropped */
+ }
+
+ if (flush == Z_SYNC_FLUSH && OutputState.cx.avail_out != 0)
+ break;
+
+ if (OutputState.cx.avail_in == 0 && mi->next != NULL) {
+ mi = mi->next;
+ OutputState.cx.next_in = MBUF_CTOP(mi);
+ OutputState.cx.avail_in = mi->cnt;
+ if (mi->next == NULL)
+ flush = Z_SYNC_FLUSH;
+ }
+
+ if (OutputState.cx.avail_out == 0) {
+ mo->next = mballoc(DEFLATE_CHUNK_LEN, MB_HDLCOUT);
+ olen += (mo->cnt = DEFLATE_CHUNK_LEN);
+ mo = mo->next;
+ mo->cnt = 0;
+ OutputState.cx.next_out = MBUF_CTOP(mo);
+ OutputState.cx.avail_out = DEFLATE_CHUNK_LEN;
+ }
+ }
+
+ olen += (mo->cnt = DEFLATE_CHUNK_LEN - OutputState.cx.avail_out);
+ olen -= 4; /* exclude the trailing EMPTY_BLOCK */
+
+ /*
+ * If the output packet (including seqno and excluding the EMPTY_BLOCK)
+ * got bigger, send the original - returning 0 to HdlcOutput() will
+ * continue to send ``mp''.
+ */
+ if (olen >= ilen) {
+ pfree(mo_head);
+ mbfree(mi_head);
+ LogPrintf(LogDEBUG, "DeflateOutput: %d => %d: Uncompressible (0x%04x)\n",
+ ilen, olen, proto);
+ CcpInfo.uncompout += ilen;
+ CcpInfo.compout += ilen; /* We measure this stuff too */
+ return 0;
+ }
+
+ pfree(mi_head);
+
+ /*
+ * Lose the last four bytes of our output.
+ * XXX: We should probably assert that these are the same as the
+ * contents of EMPTY_BLOCK.
+ */
+ for (mo = mo_head, len = mo->cnt; len < olen; mo = mo->next, len += mo->cnt)
+ ;
+ mo->cnt -= len - olen;
+ if (mo->next != NULL) {
+ pfree(mo->next);
+ mo->next = NULL;
+ }
+
+ CcpInfo.uncompout += ilen;
+ CcpInfo.compout += olen;
+
+ LogPrintf(LogDEBUG, "DeflateOutput: %d => %d bytes, proto 0x%04x\n",
+ ilen, olen, proto);
+
+ HdlcOutput(PRI_NORMAL, PROTO_COMPD, mo_head);
+ return 1;
+}
+
+static void
+DeflateResetInput(void)
+{
+ InputState.seqno = 0;
+ inflateReset(&InputState.cx);
+ LogPrintf(LogCCP, "Deflate: Input channel reset\n");
+}
+
+static struct mbuf *
+DeflateInput(u_short *proto, struct mbuf *mi)
+{
+ struct mbuf *mo, *mo_head, *mi_head;
+ u_char *wp;
+ int ilen, olen;
+ int seq, flush, res, first;
+ u_char hdr[2];
+
+ LogDumpBp(LogDEBUG, "DeflateInput: Decompress packet:", mi);
+ mi_head = mi = mbread(mi, hdr, 2);
+ ilen = 2;
+
+ /* Check the sequence number. */
+ seq = (hdr[0] << 8) + hdr[1];
+ LogPrintf(LogDEBUG, "DeflateInput: Seq %d\n", seq);
+ if (seq != InputState.seqno) {
+ LogPrintf(LogERROR, "DeflateInput: Seq error: Got %d, expected %d\n",
+ seq, InputState.seqno);
+ pfree(mi_head);
+ CcpSendResetReq(&CcpFsm);
+ return NULL;
+ }
+ InputState.seqno++;
+
+ /* Allocate an output mbuf */
+ mo_head = mo = mballoc(DEFLATE_CHUNK_LEN, MB_IPIN);
+
+ /* Our proto starts with 0 if it's compressed */
+ wp = MBUF_CTOP(mo);
+ wp[0] = '\0';
+
+ /*
+ * We set avail_out to 1 initially so we can look at the first
+ * byte of the output and decide whether we have a compressed
+ * proto field.
+ */
+ InputState.cx.next_in = MBUF_CTOP(mi);
+ InputState.cx.avail_in = mi->cnt;
+ InputState.cx.next_out = wp + 1;
+ InputState.cx.avail_out = 1;
+ ilen += mi->cnt;
+
+ flush = mi->next ? Z_NO_FLUSH : Z_SYNC_FLUSH;
+ first = 1;
+ olen = 0;
+
+ while (1) {
+ if ((res = inflate(&InputState.cx, flush)) != Z_OK) {
+ if (res == Z_STREAM_END)
+ break; /* Done */
+ LogPrintf(LogERROR, "DeflateInput: inflate returned %d (%s)\n",
+ res, InputState.cx.msg ? InputState.cx.msg : "");
+ pfree(mo_head);
+ pfree(mi);
+ CcpSendResetReq(&CcpFsm);
+ return NULL;
+ }
+
+ if (flush == Z_SYNC_FLUSH && InputState.cx.avail_out != 0)
+ break;
+
+ if (InputState.cx.avail_in == 0 && mi && (mi = mbfree(mi)) != NULL) {
+ /* underflow */
+ InputState.cx.next_in = MBUF_CTOP(mi);
+ ilen += (InputState.cx.avail_in = mi->cnt);
+ if (mi->next == NULL)
+ flush = Z_SYNC_FLUSH;
+ }
+
+ if (InputState.cx.avail_out == 0)
+ /* overflow */
+ if (first) {
+ if (!(wp[1] & 1)) {
+ /* 2 byte proto, shuffle it back in output */
+ wp[0] = wp[1];
+ InputState.cx.next_out--;
+ InputState.cx.avail_out = DEFLATE_CHUNK_LEN-1;
+ } else
+ InputState.cx.avail_out = DEFLATE_CHUNK_LEN-2;
+ first = 0;
+ } else {
+ olen += (mo->cnt = DEFLATE_CHUNK_LEN);
+ mo->next = mballoc(DEFLATE_CHUNK_LEN, MB_IPIN);
+ mo = mo->next;
+ InputState.cx.next_out = MBUF_CTOP(mo);
+ InputState.cx.avail_out = DEFLATE_CHUNK_LEN;
+ }
+ }
+
+ if (mi != NULL)
+ pfree(mi);
+
+ if (first) {
+ LogPrintf(LogERROR, "DeflateInput: Length error\n");
+ pfree(mo_head);
+ CcpSendResetReq(&CcpFsm);
+ return NULL;
+ }
+
+ olen += (mo->cnt = DEFLATE_CHUNK_LEN - InputState.cx.avail_out);
+
+ *proto = ((u_short)wp[0] << 8) | wp[1];
+ mo_head->offset += 2;
+ mo_head->cnt -= 2;
+ olen -= 2;
+
+ CcpInfo.compin += ilen;
+ CcpInfo.uncompin += olen;
+
+ LogPrintf(LogDEBUG, "DeflateInput: %d => %d bytes, proto 0x%04x\n",
+ ilen, olen, *proto);
+
+ /*
+ * Simulate an EMPTY_BLOCK so that our dictionary stays in sync.
+ * The peer will have silently removed this!
+ */
+ InputState.cx.next_out = garbage;
+ InputState.cx.avail_out = sizeof garbage;
+ InputState.cx.next_in = EMPTY_BLOCK;
+ InputState.cx.avail_in = sizeof EMPTY_BLOCK;
+ inflate(&InputState.cx, Z_SYNC_FLUSH);
+
+ return mo_head;
+}
+
+static void
+DeflateDictSetup(u_short proto, struct mbuf *mi)
+{
+ int res, flush;
+ u_char *rp;
+ struct mbuf *mi_head;
+ short len;
+
+ LogPrintf(LogDEBUG, "DeflateDictSetup: Got seq %d\n", InputState.seqno);
+
+ /*
+ * Stuff an ``uncompressed data'' block header followed by the
+ * protocol in front of the input
+ */
+ mi_head = mballoc(7, MB_HDLCOUT);
+ mi_head->next = mi;
+ len = plength(mi);
+ mi = mi_head;
+ rp = MBUF_CTOP(mi);
+ if (proto < 0x100) { /* Compress the protocol */
+ rp[5] = proto & 0377;
+ mi->cnt = 6;
+ len++;
+ } else { /* Don't compress the protocol */
+ rp[5] = proto >> 8;
+ rp[6] = proto & 0377;
+ mi->cnt = 7;
+ len += 2;
+ }
+ rp[0] = 0x80; /* BITS: 100xxxxx */
+ rp[1] = len & 0377; /* The length */
+ rp[2] = len >> 8;
+ rp[3] = (~len) & 0377; /* One's compliment of the length */
+ rp[4] = (~len) >> 8;
+
+ InputState.cx.next_in = rp;
+ InputState.cx.avail_in = mi->cnt;
+ InputState.cx.next_out = garbage;
+ InputState.cx.avail_out = sizeof garbage;
+ flush = Z_NO_FLUSH;
+
+ while (1) {
+ if ((res = inflate(&InputState.cx, flush)) != Z_OK) {
+ if (res == Z_STREAM_END)
+ break; /* Done */
+ LogPrintf(LogERROR, "DeflateDictSetup: inflate returned %d (%s)\n",
+ res, InputState.cx.msg ? InputState.cx.msg : "");
+ CcpSendResetReq(&CcpFsm);
+ mbfree(mi_head); /* lose our allocated ``head'' buf */
+ return;
+ }
+
+ if (flush == Z_SYNC_FLUSH && InputState.cx.avail_out != 0)
+ break;
+
+ if (InputState.cx.avail_in == 0 && mi && (mi = mi->next) != NULL) {
+ /* underflow */
+ InputState.cx.next_in = MBUF_CTOP(mi);
+ InputState.cx.avail_in = mi->cnt;
+ if (mi->next == NULL)
+ flush = Z_SYNC_FLUSH;
+ }
+
+ if (InputState.cx.avail_out == 0) {
+ /* overflow */
+ InputState.cx.next_out = garbage;
+ InputState.cx.avail_out = sizeof garbage;
+ }
+ }
+
+ CcpInfo.compin += len;
+ CcpInfo.uncompin += len;
+
+ InputState.seqno++;
+ mbfree(mi_head); /* lose our allocated ``head'' buf */
+}
+
+static const char *
+DeflateDispOpts(struct lcp_opt *o)
+{
+ static char disp[7];
+
+ sprintf(disp, "win %d", (o->data[0]>>4) + 8);
+ return disp;
+}
+
+static void
+DeflateGetOpts(struct lcp_opt *o)
+{
+ o->id = TY_DEFLATE;
+ o->len = 4;
+ o->data[1] = '\0';
+}
+
+static void
+DeflateGetInputOpts(struct lcp_opt *o)
+{
+ DeflateGetOpts(o);
+ o->data[0] = ((iWindowSize-8)<<4)+8;
+}
+
+static void
+DeflateGetOutputOpts(struct lcp_opt *o)
+{
+ DeflateGetOpts(o);
+ o->data[0] = ((oWindowSize-8)<<4)+8;
+}
+
+static int
+DeflateSetOpts(struct lcp_opt *o, int *sz)
+{
+ if (o->id != TY_DEFLATE || o->len != 4 ||
+ (o->data[0]&15) != 8 || o->data[1] != '\0') {
+ DeflateGetOpts(o);
+ return MODE_REJ;
+ }
+ *sz = (o->data[0] >> 4) + 8;
+ if (*sz > 15) {
+ *sz = 15;
+ DeflateGetOpts(o);
+ return MODE_NAK;
+ }
+
+ return MODE_ACK;
+}
+
+static int
+DeflateSetInputOpts(struct lcp_opt *o)
+{
+ return DeflateSetOpts(o, &iWindowSize);
+}
+
+static int
+DeflateSetOutputOpts(struct lcp_opt *o)
+{
+ return DeflateSetOpts(o, &oWindowSize);
+}
+
+static int
+DeflateInitInput(void)
+{
+ InputState.cx.zalloc = NULL;
+ InputState.cx.opaque = NULL;
+ InputState.cx.zfree = NULL;
+ InputState.cx.next_out = NULL;
+ if (inflateInit2(&InputState.cx, -iWindowSize) != Z_OK)
+ return 0;
+ DeflateResetInput();
+ return 1;
+}
+
+static int
+DeflateInitOutput(void)
+{
+ OutputState.cx.zalloc = NULL;
+ OutputState.cx.opaque = NULL;
+ OutputState.cx.zfree = NULL;
+ OutputState.cx.next_in = NULL;
+ if (deflateInit2(&OutputState.cx, Z_DEFAULT_COMPRESSION, 8,
+ -oWindowSize, 8, Z_DEFAULT_STRATEGY) != Z_OK)
+ return 0;
+ DeflateResetOutput();
+ return 1;
+}
+
+static void
+DeflateTermInput(void)
+{
+ iWindowSize = 15;
+ inflateEnd(&InputState.cx);
+}
+
+static void
+DeflateTermOutput(void)
+{
+ oWindowSize = 15;
+ deflateEnd(&OutputState.cx);
+}
+
+const struct ccp_algorithm DeflateAlgorithm = {
+ TY_DEFLATE,
+ ConfDeflate,
+ DeflateDispOpts,
+ {
+ DeflateGetInputOpts,
+ DeflateSetInputOpts,
+ DeflateInitInput,
+ DeflateTermInput,
+ DeflateResetInput,
+ DeflateInput,
+ DeflateDictSetup
+ },
+ {
+ DeflateGetOutputOpts,
+ DeflateSetOutputOpts,
+ DeflateInitOutput,
+ DeflateTermOutput,
+ DeflateResetOutput,
+ DeflateOutput
+ },
+};
diff --git a/usr.sbin/ppp/deflate.h b/usr.sbin/ppp/deflate.h
new file mode 100644
index 0000000..a879a29
--- /dev/null
+++ b/usr.sbin/ppp/deflate.h
@@ -0,0 +1,5 @@
+/*
+ * $Id$
+ */
+
+extern const struct ccp_algorithm DeflateAlgorithm;
diff --git a/usr.sbin/ppp/fsm.c b/usr.sbin/ppp/fsm.c
index 7bf11eb..48f9d07 100644
--- a/usr.sbin/ppp/fsm.c
+++ b/usr.sbin/ppp/fsm.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: fsm.c,v 1.21 1997/11/11 23:23:11 brian Exp $
+ * $Id: fsm.c,v 1.22 1997/11/22 03:37:31 brian Exp $
*
* TODO:
* o Refer loglevel for log output
@@ -44,7 +44,6 @@
#include "modem.h"
#include "loadalias.h"
#include "vars.h"
-#include "pred.h"
u_char AckBuff[200];
u_char NakBuff[200];
@@ -735,12 +734,12 @@ static void
FsmRecvResetAck(struct fsm * fp, struct fsmheader * lhp, struct mbuf * bp)
{
LogPrintf(fp->LogLevel, "RecvResetAck\n");
- Pred1Init(1); /* Initialize Input part */
+ CcpResetInput();
fp->reqid++;
pfree(bp);
}
-struct fsmcodedesc FsmCodes[] = {
+static const struct fsmcodedesc FsmCodes[] = {
{FsmRecvConfigReq, "Configure Request",},
{FsmRecvConfigAck, "Configure Ack",},
{FsmRecvConfigNak, "Configure Nak",},
@@ -763,7 +762,7 @@ FsmInput(struct fsm * fp, struct mbuf * bp)
{
int len;
struct fsmheader *lhp;
- struct fsmcodedesc *codep;
+ const struct fsmcodedesc *codep;
len = plength(bp);
if (len < sizeof(struct fsmheader)) {
diff --git a/usr.sbin/ppp/fsm.h b/usr.sbin/ppp/fsm.h
index 3c30f89..d3527af 100644
--- a/usr.sbin/ppp/fsm.h
+++ b/usr.sbin/ppp/fsm.h
@@ -15,7 +15,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: fsm.h,v 1.11 1997/10/26 01:02:39 brian Exp $
+ * $Id: fsm.h,v 1.12 1997/11/22 03:37:32 brian Exp $
*
* TODO:
*/
@@ -41,6 +41,7 @@
#define MODE_NAK 1
#define MODE_REJ 2
#define MODE_NOP 3
+#define MODE_ACK 4 /* pseudo mode for ccp negotiations */
#define OPEN_ACTIVE 0
#define OPEN_PASSIVE 1
diff --git a/usr.sbin/ppp/hdlc.c b/usr.sbin/ppp/hdlc.c
index d6fe49a..0c9ef62 100644
--- a/usr.sbin/ppp/hdlc.c
+++ b/usr.sbin/ppp/hdlc.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: hdlc.c,v 1.21 1997/10/26 12:42:10 brian Exp $
+ * $Id: hdlc.c,v 1.22 1997/11/22 03:37:32 brian Exp $
*
* TODO:
*/
@@ -46,7 +46,6 @@
#include "lqr.h"
#include "loadalias.h"
#include "vars.h"
-#include "pred.h"
#include "modem.h"
#include "ccp.h"
@@ -140,6 +139,26 @@ HdlcFcs(u_short fcs, u_char * cp, int len)
return (fcs);
}
+inline u_short
+HdlcFcsBuf(u_short fcs, struct mbuf *m)
+{
+ int len;
+ u_char *pos, *end;
+
+ len = plength(m);
+ pos = MBUF_CTOP(m);
+ end = pos + m->cnt;
+ while (len--) {
+ fcs = (fcs >> 8) ^ fcstab[(fcs ^ *pos++) & 0xff];
+ if (pos == end && len) {
+ m = m->next;
+ pos = MBUF_CTOP(m);
+ end = pos + m->cnt;
+ }
+ }
+ return (fcs);
+}
+
void
HdlcOutput(int pri, u_short proto, struct mbuf * bp)
{
@@ -149,18 +168,16 @@ HdlcOutput(int pri, u_short proto, struct mbuf * bp)
u_char *cp;
u_short fcs;
- if ((proto & 0xfff1) == 0x21) { /* Network Layer protocol */
- if (CcpFsm.state == ST_OPENED) {
- if (CcpInfo.want_proto == TY_PRED1) {
- Pred1Output(pri, proto, bp);
+ if ((proto & 0xfff1) == 0x21) /* Network Layer protocol */
+ if (CcpFsm.state == ST_OPENED)
+ if (CcpOutput(pri, proto, bp))
return;
- }
- }
- }
+
if (DEV_IS_SYNC)
mfcs = NULLBUFF;
else
mfcs = mballoc(2, MB_HDLCOUT);
+
mhp = mballoc(4, MB_HDLCOUT);
mhp->cnt = 0;
cp = MBUF_CTOP(mhp);
@@ -182,7 +199,10 @@ HdlcOutput(int pri, u_short proto, struct mbuf * bp)
mhp->cnt += 2;
}
mhp->next = bp;
+ while (bp->next != NULL)
+ bp = bp->next;
bp->next = mfcs;
+ bp = mhp->next;
lqr = &MyLqrData;
lqr->PeerOutPackets = ifOutPackets++;
@@ -216,6 +236,9 @@ HdlcOutput(int pri, u_short proto, struct mbuf * bp)
if (statp->number == proto)
break;
statp->out_count++;
+
+ LogPrintf(LogDEBUG, "HdlcOutput: proto = 0x%04x\n", proto);
+
if (DEV_IS_SYNC)
ModemOutput(pri, mhp);
else
@@ -227,7 +250,18 @@ DecodePacket(u_short proto, struct mbuf * bp)
{
u_char *cp;
- LogPrintf(LogDEBUG, "DecodePacket: proto = %04x\n", proto);
+ LogPrintf(LogDEBUG, "DecodePacket: proto = 0x%04x\n", proto);
+
+ /*
+ * If proto isn't PROTO_COMPD, we still want to pass it to the
+ * decompression routines so that the dictionary's updated
+ */
+ if (proto == PROTO_COMPD) {
+ if ((bp = CompdInput(&proto, bp)) == NULL)
+ return;
+ } else if ((proto & 0xfff1) == 0x21) /* Network Layer protocol */
+ if (CcpFsm.state == ST_OPENED)
+ CcpDictSetup(proto, bp);
switch (proto) {
case PROTO_LCP:
@@ -259,9 +293,6 @@ DecodePacket(u_short proto, struct mbuf * bp)
case PROTO_CCP:
CcpInput(bp);
break;
- case PROTO_COMPD:
- Pred1Input(bp);
- break;
default:
LogPrintf(LogPHASE, "Unknown protocol 0x%04x\n", proto);
bp->offset -= 2;
diff --git a/usr.sbin/ppp/hdlc.h b/usr.sbin/ppp/hdlc.h
index 3f14cc1..7cb5234 100644
--- a/usr.sbin/ppp/hdlc.h
+++ b/usr.sbin/ppp/hdlc.h
@@ -15,7 +15,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: hdlc.h,v 1.11 1997/10/26 01:02:45 brian Exp $
+ * $Id: hdlc.h,v 1.12 1997/11/22 03:37:33 brian Exp $
*
* TODO:
*/
@@ -62,6 +62,7 @@ extern void HdlcErrorCheck(void);
extern void HdlcInput(struct mbuf *);
extern void HdlcOutput(int, u_short, struct mbuf *bp);
extern u_short HdlcFcs(u_short, u_char *, int);
+extern u_short HdlcFcsBuf(u_short, struct mbuf *);
extern void DecodePacket(u_short, struct mbuf *);
extern int ReportHdlcStatus(struct cmdargs const *);
extern int ReportProtStatus(struct cmdargs const *);
diff --git a/usr.sbin/ppp/ipcp.c b/usr.sbin/ppp/ipcp.c
index 6e6a4c2..9628112 100644
--- a/usr.sbin/ppp/ipcp.c
+++ b/usr.sbin/ppp/ipcp.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: ipcp.c,v 1.37 1997/11/18 14:52:04 brian Exp $
+ * $Id: ipcp.c,v 1.38 1997/11/22 03:37:34 brian Exp $
*
* TODO:
* o More RFC1772 backwoard compatibility
@@ -145,10 +145,10 @@ ReportIpcpStatus(struct cmdargs const *arg)
if (!VarTerm)
return 1;
fprintf(VarTerm, "%s [%s]\n", fp->name, StateNames[fp->state]);
- fprintf(VarTerm, " his side: %s, %lx\n",
- inet_ntoa(icp->his_ipaddr), icp->his_compproto);
- fprintf(VarTerm, " my side: %s, %lx\n",
- inet_ntoa(icp->want_ipaddr), icp->want_compproto);
+ fprintf(VarTerm, " his side: %s, %s\n",
+ inet_ntoa(icp->his_ipaddr), vj2asc(icp->his_compproto));
+ fprintf(VarTerm, " my side: %s, %s\n",
+ inet_ntoa(icp->want_ipaddr), vj2asc(icp->want_compproto));
fprintf(VarTerm, "Defaults:\n");
fprintf(VarTerm, " My Address: %s/%d\n",
@@ -228,18 +228,31 @@ IpcpSendConfigReq(struct fsm * fp)
{
u_char *cp;
struct ipcpstate *icp = &IpcpInfo;
+ struct lcp_opt o;
cp = ReqBuff;
LogPrintf(LogIPCP, "IpcpSendConfigReq\n");
- if (!DEV_IS_SYNC || !REJECTED(icp, TY_IPADDR))
- PutConfValue(LogIPCP, &cp, cftypes, TY_IPADDR, 6,
- ntohl(icp->want_ipaddr.s_addr));
+ if (!DEV_IS_SYNC || !REJECTED(icp, TY_IPADDR)) {
+ o.id = TY_IPADDR;
+ o.len = 6;
+ *(u_long *)o.data = icp->want_ipaddr.s_addr;
+ cp += LcpPutConf(LogIPCP, cp, &o, cftypes[o.id],
+ inet_ntoa(icp->want_ipaddr));
+ }
+
if (icp->want_compproto && !REJECTED(icp, TY_COMPPROTO)) {
- if (icp->heis1172)
- PutConfValue(LogIPCP, &cp, cftypes, TY_COMPPROTO, 4,
- icp->want_compproto >> 16);
- else
- PutConfValue(LogIPCP, &cp, cftypes, TY_COMPPROTO, 6, icp->want_compproto);
+ const char *args;
+ o.id = TY_COMPPROTO;
+ if (icp->heis1172) {
+ o.len = 4;
+ *(u_short *)o.data = htons(PROTO_VJCOMP);
+ args = "";
+ } else {
+ o.len = 6;
+ *(u_long *)o.data = htonl(icp->want_compproto);
+ args = vj2asc(icp->want_compproto);
+ }
+ cp += LcpPutConf(LogIPCP, cp, &o, cftypes[o.id], args);
}
FsmOutput(fp, CODE_CONFIGREQ, fp->reqid++, ReqBuff, cp - ReqBuff);
}
@@ -403,7 +416,7 @@ IpcpDecodeConfig(u_char * cp, int plen, int mode_type)
case TY_COMPPROTO:
lp = (u_long *) (cp + 2);
compproto = htonl(*lp);
- LogPrintf(LogIPCP, "%s %08x\n", tbuff, compproto);
+ LogPrintf(LogIPCP, "%s %s\n", tbuff, vj2asc(compproto));
switch (mode_type) {
case MODE_REQ:
diff --git a/usr.sbin/ppp/lcp.c b/usr.sbin/ppp/lcp.c
index 5bca853..ac74eed 100644
--- a/usr.sbin/ppp/lcp.c
+++ b/usr.sbin/ppp/lcp.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: lcp.c,v 1.47 1997/11/18 14:52:05 brian Exp $
+ * $Id: lcp.c,v 1.48 1997/11/22 03:37:35 brian Exp $
*
* TODO:
* o Validate magic number received from peer.
@@ -36,6 +36,7 @@
#include <net/if_tun.h>
#include <signal.h>
+#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
@@ -68,6 +69,14 @@
#include "modem.h"
#include "tun.h"
+/* for received LQRs */
+struct lqrreq {
+ u_char type;
+ u_char length;
+ u_short proto; /* Quality protocol */
+ u_long period; /* Reporting interval */
+};
+
struct lcpstate LcpInfo;
static void LcpSendConfigReq(struct fsm *);
@@ -80,8 +89,6 @@ static void LcpLayerDown(struct fsm *);
static void LcpLayerStart(struct fsm *);
static void LcpLayerFinish(struct fsm *);
-#define REJECTED(p, x) (p->his_reject & (1<<x))
-
static const char *cftypes[] = {
/* Check out the latest ``Assigned numbers'' rfc (rfc1700.txt) */
"???",
@@ -223,78 +230,122 @@ LcpInitRestartCounter(struct fsm * fp)
fp->restart = 5;
}
-void
-PutConfValue(int level, u_char ** cpp, const char **types, u_char type,
- int len, u_long val)
+int
+LcpPutConf(int log, u_char *tgt, const struct lcp_opt *o, const char *nm,
+ const char *arg, ...)
{
- u_char *cp;
- struct in_addr ina;
-
- cp = *cpp;
- *cp++ = type;
- *cp++ = len;
- if (len == 6) {
- if (type == TY_IPADDR) {
- ina.s_addr = htonl(val);
- LogPrintf(level, " %s [%d] %s\n",
- types[type], len, inet_ntoa(ina));
- } else
- LogPrintf(level, " %s [%d] %08x\n", types[type], len, val);
- *cp++ = (val >> 24) & 0377;
- *cp++ = (val >> 16) & 0377;
- } else
- LogPrintf(level, " %s [%d] %d\n", types[type], len, val);
- *cp++ = (val >> 8) & 0377;
- *cp++ = val & 0377;
- *cpp = cp;
+ va_list ap;
+ char buf[30];
+
+ va_start(ap, arg);
+ memcpy(tgt, o, o->len);
+ if (arg == NULL || *arg == '\0')
+ LogPrintf(log, " %s[%d]\n", nm, o->len);
+ else {
+ vsnprintf(buf, sizeof buf, arg, ap);
+ LogPrintf(log, " %s[%d] %s\n", nm, o->len, buf);
+ }
+ va_end(ap);
+
+ return o->len;
}
+#define PUTN(ty) \
+do { \
+ o.id = ty; \
+ o.len = 2; \
+ cp += LcpPutConf(LogLCP, cp, &o, cftypes[o.id], NULL); \
+} while (0)
+
+#define PUTHEXL(ty, arg) \
+do { \
+ o.id = ty; \
+ o.len = 6; \
+ *(u_long *)o.data = htonl(arg); \
+ cp += LcpPutConf(LogLCP, cp, &o, cftypes[o.id], "0x%08x", (u_int)arg);\
+} while (0)
+
+#define PUTACCMAP(arg) PUTHEXL(TY_ACCMAP, arg)
+#define PUTMAGIC(arg) PUTHEXL(TY_MAGICNUM, arg)
+
+#define PUTMRU(arg) \
+do { \
+ o.id = TY_MRU; \
+ o.len = 4; \
+ *(u_short *)o.data = htons(arg); \
+ cp += LcpPutConf(LogLCP, cp, &o, cftypes[o.id], "%lu", arg); \
+} while (0)
+
+#define PUTLQR(period) \
+do { \
+ o.id = TY_QUALPROTO; \
+ o.len = 8; \
+ *(u_short *)o.data = htons(PROTO_LQR); \
+ *(u_long *)(o.data+2) = period; \
+ cp += LcpPutConf(LogLCP, cp, &o, cftypes[o.id], "period %ld", period);\
+} while (0)
+
+#define PUTPAP() \
+do { \
+ o.id = TY_AUTHPROTO; \
+ o.len = 4; \
+ *(u_short *)o.data = PROTO_PAP; \
+ cp += LcpPutConf(LogLCP, cp, &o, cftypes[o.id], "PAP REQ"); \
+} while (0)
+
+#define PUTCHAP(val) \
+do { \
+ o.id = TY_AUTHPROTO; \
+ o.len = 5; \
+ *(u_short *)o.data = PROTO_CHAP; \
+ o.data[4] = val; \
+ cp += LcpPutConf(LogLCP, cp, &o, cftypes[o.id], "CHAP REQ (0x%02x)", val);\
+} while (0)
+
+#define PUTMD5CHAP() PUTCHAP(0x05)
+#define PUTMSCHAP() PUTCHAP(0x80)
+
static void
LcpSendConfigReq(struct fsm * fp)
{
u_char *cp;
struct lcpstate *lcp = &LcpInfo;
- struct lqrreq *req;
+ struct lcp_opt o;
LogPrintf(LogLCP, "LcpSendConfigReq\n");
cp = ReqBuff;
if (!DEV_IS_SYNC) {
- if (lcp->want_acfcomp && !REJECTED(lcp, TY_ACFCOMP)) {
- *cp++ = TY_ACFCOMP;
- *cp++ = 2;
- LogPrintf(LogLCP, " %s\n", cftypes[TY_ACFCOMP]);
- }
- if (lcp->want_protocomp && !REJECTED(lcp, TY_PROTOCOMP)) {
- *cp++ = TY_PROTOCOMP;
- *cp++ = 2;
- LogPrintf(LogLCP, " %s\n", cftypes[TY_PROTOCOMP]);
- }
+ if (lcp->want_acfcomp && !REJECTED(lcp, TY_ACFCOMP))
+ PUTN(TY_ACFCOMP);
+
+ if (lcp->want_protocomp && !REJECTED(lcp, TY_PROTOCOMP))
+ PUTN(TY_PROTOCOMP);
+
if (!REJECTED(lcp, TY_ACCMAP))
- PutConfValue(LogLCP, &cp, cftypes, TY_ACCMAP, 6, lcp->want_accmap);
+ PUTACCMAP(lcp->want_accmap);
}
+
if (!REJECTED(lcp, TY_MRU))
- PutConfValue(LogLCP, &cp, cftypes, TY_MRU, 4, lcp->want_mru);
+ PUTMRU(lcp->want_mru);
+
if (lcp->want_magic && !REJECTED(lcp, TY_MAGICNUM))
- PutConfValue(LogLCP, &cp, cftypes, TY_MAGICNUM, 6, lcp->want_magic);
- if (lcp->want_lqrperiod && !REJECTED(lcp, TY_QUALPROTO)) {
- req = (struct lqrreq *) cp;
- req->type = TY_QUALPROTO;
- req->length = sizeof(struct lqrreq);
- req->proto = htons(PROTO_LQR);
- req->period = htonl(lcp->want_lqrperiod);
- cp += sizeof(struct lqrreq);
- LogPrintf(LogLCP, " %s (%d)\n", cftypes[TY_QUALPROTO], lcp->want_lqrperiod);
- }
+ PUTMAGIC(lcp->want_magic);
+
+ if (lcp->want_lqrperiod && !REJECTED(lcp, TY_QUALPROTO))
+ PUTLQR(lcp->want_lqrperiod);
+
switch (lcp->want_auth) {
case PROTO_PAP:
- PutConfValue(LogLCP, &cp, cftypes, TY_AUTHPROTO, 4, lcp->want_auth);
+ PUTPAP();
break;
+
case PROTO_CHAP:
- PutConfValue(LogLCP, &cp, cftypes, TY_AUTHPROTO, 5, lcp->want_auth);
#ifdef HAVE_DES
- *cp++ = VarMSChap ? 0x80 : 0x05; /* Use MSChap vs. RFC 1994 (MD5) */
+ if (VarMSChap)
+ PUTMSCHAP(); /* Use MSChap */
+ else
#else
- *cp++ = 0x05; /* Use MD5 */
+ PUTMD5CHAP(); /* Use MD5 */
#endif
break;
}
@@ -420,13 +471,13 @@ LcpClose()
* XXX: Should validate option length
*/
static void
-LcpDecodeConfig(u_char * cp, int plen, int mode_type)
+LcpDecodeConfig(u_char *cp, int plen, int mode_type)
{
- const char *request;
- int type, length, mru, mtu;
+ int type, length, mru, mtu, sz, pos;
u_long *lp, magic, accmap;
u_short *sp, proto;
struct lqrreq *req;
+ char request[20], desc[22];
ackp = AckBuff;
nakp = NakBuff;
@@ -435,16 +486,17 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
while (plen >= sizeof(struct fsmconfig)) {
type = *cp;
length = cp[1];
- if (type < NCFTYPES)
- request = cftypes[type];
+
+ if (type < 0 || type >= NCFTYPES)
+ snprintf(request, sizeof request, " <%d>[%d]", type, length);
else
- request = "???";
+ snprintf(request, sizeof request, " %s[%d]", cftypes[type], length);
switch (type) {
case TY_MRU:
sp = (u_short *) (cp + 2);
mru = htons(*sp);
- LogPrintf(LogLCP, " %s %d\n", request, mru);
+ LogPrintf(LogLCP, "%s %d\n", request, mru);
switch (mode_type) {
case MODE_REQ:
@@ -474,10 +526,11 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
break;
}
break;
+
case TY_ACCMAP:
lp = (u_long *) (cp + 2);
accmap = htonl(*lp);
- LogPrintf(LogLCP, " %s %08x\n", request, accmap);
+ LogPrintf(LogLCP, "%s 0x%08x\n", request, accmap);
switch (mode_type) {
case MODE_REQ:
@@ -493,17 +546,18 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
break;
}
break;
+
case TY_AUTHPROTO:
sp = (u_short *) (cp + 2);
proto = ntohs(*sp);
- LogPrintf(LogLCP, " %s proto = %04x\n", request, proto);
+ LogPrintf(LogLCP, "%s 0x%04x\n", request, proto);
switch (mode_type) {
case MODE_REQ:
switch (proto) {
case PROTO_PAP:
if (length != 4) {
- LogPrintf(LogLCP, " %s bad length (%d)\n", request, length);
+ LogPrintf(LogLCP, " Bad length!\n");
goto reqreject;
}
if (Acceptable(ConfPap)) {
@@ -519,9 +573,10 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
} else
goto reqreject;
break;
+
case PROTO_CHAP:
if (length < 5) {
- LogPrintf(LogLCP, " %s bad length (%d)\n", request, length);
+ LogPrintf(LogLCP, " Bad length!\n");
goto reqreject;
}
#ifdef HAVE_DES
@@ -544,8 +599,9 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
} else
goto reqreject;
break;
+
default:
- LogPrintf(LogLCP, " %s not implemented, NAK.\n", request);
+ LogPrintf(LogLCP, " proto %d not implemented, NAK.\n", proto);
memcpy(nakp, cp, length);
nakp += length;
break;
@@ -558,10 +614,11 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
break;
}
break;
+
case TY_QUALPROTO:
req = (struct lqrreq *) cp;
- LogPrintf(LogLCP, " %s proto: %x, interval: %dms\n",
- request, ntohs(req->proto), ntohl(req->period) * 10);
+ LogPrintf(LogLCP, "%s proto %x, interval %dms\n",
+ request, ntohs(req->proto), ntohl(req->period) * 10);
switch (mode_type) {
case MODE_REQ:
if (ntohs(req->proto) != PROTO_LQR || !Acceptable(ConfLqr))
@@ -582,10 +639,11 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
break;
}
break;
+
case TY_MAGICNUM:
lp = (u_long *) (cp + 2);
magic = ntohl(*lp);
- LogPrintf(LogLCP, " %s %08x\n", request, magic);
+ LogPrintf(LogLCP, "%s 0x%08x\n", request, magic);
switch (mode_type) {
case MODE_REQ:
@@ -611,18 +669,19 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
}
break;
case MODE_NAK:
- LogPrintf(LogLCP, " %s magic %08x has NAKed\n", request, magic);
+ LogPrintf(LogLCP, " Magic 0x%08x is NAKed!\n", magic);
LcpInfo.want_magic = GenerateMagic();
break;
case MODE_REJ:
- LogPrintf(LogLCP, " %s magic has REJected\n", request);
+ LogPrintf(LogLCP, " Magic 0x%80x is REJected!\n", magic);
LcpInfo.want_magic = 0;
LcpInfo.his_reject |= (1 << type);
break;
}
break;
+
case TY_PROTOCOMP:
- LogPrintf(LogLCP, " %s\n", request);
+ LogPrintf(LogLCP, "%s\n", request);
switch (mode_type) {
case MODE_REQ:
@@ -651,8 +710,9 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
break;
}
break;
+
case TY_ACFCOMP:
- LogPrintf(LogLCP, " %s\n", request);
+ LogPrintf(LogLCP, "%s\n", request);
switch (mode_type) {
case MODE_REQ:
if (Acceptable(ConfAcfcomp)) {
@@ -680,8 +740,9 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
break;
}
break;
+
case TY_SDP:
- LogPrintf(LogLCP, " %s\n", request);
+ LogPrintf(LogLCP, "%s\n", request);
switch (mode_type) {
case MODE_REQ:
case MODE_NAK:
@@ -689,13 +750,30 @@ LcpDecodeConfig(u_char * cp, int plen, int mode_type)
break;
}
break;
+
default:
- LogPrintf(LogLCP, " %s[02x]\n", request, type);
+ sz = (sizeof(desc)-2)/2;
+ if (sz > length - 2)
+ sz = length - 2;
+ pos = 0;
+ desc[0] = sz ? ' ' : '\0';
+ for (pos = 0; sz--; pos++)
+ sprintf(desc+(pos<<1)+1, "%02x", cp[pos+2]);
+
+ LogPrintf(LogLCP, "%s%s\n", request, desc);
+
if (mode_type == MODE_REQ) {
- reqreject:
+reqreject:
+ if (length > sizeof(RejBuff) - (rejp - RejBuff)) {
+ length = sizeof(RejBuff) - (rejp - RejBuff);
+ LogPrintf(LogLCP, "Can't REJ length %d - trunating to %d\n",
+ cp[1], length);
+ }
memcpy(rejp, cp, length);
rejp += length;
LcpInfo.my_reject |= (1 << type);
+ if (length != cp[1])
+ return;
}
break;
}
diff --git a/usr.sbin/ppp/lcp.h b/usr.sbin/ppp/lcp.h
index ea5388c..9bf9b00 100644
--- a/usr.sbin/ppp/lcp.h
+++ b/usr.sbin/ppp/lcp.h
@@ -15,11 +15,13 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: lcp.h,v 1.12 1997/11/14 15:39:15 brian Exp $
+ * $Id: lcp.h,v 1.13 1997/11/22 03:37:36 brian Exp $
*
* TODO:
*/
+#define REJECTED(p, x) (p->his_reject & (1<<x))
+
struct lcpstate {
u_long his_mru;
u_long his_accmap;
@@ -57,13 +59,14 @@ struct lcpstate {
#define TY_FCSALT 9 /* FCS-Alternatives */
#define TY_SDP 10 /* Self-Describing-Padding */
-struct lqrreq {
- u_char type;
- u_char length;
- u_short proto; /* Quality protocol */
- u_long period; /* Reporting interval */
+#define MAX_LCP_OPT_LEN 10
+struct lcp_opt {
+ u_char id;
+ u_char len;
+ u_char data[MAX_LCP_OPT_LEN-2];
};
+
extern struct lcpstate LcpInfo;
extern struct fsm LcpFsm;
@@ -73,6 +76,7 @@ extern void LcpSendProtoRej(u_char *, int);
extern void LcpOpen(int);
extern void LcpClose(void);
extern void LcpDown(void);
-extern void PutConfValue(int, u_char **, const char **, u_char, int, u_long);
+extern int LcpPutConf(int, u_char *, const struct lcp_opt *, const char *,
+ const char *, ...);
extern int ReportLcpStatus(struct cmdargs const *);
extern void LcpInput(struct mbuf *);
diff --git a/usr.sbin/ppp/main.c b/usr.sbin/ppp/main.c
index 10add86..c7baf09 100644
--- a/usr.sbin/ppp/main.c
+++ b/usr.sbin/ppp/main.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: main.c,v 1.104 1997/11/18 18:17:25 brian Exp $
+ * $Id: main.c,v 1.105 1997/11/22 03:37:39 brian Exp $
*
* TODO:
* o Add commands for traffic summary, version display, etc.
@@ -61,8 +61,8 @@
#include "modem.h"
#include "os.h"
#include "hdlc.h"
-#include "ccp.h"
#include "lcp.h"
+#include "ccp.h"
#include "ipcp.h"
#include "loadalias.h"
#include "vars.h"
@@ -748,12 +748,9 @@ DoLoop(void)
int tries;
int qlen;
int res;
- pid_t pgroup;
struct tun_data tun;
#define rbuff tun.data
- pgroup = getpgrp();
-
if (mode & MODE_DIRECT) {
LogPrintf(LogDEBUG, "Opening modem\n");
if (OpenModem() < 0)
@@ -976,48 +973,46 @@ DoLoop(void)
IsInteractive(1);
Prompt();
}
- if (netfd >= 0 && FD_ISSET(netfd, &rfds) &&
- ((mode & MODE_OUTGOING_DAEMON) || pgroup == tcgetpgrp(0))) {
+ if (netfd >= 0 && FD_ISSET(netfd, &rfds))
/* something to read from tty */
ReadTty();
+ if (modem >= 0 && FD_ISSET(modem, &wfds)) {
+ /* ready to write into modem */
+ ModemStartOutput(modem);
+ if (modem < 0)
+ dial_up = 1;
}
- if (modem >= 0) {
- if (FD_ISSET(modem, &wfds)) { /* ready to write into modem */
- ModemStartOutput(modem);
- }
- if (FD_ISSET(modem, &rfds)) { /* something to read from modem */
- if (LcpFsm.state <= ST_CLOSED)
- nointr_usleep(10000);
- n = read(modem, rbuff, sizeof(rbuff));
- if ((mode & MODE_DIRECT) && n <= 0) {
- DownConnection();
- } else
- LogDumpBuff(LogASYNC, "ReadFromModem", rbuff, n);
-
- if (LcpFsm.state <= ST_CLOSED) {
+ if (modem >= 0 && FD_ISSET(modem, &rfds)) {
+ /* something to read from modem */
+ if (LcpFsm.state <= ST_CLOSED)
+ nointr_usleep(10000);
+ n = read(modem, rbuff, sizeof(rbuff));
+ if ((mode & MODE_DIRECT) && n <= 0) {
+ DownConnection();
+ } else
+ LogDumpBuff(LogASYNC, "ReadFromModem", rbuff, n);
- /*
- * In dedicated mode, we just discard input until LCP is started.
- */
- if (!(mode & MODE_DEDICATED)) {
- cp = HdlcDetect(rbuff, n);
- if (cp) {
-
- /*
- * LCP packet is detected. Turn ourselves into packet mode.
- */
- if (cp != rbuff) {
- write(modem, rbuff, cp - rbuff);
- write(modem, "\r\n", 2);
- }
- PacketMode();
- } else
- write(fileno(VarTerm), rbuff, n);
- }
- } else {
- if (n > 0)
- AsyncInput(rbuff, n);
+ if (LcpFsm.state <= ST_CLOSED) {
+ /*
+ * In dedicated mode, we just discard input until LCP is started.
+ */
+ if (!(mode & MODE_DEDICATED)) {
+ cp = HdlcDetect(rbuff, n);
+ if (cp) {
+ /*
+ * LCP packet is detected. Turn ourselves into packet mode.
+ */
+ if (cp != rbuff) {
+ write(modem, rbuff, cp - rbuff);
+ write(modem, "\r\n", 2);
+ }
+ PacketMode();
+ } else
+ write(fileno(VarTerm), rbuff, n);
}
+ } else {
+ if (n > 0)
+ AsyncInput(rbuff, n);
}
}
if (tun_in >= 0 && FD_ISSET(tun_in, &rfds)) { /* something to read
diff --git a/usr.sbin/ppp/mbuf.h b/usr.sbin/ppp/mbuf.h
index cdf38af..6877126 100644
--- a/usr.sbin/ppp/mbuf.h
+++ b/usr.sbin/ppp/mbuf.h
@@ -15,7 +15,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: mbuf.h,v 1.8 1997/10/26 12:42:13 brian Exp $
+ * $Id: mbuf.h,v 1.9 1997/11/22 03:37:40 brian Exp $
*
* TODO:
*/
@@ -58,6 +58,5 @@ extern struct mbuf *mbfree(struct mbuf *);
extern void pfree(struct mbuf *);
extern void mbwrite(struct mbuf *, u_char *, int);
extern struct mbuf *mbread(struct mbuf *, u_char *, int);
-extern void DumpBp(struct mbuf *);
extern void LogMemory(void);
extern int ShowMemMap(struct cmdargs const *);
diff --git a/usr.sbin/ppp/os.c b/usr.sbin/ppp/os.c
index 025a24e..1f13b34 100644
--- a/usr.sbin/ppp/os.c
+++ b/usr.sbin/ppp/os.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: os.c,v 1.34 1997/11/16 22:15:07 brian Exp $
+ * $Id: os.c,v 1.35 1997/11/22 03:37:42 brian Exp $
*
*/
#include <sys/param.h>
@@ -55,6 +55,7 @@
#include "arp.h"
#include "systems.h"
#include "route.h"
+#include "lcp.h"
#include "ccp.h"
#include "modem.h"
diff --git a/usr.sbin/ppp/ppp.8 b/usr.sbin/ppp/ppp.8
index 949e5df..a607e55 100644
--- a/usr.sbin/ppp/ppp.8
+++ b/usr.sbin/ppp/ppp.8
@@ -1,4 +1,4 @@
-.\" $Id: ppp.8,v 1.79 1997/11/14 20:07:39 brian Exp $
+.\" $Id: ppp.8,v 1.80 1997/11/18 14:52:06 brian Exp $
.Dd 20 September 1995
.Os FreeBSD
.Dt PPP 8
@@ -1061,7 +1061,7 @@ the current IETF-draft specs. As a default behaviour,
will attempt to use (or be willing to accept) this capability when the
peer agrees (or requests it).
-To disable CCP/predictor functionality completely, use the
+To disable CCP/predictor1 functionality completely, use the
.Dq disable pred1
and
.Dq deny pred1
@@ -1587,6 +1587,14 @@ challenge. Refer to the description of the
.Dq set encrypt
command for further details.
+.It deflate
+Default: Enabled and Accepted. This option decides if deflate
+compression will be used by the Compression Control Protocol (CCP).
+This is the same algorithm as used by the
+.Xr gzip 1
+program.
+
+
.It lqr
Default: Disabled and Accepted. This option decides if Link Quality
Requests will be sent. LQR is a protocol that allows
@@ -1594,13 +1602,6 @@ Requests will be sent. LQR is a protocol that allows
to determine that the link is down without relying on the modems
carrier detect.
-.It msext
-Default: Disabled. This option allows the use of Microsoft's
-.Em PPP
-extensions, supporting the negotiation of the DNS and the NetBIOS NS.
-Enabling this allows us to pass back the values given in "set ns"
-and "set nbns".
-
.It pap
Default: Disabled and Accepted. PAP stands for Password Authentication
Protocol. Only one of PAP and CHAP (above) may be negotiated. With
@@ -1629,7 +1630,7 @@ PAP is accepted by default.
.It pred1
Default: Enabled and Accepted. This option decides if Predictor 1
-compression will be used.
+compression will be used by the Compression Control Protocol (CCP).
.It protocomp
Default: Enabled and Accepted. This option is used to negotiate
@@ -1646,6 +1647,13 @@ The following options are not actually negotiated with the peer.
Therefore, accepting or denying them makes no sense.
.Bl -tag -width 20
+.It msext
+Default: Disabled. This option allows the use of Microsoft's
+.Em PPP
+extensions, supporting the negotiation of the DNS and the NetBIOS NS.
+Enabling this allows us to pass back the values given in "set ns"
+and "set nbns".
+
.It passwdauth
Default: Disabled. Enabling this option will tell the PAP authentication
code to use the password file (see
@@ -2430,6 +2438,7 @@ Get port number if port number is using service name.
.Xr crontab 5 ,
.Xr ftp 1 ,
.Xr getty 8 ,
+.Xr gzip 1 ,
.Xr hostname 1 ,
.Xr inetd 8 ,
.Xr init 8 ,
@@ -2451,3 +2460,7 @@ Get port number if port number is using service name.
This program was originally written by Toshiharu OHNO (tony-o@iij.ad.jp),
and was submitted to FreeBSD-2.0.5 by Atsushi Murai (amurai@spec.co.jp).
It has since had an enormous face lift and looks substantially different.
+
+.Pp
+The zlib compression algorithms used in the DEFLATE protocol are provided
+thanks to Jean-loup Gailly (Copyright 1995).
diff --git a/usr.sbin/ppp/ppp.8.m4 b/usr.sbin/ppp/ppp.8.m4
index 949e5df..a607e55 100644
--- a/usr.sbin/ppp/ppp.8.m4
+++ b/usr.sbin/ppp/ppp.8.m4
@@ -1,4 +1,4 @@
-.\" $Id: ppp.8,v 1.79 1997/11/14 20:07:39 brian Exp $
+.\" $Id: ppp.8,v 1.80 1997/11/18 14:52:06 brian Exp $
.Dd 20 September 1995
.Os FreeBSD
.Dt PPP 8
@@ -1061,7 +1061,7 @@ the current IETF-draft specs. As a default behaviour,
will attempt to use (or be willing to accept) this capability when the
peer agrees (or requests it).
-To disable CCP/predictor functionality completely, use the
+To disable CCP/predictor1 functionality completely, use the
.Dq disable pred1
and
.Dq deny pred1
@@ -1587,6 +1587,14 @@ challenge. Refer to the description of the
.Dq set encrypt
command for further details.
+.It deflate
+Default: Enabled and Accepted. This option decides if deflate
+compression will be used by the Compression Control Protocol (CCP).
+This is the same algorithm as used by the
+.Xr gzip 1
+program.
+
+
.It lqr
Default: Disabled and Accepted. This option decides if Link Quality
Requests will be sent. LQR is a protocol that allows
@@ -1594,13 +1602,6 @@ Requests will be sent. LQR is a protocol that allows
to determine that the link is down without relying on the modems
carrier detect.
-.It msext
-Default: Disabled. This option allows the use of Microsoft's
-.Em PPP
-extensions, supporting the negotiation of the DNS and the NetBIOS NS.
-Enabling this allows us to pass back the values given in "set ns"
-and "set nbns".
-
.It pap
Default: Disabled and Accepted. PAP stands for Password Authentication
Protocol. Only one of PAP and CHAP (above) may be negotiated. With
@@ -1629,7 +1630,7 @@ PAP is accepted by default.
.It pred1
Default: Enabled and Accepted. This option decides if Predictor 1
-compression will be used.
+compression will be used by the Compression Control Protocol (CCP).
.It protocomp
Default: Enabled and Accepted. This option is used to negotiate
@@ -1646,6 +1647,13 @@ The following options are not actually negotiated with the peer.
Therefore, accepting or denying them makes no sense.
.Bl -tag -width 20
+.It msext
+Default: Disabled. This option allows the use of Microsoft's
+.Em PPP
+extensions, supporting the negotiation of the DNS and the NetBIOS NS.
+Enabling this allows us to pass back the values given in "set ns"
+and "set nbns".
+
.It passwdauth
Default: Disabled. Enabling this option will tell the PAP authentication
code to use the password file (see
@@ -2430,6 +2438,7 @@ Get port number if port number is using service name.
.Xr crontab 5 ,
.Xr ftp 1 ,
.Xr getty 8 ,
+.Xr gzip 1 ,
.Xr hostname 1 ,
.Xr inetd 8 ,
.Xr init 8 ,
@@ -2451,3 +2460,7 @@ Get port number if port number is using service name.
This program was originally written by Toshiharu OHNO (tony-o@iij.ad.jp),
and was submitted to FreeBSD-2.0.5 by Atsushi Murai (amurai@spec.co.jp).
It has since had an enormous face lift and looks substantially different.
+
+.Pp
+The zlib compression algorithms used in the DEFLATE protocol are provided
+thanks to Jean-loup Gailly (Copyright 1995).
diff --git a/usr.sbin/ppp/pred.c b/usr.sbin/ppp/pred.c
index 3b4cfff..23b9ec3 100644
--- a/usr.sbin/ppp/pred.c
+++ b/usr.sbin/ppp/pred.c
@@ -5,24 +5,28 @@
* Updated by: Carsten Bormann <cabo@cs.tu-berlin.de>
* Original : Dave Rand <dlr@bungi.com>/<dave_rand@novell.com>
*
- * $Id: pred.c,v 1.16 1997/11/09 06:22:46 brian Exp $
+ * $Id: pred.c,v 1.17 1997/11/22 03:37:44 brian Exp $
*
*/
-#include <sys/types.h>
+#include <sys/param.h>
#include <netinet/in.h>
#include <stdio.h>
+#include <stdlib.h>
#include <string.h>
#include "command.h"
#include "mbuf.h"
#include "log.h"
#include "defs.h"
+#include "loadalias.h"
+#include "vars.h"
#include "timer.h"
#include "fsm.h"
#include "hdlc.h"
#include "lcpproto.h"
+#include "lcp.h"
#include "ccp.h"
#include "pred.h"
@@ -34,10 +38,11 @@
*/
#define IHASH(x) do {iHash = (iHash << 4) ^ (x);} while(0)
#define OHASH(x) do {oHash = (oHash << 4) ^ (x);} while(0)
+#define GUESS_TABLE_SIZE 65536
static unsigned short int iHash, oHash;
-static unsigned char InputGuessTable[65536];
-static unsigned char OutputGuessTable[65536];
+static unsigned char *InputGuessTable;
+static unsigned char *OutputGuessTable;
static int
compress(u_char * source, u_char * dest, int len)
@@ -102,20 +107,61 @@ decompress(u_char * source, u_char * dest, int len)
return (dest - orgdest);
}
-void
-Pred1Init(int direction)
+static void
+Pred1TermInput(void)
{
- if (direction & 1) { /* Input part */
- iHash = 0;
- memset(InputGuessTable, '\0', sizeof(InputGuessTable));
+ if (InputGuessTable != NULL) {
+ free(InputGuessTable);
+ InputGuessTable = NULL;
}
- if (direction & 2) { /* Output part */
- oHash = 0;
- memset(OutputGuessTable, '\0', sizeof(OutputGuessTable));
+}
+
+static void
+Pred1TermOutput(void)
+{
+ if (OutputGuessTable != NULL) {
+ free(OutputGuessTable);
+ OutputGuessTable = NULL;
}
}
-void
+static void
+Pred1ResetInput(void)
+{
+ iHash = 0;
+ memset(InputGuessTable, '\0', GUESS_TABLE_SIZE);
+ LogPrintf(LogCCP, "Predictor1: Input channel reset\n");
+}
+
+static void
+Pred1ResetOutput(void)
+{
+ oHash = 0;
+ memset(OutputGuessTable, '\0', GUESS_TABLE_SIZE);
+ LogPrintf(LogCCP, "Predictor1: Output channel reset\n");
+}
+
+static int
+Pred1InitInput(void)
+{
+ if (InputGuessTable == NULL)
+ if ((InputGuessTable = malloc(GUESS_TABLE_SIZE)) == NULL)
+ return 0;
+ Pred1ResetInput();
+ return 1;
+}
+
+static int
+Pred1InitOutput(void)
+{
+ if (OutputGuessTable == NULL)
+ if ((OutputGuessTable = malloc(GUESS_TABLE_SIZE)) == NULL)
+ return 0;
+ Pred1ResetOutput();
+ return 1;
+}
+
+static int
Pred1Output(int pri, u_short proto, struct mbuf * bp)
{
struct mbuf *mwp;
@@ -138,7 +184,7 @@ Pred1Output(int pri, u_short proto, struct mbuf * bp)
len = compress(bufp + 2, wp, orglen);
LogPrintf(LogDEBUG, "Pred1Output: orglen (%d) --> len (%d)\n", orglen, len);
- CcpInfo.orgout += orglen;
+ CcpInfo.uncompout += orglen;
if (len < orglen) {
*hp |= 0x80;
wp += len;
@@ -153,16 +199,17 @@ Pred1Output(int pri, u_short proto, struct mbuf * bp)
*wp++ = fcs >> 8;
mwp->cnt = wp - MBUF_CTOP(mwp);
HdlcOutput(PRI_NORMAL, PROTO_COMPD, mwp);
+ return 1;
}
-void
-Pred1Input(struct mbuf * bp)
+static struct mbuf *
+Pred1Input(u_short *proto, struct mbuf *bp)
{
u_char *cp, *pp;
int len, olen, len1;
struct mbuf *wp;
u_char *bufp;
- u_short fcs, proto;
+ u_short fcs;
wp = mballoc(MAX_MTU + 2, MB_IPIN);
cp = MBUF_CTOP(bp);
@@ -172,17 +219,17 @@ Pred1Input(struct mbuf * bp)
len = *cp++ << 8;
*pp++ = *cp;
len += *cp++;
- CcpInfo.orgin += len & 0x7fff;
+ CcpInfo.uncompin += len & 0x7fff;
if (len & 0x8000) {
len1 = decompress(cp, pp, olen - 4);
CcpInfo.compin += olen;
len &= 0x7fff;
if (len != len1) { /* Error is detected. Send reset request */
- LogPrintf(LogLCP, "%s: Length Error\n", CcpFsm.name);
+ LogPrintf(LogCCP, "Pred1: Length error\n");
CcpSendResetReq(&CcpFsm);
pfree(bp);
pfree(wp);
- return;
+ return NULL;
}
cp += olen - 4;
pp += len1;
@@ -203,20 +250,72 @@ Pred1Input(struct mbuf * bp)
wp->offset += 2; /* skip length */
wp->cnt -= 4; /* skip length & CRC */
pp = MBUF_CTOP(wp);
- proto = *pp++;
- if (proto & 1) {
+ *proto = *pp++;
+ if (*proto & 1) {
wp->offset++;
wp->cnt--;
} else {
wp->offset += 2;
wp->cnt -= 2;
- proto = (proto << 8) | *pp++;
+ *proto = (*proto << 8) | *pp++;
}
- DecodePacket(proto, wp);
+ return wp;
} else {
LogDumpBp(LogHDLC, "Bad FCS", wp);
CcpSendResetReq(&CcpFsm);
pfree(wp);
}
pfree(bp);
+ return NULL;
+}
+
+static void
+Pred1DictSetup(u_short proto, struct mbuf * bp)
+{
+}
+
+static const char *
+Pred1DispOpts(struct lcp_opt *o)
+{
+ return NULL;
}
+
+static void
+Pred1GetOpts(struct lcp_opt *o)
+{
+ o->id = TY_PRED1;
+ o->len = 2;
+}
+
+static int
+Pred1SetOpts(struct lcp_opt *o)
+{
+ if (o->id != TY_PRED1 || o->len != 2) {
+ Pred1GetOpts(o);
+ return MODE_NAK;
+ }
+ return MODE_ACK;
+}
+
+const struct ccp_algorithm Pred1Algorithm = {
+ TY_PRED1,
+ ConfPred1,
+ Pred1DispOpts,
+ {
+ Pred1GetOpts,
+ Pred1SetOpts,
+ Pred1InitInput,
+ Pred1TermInput,
+ Pred1ResetInput,
+ Pred1Input,
+ Pred1DictSetup
+ },
+ {
+ Pred1GetOpts,
+ Pred1SetOpts,
+ Pred1InitOutput,
+ Pred1TermOutput,
+ Pred1ResetOutput,
+ Pred1Output
+ },
+};
diff --git a/usr.sbin/ppp/pred.h b/usr.sbin/ppp/pred.h
index 9bcc21b..08a0911 100644
--- a/usr.sbin/ppp/pred.h
+++ b/usr.sbin/ppp/pred.h
@@ -15,11 +15,9 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: pred.h,v 1.5 1997/08/25 00:29:26 brian Exp $
+ * $Id: pred.h,v 1.6 1997/10/26 01:03:35 brian Exp $
*
* TODO:
*/
-extern void Pred1Output(int, u_short, struct mbuf *);
-extern void Pred1Input(struct mbuf *);
-extern void Pred1Init(int);
+extern const struct ccp_algorithm Pred1Algorithm;
diff --git a/usr.sbin/ppp/server.c b/usr.sbin/ppp/server.c
index cb7884b..d55dbb4 100644
--- a/usr.sbin/ppp/server.c
+++ b/usr.sbin/ppp/server.c
@@ -1,5 +1,5 @@
/*
- * $Id: server.c,v 1.10 1997/11/11 22:58:13 brian Exp $
+ * $Id: server.c,v 1.11 1997/11/22 03:37:45 brian Exp $
*/
#include <sys/param.h>
@@ -69,7 +69,6 @@ ServerLocalOpen(const char *name, mode_t mask)
if (errno == EADDRINUSE && VarTerm)
fprintf(VarTerm, "Wait for a while, then try again.\n");
close(s);
- ID0unlink(name);
return 4;
}
if (mask != (mode_t)-1)
diff --git a/usr.sbin/ppp/vars.c b/usr.sbin/ppp/vars.c
index 8c5b724..fde9089 100644
--- a/usr.sbin/ppp/vars.c
+++ b/usr.sbin/ppp/vars.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: vars.c,v 1.36 1997/11/22 03:37:53 brian Exp $
+ * $Id: vars.c,v 1.37 1997/11/22 13:47:02 brian Exp $
*
*/
#include <sys/param.h>
@@ -39,7 +39,7 @@
#include "auth.h"
char VarVersion[] = "PPP Version 1.5";
-char VarLocalVersion[] = "$Date: 1997/11/22 03:37:53 $";
+char VarLocalVersion[] = "$Date: 1997/11/22 13:47:02 $";
int Utmp = 0;
int ipInOctets = 0;
int ipOutOctets = 0;
@@ -53,18 +53,19 @@ int reconnectCount = 0;
* Order of conf option is important. See vars.h.
*/
struct confdesc pppConfs[] = {
- {"vjcomp", CONF_ENABLE, CONF_ACCEPT},
- {"lqr", CONF_DISABLE, CONF_ACCEPT},
+ {"acfcomp", CONF_ENABLE, CONF_ACCEPT},
{"chap", CONF_DISABLE, CONF_ACCEPT},
+ {"deflate", CONF_ENABLE, CONF_ACCEPT},
+ {"lqr", CONF_DISABLE, CONF_ACCEPT},
{"pap", CONF_DISABLE, CONF_ACCEPT},
- {"acfcomp", CONF_ENABLE, CONF_ACCEPT},
- {"protocomp", CONF_ENABLE, CONF_ACCEPT},
{"pred1", CONF_ENABLE, CONF_ACCEPT},
- {"proxy", CONF_DISABLE, CONF_NONE},
+ {"protocomp", CONF_ENABLE, CONF_ACCEPT},
+ {"vjcomp", CONF_ENABLE, CONF_ACCEPT},
{"msext", CONF_DISABLE, CONF_NONE},
{"passwdauth", CONF_DISABLE, CONF_NONE},
- {"utmp", CONF_ENABLE, CONF_NONE},
+ {"proxy", CONF_DISABLE, CONF_NONE},
{"throughput", CONF_DISABLE, CONF_NONE},
+ {"utmp", CONF_ENABLE, CONF_NONE},
{NULL},
};
diff --git a/usr.sbin/ppp/vars.h b/usr.sbin/ppp/vars.h
index 79f4f82..5f6cf88 100644
--- a/usr.sbin/ppp/vars.h
+++ b/usr.sbin/ppp/vars.h
@@ -15,7 +15,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: vars.h,v 1.34 1997/11/18 14:52:08 brian Exp $
+ * $Id: vars.h,v 1.35 1997/11/22 03:37:54 brian Exp $
*
* TODO:
*/
@@ -32,19 +32,21 @@ struct confdesc {
#define CONF_DENY 0
#define CONF_ACCEPT 1
-#define ConfVjcomp 0
-#define ConfLqr 1
-#define ConfChap 2
-#define ConfPap 3
-#define ConfAcfcomp 4
-#define ConfProtocomp 5
-#define ConfPred1 6
-#define ConfProxy 7
+#define ConfAcfcomp 0
+#define ConfChap 1
+#define ConfDeflate 2
+#define ConfLqr 3
+#define ConfPap 4
+#define ConfPred1 5
+#define ConfProtocomp 6
+#define ConfVjcomp 7
+
#define ConfMSExt 8
#define ConfPasswdAuth 9
-#define ConfUtmp 10
+#define ConfProxy 10
#define ConfThroughput 11
-#define MAXCONFS 12
+#define ConfUtmp 12
+#define MAXCONFS 13
#define Enabled(x) (pppConfs[x].myside & CONF_ENABLE)
#define Acceptable(x) (pppConfs[x].hisside & CONF_ACCEPT)
diff --git a/usr.sbin/ppp/vjcomp.c b/usr.sbin/ppp/vjcomp.c
index c0fc76f..74e4371 100644
--- a/usr.sbin/ppp/vjcomp.c
+++ b/usr.sbin/ppp/vjcomp.c
@@ -17,7 +17,7 @@
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * $Id: vjcomp.c,v 1.12 1997/11/09 06:22:49 brian Exp $
+ * $Id: vjcomp.c,v 1.13 1997/11/22 03:37:54 brian Exp $
*
* TODO:
*/
@@ -55,14 +55,14 @@ void
SendPppFrame(struct mbuf * bp)
{
int type;
- int proto;
- int cproto = IpcpInfo.his_compproto >> 16;
+ u_short proto;
+ u_short cproto = IpcpInfo.his_compproto >> 16;
LogPrintf(LogDEBUG, "SendPppFrame: proto = %x\n", IpcpInfo.his_compproto);
if (((struct ip *) MBUF_CTOP(bp))->ip_p == IPPROTO_TCP
&& cproto == PROTO_VJCOMP) {
- type = sl_compress_tcp(bp, (struct ip *) MBUF_CTOP(bp), &cslc, IpcpInfo.his_compproto & 0xff);
-
+ type = sl_compress_tcp(bp, (struct ip *)MBUF_CTOP(bp), &cslc,
+ IpcpInfo.his_compproto & 0xff);
LogPrintf(LogDEBUG, "SendPppFrame: type = %x\n", type);
switch (type) {
case TYPE_IP:
@@ -153,3 +153,13 @@ VjCompInput(struct mbuf * bp, int proto)
bp = VjUncompressTcp(bp, type);
return (bp);
}
+
+const char *
+vj2asc(u_long val)
+{
+ static char asc[50];
+
+ sprintf(asc, "%ld VJ slots %s slot compression",
+ ((val>>8)&15)+1, val & 1 ? "with" : "without");
+ return asc;
+}
diff --git a/usr.sbin/ppp/vjcomp.h b/usr.sbin/ppp/vjcomp.h
index 221b591..1589044 100644
--- a/usr.sbin/ppp/vjcomp.h
+++ b/usr.sbin/ppp/vjcomp.h
@@ -1,7 +1,8 @@
/*
- * $Id: vjcomp.h,v 1.1 1997/10/26 01:04:02 brian Exp $
+ * $Id: vjcomp.h,v 1.2 1997/10/26 12:42:13 brian Exp $
*/
extern void VjInit(int);
extern void SendPppFrame(struct mbuf *);
extern struct mbuf *VjCompInput(struct mbuf *, int);
+extern const char *vj2asc(u_long);
OpenPOWER on IntegriCloud