summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGregory Nutt <gnutt@nuttx.org>2015-03-11 07:53:04 -0600
committerGregory Nutt <gnutt@nuttx.org>2015-03-11 07:53:04 -0600
commit55c6a5ce38c1433e984ee5c209d893ceb8ce2312 (patch)
treef4d1b0ea9a094f746d3af4d4a4978fcf25b3c293
parent566ed4018ab7d5b95b29f76daca454385756e578 (diff)
downloadpx4-nuttx-55c6a5ce38c1433e984ee5c209d893ceb8ce2312.tar.gz
px4-nuttx-55c6a5ce38c1433e984ee5c209d893ceb8ce2312.tar.bz2
px4-nuttx-55c6a5ce38c1433e984ee5c209d893ceb8ce2312.zip
Add a PPP daemon. From Max Neklyudov
-rw-r--r--apps/netutils/Kconfig1
-rw-r--r--apps/netutils/Make.defs4
-rw-r--r--apps/netutils/pppd/.gitignore6
-rw-r--r--apps/netutils/pppd/Kconfig23
-rw-r--r--apps/netutils/pppd/Makefile111
-rw-r--r--apps/netutils/pppd/ahdlc.c451
-rw-r--r--apps/netutils/pppd/ahdlc.h84
-rw-r--r--apps/netutils/pppd/chat.c136
-rw-r--r--apps/netutils/pppd/chat.h46
-rw-r--r--apps/netutils/pppd/ipcp.c513
-rw-r--r--apps/netutils/pppd/ipcp.h117
-rw-r--r--apps/netutils/pppd/lcp.c589
-rw-r--r--apps/netutils/pppd/lcp.h133
-rw-r--r--apps/netutils/pppd/ntpv3.h207
-rw-r--r--apps/netutils/pppd/pap.c188
-rw-r--r--apps/netutils/pppd/pap.h113
-rw-r--r--apps/netutils/pppd/ppp.c456
-rw-r--r--apps/netutils/pppd/ppp.h233
-rw-r--r--apps/netutils/pppd/ppp_arch.h59
-rw-r--r--apps/netutils/pppd/ppp_conf.h36
-rw-r--r--apps/netutils/pppd/pppd.c435
21 files changed, 3941 insertions, 0 deletions
diff --git a/apps/netutils/Kconfig b/apps/netutils/Kconfig
index 33702e5a2..114fe044d 100644
--- a/apps/netutils/Kconfig
+++ b/apps/netutils/Kconfig
@@ -22,3 +22,4 @@ source "$APPSDIR/netutils/webserver/Kconfig"
source "$APPSDIR/netutils/ntpclient/Kconfig"
source "$APPSDIR/netutils/discover/Kconfig"
source "$APPSDIR/netutils/xmlrpc/Kconfig"
+source "$APPSDIR/netutils/pppd/Kconfig"
diff --git a/apps/netutils/Make.defs b/apps/netutils/Make.defs
index 41ed1dff9..07998a91c 100644
--- a/apps/netutils/Make.defs
+++ b/apps/netutils/Make.defs
@@ -62,6 +62,10 @@ ifeq ($(CONFIG_NETUTILS_NTPCLIENT),y)
CONFIGURED_APPS += netutils/ntpclient
endif
+ifeq ($(CONFIG_NETUTILS_PPPD),y)
+CONFIGURED_APPS += netutils/pppd
+endif
+
ifeq ($(CONFIG_NETUTILS_DNSCLIENT),y)
CONFIGURED_APPS += netutils/dnsclient
endif
diff --git a/apps/netutils/pppd/.gitignore b/apps/netutils/pppd/.gitignore
new file mode 100644
index 000000000..f21c854d1
--- /dev/null
+++ b/apps/netutils/pppd/.gitignore
@@ -0,0 +1,6 @@
+/.built
+/.depend
+/Make.dep
+/*.src
+/*.obj
+/*.lst
diff --git a/apps/netutils/pppd/Kconfig b/apps/netutils/pppd/Kconfig
new file mode 100644
index 000000000..3d5f92644
--- /dev/null
+++ b/apps/netutils/pppd/Kconfig
@@ -0,0 +1,23 @@
+#
+# For a description of the syntax of this configuration file,
+# see misc/tools/kconfig-language.txt.
+#
+
+config NETUTILS_PPPD
+ bool "PPP daemon"
+ default n
+ select NET_TUN
+ ---help---
+ Enable support for the PPP daemon.
+
+if NETUTILS_PPPD
+
+config NETUTILS_PPPD_STACKSIZE
+ int "PPP daemon stack stack size"
+ default 2048
+
+config NETUTILS_PPPD_SERVERPRIO
+ int "NTP daemon priority"
+ default 100
+
+endif # NETUTILS_PPPD
diff --git a/apps/netutils/pppd/Makefile b/apps/netutils/pppd/Makefile
new file mode 100644
index 000000000..3dafdcc40
--- /dev/null
+++ b/apps/netutils/pppd/Makefile
@@ -0,0 +1,111 @@
+############################################################################
+# apps/netutils/pppd/Makefile
+#
+# Copyright (C) 2015 Max Nekludov. All rights reserved.
+# Author: Max Nekludov <macscomp@gmail.com>
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+#
+# 1. Redistributions of source code must retain the above copyright
+# notice, this list of conditions and the following disclaimer.
+# 2. Redistributions in binary form must reproduce the above copyright
+# notice, this list of conditions and the following disclaimer in
+# the documentation and/or other materials provided with the
+# distribution.
+# 3. Neither the name NuttX nor the names of its contributors may be
+# used to endorse or promote products derived from this software
+# without specific prior written permission.
+#
+# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+# FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+# COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+# OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+# POSSIBILITY OF SUCH DAMAGE.
+#
+############################################################################
+
+-include $(TOPDIR)/.config
+-include $(TOPDIR)/Make.defs
+include $(APPDIR)/Make.defs
+
+APPNAME = pppd
+PRIORITY = SCHED_PRIORITY_DEFAULT
+STACKSIZE = $(CONFIG_NETUTILS_PPPD_STACKSIZE)
+
+ASRCS =
+CSRCS =
+
+CSRCS += pppd.c chat.c ppp.c ahdlc.c lcp.c pap.c ipcp.c
+
+AOBJS = $(ASRCS:.S=$(OBJEXT))
+COBJS = $(CSRCS:.c=$(OBJEXT))
+
+SRCS = $(ASRCS) $(CSRCS)
+OBJS = $(AOBJS) $(COBJS)
+
+ifeq ($(CONFIG_WINDOWS_NATIVE),y)
+ BIN = ..\..\libapps$(LIBEXT)
+else
+ifeq ($(WINTOOL),y)
+ BIN = ..\\..\\libapps$(LIBEXT)
+else
+ BIN = ../../libapps$(LIBEXT)
+endif
+endif
+
+ROOTDEPPATH = --dep-path .
+
+# Common build
+
+VPATH =
+
+all: .built
+.PHONY: context depend clean distclean
+
+$(AOBJS): %$(OBJEXT): %.S
+ $(call ASSEMBLE, $<, $@)
+
+$(COBJS): %$(OBJEXT): %.c
+ $(call COMPILE, $<, $@)
+
+.built: $(OBJS)
+ $(call ARCHIVE, $(BIN), $(OBJS))
+ $(Q) touch .built
+
+install:
+
+# Register application
+
+ifeq ($(CONFIG_NSH_BUILTIN_APPS),y)
+$(BUILTIN_REGISTRY)$(DELIM)$(APPNAME)_main.bdat: $(DEPCONFIG) Makefile
+ $(call REGISTER,$(APPNAME),$(PRIORITY),$(STACKSIZE),$(APPNAME)_main)
+
+context: $(BUILTIN_REGISTRY)$(DELIM)$(APPNAME)_main.bdat
+else
+context:
+endif
+
+.depend: Makefile $(SRCS)
+ $(Q) $(MKDEP) $(ROOTDEPPATH) "$(CC)" -- $(CFLAGS) -- $(SRCS) >Make.dep
+ $(Q) touch $@
+
+depend: .depend
+
+clean:
+ $(call DELFILE, .built)
+ $(call CLEAN)
+
+distclean: clean
+ $(call DELFILE, Make.dep)
+ $(call DELFILE, .depend)
+
+-include Make.dep
diff --git a/apps/netutils/pppd/ahdlc.c b/apps/netutils/pppd/ahdlc.c
new file mode 100644
index 000000000..43c911893
--- /dev/null
+++ b/apps/netutils/pppd/ahdlc.c
@@ -0,0 +1,451 @@
+/* www.mycal.com
+ *---------------------------------------------------------------------------
+ * ahdlc.c - Ahdlc receive and transmit processor for PPP engine.
+ *
+ *---------------------------------------------------------------------------
+ * Version
+ * 0.1 Original Version Jan 11, 1998
+ *
+ *---------------------------------------------------------------------------
+ *
+ * Copyright (C) 1998, Mycal Labs www.mycal.com
+ *
+ *---------------------------------------------------------------------------
+ */
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: ahdlc.c,v 1.1 2007/05/26 07:14:39 oliverschmidt Exp $
+ *
+ */
+
+/* */
+/* include files */
+/* */
+
+#include "ppp_conf.h"
+#include "ppp.h"
+
+#if PPP_DEBUG
+# define DEBUG1(x) debug_printf x
+# define PACKET_TX_DEBUG 1
+#else
+# define DEBUG1(x)
+# undef PACKET_TX_DEBUG
+#endif
+
+/*---------------------------------------------------------------------------
+ * ahdlc flags bit defins, for ahdlc_flags variable
+ ---------------------------------------------------------------------------*/
+
+/* Escaped mode bit */
+
+#define AHDLC_ESCAPED 0x1
+
+/* Frame is ready bit */
+
+#define AHDLC_RX_READY 0x2
+#define AHDLC_RX_ASYNC_MAP 0x4
+#define AHDLC_TX_ASYNC_MAP 0x8
+#define AHDLC_PFC 0x10
+#define AHDLC_ACFC 0x20
+
+/*---------------------------------------------------------------------------*/
+/* Simple and fast CRC16 routine for embedded processors.
+ * Just slightly slower than the table lookup method but consumes
+ * almost no space. Much faster and smaller than the loop and
+ * shift method that is widely used in the embedded space.
+ * Can be optimized even more in .ASM
+ *
+ * data = (crcvalue ^ inputchar) & 0xff;
+ * data = (data ^ (data << 4)) & 0xff;
+ * crc = (crc >> 8) ^ ((data << 8) ^ (data <<3) ^ (data >> 4))
+ */
+/*---------------------------------------------------------------------------*/
+
+static u16_t crcadd(u16_t crcvalue, u8_t c)
+{
+ u16_t b;
+
+ b = (crcvalue ^ c) & 0xFF;
+ b = (b ^ (b << 4)) & 0xFF;
+ b = (b << 8) ^ (b << 3) ^ (b >> 4);
+
+ return ((crcvalue >> 8) ^ b);
+}
+
+/*---------------------------------------------------------------------------*/
+/* ahdlc_init(buffer, buffersize) - this initializes the ahdlc engine to
+ * allow for rx frames.
+ */
+/*---------------------------------------------------------------------------*/
+
+void ahdlc_init(struct ppp_context_s *ctx)
+{
+ ctx->ahdlc_flags = 0 | AHDLC_RX_ASYNC_MAP;
+ ctx->ahdlc_rx_count = 0;
+ ctx->ahdlc_tx_offline = 0;
+
+#ifdef PPP_STATISTICS
+ ctx->ahdlc_rx_tobig_error = 0;
+#endif
+}
+
+/*---------------------------------------------------------------------------*/
+/* ahdlc_rx_ready() - resets the ahdlc engine to the beginning of frame
+ * state.
+ */
+/*---------------------------------------------------------------------------*/
+
+void ahdlc_rx_ready(struct ppp_context_s *ctx)
+{
+ ctx->ahdlc_rx_count = 0;
+ ctx->ahdlc_rx_crc = 0xffff;
+ ctx->ahdlc_flags |= AHDLC_RX_READY;
+}
+
+/*---------------------------------------------------------------------------*/
+/* ahdlc receive function - This routine processes incoming bytes and tries
+ * to build a PPP frame.
+ *
+ * Two possible reasons that ahdlc_rx will not process characters:
+ * o Buffer is locked - in this case ahdlc_rx returns 1, char
+ * sending routing should retry.
+ */
+/*---------------------------------------------------------------------------*/
+
+u8_t ahdlc_rx(struct ppp_context_s *ctx, u8_t c)
+{
+ //static u16_t protocol;
+
+ /* Check to see if PPP packet is useable, we should have hardware
+ flow control set, but if host ignores it and sends us a char when
+ the PPP Receive packet is in use, discard the character. */
+
+ if (ctx->ahdlc_flags & AHDLC_RX_READY)
+ {
+ /* Check to see if character is less than 0x20 hex we really
+ should set AHDLC_RX_ASYNC_MAP on by default and only turn it
+ off when it is negotiated off to handle some buggy stacks. */
+
+ if ((c < 0x20) && ((ctx->ahdlc_flags & AHDLC_RX_ASYNC_MAP) == 0))
+ {
+ /* Discard character */
+
+ DEBUG1(("Discard because char is < 0x20 hex and asysnc map is 0\n"));
+ return 0;
+ }
+
+ /* Are we in escaped mode? */
+
+ if (ctx->ahdlc_flags & AHDLC_ESCAPED)
+ {
+ /* Set escaped to FALSE */
+
+ ctx->ahdlc_flags &= ~AHDLC_ESCAPED;
+
+ /* If value is 0x7e then silently discard and reset receive packet */
+
+ if (c == 0x7e)
+ {
+ ahdlc_rx_ready(ctx);
+ return 0;
+ }
+
+ /* Incoming char = itself xor 20 */
+
+ c = c ^ 0x20;
+ }
+ else if (c == 0x7e)
+ {
+ /* Handle frame end */
+
+ if (ctx->ahdlc_rx_crc == CRC_GOOD_VALUE)
+ {
+ DEBUG1(("\nReceiving packet with good crc value, len %d\n",
+ ctx->ahdlc_rx_count));
+
+ /* we hae a good packet, turn off CTS until we are done with
+ this packet */
+ /*CTS_OFF();*/
+
+#if PPP_STATISTICS
+ /* Update statistics */
+
+ ++ctx->ppp_rx_frame_count;
+#endif
+
+ /* Femove CRC bytes from packet */
+
+ ctx->ahdlc_rx_count -= 2;
+
+ /* Lock PPP buffer */
+
+ ctx->ahdlc_flags &= ~AHDLC_RX_READY;
+
+ /*upcall routine must fully process frame before return
+ * as returning signifies that buffer belongs to AHDLC again.
+ */
+
+ if ((c & 0x1) && (ctx->ahdlc_flags & PPP_PFC))
+ {
+ /* Send up packet */
+
+ ppp_upcall(ctx, (u16_t)ctx->ahdlc_rx_buffer[0],
+ (u8_t *)&ctx->ahdlc_rx_buffer[1],
+ (u16_t)(ctx->ahdlc_rx_count - 1));
+ }
+ else
+ {
+ /* Send up packet */
+
+ ppp_upcall(ctx, (u16_t)(ctx->ahdlc_rx_buffer[0] << 8 | ctx->ahdlc_rx_buffer[1]),
+ (u8_t *)&ctx->ahdlc_rx_buffer[2], (u16_t)(ctx->ahdlc_rx_count - 2));
+ }
+
+ ctx->ahdlc_tx_offline = 0; /* The remote side is alive */
+ ahdlc_rx_ready(ctx);
+ return 0;
+ }
+ else if (ctx->ahdlc_rx_count > 3)
+ {
+ DEBUG1(("\nReceiving packet with bad crc value, was 0x%04x len %d\n",
+ ctx->ahdlc_rx_crc, ctx->ahdlc_rx_count));
+#ifdef PPP_STATISTICS
+ ++ctx->ahdlc_crc_error;
+#endif
+ /* Shouldn't we dump the packet and not pass it up? */
+
+ /*ppp_upcall((u16_t)ahdlc_rx_buffer[0],
+ (u8_t *)&ahdlc_rx_buffer[0], (u16_t)(ahdlc_rx_count+2));
+ dump_ppp_packet(&ahdlc_rx_buffer[0],ahdlc_rx_count);*/
+ }
+
+ ahdlc_rx_ready(ctx);
+ return 0;
+ }
+ else if (c == 0x7d)
+ {
+ /* Handle escaped chars*/
+
+ ctx->ahdlc_flags |= PPP_ESCAPED;
+ return 0;
+ }
+
+ /* Rry to store char if not too big */
+
+ if (ctx->ahdlc_rx_count >= PPP_RX_BUFFER_SIZE)
+ {
+#ifdef PPP_STATISTICS
+ ++ctx->ahdlc_rx_tobig_error;
+#endif
+ ahdlc_rx_ready(ctx);
+ }
+ else
+ {
+ /* Add CRC in */
+
+ ctx->ahdlc_rx_crc = crcadd(ctx->ahdlc_rx_crc, c);
+
+ /* Do auto ACFC, if packet len is zero discard 0xff and 0x03 */
+
+ if (ctx->ahdlc_rx_count == 0)
+ {
+ if ((c == 0xff) || (c == 0x03))
+ {
+ return 0;
+ }
+ }
+
+ /* Store char */
+
+ ctx->ahdlc_rx_buffer[ctx->ahdlc_rx_count++] = c;
+ }
+ }
+ else
+ {
+ /* we are busy and didn't process the character. */
+ DEBUG1(("Busy/not active\n"));
+ return 1;
+ }
+
+ return 0;
+}
+
+/*---------------------------------------------------------------------------*/
+/* ahdlc_tx_char(char) - write a character to the serial device,
+ * escape if necessary.
+ *
+ * Relies on local global vars : ahdlc_tx_crc, ahdlc_flags.
+ * Modifies local global vars : ahdlc_tx_crc.
+ */
+/*---------------------------------------------------------------------------*/
+
+void ahdlc_tx_char(struct ppp_context_s *ctx, u16_t protocol, u8_t c)
+{
+ /* Add in crc */
+
+ ctx->ahdlc_tx_crc = crcadd(ctx->ahdlc_tx_crc, c);
+
+ /* See if we need to escape char, we always escape 0x7d and 0x7e, in the case
+ * of char < 0x20 we only support async map of default or none, so escape if
+ * ASYNC map is not set. We may want to modify this to support a bitmap set
+ * ASYNC map.
+ */
+
+ if ((c == 0x7d) || (c == 0x7e) || ((c < 0x20) && ((protocol == LCP) ||
+ (ctx->ahdlc_flags & PPP_TX_ASYNC_MAP) == 0)))
+ {
+ /* Send escape char and xor byte by 0x20 */
+
+ ppp_arch_putchar(ctx, 0x7d);
+ c ^= 0x20;
+ }
+
+ ppp_arch_putchar(ctx, c);
+}
+
+/*---------------------------------------------------------------------------*/
+/* ahdlc_tx(protocol,buffer,len) - Transmit a PPP frame.
+ * Buffer contains protocol data, ahdlc_tx addes address, control and
+ * protocol data.
+ *
+ * Relies on local global vars : ahdlc_tx_crc, ahdlc_flags.
+ * Modifies local global vars : ahdlc_tx_crc.
+ */
+/*---------------------------------------------------------------------------*/
+
+u8_t ahdlc_tx(struct ppp_context_s *ctx, u16_t protocol, u8_t *header,
+ u8_t *buffer, u16_t headerlen, u16_t datalen)
+{
+ u16_t i;
+ u8_t c;
+
+ DEBUG1(("\nAHDLC_TX - transmit frame, protocol 0x%04x, length %d offline %d\n",
+ protocol, datalen + headerlen, ctx->ahdlc_tx_offline));
+
+ if (AHDLC_TX_OFFLINE && (ctx->ahdlc_tx_offline++ > AHDLC_TX_OFFLINE))
+ {
+ ctx->ahdlc_tx_offline = 0;
+ DEBUG1(("\nAHDLC_TX to many outstanding TX packets => ppp_reconnect()\n"));
+ ppp_reconnect(ctx);
+ return 0;
+ }
+
+#if PACKET_TX_DEBUG
+ DEBUG1(("\n"));
+ for(i = 0; i < headerlen; ++i)
+ {
+ DEBUG1(("0x%02x ", header[i]));
+ }
+
+ for(i = 0; i < datalen; ++i)
+ {
+ DEBUG1(("0x%02x ", buffer[i]));
+ }
+
+ DEBUG1(("\n\n"));
+#endif
+
+ /* Check to see that physical layer is up, we can assume is some
+ cases */
+
+ /* Write leading 0x7e */
+
+ ppp_arch_putchar(ctx, 0x7e);
+
+ /* Set initial CRC value */
+
+ ctx->ahdlc_tx_crc = 0xffff;
+
+ /* send HDLC control and address if not disabled or of LCP frame type */
+
+ /*if ((0==(ahdlc_flags & PPP_ACFC)) || ((0xc0==buffer[0]) && (0x21==buffer[1]))) */
+ if ((0 == (ctx->ahdlc_flags & PPP_ACFC)) || (protocol == LCP))
+ {
+ ahdlc_tx_char(ctx, protocol, 0xff);
+ ahdlc_tx_char(ctx, protocol, 0x03);
+ }
+
+ /* Write Protocol */
+
+ ahdlc_tx_char(ctx, protocol,(u8_t)(protocol >> 8));
+ ahdlc_tx_char(ctx, protocol,(u8_t)(protocol & 0xff));
+
+ /* Write header if it exists */
+
+ for(i = 0; i < headerlen; ++i)
+ {
+ /* Get next byte from buffer */
+
+ c = header[i];
+
+ /* Write it...*/
+
+ ahdlc_tx_char(ctx, protocol, c);
+ }
+
+ /* Write frame bytes */
+
+ for(i = 0; i < datalen; ++i)
+ {
+ /* Get next byte from buffer */
+
+ c = buffer[i];
+
+ /* Write it...*/
+
+ ahdlc_tx_char(ctx, protocol, c);
+ }
+
+ /* Send crc, lsb then msb */
+
+ i = ctx->ahdlc_tx_crc ^ 0xffff;
+ ahdlc_tx_char(ctx, protocol, (u8_t)(i & 0xff));
+ ahdlc_tx_char(ctx, protocol, (u8_t)((i >> 8) & 0xff));
+
+ /* Write trailing 0x7e, probably not needed but it doesn't hurt */
+
+ ppp_arch_putchar(ctx, 0x7e);
+
+#if PPP_STATISTICS
+ /* Update statistics */
+
+ ++ctx->ppp_tx_frame_count;
+#endif
+O
+ return 0;
+}
+
+/*---------------------------------------------------------------------------*/
diff --git a/apps/netutils/pppd/ahdlc.h b/apps/netutils/pppd/ahdlc.h
new file mode 100644
index 000000000..84fbc442c
--- /dev/null
+++ b/apps/netutils/pppd/ahdlc.h
@@ -0,0 +1,84 @@
+/*---------------------------------------------------------------------------
+ ahdlc.h - ahdlc header file
+---------------------------------------------------------------------------
+ Version
+ 0.1 Original Version Jan 11, 1998
+ (c)1998 Mycal Labs, All Rights Reserved
+ ---------------------------------------------------------------------------*/
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: ahdlc.h,v 1.1 2007/05/26 07:14:39 oliverschmidt Exp $
+ *
+ */
+
+#ifndef __APPS_NETUTILS_PPPD_AHDLC_H
+#define __APPS_NETUTILS_PPPD_AHDLC_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include "ppp_conf.h"
+#include "ppp_arch.h"
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+struct ppp_context_s;
+
+#undef EXTERN
+#if defined(__cplusplus)
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+void ahdlc_init(struct ppp_context_s *ctx);
+
+void ahdlc_rx_ready(struct ppp_context_s *ctx);
+
+u8_t ahdlc_rx(struct ppp_context_s *ctx, u8_t);
+u8_t ahdlc_tx(struct ppp_context_s *ctx, u16_t protocol, u8_t *header,
+ u8_t *buffer, u16_t headerlen, u16_t datalen);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __APPS_NETUTILS_PPPD_AHDLC_H */
diff --git a/apps/netutils/pppd/chat.c b/apps/netutils/pppd/chat.c
new file mode 100644
index 000000000..9042437dc
--- /dev/null
+++ b/apps/netutils/pppd/chat.c
@@ -0,0 +1,136 @@
+#include "ppp_conf.h"
+#include "ppp_arch.h"
+#include "chat.h"
+
+#include <poll.h>
+
+#define CHAT_MAX_SKIP 8
+#define CHAT_ECHO_TIMEOUT 500
+
+static int chat_read_byte(int fd, char* c, int timeout)
+{
+ int ret;
+ struct pollfd fds;
+
+ fds.fd = fd;
+ fds.events = POLLIN;
+ fds.revents = 0;
+
+ ret = poll(&fds, 1, timeout);
+ if (ret <= 0)
+ {
+ return -1;
+ }
+
+ ret = read(fd, c, 1);
+ if (ret != 1)
+ {
+ return -1;
+ }
+
+ printf("chat: char = %c (0x%02X)\n", *c, *c);
+
+ return 0;
+}
+
+static void chat_flush(int fd)
+{
+ char tmp;
+ while (chat_read_byte(fd, &tmp, 0) == 0);
+}
+
+static int chat_check_response(int fd, const char* response, int timeout)
+{
+ char c;
+ int ret;
+ int skip = CHAT_MAX_SKIP;
+
+ while (*response)
+ {
+ ret = chat_read_byte(fd, &c, timeout);
+ if (ret < 0)
+ {
+ return ret;
+ }
+
+ if (skip > 0 && (c == '\r' || c == '\n'))
+ {
+ --skip;
+ continue;
+ }
+
+ if (c == *response)
+ {
+ ++response;
+ }
+ else
+ {
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+int ppp_chat(int fd, struct chat_script_s *script, int echo)
+{
+ int ret;
+ size_t len;
+ struct chat_line_s *line = script->lines;
+ const char* request = line->request;
+ const char* response = line->response;
+
+ while (request)
+ {
+ chat_flush(fd);
+
+ printf("chat: send '%s`\n", request);
+ len = strlen(request);
+ ret = write(fd, request, len);
+ if (ret < 0)
+ {
+ return ret;
+ }
+ else if ((size_t)ret != len)
+ {
+ return -1;
+ }
+
+ ret = write(fd, "\r\n", 2);
+ if (ret != 2)
+ {
+ return -1;
+ }
+
+ /* Check echo if enabled */
+
+ if (echo)
+ {
+ ret = chat_check_response(fd, request, CHAT_ECHO_TIMEOUT);
+ if (ret < 0)
+ {
+ printf("chat: invalid echo\n");
+ return ret;
+ }
+ }
+
+ if (response)
+ {
+ printf("chat: wait for '%s`\n", response);
+ ret = chat_check_response(fd, response, script->timeout * 1000);
+ if (ret < 0)
+ {
+ printf("chat: bad response\n");
+ return ret;
+ }
+
+ printf("chat: got it!\n");
+ }
+
+ ++line;
+ request = line->request;
+ response = line->response;
+ }
+
+ return 0;
+} \ No newline at end of file
diff --git a/apps/netutils/pppd/chat.h b/apps/netutils/pppd/chat.h
new file mode 100644
index 000000000..7d1cb8df8
--- /dev/null
+++ b/apps/netutils/pppd/chat.h
@@ -0,0 +1,46 @@
+#ifndef __APPS_NETUTILS_PPPD_CHAT_H
+#define __APPS_NETUTILS_PPPD_CHAT_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <time.h>
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+struct chat_line_s
+{
+ const char *request;
+ const char *response;
+};
+
+struct chat_script_s
+{
+ time_t timeout;
+ struct chat_line_s lines[];
+};
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+#undef EXTERN
+#if defined(__cplusplus)
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+int ppp_chat(int fd, struct chat_script_s *script, int echo);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __APPS_NETUTILS_PPPD_CHAT_H */ \ No newline at end of file
diff --git a/apps/netutils/pppd/ipcp.c b/apps/netutils/pppd/ipcp.c
new file mode 100644
index 000000000..b1aa6a691
--- /dev/null
+++ b/apps/netutils/pppd/ipcp.c
@@ -0,0 +1,513 @@
+/*
+ *---------------------------------------------------------------------------
+ * ipcp.c - PPP IPCP (intrnet protocol) Processor/Handler
+ *
+ *---------------------------------------------------------------------------
+ *
+ * Version
+ * 0.1 Original Version Jun 3, 2000
+ *
+ *---------------------------------------------------------------------------
+ *
+ * Copyright (C) 2000, Mycal Labs www.mycal.com
+ *
+ *---------------------------------------------------------------------------
+ */
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: ipcp.c,v 1.2 2010/10/19 18:29:03 adamdunkels Exp $
+ *
+ */
+
+/* */
+/* include files */
+/* */
+
+#include "ppp_conf.h"
+#include "ppp_arch.h"
+#include "ipcp.h"
+#include "ppp.h"
+#include "ahdlc.h"
+
+#if PPP_DEBUG
+# define DEBUG1(x) debug_printf x
+#else
+# define DEBUG1(x)
+#endif
+
+/* In the future add compression protocol and name servers (possibly for servers
+ * only)
+ */
+
+static const u8_t ipcplist[] =
+{
+ 0x3,
+ 0
+};
+
+/*---------------------------------------------------------------------------*/
+
+#if 0
+void
+printip(uip_ipaddr_t ip2)
+{
+ char *ip = (u8_t*)ip2;
+ DEBUG1((" %d.%d.%d.%d ",ip[0],ip[1],ip[2],ip[3]));
+}
+#else
+# define printip(x)
+#endif
+
+/*---------------------------------------------------------------------------*/
+
+void ipcp_init(struct ppp_context_s *ctx)
+{
+ DEBUG1(("ipcp init\n"));
+
+ ctx->ipcp_state = 0;
+ ctx->ipcp_retry = 0;
+ ctx->ipcp_prev_seconds = 0;
+
+ memset(&ctx->local_ip, 0, sizeof(struct in_addr));
+#ifdef IPCP_GET_PEER_IP
+ memset(&ctx->peer_ip, 0, sizeof(struct in_addr));
+#endif
+#ifdef IPCP_GET_PRI_DNS
+ memset(&ctx->pri_dns_addr, 0, sizeof(struct in_addr));
+#endif
+#ifdef IPCP_GET_SEC_DNS
+ memset(&ctx->sec_dns_addr, 0, sizeof(struct in_addr));
+#endif
+}
+
+/*---------------------------------------------------------------------------*/
+/* IPCP RX protocol Handler */
+
+void ipcp_rx(struct ppp_context_s *ctx, u8_t *buffer, u16_t count)
+{
+ u8_t *bptr = buffer;
+ //IPCPPKT *pkt=(IPCPPKT *)buffer;
+ u16_t len;
+
+ DEBUG1(("IPCP len %d\n",count));
+
+ switch (*bptr++)
+ {
+ case CONF_REQ:
+ /* Parse request and see if we can ACK it */
+
+ ++bptr;
+ len = (*bptr++ << 8);
+ len |= *bptr++;
+ /* len-=2; */
+
+ DEBUG1(("check lcplist\n"));
+ if (scan_packet(ctx, IPCP, ipcplist, buffer, bptr, (u16_t)(len - 4)))
+ {
+ DEBUG1(("option was bad\n"));
+ }
+ else
+ {
+ DEBUG1(("IPCP options are good\n"));
+
+ /* Parse out the results */
+ /* lets try to implement what peer wants */
+ /* Reject any protocol not */
+ /* Error? if we we need to send a config Reject ++++ this is good for a subroutine*/
+ /* All we should get is the peer IP address */
+
+ if (IPCP_IPADDRESS == *bptr++)
+ {
+ /* Dump length */
+
+ ++bptr;
+#ifdef IPCP_GET_PEER_IP
+ ((u8_t*)&ctx->peer_ip)[0] = *bptr++;
+ ((u8_t*)&ctx->peer_ip)[1] = *bptr++;
+ ((u8_t*)&ctx->peer_ip)[2] = *bptr++;
+ ((u8_t*)&ctx->peer_ip)[3] = *bptr++;
+
+ DEBUG1(("Peer IP "));
+ /* printip(peer_ip_addr); */
+ DEBUG1(("\n"));
+
+ netlib_set_dripv4addr((char*)ctx->ifname, &ctx->peer_ip);
+#else
+ bptr += 4;
+#endif
+ }
+ else
+ {
+ DEBUG1(("HMMMM this shouldn't happen IPCP1\n"));
+ }
+
+#if 0
+ if (error)
+ {
+ /* Write the config NAK packet we've built above, take on the header */
+
+ bptr = buffer;
+ *bptr++ = CONF_NAK; /* Write Conf_rej */
+ *bptr++;
+ /*tptr++;*/ /* skip over ID */
+
+ /* Write new length */
+
+ *bptr++ = 0;
+ *bptr = tptr - buffer;
+
+ /* Write the reject frame */
+
+ DEBUG1(("Writing NAK frame \n"));
+ ahdlc_tx(IPCP, buffer, (u16_t)(tptr - buffer));
+ DEBUG1(("- End NAK Write frame\n"));
+ }
+ else
+ {
+ }
+#endif
+ /* If we get here then we are OK, lets send an ACK and tell the rest
+ * of our modules our negotiated config.
+ */
+
+ ctx->ipcp_state |= IPCP_RX_UP;
+ DEBUG1(("Send IPCP ACK!\n"));
+ bptr = buffer;
+ *bptr++ = CONF_ACK; /* Write Conf_ACK */
+ bptr++; /* Skip ID (send same one) */
+
+ /* Set stuff */
+
+ /* ppp_flags |= tflag; */
+ DEBUG1(("SET- stuff -- are we up? c=%d dif=%d \n", count, (u16_t)(bptr - buffer)));
+
+ /* Write the ACK frame */
+
+ DEBUG1(("Writing ACK frame \n"));
+
+ /* Send packet ahdlc_txz(procol,header,data,headerlen,datalen); */
+
+ ahdlc_tx(ctx, IPCP, 0, buffer, 0, count /*bptr-buffer*/);
+ DEBUG1(("- End ACK Write frame\n"));
+ }
+ break;
+
+ case CONF_ACK: /* config Ack */
+ DEBUG1(("CONF ACK\n"));
+ /* Parse out the results
+ *
+ * Dump the ID and get the length.
+ */
+
+ /* Dump the ID */
+
+ bptr++;
+
+ /* Get the length */
+
+ len = (*bptr++ << 8);
+ len |= *bptr++;
+
+#if 0
+ /* Parse ACK and set data */
+
+ while (bptr < buffer + len)
+ {
+ switch (*bptr++)
+ {
+ case IPCP_IPADDRESS:
+ /* Dump length */
+
+ bptr++;
+ ((u8_t*)ipaddr)[0] = *bptr++;
+ ((u8_t*)ipaddr)[1] = *bptr++;
+ ((u8_t*)ipaddr)[2] = *bptr++;
+ ((u8_t*)ipaddr)[3] = *bptr++;
+ break;
+
+ case IPCP_PRIMARY_DNS:
+ bptr++;
+ ((u8_t*)pri_dns_addr)[0] = *bptr++;
+ ((u8_t*)pri_dns_addr)[1] = *bptr++;
+ ((u8_t*)pri_dns_addr)[2] = *bptr++;
+ ((u8_t*)pri_dns_addr)[3] = *bptr++;
+ break;
+
+ case IPCP_SECONDARY_DNS:
+ bptr++;
+ ((u8_t*)sec_dns_addr)[0] = *bptr++;
+ ((u8_t*)sec_dns_addr)[1] = *bptr++;
+ ((u8_t*)sec_dns_addr)[2] = *bptr++;
+ ((u8_t*)sec_dns_addr)[3] = *bptr++;
+ break;
+
+ default:
+ DEBUG1(("IPCP CONFIG_ACK problem1\n"));
+ }
+ }
+#endif
+
+ ctx->ipcp_state |= IPCP_TX_UP;
+ /*ppp_ipcp_state &= ~IPCP_RX_UP;*/
+
+ DEBUG1(("were up! \n"));
+ //printip(pppif.ipaddr);
+#ifdef IPCP_GET_PRI_DNS
+ printip(pri_dns_addr);
+#endif
+#ifdef IPCP_GET_SEC_DNS
+ printip(sec_dns_addr);
+#endif
+ DEBUG1(("\n"));
+ break;
+
+ case CONF_NAK: /* Config Nack */
+ DEBUG1(("CONF NAK\n"));
+
+ /* Dump the ID */
+
+ bptr++;
+
+ /* Get the length */
+
+ len = (*bptr++ << 8);
+ len |= *bptr++;
+
+ /* Parse ACK and set data */
+
+ while (bptr < buffer + len)
+ {
+ switch (*bptr++)
+ {
+ case IPCP_IPADDRESS:
+ /* dump length */
+ bptr++;
+
+ ((u8_t*)&ctx->local_ip)[0] = (char)*bptr++;
+ ((u8_t*)&ctx->local_ip)[1] = (char)*bptr++;
+ ((u8_t*)&ctx->local_ip)[2] = (char)*bptr++;
+ ((u8_t*)&ctx->local_ip)[3] = (char)*bptr++;
+
+ netlib_ifup((char*)ctx->ifname);
+ netlib_set_ipv4addr((char*)ctx->ifname, &ctx->local_ip);
+ //DEBUG1(("My PPP-ipno: (%d.%d.%d.%d)\n", ((u8_t*)pppif.ipaddr)[0], ((u8_t*)pppif.ipaddr)[1], ((u8_t*)pppif.ipaddr)[2], ((u8_t*)pppif.ipaddr)[3]));
+ break;
+
+#ifdef IPCP_GET_PRI_DNS
+ case IPCP_PRIMARY_DNS:
+ bptr++;
+ ((u8_t*)&ctx->pri_dns_addr)[0] = *bptr++;
+ ((u8_t*)&ctx->pri_dns_addr)[1] = *bptr++;
+ ((u8_t*)&ctx->pri_dns_addr)[2] = *bptr++;
+ ((u8_t*)&ctx->pri_dns_addr)[3] = *bptr++;
+ break;
+#endif
+
+#ifdef IPCP_GET_SEC_DNS
+ case IPCP_SECONDARY_DNS:
+ bptr++;
+ ((u8_t*)&ctx->sec_dns_addr)[0] = *bptr++;
+ ((u8_t*)&ctx->sec_dns_addr)[1] = *bptr++;
+ ((u8_t*)&ctx->sec_dns_addr)[2] = *bptr++;
+ ((u8_t*)&ctx->sec_dns_addr)[3] = *bptr++;
+ break;
+#endif
+
+ default:
+ DEBUG1(("IPCP CONFIG_ACK problem 2\n"));
+ }
+ }
+
+ ctx->ppp_id++;
+
+ printip(pppif.ipaddr);
+#ifdef IPCP_GET_PRI_DNS
+ printip(pri_dns_addr);
+#endif
+#ifdef IPCP_GET_PRI_DNS
+ printip(sec_dns_addr);
+#endif
+ DEBUG1(("\n"));
+ break;
+
+ case CONF_REJ: /* Config Reject */
+ DEBUG1(("CONF REJ\n"));
+
+ /* Remove the offending options*/
+
+ ctx->ppp_id++;
+
+ /* Dump the ID */
+
+ bptr++;
+
+ /* Get the length */
+
+ len = (*bptr++ << 8);
+ len |= *bptr++;
+
+ /* Parse ACK and set data */
+
+ while (bptr < buffer + len)
+ {
+ switch (*bptr++)
+ {
+ case IPCP_IPADDRESS:
+ ctx->ipcp_state |= IPCP_IP_BIT;
+ bptr += 5;
+ break;
+
+#ifdef IPCP_GET_PRI_DNS
+ case IPCP_PRIMARY_DNS:
+ ctx->ipcp_state |= IPCP_PRI_DNS_BIT;
+ bptr += 5;
+ break;
+#endif
+
+#ifdef IPCP_GET_PRI_DNS
+ case IPCP_SECONDARY_DNS:
+ ctx->ipcp_state |= IPCP_SEC_DNS_BIT;
+ bptr += 5;
+ break;
+#endif
+
+ default:
+ DEBUG1(("IPCP this shoudln't happen 3\n"));
+ }
+ }
+ break;
+
+ default:
+ DEBUG1(("-Unknown 4\n"));
+ }
+}
+
+/*---------------------------------------------------------------------------*/
+
+void ipcp_task(struct ppp_context_s *ctx, u8_t *buffer)
+{
+ u8_t *bptr;
+ u16_t t;
+ IPCPPKT *pkt;
+
+ /* IPCP tx not up and hasn't timed out then lets see if we need to
+ send a request */
+
+ if (!(ctx->ipcp_state & IPCP_TX_UP) && !(ctx->ipcp_state & IPCP_TX_TIMEOUT))
+ {
+ /* Check if we have a request pending */
+
+ if ((ppp_arch_clock_seconds() - ctx->ipcp_prev_seconds) > IPCP_TIMEOUT)
+ {
+ ctx->ipcp_prev_seconds = ppp_arch_clock_seconds();
+
+ /* No pending request, lets build one */
+
+ pkt=(IPCPPKT *)buffer;
+
+ /* Configure-Request only here, write id */
+
+ pkt->code = CONF_REQ;
+ pkt->id = ctx->ppp_id;
+
+ bptr = pkt->data;
+
+ /* Write options, we want IP address, and DNS addresses if set. */
+ /* Write zeros for IP address the first time */
+
+ *bptr++ = IPCP_IPADDRESS;
+ *bptr++ = 0x6;
+ *bptr++ = (u8_t)((u8_t*)&ctx->local_ip)[0];
+ *bptr++ = (u8_t)((u8_t*)&ctx->local_ip)[1];
+ *bptr++ = (u8_t)((u8_t*)&ctx->local_ip)[2];
+ *bptr++ = (u8_t)((u8_t*)&ctx->local_ip)[3];
+
+#ifdef IPCP_GET_PRI_DNS
+ if (!(ppp_ipcp_state & IPCP_PRI_DNS_BIT))
+ {
+ /* Write zeros for IP address the first time */
+
+ *bptr++ = IPCP_PRIMARY_DNS;
+ *bptr++ = 0x6;
+ *bptr++ = ((u8_t*)&ctx->pri_dns_addr)[0];
+ *bptr++ = ((u8_t*)&ctx->pri_dns_addr)[1];
+ *bptr++ = ((u8_t*)&ctx->pri_dns_addr)[2];
+ *bptr++ = ((u8_t*)&ctx->pri_dns_addr)[3];
+ }
+#endif
+
+#ifdef IPCP_GET_SEC_DNS
+ if (!(ppp_ipcp_state & IPCP_SEC_DNS_BIT))
+ {
+ /* Write zeros for IP address the first time */
+
+ *bptr++ = IPCP_SECONDARY_DNS;
+ *bptr++ = 0x6;
+ *bptr++ = ((u8_t*)&ctx->sec_dns_addr)[0];
+ *bptr++ = ((u8_t*)&ctx->sec_dns_addr)[1];
+ *bptr++ = ((u8_t*)&ctx->sec_dns_addr)[2];
+ *bptr++ = ((u8_t*)&ctx->sec_dns_addr)[3];
+ }
+#endif
+
+ /* Write length */
+
+ t = bptr - buffer;
+
+ /* length here - code and ID + */
+
+ pkt->len = htons(t);
+
+ DEBUG1(("\n**Sending IPCP Request packet\n"));
+
+ /* Send packet ahdlc_txz(procol,header,data,headerlen,datalen); */
+
+ ahdlc_tx(ctx, IPCP, 0, buffer, 0, t);
+
+ /* Inc retry */
+
+ ctx->ipcp_retry++;
+
+ /* Have we timed out? (combine the timers?) */
+
+ if (ctx->ipcp_retry > IPCP_RETRY_COUNT)
+ {
+ ctx->ipcp_state &= IPCP_TX_TIMEOUT;
+ }
+ }
+ }
+}
+
+/*---------------------------------------------------------------------------*/
diff --git a/apps/netutils/pppd/ipcp.h b/apps/netutils/pppd/ipcp.h
new file mode 100644
index 000000000..ee58f1cf7
--- /dev/null
+++ b/apps/netutils/pppd/ipcp.h
@@ -0,0 +1,117 @@
+/* www.mycal.com
+ ---------------------------------------------------------------------------
+ IPCP.h - Internet Protocol Control Protocol header file
+ ---------------------------------------------------------------------------
+ Version
+ 0.1 Original Version June 3, 2000
+ (c)2000 Mycal Labs, All Rights Reserved
+ ---------------------------------------------------------------------------
+*/
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: ipcp.h,v 1.1 2007/05/26 07:14:39 oliverschmidt Exp $
+ *
+ */
+
+#ifndef __APPS_NETUTILS_PPPD_IPCP_H
+#define __APPS_NETUTILS_PPPD_IPCP_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include "ppp_arch.h"
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/* Config options (move to pppconfig)
+ #define IPCP_RETRY_COUNT 5
+ #define IPCP_TIMEOUT 5
+*/
+
+/* IPCP Option Types */
+
+#define IPCP_IPADDRESS 0x03
+#define IPCP_PRIMARY_DNS 0x81
+#define IPCP_SECONDARY_DNS 0x83
+
+/* IPCP state machine flags */
+
+#define IPCP_TX_UP 0x01
+#define IPCP_RX_UP 0x02
+#define IPCP_IP_BIT 0x04
+#define IPCP_TX_TIMEOUT 0x08
+#define IPCP_PRI_DNS_BIT 0x08
+#define IPCP_SEC_DNS_BIT 0x10
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+struct ppp_context_s;
+
+typedef struct _ipcp
+{
+ u8_t code;
+ u8_t id;
+ u16_t len;
+ u8_t data[0];
+} IPCPPKT;
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+#undef EXTERN
+#if defined(__cplusplus)
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+void ipcp_init(struct ppp_context_s *ctx);
+void ipcp_task(struct ppp_context_s *ctx, u8_t *buffer);
+void ipcp_rx(struct ppp_context_s *ctx, u8_t *, u16_t);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __APPS_NETUTILS_PPPD_IPCP_H */
diff --git a/apps/netutils/pppd/lcp.c b/apps/netutils/pppd/lcp.c
new file mode 100644
index 000000000..2a58c0218
--- /dev/null
+++ b/apps/netutils/pppd/lcp.c
@@ -0,0 +1,589 @@
+/* www.mycal.com
+ *---------------------------------------------------------------------------
+ *lcp.c - Link Configuration Protocol Handler. - -
+ *---------------------------------------------------------------------------
+ *Version - 0.1 Original Version June 3, 2000 -
+ *
+ *---------------------------------------------------------------------------
+ *- Copyright (C) 2000, Mycal Labs www.mycal.com - -
+ *---------------------------------------------------------------------------
+ */
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: lcp.c,v 1.2 2010/10/19 18:29:03 adamdunkels Exp $
+ *
+ */
+
+/* include files */
+
+#include "ppp_conf.h"
+#include "ppp_arch.h"
+#include "ppp.h"
+#include "ahdlc.h"
+#include "lcp.h"
+
+#if PPP_DEBUG
+# define DEBUG1(x) debug_printf x
+# define DEBUG2(x) debug_printf x
+#else
+# define DEBUG1(x)
+# define DEBUG2(x)
+#endif
+
+/* We need this when we neg our direction.
+ u8_t lcp_tx_options; */
+
+/* Define the supported parameters for this module here. */
+
+static const u8_t lcplist[] =
+{
+ LPC_MAGICNUMBER,
+ LPC_PFC,
+ LPC_ACFC,
+ LPC_AUTH,
+ LPC_ACCM,
+ LPC_MRU,
+ 0
+};
+
+/*---------------------------------------------------------------------------*/
+/* lcp_init() - Initialize the LCP engine to startup values */
+/*---------------------------------------------------------------------------*/
+
+void lcp_init(struct ppp_context_s *ctx)
+{
+ ctx->lcp_state = 0;
+ ctx->lcp_retry = 0;
+}
+
+/*---------------------------------------------------------------------------*/
+/* lcp_rx() - Receive an LCP packet and process it.
+ * This routine receives a LCP packet in buffer of length count.
+ * Process it here, support for CONF_REQ, CONF_ACK, CONF_NACK, CONF_REJ or
+ * TERM_REQ.
+ */
+/*---------------------------------------------------------------------------*/
+
+void lcp_rx(struct ppp_context_s *ctx, u8_t *buffer, u16_t count)
+{
+ u8_t *bptr = buffer, *tptr;
+ u8_t error = 0;
+ u8_t id;
+ u16_t len, j;
+
+ switch (*bptr++)
+ {
+ case CONF_REQ: /* config request */
+ /* Parse request and see if we can ACK it */
+
+ id = *bptr++;
+ len = (*bptr++ << 8);
+ len |= *bptr++;
+ /*len -= 2;*/
+
+ /* In case of new peer connection */
+
+ ipcp_init(ctx);
+ ctx->lcp_state &= ~LCP_TX_UP;
+
+ DEBUG1(("received [LCP Config Request id %u\n", id));
+ if (scan_packet(ctx, (u16_t)LCP, lcplist, buffer, bptr, (u16_t)(len-4)))
+ {
+ /* Must do the -4 here, !scan packet */
+
+ DEBUG1((" options were rejected\n"));
+ }
+ else
+ {
+ /* Lets try to implement what peer wants */
+
+ tptr = bptr = buffer;
+ bptr += 4; /* skip code, id, len */
+ error = 0;
+
+ /* First scan for unknown values */
+
+ while(bptr < (buffer + len))
+ {
+ switch (*bptr++)
+ {
+ case LPC_MRU: /* mru */
+ j = *bptr++;
+ j -= 2;
+
+ if (j == 2)
+ {
+ ctx->ppp_tx_mru = ((int)*bptr++) << 8;
+ ctx->ppp_tx_mru |= *bptr++;
+ DEBUG1(("<mru %d> ", ctx->ppp_tx_mru));
+ }
+ else
+ {
+ DEBUG1(("<mru ?? > "));
+ }
+ break;
+
+ case LPC_ACCM:
+ bptr++; /* skip length */
+ j = *bptr++;
+ j += *bptr++;
+ j += *bptr++;
+ j += *bptr++;
+
+ if (j==0)
+ {
+ // ok
+ DEBUG1(("<asyncmap sum=0x%04x>",j));
+ //ahdlc_flags |= PPP_TX_ASYNC_MAP;
+ }
+ else if (j!=0)
+ {
+ // ok
+ DEBUG1(("<asyncmap sum=0x%04x>, assume 0xffffffff",j));
+ }
+ else
+ {
+ /* Fail. We only support default or all zeros */
+
+ DEBUG1(("We only support default or all zeros for ACCM "));
+ error = 1;
+ *tptr++ = LPC_ACCM;
+ *tptr++ = 0x6;
+ *tptr++ = 0;
+ *tptr++ = 0;
+ *tptr++ = 0;
+ *tptr++ = 0;
+ }
+ break;
+
+ case LPC_AUTH:
+ bptr++;
+ if ((*bptr++ == 0xc0) && (*bptr++ == 0x23))
+ {
+ /* Negotiate PAP */
+
+ if (strlen((char*)ctx->pap_username) > 0)
+ {
+ DEBUG1(("<auth pap> "));
+ ctx->lcp_state |= LCP_RX_AUTH;
+ }
+ else
+ {
+ DEBUG1(("<rej auth pap> "));
+
+ *tptr++ = CONF_REJ;
+ tptr++; // Keep ID
+ *tptr++ = 0;
+ *tptr++ = 8;
+ *tptr++ = LPC_AUTH;
+ *tptr++ = 0x4;
+ *tptr++ = 0xc0;
+ *tptr++ = 0x23;
+ ahdlc_tx(ctx, LCP, 0, buffer, 0, (u16_t)(tptr-buffer));
+ return;
+ }
+ }
+ else
+ {
+ /* We only support PAP */
+
+ DEBUG1(("<auth ?? >"));
+ error = 1;
+ *tptr++ = LPC_AUTH;
+ *tptr++ = 0x4;
+ *tptr++ = 0xc0;
+ *tptr++ = 0x23;
+ }
+ break;
+
+ case LPC_MAGICNUMBER:
+ DEBUG1(("<magic > "));
+
+ /* Compare incoming number to our number (not implemented) */
+
+ bptr++; /* For now just dump */
+ bptr++;
+ bptr++;
+ bptr++;
+ bptr++;
+ break;
+
+ case LPC_PFC:
+ bptr++;
+ DEBUG1(("<pcomp> "));
+ /*tflag|=PPP_PFC;*/
+ break;
+
+ case LPC_ACFC:
+ bptr++;
+ DEBUG1(("<accomp> "));
+ /*tflag|=PPP_ACFC;*/
+ break;
+ }
+ }
+
+ /* Error? if we we need to send a config Reject ++++ this is good
+ * for a subroutine.
+ */
+
+ if (error)
+ {
+ /* Write the config NAK packet we've built above, take on the
+ * header
+ */
+
+ bptr = buffer;
+ *bptr++ = CONF_NAK; /* Write Conf_rej */
+ bptr++;/*tptr++;*/ /* skip over ID */
+
+ /* Write new length */
+
+ *bptr++ = 0;
+ *bptr = tptr - buffer;
+
+ /* Write the reject frame */
+
+ DEBUG1(("\nWriting NAK frame \n"));
+ // Send packet ahdlc_txz(procol,header,data,headerlen,datalen);
+ ahdlc_tx(ctx, LCP, 0, buffer, 0, (u16_t)(tptr-buffer));
+ DEBUG1(("- end NAK Write frame\n"));
+ }
+ else
+ {
+ /* If we get here then we are OK, lets send an ACK and tell the rest
+ * of our modules our negotiated config.
+ */
+
+ DEBUG1(("\nSend ACK!\n"));
+ bptr = buffer;
+ *bptr++ = CONF_ACK; /* Write Conf_ACK */
+ bptr++; /* Skip ID (send same one) */
+
+ /* Set stuff */
+
+ /*ppp_flags|=tflag;*/
+ /* DEBUG2("SET- stuff -- are we up? c=%d dif=%d \n", count, (u16_t)(bptr-buffer)); */
+
+ /* Write the ACK frame */
+
+ DEBUG2(("Writing ACK frame \n"));
+
+ /* Send packet ahdlc_txz(procol,header,data,headerlen,datalen); */
+
+ ahdlc_tx(ctx, LCP, 0, buffer, 0, count /*bptr-buffer*/);
+ DEBUG2(("- end ACK Write frame\n"));
+ ctx->lcp_state |= LCP_RX_UP;
+ }
+ }
+ break;
+
+ case CONF_ACK: /* config Ack Anytime we do an ack reset the timer to force send. */
+ DEBUG1(("LCP-ACK - "));
+
+ /* Check that ID matches one sent */
+
+ if (*bptr++ == ctx->ppp_id)
+ {
+ /* Change state to PPP up. */
+
+ DEBUG1((">>>>>>>> good ACK id up! %d\n", ctx->ppp_id));
+
+ /* Copy negotiated values over */
+
+ ctx->lcp_state |= LCP_TX_UP;
+ }
+ else
+ {
+ DEBUG1(("*************++++++++++ bad id %d\n", ctx->ppp_id));
+ }
+ break;
+
+ case CONF_NAK: /* Config Nack */
+ DEBUG1(("LCP-CONF NAK\n"));
+ ctx->ppp_id++;
+ break;
+
+ case CONF_REJ: /* Config Reject */
+ DEBUG1(("LCP-CONF REJ\n"));
+ ctx->ppp_id++;
+ break;
+
+ case TERM_REQ: /* Terminate Request */
+ DEBUG1(("LCP-TERM-REQ -"));
+ bptr = buffer;
+ *bptr++ = TERM_ACK; /* Write TERM_ACK */
+
+ /* Write the reject frame */
+
+ DEBUG1(("Writing TERM_ACK frame \n"));
+
+ /* Send packet ahdlc_txz(procol,header,data,headerlen,datalen); */
+
+ ahdlc_tx(ctx, LCP, 0, buffer, 0, count);
+
+ ctx->lcp_state &= ~LCP_TX_UP;
+ ctx->lcp_state |= LCP_TERM_PEER;
+ break;
+
+ case TERM_ACK:
+ DEBUG1(("LCP-TERM ACK\n"));
+ break;
+
+ case ECHO_REQ:
+ if ((ctx->lcp_state & LCP_TX_UP) && (ctx->lcp_state & LCP_RX_UP))
+ {
+ bptr = buffer;
+ *bptr++ = ECHO_REP; /* Write ECHO-REPLY */
+
+ bptr += 3; /* Skip id and length */
+
+ *bptr++ = 0; /* Zero Magic */
+ *bptr++ = 0;
+ *bptr++ = 0;
+ *bptr++ = 0;
+
+ /* Write the echo reply frame */
+
+ DEBUG1(("\nWriting ECHO-REPLY frame \n"));
+ // Send packet ahdlc_txz(procol,header,data,headerlen,datalen);
+ ahdlc_tx(ctx, LCP, 0, buffer, 0, count);
+ DEBUG1(("- end ECHO-REPLY Write frame\n"));
+ }
+ break;
+
+ case ECHO_REP:
+ DEBUG1(("LCP-ECHO REPLY\n"));
+ if ((ctx->lcp_state & LCP_TX_UP) && (ctx->lcp_state & LCP_RX_UP))
+ {
+ ctx->ppp_id++;
+ }
+ break;
+
+ default:
+ DEBUG1(("LCP unknown packet: %02x", *(bptr-1)));
+ break;
+ }
+}
+
+/*---------------------------------------------------------------------------*/
+
+void lcp_disconnect(struct ppp_context_s *ctx, u8_t id)
+{
+ u8_t buffer[4];
+ u8_t *bptr = buffer;
+
+ *bptr++ = TERM_REQ;
+ *bptr++ = id;
+ *bptr++ = 0;
+ *bptr++ = 4;
+
+ ahdlc_tx(ctx, LCP, 0, buffer, 0, bptr - buffer);
+}
+
+/*---------------------------------------------------------------------------*/
+
+void lcp_echo_request(struct ppp_context_s *ctx, u8_t *buffer)
+{
+ u8_t *bptr;
+ u16_t t;
+ LCPPKT *pkt;
+
+ if ((ctx->lcp_state & LCP_TX_UP) && (ctx->lcp_state & LCP_RX_UP))
+ {
+ if ((ppp_arch_clock_seconds() - ctx->lcp_prev_seconds) > LCP_ECHO_INTERVAL)
+ {
+ ctx->lcp_prev_seconds = ppp_arch_clock_seconds();
+
+ pkt = (LCPPKT *)buffer;
+
+ /* Configure-Request only here, write id */
+
+ pkt->code = ECHO_REQ;
+ pkt->id = ctx->ppp_id;
+
+ bptr = pkt->data;
+
+ *bptr++ = 0;
+ *bptr++ = 0;
+ *bptr++ = 0;
+ *bptr++ = 0;
+
+ /* Write length */
+
+ t = bptr - buffer;
+ pkt->len = htons(t); /* length here - code and ID + */
+
+ DEBUG1((" len %d\n",t));
+
+ /* Send packet */
+ /* Send packet ahdlc_txz(procol,header,data,headerlen,datalen); */
+
+ DEBUG1(("\nWriting ECHO-REQUEST frame \n"));
+ ahdlc_tx(ctx, LCP, 0, buffer, 0, t);
+ DEBUG1(("- end ECHO-REQUEST Write frame\n"));
+ }
+ }
+}
+
+/*---------------------------------------------------------------------------*/
+/* lcp_task(buffer) - This routine see if a lcp request needs to be sent
+ * out. It uses the passed buffer to form the packet. This formed LCP
+ * request is what we negotiate for sending options on the link.
+ *
+ * Currently we negotiate : Magic Number Only, but this will change.
+ */
+/*---------------------------------------------------------------------------*/
+
+void lcp_task(struct ppp_context_s *ctx, u8_t *buffer)
+{
+ u8_t *bptr;
+ u16_t t;
+ LCPPKT *pkt;
+
+ /* lcp tx not up and hasn't timed out then lets see if we need to send a
+ * request
+ */
+
+ if (!(ctx->lcp_state & LCP_TX_UP) && !(ctx->lcp_state & LCP_TX_TIMEOUT))
+ {
+ /* Check if we have a request pending */
+
+ if ((ppp_arch_clock_seconds() - ctx->lcp_prev_seconds) > LCP_TIMEOUT)
+ {
+ ctx->lcp_prev_seconds = ppp_arch_clock_seconds();
+
+ DEBUG1(("\nSending LCP request packet - "));
+
+ /* No pending request, lets build one */
+
+ pkt = (LCPPKT *)buffer;
+
+ /* Configure-Request only here, write id */
+
+ pkt->code = CONF_REQ;
+ pkt->id = ctx->ppp_id;
+
+ bptr = pkt->data;
+
+ /* Write options */
+
+ *bptr++ = LPC_ACCM;
+ *bptr++ = 0x6;
+ *bptr++ = 0xff;
+ *bptr++ = 0xff;
+ *bptr++ = 0xff;
+ *bptr++ = 0xff;
+
+#if 0
+ /* Write magic number */
+
+ DEBUG1(("LPC_MAGICNUMBER -"));
+ *bptr++ = LPC_MAGICNUMBER;
+ *bptr++ = 0x6;
+
+ /*
+ *bptr++ = random_rand() & 0xff;
+ *bptr++ = random_rand() & 0xff;
+ *bptr++ = random_rand() & 0xff;
+ *bptr++ = random_rand() & 0xff;
+ */
+
+ *bptr++ = 0x11;
+ *bptr++ = 0x11;
+ *bptr++ = 0x11;
+ *bptr++ = 0x11;
+#endif
+
+#if 0
+ /* Authentication protocol */
+
+ if ((lcp_tx_options & LCP_OPT_AUTH) && 0)
+ {
+ /* If turned on, we only negotiate PAP */
+
+ *bptr++ = LPC_AUTH;
+ *bptr++ = 0x4;
+ *bptr++ = 0xc0;
+ *bptr++ = 0x23;
+ }
+
+ /* PFC */
+
+ if ((lcp_tx_options & LCP_OPT_PFC) && 0)
+ {
+ /* If turned on, we only negotiate PAP */
+
+ *bptr++ = LPC_PFC;
+ *bptr++ = 0x2;
+ }
+
+ /* ACFC */
+
+ if ((lcp_tx_options & LCP_OPT_ACFC) && 0)
+ {
+ /* If turned on, we only negotiate PAP */
+
+ *bptr++ = LPC_ACFC;
+ *bptr++ = 0x2;
+ }
+#endif
+
+ /* Write length */
+
+ t = bptr - buffer;
+ pkt->len = htons(t); /* length here - code and ID + */
+
+ DEBUG1((" len %d\n",t));
+
+ /* Send packet */
+ /* Send packet ahdlc_txz(procol,header,data,headerlen,datalen); */
+
+ ahdlc_tx(ctx, LCP, 0, buffer, 0, t);
+
+ /* Inc retry */
+
+ ctx->lcp_retry++;
+
+ /* Have we timed out? */
+
+ if (ctx->lcp_retry > LCP_RETRY_COUNT)
+ {
+ ctx->lcp_state &= LCP_TX_TIMEOUT;
+ }
+ }
+ }
+}
+
+/*---------------------------------------------------------------------------*/
diff --git a/apps/netutils/pppd/lcp.h b/apps/netutils/pppd/lcp.h
new file mode 100644
index 000000000..2565e43a7
--- /dev/null
+++ b/apps/netutils/pppd/lcp.h
@@ -0,0 +1,133 @@
+/* www.mycal.com
+ ---------------------------------------------------------------------------
+ LCP.h - LCP header file
+ ---------------------------------------------------------------------------
+ Version -
+ 0.1 Original Version June 3, 2000
+ (c)2000 Mycal Labs, All Rights Reserved
+ ---------------------------------------------------------------------------
+*/
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: lcp.h,v 1.1 2007/05/26 07:14:39 oliverschmidt Exp $
+ *
+ */
+
+#ifndef __APPS_NETUTILS_PPPD_LCP_H
+#define __APPS_NETUTILS_PPPD_LCP_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include "ppp_arch.h"
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/* LCP Option Types */
+
+#define LPC_VENDERX 0x0
+#define LPC_MRU 0x1
+#define LPC_ACCM 0x2
+#define LPC_AUTH 0x3
+#define LPC_QUALITY 0x4
+#define LPC_MAGICNUMBER 0x5
+#define LPC_PFC 0x7
+#define LPC_ACFC 0x8
+
+/* LCP Negotiated options flag equates */
+
+#define LCP_OPT_ACCM 0x1
+#define LCP_OPT_AUTH 0x2
+#define LCP_OPT_PFC 0x4
+#define LCP_OPT_ACFC 0x4
+
+/* LCP state machine flags */
+
+#define LCP_TX_UP 0x1
+#define LCP_RX_UP 0x2
+
+#define LCP_RX_AUTH 0x10
+
+/* LCP request for auth */
+
+#define LCP_TERM_PEER 0x20
+
+/* LCP Terminated by peer */
+
+#define LCP_RX_TIMEOUT 0x40
+#define LCP_TX_TIMEOUT 0x80
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+struct ppp_context_s;
+
+typedef struct _lcppkt
+{
+ u8_t code;
+ u8_t id;
+ u16_t len;
+ u8_t data[0];
+} LCPPKT;
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+#undef EXTERN
+#if defined(__cplusplus)
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+void lcp_init(struct ppp_context_s *ctx);
+void lcp_rx(struct ppp_context_s *ctx, u8_t *, u16_t);
+void lcp_task(struct ppp_context_s *ctx, u8_t *buffer);
+void lcp_disconnect(struct ppp_context_s *ctx, u8_t id);
+void lcp_echo_request(struct ppp_context_s *ctx, u8_t *buffer);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __APPS_NETUTILS_PPPD_LCP_H */
diff --git a/apps/netutils/pppd/ntpv3.h b/apps/netutils/pppd/ntpv3.h
new file mode 100644
index 000000000..563b7226f
--- /dev/null
+++ b/apps/netutils/pppd/ntpv3.h
@@ -0,0 +1,207 @@
+/****************************************************************************
+ * apps/netutils/pppd/ntpv3.h
+ *
+ * Copyright (C) 2014-2015 Gregory Nutt. All rights reserved.
+ * Author: Gregory Nutt <gnutt@nuttx.org>
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in
+ * the documentation and/or other materials provided with the
+ * distribution.
+ * 3. Neither the name NuttX nor the names of its contributors may be
+ * used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+ * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ ****************************************************************************/
+
+#ifndef __APPS_NETUTILS_NTPCLIENT_NTPV3_H
+#define __APPS_NETUTILS_NTPCLIENT_NTPV3_H 1
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/* The NTP version is described in RFC 1305 (NTP version 3), Appendix A:
+ *
+ * 0 1 2 3
+ * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * |LI | VN |Mode | Stratum | Poll | Precision |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | Root Delay |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | Root Dispersion |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | Reference Identifier |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | |
+ * | Reference Timestamp (64) |
+ * | |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | |
+ * | Originate Timestamp (64) |
+ * | |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | |
+ * | Receive Timestamp (64) |
+ * | |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | |
+ * | Transmit Timestamp (64) |
+ * | |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | Key Identifier (optional) (32) |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | |
+ * | |
+ * | Message Digest (optional) (128) |
+ * | |
+ * | |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ */
+
+#define NTP_DATAGRAM_MINSIZE (12 * sizeof(uint32_t))
+#define NTP_DATAGRAM_MAXSIZE (17 * sizeof(uint32_t))
+
+/* Leap Indicator (LI): 2-bit code warning of impending leap-second to be
+ * inserted at the end of the last day of the current month. Bits are coded
+ * as follows:
+ *
+ * 00 no warning
+ * 01 last minute has 61 seconds
+ * 10 last minute has 59 seconds
+ * 11 alarm condition (clock not synchronized)
+ *
+ * Version Number (VN): This is a three-bit integer indicating the NTP
+ * version number. In this case, three (3).
+ *
+ * Mode: This is a three-bit integer indicating the mode, with values
+ * defined as follows:
+ *
+ * 0 reserved
+ * 1 symmetric active
+ * 2 symmetric passive
+ * 3 client
+ * 4 server
+ * 5 broadcast
+ * 6 reserved for NTP control message (see Appendix B)
+ * 7 reserved for private use
+ *
+ * Stratum: This is a eight-bit integer indicating the stratum level of the
+ * local clock, with values defined as follows:
+ *
+ * 0 unspecified
+ * 1 primary reference (e.g., radio clock)
+ * 2-255 secondary reference (via NTP)
+ *
+ * Poll Interval: This is an eight-bit signed integer indicating the maximum
+ * interval between successive messages, in seconds to the nearest power of
+ * two.
+ *
+ * Precision: This is an eight-bit signed integer indicating the precision
+ * of the local clock, in seconds to the nearest power of two.
+ *
+ * Root Delay: This is a 32-bit signed fixed-point number indicating the
+ * total roundtrip delay to the primary reference source, in seconds with
+ * fraction point between bits 15 and 16. Note that this variable can take
+ * on both positive and negative values, depending on clock precision and
+ * skew.
+ *
+ * Root Dispersion: This is a 32-bit signed fixed-point number indicating
+ * the maximum error relative to the primary reference source, in seconds
+ * with fraction point between bits 15 and 16. Only positive values greater
+ * than zero are possible.
+ *
+ * Reference Clock Identifier: This is a 32-bit code identifying the
+ * particular reference clock. In the case of stratum 0 (unspecified) or
+ * stratum 1 (primary reference), this is a four-octet, left-justified,
+ * zero-padded ASCII string.
+ *
+ * While not enumerated as part of the NTP specification, the following are
+ * suggested ASCII identifiers:
+ *
+ * Stratum Code Meaning
+ * 0 DCN DCN routing protocol
+ * 0 NIST NIST public modem
+ * 0 TSP TSP time protocol
+ * 0 DTS Digital Time Service
+ * 1 ATOM Atomic clock (calibrated)
+ * 1 VLF VLF radio (OMEGA, etc.)
+ * 1 callsign Generic radio
+ * 1 LORC LORAN-C radionavigation
+ * 1 GOES GOES UHF environment satellite
+ * 1 GPS GPS UHF satellite positioning
+ *
+ * In the case of stratum 2 and greater (secondary reference) this is the
+ * four-octet Internet address of the primary reference host.
+ *
+ * Reference Timestamp: This is the local time at which the local clock was
+ * last set or corrected, in 64-bit timestamp format.
+ *
+ * Originate Timestamp: This is the local time at which the request departed
+ * the client host for the service host, in 64-bit timestamp format.
+ *
+ * Receive Timestamp: This is the local time at which the request arrived at
+ * the service host, in 64-bit timestamp format.
+ *
+ * Transmit Timestamp: This is the local time at which the reply departed
+ * the service host for the client host, in 64-bit timestamp format.
+ *
+ * Authenticator (optional): When the NTP authentication mechanism is
+ * implemented, this contains the authenticator information defined in
+ * Appendix C.
+ */
+
+#define MKLVM(l,v,m) ((uint8_t)(l) << 6 | (uint8_t)(v) << 3 | (uint8_t)(m))
+#define GETLI(lvm) ((uint8_t)(lvm) >> 6)
+#define GETVN(lvm) ((uint8_t)(lvm) >> 3) & 7)
+#define GETMODE(lvm) ((uint8_t)(lvm) & 7)
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+struct ntp_datagram_s
+{
+ uint8_t lvm; /* LI | VN | Mode */
+ uint8_t stratum; /* Stratum */
+ uint8_t poll; /* Poll interval */
+ uint8_t precision; /* Precision */
+ uint8_t rootdelay[4]; /* Root Delay */
+ uint8_t rootdispersion[4]; /* Root dispersion */
+ uint8_t refid[4]; /* Reference Clock Identifier */
+ uint8_t reftimestamp[8]; /* Rererence Timestamp */
+ uint8_t origtimestamp[8]; /* Originate Timestamp */
+ uint8_t recvtimestamp[8]; /* Receive Timestamp */
+ uint8_t xmittimestamp[8]; /* Transmit Timestamp */
+ uint8_t keyid[4]; /* Authenticator data */
+ uint8_t digest1[4];
+ uint8_t digest2[4];
+ uint8_t digest3[4];
+ uint8_t digest4[4];
+};
+
+#endif /* __APPS_NETUTILS_NTPCLIENT_NTPV3_H */
diff --git a/apps/netutils/pppd/pap.c b/apps/netutils/pppd/pap.c
new file mode 100644
index 000000000..982fe83c0
--- /dev/null
+++ b/apps/netutils/pppd/pap.c
@@ -0,0 +1,188 @@
+/* www.mycal.net
+ *---------------------------------------------------------------------------
+ *pap.c - PAP processor for the PPP module - -
+ *---------------------------------------------------------------------------
+ *Version - 0.1 Original Version Jun 3, 2000 - -
+ *---------------------------------------------------------------------------
+ *- Copyright (C) 2000, Mycal Labs www.mycal.com - -
+ *---------------------------------------------------------------------------
+*/
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: pap.c,v 1.2 2010/10/19 18:29:03 adamdunkels Exp $
+ *
+ */
+
+/* */
+/* include files */
+/* */
+
+#include "ppp_conf.h"
+#include "ppp_arch.h"
+#include "ppp.h"
+#include "pap.h"
+#include "lcp.h"
+
+#if PPP_DEBUG
+# define DEBUG1(x) debug_printf x
+#else
+# define DEBUG1(x)
+#endif
+
+/*---------------------------------------------------------------------------*/
+
+void pap_init(struct ppp_context_s *ctx)
+{
+ ctx->pap_retry = 0;
+ ctx->pap_state = 0;
+ ctx->pap_prev_seconds = 0;
+}
+
+/*---------------------------------------------------------------------------*/
+/* pap_rx() - PAP RX protocol Handler */
+/*---------------------------------------------------------------------------*/
+
+void pap_rx(struct ppp_context_s *ctx, u8_t *buffer, u16_t count)
+{
+ u8_t *bptr=buffer;
+ u8_t len;
+
+ switch (*bptr++)
+ {
+ case CONF_REQ:
+ DEBUG1(("CONF REQ - only for server, no support\n"));
+ break;
+
+ case CONF_ACK: /* config Ack */
+ DEBUG1(("CONF ACK - PAP good - "));
+
+ /* Display message if debug */
+
+ len = *bptr++;
+ *(bptr + len) = 0;
+ DEBUG1((" %s \n",bptr));
+ ctx->pap_state |= PAP_TX_UP;
+ break;
+
+ case CONF_NAK:
+ DEBUG1(("CONF NAK - Failed Auth - "));
+ ctx->pap_state |= PAP_TX_AUTH_FAIL;
+
+ /* Display message if debug */
+
+ len = *bptr++;
+ *(bptr + len)=0;
+ DEBUG1((" %s \n",bptr));
+ break;
+ }
+}
+/*---------------------------------------------------------------------------*/
+/* pap_task() - This task needs to be called every so often during the PAP
+ * negotiation phase. This task sends PAP REQ packets.
+ */
+/*---------------------------------------------------------------------------*/
+
+void pap_task(struct ppp_context_s *ctx, u8_t *buffer)
+{
+ u8_t *bptr;
+ u16_t t;
+ PAPPKT *pkt;
+
+ /* If LCP is up and PAP negotiated, try to bring up PAP */
+
+ if (!(ctx->pap_state & PAP_TX_UP) && !(ctx->pap_state & PAP_TX_TIMEOUT))
+ {
+ /* Do we need to send a PAP auth packet?
+ Check if we have a request pending*/
+
+ if ((ppp_arch_clock_seconds() - ctx->pap_prev_seconds) > PAP_TIMEOUT)
+ {
+ ctx->pap_prev_seconds = ppp_arch_clock_seconds();
+
+ /* We need to send a PAP authentication request */
+
+ DEBUG1(("\nSending PAP Request packet - "));
+
+ /* Build a PAP request packet */
+
+ pkt = (PAPPKT *)buffer;
+
+ /* Configure-Request only here, write id */
+
+ pkt->code = CONF_REQ;
+ pkt->id = ctx->ppp_id;
+ bptr = pkt->data;
+
+ /* Write options */
+
+ t = strlen((char*)ctx->pap_username);
+
+ /* Write peer length */
+
+ *bptr++ = (u8_t)t;
+ bptr = memcpy(bptr, ctx->pap_username, t);
+
+ t = strlen((char*)ctx->pap_password);
+ *bptr++ = (u8_t)t;
+ bptr = memcpy(bptr, ctx->pap_password, t);
+
+ /* Write length */
+
+ t = bptr - buffer;
+
+ /* length here - code and ID + */
+
+ pkt->len = htons(t);
+
+ DEBUG1((" Len %d\n",t));
+
+ /* Send packet */
+
+ ahdlc_tx(ctx, PAP, buffer, 0, t, 0);
+
+ ctx->pap_retry++;
+
+ /* Have we failed? */
+
+ if (ctx->pap_retry > PAP_RETRY_COUNT)
+ {
+ DEBUG1(("PAP - timout\n"));
+ ctx->pap_state &= PAP_TX_TIMEOUT;
+ }
+ }
+ }
+}
+
+/*---------------------------------------------------------------------------*/
diff --git a/apps/netutils/pppd/pap.h b/apps/netutils/pppd/pap.h
new file mode 100644
index 000000000..915bc0f27
--- /dev/null
+++ b/apps/netutils/pppd/pap.h
@@ -0,0 +1,113 @@
+/*
+ www.mycal.com
+ ---------------------------------------------------------------------------
+ pap.h - pap header file
+ ---------------------------------------------------------------------------
+ Version
+ 0.1 Original Version June 3, 2000
+ (c)2000 Mycal Labs, All Rights Reserved
+ ---------------------------------------------------------------------------
+*/
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: pap.h,v 1.1 2007/05/26 07:14:40 oliverschmidt Exp $
+ *
+ */
+
+#ifndef __APPS_NETUTILS_PPPD_PAP_H
+#define __APPS_NETUTILS_PPPD_PAP_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include "ppp_arch.h"
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/* PAP state machine flags */
+/* Client only */
+
+#define PAP_TX_UP 0x01
+
+/* Server only */
+
+#define PAP_RX_UP 0x02
+
+#define PAP_RX_AUTH_FAIL 0x10
+#define PAP_TX_AUTH_FAIL 0x20
+#define PAP_RX_TIMEOUT 0x80
+#define PAP_TX_TIMEOUT 0x80
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+struct ppp_context_s;
+
+typedef struct _pappkt
+{
+ u8_t code;
+ u8_t id;
+ u16_t len;
+ u8_t data[0];
+} PAPPKT;
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+#undef EXTERN
+#if defined(__cplusplus)
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+/* Function prototypes */
+void pap_init(struct ppp_context_s *ctx);
+void pap_rx(struct ppp_context_s *ctx, u8_t *, u16_t);
+void pap_task(struct ppp_context_s *ctx, u8_t *buffer);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __APPS_NETUTILS_PPPD_PAP_H */
diff --git a/apps/netutils/pppd/ppp.c b/apps/netutils/pppd/ppp.c
new file mode 100644
index 000000000..b1b19a286
--- /dev/null
+++ b/apps/netutils/pppd/ppp.c
@@ -0,0 +1,456 @@
+/*
+ *---------------------------------------------------------------------------
+ * ppp.c - PPP Processor/Handler
+ *
+ *---------------------------------------------------------------------------
+ *
+ * Version
+ * 0.1 Original Version Jun 3, 2000
+ *
+ *---------------------------------------------------------------------------
+ */
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: ppp.c,v 1.2 2010/10/19 18:29:03 adamdunkels Exp $
+ *
+ */
+
+/* */
+/* include files */
+/* */
+
+#include "ppp_conf.h"
+#include "ppp_arch.h"
+#include "ppp.h"
+#include "ahdlc.h"
+#include "ipcp.h"
+#include "lcp.h"
+#include "pap.h"
+
+#if PPP_DEBUG
+# define DEBUG1(x) debug_printf x
+#else
+# define DEBUG1(x)
+#endif
+
+/* Set the debug message level */
+
+#define PACKET_RX_DEBUG 1
+
+/*---------------------------------------------------------------------------*/
+/* Unknown Protocol Handler, sends reject */
+
+static void ppp_reject_protocol(struct ppp_context_s *ctx, u16_t protocol,
+ u8_t *buffer, u16_t count)
+{
+ u16_t i;
+ u8_t *dptr, *sptr;
+ LCPPKT *pkt;
+
+ /* first copy rejected packet back, start from end and work forward,
+ +++ Pay attention to buffer management when updated. Assumes fixed
+ PPP blocks. */
+
+ DEBUG1(("Rejecting Protocol\n"));
+ if ((count + 6) > PPP_RX_BUFFER_SIZE)
+ {
+ /* This is a fatal error +++ do something about it. */
+
+ DEBUG1(("Cannot Reject Protocol, PKT to big\n"));
+ return;
+ }
+
+ dptr = buffer + count + 6;
+ sptr = buffer + count;
+ for(i = 0; i < count; ++i)
+ {
+ *dptr-- = *sptr--;
+ }
+
+ pkt = (LCPPKT *)buffer;
+ pkt->code = PROT_REJ; /* Write Conf_rej */
+ /*pkt->id = tid++;*/ /* write tid */
+ pkt->len = htons(count + 6);
+ *((u16_t *)(&pkt->data[0])) = htons(protocol);
+
+ ahdlc_tx(ctx, LCP, buffer, 0, (u16_t)(count + 6), 0);
+}
+
+/*---------------------------------------------------------------------------*/
+
+#if PACKET_RX_DEBUG
+void dump_ppp_packet(u8_t *buffer, u16_t len)
+{
+ int i;
+
+ DEBUG1(("\n"));
+ for(i = 0;i < len; ++i)
+ {
+ if ((i & 0x1f) == 0x10)
+ {
+ DEBUG1(("\n"));
+ }
+
+ DEBUG1(("0x%02x ",buffer[i]));
+ }
+
+ DEBUG1(("\n\n"));
+}
+#endif
+
+/*---------------------------------------------------------------------------*/
+/* Initialize and start PPP engine. This just sets things up to
+ * starting values. This can stay a private method.
+ */
+/*---------------------------------------------------------------------------*/
+
+void ppp_init(struct ppp_context_s *ctx)
+{
+#ifdef PPP_STATISTICS
+ ctx->ppp_rx_frame_count = 0;
+#endif
+ ctx->ppp_flags = 0;
+ ctx->ip_no_data_time = 0;
+ ctx->ppp_id = 0;
+
+ pap_init(ctx);
+ ipcp_init(ctx);
+ lcp_init(ctx);
+
+ ahdlc_init(ctx);
+ ahdlc_rx_ready(ctx);
+}
+
+/*---------------------------------------------------------------------------*/
+/* raise_ppp() - This routine will try to bring up a PPP connection,
+ * It is blocking. In the future we probably want to pass a
+ * structure with all the options on bringing up a PPP link, like
+ * server/client, DSN server, username password for PAP... +++ for
+ * now just use config and bit defines
+ */
+/*---------------------------------------------------------------------------*/
+
+#if 0
+u16_t
+ppp_raise(u8_t config, u8_t *username, u8_t *password)
+{
+ u16_t status = 0;
+
+ /* Initialize PPP engine */
+ /* init_ppp(); */
+
+ pap_init();
+ ipcp_init();
+ lcp_init();
+
+ /* Enable PPP */
+
+ ppp_flags = PPP_RX_READY;
+
+ /* Try to bring up the layers */
+
+ while (status == 0)
+ {
+#ifdef SYSTEM_POLLER
+ /* If the the serial interrupt is not hooked to ahdlc_rx, or the
+ system needs to handle other stuff while were blocking, call
+ the system poller.*/
+
+ system_poller();
+#endif
+
+ /* Call the lcp task to bring up the LCP layer */
+
+ lcp_task(ppp_tx_buffer);
+
+ /* If LCP is up, neg next layer */
+
+ if (lcp_state & LCP_TX_UP)
+ {
+ /* If LCP wants PAP, try to authenticate, else bring up IPCP */
+
+ if ((lcp_state & LCP_RX_AUTH) && (!(pap_state & PAP_TX_UP)))
+ {
+ pap_task(ppp_tx_buffer,username,password);
+ }
+ else
+ {
+ ipcp_task(ppp_tx_buffer);
+ }
+ }
+
+ /* If IPCP came up then our link should be up. */
+
+ if ((ipcp_state & IPCP_TX_UP) && (ipcp_state & IPCP_RX_UP))
+ {
+ break;
+ }
+
+ status = check_ppp_errors();
+ }
+
+ return status;
+}
+#endif
+
+/*---------------------------------------------------------------------------*/
+
+void ppp_connect(struct ppp_context_s *ctx)
+{
+ /* Initialize PPP engine */
+
+ /* init_ppp(); */
+ pap_init(ctx);
+ ipcp_init(ctx);
+ lcp_init(ctx);
+
+ /* Enable PPP */
+
+ ctx->ppp_flags = PPP_RX_READY;
+}
+
+/*---------------------------------------------------------------------------*/
+
+void ppp_send(struct ppp_context_s *ctx)
+{
+ /* If IPCP came up then our link should be up. */
+
+ if ((ctx->ipcp_state & IPCP_TX_UP) && (ctx->ipcp_state & IPCP_RX_UP))
+ {
+ ahdlc_tx(ctx, IPV4, 0, ctx->ip_buf, 0, ctx->ip_len);
+ }
+}
+
+/*---------------------------------------------------------------------------*/
+
+void ppp_poll(struct ppp_context_s *ctx)
+{
+ u8_t c;
+
+ ctx->ip_len = 0;
+
+ ++ctx->ip_no_data_time;
+ if (ctx->ip_no_data_time > PPP_IP_TIMEOUT)
+ {
+ ppp_reconnect(ctx);
+ return;
+ }
+
+ if (!(ctx->ppp_flags & PPP_RX_READY))
+ {
+ return;
+ }
+
+ while (ctx->ip_len == 0 && ppp_arch_getchar(ctx, &c))
+ {
+ ahdlc_rx(ctx, c);
+ }
+
+ /* If IPCP came up then our link should be up. */
+
+ if ((ctx->ipcp_state & IPCP_TX_UP) && (ctx->ipcp_state & IPCP_RX_UP))
+ {
+ lcp_echo_request(ctx, ctx->ip_buf);
+ return;
+ }
+
+ /* Call the lcp task to bring up the LCP layer */
+
+ lcp_task(ctx, ctx->ip_buf);
+
+ /* If LCP is up, neg next layer */
+
+ if ((ctx->lcp_state & LCP_TX_UP) && (ctx->lcp_state & LCP_RX_UP))
+ {
+ /* If LCP wants PAP, try to authenticate, else bring up IPCP */
+
+ if ((ctx->lcp_state & LCP_RX_AUTH) && (!(ctx->pap_state & PAP_TX_UP)))
+ {
+ pap_task(ctx, ctx->ip_buf);
+ }
+ else
+ {
+ ipcp_task(ctx, ctx->ip_buf);
+ }
+ }
+}
+
+/*---------------------------------------------------------------------------*/
+/* ppp_upcall() - this is where valid PPP frames from the ahdlc layer are
+ * sent to be processed and demuxed.
+ */
+/*---------------------------------------------------------------------------*/
+
+void ppp_upcall(struct ppp_context_s *ctx, u16_t protocol, u8_t *buffer, u16_t len)
+{
+#ifdef PPP_STATISTICS
+ ++ctx->ppp_rx_frame_count;
+
+#ifdef PPP_DEBUG
+ dump_ppp_packet(buffer, len);
+#endif
+
+#endif /* PPP_STATISTICS */
+
+ /* Check to see if we have a packet waiting to be processed */
+
+ if (ctx->ppp_flags & PPP_RX_READY)
+ {
+ /* Demux on protocol field */
+
+ switch(protocol) {
+ case LCP: /* We must support some level of LCP */
+ DEBUG1(("LCP Packet - "));
+ lcp_rx(ctx, buffer, len);
+ DEBUG1(("\n"));
+ break;
+
+ case PAP: /* PAP should be compile in optional */
+ DEBUG1(("PAP Packet - "));
+ pap_rx(ctx, buffer, len);
+ DEBUG1(("\n"));
+ break;
+
+ case IPCP: /* IPCP should be compile in optional. */
+ DEBUG1(("IPCP Packet - "));
+ ipcp_rx(ctx, buffer, len);
+ DEBUG1(("\n"));
+ break;
+
+ case IPV4: /* We must support IPV4 */
+ DEBUG1(("IPV4 Packet---\n"));
+ memcpy(ctx->ip_buf, buffer, len);
+ ctx->ip_len = len;
+ ctx->ip_no_data_time = 0;
+ DEBUG1(("\n"));
+ break;
+
+ default:
+ DEBUG1(("Unknown PPP Packet Type 0x%04x - ",protocol));
+ ppp_reject_protocol(ctx, protocol, buffer, len);
+ DEBUG1(("\n"));
+ break;
+ }
+ }
+}
+
+/*---------------------------------------------------------------------------*/
+/* scan_packet(list,buffer,len)
+ *
+ * list = list of supported ID's
+ * *buffer pointer to the first code in the packet
+ * length of the codespace
+ */
+
+u16_t scan_packet(struct ppp_context_s *ctx, u16_t protocol, const u8_t *list,
+ u8_t *buffer, u8_t *options, u16_t len)
+{
+ const u8_t *tlist;
+ u8_t *bptr;
+ u8_t *tptr;
+ u8_t bad = 0;
+ u8_t i, j, good;
+
+ bptr = tptr = options;
+
+ /* Scan through the packet and see if it has any unsupported codes */
+
+ while (bptr < options + len)
+ {
+ /* Get code and see if it matches somwhere in the list, if not
+ we don't support it */
+
+ i = *bptr++;
+
+ /* DEBUG2("%x - ",i); */
+
+ tlist = list;
+ good = 0;
+ while (*tlist)
+ {
+ /* DEBUG2("%x ",*tlist); */
+ if (i == *tlist++)
+ {
+ good = 1;
+ break;
+ }
+ }
+
+ if (!good)
+ {
+ /* We don't understand it, write it back */
+
+ DEBUG1(("We don't understand option 0x%02x\n",i));
+ bad = 1;
+ *tptr++ = i;
+ j = *tptr++ = *bptr++;
+ for(i = 0; i < j - 2; ++i)
+ {
+ *tptr++ = *bptr++;
+ }
+ }
+ else
+ {
+ /* Advance over to next option */
+
+ bptr += *bptr - 1;
+ }
+ }
+
+ /* Bad? if we we need to send a config Reject */
+
+ if (bad)
+ {
+ /* Write the config Rej packet we've built above, take on the header */
+
+ bptr = buffer;
+ *bptr++ = CONF_REJ; /* Write Conf_rej */
+ bptr++; /* skip over ID */
+ *bptr++ = 0;
+ *bptr = tptr - buffer;
+
+ /* Length right here? */
+
+ /* Write the reject frame */
+
+ DEBUG1(("Writing Reject frame --\n"));
+ ahdlc_tx(ctx, protocol, buffer, 0, (u16_t)(tptr - buffer), 0);
+ DEBUG1(("\nEnd writing reject \n"));
+ }
+
+ return bad;
+}
+
+/*---------------------------------------------------------------------------*/
diff --git a/apps/netutils/pppd/ppp.h b/apps/netutils/pppd/ppp.h
new file mode 100644
index 000000000..f70b63c60
--- /dev/null
+++ b/apps/netutils/pppd/ppp.h
@@ -0,0 +1,233 @@
+/* www.mycal.net
+---------------------------------------------------------------------------
+ ppp.h - ppp header file
+---------------------------------------------------------------------------
+ Version
+ 0.1 Original Version June 3, 2000
+ (c)2000 Mycal Labs, All Rights Reserved
+ --------------------------------------------------------------------------- */
+/*
+ * Copyright (c) 2003, Mike Johnson, Mycal Labs, www.mycal.net
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Mike Johnson/Mycal Labs
+ * www.mycal.net.
+ * 4. The name of the author may not be used to endorse or promote
+ * products derived from this software without specific prior
+ * written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * This file is part of the Mycal Modified uIP TCP/IP stack.
+ *
+ * $Id: ppp.h,v 1.1 2007/05/26 07:14:40 oliverschmidt Exp $
+ *
+ */
+
+#ifndef __APPS_NETUTILS_PPPD_PPP_H
+#define __APPS_NETUTILS_PPPD_PPP_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include "ppp_conf.h"
+#include "ahdlc.h"
+#include "lcp.h"
+#include "ipcp.h"
+#include "pap.h"
+#include "ppp_arch.h"
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+#define CRC_GOOD_VALUE 0xf0b8
+
+/* ppp_rx_status values */
+
+#define PPP_RX_IDLE 0
+#define PPP_READY 1
+
+/* ppp flags */
+
+#define PPP_ESCAPED 0x1
+#define PPP_RX_READY 0x2
+#define PPP_RX_ASYNC_MAP 0x8
+#define PPP_TX_ASYNC_MAP 0x8
+#define PPP_PFC 0x10
+#define PPP_ACFC 0x20
+
+/* Supported PPP Protocols */
+
+#define LCP 0xc021
+#define PAP 0xc023
+#define IPCP 0x8021
+#define IPV4 0x0021
+
+/* LCP codes packet types */
+
+#define CONF_REQ 0x1
+#define CONF_ACK 0x2
+#define CONF_NAK 0x3
+#define CONF_REJ 0x4
+#define TERM_REQ 0x5
+#define TERM_ACK 0x6
+#define PROT_REJ 0x8
+#define ECHO_REQ 0x9
+#define ECHO_REP 0xa
+
+/* Raise PPP config bits */
+
+#define USE_PAP 0x1
+#define USE_NOACCMBUG 0x2
+#define USE_GETDNS 0x4
+
+#define ppp_setusername(un) strncpy(pap_username, (un), PAP_USERNAME_SIZE)
+#define ppp_setpassword(pw) strncpy(pap_password, (pw), PAP_PASSWORD_SIZE)
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+struct chat_script_s;
+
+/* PPP context definition */
+
+struct ppp_context_s
+{
+ /* IP Buffer */
+
+ u8_t ip_buf[PPP_RX_BUFFER_SIZE];
+ u16_t ip_len;
+
+ /* Main status */
+
+ u8_t ppp_flags;
+ u8_t ppp_status;
+ u16_t ppp_tx_mru;
+ u8_t ppp_id;
+
+ /* IP timeout */
+
+ u16_t ip_no_data_time;
+
+ /* Interfaces */
+
+ int tty_fd;
+ u8_t ttyname[TTYNAMSIZ];
+ int if_fd;
+ u8_t ifname[IFNAMSIZ];
+
+ /* Addresses */
+
+ struct in_addr local_ip;
+#ifdef IPCP_GET_PEER_IP
+ struct in_addr peer_ip;
+#endif
+#ifdef IPCP_GET_PRI_DNS
+ struct in_addr pri_dns_addr;
+#endif
+#ifdef IPCP_GET_SEC_DNS
+ struct in_addr sec_dns_addr;
+#endif
+
+ /* LCP */
+
+ u8_t lcp_state;
+ u16_t lcp_tx_mru;
+ u8_t lcp_retry;
+ time_t lcp_prev_seconds;
+
+ /* PAP */
+
+ u8_t pap_username[PAP_USERNAME_SIZE];
+ u8_t pap_password[PAP_PASSWORD_SIZE];
+ u8_t pap_state;
+ u8_t pap_retry;
+ time_t pap_prev_seconds;
+
+ /* IPCP */
+
+ u8_t ipcp_state;
+ u8_t ipcp_retry;
+ time_t ipcp_prev_seconds;
+
+ /* AHDLC */
+
+ u8_t ahdlc_rx_buffer[PPP_RX_BUFFER_SIZE];
+ u16_t ahdlc_tx_crc; /* running tx CRC */
+ u16_t ahdlc_rx_crc; /* running rx CRC */
+ u16_t ahdlc_rx_count; /* number of rx bytes processed, cur frame */
+ u8_t ahdlc_flags; /* ahdlc state flags, see above */
+ u8_t ahdlc_tx_offline;
+
+ /* Scripts */
+
+ struct chat_script_s *connect_script;
+ struct chat_script_s *disconnect_script;
+
+ /* Statistics counters */
+
+#ifdef PPP_STATISTICS
+ u16_t ahdlc_crc_error;
+ u16_t ahdlc_rx_tobig_error;
+ u32_t ppp_rx_frame_count;
+ u32_t ppp_tx_frame_count;
+#endif
+};
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+#undef EXTERN
+#if defined(__cplusplus)
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+/*
+ * Function Prototypes
+ */
+void ppp_init(struct ppp_context_s *ctx);
+void ppp_connect(struct ppp_context_s *ctx);
+
+extern void ppp_reconnect(struct ppp_context_s *ctx);
+
+void ppp_send(struct ppp_context_s *ctx);
+void ppp_poll(struct ppp_context_s *ctx);
+
+void ppp_upcall(struct ppp_context_s *ctx, u16_t, u8_t *, u16_t);
+u16_t scan_packet(struct ppp_context_s *ctx, u16_t, const u8_t *list,
+ u8_t *buffer, u8_t *options, u16_t len);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __APPS_NETUTILS_PPPD_PPP_H */
diff --git a/apps/netutils/pppd/ppp_arch.h b/apps/netutils/pppd/ppp_arch.h
new file mode 100644
index 000000000..5226df48f
--- /dev/null
+++ b/apps/netutils/pppd/ppp_arch.h
@@ -0,0 +1,59 @@
+#ifndef __APPS_NETUTILS_PPPD_PPP_ARCH_H
+#define __APPS_NETUTILS_PPPD_PPP_ARCH_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <stdint.h>
+#include <string.h>
+#include <time.h>
+#include <stdio.h>
+
+#include <arpa/inet.h>
+#include <net/if.h>
+
+#include <apps/netutils/netlib.h>
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+#define TTYNAMSIZ 16
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+struct ppp_context_s;
+
+typedef uint8_t u8_t;
+typedef uint16_t u16_t;
+typedef uint32_t u32_t;
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+#undef EXTERN
+#if defined(__cplusplus)
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+time_t ppp_arch_clock_seconds(void);
+
+int ppp_arch_getchar(struct ppp_context_s *ctx, u8_t *p);
+int ppp_arch_putchar(struct ppp_context_s *ctx, u8_t c);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __APPS_NETUTILS_PPPD_PPP_ARCH_H */ \ No newline at end of file
diff --git a/apps/netutils/pppd/ppp_conf.h b/apps/netutils/pppd/ppp_conf.h
new file mode 100644
index 000000000..dfbfbfd22
--- /dev/null
+++ b/apps/netutils/pppd/ppp_conf.h
@@ -0,0 +1,36 @@
+#ifndef __APPS_NETUTILS_PPPD_PPP_CONF_H
+#define __APPS_NETUTILS_PPPD_PPP_CONF_H
+
+#define IPCP_RETRY_COUNT 5
+#define IPCP_TIMEOUT 5
+#define IPV6CP_RETRY_COUNT 5
+#define IPV6CP_TIMEOUT 5
+#define LCP_RETRY_COUNT 5
+#define LCP_TIMEOUT 5
+#define PAP_RETRY_COUNT 5
+#define PAP_TIMEOUT 5
+#define LCP_ECHO_INTERVAL 20
+
+#define PPP_IP_TIMEOUT (6*3600)
+#define PPP_MAX_CONNECT 15
+
+#define PAP_USERNAME_SIZE 16
+#define PAP_PASSWORD_SIZE 16
+#define PAP_USERNAME "user"
+#define PAP_PASSWORD "pass"
+
+#define xxdebug_printf printf
+#define debug_printf printf
+
+#define PPP_RX_BUFFER_SIZE 1024 //1024 //GD 2048 for 1280 IPv6 MTU
+#define PPP_TX_BUFFER_SIZE 64
+
+#define AHDLC_TX_OFFLINE 5
+//#define AHDLC_COUNTERS 1 //defined for AHDLC stats support, Guillaume Descamps, September 19th, 2011
+
+#define IPCP_GET_PEER_IP 1
+
+#define PPP_STATISTICS 1
+#define PPP_DEBUG 1
+
+#endif /* __APPS_NETUTILS_PPPD_PPP_CONF_H */ \ No newline at end of file
diff --git a/apps/netutils/pppd/pppd.c b/apps/netutils/pppd/pppd.c
new file mode 100644
index 000000000..2cd456143
--- /dev/null
+++ b/apps/netutils/pppd/pppd.c
@@ -0,0 +1,435 @@
+/****************************************************************************
+ * netutils/pppd/pppd.c
+ *
+ * Copyright (C) 2015 Max Nekludov. All rights reserved.
+ * Author: Max Nekludov <macscomp@gmail.com>
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in
+ * the documentation and/or other materials provided with the
+ * distribution.
+ * 3. Neither the name NuttX nor the names of its contributors may be
+ * used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
+ * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <sys/socket.h>
+#include <sys/ioctl.h>
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <time.h>
+#include <sched.h>
+#include <fcntl.h>
+#include <errno.h>
+#include <poll.h>
+#include <time.h>
+#include <debug.h>
+
+#include <netinet/in.h>
+#include <net/if.h>
+#include <nuttx/net/tun.h>
+
+#include "ppp.h"
+#include "chat.h"
+
+#if PPP_ARCH_HAVE_MODEM_RESET
+extern void ppp_arch_modem_reset(const char *tty);
+#endif
+
+/*
+socat /dev/ttyUSB2,raw,echo=0,b115200,crtscts=0 /dev/ttyUSB7,raw,echo=0,b115200,crtscts=0
+*/
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Private Types
+ ****************************************************************************/
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+/* This type describes the state of the NTP client daemon. Only once
+ * instance of the NTP daemon is permitted in this implementation. This
+ * limitation is due only to this global data structure.
+ */
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+static struct chat_script_s connect_script =
+{
+ .timeout = 30,
+ .lines =
+ {
+ {"AT", "OK"},
+ {"AT+CGDCONT = 1,\"IP\",\"internet\"", "OK"},
+ {"ATD*99***1#", "CONNECT"},
+ {0, 0}
+ },
+};
+
+static struct chat_script_s disconnect_script =
+{
+ .timeout = 30,
+ .lines =
+ {
+ {"ATZ", "OK"},
+ {0, 0}
+ },
+};
+
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: make_nonblock
+ ****************************************************************************/
+
+static int make_nonblock(int fd)
+{
+ int flags;
+
+ if( (flags = fcntl(fd, F_GETFL, 0)) < 0)
+ {
+ return flags;
+ }
+
+ if( (flags = fcntl(fd, F_SETFL, flags | O_NONBLOCK)) < 0 )
+ {
+ return flags;
+ }
+
+ return 0;
+}
+
+/****************************************************************************
+ * Name: tun_alloc
+ ****************************************************************************/
+
+static int tun_alloc(char *dev)
+{
+ struct ifreq ifr;
+ int fd, err;
+
+ if( (fd = open("/dev/tun", O_RDWR)) < 0 )
+ return fd;
+
+ printf("tun fd:%i\n", fd);
+
+ if ((err = make_nonblock(fd)) < 0)
+ {
+ close(fd);
+ return err;
+ }
+
+ memset(&ifr, 0, sizeof(ifr));
+ ifr.ifr_flags = IFF_TUN;
+ if( *dev )
+ {
+ strncpy(ifr.ifr_name, dev, IFNAMSIZ);
+ }
+
+ if( (err = ioctl(fd, TUNSETIFF, (unsigned long)&ifr)) < 0 )
+ {
+ close(fd);
+ return err;
+ }
+
+ strcpy(dev, ifr.ifr_name);
+
+ return fd;
+}
+
+/****************************************************************************
+ * Name: open_tty
+ ****************************************************************************/
+
+static int open_tty(char *dev)
+{
+ int fd;
+ int err;
+
+ if( (fd = open(dev, O_RDWR)) < 0 )
+ return fd;
+
+ if ((err = make_nonblock(fd)) < 0)
+ {
+ close(fd);
+ return err;
+ }
+
+ printf("tty fd:%i\n", fd);
+
+ return fd;
+}
+
+/****************************************************************************
+ * Name: ppp_check_errors
+ ****************************************************************************/
+
+static u8_t ppp_check_errors(struct ppp_context_s *ctx)
+{
+ u8_t ret = 0;
+
+ /* Check Errors */
+
+ if(ctx->lcp_state & (LCP_TX_TIMEOUT | LCP_RX_TIMEOUT | LCP_TERM_PEER))
+ {
+ ret = 1;
+ }
+
+ if(ctx->pap_state & (PAP_TX_AUTH_FAIL | PAP_RX_AUTH_FAIL | PAP_TX_TIMEOUT | PAP_RX_TIMEOUT))
+ {
+ ret = 2;
+ }
+
+ if(ctx->ipcp_state & (IPCP_TX_TIMEOUT))
+ {
+ ret = 3;
+ }
+
+ return ret;
+}
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: ppp_reconnect
+ ****************************************************************************/
+
+void ppp_reconnect(struct ppp_context_s *ctx)
+{
+ int ret;
+ int retry = PPP_MAX_CONNECT;
+
+ netlib_ifdown((char*)ctx->ifname);
+
+ lcp_disconnect(ctx, ++ctx->ppp_id);
+ sleep(1);
+ lcp_disconnect(ctx, ++ctx->ppp_id);
+ sleep(1);
+ write(ctx->tty_fd, "+++", 3);
+ sleep(2);
+ write(ctx->tty_fd, "ATE1\r\n", 6);
+
+ if (ctx->disconnect_script)
+ {
+ ret = ppp_chat(ctx->tty_fd, ctx->disconnect_script, 1 /*echo on*/);
+ if (ret < 0)
+ {
+ printf("ppp: disconnect script failed\n");
+ }
+ }
+
+ if (ctx->connect_script)
+ {
+ do
+ {
+ ret = ppp_chat(ctx->tty_fd, ctx->connect_script, 1 /*echo on*/);
+ if (ret < 0)
+ {
+ printf("ppp: connect script failed\n");
+ --retry;
+ if (retry == 0)
+ {
+ retry = PPP_MAX_CONNECT;
+#if PPP_ARCH_HAVE_MODEM_RESET
+ ppp_arch_modem_reset((char*)ctx->ttyname);
+#endif
+ sleep(45);
+ }
+ else
+ {
+ sleep(10);
+ }
+ }
+ }
+ while (ret != 0);
+ }
+
+ ppp_init(ctx);
+ ppp_connect(ctx);
+
+ ctx->ip_len = 0;
+}
+
+/****************************************************************************
+ * Name: ppp_arch_clock_seconds
+ ****************************************************************************/
+
+time_t ppp_arch_clock_seconds(void)
+{
+ struct timespec ts;
+
+ if (clock_gettime(CLOCK_MONOTONIC, &ts) < 0)
+ {
+ return 0;
+ }
+
+ return ts.tv_sec;
+}
+
+/****************************************************************************
+ * Name: ppp_arch_getchar
+ ****************************************************************************/
+
+int ppp_arch_getchar(struct ppp_context_s *ctx, u8_t *c)
+{
+ int ret;
+ ret = read(ctx->tty_fd, c, 1);
+ return ret == 1 ? ret : 0;
+}
+
+/****************************************************************************
+ * Name: ppp_arch_putchar
+ ****************************************************************************/
+
+int ppp_arch_putchar(struct ppp_context_s *ctx, u8_t c)
+{
+ int ret;
+ struct pollfd fds;
+
+ ret = write(ctx->tty_fd, &c, 1);
+ if (ret < 0 && errno == EAGAIN)
+ {
+ fds.fd = ctx->tty_fd;
+ fds.events = POLLOUT;
+ fds.revents = 0;
+
+ ret = poll(&fds, 1, 1000);
+ if (ret > 0)
+ {
+ ret = write(ctx->tty_fd, &c, 1);
+ }
+ }
+
+ return ret == 1 ? ret : 0;
+}
+
+/****************************************************************************
+ * Name: pppd_main
+ ****************************************************************************/
+
+int pppd_main(int argc, char **argv)
+{
+ struct pollfd fds[2];
+ int ret;
+ struct ppp_context_s *ctx;
+
+ ctx = (struct ppp_context_s*)malloc(sizeof(struct ppp_context_s));
+ memset(ctx, 0, sizeof(struct ppp_context_s));
+
+ strcpy((char*)ctx->pap_username, PAP_USERNAME);
+ strcpy((char*)ctx->pap_password, PAP_PASSWORD);
+ strcpy((char*)ctx->ifname, "ppp%d");
+ strcpy((char*)ctx->ttyname, "/dev/ttyS2");
+
+ ctx->connect_script = &connect_script;
+ ctx->disconnect_script = &disconnect_script;
+
+ ctx->if_fd = tun_alloc((char*)ctx->ifname);
+ if (ctx->if_fd < 0)
+ {
+ free(ctx);
+ return 2;
+ }
+
+ ctx->tty_fd = open_tty((char*)ctx->ttyname);
+ if (ctx->tty_fd < 0)
+ {
+ close(ctx->tty_fd);
+ free(ctx);
+ return 2;
+ }
+
+ fds[0].fd = ctx->if_fd;
+ fds[0].events = POLLIN;
+
+ fds[1].fd = ctx->tty_fd;
+ fds[1].events = POLLIN;
+
+ ppp_init(ctx);
+ ppp_reconnect(ctx);
+
+ while (1)
+ {
+ fds[0].revents = fds[1].revents = 0;
+
+ ret = poll(fds, 2, 1000);
+
+ if (ret > 0 && fds[0].revents & POLLIN)
+ {
+ ret = read(ctx->if_fd, ctx->ip_buf, PPP_RX_BUFFER_SIZE);
+ printf("read from tun :%i\n", ret);
+ if (ret > 0)
+ {
+ ctx->ip_len = ret;
+ ppp_send(ctx);
+ ctx->ip_len = 0;
+ }
+ }
+
+ ppp_poll(ctx);
+
+ if (ppp_check_errors(ctx))
+ {
+ ppp_reconnect(ctx);
+ }
+ else
+ {
+ if (ctx->ip_len > 0)
+ {
+ ret = write(ctx->if_fd, ctx->ip_buf, ctx->ip_len);
+ //printf("write to tun :%i\n", ret);
+ ctx->ip_len = 0;
+
+ ret = read(ctx->if_fd, ctx->ip_buf, PPP_RX_BUFFER_SIZE);
+ //printf("read (after write) from tun :%i\n", ret);
+ if (ret > 0)
+ {
+ ctx->ip_len = ret;
+ ppp_send(ctx);
+ ctx->ip_len = 0;
+ }
+ }
+ }
+ }
+
+ return 1;
+}