mirror of
https://github.com/apache/nuttx.git
synced 2026-06-02 01:21:26 +08:00
Import of uIP 1.0
git-svn-id: svn://svn.code.sf.net/p/nuttx/code/trunk@308 42af7a65-404d-4744-a932-0658087f49c3
This commit is contained in:
@@ -0,0 +1,77 @@
|
|||||||
|
############################################################
|
||||||
|
# Makefile
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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 Gregory Nutt 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
|
||||||
|
|
||||||
|
MKDEP = $(TOPDIR)/tools/mkdeps.sh
|
||||||
|
|
||||||
|
ASRCS =
|
||||||
|
AOBJS = $(ASRCS:.S=$(OBJEXT))
|
||||||
|
CSRCS = main.c
|
||||||
|
COBJS = $(CSRCS:.c=$(OBJEXT))
|
||||||
|
|
||||||
|
SRCS = $(ASRCS) $(CSRCS)
|
||||||
|
OBJS = $(AOBJS) $(COBJS)
|
||||||
|
|
||||||
|
BIN = lib$(CONFIG_EXAMPLE)$(LIBEXT)
|
||||||
|
|
||||||
|
all: $(BIN)
|
||||||
|
|
||||||
|
$(AOBJS): %$(OBJEXT): %.S
|
||||||
|
$(CC) -c $(CFLAGS) $< -o $@
|
||||||
|
|
||||||
|
$(COBJS): %$(OBJEXT): %.c
|
||||||
|
$(CC) -c $(CFLAGS) $< -o $@
|
||||||
|
|
||||||
|
$(BIN): $(OBJS)
|
||||||
|
( for obj in $(OBJS) ; do \
|
||||||
|
$(AR) $@ $${obj} || \
|
||||||
|
{ echo "$(AR) $@ $obj FAILED!" ; exit 1 ; } ; \
|
||||||
|
done ; )
|
||||||
|
|
||||||
|
.depend: Makefile $(SRCS)
|
||||||
|
$(MKDEP) $(CC) -- $(CFLAGS) -- $(SRCS) >Make.dep
|
||||||
|
touch $@
|
||||||
|
|
||||||
|
depend: .depend
|
||||||
|
|
||||||
|
clean:
|
||||||
|
rm -f $(BIN) *.o *.rel *.asm *.lst *.sym *.adb *~
|
||||||
|
|
||||||
|
distclean: clean
|
||||||
|
rm -f Make.dep .depend
|
||||||
|
|
||||||
|
-include Make.dep
|
||||||
@@ -0,0 +1,165 @@
|
|||||||
|
/* main.c
|
||||||
|
* Copyright (c) 2001, Adam Dunkels.
|
||||||
|
* 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 Adam Dunkels.
|
||||||
|
* 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 uIP TCP/IP stack.
|
||||||
|
*
|
||||||
|
* $Id: main.c,v 1.1.1.1 2007-08-26 23:10:37 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <time.h>
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
#include <net/uip/uip-arp.h>
|
||||||
|
|
||||||
|
/* Here we include the header file for the application(s) we use in
|
||||||
|
* our project as defined in the config/<board-name>/defconfig file
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define CONFIG_EXAMPLE_UIP_WEBSERVER 1 /* For now */
|
||||||
|
|
||||||
|
#if defined(CONFIG_EXAMPLE_UIP_SMTP)
|
||||||
|
# include <net/uip/smtp.h>
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_TELNETD)
|
||||||
|
# include <net/uip/telnetd.h>
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_WEBSERVER)
|
||||||
|
# include <net/uip/httpd.h>
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_DHCPC)
|
||||||
|
# include <net/uip/dhcpc.h>
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_RESOLV)
|
||||||
|
# include <net/uip/resolv.h>
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_WEBCLIENT)
|
||||||
|
# include <net/uip/webclient.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
int user_start(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
uip_ipaddr_t ipaddr;
|
||||||
|
#if defined(CONFIG_EXAMPLE_UIP_DHCPC)
|
||||||
|
uint16 mac[6] = {1,2,3,4,5,6};
|
||||||
|
#endif
|
||||||
|
|
||||||
|
uip_ipaddr(ipaddr, 192,168,0,2);
|
||||||
|
uip_sethostaddr(ipaddr);
|
||||||
|
uip_ipaddr(ipaddr, 192,168,0,1);
|
||||||
|
uip_setdraddr(ipaddr);
|
||||||
|
uip_ipaddr(ipaddr, 255,255,255,0);
|
||||||
|
uip_setnetmask(ipaddr);
|
||||||
|
|
||||||
|
#if defined(CONFIG_EXAMPLE_UIP_WEBSERVER)
|
||||||
|
httpd_init();
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_TELNETD)
|
||||||
|
telnetd_init();
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_DHCPC)
|
||||||
|
dhcpc_init(&mac, 6);
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_SMTP)
|
||||||
|
uip_ipaddr(ipaddr, 127,0,0,1);
|
||||||
|
smtp_configure("localhost", ipaddr);
|
||||||
|
SMTP_SEND("adam@sics.se", NULL, "uip-testing@example.com",
|
||||||
|
"Testing SMTP from uIP",
|
||||||
|
"Test message sent by uIP\r\n");
|
||||||
|
#elif defined(CONFIG_EXAMPLE_UIP_WEBCLIENT)
|
||||||
|
webclient_init();
|
||||||
|
resolv_init();
|
||||||
|
uip_ipaddr(ipaddr, 195,54,122,204);
|
||||||
|
resolv_conf(ipaddr);
|
||||||
|
resolv_query("www.sics.se");
|
||||||
|
#endif
|
||||||
|
|
||||||
|
while(1)
|
||||||
|
{
|
||||||
|
sleep(3);
|
||||||
|
printf("main: Still running\n");
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void uip_log(char *m)
|
||||||
|
{
|
||||||
|
printf("uIP log message: %s\n", m);
|
||||||
|
}
|
||||||
|
|
||||||
|
void resolv_found(char *name, uint16 *ipaddr)
|
||||||
|
{
|
||||||
|
if (ipaddr == NULL)
|
||||||
|
{
|
||||||
|
printf("Host '%s' not found.\n", name);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
printf("Found name '%s' = %d.%d.%d.%d\n", name,
|
||||||
|
htons(ipaddr[0]) >> 8, htons(ipaddr[0]) & 0xff,
|
||||||
|
htons(ipaddr[1]) >> 8, htons(ipaddr[1]) & 0xff);
|
||||||
|
/* webclient_get("www.sics.se", 80, "/~adam/uip");*/
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifdef __DHCPC_H__
|
||||||
|
void dhcpc_configured(const struct dhcpc_state *s)
|
||||||
|
{
|
||||||
|
uip_sethostaddr(s->ipaddr);
|
||||||
|
uip_setnetmask(s->netmask);
|
||||||
|
uip_setdraddr(s->default_router);
|
||||||
|
resolv_conf(s->dnsaddr);
|
||||||
|
}
|
||||||
|
#endif /* __DHCPC_H__ */
|
||||||
|
|
||||||
|
void smtp_done(unsigned char code)
|
||||||
|
{
|
||||||
|
printf("SMTP done with code %d\n", code);
|
||||||
|
}
|
||||||
|
|
||||||
|
void webclient_closed(void)
|
||||||
|
{
|
||||||
|
printf("Webclient: connection closed\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
void webclient_aborted(void)
|
||||||
|
{
|
||||||
|
printf("Webclient: connection aborted\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
void webclient_timedout(void)
|
||||||
|
{
|
||||||
|
printf("Webclient: connection timed out\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
void webclient_connected(void)
|
||||||
|
{
|
||||||
|
printf("Webclient: connected, waiting for data...\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
void webclient_datahandler(char *data, uint16 len)
|
||||||
|
{
|
||||||
|
printf("Webclient: got %d bytes of data.\n", len);
|
||||||
|
}
|
||||||
@@ -0,0 +1,78 @@
|
|||||||
|
/* httpd.h
|
||||||
|
*
|
||||||
|
* Copyright (c) 2001-2005, Adam Dunkels.
|
||||||
|
* 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. 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __HTTPD_H__
|
||||||
|
#define __HTTPD_H__
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <net/uip/psock.h>
|
||||||
|
|
||||||
|
#define HTTPD_FS_STATISTICS 1
|
||||||
|
|
||||||
|
struct httpd_fs_file
|
||||||
|
{
|
||||||
|
char *data;
|
||||||
|
int len;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct httpd_state
|
||||||
|
{
|
||||||
|
unsigned char timer;
|
||||||
|
struct psock sin, sout;
|
||||||
|
char inputbuf[50];
|
||||||
|
char filename[20];
|
||||||
|
char state;
|
||||||
|
struct httpd_fs_file file;
|
||||||
|
int len;
|
||||||
|
char *scriptptr;
|
||||||
|
int scriptlen;
|
||||||
|
|
||||||
|
unsigned short count;
|
||||||
|
};
|
||||||
|
|
||||||
|
#ifdef HTTPD_FS_STATISTICS
|
||||||
|
#if HTTPD_FS_STATISTICS == 1
|
||||||
|
extern uint16 httpd_fs_count(char *name);
|
||||||
|
#endif /* HTTPD_FS_STATISTICS */
|
||||||
|
#endif /* HTTPD_FS_STATISTICS */
|
||||||
|
|
||||||
|
void httpd_init(void);
|
||||||
|
void httpd_log(char *msg);
|
||||||
|
void httpd_log_file(uint16 *requester, char *file);
|
||||||
|
|
||||||
|
/* file must be allocated by caller and will be filled in
|
||||||
|
* by the function.
|
||||||
|
*/
|
||||||
|
|
||||||
|
int httpd_fs_open(const char *name, struct httpd_fs_file *file);
|
||||||
|
void httpd_fs_init(void);
|
||||||
|
|
||||||
|
|
||||||
|
#endif /* __HTTPD_H__ */
|
||||||
@@ -0,0 +1,237 @@
|
|||||||
|
/* psock.h
|
||||||
|
* Protosocket library header file
|
||||||
|
* Author: Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
* Copyright (c) 2004, Swedish Institute of Computer Science.
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* psock Protosockets library
|
||||||
|
*
|
||||||
|
* The protosocket library provides an interface to the uIP stack that is
|
||||||
|
* similar to the traditional BSD socket interface. Unlike programs
|
||||||
|
* written for the ordinary uIP event-driven interface, programs
|
||||||
|
* written with the protosocket library are executed in a sequential
|
||||||
|
* fashion and does not have to be implemented as explicit state
|
||||||
|
* machines.
|
||||||
|
*
|
||||||
|
* Protosockets only work with TCP connections.
|
||||||
|
*
|
||||||
|
* The protosocket library uses \ref pt protothreads to provide
|
||||||
|
* sequential control flow. This makes the protosockets lightweight in
|
||||||
|
* terms of memory, but also means that protosockets inherits the
|
||||||
|
* functional limitations of protothreads. Each protosocket lives only
|
||||||
|
* within a single function. Automatic variables (stack variables) are
|
||||||
|
* not retained across a protosocket library function call.
|
||||||
|
*
|
||||||
|
* \note Because the protosocket library uses protothreads, local
|
||||||
|
* variables will not always be saved across a call to a protosocket
|
||||||
|
* library function. It is therefore advised that local variables are
|
||||||
|
* used with extreme care.
|
||||||
|
*
|
||||||
|
* The protosocket library provides functions for sending data without
|
||||||
|
* having to deal with retransmissions and acknowledgements, as well
|
||||||
|
* as functions for reading data without having to deal with data
|
||||||
|
* being split across more than one TCP segment.
|
||||||
|
*
|
||||||
|
* Because each protosocket runs as a protothread, the protosocket has to be
|
||||||
|
* started with a call to PSOCK_BEGIN() at the start of the function
|
||||||
|
* in which the protosocket is used. Similarly, the protosocket protothread can
|
||||||
|
* be terminated by a call to PSOCK_EXIT().
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __PSOCK_H__
|
||||||
|
#define __PSOCK_H__
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <net/uip/uipopt.h>
|
||||||
|
|
||||||
|
/* The structure that holds the state of a buffer.
|
||||||
|
*
|
||||||
|
* This structure holds the state of a uIP buffer. The structure has
|
||||||
|
* no user-visible elements, but is used through the functions
|
||||||
|
* provided by the library.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
struct psock_buf
|
||||||
|
{
|
||||||
|
uint8 *ptr;
|
||||||
|
unsigned short left;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* The representation of a protosocket.
|
||||||
|
*
|
||||||
|
* The protosocket structrure is an opaque structure with no user-visible
|
||||||
|
* elements.
|
||||||
|
*/
|
||||||
|
|
||||||
|
struct psock
|
||||||
|
{
|
||||||
|
const uint8 *sendptr; /* Pointer to the next data to be sent. */
|
||||||
|
uint8 *readptr; /* Pointer to the next data to be read. */
|
||||||
|
uint8 *bufptr; /* Pointer to the buffer used for buffering incoming data. */
|
||||||
|
uint16 sendlen; /* The number of bytes left to be sent. */
|
||||||
|
uint16 readlen; /* The number of bytes left to be read. */
|
||||||
|
struct psock_buf buf; /* The structure holding the state of the input buffer. */
|
||||||
|
unsigned int bufsize; /* The size of the input buffer. */
|
||||||
|
unsigned char state; /* The state of the protosocket. */
|
||||||
|
};
|
||||||
|
|
||||||
|
/* Initialize a protosocket.
|
||||||
|
*
|
||||||
|
* Initializes a protosocket and must be called before the
|
||||||
|
* protosocket is used. The initialization also specifies the input buffer
|
||||||
|
* for the protosocket.
|
||||||
|
*
|
||||||
|
* psock (struct psock *) A pointer to the protosocket to be
|
||||||
|
* initialized
|
||||||
|
*
|
||||||
|
* buffer (char *) A pointer to the input buffer for the
|
||||||
|
* protosocket.
|
||||||
|
*
|
||||||
|
* buffersize (unsigned int) The size of the input buffer.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern void psock_init(struct psock *psock, char *buffer, unsigned int buffersize);
|
||||||
|
|
||||||
|
/* Send data.
|
||||||
|
*
|
||||||
|
* This macro sends data over a protosocket. The protosocket protothread blocks
|
||||||
|
* until all data has been sent and is known to have been received by
|
||||||
|
* the remote end of the TCP connection.
|
||||||
|
*
|
||||||
|
* psock (struct psock *) A pointer to the protosocket over which
|
||||||
|
* data is to be sent.
|
||||||
|
*
|
||||||
|
* data (char *) A pointer to the data that is to be sent.
|
||||||
|
*
|
||||||
|
* datalen (unsigned int) The length of the data that is to be
|
||||||
|
* sent.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern void psock_send(struct psock *psock, const char *buf, unsigned int len);
|
||||||
|
|
||||||
|
/*Send a null-terminated string.
|
||||||
|
*
|
||||||
|
* psock Pointer to the protosocket.
|
||||||
|
* str The string to be sent.
|
||||||
|
*
|
||||||
|
* This function sends a null-terminated string over the
|
||||||
|
* protosocket.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define PSOCK_SEND_STR(psock, str) psock_send(psock, str, strlen(str))
|
||||||
|
|
||||||
|
/* Generate data with a function and send it
|
||||||
|
*
|
||||||
|
* psock Pointer to the protosocket.
|
||||||
|
* generator Pointer to the generator function
|
||||||
|
* arg Argument to the generator function
|
||||||
|
*
|
||||||
|
* This function generates data and sends it over the
|
||||||
|
* protosocket. This can be used to dynamically generate
|
||||||
|
* data for a transmission, instead of generating the data
|
||||||
|
* in a buffer beforehand. This function reduces the need for
|
||||||
|
* buffer memory. The generator function is implemented by
|
||||||
|
* the application, and a pointer to the function is given
|
||||||
|
* as an argument with the call to PSOCK_GENERATOR_SEND().
|
||||||
|
*
|
||||||
|
* The generator function should place the generated data
|
||||||
|
* directly in the uip_appdata buffer, and return the
|
||||||
|
* length of the generated data. The generator function is
|
||||||
|
* called by the protosocket layer when the data first is
|
||||||
|
* sent, and once for every retransmission that is needed.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern void psock_generator_send(struct psock *psock, unsigned short (*f)(void *), void *arg);
|
||||||
|
|
||||||
|
/* Close a protosocket.
|
||||||
|
*
|
||||||
|
* This macro closes a protosocket and can only be called from within the
|
||||||
|
* protothread in which the protosocket lives.
|
||||||
|
*
|
||||||
|
* psock (struct psock *) A pointer to the protosocket that is to
|
||||||
|
* be closed.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define PSOCK_CLOSE(psock) uip_close()
|
||||||
|
|
||||||
|
/* Read data until the buffer is full.
|
||||||
|
*
|
||||||
|
* This macro will block waiting for data and read the data into the
|
||||||
|
* input buffer specified with the call to PSOCK_INIT(). Data is read
|
||||||
|
* until the buffer is full..
|
||||||
|
*
|
||||||
|
* psock (struct psock *) A pointer to the protosocket from which
|
||||||
|
* data should be read.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern void psock_readbuf(struct psock *psock);
|
||||||
|
|
||||||
|
/* Read data up to a specified character.
|
||||||
|
*
|
||||||
|
* This macro will block waiting for data and read the data into the
|
||||||
|
* input buffer specified with the call to PSOCK_INIT(). Data is only
|
||||||
|
* read until the specifieed character appears in the data stream.
|
||||||
|
*
|
||||||
|
* psock (struct psock *) A pointer to the protosocket from which
|
||||||
|
* data should be read.
|
||||||
|
*
|
||||||
|
* c (char) The character at which to stop reading.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern void psock_readto(struct psock *psock, unsigned char c);
|
||||||
|
|
||||||
|
/* The length of the data that was previously read.
|
||||||
|
*
|
||||||
|
* Returns the length of the data that was previously read
|
||||||
|
* using PSOCK_READTO() or PSOCK_READ().
|
||||||
|
*
|
||||||
|
* psock (struct psock *) A pointer to the protosocket holding the data.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern uint16 psock_datalen(struct psock *psock);
|
||||||
|
|
||||||
|
/* Check if there is new data has arrived on a protosocket without blocking
|
||||||
|
*
|
||||||
|
* psock (struct psock *) A pointer to the protosocket.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern boolean psock_checknewdata(struct psock *s);
|
||||||
|
|
||||||
|
/* Block until new data has arrived on a protosocket.
|
||||||
|
*
|
||||||
|
* psock (struct psock *) A pointer to the protosocket.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern void psock_waitnewdata(struct psock *s);
|
||||||
|
|
||||||
|
#endif /* __PSOCK_H__ */
|
||||||
|
|
||||||
|
/** @} */
|
||||||
@@ -0,0 +1,60 @@
|
|||||||
|
/* resolv.h
|
||||||
|
* DNS resolver code header file.
|
||||||
|
* Authtor Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* Copyright (c) 2002-2003, Adam Dunkels.
|
||||||
|
* 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. 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __UIP_RESOLV_H__
|
||||||
|
#define __UIP_RESOLV_H__
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <net/uip/uipopt.h>
|
||||||
|
|
||||||
|
/* Callback function which is called when a hostname is found.
|
||||||
|
*
|
||||||
|
* This function must be implemented by the module that uses the DNS
|
||||||
|
* resolver. It is called when a hostname is found, or when a hostname
|
||||||
|
* was not found.
|
||||||
|
*
|
||||||
|
* name A pointer to the name that was looked up. \param
|
||||||
|
* ipaddr A pointer to a 4-byte array containing the IP address of the
|
||||||
|
* hostname, or NULL if the hostname could not be found.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern void resolv_found(char *name, uint16 *ipaddr);
|
||||||
|
|
||||||
|
/* Functions. */
|
||||||
|
|
||||||
|
extern void resolv_conf(uint16 *dnsserver);
|
||||||
|
extern uint16 *resolv_getserver(void);
|
||||||
|
extern void resolv_init(void);
|
||||||
|
extern uint16 *resolv_lookup(char *name);
|
||||||
|
extern void resolv_query(char *name);
|
||||||
|
|
||||||
|
#endif /* __UIP_RESOLV_H__ */
|
||||||
@@ -0,0 +1,75 @@
|
|||||||
|
/* smtp.h
|
||||||
|
* SMTP header file
|
||||||
|
* Author: Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* Copyright (c) 2002, Adam Dunkels.
|
||||||
|
* 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. 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __SMTP_H__
|
||||||
|
#define __SMTP_H__
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
#include <net/uip/uipopt.h>
|
||||||
|
|
||||||
|
/* Error number that signifies a non-error condition. */
|
||||||
|
|
||||||
|
#define SMTP_ERR_OK 0
|
||||||
|
|
||||||
|
/* Callback function that is called when an e-mail transmission is
|
||||||
|
* done.
|
||||||
|
*
|
||||||
|
* This function must be implemented by the module that uses the SMTP
|
||||||
|
* module.
|
||||||
|
*
|
||||||
|
* error The number of the error if an error occured, or
|
||||||
|
* SMTP_ERR_OK.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void smtp_done(unsigned char error);
|
||||||
|
|
||||||
|
void smtp_init(void);
|
||||||
|
void smtp_configure(char *localhostname, uint16 *smtpserver);
|
||||||
|
unsigned char smtp_send(char *to, char *from,
|
||||||
|
char *subject, char *msg,
|
||||||
|
uint16 msglen);
|
||||||
|
|
||||||
|
struct smtp_state
|
||||||
|
{
|
||||||
|
uint8 state;
|
||||||
|
char *to;
|
||||||
|
char *from;
|
||||||
|
char *subject;
|
||||||
|
char *msg;
|
||||||
|
uint16 msglen;
|
||||||
|
|
||||||
|
uint16 sentlen, textlen;
|
||||||
|
uint16 sendptr;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif /* __SMTP_H__ */
|
||||||
@@ -0,0 +1,343 @@
|
|||||||
|
/****************************************************************************
|
||||||
|
* uip-arch.h
|
||||||
|
* Defines architecture-specific device driver interfaces to uIP
|
||||||
|
*
|
||||||
|
* Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
* Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
*
|
||||||
|
* Derived largely from portions of uIP with has a similar BSD-styple license:
|
||||||
|
*
|
||||||
|
* Copyright (c) 2001-2003, Adam Dunkels.
|
||||||
|
* 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. 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 __UIP_ARCH_H
|
||||||
|
#define __UIP_ARCH_H
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Included Files
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
#include <net/uip/uipopt.h>
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Definitions
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/* The following flags are passed as an argument to the uip_interrupt()
|
||||||
|
* function. They are used to distinguish between the two cases where
|
||||||
|
* uip_interrupt() is called. It can be called either because we have
|
||||||
|
* incoming data that should be processed, or because the periodic
|
||||||
|
* timer has fired. These values are never used directly, but only in
|
||||||
|
* the macrose defined in this file.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define UIP_DATA 1 /* Tells uIP that there is incoming data in the uip_buf buffer. The
|
||||||
|
* length of the data is stored in the global variable uip_len. */
|
||||||
|
#define UIP_TIMER 2 /* Tells uIP that the periodic timer has fired. */
|
||||||
|
#define UIP_POLL_REQUEST 3 /* Tells uIP that a connection should be polled. */
|
||||||
|
#define UIP_UDP_SEND_CONN 4 /* Tells uIP that a UDP datagram should be constructed in the
|
||||||
|
* uip_buf buffer. */
|
||||||
|
#if UIP_UDP
|
||||||
|
# define UIP_UDP_TIMER 5
|
||||||
|
#endif /* UIP_UDP */
|
||||||
|
|
||||||
|
/* uIP device driver functions
|
||||||
|
*
|
||||||
|
* These functions are used by a network device driver for interacting
|
||||||
|
* with uIP.
|
||||||
|
*
|
||||||
|
* Process an incoming packet.
|
||||||
|
*
|
||||||
|
* This function should be called when the device driver has received
|
||||||
|
* a packet from the network. The packet from the device driver must
|
||||||
|
* be present in the uip_buf buffer, and the length of the packet
|
||||||
|
* should be placed in the uip_len variable.
|
||||||
|
*
|
||||||
|
* When the function returns, there may be an outbound packet placed
|
||||||
|
* in the uip_buf packet buffer. If so, the uip_len variable is set to
|
||||||
|
* the length of the packet. If no packet is to be sent out, the
|
||||||
|
* uip_len variable is set to 0.
|
||||||
|
*
|
||||||
|
* The usual way of calling the function is presented by the source
|
||||||
|
* code below.
|
||||||
|
*
|
||||||
|
* uip_len = devicedriver_poll();
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* uip_input();
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* devicedriver_send();
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*
|
||||||
|
* Note: If you are writing a uIP device driver that needs ARP
|
||||||
|
* (Address Resolution Protocol), e.g., when running uIP over
|
||||||
|
* Ethernet, you will need to call the uIP ARP code before calling
|
||||||
|
* this function:
|
||||||
|
*
|
||||||
|
* #define BUF ((struct uip_eth_hdr *)&uip_buf[0])
|
||||||
|
* uip_len = ethernet_devicedrver_poll();
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* if(BUF->type == HTONS(UIP_ETHTYPE_IP)) {
|
||||||
|
* uip_arp_ipin();
|
||||||
|
* uip_input();
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* uip_arp_out();
|
||||||
|
* ethernet_devicedriver_send();
|
||||||
|
* }
|
||||||
|
* } else if(BUF->type == HTONS(UIP_ETHTYPE_ARP)) {
|
||||||
|
* uip_arp_arpin();
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* ethernet_devicedriver_send();
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define uip_input() uip_interrupt(UIP_DATA)
|
||||||
|
|
||||||
|
/* Periodic processing for a connection identified by its number.
|
||||||
|
*
|
||||||
|
* This function does the necessary periodic processing (timers,
|
||||||
|
* polling) for a uIP TCP conneciton, and should be called when the
|
||||||
|
* periodic uIP timer goes off. It should be called for every
|
||||||
|
* connection, regardless of whether they are open of closed.
|
||||||
|
*
|
||||||
|
* When the function returns, it may have an outbound packet waiting
|
||||||
|
* for service in the uIP packet buffer, and if so the uip_len
|
||||||
|
* variable is set to a value larger than zero. The device driver
|
||||||
|
* should be called to send out the packet.
|
||||||
|
*
|
||||||
|
* The ususal way of calling the function is through a for() loop like
|
||||||
|
* this:
|
||||||
|
*
|
||||||
|
* for(i = 0; i < UIP_CONNS; ++i) {
|
||||||
|
* uip_periodic(i);
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* devicedriver_send();
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*
|
||||||
|
* Note: If you are writing a uIP device driver that needs ARP
|
||||||
|
* (Address Resolution Protocol), e.g., when running uIP over
|
||||||
|
* Ethernet, you will need to call the uip_arp_out() function before
|
||||||
|
* calling the device driver:
|
||||||
|
*
|
||||||
|
* for(i = 0; i < UIP_CONNS; ++i) {
|
||||||
|
* uip_periodic(i);
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* uip_arp_out();
|
||||||
|
* ethernet_devicedriver_send();
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*
|
||||||
|
* conn The number of the connection which is to be periodically polled.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define uip_periodic(conn) do { uip_conn = &uip_conns[conn]; \
|
||||||
|
uip_interrupt(UIP_TIMER); } while (0)
|
||||||
|
|
||||||
|
#define uip_conn_active(conn) (uip_conns[conn].tcpstateflags != UIP_CLOSED)
|
||||||
|
|
||||||
|
/* Perform periodic processing for a connection identified by a pointer
|
||||||
|
* to its structure.
|
||||||
|
*
|
||||||
|
* Same as uip_periodic() but takes a pointer to the actual uip_conn
|
||||||
|
* struct instead of an integer as its argument. This function can be
|
||||||
|
* used to force periodic processing of a specific connection.
|
||||||
|
*
|
||||||
|
* conn A pointer to the uip_conn struct for the connection to
|
||||||
|
* be processed.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define uip_periodic_conn(conn) do { uip_conn = conn; uip_interrupt(UIP_TIMER); } while (0)
|
||||||
|
|
||||||
|
/* Request that a particular connection should be polled.
|
||||||
|
*
|
||||||
|
* Similar to uip_periodic_conn() but does not perform any timer
|
||||||
|
* processing. The application is polled for new data.
|
||||||
|
*
|
||||||
|
* conn A pointer to the uip_conn struct for the connection to
|
||||||
|
* be processed.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define uip_poll_conn(conn) do { uip_conn = conn; uip_interrupt(UIP_POLL_REQUEST); } while (0)
|
||||||
|
|
||||||
|
|
||||||
|
#if UIP_UDP
|
||||||
|
/* Periodic processing for a UDP connection identified by its number.
|
||||||
|
*
|
||||||
|
* This function is essentially the same as uip_periodic(), but for
|
||||||
|
* UDP connections. It is called in a similar fashion as the
|
||||||
|
* uip_periodic() function:
|
||||||
|
*
|
||||||
|
* for(i = 0; i < UIP_UDP_CONNS; i++) {
|
||||||
|
* uip_udp_periodic(i);
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* devicedriver_send();
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*
|
||||||
|
* Note: As for the uip_periodic() function, special care has to be
|
||||||
|
* taken when using uIP together with ARP and Ethernet:
|
||||||
|
*
|
||||||
|
* for(i = 0; i < UIP_UDP_CONNS; i++) {
|
||||||
|
* uip_udp_periodic(i);
|
||||||
|
* if(uip_len > 0) {
|
||||||
|
* uip_arp_out();
|
||||||
|
* ethernet_devicedriver_send();
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*
|
||||||
|
* conn The number of the UDP connection to be processed.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define uip_udp_periodic(conn) do { uip_udp_conn = &uip_udp_conns[conn]; \
|
||||||
|
uip_interrupt(UIP_UDP_TIMER); } while (0)
|
||||||
|
|
||||||
|
/* Periodic processing for a UDP connection identified by a pointer to
|
||||||
|
* its structure.
|
||||||
|
*
|
||||||
|
* Same as uip_udp_periodic() but takes a pointer to the actual
|
||||||
|
* uip_conn struct instead of an integer as its argument. This
|
||||||
|
* function can be used to force periodic processing of a specific
|
||||||
|
* connection.
|
||||||
|
*
|
||||||
|
* conn A pointer to the uip_udp_conn struct for the connection
|
||||||
|
* to be processed.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define uip_udp_periodic_conn(conn) do { uip_udp_conn = conn; \
|
||||||
|
uip_interrupt(UIP_UDP_TIMER); } while (0)
|
||||||
|
|
||||||
|
|
||||||
|
#endif /* UIP_UDP */
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Public Types
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Public Variables
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Pulblic Function Prototypes
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/* Architecure support
|
||||||
|
*
|
||||||
|
* uip_interrupt(flag):
|
||||||
|
*
|
||||||
|
* The actual uIP function which does all the work. Called from the
|
||||||
|
* interrupt level by a device driver.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern void uip_interrupt(uint8 flag);
|
||||||
|
|
||||||
|
/* By defining UIP_ARCH_CHKSUM, the architecture can replace the following
|
||||||
|
* functions with hardware assisted solutions.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Carry out a 32-bit addition.
|
||||||
|
*
|
||||||
|
* Because not all architectures for which uIP is intended has native
|
||||||
|
* 32-bit arithmetic, uIP uses an external C function for doing the
|
||||||
|
* required 32-bit additions in the TCP protocol processing. This
|
||||||
|
* function should add the two arguments and place the result in the
|
||||||
|
* global variable uip_acc32.
|
||||||
|
*
|
||||||
|
* Note: The 32-bit integer pointed to by the op32 parameter and the
|
||||||
|
* result in the uip_acc32 variable are in network byte order (big
|
||||||
|
* endian).
|
||||||
|
*
|
||||||
|
* op32 A pointer to a 4-byte array representing a 32-bit
|
||||||
|
* integer in network byte order (big endian).
|
||||||
|
*
|
||||||
|
* op16 A 16-bit integer in host byte order.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#if UIP_ARCH_ADD32
|
||||||
|
extern void uip_add32(uint8 *op32, uint16 op16);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* Calculate the Internet checksum over a buffer.
|
||||||
|
*
|
||||||
|
* The Internet checksum is the one's complement of the one's
|
||||||
|
* complement sum of all 16-bit words in the buffer.
|
||||||
|
*
|
||||||
|
* See RFC1071.
|
||||||
|
*
|
||||||
|
* Note: This function is not called in the current version of uIP,
|
||||||
|
* but future versions might make use of it.
|
||||||
|
*
|
||||||
|
* buf A pointer to the buffer over which the checksum is to be
|
||||||
|
* computed.
|
||||||
|
*
|
||||||
|
* len The length of the buffer over which the checksum is to
|
||||||
|
* be computed.
|
||||||
|
*
|
||||||
|
* Return: The Internet checksum of the buffer.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern uint16 uip_chksum(uint16 *buf, uint16 len);
|
||||||
|
|
||||||
|
/* Calculate the IP header checksum of the packet header in uip_buf.
|
||||||
|
*
|
||||||
|
* The IP header checksum is the Internet checksum of the 20 bytes of
|
||||||
|
* the IP header.
|
||||||
|
*
|
||||||
|
* Return: The IP header checksum of the IP header in the uip_buf
|
||||||
|
* buffer.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern uint16 uip_ipchksum(void);
|
||||||
|
|
||||||
|
/* Calculate the TCP checksum of the packet in uip_buf and uip_appdata.
|
||||||
|
*
|
||||||
|
* The TCP checksum is the Internet checksum of data contents of the
|
||||||
|
* TCP segment, and a pseudo-header as defined in RFC793.
|
||||||
|
*
|
||||||
|
* Note: The uip_appdata pointer that points to the packet data may
|
||||||
|
* point anywhere in memory, so it is not possible to simply calculate
|
||||||
|
* the Internet checksum of the contents of the uip_buf buffer.
|
||||||
|
*
|
||||||
|
* Return: The TCP checksum of the TCP segment in uip_buf and pointed
|
||||||
|
* to by uip_appdata.
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern uint16 uip_tcpchksum(void);
|
||||||
|
|
||||||
|
extern uint16 uip_udpchksum(void);
|
||||||
|
|
||||||
|
#endif /* __UIP_ARCH_H */
|
||||||
@@ -0,0 +1,122 @@
|
|||||||
|
/* uip-arp.h
|
||||||
|
* Macros and definitions for the ARP module.
|
||||||
|
* Author: Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* Copyright (c) 2001-2003, Adam Dunkels.
|
||||||
|
* 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. 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.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __UIP_ARP_H__
|
||||||
|
#define __UIP_ARP_H__
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
|
||||||
|
extern struct uip_eth_addr uip_ethaddr;
|
||||||
|
|
||||||
|
/* The Ethernet header */
|
||||||
|
|
||||||
|
struct uip_eth_hdr
|
||||||
|
{
|
||||||
|
struct uip_eth_addr dest;
|
||||||
|
struct uip_eth_addr src;
|
||||||
|
uint16 type;
|
||||||
|
};
|
||||||
|
|
||||||
|
#define UIP_ETHTYPE_ARP 0x0806
|
||||||
|
#define UIP_ETHTYPE_IP 0x0800
|
||||||
|
#define UIP_ETHTYPE_IP6 0x86dd
|
||||||
|
|
||||||
|
/* The uip_arp_init() function must be called before any of the other
|
||||||
|
* ARP functions.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_arp_init(void);
|
||||||
|
|
||||||
|
/* The uip_arp_ipin() function should be called whenever an IP packet
|
||||||
|
* arrives from the Ethernet. This function refreshes the ARP table or
|
||||||
|
* inserts a new mapping if none exists. The function assumes that an
|
||||||
|
* IP packet with an Ethernet header is present in the uip_buf buffer
|
||||||
|
* and that the length of the packet is in the uip_len variable.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*void uip_arp_ipin(void);*/
|
||||||
|
#define uip_arp_ipin()
|
||||||
|
|
||||||
|
/* The uip_arp_arpin() should be called when an ARP packet is received
|
||||||
|
* by the Ethernet driver. This function also assumes that the
|
||||||
|
* Ethernet frame is present in the uip_buf buffer. When the
|
||||||
|
* uip_arp_arpin() function returns, the contents of the uip_buf
|
||||||
|
* buffer should be sent out on the Ethernet if the uip_len variable
|
||||||
|
* is > 0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_arp_arpin(void);
|
||||||
|
|
||||||
|
/* The uip_arp_out() function should be called when an IP packet
|
||||||
|
* should be sent out on the Ethernet. This function creates an
|
||||||
|
* Ethernet header before the IP header in the uip_buf buffer. The
|
||||||
|
* Ethernet header will have the correct Ethernet MAC destination
|
||||||
|
* address filled in if an ARP table entry for the destination IP
|
||||||
|
* address (or the IP address of the default router) is present. If no
|
||||||
|
* such table entry is found, the IP packet is overwritten with an ARP
|
||||||
|
* request and we rely on TCP to retransmit the packet that was
|
||||||
|
* overwritten. In any case, the uip_len variable holds the length of
|
||||||
|
* the Ethernet frame that should be transmitted.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_arp_out(void);
|
||||||
|
|
||||||
|
/* The uip_arp_timer() function should be called every ten seconds. It
|
||||||
|
* is responsible for flushing old entries in the ARP table.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_arp_timer(void);
|
||||||
|
|
||||||
|
/* Specifiy the Ethernet MAC address.
|
||||||
|
*
|
||||||
|
* The ARP code needs to know the MAC address of the Ethernet card in
|
||||||
|
* order to be able to respond to ARP queries and to generate working
|
||||||
|
* Ethernet headers.
|
||||||
|
*
|
||||||
|
* Note: This macro only specifies the Ethernet MAC address to the ARP
|
||||||
|
* code. It cannot be used to change the MAC address of the Ethernet
|
||||||
|
* card.
|
||||||
|
*
|
||||||
|
* eaddr A pointer to a struct uip_eth_addr containing the
|
||||||
|
* Ethernet MAC address of the Ethernet card.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define uip_setethaddr(eaddr) do {uip_ethaddr.addr[0] = eaddr.addr[0]; \
|
||||||
|
uip_ethaddr.addr[1] = eaddr.addr[1];\
|
||||||
|
uip_ethaddr.addr[2] = eaddr.addr[2];\
|
||||||
|
uip_ethaddr.addr[3] = eaddr.addr[3];\
|
||||||
|
uip_ethaddr.addr[4] = eaddr.addr[4];\
|
||||||
|
uip_ethaddr.addr[5] = eaddr.addr[5];} while(0)
|
||||||
|
|
||||||
|
#endif /* __UIP_ARP_H__ */
|
||||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,423 @@
|
|||||||
|
/****************************************************************************
|
||||||
|
* uipopt.h
|
||||||
|
* Configuration options for uIP.
|
||||||
|
* author Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* This file is used for tweaking various configuration options for
|
||||||
|
* uIP. You should make a copy of this file into one of your project's
|
||||||
|
* directories instead of editing this example "uipopt.h" file that
|
||||||
|
* comes with the uIP distribution.
|
||||||
|
*
|
||||||
|
* uIP is configured using the per-project configuration file
|
||||||
|
* uipopt.h. This file contains all compile-time options for uIP and
|
||||||
|
* should be tweaked to match each specific project. The uIP
|
||||||
|
* distribution contains a documented example "uipopt.h" that can be
|
||||||
|
* copied and modified for each project.
|
||||||
|
*
|
||||||
|
* Note: Most of the configuration options in the uipopt.h should not
|
||||||
|
* be changed, but rather the per-project defconfig file.
|
||||||
|
*
|
||||||
|
* Copyright (c) 2001-2003, Adam Dunkels.
|
||||||
|
* 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. 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 uIP TCP/IP stack.
|
||||||
|
*
|
||||||
|
* $Id: uipopt.h,v 1.1.1.1 2007-08-26 23:12:17 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __UIPOPT_H__
|
||||||
|
#define __UIPOPT_H__
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <nuttx/config.h>
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \name Static configuration options
|
||||||
|
*
|
||||||
|
* These configuration options can be used for setting the IP address
|
||||||
|
* settings statically, but only if UIP_FIXEDADDR is set to 1. The
|
||||||
|
* configuration options for a specific node includes IP address,
|
||||||
|
* netmask and default router as well as the Ethernet address. The
|
||||||
|
* netmask, default router and Ethernet address are appliciable only
|
||||||
|
* if uIP should be run over Ethernet.
|
||||||
|
*
|
||||||
|
* All of these should be changed to suit your project.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Statistics datatype
|
||||||
|
*
|
||||||
|
* This typedef defines the dataype used for keeping statistics in
|
||||||
|
* uIP.
|
||||||
|
*/
|
||||||
|
typedef uint16 uip_stats_t;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determines if uIP should use a fixed IP address or not.
|
||||||
|
*
|
||||||
|
* If uIP should use a fixed IP address, the settings are set in the
|
||||||
|
* uipopt.h file. If not, the macros uip_sethostaddr(),
|
||||||
|
* uip_setdraddr() and uip_setnetmask() should be used instead.
|
||||||
|
*/
|
||||||
|
#define UIP_FIXEDADDR 0
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Ping IP address asignment.
|
||||||
|
*
|
||||||
|
* uIP uses a "ping" packets for setting its own IP address if this
|
||||||
|
* option is set. If so, uIP will start with an empty IP address and
|
||||||
|
* the destination IP address of the first incoming "ping" (ICMP echo)
|
||||||
|
* packet will be used for setting the hosts IP address.
|
||||||
|
*
|
||||||
|
* \note This works only if UIP_FIXEDADDR is 0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifdef CONFIG_UIP_PINGADDRCONF
|
||||||
|
#define UIP_PINGADDRCONF CONFIG_UIP_PINGADDRCONF
|
||||||
|
#else /* CONFIG_UIP_PINGADDRCONF */
|
||||||
|
#define UIP_PINGADDRCONF 0
|
||||||
|
#endif /* CONFIG_UIP_PINGADDRCONF */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Specifies if the uIP ARP module should be compiled with a fixed
|
||||||
|
* Ethernet MAC address or not.
|
||||||
|
*
|
||||||
|
* If this configuration option is 0, the macro uip_setethaddr() can
|
||||||
|
* be used to specify the Ethernet address at run-time.
|
||||||
|
*/
|
||||||
|
#define UIP_FIXEDETHADDR 0
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* \name IP configuration options
|
||||||
|
*/
|
||||||
|
/**
|
||||||
|
* The IP TTL (time to live) of IP packets sent by uIP.
|
||||||
|
*
|
||||||
|
* This should normally not be changed.
|
||||||
|
*/
|
||||||
|
#define UIP_TTL 64
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Turn on support for IP packet reassembly.
|
||||||
|
*
|
||||||
|
* uIP supports reassembly of fragmented IP packets. This features
|
||||||
|
* requires an additonal amount of RAM to hold the reassembly buffer
|
||||||
|
* and the reassembly code size is approximately 700 bytes. The
|
||||||
|
* reassembly buffer is of the same size as the uip_buf buffer
|
||||||
|
* (configured by UIP_BUFSIZE).
|
||||||
|
*
|
||||||
|
* \note IP packet reassembly is not heavily tested.
|
||||||
|
*/
|
||||||
|
#define UIP_REASSEMBLY 0
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The maximum time an IP fragment should wait in the reassembly
|
||||||
|
* buffer before it is dropped.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#define UIP_REASS_MAXAGE 40
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* \name UDP configuration options
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Toggles wether UDP support should be compiled in or not.
|
||||||
|
*/
|
||||||
|
#ifdef CONFIG_UIP_UDP
|
||||||
|
# define UIP_UDP CONFIG_UIP_UDP
|
||||||
|
#else /* CONFIG_UIP_UDP */
|
||||||
|
# define UIP_UDP 0
|
||||||
|
#endif /* CONFIG_UIP_UDP */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Toggles if UDP checksums should be used or not.
|
||||||
|
*
|
||||||
|
* \note Support for UDP checksums is currently not included in uIP,
|
||||||
|
* so this option has no function.
|
||||||
|
*/
|
||||||
|
#ifdef CONFIG_UIP_UDP_CHECKSUMS
|
||||||
|
# define UIP_UDP_CHECKSUMS CONFIG_UIP_UDP_CHECKSUMS
|
||||||
|
#else
|
||||||
|
# define UIP_UDP_CHECKSUMS 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The maximum amount of concurrent UDP connections.
|
||||||
|
*/
|
||||||
|
#ifdef CONFIG_UIP_UDP_CONNS
|
||||||
|
# define UIP_UDP_CONNS CONFIG_UIP_UDP_CONNS
|
||||||
|
#else /* CONFIG_UIP_UDP_CONNS */
|
||||||
|
# define UIP_UDP_CONNS 10
|
||||||
|
#endif /* CONFIG_UIP_UDP_CONNS */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The name of the function that should be called when UDP datagrams arrive.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* \name TCP configuration options
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determines if support for opening connections from uIP should be
|
||||||
|
* compiled in.
|
||||||
|
*
|
||||||
|
* If the applications that are running on top of uIP for this project
|
||||||
|
* do not need to open outgoing TCP connections, this configration
|
||||||
|
* option can be turned off to reduce the code size of uIP.
|
||||||
|
*/
|
||||||
|
#define UIP_ACTIVE_OPEN 1
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The maximum number of simultaneously open TCP connections.
|
||||||
|
*
|
||||||
|
* Since the TCP connections are statically allocated, turning this
|
||||||
|
* configuration knob down results in less RAM used. Each TCP
|
||||||
|
* connection requires approximatly 30 bytes of memory.
|
||||||
|
*/
|
||||||
|
#ifndef CONFIG_UIP_MAX_CONNECTIONS
|
||||||
|
# define UIP_CONNS 10
|
||||||
|
#else /* CONFIG_UIP_MAX_CONNECTIONS */
|
||||||
|
# define UIP_CONNS CONFIG_UIP_MAX_CONNECTIONS
|
||||||
|
#endif /* CONFIG_UIP_MAX_CONNECTIONS */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The maximum number of simultaneously listening TCP ports.
|
||||||
|
*
|
||||||
|
* Each listening TCP port requires 2 bytes of memory.
|
||||||
|
*/
|
||||||
|
#ifndef CONFIG_UIP_MAX_LISTENPORTS
|
||||||
|
# define UIP_LISTENPORTS 20
|
||||||
|
#else /* CONFIG_UIP_MAX_LISTENPORTS */
|
||||||
|
# define UIP_LISTENPORTS CONFIG_UIP_MAX_LISTENPORTS
|
||||||
|
#endif /* CONFIG_UIP_MAX_LISTENPORTS */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determines if support for TCP urgent data notification should be
|
||||||
|
* compiled in.
|
||||||
|
*
|
||||||
|
* Urgent data (out-of-band data) is a rarely used TCP feature that
|
||||||
|
* very seldom would be required.
|
||||||
|
*/
|
||||||
|
#define UIP_URGDATA 0
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The initial retransmission timeout counted in timer pulses.
|
||||||
|
*
|
||||||
|
* This should not be changed.
|
||||||
|
*/
|
||||||
|
#define UIP_RTO 3
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The maximum number of times a segment should be retransmitted
|
||||||
|
* before the connection should be aborted.
|
||||||
|
*
|
||||||
|
* This should not be changed.
|
||||||
|
*/
|
||||||
|
#define UIP_MAXRTX 8
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The maximum number of times a SYN segment should be retransmitted
|
||||||
|
* before a connection request should be deemed to have been
|
||||||
|
* unsuccessful.
|
||||||
|
*
|
||||||
|
* This should not need to be changed.
|
||||||
|
*/
|
||||||
|
#define UIP_MAXSYNRTX 5
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The TCP maximum segment size.
|
||||||
|
*
|
||||||
|
* This is should not be to set to more than
|
||||||
|
* UIP_BUFSIZE - UIP_LLH_LEN - UIP_TCPIP_HLEN.
|
||||||
|
*/
|
||||||
|
#define UIP_TCP_MSS (UIP_BUFSIZE - UIP_LLH_LEN - UIP_TCPIP_HLEN)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The size of the advertised receiver's window.
|
||||||
|
*
|
||||||
|
* Should be set low (i.e., to the size of the uip_buf buffer) is the
|
||||||
|
* application is slow to process incoming data, or high (32768 bytes)
|
||||||
|
* if the application processes data quickly.
|
||||||
|
*/
|
||||||
|
#ifndef CONFIG_UIP_RECEIVE_WINDOW
|
||||||
|
# define UIP_RECEIVE_WINDOW UIP_TCP_MSS
|
||||||
|
#else
|
||||||
|
# define UIP_RECEIVE_WINDOW CONFIG_UIP_RECEIVE_WINDOW
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/**
|
||||||
|
* How long a connection should stay in the TIME_WAIT state.
|
||||||
|
*
|
||||||
|
* This configiration option has no real implication, and it should be
|
||||||
|
* left untouched.
|
||||||
|
*/
|
||||||
|
#define UIP_TIME_WAIT_TIMEOUT 120
|
||||||
|
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* \name ARP configuration options
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The size of the ARP table.
|
||||||
|
*
|
||||||
|
* This option should be set to a larger value if this uIP node will
|
||||||
|
* have many connections from the local network.
|
||||||
|
*/
|
||||||
|
#ifdef CONFIG_UIP_ARPTAB_SIZE
|
||||||
|
# define UIP_ARPTAB_SIZE CONFIG_UIP_ARPTAB_SIZE
|
||||||
|
#else
|
||||||
|
# define UIP_ARPTAB_SIZE 8
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The maxium age of ARP table entries measured in 10ths of seconds.
|
||||||
|
*
|
||||||
|
* An UIP_ARP_MAXAGE of 120 corresponds to 20 minutes (BSD
|
||||||
|
* default).
|
||||||
|
*/
|
||||||
|
#define UIP_ARP_MAXAGE 120
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \name General configuration options
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The size of the uIP packet buffer.
|
||||||
|
*
|
||||||
|
* The uIP packet buffer should not be smaller than 60 bytes, and does
|
||||||
|
* not need to be larger than 1500 bytes. Lower size results in lower
|
||||||
|
* TCP throughput, larger size results in higher TCP throughput.
|
||||||
|
*/
|
||||||
|
#ifndef CONFIG_UIP_BUFFER_SIZE
|
||||||
|
# define UIP_BUFSIZE 400
|
||||||
|
#else /* CONFIG_UIP_BUFFER_SIZE */
|
||||||
|
# define UIP_BUFSIZE CONFIG_UIP_BUFFER_SIZE
|
||||||
|
#endif /* CONFIG_UIP_BUFFER_SIZE */
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determines if statistics support should be compiled in.
|
||||||
|
*
|
||||||
|
* The statistics is useful for debugging and to show the user.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef CONFIG_UIP_STATISTICS
|
||||||
|
# define UIP_STATISTICS 0
|
||||||
|
#else /* CONFIG_UIP_STATISTICS */
|
||||||
|
# define UIP_STATISTICS CONFIG_UIP_STATISTICS
|
||||||
|
#endif /* CONFIG_UIP_STATISTICS */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determines if logging of certain events should be compiled in.
|
||||||
|
*
|
||||||
|
* This is useful mostly for debugging. The function uip_log()
|
||||||
|
* must be implemented to suit the architecture of the project, if
|
||||||
|
* logging is turned on.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef CONFIG_UIP_LOGGING
|
||||||
|
# define UIP_LOGGING 0
|
||||||
|
#else /* CONFIG_UIP_LOGGING */
|
||||||
|
# define UIP_LOGGING CONFIG_UIP_LOGGING
|
||||||
|
#endif /* CONFIG_UIP_LOGGING */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Broadcast support.
|
||||||
|
*
|
||||||
|
* This flag configures IP broadcast support. This is useful only
|
||||||
|
* together with UDP.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef CONFIG_UIP_BROADCAST
|
||||||
|
# define UIP_BROADCAST 0
|
||||||
|
#else /* CONFIG_UIP_BROADCAST */
|
||||||
|
# define UIP_BROADCAST CONFIG_UIP_BROADCAST
|
||||||
|
#endif /* CONFIG_UIP_BROADCAST */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Print out a uIP log message.
|
||||||
|
*
|
||||||
|
* This function must be implemented by the module that uses uIP, and
|
||||||
|
* is called by uIP whenever a log message is generated.
|
||||||
|
*/
|
||||||
|
void uip_log(char *msg);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The link level header length.
|
||||||
|
*
|
||||||
|
* This is the offset into the uip_buf where the IP header can be
|
||||||
|
* found. For Ethernet, this should be set to 14. For SLIP, this
|
||||||
|
* should be set to 0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifdef CONFIG_UIP_LLH_LEN
|
||||||
|
# define UIP_LLH_LEN CONFIG_UIP_LLH_LEN
|
||||||
|
#else /* CONFIG_UIP_LLH_LEN */
|
||||||
|
# define UIP_LLH_LEN 14
|
||||||
|
#endif /* CONFIG_UIP_LLH_LEN */
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* \name CPU architecture configuration
|
||||||
|
*
|
||||||
|
* The CPU architecture configuration is where the endianess of the
|
||||||
|
* CPU on which uIP is to be run is specified. Most CPUs today are
|
||||||
|
* little endian, and the most notable exception are the Motorolas
|
||||||
|
* which are big endian. The CONFIG_ENDIAN_BIG macro should be changed
|
||||||
|
* if uIP is to be run on a big endian architecture.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The byte order of the CPU architecture on which uIP is to be run.
|
||||||
|
*
|
||||||
|
* This option can be either CONFIG_ENDIAN_BIG (Motorola byte order) or
|
||||||
|
* default little endian byte order (Intel byte order).
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define UIP_BIG_ENDIAN 1234
|
||||||
|
#define UIP_LITTLE_ENDIAN 3412
|
||||||
|
|
||||||
|
#ifdef CONFIG_ENDIAN_BIG
|
||||||
|
# define UIP_BYTE_ORDER UIP_BIG_ENDIAN
|
||||||
|
#else
|
||||||
|
# define UIP_BYTE_ORDER UIP_LITTLE_ENDIAN
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif /* __UIPOPT_H__ */
|
||||||
@@ -0,0 +1,86 @@
|
|||||||
|
############################################################
|
||||||
|
# Makefile
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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 Gregory Nutt 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)/Make.defs
|
||||||
|
|
||||||
|
MKDEP = $(TOPDIR)/tools/mkdeps.sh
|
||||||
|
|
||||||
|
ifeq ($(CONFIG_NET_UIP),y)
|
||||||
|
include uip/Make.defs
|
||||||
|
endif
|
||||||
|
|
||||||
|
ASRCS = $(UIP_ASRCS)
|
||||||
|
AOBJS = $(ASRCS:.S=$(OBJEXT))
|
||||||
|
|
||||||
|
CSRCS = $(UIP_CSRCS)
|
||||||
|
COBJS = $(CSRCS:.c=$(OBJEXT))
|
||||||
|
|
||||||
|
SRCS = $(ASRCS) $(CSRCS)
|
||||||
|
OBJS = $(AOBJS) $(COBJS)
|
||||||
|
|
||||||
|
BIN = libnet$(LIBEXT)
|
||||||
|
|
||||||
|
VPATH = uip
|
||||||
|
|
||||||
|
all: $(BIN)
|
||||||
|
|
||||||
|
$(AOBJS): %$(OBJEXT): %.S
|
||||||
|
$(CC) -c $(CFLAGS) -D__ASSEMBLY__ $< -o $@
|
||||||
|
|
||||||
|
$(COBJS): %$(OBJEXT): %.c
|
||||||
|
$(CC) -c $(CFLAGS) $< -o $@
|
||||||
|
|
||||||
|
$(BIN): $(OBJS)
|
||||||
|
( for obj in $(OBJS) ; do \
|
||||||
|
$(AR) $@ $${obj} || \
|
||||||
|
{ echo "$(AR) $@ $obj FAILED!" ; exit 1 ; } ; \
|
||||||
|
done ; )
|
||||||
|
|
||||||
|
.depend: Makefile $(SRCS)
|
||||||
|
ifeq ($(CONFIG_NET_UIP),y)
|
||||||
|
$(MKDEP) --dep-path uip $(CC) -- $(CFLAGS) -- $(SRCS) >Make.dep
|
||||||
|
endif
|
||||||
|
touch $@
|
||||||
|
|
||||||
|
depend: .depend
|
||||||
|
|
||||||
|
clean:
|
||||||
|
rm -f $(BIN) *.o *.rel *.asm *.lst *.sym *.adb *~
|
||||||
|
if [ ! -z "$(OBJEXT)" ]; then rm -f *$(OBJEXT); fi
|
||||||
|
|
||||||
|
distclean: clean
|
||||||
|
rm -f Make.dep .depend
|
||||||
|
|
||||||
|
-include Make.dep
|
||||||
Binary file not shown.
@@ -0,0 +1,38 @@
|
|||||||
|
############################################################################
|
||||||
|
# Make.defs
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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 Gregory Nutt 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.
|
||||||
|
#
|
||||||
|
############################################################################
|
||||||
|
|
||||||
|
UIP_ASRCS =
|
||||||
|
UIP_CSRCS = psock.c uip-arp.c uip.c uip-fw.c uip-neighbor.c uip-split.c uip-wait.c
|
||||||
|
|
||||||
+377
@@ -0,0 +1,377 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2004, Swedish Institute of Computer Science.
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
|
||||||
|
*
|
||||||
|
* This file is part of the uIP TCP/IP stack
|
||||||
|
*
|
||||||
|
* Author: Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
* $Id: psock.c,v 1.1.1.1 2007-08-26 23:04:11 patacongo Exp $
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <pthread.h>
|
||||||
|
#include <debug.h>
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
#include <net/uip/uipopt.h>
|
||||||
|
#include <net/uip/psock.h>
|
||||||
|
|
||||||
|
#define STATE_NONE 0
|
||||||
|
#define STATE_ACKED 1
|
||||||
|
#define STATE_READ 2
|
||||||
|
#define STATE_BLOCKED_NEWDATA 3
|
||||||
|
#define STATE_BLOCKED_CLOSE 4
|
||||||
|
#define STATE_BLOCKED_SEND 5
|
||||||
|
#define STATE_DATA_SENT 6
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Return value of the buffering functions that indicates that a
|
||||||
|
* buffer was not filled by incoming data.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#define BUF_NOT_FULL 0
|
||||||
|
#define BUF_NOT_FOUND 0
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Return value of the buffering functions that indicates that a
|
||||||
|
* buffer was completely filled by incoming data.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#define BUF_FULL 1
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Return value of the buffering functions that indicates that an
|
||||||
|
* end-marker byte was found.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#define BUF_FOUND 2
|
||||||
|
|
||||||
|
static void buf_setup(struct psock_buf *buf, uint8 *bufptr, uint16 bufsize)
|
||||||
|
{
|
||||||
|
buf->ptr = bufptr;
|
||||||
|
buf->left = bufsize;
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint8 buf_bufdata(struct psock_buf *buf, uint16 len, uint8 **dataptr, uint16 *datalen)
|
||||||
|
{
|
||||||
|
if (*datalen < buf->left)
|
||||||
|
{
|
||||||
|
memcpy(buf->ptr, *dataptr, *datalen);
|
||||||
|
buf->ptr += *datalen;
|
||||||
|
buf->left -= *datalen;
|
||||||
|
*dataptr += *datalen;
|
||||||
|
*datalen = 0;
|
||||||
|
return BUF_NOT_FULL;
|
||||||
|
}
|
||||||
|
else if (*datalen == buf->left)
|
||||||
|
{
|
||||||
|
memcpy(buf->ptr, *dataptr, *datalen);
|
||||||
|
buf->ptr += *datalen;
|
||||||
|
buf->left = 0;
|
||||||
|
*dataptr += *datalen;
|
||||||
|
*datalen = 0;
|
||||||
|
return BUF_FULL;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
memcpy(buf->ptr, *dataptr, buf->left);
|
||||||
|
buf->ptr += buf->left;
|
||||||
|
*datalen -= buf->left;
|
||||||
|
*dataptr += buf->left;
|
||||||
|
buf->left = 0;
|
||||||
|
return BUF_FULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint8 buf_bufto(struct psock_buf *buf, uint8 endmarker, uint8 **dataptr, uint16 *datalen)
|
||||||
|
{
|
||||||
|
uint8 c;
|
||||||
|
while(buf->left > 0 && *datalen > 0)
|
||||||
|
{
|
||||||
|
c = *buf->ptr = **dataptr;
|
||||||
|
++*dataptr;
|
||||||
|
++buf->ptr;
|
||||||
|
--*datalen;
|
||||||
|
--buf->left;
|
||||||
|
|
||||||
|
if (c == endmarker)
|
||||||
|
{
|
||||||
|
return BUF_FOUND;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (*datalen == 0)
|
||||||
|
{
|
||||||
|
return BUF_NOT_FOUND;
|
||||||
|
}
|
||||||
|
|
||||||
|
while(*datalen > 0)
|
||||||
|
{
|
||||||
|
c = **dataptr;
|
||||||
|
--*datalen;
|
||||||
|
++*dataptr;
|
||||||
|
|
||||||
|
if (c == endmarker)
|
||||||
|
{
|
||||||
|
return BUF_FOUND | BUF_FULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return BUF_FULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean send_data(register struct psock *s)
|
||||||
|
{
|
||||||
|
/* Inidicate that we are blocked waiting for the send to complete */
|
||||||
|
|
||||||
|
s->state = STATE_BLOCKED_SEND;
|
||||||
|
|
||||||
|
/* Loop until we successfully send the data */
|
||||||
|
|
||||||
|
for (;;)
|
||||||
|
{
|
||||||
|
/* If the data has not been sent OR if it needs to be retransmitted,
|
||||||
|
* then send it now.
|
||||||
|
*/
|
||||||
|
|
||||||
|
if (s->state != STATE_DATA_SENT || uip_rexmit())
|
||||||
|
{
|
||||||
|
if (s->sendlen > uip_mss())
|
||||||
|
{
|
||||||
|
uip_send(s->sendptr, uip_mss());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
uip_send(s->sendptr, s->sendlen);
|
||||||
|
}
|
||||||
|
|
||||||
|
s->state = STATE_DATA_SENT;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Check if all data has been sent and acknowledged */
|
||||||
|
|
||||||
|
if (s->state == STATE_DATA_SENT && uip_acked())
|
||||||
|
{
|
||||||
|
/* Yes.. the data has been sent AND acknowledge */
|
||||||
|
|
||||||
|
if (s->sendlen > uip_mss())
|
||||||
|
{
|
||||||
|
s->sendlen -= uip_mss();
|
||||||
|
s->sendptr += uip_mss();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
s->sendptr += s->sendlen;
|
||||||
|
s->sendlen = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
s->state = STATE_ACKED;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* No.. then wait on the retransmit or acked events */
|
||||||
|
|
||||||
|
(void)uip_event_wait(UIP_ACKDATA|UIP_REXMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
return FALSE; /* We never get here */
|
||||||
|
}
|
||||||
|
|
||||||
|
void psock_send(struct psock *s, const char *buf, unsigned int len)
|
||||||
|
{
|
||||||
|
/* If there is no data to send, we exit immediately. */
|
||||||
|
|
||||||
|
if (len > 0)
|
||||||
|
{
|
||||||
|
/* Save the length of and a pointer to the data that is to be sent. */
|
||||||
|
|
||||||
|
s->sendptr = (const uint8*)buf;
|
||||||
|
s->sendlen = len;
|
||||||
|
s->state = STATE_NONE;
|
||||||
|
|
||||||
|
/* Loop here until all data is sent. The s->sendlen variable is updated
|
||||||
|
* by the data_sent() function.
|
||||||
|
*/
|
||||||
|
|
||||||
|
while(s->sendlen > 0) {
|
||||||
|
|
||||||
|
/* Wait until the data has been sent and acknowledged */
|
||||||
|
|
||||||
|
send_data(s);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Done */
|
||||||
|
|
||||||
|
s->state = STATE_NONE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void psock_generator_send(register struct psock *s, unsigned short (*generate)(void *), void *arg)
|
||||||
|
{
|
||||||
|
/* Ensure that there is a generator function to call. */
|
||||||
|
|
||||||
|
if (generate != NULL)
|
||||||
|
{
|
||||||
|
/* Call the generator function to generate the data in the uip_appdata
|
||||||
|
* buffer.
|
||||||
|
*/
|
||||||
|
|
||||||
|
s->sendlen = generate(arg);
|
||||||
|
s->sendptr = uip_appdata;
|
||||||
|
s->state = STATE_NONE;
|
||||||
|
|
||||||
|
do
|
||||||
|
{
|
||||||
|
/* Call the generator function again if we are called to perform a
|
||||||
|
* retransmission.
|
||||||
|
*/
|
||||||
|
|
||||||
|
if (uip_rexmit())
|
||||||
|
{
|
||||||
|
generate(arg);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Wait until all data is sent and acknowledged. */
|
||||||
|
|
||||||
|
send_data(s);
|
||||||
|
}
|
||||||
|
while(s->sendlen > 0);
|
||||||
|
|
||||||
|
/* Done */
|
||||||
|
|
||||||
|
s->state = STATE_NONE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
uint16 psock_datalen(struct psock *psock)
|
||||||
|
{
|
||||||
|
return psock->bufsize - psock->buf.left;
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean psock_checknewdata(struct psock *s)
|
||||||
|
{
|
||||||
|
if (s->readlen > 0)
|
||||||
|
{
|
||||||
|
/* There is data in the uip_appdata buffer that has not yet been read
|
||||||
|
* with the PSOCK_READ functions.
|
||||||
|
*/
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
else if (s->state == STATE_READ)
|
||||||
|
{
|
||||||
|
/* All data in uip_appdata buffer already consumed. */
|
||||||
|
|
||||||
|
s->state = STATE_BLOCKED_NEWDATA;
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
else if (uip_newdata())
|
||||||
|
{
|
||||||
|
/* There is new data that has not been consumed. */
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
/* There is no new data. */
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void psock_waitnewdata(struct psock *s)
|
||||||
|
{
|
||||||
|
while (!psock_checknewdata(s))
|
||||||
|
{
|
||||||
|
uip_event_wait(UIP_NEWDATA);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void psock_readto(register struct psock *psock, unsigned char c)
|
||||||
|
{
|
||||||
|
restart:
|
||||||
|
buf_setup(&psock->buf, psock->bufptr, psock->bufsize);
|
||||||
|
|
||||||
|
/* XXX: Should add buf_checkmarker() before do{} loop, if
|
||||||
|
incoming data has been handled while waiting for a write. */
|
||||||
|
|
||||||
|
do
|
||||||
|
{
|
||||||
|
if (psock->readlen == 0)
|
||||||
|
{
|
||||||
|
psock_waitnewdata(psock);
|
||||||
|
psock->state = STATE_READ;
|
||||||
|
psock->readptr = (uint8 *)uip_appdata;
|
||||||
|
psock->readlen = uip_datalen();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
while((buf_bufto(&psock->buf, c, &psock->readptr, &psock->readlen) & BUF_FOUND) == 0);
|
||||||
|
|
||||||
|
if (psock_datalen(psock) == 0)
|
||||||
|
{
|
||||||
|
psock->state = STATE_NONE;
|
||||||
|
goto restart;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void psock_readbuf(register struct psock *psock)
|
||||||
|
{
|
||||||
|
restart:
|
||||||
|
buf_setup(&psock->buf, psock->bufptr, psock->bufsize);
|
||||||
|
|
||||||
|
/* XXX: Should add buf_checkmarker() before do{} loop, if
|
||||||
|
incoming data has been handled while waiting for a write. */
|
||||||
|
|
||||||
|
do
|
||||||
|
{
|
||||||
|
if (psock->readlen == 0)
|
||||||
|
{
|
||||||
|
psock_waitnewdata(psock);
|
||||||
|
dbg("Waited for newdata\n");
|
||||||
|
psock->state = STATE_READ;
|
||||||
|
psock->readptr = (uint8 *)uip_appdata;
|
||||||
|
psock->readlen = uip_datalen();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
while(buf_bufdata(&psock->buf, psock->bufsize, &psock->readptr, &psock->readlen) != BUF_FULL);
|
||||||
|
|
||||||
|
if (psock_datalen(psock) == 0)
|
||||||
|
{
|
||||||
|
psock->state = STATE_NONE;
|
||||||
|
goto restart;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void psock_init(register struct psock *psock, char *buffer, unsigned int buffersize)
|
||||||
|
{
|
||||||
|
psock->state = STATE_NONE;
|
||||||
|
psock->readlen = 0;
|
||||||
|
psock->bufptr = (uint8*)buffer;
|
||||||
|
psock->bufsize = buffersize;
|
||||||
|
buf_setup(&psock->buf, (uint8*)buffer, buffersize);
|
||||||
|
}
|
||||||
@@ -0,0 +1,405 @@
|
|||||||
|
/* uip-arp.c
|
||||||
|
* Implementation of the ARP Address Resolution Protocol.
|
||||||
|
* Author: Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* The Address Resolution Protocol ARP is used for mapping between IP
|
||||||
|
* addresses and link level addresses such as the Ethernet MAC
|
||||||
|
* addresses. ARP uses broadcast queries to ask for the link level
|
||||||
|
* address of a known IP address and the host which is configured with
|
||||||
|
* the IP address for which the query was meant, will respond with its
|
||||||
|
* link level address.
|
||||||
|
*
|
||||||
|
* Note: This ARP implementation only supports Ethernet.
|
||||||
|
*
|
||||||
|
* Copyright (c) 2001-2003, Adam Dunkels.
|
||||||
|
* 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. 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <net/uip/uip-arp.h>
|
||||||
|
|
||||||
|
struct arp_hdr
|
||||||
|
{
|
||||||
|
struct uip_eth_hdr ethhdr;
|
||||||
|
uint16 hwtype;
|
||||||
|
uint16 protocol;
|
||||||
|
uint8 hwlen;
|
||||||
|
uint8 protolen;
|
||||||
|
uint16 opcode;
|
||||||
|
struct uip_eth_addr shwaddr;
|
||||||
|
uint16 sipaddr[2];
|
||||||
|
struct uip_eth_addr dhwaddr;
|
||||||
|
uint16 dipaddr[2];
|
||||||
|
};
|
||||||
|
|
||||||
|
struct ethip_hdr {
|
||||||
|
struct uip_eth_hdr ethhdr;
|
||||||
|
/* IP header. */
|
||||||
|
uint8 vhl,
|
||||||
|
tos,
|
||||||
|
len[2],
|
||||||
|
ipid[2],
|
||||||
|
ipoffset[2],
|
||||||
|
ttl,
|
||||||
|
proto;
|
||||||
|
uint16 ipchksum;
|
||||||
|
uint16 srcipaddr[2],
|
||||||
|
destipaddr[2];
|
||||||
|
};
|
||||||
|
|
||||||
|
#define ARP_REQUEST 1
|
||||||
|
#define ARP_REPLY 2
|
||||||
|
|
||||||
|
#define ARP_HWTYPE_ETH 1
|
||||||
|
|
||||||
|
struct arp_entry {
|
||||||
|
uint16 ipaddr[2];
|
||||||
|
struct uip_eth_addr ethaddr;
|
||||||
|
uint8 time;
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct uip_eth_addr broadcast_ethaddr =
|
||||||
|
{{0xff,0xff,0xff,0xff,0xff,0xff}};
|
||||||
|
static const uint16 broadcast_ipaddr[2] = {0xffff,0xffff};
|
||||||
|
|
||||||
|
static struct arp_entry arp_table[UIP_ARPTAB_SIZE];
|
||||||
|
static uint16 ipaddr[2];
|
||||||
|
static uint8 i, c;
|
||||||
|
|
||||||
|
static uint8 arptime;
|
||||||
|
static uint8 tmpage;
|
||||||
|
|
||||||
|
#define BUF ((struct arp_hdr *)&uip_buf[0])
|
||||||
|
#define IPBUF ((struct ethip_hdr *)&uip_buf[0])
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Initialize the ARP module.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_arp_init(void)
|
||||||
|
{
|
||||||
|
for(i = 0; i < UIP_ARPTAB_SIZE; ++i) {
|
||||||
|
memset(arp_table[i].ipaddr, 0, 4);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Periodic ARP processing function.
|
||||||
|
*
|
||||||
|
* This function performs periodic timer processing in the ARP module
|
||||||
|
* and should be called at regular intervals. The recommended interval
|
||||||
|
* is 10 seconds between the calls.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_arp_timer(void)
|
||||||
|
{
|
||||||
|
struct arp_entry *tabptr;
|
||||||
|
|
||||||
|
++arptime;
|
||||||
|
for(i = 0; i < UIP_ARPTAB_SIZE; ++i) {
|
||||||
|
tabptr = &arp_table[i];
|
||||||
|
if((tabptr->ipaddr[0] | tabptr->ipaddr[1]) != 0 &&
|
||||||
|
arptime - tabptr->time >= UIP_ARP_MAXAGE) {
|
||||||
|
memset(tabptr->ipaddr, 0, 4);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
uip_arp_update(uint16 *pipaddr, struct uip_eth_addr *ethaddr)
|
||||||
|
{
|
||||||
|
register struct arp_entry *tabptr;
|
||||||
|
/* Walk through the ARP mapping table and try to find an entry to
|
||||||
|
update. If none is found, the IP -> MAC address mapping is
|
||||||
|
inserted in the ARP table. */
|
||||||
|
for(i = 0; i < UIP_ARPTAB_SIZE; ++i) {
|
||||||
|
|
||||||
|
tabptr = &arp_table[i];
|
||||||
|
/* Only check those entries that are actually in use. */
|
||||||
|
if(tabptr->ipaddr[0] != 0 &&
|
||||||
|
tabptr->ipaddr[1] != 0) {
|
||||||
|
|
||||||
|
/* Check if the source IP address of the incoming packet matches
|
||||||
|
the IP address in this ARP table entry. */
|
||||||
|
if(pipaddr[0] == tabptr->ipaddr[0] &&
|
||||||
|
pipaddr[1] == tabptr->ipaddr[1]) {
|
||||||
|
|
||||||
|
/* An old entry found, update this and return. */
|
||||||
|
memcpy(tabptr->ethaddr.addr, ethaddr->addr, 6);
|
||||||
|
tabptr->time = arptime;
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* If we get here, no existing ARP table entry was found, so we
|
||||||
|
create one. */
|
||||||
|
|
||||||
|
/* First, we try to find an unused entry in the ARP table. */
|
||||||
|
for(i = 0; i < UIP_ARPTAB_SIZE; ++i) {
|
||||||
|
tabptr = &arp_table[i];
|
||||||
|
if(tabptr->ipaddr[0] == 0 &&
|
||||||
|
tabptr->ipaddr[1] == 0) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* If no unused entry is found, we try to find the oldest entry and
|
||||||
|
throw it away. */
|
||||||
|
if(i == UIP_ARPTAB_SIZE) {
|
||||||
|
tmpage = 0;
|
||||||
|
c = 0;
|
||||||
|
for(i = 0; i < UIP_ARPTAB_SIZE; ++i) {
|
||||||
|
tabptr = &arp_table[i];
|
||||||
|
if(arptime - tabptr->time > tmpage) {
|
||||||
|
tmpage = arptime - tabptr->time;
|
||||||
|
c = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
i = c;
|
||||||
|
tabptr = &arp_table[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Now, i is the ARP table entry which we will fill with the new
|
||||||
|
information. */
|
||||||
|
memcpy(tabptr->ipaddr, pipaddr, 4);
|
||||||
|
memcpy(tabptr->ethaddr.addr, ethaddr->addr, 6);
|
||||||
|
tabptr->time = arptime;
|
||||||
|
}
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* ARP processing for incoming IP packets
|
||||||
|
*
|
||||||
|
* This function should be called by the device driver when an IP
|
||||||
|
* packet has been received. The function will check if the address is
|
||||||
|
* in the ARP cache, and if so the ARP cache entry will be
|
||||||
|
* refreshed. If no ARP cache entry was found, a new one is created.
|
||||||
|
*
|
||||||
|
* This function expects an IP packet with a prepended Ethernet header
|
||||||
|
* in the uip_buf[] buffer, and the length of the packet in the global
|
||||||
|
* variable uip_len.
|
||||||
|
*/
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
#if 0
|
||||||
|
void
|
||||||
|
uip_arp_ipin(void)
|
||||||
|
{
|
||||||
|
uip_len -= sizeof(struct uip_eth_hdr);
|
||||||
|
|
||||||
|
/* Only insert/update an entry if the source IP address of the
|
||||||
|
incoming IP packet comes from a host on the local network. */
|
||||||
|
if((IPBUF->srcipaddr[0] & uip_netmask[0]) !=
|
||||||
|
(uip_hostaddr[0] & uip_netmask[0])) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if((IPBUF->srcipaddr[1] & uip_netmask[1]) !=
|
||||||
|
(uip_hostaddr[1] & uip_netmask[1])) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
uip_arp_update(IPBUF->srcipaddr, &(IPBUF->ethhdr.src));
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
#endif /* 0 */
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* ARP processing for incoming ARP packets.
|
||||||
|
*
|
||||||
|
* This function should be called by the device driver when an ARP
|
||||||
|
* packet has been received. The function will act differently
|
||||||
|
* depending on the ARP packet type: if it is a reply for a request
|
||||||
|
* that we previously sent out, the ARP cache will be filled in with
|
||||||
|
* the values from the ARP reply. If the incoming ARP packet is an ARP
|
||||||
|
* request for our IP address, an ARP reply packet is created and put
|
||||||
|
* into the uip_buf[] buffer.
|
||||||
|
*
|
||||||
|
* When the function returns, the value of the global variable uip_len
|
||||||
|
* indicates whether the device driver should send out a packet or
|
||||||
|
* not. If uip_len is zero, no packet should be sent. If uip_len is
|
||||||
|
* non-zero, it contains the length of the outbound packet that is
|
||||||
|
* present in the uip_buf[] buffer.
|
||||||
|
*
|
||||||
|
* This function expects an ARP packet with a prepended Ethernet
|
||||||
|
* header in the uip_buf[] buffer, and the length of the packet in the
|
||||||
|
* global variable uip_len.
|
||||||
|
*/
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_arp_arpin(void)
|
||||||
|
{
|
||||||
|
|
||||||
|
if(uip_len < sizeof(struct arp_hdr)) {
|
||||||
|
uip_len = 0;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
uip_len = 0;
|
||||||
|
|
||||||
|
switch(BUF->opcode) {
|
||||||
|
case HTONS(ARP_REQUEST):
|
||||||
|
/* ARP request. If it asked for our address, we send out a
|
||||||
|
reply. */
|
||||||
|
if(uip_ipaddr_cmp(BUF->dipaddr, uip_hostaddr)) {
|
||||||
|
/* First, we register the one who made the request in our ARP
|
||||||
|
table, since it is likely that we will do more communication
|
||||||
|
with this host in the future. */
|
||||||
|
uip_arp_update(BUF->sipaddr, &BUF->shwaddr);
|
||||||
|
|
||||||
|
/* The reply opcode is 2. */
|
||||||
|
BUF->opcode = HTONS(2);
|
||||||
|
|
||||||
|
memcpy(BUF->dhwaddr.addr, BUF->shwaddr.addr, 6);
|
||||||
|
memcpy(BUF->shwaddr.addr, uip_ethaddr.addr, 6);
|
||||||
|
memcpy(BUF->ethhdr.src.addr, uip_ethaddr.addr, 6);
|
||||||
|
memcpy(BUF->ethhdr.dest.addr, BUF->dhwaddr.addr, 6);
|
||||||
|
|
||||||
|
BUF->dipaddr[0] = BUF->sipaddr[0];
|
||||||
|
BUF->dipaddr[1] = BUF->sipaddr[1];
|
||||||
|
BUF->sipaddr[0] = uip_hostaddr[0];
|
||||||
|
BUF->sipaddr[1] = uip_hostaddr[1];
|
||||||
|
|
||||||
|
BUF->ethhdr.type = HTONS(UIP_ETHTYPE_ARP);
|
||||||
|
uip_len = sizeof(struct arp_hdr);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case HTONS(ARP_REPLY):
|
||||||
|
/* ARP reply. We insert or update the ARP table if it was meant
|
||||||
|
for us. */
|
||||||
|
if(uip_ipaddr_cmp(BUF->dipaddr, uip_hostaddr)) {
|
||||||
|
uip_arp_update(BUF->sipaddr, &BUF->shwaddr);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Prepend Ethernet header to an outbound IP packet and see if we need
|
||||||
|
* to send out an ARP request.
|
||||||
|
*
|
||||||
|
* This function should be called before sending out an IP packet. The
|
||||||
|
* function checks the destination IP address of the IP packet to see
|
||||||
|
* what Ethernet MAC address that should be used as a destination MAC
|
||||||
|
* address on the Ethernet.
|
||||||
|
*
|
||||||
|
* If the destination IP address is in the local network (determined
|
||||||
|
* by logical ANDing of netmask and our IP address), the function
|
||||||
|
* checks the ARP cache to see if an entry for the destination IP
|
||||||
|
* address is found. If so, an Ethernet header is prepended and the
|
||||||
|
* function returns. If no ARP cache entry is found for the
|
||||||
|
* destination IP address, the packet in the uip_buf[] is replaced by
|
||||||
|
* an ARP request packet for the IP address. The IP packet is dropped
|
||||||
|
* and it is assumed that they higher level protocols (e.g., TCP)
|
||||||
|
* eventually will retransmit the dropped packet.
|
||||||
|
*
|
||||||
|
* If the destination IP address is not on the local network, the IP
|
||||||
|
* address of the default router is used instead.
|
||||||
|
*
|
||||||
|
* When the function returns, a packet is present in the uip_buf[]
|
||||||
|
* buffer, and the length of the packet is in the global variable
|
||||||
|
* uip_len.
|
||||||
|
*/
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_arp_out(void)
|
||||||
|
{
|
||||||
|
struct arp_entry *tabptr;
|
||||||
|
|
||||||
|
/* Find the destination IP address in the ARP table and construct
|
||||||
|
the Ethernet header. If the destination IP addres isn't on the
|
||||||
|
local network, we use the default router's IP address instead.
|
||||||
|
|
||||||
|
If not ARP table entry is found, we overwrite the original IP
|
||||||
|
packet with an ARP request for the IP address. */
|
||||||
|
|
||||||
|
/* First check if destination is a local broadcast. */
|
||||||
|
if(uip_ipaddr_cmp(IPBUF->destipaddr, broadcast_ipaddr)) {
|
||||||
|
memcpy(IPBUF->ethhdr.dest.addr, broadcast_ethaddr.addr, 6);
|
||||||
|
} else {
|
||||||
|
/* Check if the destination address is on the local network. */
|
||||||
|
if(!uip_ipaddr_maskcmp(IPBUF->destipaddr, uip_hostaddr, uip_netmask)) {
|
||||||
|
/* Destination address was not on the local network, so we need to
|
||||||
|
use the default router's IP address instead of the destination
|
||||||
|
address when determining the MAC address. */
|
||||||
|
uip_ipaddr_copy(ipaddr, uip_draddr);
|
||||||
|
} else {
|
||||||
|
/* Else, we use the destination IP address. */
|
||||||
|
uip_ipaddr_copy(ipaddr, IPBUF->destipaddr);
|
||||||
|
}
|
||||||
|
|
||||||
|
for(i = 0; i < UIP_ARPTAB_SIZE; ++i) {
|
||||||
|
tabptr = &arp_table[i];
|
||||||
|
if(uip_ipaddr_cmp(ipaddr, tabptr->ipaddr)) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if(i == UIP_ARPTAB_SIZE) {
|
||||||
|
/* The destination address was not in our ARP table, so we
|
||||||
|
overwrite the IP packet with an ARP request. */
|
||||||
|
|
||||||
|
memset(BUF->ethhdr.dest.addr, 0xff, 6);
|
||||||
|
memset(BUF->dhwaddr.addr, 0x00, 6);
|
||||||
|
memcpy(BUF->ethhdr.src.addr, uip_ethaddr.addr, 6);
|
||||||
|
memcpy(BUF->shwaddr.addr, uip_ethaddr.addr, 6);
|
||||||
|
|
||||||
|
uip_ipaddr_copy(BUF->dipaddr, ipaddr);
|
||||||
|
uip_ipaddr_copy(BUF->sipaddr, uip_hostaddr);
|
||||||
|
BUF->opcode = HTONS(ARP_REQUEST); /* ARP request. */
|
||||||
|
BUF->hwtype = HTONS(ARP_HWTYPE_ETH);
|
||||||
|
BUF->protocol = HTONS(UIP_ETHTYPE_IP);
|
||||||
|
BUF->hwlen = 6;
|
||||||
|
BUF->protolen = 4;
|
||||||
|
BUF->ethhdr.type = HTONS(UIP_ETHTYPE_ARP);
|
||||||
|
|
||||||
|
uip_appdata = &uip_buf[UIP_TCPIP_HLEN + UIP_LLH_LEN];
|
||||||
|
|
||||||
|
uip_len = sizeof(struct arp_hdr);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Build an ethernet header. */
|
||||||
|
memcpy(IPBUF->ethhdr.dest.addr, tabptr->ethaddr.addr, 6);
|
||||||
|
}
|
||||||
|
memcpy(IPBUF->ethhdr.src.addr, uip_ethaddr.addr, 6);
|
||||||
|
|
||||||
|
IPBUF->ethhdr.type = HTONS(UIP_ETHTYPE_IP);
|
||||||
|
|
||||||
|
uip_len += sizeof(struct uip_eth_hdr);
|
||||||
|
}
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
/** @} */
|
||||||
|
/** @} */
|
||||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,176 @@
|
|||||||
|
/**
|
||||||
|
* \addtogroup uipfw
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \file
|
||||||
|
* uIP packet forwarding header file.
|
||||||
|
* \author Adam Dunkels <adam@sics.se>
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2004, Swedish Institute of Computer Science.
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
|
||||||
|
*
|
||||||
|
* This file is part of the uIP TCP/IP stack
|
||||||
|
*
|
||||||
|
* Author: Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
* $Id: uip-fw.h,v 1.1.1.1 2007-08-26 23:04:07 patacongo Exp $
|
||||||
|
*/
|
||||||
|
#ifndef __UIP_FW_H__
|
||||||
|
#define __UIP_FW_H__
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Representation of a uIP network interface.
|
||||||
|
*/
|
||||||
|
struct uip_fw_netif {
|
||||||
|
struct uip_fw_netif *next; /**< Pointer to the next interface when
|
||||||
|
linked in a list. */
|
||||||
|
uint16 ipaddr[2]; /**< The IP address of this interface. */
|
||||||
|
uint16 netmask[2]; /**< The netmask of the interface. */
|
||||||
|
uint8 (* output)(void);
|
||||||
|
/**< A pointer to the function that
|
||||||
|
sends a packet. */
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Intantiating macro for a uIP network interface.
|
||||||
|
*
|
||||||
|
* Example:
|
||||||
|
\code
|
||||||
|
struct uip_fw_netif slipnetif =
|
||||||
|
{UIP_FW_NETIF(192,168,76,1, 255,255,255,0, slip_output)};
|
||||||
|
\endcode
|
||||||
|
* \param ip1,ip2,ip3,ip4 The IP address of the network interface.
|
||||||
|
*
|
||||||
|
* \param nm1,nm2,nm3,nm4 The netmask of the network interface.
|
||||||
|
*
|
||||||
|
* \param outputfunc A pointer to the output function of the network interface.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define UIP_FW_NETIF(ip1,ip2,ip3,ip4, nm1,nm2,nm3,nm4, outputfunc) \
|
||||||
|
NULL, \
|
||||||
|
{HTONS((ip1 << 8) | ip2), HTONS((ip3 << 8) | ip4)}, \
|
||||||
|
{HTONS((nm1 << 8) | nm2), HTONS((nm3 << 8) | nm4)}, \
|
||||||
|
outputfunc
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the IP address of a network interface.
|
||||||
|
*
|
||||||
|
* \param netif A pointer to the uip_fw_netif structure for the network interface.
|
||||||
|
*
|
||||||
|
* \param addr A pointer to an IP address.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define uip_fw_setipaddr(netif, addr) \
|
||||||
|
do { (netif)->ipaddr[0] = ((uint16 *)(addr))[0]; \
|
||||||
|
(netif)->ipaddr[1] = ((uint16 *)(addr))[1]; } while(0)
|
||||||
|
/**
|
||||||
|
* Set the netmask of a network interface.
|
||||||
|
*
|
||||||
|
* \param netif A pointer to the uip_fw_netif structure for the network interface.
|
||||||
|
*
|
||||||
|
* \param addr A pointer to an IP address representing the netmask.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define uip_fw_setnetmask(netif, addr) \
|
||||||
|
do { (netif)->netmask[0] = ((uint16 *)(addr))[0]; \
|
||||||
|
(netif)->netmask[1] = ((uint16 *)(addr))[1]; } while(0)
|
||||||
|
|
||||||
|
void uip_fw_init(void);
|
||||||
|
uint8 uip_fw_forward(void);
|
||||||
|
uint8 uip_fw_output(void);
|
||||||
|
void uip_fw_register(struct uip_fw_netif *netif);
|
||||||
|
void uip_fw_default(struct uip_fw_netif *netif);
|
||||||
|
void uip_fw_periodic(void);
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A non-error message that indicates that a packet should be
|
||||||
|
* processed locally.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define UIP_FW_LOCAL 0
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A non-error message that indicates that something went OK.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define UIP_FW_OK 0
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A non-error message that indicates that a packet was forwarded.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define UIP_FW_FORWARDED 1
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A non-error message that indicates that a zero-length packet
|
||||||
|
* transmission was attempted, and that no packet was sent.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define UIP_FW_ZEROLEN 2
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An error message that indicates that a packet that was too large
|
||||||
|
* for the outbound network interface was detected.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define UIP_FW_TOOLARGE 3
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An error message that indicates that no suitable interface could be
|
||||||
|
* found for an outbound packet.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define UIP_FW_NOROUTE 4
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An error message that indicates that a packet that should be
|
||||||
|
* forwarded or output was dropped.
|
||||||
|
*
|
||||||
|
* \hideinitializer
|
||||||
|
*/
|
||||||
|
#define UIP_FW_DROPPED 5
|
||||||
|
|
||||||
|
|
||||||
|
#endif /* __UIP_FW_H__ */
|
||||||
|
|
||||||
|
/** @} */
|
||||||
@@ -0,0 +1,158 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2006, Swedish Institute of Computer Science.
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
|
||||||
|
*
|
||||||
|
* This file is part of the uIP TCP/IP stack
|
||||||
|
*
|
||||||
|
* $Id: uip-neighbor.c,v 1.1.1.1 2007-08-26 23:04:08 patacongo Exp $
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \file
|
||||||
|
* Database of link-local neighbors, used by IPv6 code and
|
||||||
|
* to be used by a future ARP code rewrite.
|
||||||
|
* \author
|
||||||
|
* Adam Dunkels <adam@sics.se>
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "uip-neighbor.h"
|
||||||
|
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#define MAX_TIME 128
|
||||||
|
|
||||||
|
#ifdef UIP_NEIGHBOR_CONF_ENTRIES
|
||||||
|
#define ENTRIES UIP_NEIGHBOR_CONF_ENTRIES
|
||||||
|
#else /* UIP_NEIGHBOR_CONF_ENTRIES */
|
||||||
|
#define ENTRIES 8
|
||||||
|
#endif /* UIP_NEIGHBOR_CONF_ENTRIES */
|
||||||
|
|
||||||
|
struct neighbor_entry {
|
||||||
|
uip_ipaddr_t ipaddr;
|
||||||
|
struct uip_neighbor_addr addr;
|
||||||
|
uint8 time;
|
||||||
|
};
|
||||||
|
static struct neighbor_entry entries[ENTRIES];
|
||||||
|
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_neighbor_init(void)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for(i = 0; i < ENTRIES; ++i) {
|
||||||
|
entries[i].time = MAX_TIME;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_neighbor_periodic(void)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for(i = 0; i < ENTRIES; ++i) {
|
||||||
|
if(entries[i].time < MAX_TIME) {
|
||||||
|
entries[i].time++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_neighbor_add(uip_ipaddr_t ipaddr, struct uip_neighbor_addr *addr)
|
||||||
|
{
|
||||||
|
int i, oldest;
|
||||||
|
uint8 oldest_time;
|
||||||
|
|
||||||
|
printf("Adding neighbor with link address %02x:%02x:%02x:%02x:%02x:%02x\n",
|
||||||
|
addr->addr.addr[0], addr->addr.addr[1], addr->addr.addr[2], addr->addr.addr[3],
|
||||||
|
addr->addr.addr[4], addr->addr.addr[5]);
|
||||||
|
|
||||||
|
/* Find the first unused entry or the oldest used entry. */
|
||||||
|
oldest_time = 0;
|
||||||
|
oldest = 0;
|
||||||
|
for(i = 0; i < ENTRIES; ++i) {
|
||||||
|
if(entries[i].time == MAX_TIME) {
|
||||||
|
oldest = i;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if(uip_ipaddr_cmp(entries[i].ipaddr, addr)) {
|
||||||
|
oldest = i;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if(entries[i].time > oldest_time) {
|
||||||
|
oldest = i;
|
||||||
|
oldest_time = entries[i].time;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Use the oldest or first free entry (either pointed to by the
|
||||||
|
"oldest" variable). */
|
||||||
|
entries[oldest].time = 0;
|
||||||
|
uip_ipaddr_copy(entries[oldest].ipaddr, ipaddr);
|
||||||
|
memcpy(&entries[oldest].addr, addr, sizeof(struct uip_neighbor_addr));
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static struct neighbor_entry *
|
||||||
|
find_entry(uip_ipaddr_t ipaddr)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for(i = 0; i < ENTRIES; ++i) {
|
||||||
|
if(uip_ipaddr_cmp(entries[i].ipaddr, ipaddr)) {
|
||||||
|
return &entries[i];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_neighbor_update(uip_ipaddr_t ipaddr)
|
||||||
|
{
|
||||||
|
struct neighbor_entry *e;
|
||||||
|
|
||||||
|
e = find_entry(ipaddr);
|
||||||
|
if(e != NULL) {
|
||||||
|
e->time = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
struct uip_neighbor_addr *
|
||||||
|
uip_neighbor_lookup(uip_ipaddr_t ipaddr)
|
||||||
|
{
|
||||||
|
struct neighbor_entry *e;
|
||||||
|
|
||||||
|
e = find_entry(ipaddr);
|
||||||
|
if(e != NULL) {
|
||||||
|
/* printf("Lookup neighbor with link address %02x:%02x:%02x:%02x:%02x:%02x\n",
|
||||||
|
e->addr.addr.addr[0], e->addr.addr.addr[1], e->addr.addr.addr[2], e->addr.addr.addr[3],
|
||||||
|
e->addr.addr.addr[4], e->addr.addr.addr[5]);*/
|
||||||
|
|
||||||
|
return &e->addr;
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
@@ -0,0 +1,54 @@
|
|||||||
|
/* uip-neighbor.h
|
||||||
|
* Header file for database of link-local neighbors, used by IPv6 code and
|
||||||
|
* to be used by future ARP code.
|
||||||
|
* Author: Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
* Copyright (c) 2006, Swedish Institute of Computer Science.
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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 __UIP_NEIGHBOR_H__
|
||||||
|
#define __UIP_NEIGHBOR_H__
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
|
||||||
|
struct uip_neighbor_addr
|
||||||
|
{
|
||||||
|
#if UIP_NEIGHBOR_CONF_ADDRTYPE
|
||||||
|
UIP_NEIGHBOR_CONF_ADDRTYPE addr;
|
||||||
|
#else
|
||||||
|
struct uip_eth_addr addr;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
void uip_neighbor_init(void);
|
||||||
|
void uip_neighbor_add(uip_ipaddr_t ipaddr, struct uip_neighbor_addr *addr);
|
||||||
|
void uip_neighbor_update(uip_ipaddr_t ipaddr);
|
||||||
|
struct uip_neighbor_addr *uip_neighbor_lookup(uip_ipaddr_t ipaddr);
|
||||||
|
void uip_neighbor_periodic(void);
|
||||||
|
|
||||||
|
#endif /* __UIP-NEIGHBOR_H__ */
|
||||||
@@ -0,0 +1,132 @@
|
|||||||
|
/* uip-split.c
|
||||||
|
* Author: Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
* Copyright (c) 2004, Swedish Institute of Computer Science.
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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 <nuttx/config.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
#include <net/uip/uip-arch.h>
|
||||||
|
|
||||||
|
#include "uip-split.h"
|
||||||
|
#include "uip-fw.h"
|
||||||
|
|
||||||
|
#define BUF ((struct uip_tcpip_hdr *)&uip_buf[UIP_LLH_LEN])
|
||||||
|
|
||||||
|
/*-----------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
uip_split_output(void)
|
||||||
|
{
|
||||||
|
uint16 tcplen, len1, len2;
|
||||||
|
|
||||||
|
/* We only try to split maximum sized TCP segments. */
|
||||||
|
if(BUF->proto == UIP_PROTO_TCP &&
|
||||||
|
uip_len == UIP_BUFSIZE - UIP_LLH_LEN) {
|
||||||
|
|
||||||
|
tcplen = uip_len - UIP_TCPIP_HLEN;
|
||||||
|
/* Split the segment in two. If the original packet length was
|
||||||
|
odd, we make the second packet one byte larger. */
|
||||||
|
len1 = len2 = tcplen / 2;
|
||||||
|
if(len1 + len2 < tcplen) {
|
||||||
|
++len2;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Create the first packet. This is done by altering the length
|
||||||
|
field of the IP header and updating the checksums. */
|
||||||
|
uip_len = len1 + UIP_TCPIP_HLEN;
|
||||||
|
#ifdef CONFIG_NET_UIP_IPv6
|
||||||
|
/* For IPv6, the IP length field does not include the IPv6 IP header
|
||||||
|
length. */
|
||||||
|
BUF->len[0] = ((uip_len - UIP_IPH_LEN) >> 8);
|
||||||
|
BUF->len[1] = ((uip_len - UIP_IPH_LEN) & 0xff);
|
||||||
|
#else /* CONFIG_NET_UIP_IPv6 */
|
||||||
|
BUF->len[0] = uip_len >> 8;
|
||||||
|
BUF->len[1] = uip_len & 0xff;
|
||||||
|
#endif /* CONFIG_NET_UIP_IPv6 */
|
||||||
|
|
||||||
|
/* Recalculate the TCP checksum. */
|
||||||
|
BUF->tcpchksum = 0;
|
||||||
|
BUF->tcpchksum = ~(uip_tcpchksum());
|
||||||
|
|
||||||
|
#ifndef CONFIG_NET_UIP_IPv6
|
||||||
|
/* Recalculate the IP checksum. */
|
||||||
|
BUF->ipchksum = 0;
|
||||||
|
BUF->ipchksum = ~(uip_ipchksum());
|
||||||
|
#endif /* CONFIG_NET_UIP_IPv6 */
|
||||||
|
|
||||||
|
/* Transmit the first packet. */
|
||||||
|
/* uip_fw_output();*/
|
||||||
|
tcpip_output();
|
||||||
|
|
||||||
|
/* Now, create the second packet. To do this, it is not enough to
|
||||||
|
just alter the length field, but we must also update the TCP
|
||||||
|
sequence number and point the uip_appdata to a new place in
|
||||||
|
memory. This place is detemined by the length of the first
|
||||||
|
packet (len1). */
|
||||||
|
uip_len = len2 + UIP_TCPIP_HLEN;
|
||||||
|
#ifdef CONFIG_NET_UIP_IPv6
|
||||||
|
/* For IPv6, the IP length field does not include the IPv6 IP header
|
||||||
|
length. */
|
||||||
|
BUF->len[0] = ((uip_len - UIP_IPH_LEN) >> 8);
|
||||||
|
BUF->len[1] = ((uip_len - UIP_IPH_LEN) & 0xff);
|
||||||
|
#else /* CONFIG_NET_UIP_IPv6 */
|
||||||
|
BUF->len[0] = uip_len >> 8;
|
||||||
|
BUF->len[1] = uip_len & 0xff;
|
||||||
|
#endif /* CONFIG_NET_UIP_IPv6 */
|
||||||
|
|
||||||
|
/* uip_appdata += len1;*/
|
||||||
|
memcpy(uip_appdata, (uint8 *)uip_appdata + len1, len2);
|
||||||
|
|
||||||
|
uip_add32(BUF->seqno, len1);
|
||||||
|
BUF->seqno[0] = uip_acc32[0];
|
||||||
|
BUF->seqno[1] = uip_acc32[1];
|
||||||
|
BUF->seqno[2] = uip_acc32[2];
|
||||||
|
BUF->seqno[3] = uip_acc32[3];
|
||||||
|
|
||||||
|
/* Recalculate the TCP checksum. */
|
||||||
|
BUF->tcpchksum = 0;
|
||||||
|
BUF->tcpchksum = ~(uip_tcpchksum());
|
||||||
|
|
||||||
|
#ifndef CONFIG_NET_UIP_IPv6
|
||||||
|
/* Recalculate the IP checksum. */
|
||||||
|
BUF->ipchksum = 0;
|
||||||
|
BUF->ipchksum = ~(uip_ipchksum());
|
||||||
|
#endif /* CONFIG_NET_UIP_IPv6 */
|
||||||
|
|
||||||
|
/* Transmit the second packet. */
|
||||||
|
/* uip_fw_output();*/
|
||||||
|
tcpip_output();
|
||||||
|
} else {
|
||||||
|
/* uip_fw_output();*/
|
||||||
|
tcpip_output();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
/*-----------------------------------------------------------------------------*/
|
||||||
@@ -0,0 +1,96 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2004, Swedish Institute of Computer Science.
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
|
||||||
|
*
|
||||||
|
* This file is part of the uIP TCP/IP stack
|
||||||
|
*
|
||||||
|
* Author: Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
* $Id: uip-split.h,v 1.1.1.1 2007-08-26 23:04:08 patacongo Exp $
|
||||||
|
*/
|
||||||
|
/**
|
||||||
|
* \addtogroup uip
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \defgroup uipsplit uIP TCP throughput booster hack
|
||||||
|
* @{
|
||||||
|
*
|
||||||
|
* The basic uIP TCP implementation only allows each TCP connection to
|
||||||
|
* have a single TCP segment in flight at any given time. Because of
|
||||||
|
* the delayed ACK algorithm employed by most TCP receivers, uIP's
|
||||||
|
* limit on the amount of in-flight TCP segments seriously reduces the
|
||||||
|
* maximum achievable throughput for sending data from uIP.
|
||||||
|
*
|
||||||
|
* The uip-split module is a hack which tries to remedy this
|
||||||
|
* situation. By splitting maximum sized outgoing TCP segments into
|
||||||
|
* two, the delayed ACK algorithm is not invoked at TCP
|
||||||
|
* receivers. This improves the throughput when sending data from uIP
|
||||||
|
* by orders of magnitude.
|
||||||
|
*
|
||||||
|
* The uip-split module uses the uip-fw module (uIP IP packet
|
||||||
|
* forwarding) for sending packets. Therefore, the uip-fw module must
|
||||||
|
* be set up with the appropriate network interfaces for this module
|
||||||
|
* to work.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \file
|
||||||
|
* Module for splitting outbound TCP segments in two to avoid the
|
||||||
|
* delayed ACK throughput degradation.
|
||||||
|
* \author
|
||||||
|
* Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __UIP_SPLIT_H__
|
||||||
|
#define __UIP_SPLIT_H__
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle outgoing packets.
|
||||||
|
*
|
||||||
|
* This function inspects an outgoing packet in the uip_buf buffer and
|
||||||
|
* sends it out using the uip_fw_output() function. If the packet is a
|
||||||
|
* full-sized TCP segment it will be split into two segments and
|
||||||
|
* transmitted separately. This function should be called instead of
|
||||||
|
* the actual device driver output function, or the uip_fw_output()
|
||||||
|
* function.
|
||||||
|
*
|
||||||
|
* The headers of the outgoing packet is assumed to be in the uip_buf
|
||||||
|
* buffer and the payload is assumed to be wherever uip_appdata
|
||||||
|
* points. The length of the outgoing packet is assumed to be in the
|
||||||
|
* uip_len variable.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
void uip_split_output(void);
|
||||||
|
|
||||||
|
#endif /* __UIP_SPLIT_H__ */
|
||||||
|
|
||||||
|
/** @} */
|
||||||
|
/** @} */
|
||||||
@@ -0,0 +1,180 @@
|
|||||||
|
/************************************************************
|
||||||
|
* uip-wait.c
|
||||||
|
*
|
||||||
|
* Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
* Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
*
|
||||||
|
* 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 <semaphore.h>
|
||||||
|
#include <wdog.h>
|
||||||
|
#include <arch/irq.h>
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Definitions
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Private Data
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
/* Threads and tasks can both wait a semaphore. This
|
||||||
|
* initializer uses internal, non-portable knowledge of the\
|
||||||
|
* structure of sem_t to initialize it to the value 0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
static sem_t uip_waitsem = { 0 }; /* Semaphore to wait on */
|
||||||
|
static uint16 uip_waitflags = 0; /* UIP flags to wait for */
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Private Functions
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
/* Called from the timer interrupt handler when a event wait
|
||||||
|
* watchdog expires.
|
||||||
|
*/
|
||||||
|
|
||||||
|
static void uip_event_timeout(int argc, uint32 itcb, ...)
|
||||||
|
{
|
||||||
|
irqstate_t save = irqsave(); /* Should not be necessary */
|
||||||
|
uip_flags |= UIP_APPTIMEOUT; /* Set software timeout event */
|
||||||
|
uip_event_signal(); /* Signal the waiting thread/task */
|
||||||
|
irqrestore(save); /* Restore interrupts */
|
||||||
|
}
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Global Functions
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
/* This function is called user code to set up the wait */
|
||||||
|
|
||||||
|
int uip_event_timedwait(uint16 waitflags, int timeout)
|
||||||
|
{
|
||||||
|
/* Prevent conflicts with the interrupt level operation of
|
||||||
|
* uip_event_signal().
|
||||||
|
*/
|
||||||
|
irqstate_t save = irqsave();
|
||||||
|
WDOG_ID wdog;
|
||||||
|
|
||||||
|
/* At present, we support only a single waiter. If uip_waitflags
|
||||||
|
* is non-zero on entry, then there is a problem.
|
||||||
|
*/
|
||||||
|
|
||||||
|
if ( uip_waitflags == 0)
|
||||||
|
{
|
||||||
|
/* If the requested event bits are not set in the uip_flags,
|
||||||
|
* then wait. We will be awakened as soon as an interrupt is
|
||||||
|
* received that sets these bits.
|
||||||
|
*/
|
||||||
|
|
||||||
|
goto errout_with_irqdisabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Loop until the requested bits are set in the flags */
|
||||||
|
|
||||||
|
while ((waitflags & uip_flags) != 0)
|
||||||
|
{
|
||||||
|
/* Set the event flags that the caller is waiting on */
|
||||||
|
|
||||||
|
uip_waitflags = waitflags;
|
||||||
|
|
||||||
|
/* Was a timeut requested as well? */
|
||||||
|
|
||||||
|
if (timeout)
|
||||||
|
{
|
||||||
|
/* Yes, then set the application timeout event as well */
|
||||||
|
|
||||||
|
uip_waitflags |= UIP_APPTIMEOUT;
|
||||||
|
|
||||||
|
/* Create a watchdog */
|
||||||
|
|
||||||
|
wdog = wd_create();
|
||||||
|
if (!wdog)
|
||||||
|
{
|
||||||
|
goto errout_with_irqdisabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Start the watchdog */
|
||||||
|
|
||||||
|
wd_start(wdog, timeout, (wdentry_t)uip_event_timeout, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Wait for the event (or timeout) to occur */
|
||||||
|
|
||||||
|
if (sem_wait(&uip_waitsem) != 0)
|
||||||
|
{
|
||||||
|
goto errout_with_watchdog;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* We no longer need the watchdog */
|
||||||
|
|
||||||
|
if (wdog)
|
||||||
|
{
|
||||||
|
wd_delete(wdog);
|
||||||
|
wdog = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
irqrestore(save);
|
||||||
|
return OK;
|
||||||
|
|
||||||
|
errout_with_watchdog:
|
||||||
|
if (wdog)
|
||||||
|
{
|
||||||
|
wd_delete(wdog);
|
||||||
|
}
|
||||||
|
|
||||||
|
errout_with_irqdisabled:
|
||||||
|
irqrestore(save);
|
||||||
|
return ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* This function is called from uip_interrupt() to wake up any
|
||||||
|
* waiting threads/tasks.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_event_signal(void)
|
||||||
|
{
|
||||||
|
/* If any bits in uip_waitflags match bits set in uip_flags, then
|
||||||
|
* there must be a thread/task waiting for this event to occur.
|
||||||
|
*/
|
||||||
|
|
||||||
|
if ((uip_waitflags & uip_flags) != 0)
|
||||||
|
{
|
||||||
|
sem_post(&uip_waitsem); /* Post the event */
|
||||||
|
uip_waitflags = 0; /* Prohibit posting the event multiple times */
|
||||||
|
}
|
||||||
|
}
|
||||||
+2091
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,97 @@
|
|||||||
|
############################################################
|
||||||
|
# Makefile
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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)/Make.defs
|
||||||
|
|
||||||
|
MKDEP = $(TOPDIR)/tools/mkdeps.sh
|
||||||
|
|
||||||
|
ifeq ($(CONFIG_NET_UIP),y)
|
||||||
|
include uiplib/Make.defs
|
||||||
|
include dhcpc/Make.defs
|
||||||
|
include resolv/Make.defs
|
||||||
|
include smtp/Make.defs
|
||||||
|
include telnetd/Make.defs
|
||||||
|
include webclient/Make.defs
|
||||||
|
include webserver/Make.defs
|
||||||
|
endif
|
||||||
|
|
||||||
|
ASRCS = $(UIPLIB_ASRCS) $(DHCPC_ASRCS) $(RESOLV_ASRCS) $(SMTP_ASRCS) \
|
||||||
|
$(TELNETD_ASRCS) $(WEBCLIENT_ASRCS) $(WEBSERVER_ASRCS)
|
||||||
|
AOBJS = $(ASRCS:.S=$(OBJEXT))
|
||||||
|
|
||||||
|
CSRCS = $(UIPLIB_CSRCS) $(DHCPC_CSRCS) $(RESOLV_CSRCS) $(SMTP_CSRCS) \
|
||||||
|
$(TELNETD_CSRCS) $(WEBCLIENT_CSRCS) $(WEBSERVER_CSRCS)
|
||||||
|
COBJS = $(CSRCS:.c=$(OBJEXT))
|
||||||
|
|
||||||
|
SRCS = $(ASRCS) $(CSRCS)
|
||||||
|
OBJS = $(AOBJS) $(COBJS)
|
||||||
|
|
||||||
|
BIN = libnetutils$(LIBEXT)
|
||||||
|
|
||||||
|
VPATH = uiplib:dhcpc:resolv:smtp:telnetd:webclient:webserver
|
||||||
|
|
||||||
|
all: $(BIN)
|
||||||
|
|
||||||
|
$(AOBJS): %$(OBJEXT): %.S
|
||||||
|
$(CC) -c $(CFLAGS) -D__ASSEMBLY__ $< -o $@
|
||||||
|
|
||||||
|
$(COBJS): %$(OBJEXT): %.c
|
||||||
|
$(CC) -c $(CFLAGS) $< -o $@
|
||||||
|
|
||||||
|
$(BIN): $(OBJS)
|
||||||
|
( for obj in $(OBJS) ; do \
|
||||||
|
$(AR) $@ $${obj} || \
|
||||||
|
{ echo "$(AR) $@ $obj FAILED!" ; exit 1 ; } ; \
|
||||||
|
done ; )
|
||||||
|
|
||||||
|
.depend: Makefile $(SRCS)
|
||||||
|
ifeq ($(CONFIG_NET_UIP),y)
|
||||||
|
$(MKDEP) --dep-path uiplib --dep-path dhcpc --dep-path smtp --dep-path webclient \
|
||||||
|
--dep-path resolv --dep-path telnetd --dep-path webserver \
|
||||||
|
$(CC) -- $(CFLAGS) -- $(SRCS) >Make.dep
|
||||||
|
endif
|
||||||
|
touch $@
|
||||||
|
|
||||||
|
depend: .depend
|
||||||
|
|
||||||
|
clean:
|
||||||
|
rm -f $(BIN) *.o *.rel *.asm *.lst *.sym *.adb *~
|
||||||
|
rm -f uiplib/*~ dhcpc/*~ resolv/*~ smtp/*~ telnetd/*~ webclient/*~ webserver/*~
|
||||||
|
if [ ! -z "$(OBJEXT)" ]; then rm -f *$(OBJEXT); fi
|
||||||
|
|
||||||
|
distclean: clean
|
||||||
|
rm -f Make.dep .depend
|
||||||
|
|
||||||
|
-include Make.dep
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
netutils
|
||||||
|
^^^^^^^^
|
||||||
|
|
||||||
|
This directory contains most of the network applications contained under the uIP-1.0 apps directory.
|
||||||
|
As the uIP apps/README says, there applications "are not all heavily tested."
|
||||||
@@ -0,0 +1,39 @@
|
|||||||
|
############################################################################
|
||||||
|
# Make.defs
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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.
|
||||||
|
#
|
||||||
|
############################################################################
|
||||||
|
|
||||||
|
ifeq ($(CONFIG_UIP_UDP),y)
|
||||||
|
DHCPC_ASRCS =
|
||||||
|
DHCPC_CSRCS = dhcpc.c
|
||||||
|
endif
|
||||||
@@ -0,0 +1,390 @@
|
|||||||
|
/************************************************************
|
||||||
|
* dhcpc.c
|
||||||
|
*
|
||||||
|
* Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
* Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
*
|
||||||
|
* Based heavily on portions of uIP:
|
||||||
|
*
|
||||||
|
* Copyright (c) 2005, Swedish Institute of Computer Science
|
||||||
|
* 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. 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 <sys/types.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <pthread.h>
|
||||||
|
#include <time.h>
|
||||||
|
#include <debug.h>
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
|
||||||
|
#include "dhcpc.h"
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Definitions
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
/* CLK_TCK is the frequency of the system clock (typically 100Hz) */
|
||||||
|
#define CLOCK_SECOND CLK_TCK
|
||||||
|
|
||||||
|
#define STATE_INITIAL 0
|
||||||
|
#define STATE_SENDING 1
|
||||||
|
#define STATE_OFFER_RECEIVED 2
|
||||||
|
#define STATE_CONFIG_RECEIVED 3
|
||||||
|
|
||||||
|
#define BOOTP_BROADCAST 0x8000
|
||||||
|
|
||||||
|
#define DHCP_REQUEST 1
|
||||||
|
#define DHCP_REPLY 2
|
||||||
|
#define DHCP_HTYPE_ETHERNET 1
|
||||||
|
#define DHCP_HLEN_ETHERNET 6
|
||||||
|
#define DHCP_MSG_LEN 236
|
||||||
|
|
||||||
|
#define DHCPC_SERVER_PORT 67
|
||||||
|
#define DHCPC_CLIENT_PORT 68
|
||||||
|
|
||||||
|
#define DHCPDISCOVER 1
|
||||||
|
#define DHCPOFFER 2
|
||||||
|
#define DHCPREQUEST 3
|
||||||
|
#define DHCPDECLINE 4
|
||||||
|
#define DHCPACK 5
|
||||||
|
#define DHCPNAK 6
|
||||||
|
#define DHCPRELEASE 7
|
||||||
|
|
||||||
|
#define DHCP_OPTION_SUBNET_MASK 1
|
||||||
|
#define DHCP_OPTION_ROUTER 3
|
||||||
|
#define DHCP_OPTION_DNS_SERVER 6
|
||||||
|
#define DHCP_OPTION_REQ_IPADDR 50
|
||||||
|
#define DHCP_OPTION_LEASE_TIME 51
|
||||||
|
#define DHCP_OPTION_MSG_TYPE 53
|
||||||
|
#define DHCP_OPTION_SERVER_ID 54
|
||||||
|
#define DHCP_OPTION_REQ_LIST 55
|
||||||
|
#define DHCP_OPTION_END 255
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Private Types
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
struct dhcp_msg
|
||||||
|
{
|
||||||
|
uint8 op, htype, hlen, hops;
|
||||||
|
uint8 xid[4];
|
||||||
|
uint16 secs, flags;
|
||||||
|
uint8 ciaddr[4];
|
||||||
|
uint8 yiaddr[4];
|
||||||
|
uint8 siaddr[4];
|
||||||
|
uint8 giaddr[4];
|
||||||
|
uint8 chaddr[16];
|
||||||
|
#ifndef CONFIG_UIP_DHCP_LIGHT
|
||||||
|
uint8 sname[64];
|
||||||
|
uint8 file[128];
|
||||||
|
#endif
|
||||||
|
uint8 options[312];
|
||||||
|
};
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Private Data
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
static struct dhcpc_state s;
|
||||||
|
|
||||||
|
static const uint8 xid[4] = {0xad, 0xde, 0x12, 0x23};
|
||||||
|
static const uint8 magic_cookie[4] = {99, 130, 83, 99};
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Private Functions
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
static uint8 *add_msg_type(uint8 *optptr, uint8 type)
|
||||||
|
{
|
||||||
|
*optptr++ = DHCP_OPTION_MSG_TYPE;
|
||||||
|
*optptr++ = 1;
|
||||||
|
*optptr++ = type;
|
||||||
|
return optptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint8 *add_server_id(uint8 *optptr)
|
||||||
|
{
|
||||||
|
*optptr++ = DHCP_OPTION_SERVER_ID;
|
||||||
|
*optptr++ = 4;
|
||||||
|
memcpy(optptr, s.serverid, 4);
|
||||||
|
return optptr + 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint8 *add_req_ipaddr(uint8 *optptr)
|
||||||
|
{
|
||||||
|
*optptr++ = DHCP_OPTION_REQ_IPADDR;
|
||||||
|
*optptr++ = 4;
|
||||||
|
memcpy(optptr, s.ipaddr, 4);
|
||||||
|
return optptr + 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint8 *add_req_options(uint8 *optptr)
|
||||||
|
{
|
||||||
|
*optptr++ = DHCP_OPTION_REQ_LIST;
|
||||||
|
*optptr++ = 3;
|
||||||
|
*optptr++ = DHCP_OPTION_SUBNET_MASK;
|
||||||
|
*optptr++ = DHCP_OPTION_ROUTER;
|
||||||
|
*optptr++ = DHCP_OPTION_DNS_SERVER;
|
||||||
|
return optptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint8 *add_end(uint8 *optptr)
|
||||||
|
{
|
||||||
|
*optptr++ = DHCP_OPTION_END;
|
||||||
|
return optptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void create_msg(register struct dhcp_msg *m)
|
||||||
|
{
|
||||||
|
m->op = DHCP_REQUEST;
|
||||||
|
m->htype = DHCP_HTYPE_ETHERNET;
|
||||||
|
m->hlen = s.mac_len;
|
||||||
|
m->hops = 0;
|
||||||
|
memcpy(m->xid, xid, sizeof(m->xid));
|
||||||
|
m->secs = 0;
|
||||||
|
m->flags = HTONS(BOOTP_BROADCAST); /* Broadcast bit. */
|
||||||
|
/* uip_ipaddr_copy(m->ciaddr, uip_hostaddr);*/
|
||||||
|
memcpy(m->ciaddr, uip_hostaddr, sizeof(m->ciaddr));
|
||||||
|
memset(m->yiaddr, 0, sizeof(m->yiaddr));
|
||||||
|
memset(m->siaddr, 0, sizeof(m->siaddr));
|
||||||
|
memset(m->giaddr, 0, sizeof(m->giaddr));
|
||||||
|
memcpy(m->chaddr, s.mac_addr, s.mac_len);
|
||||||
|
memset(&m->chaddr[s.mac_len], 0, sizeof(m->chaddr) - s.mac_len);
|
||||||
|
#ifndef CONFIG_UIP_DHCP_LIGHT
|
||||||
|
memset(m->sname, 0, sizeof(m->sname));
|
||||||
|
memset(m->file, 0, sizeof(m->file));
|
||||||
|
#endif
|
||||||
|
|
||||||
|
memcpy(m->options, magic_cookie, sizeof(magic_cookie));
|
||||||
|
}
|
||||||
|
|
||||||
|
static void send_discover(void)
|
||||||
|
{
|
||||||
|
uint8 *end;
|
||||||
|
struct dhcp_msg *m = (struct dhcp_msg *)uip_appdata;
|
||||||
|
|
||||||
|
create_msg(m);
|
||||||
|
|
||||||
|
end = add_msg_type(&m->options[4], DHCPDISCOVER);
|
||||||
|
end = add_req_options(end);
|
||||||
|
end = add_end(end);
|
||||||
|
|
||||||
|
uip_send(uip_appdata, end - (uint8 *)uip_appdata);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void send_request(void)
|
||||||
|
{
|
||||||
|
uint8 *end;
|
||||||
|
struct dhcp_msg *m = (struct dhcp_msg *)uip_appdata;
|
||||||
|
|
||||||
|
create_msg(m);
|
||||||
|
|
||||||
|
end = add_msg_type(&m->options[4], DHCPREQUEST);
|
||||||
|
end = add_server_id(end);
|
||||||
|
end = add_req_ipaddr(end);
|
||||||
|
end = add_end(end);
|
||||||
|
|
||||||
|
uip_send(uip_appdata, end - (uint8 *)uip_appdata);
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint8 parse_options(uint8 *optptr, int len)
|
||||||
|
{
|
||||||
|
uint8 *end = optptr + len;
|
||||||
|
uint8 type = 0;
|
||||||
|
|
||||||
|
while (optptr < end)
|
||||||
|
{
|
||||||
|
switch(*optptr)
|
||||||
|
{
|
||||||
|
case DHCP_OPTION_SUBNET_MASK:
|
||||||
|
memcpy(s.netmask, optptr + 2, 4);
|
||||||
|
break;
|
||||||
|
case DHCP_OPTION_ROUTER:
|
||||||
|
memcpy(s.default_router, optptr + 2, 4);
|
||||||
|
break;
|
||||||
|
case DHCP_OPTION_DNS_SERVER:
|
||||||
|
memcpy(s.dnsaddr, optptr + 2, 4);
|
||||||
|
break;
|
||||||
|
case DHCP_OPTION_MSG_TYPE:
|
||||||
|
type = *(optptr + 2);
|
||||||
|
break;
|
||||||
|
case DHCP_OPTION_SERVER_ID:
|
||||||
|
memcpy(s.serverid, optptr + 2, 4);
|
||||||
|
break;
|
||||||
|
case DHCP_OPTION_LEASE_TIME:
|
||||||
|
memcpy(s.lease_time, optptr + 2, 4);
|
||||||
|
break;
|
||||||
|
case DHCP_OPTION_END:
|
||||||
|
return type;
|
||||||
|
}
|
||||||
|
|
||||||
|
optptr += optptr[1] + 2;
|
||||||
|
}
|
||||||
|
return type;
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint8 parse_msg(void)
|
||||||
|
{
|
||||||
|
struct dhcp_msg *m = (struct dhcp_msg *)uip_appdata;
|
||||||
|
|
||||||
|
if (m->op == DHCP_REPLY &&
|
||||||
|
memcmp(m->xid, xid, sizeof(xid)) == 0 &&
|
||||||
|
memcmp(m->chaddr, s.mac_addr, s.mac_len) == 0)
|
||||||
|
{
|
||||||
|
memcpy(s.ipaddr, m->yiaddr, 4);
|
||||||
|
return parse_options(&m->options[4], uip_datalen());
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void handle_dhcp(void)
|
||||||
|
{
|
||||||
|
restart:
|
||||||
|
s.state = STATE_SENDING;
|
||||||
|
s.ticks = CLOCK_SECOND;
|
||||||
|
|
||||||
|
do
|
||||||
|
{
|
||||||
|
/* Send the command */
|
||||||
|
|
||||||
|
send_discover();
|
||||||
|
|
||||||
|
/* Wait for the response */
|
||||||
|
|
||||||
|
uip_event_timedwait(UIP_NEWDATA, CLOCK_SECOND);
|
||||||
|
|
||||||
|
if (uip_newdata() && parse_msg() == DHCPOFFER)
|
||||||
|
{
|
||||||
|
s.state = STATE_OFFER_RECEIVED;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (s.ticks < CLOCK_SECOND * 60)
|
||||||
|
{
|
||||||
|
s.ticks *= 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
while(s.state != STATE_OFFER_RECEIVED);
|
||||||
|
|
||||||
|
s.ticks = CLOCK_SECOND;
|
||||||
|
|
||||||
|
do
|
||||||
|
{
|
||||||
|
/* Send the request */
|
||||||
|
|
||||||
|
send_request();
|
||||||
|
|
||||||
|
/* Then wait to received the response */
|
||||||
|
|
||||||
|
uip_event_timedwait(UIP_NEWDATA, CLOCK_SECOND);
|
||||||
|
|
||||||
|
if (uip_newdata() && parse_msg() == DHCPACK)
|
||||||
|
{
|
||||||
|
s.state = STATE_CONFIG_RECEIVED;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (s.ticks <= CLOCK_SECOND * 10)
|
||||||
|
{
|
||||||
|
s.ticks += CLOCK_SECOND;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
goto restart;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
while(s.state != STATE_CONFIG_RECEIVED);
|
||||||
|
|
||||||
|
dbg("Got IP address %d.%d.%d.%d\n",
|
||||||
|
uip_ipaddr1(s.ipaddr), uip_ipaddr2(s.ipaddr),
|
||||||
|
uip_ipaddr3(s.ipaddr), uip_ipaddr4(s.ipaddr));
|
||||||
|
dbg("Got netmask %d.%d.%d.%d\n",
|
||||||
|
uip_ipaddr1(s.netmask), uip_ipaddr2(s.netmask),
|
||||||
|
uip_ipaddr3(s.netmask), uip_ipaddr4(s.netmask));
|
||||||
|
dbg("Got DNS server %d.%d.%d.%d\n",
|
||||||
|
uip_ipaddr1(s.dnsaddr), uip_ipaddr2(s.dnsaddr),
|
||||||
|
uip_ipaddr3(s.dnsaddr), uip_ipaddr4(s.dnsaddr));
|
||||||
|
dbg("Got default router %d.%d.%d.%d\n",
|
||||||
|
uip_ipaddr1(s.default_router), uip_ipaddr2(s.default_router),
|
||||||
|
uip_ipaddr3(s.default_router), uip_ipaddr4(s.default_router));
|
||||||
|
dbg("Lease expires in %ld seconds\n",
|
||||||
|
ntohs(s.lease_time[0])*65536ul + ntohs(s.lease_time[1]));
|
||||||
|
|
||||||
|
dhcpc_configured(&s);
|
||||||
|
|
||||||
|
pthread_exit(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
/************************************************************
|
||||||
|
* Global Functions
|
||||||
|
************************************************************/
|
||||||
|
|
||||||
|
void dhcpc_init(const void *mac_addr, int mac_len)
|
||||||
|
{
|
||||||
|
uip_ipaddr_t addr;
|
||||||
|
|
||||||
|
s.mac_addr = mac_addr;
|
||||||
|
s.mac_len = mac_len;
|
||||||
|
|
||||||
|
s.state = STATE_INITIAL;
|
||||||
|
uip_ipaddr(addr, 255,255,255,255);
|
||||||
|
s.conn = uip_udp_new(&addr, HTONS(DHCPC_SERVER_PORT));
|
||||||
|
if (s.conn != NULL)
|
||||||
|
{
|
||||||
|
uip_udp_bind(s.conn, HTONS(DHCPC_CLIENT_PORT));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* This function is called by the UIP interrupt handling logic whenevent an
|
||||||
|
* event of interest occurs.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_interrupt_udp_event(void)
|
||||||
|
{
|
||||||
|
handle_dhcp();
|
||||||
|
}
|
||||||
|
|
||||||
|
void dhcpc_request(void)
|
||||||
|
{
|
||||||
|
uint16 ipaddr[2];
|
||||||
|
|
||||||
|
if (s.state == STATE_INITIAL)
|
||||||
|
{
|
||||||
|
uip_ipaddr(ipaddr, 0,0,0,0);
|
||||||
|
uip_sethostaddr(ipaddr);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,58 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2005, Swedish Institute of Computer Science
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
|
||||||
|
*
|
||||||
|
* This file is part of the uIP TCP/IP stack
|
||||||
|
*
|
||||||
|
* @(#)$Id: dhcpc.h,v 1.1.1.1 2007-08-26 23:07:02 patacongo Exp $
|
||||||
|
*/
|
||||||
|
#ifndef __DHCPC_H__
|
||||||
|
#define __DHCPC_H__
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
struct dhcpc_state {
|
||||||
|
char state;
|
||||||
|
struct uip_udp_conn *conn;
|
||||||
|
uint16 ticks;
|
||||||
|
const void *mac_addr;
|
||||||
|
int mac_len;
|
||||||
|
|
||||||
|
uint8 serverid[4];
|
||||||
|
|
||||||
|
uint16 lease_time[2];
|
||||||
|
uint16 ipaddr[2];
|
||||||
|
uint16 netmask[2];
|
||||||
|
uint16 dnsaddr[2];
|
||||||
|
uint16 default_router[2];
|
||||||
|
};
|
||||||
|
|
||||||
|
void dhcpc_init(const void *mac_addr, int mac_len);
|
||||||
|
void dhcpc_request(void);
|
||||||
|
void dhcpc_configured(const struct dhcpc_state *s);
|
||||||
|
|
||||||
|
#endif /* __DHCPC_H__ */
|
||||||
@@ -0,0 +1,39 @@
|
|||||||
|
############################################################################
|
||||||
|
# Make.defs
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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.
|
||||||
|
#
|
||||||
|
############################################################################
|
||||||
|
|
||||||
|
ifeq ($(CONFIG_UIP_UDP),y)
|
||||||
|
RESOLV_ASRCS =
|
||||||
|
RESOLV_CSRCS = resolv.c
|
||||||
|
endif
|
||||||
@@ -0,0 +1,450 @@
|
|||||||
|
/* uip-resolv.c
|
||||||
|
* DNS host name to IP address resolver.
|
||||||
|
* Author: Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* The uIP DNS resolver functions are used to lookup a hostname and
|
||||||
|
* map it to a numerical IP address. It maintains a list of resolved
|
||||||
|
* hostnames that can be queried with the resolv_lookup()
|
||||||
|
* function. New hostnames can be resolved using the resolv_query()
|
||||||
|
* function.
|
||||||
|
*
|
||||||
|
* When a hostname has been resolved (or found to be non-existant),
|
||||||
|
* the resolver code calls a callback function called resolv_found()
|
||||||
|
* that must be implemented by the module that uses the resolver.
|
||||||
|
*
|
||||||
|
* Copyright (c) 2002-2003, Adam Dunkels.
|
||||||
|
* 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. 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 uIP TCP/IP stack.
|
||||||
|
*
|
||||||
|
* $Id: resolv.c,v 1.1.1.1 2007-08-26 23:07:05 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
#include <net/uip/resolv.h>
|
||||||
|
|
||||||
|
#ifndef NULL
|
||||||
|
#define NULL (void *)0
|
||||||
|
#endif /* NULL */
|
||||||
|
|
||||||
|
/** \internal The maximum number of retries when asking for a name. */
|
||||||
|
#define MAX_RETRIES 8
|
||||||
|
|
||||||
|
/** \internal The DNS message header. */
|
||||||
|
struct dns_hdr {
|
||||||
|
uint16 id;
|
||||||
|
uint8 flags1, flags2;
|
||||||
|
#define DNS_FLAG1_RESPONSE 0x80
|
||||||
|
#define DNS_FLAG1_OPCODE_STATUS 0x10
|
||||||
|
#define DNS_FLAG1_OPCODE_INVERSE 0x08
|
||||||
|
#define DNS_FLAG1_OPCODE_STANDARD 0x00
|
||||||
|
#define DNS_FLAG1_AUTHORATIVE 0x04
|
||||||
|
#define DNS_FLAG1_TRUNC 0x02
|
||||||
|
#define DNS_FLAG1_RD 0x01
|
||||||
|
#define DNS_FLAG2_RA 0x80
|
||||||
|
#define DNS_FLAG2_ERR_MASK 0x0f
|
||||||
|
#define DNS_FLAG2_ERR_NONE 0x00
|
||||||
|
#define DNS_FLAG2_ERR_NAME 0x03
|
||||||
|
uint16 numquestions;
|
||||||
|
uint16 numanswers;
|
||||||
|
uint16 numauthrr;
|
||||||
|
uint16 numextrarr;
|
||||||
|
};
|
||||||
|
|
||||||
|
/** \internal The DNS answer message structure. */
|
||||||
|
struct dns_answer {
|
||||||
|
/* DNS answer record starts with either a domain name or a pointer
|
||||||
|
to a name already present somewhere in the packet. */
|
||||||
|
uint16 type;
|
||||||
|
uint16 class;
|
||||||
|
uint16 ttl[2];
|
||||||
|
uint16 len;
|
||||||
|
uip_ipaddr_t ipaddr;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct namemap {
|
||||||
|
#define STATE_UNUSED 0
|
||||||
|
#define STATE_NEW 1
|
||||||
|
#define STATE_ASKING 2
|
||||||
|
#define STATE_DONE 3
|
||||||
|
#define STATE_ERROR 4
|
||||||
|
uint8 state;
|
||||||
|
uint8 tmr;
|
||||||
|
uint8 retries;
|
||||||
|
uint8 seqno;
|
||||||
|
uint8 err;
|
||||||
|
char name[32];
|
||||||
|
uip_ipaddr_t ipaddr;
|
||||||
|
};
|
||||||
|
|
||||||
|
#ifndef CONFIG_UIP_RESOLV_ENTRIES
|
||||||
|
#define RESOLV_ENTRIES 4
|
||||||
|
#else /* CONFIG_UIP_RESOLV_ENTRIES */
|
||||||
|
#define RESOLV_ENTRIES CONFIG_UIP_RESOLV_ENTRIES
|
||||||
|
#endif /* CONFIG_UIP_RESOLV_ENTRIES */
|
||||||
|
|
||||||
|
|
||||||
|
static struct namemap names[RESOLV_ENTRIES];
|
||||||
|
|
||||||
|
static uint8 seqno;
|
||||||
|
|
||||||
|
static struct uip_udp_conn *resolv_conn = NULL;
|
||||||
|
|
||||||
|
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/** \internal
|
||||||
|
* Walk through a compact encoded DNS name and return the end of it.
|
||||||
|
*
|
||||||
|
* \return The end of the name.
|
||||||
|
*/
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static unsigned char *parse_name(unsigned char *query)
|
||||||
|
{
|
||||||
|
unsigned char n;
|
||||||
|
|
||||||
|
do {
|
||||||
|
n = *query++;
|
||||||
|
|
||||||
|
while(n > 0)
|
||||||
|
{
|
||||||
|
++query;
|
||||||
|
--n;
|
||||||
|
};
|
||||||
|
} while(*query != 0);
|
||||||
|
return query + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/** \internal
|
||||||
|
* Runs through the list of names to see if there are any that have
|
||||||
|
* not yet been queried and, if so, sends out a query.
|
||||||
|
*/
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
check_entries(void)
|
||||||
|
{
|
||||||
|
register struct dns_hdr *hdr;
|
||||||
|
char *query, *nptr, *nameptr;
|
||||||
|
static uint8 i;
|
||||||
|
static uint8 n;
|
||||||
|
register struct namemap *namemapptr;
|
||||||
|
|
||||||
|
for(i = 0; i < RESOLV_ENTRIES; ++i) {
|
||||||
|
namemapptr = &names[i];
|
||||||
|
if(namemapptr->state == STATE_NEW ||
|
||||||
|
namemapptr->state == STATE_ASKING) {
|
||||||
|
if(namemapptr->state == STATE_ASKING) {
|
||||||
|
if(--namemapptr->tmr == 0) {
|
||||||
|
if(++namemapptr->retries == MAX_RETRIES) {
|
||||||
|
namemapptr->state = STATE_ERROR;
|
||||||
|
resolv_found(namemapptr->name, NULL);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
namemapptr->tmr = namemapptr->retries;
|
||||||
|
} else {
|
||||||
|
/* printf("Timer %d\n", namemapptr->tmr);*/
|
||||||
|
/* Its timer has not run out, so we move on to next
|
||||||
|
entry. */
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
namemapptr->state = STATE_ASKING;
|
||||||
|
namemapptr->tmr = 1;
|
||||||
|
namemapptr->retries = 0;
|
||||||
|
}
|
||||||
|
hdr = (struct dns_hdr *)uip_appdata;
|
||||||
|
memset(hdr, 0, sizeof(struct dns_hdr));
|
||||||
|
hdr->id = htons(i);
|
||||||
|
hdr->flags1 = DNS_FLAG1_RD;
|
||||||
|
hdr->numquestions = HTONS(1);
|
||||||
|
query = (char *)uip_appdata + 12;
|
||||||
|
nameptr = namemapptr->name;
|
||||||
|
--nameptr;
|
||||||
|
/* Convert hostname into suitable query format. */
|
||||||
|
do {
|
||||||
|
++nameptr;
|
||||||
|
nptr = query;
|
||||||
|
++query;
|
||||||
|
for(n = 0; *nameptr != '.' && *nameptr != 0; ++nameptr) {
|
||||||
|
*query = *nameptr;
|
||||||
|
++query;
|
||||||
|
++n;
|
||||||
|
}
|
||||||
|
*nptr = n;
|
||||||
|
} while(*nameptr != 0);
|
||||||
|
{
|
||||||
|
static unsigned char endquery[] =
|
||||||
|
{0,0,1,0,1};
|
||||||
|
memcpy(query, endquery, 5);
|
||||||
|
}
|
||||||
|
uip_udp_send((unsigned char)(query + 5 - (char *)uip_appdata));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/** \internal
|
||||||
|
* Called when new UDP data arrives.
|
||||||
|
*/
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
newdata(void)
|
||||||
|
{
|
||||||
|
unsigned char *nameptr;
|
||||||
|
struct dns_answer *ans;
|
||||||
|
struct dns_hdr *hdr;
|
||||||
|
static uint8 nquestions, nanswers;
|
||||||
|
static uint8 i;
|
||||||
|
register struct namemap *namemapptr;
|
||||||
|
|
||||||
|
hdr = (struct dns_hdr *)uip_appdata;
|
||||||
|
/* printf("ID %d\n", htons(hdr->id));
|
||||||
|
printf("Query %d\n", hdr->flags1 & DNS_FLAG1_RESPONSE);
|
||||||
|
printf("Error %d\n", hdr->flags2 & DNS_FLAG2_ERR_MASK);
|
||||||
|
printf("Num questions %d, answers %d, authrr %d, extrarr %d\n",
|
||||||
|
htons(hdr->numquestions),
|
||||||
|
htons(hdr->numanswers),
|
||||||
|
htons(hdr->numauthrr),
|
||||||
|
htons(hdr->numextrarr));
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* The ID in the DNS header should be our entry into the name
|
||||||
|
table. */
|
||||||
|
i = htons(hdr->id);
|
||||||
|
namemapptr = &names[i];
|
||||||
|
if(i < RESOLV_ENTRIES &&
|
||||||
|
namemapptr->state == STATE_ASKING) {
|
||||||
|
|
||||||
|
/* This entry is now finished. */
|
||||||
|
namemapptr->state = STATE_DONE;
|
||||||
|
namemapptr->err = hdr->flags2 & DNS_FLAG2_ERR_MASK;
|
||||||
|
|
||||||
|
/* Check for error. If so, call callback to inform. */
|
||||||
|
if(namemapptr->err != 0) {
|
||||||
|
namemapptr->state = STATE_ERROR;
|
||||||
|
resolv_found(namemapptr->name, NULL);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* We only care about the question(s) and the answers. The authrr
|
||||||
|
and the extrarr are simply discarded. */
|
||||||
|
nquestions = htons(hdr->numquestions);
|
||||||
|
nanswers = htons(hdr->numanswers);
|
||||||
|
|
||||||
|
/* Skip the name in the question. XXX: This should really be
|
||||||
|
checked agains the name in the question, to be sure that they
|
||||||
|
match. */
|
||||||
|
nameptr = parse_name((unsigned char *)uip_appdata + 12) + 4;
|
||||||
|
|
||||||
|
while(nanswers > 0) {
|
||||||
|
/* The first byte in the answer resource record determines if it
|
||||||
|
is a compressed record or a normal one. */
|
||||||
|
if(*nameptr & 0xc0) {
|
||||||
|
/* Compressed name. */
|
||||||
|
nameptr +=2;
|
||||||
|
/* printf("Compressed anwser\n");*/
|
||||||
|
} else {
|
||||||
|
/* Not compressed name. */
|
||||||
|
nameptr = parse_name(nameptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
ans = (struct dns_answer *)nameptr;
|
||||||
|
/* printf("Answer: type %x, class %x, ttl %x, length %x\n",
|
||||||
|
htons(ans->type), htons(ans->class), (htons(ans->ttl[0])
|
||||||
|
<< 16) | htons(ans->ttl[1]), htons(ans->len));*/
|
||||||
|
|
||||||
|
/* Check for IP address type and Internet class. Others are
|
||||||
|
discarded. */
|
||||||
|
if(ans->type == HTONS(1) &&
|
||||||
|
ans->class == HTONS(1) &&
|
||||||
|
ans->len == HTONS(4)) {
|
||||||
|
/* printf("IP address %d.%d.%d.%d\n",
|
||||||
|
htons(ans->ipaddr[0]) >> 8,
|
||||||
|
htons(ans->ipaddr[0]) & 0xff,
|
||||||
|
htons(ans->ipaddr[1]) >> 8,
|
||||||
|
htons(ans->ipaddr[1]) & 0xff);*/
|
||||||
|
/* XXX: we should really check that this IP address is the one
|
||||||
|
we want. */
|
||||||
|
namemapptr->ipaddr[0] = ans->ipaddr[0];
|
||||||
|
namemapptr->ipaddr[1] = ans->ipaddr[1];
|
||||||
|
|
||||||
|
resolv_found(namemapptr->name, namemapptr->ipaddr);
|
||||||
|
return;
|
||||||
|
} else {
|
||||||
|
nameptr = nameptr + 10 + htons(ans->len);
|
||||||
|
}
|
||||||
|
--nanswers;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/* This function is called by the UIP interrupt handling logic whenevent an
|
||||||
|
* event of interest occurs.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_interrupt_udp_event(void)
|
||||||
|
{
|
||||||
|
if(uip_udp_conn->rport == HTONS(53))
|
||||||
|
{
|
||||||
|
if(uip_poll())
|
||||||
|
{
|
||||||
|
check_entries();
|
||||||
|
}
|
||||||
|
if(uip_newdata())
|
||||||
|
{
|
||||||
|
newdata();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Queues a name so that a question for the name will be sent out.
|
||||||
|
*
|
||||||
|
* \param name The hostname that is to be queried.
|
||||||
|
*/
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
resolv_query(char *name)
|
||||||
|
{
|
||||||
|
static uint8 i;
|
||||||
|
static uint8 lseq, lseqi;
|
||||||
|
register struct namemap *nameptr;
|
||||||
|
|
||||||
|
lseq = lseqi = 0;
|
||||||
|
|
||||||
|
for(i = 0; i < RESOLV_ENTRIES; ++i) {
|
||||||
|
nameptr = &names[i];
|
||||||
|
if(nameptr->state == STATE_UNUSED) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if(seqno - nameptr->seqno > lseq) {
|
||||||
|
lseq = seqno - nameptr->seqno;
|
||||||
|
lseqi = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if(i == RESOLV_ENTRIES) {
|
||||||
|
i = lseqi;
|
||||||
|
nameptr = &names[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
/* printf("Using entry %d\n", i);*/
|
||||||
|
|
||||||
|
strcpy(nameptr->name, name);
|
||||||
|
nameptr->state = STATE_NEW;
|
||||||
|
nameptr->seqno = seqno;
|
||||||
|
++seqno;
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Look up a hostname in the array of known hostnames.
|
||||||
|
*
|
||||||
|
* \note This function only looks in the internal array of known
|
||||||
|
* hostnames, it does not send out a query for the hostname if none
|
||||||
|
* was found. The function resolv_query() can be used to send a query
|
||||||
|
* for a hostname.
|
||||||
|
*
|
||||||
|
* \return A pointer to a 4-byte representation of the hostname's IP
|
||||||
|
* address, or NULL if the hostname was not found in the array of
|
||||||
|
* hostnames.
|
||||||
|
*/
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
uint16 *
|
||||||
|
resolv_lookup(char *name)
|
||||||
|
{
|
||||||
|
static uint8 i;
|
||||||
|
struct namemap *nameptr;
|
||||||
|
|
||||||
|
/* Walk through the list to see if the name is in there. If it is
|
||||||
|
not, we return NULL. */
|
||||||
|
for(i = 0; i < RESOLV_ENTRIES; ++i) {
|
||||||
|
nameptr = &names[i];
|
||||||
|
if(nameptr->state == STATE_DONE &&
|
||||||
|
strcmp(name, nameptr->name) == 0) {
|
||||||
|
return nameptr->ipaddr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Obtain the currently configured DNS server.
|
||||||
|
*
|
||||||
|
* \return A pointer to a 4-byte representation of the IP address of
|
||||||
|
* the currently configured DNS server or NULL if no DNS server has
|
||||||
|
* been configured.
|
||||||
|
*/
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
uint16 *
|
||||||
|
resolv_getserver(void)
|
||||||
|
{
|
||||||
|
if(resolv_conn == NULL) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
return resolv_conn->ripaddr;
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Configure which DNS server to use for queries.
|
||||||
|
*
|
||||||
|
* \param dnsserver A pointer to a 4-byte representation of the IP
|
||||||
|
* address of the DNS server to be configured.
|
||||||
|
*/
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
resolv_conf(uint16 *dnsserver)
|
||||||
|
{
|
||||||
|
if(resolv_conn != NULL) {
|
||||||
|
uip_udp_remove(resolv_conn);
|
||||||
|
}
|
||||||
|
|
||||||
|
resolv_conn = uip_udp_new(dnsserver, HTONS(53));
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Initalize the resolver.
|
||||||
|
*/
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
resolv_init(void)
|
||||||
|
{
|
||||||
|
static uint8 i;
|
||||||
|
|
||||||
|
for(i = 0; i < RESOLV_ENTRIES; ++i) {
|
||||||
|
names[i].state = STATE_DONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
/** @} */
|
||||||
|
/** @} */
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
############################################################################
|
||||||
|
# Make.defs
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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.
|
||||||
|
#
|
||||||
|
############################################################################
|
||||||
|
|
||||||
|
# Does not build
|
||||||
|
# SMTP_ASRCS =
|
||||||
|
# SMTP_CSRCS = smtp.c smtp-strings.c
|
||||||
Executable
+40
@@ -0,0 +1,40 @@
|
|||||||
|
#!/usr/bin/perl
|
||||||
|
|
||||||
|
|
||||||
|
sub stringify {
|
||||||
|
my $name = shift(@_);
|
||||||
|
open(OUTPUTC, "> $name.c");
|
||||||
|
open(OUTPUTH, "> $name.h");
|
||||||
|
|
||||||
|
open(FILE, "$name");
|
||||||
|
|
||||||
|
while(<FILE>) {
|
||||||
|
if(/(.+) "(.+)"/) {
|
||||||
|
$var = $1;
|
||||||
|
$data = $2;
|
||||||
|
|
||||||
|
$datan = $data;
|
||||||
|
$datan =~ s/\\r/\r/g;
|
||||||
|
$datan =~ s/\\n/\n/g;
|
||||||
|
$datan =~ s/\\01/\01/g;
|
||||||
|
$datan =~ s/\\0/\0/g;
|
||||||
|
|
||||||
|
printf(OUTPUTC "const char $var\[%d] = \n", length($datan) + 1);
|
||||||
|
printf(OUTPUTC "/* \"$data\" */\n");
|
||||||
|
printf(OUTPUTC "{");
|
||||||
|
for($j = 0; $j < length($datan); $j++) {
|
||||||
|
printf(OUTPUTC "%#02x, ", unpack("C", substr($datan, $j, 1)));
|
||||||
|
}
|
||||||
|
printf(OUTPUTC "};\n");
|
||||||
|
|
||||||
|
printf(OUTPUTH "extern const char $var\[%d];\n", length($datan) + 1);
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
close(OUTPUTC);
|
||||||
|
close(OUTPUTH);
|
||||||
|
}
|
||||||
|
stringify("smtp-strings");
|
||||||
|
|
||||||
|
exit 0;
|
||||||
|
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
smtp_220 "220"
|
||||||
|
smtp_helo "HELO "
|
||||||
|
smtp_mail_from "MAIL FROM: "
|
||||||
|
smtp_rcpt_to "RCPT TO: "
|
||||||
|
smtp_data "DATA\r\n"
|
||||||
|
smtp_to "To: "
|
||||||
|
smtp_from "From: "
|
||||||
|
smtp_subject "Subject: "
|
||||||
|
smtp_quit "QUIT\r\n"
|
||||||
|
smtp_crnl "\r\n"
|
||||||
|
smtp_crnlperiodcrnl "\r\n.\r\n"
|
||||||
@@ -0,0 +1,33 @@
|
|||||||
|
const char smtp_220[4] =
|
||||||
|
/* "220" */
|
||||||
|
{0x32, 0x32, 0x30, };
|
||||||
|
const char smtp_helo[6] =
|
||||||
|
/* "HELO " */
|
||||||
|
{0x48, 0x45, 0x4c, 0x4f, 0x20, };
|
||||||
|
const char smtp_mail_from[12] =
|
||||||
|
/* "MAIL FROM: " */
|
||||||
|
{0x4d, 0x41, 0x49, 0x4c, 0x20, 0x46, 0x52, 0x4f, 0x4d, 0x3a, 0x20, };
|
||||||
|
const char smtp_rcpt_to[10] =
|
||||||
|
/* "RCPT TO: " */
|
||||||
|
{0x52, 0x43, 0x50, 0x54, 0x20, 0x54, 0x4f, 0x3a, 0x20, };
|
||||||
|
const char smtp_data[7] =
|
||||||
|
/* "DATA\r\n" */
|
||||||
|
{0x44, 0x41, 0x54, 0x41, 0xd, 0xa, };
|
||||||
|
const char smtp_to[5] =
|
||||||
|
/* "To: " */
|
||||||
|
{0x54, 0x6f, 0x3a, 0x20, };
|
||||||
|
const char smtp_from[7] =
|
||||||
|
/* "From: " */
|
||||||
|
{0x46, 0x72, 0x6f, 0x6d, 0x3a, 0x20, };
|
||||||
|
const char smtp_subject[10] =
|
||||||
|
/* "Subject: " */
|
||||||
|
{0x53, 0x75, 0x62, 0x6a, 0x65, 0x63, 0x74, 0x3a, 0x20, };
|
||||||
|
const char smtp_quit[7] =
|
||||||
|
/* "QUIT\r\n" */
|
||||||
|
{0x51, 0x55, 0x49, 0x54, 0xd, 0xa, };
|
||||||
|
const char smtp_crnl[3] =
|
||||||
|
/* "\r\n" */
|
||||||
|
{0xd, 0xa, };
|
||||||
|
const char smtp_crnlperiodcrnl[6] =
|
||||||
|
/* "\r\n.\r\n" */
|
||||||
|
{0xd, 0xa, 0x2e, 0xd, 0xa, };
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
extern const char smtp_220[4];
|
||||||
|
extern const char smtp_helo[6];
|
||||||
|
extern const char smtp_mail_from[12];
|
||||||
|
extern const char smtp_rcpt_to[10];
|
||||||
|
extern const char smtp_data[7];
|
||||||
|
extern const char smtp_to[5];
|
||||||
|
extern const char smtp_from[7];
|
||||||
|
extern const char smtp_subject[10];
|
||||||
|
extern const char smtp_quit[7];
|
||||||
|
extern const char smtp_crnl[3];
|
||||||
|
extern const char smtp_crnlperiodcrnl[6];
|
||||||
@@ -0,0 +1,252 @@
|
|||||||
|
/* smtp.c
|
||||||
|
* smtp SMTP E-mail sender
|
||||||
|
* Author: Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* The Simple Mail Transfer Protocol (SMTP) as defined by RFC821 is
|
||||||
|
* the standard way of sending and transfering e-mail on the
|
||||||
|
* Internet. This simple example implementation is intended as an
|
||||||
|
* example of how to implement protocols in uIP, and is able to send
|
||||||
|
* out e-mail but has not been extensively tested.
|
||||||
|
*
|
||||||
|
* Copyright (c) 2004, Adam Dunkels.
|
||||||
|
* 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. Neither the name of the Institute 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 INSTITUTE 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 INSTITUTE 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.
|
||||||
|
*
|
||||||
|
* This file is part of the uIP TCP/IP stack.
|
||||||
|
*
|
||||||
|
* Author: Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
* $Id: smtp.c,v 1.1.1.1 2007-08-26 23:07:06 patacongo Exp $
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
#include <net/uip/psock.h>
|
||||||
|
#include <net/uip/smtp.h>
|
||||||
|
|
||||||
|
#include "smtp-strings.h"
|
||||||
|
|
||||||
|
static struct smtp_state s;
|
||||||
|
|
||||||
|
static char *localhostname;
|
||||||
|
static uip_ipaddr_t smtpserver;
|
||||||
|
|
||||||
|
#define ISO_nl 0x0a
|
||||||
|
#define ISO_cr 0x0d
|
||||||
|
|
||||||
|
#define ISO_period 0x2e
|
||||||
|
|
||||||
|
#define ISO_2 0x32
|
||||||
|
#define ISO_3 0x33
|
||||||
|
#define ISO_4 0x34
|
||||||
|
#define ISO_5 0x35
|
||||||
|
|
||||||
|
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static
|
||||||
|
void smtp_thread(void)
|
||||||
|
{
|
||||||
|
psock_readto(&s.psock, ISO_nl);
|
||||||
|
|
||||||
|
if(strncmp(s.inputbuffer, smtp_220, 3) != 0) {
|
||||||
|
PSOCK_CLOSE(&s.psock);
|
||||||
|
smtp_done(2);
|
||||||
|
pthread_exit(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_helo);
|
||||||
|
PSOCK_SEND_STR(&s.psock, localhostname);
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnl);
|
||||||
|
|
||||||
|
psock_readto(&s.psock, ISO_nl);
|
||||||
|
|
||||||
|
if(s.inputbuffer[0] != ISO_2) {
|
||||||
|
PSOCK_CLOSE(&s.psock);
|
||||||
|
smtp_done(3);
|
||||||
|
pthread_exit(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_mail_from);
|
||||||
|
PSOCK_SEND_STR(&s.psock, s.from);
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnl);
|
||||||
|
|
||||||
|
psock_readto(&s.psock, ISO_nl);
|
||||||
|
|
||||||
|
if(s.inputbuffer[0] != ISO_2) {
|
||||||
|
PSOCK_CLOSE(&s.psock);
|
||||||
|
smtp_done(4);
|
||||||
|
pthread_exit(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_rcpt_to);
|
||||||
|
PSOCK_SEND_STR(&s.psock, s.to);
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnl);
|
||||||
|
|
||||||
|
psock_readto(&s.psock, ISO_nl);
|
||||||
|
|
||||||
|
if(s.inputbuffer[0] != ISO_2) {
|
||||||
|
PSOCK_CLOSE(&s.psock);
|
||||||
|
smtp_done(5);
|
||||||
|
pthread_exit(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(s.cc != 0) {
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_rcpt_to);
|
||||||
|
PSOCK_SEND_STR(&s.psock, s.cc);
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnl);
|
||||||
|
|
||||||
|
psock_readto(&s.psock, ISO_nl);
|
||||||
|
|
||||||
|
if(s.inputbuffer[0] != ISO_2) {
|
||||||
|
PSOCK_CLOSE(&s.psock);
|
||||||
|
smtp_done(6);
|
||||||
|
pthread_exit(NULL);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_data);
|
||||||
|
|
||||||
|
psock_readto(&s.psock, ISO_nl);
|
||||||
|
|
||||||
|
if(s.inputbuffer[0] != ISO_3) {
|
||||||
|
PSOCK_CLOSE(&s.psock);
|
||||||
|
smtp_done(7);
|
||||||
|
pthread_exit(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_to);
|
||||||
|
PSOCK_SEND_STR(&s.psock, s.to);
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnl);
|
||||||
|
|
||||||
|
if(s.cc != 0) {
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_cc);
|
||||||
|
PSOCK_SEND_STR(&s.psock, s.cc);
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnl);
|
||||||
|
}
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_from);
|
||||||
|
PSOCK_SEND_STR(&s.psock, s.from);
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnl);
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_subject);
|
||||||
|
PSOCK_SEND_STR(&s.psock, s.subject);
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnl);
|
||||||
|
|
||||||
|
psock_send(&s.psock, s.msg, s.msglen);
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_crnlperiodcrnl);
|
||||||
|
|
||||||
|
psock_readto(&s.psock, ISO_nl);
|
||||||
|
if(s.inputbuffer[0] != ISO_2) {
|
||||||
|
PSOCK_CLOSE(&s.psock);
|
||||||
|
smtp_done(8);
|
||||||
|
pthread_exit(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
PSOCK_SEND_STR(&s.psock, (char *)smtp_quit);
|
||||||
|
smtp_done(SMTP_ERR_OK);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* This function is called by the UIP interrupt handling logic whenevent an
|
||||||
|
* event of interest occurs.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_interrupt_event(void)
|
||||||
|
{
|
||||||
|
if(uip_closed()) {
|
||||||
|
s.connected = 0;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if(uip_aborted() || uip_timedout()) {
|
||||||
|
s.connected = 0;
|
||||||
|
smtp_done(1);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
smtp_thread();
|
||||||
|
}
|
||||||
|
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Specificy an SMTP server and hostname.
|
||||||
|
*
|
||||||
|
* This function is used to configure the SMTP module with an SMTP
|
||||||
|
* server and the hostname of the host.
|
||||||
|
*
|
||||||
|
* \param lhostname The hostname of the uIP host.
|
||||||
|
*
|
||||||
|
* \param server A pointer to a 4-byte array representing the IP
|
||||||
|
* address of the SMTP server to be configured.
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
smtp_configure(char *lhostname, void *server)
|
||||||
|
{
|
||||||
|
localhostname = lhostname;
|
||||||
|
uip_ipaddr_copy(smtpserver, server);
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/**
|
||||||
|
* Send an e-mail.
|
||||||
|
*
|
||||||
|
* \param to The e-mail address of the receiver of the e-mail.
|
||||||
|
* \param cc The e-mail address of the CC: receivers of the e-mail.
|
||||||
|
* \param from The e-mail address of the sender of the e-mail.
|
||||||
|
* \param subject The subject of the e-mail.
|
||||||
|
* \param msg The actual e-mail message.
|
||||||
|
* \param msglen The length of the e-mail message.
|
||||||
|
*/
|
||||||
|
unsigned char
|
||||||
|
smtp_send(char *to, char *cc, char *from,
|
||||||
|
char *subject, char *msg, uint16 msglen)
|
||||||
|
{
|
||||||
|
struct uip_conn *conn;
|
||||||
|
|
||||||
|
conn = uip_connect(smtpserver, HTONS(25));
|
||||||
|
if(conn == NULL) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
s.connected = 1;
|
||||||
|
s.to = to;
|
||||||
|
s.cc = cc;
|
||||||
|
s.from = from;
|
||||||
|
s.subject = subject;
|
||||||
|
s.msg = msg;
|
||||||
|
s.msglen = msglen;
|
||||||
|
|
||||||
|
psock_init(&s.psock, s.inputbuffer, sizeof(s.inputbuffer));
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
smtp_init(void)
|
||||||
|
{
|
||||||
|
s.connected = 0;
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
/** @} */
|
||||||
|
/** @} */
|
||||||
@@ -0,0 +1,37 @@
|
|||||||
|
############################################################################
|
||||||
|
# Make.defs
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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.
|
||||||
|
#
|
||||||
|
############################################################################
|
||||||
|
|
||||||
|
TELNETD_ASRCS =
|
||||||
|
TELNETD_CSRCS = telnetd.c shell.c
|
||||||
@@ -0,0 +1,123 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2003, Adam Dunkels.
|
||||||
|
* 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. 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 uIP TCP/IP stack.
|
||||||
|
*
|
||||||
|
* $Id: shell.c,v 1.1.1.1 2007-08-26 23:07:06 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "shell.h"
|
||||||
|
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
struct ptentry {
|
||||||
|
char *commandstr;
|
||||||
|
void (* pfunc)(char *str);
|
||||||
|
};
|
||||||
|
|
||||||
|
#define SHELL_PROMPT "uIP 1.0> "
|
||||||
|
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
parse(register char *str, struct ptentry *t)
|
||||||
|
{
|
||||||
|
struct ptentry *p;
|
||||||
|
for(p = t; p->commandstr != NULL; ++p) {
|
||||||
|
if(strncmp(p->commandstr, str, strlen(p->commandstr)) == 0) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
p->pfunc(str);
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
inttostr(register char *str, unsigned int i)
|
||||||
|
{
|
||||||
|
str[0] = '0' + i / 100;
|
||||||
|
if(str[0] == '0') {
|
||||||
|
str[0] = ' ';
|
||||||
|
}
|
||||||
|
str[1] = '0' + (i / 10) % 10;
|
||||||
|
if(str[0] == ' ' && str[1] == '0') {
|
||||||
|
str[1] = ' ';
|
||||||
|
}
|
||||||
|
str[2] = '0' + i % 10;
|
||||||
|
str[3] = ' ';
|
||||||
|
str[4] = 0;
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
help(char *str)
|
||||||
|
{
|
||||||
|
shell_output("Available commands:", "");
|
||||||
|
shell_output("stats - show network statistics", "");
|
||||||
|
shell_output("conn - show TCP connections", "");
|
||||||
|
shell_output("help, ? - show help", "");
|
||||||
|
shell_output("exit - exit shell", "");
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
unknown(char *str)
|
||||||
|
{
|
||||||
|
if(strlen(str) > 0) {
|
||||||
|
shell_output("Unknown command: ", str);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static struct ptentry parsetab[] =
|
||||||
|
{{"stats", help},
|
||||||
|
{"conn", help},
|
||||||
|
{"help", help},
|
||||||
|
{"exit", shell_quit},
|
||||||
|
{"?", help},
|
||||||
|
|
||||||
|
/* Default action */
|
||||||
|
{NULL, unknown}};
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
shell_init(void)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
shell_start(void)
|
||||||
|
{
|
||||||
|
shell_output("uIP command shell", "");
|
||||||
|
shell_output("Type '?' and return for help", "");
|
||||||
|
shell_prompt(SHELL_PROMPT);
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
shell_input(char *cmd)
|
||||||
|
{
|
||||||
|
parse(cmd, parsetab);
|
||||||
|
shell_prompt(SHELL_PROMPT);
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
@@ -0,0 +1,104 @@
|
|||||||
|
/**
|
||||||
|
* \file
|
||||||
|
* Interface for the Contiki shell.
|
||||||
|
* \author Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* Some of the functions declared in this file must be implemented as
|
||||||
|
* a shell back-end in the architecture specific files of a Contiki
|
||||||
|
* port.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2003, Adam Dunkels.
|
||||||
|
* 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. 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 Contiki desktop OS.
|
||||||
|
*
|
||||||
|
* $Id: shell.h,v 1.1.1.1 2007-08-26 23:07:06 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#ifndef __SHELL_H__
|
||||||
|
#define __SHELL_H__
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Initialize the shell.
|
||||||
|
*
|
||||||
|
* Called when the shell front-end process starts. This function may
|
||||||
|
* be used to start listening for signals.
|
||||||
|
*/
|
||||||
|
void shell_init(void);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Start the shell back-end.
|
||||||
|
*
|
||||||
|
* Called by the front-end when a new shell is started.
|
||||||
|
*/
|
||||||
|
void shell_start(void);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Process a shell command.
|
||||||
|
*
|
||||||
|
* This function will be called by the shell GUI / telnet server whan
|
||||||
|
* a command has been entered that should be processed by the shell
|
||||||
|
* back-end.
|
||||||
|
*
|
||||||
|
* \param command The command to be processed.
|
||||||
|
*/
|
||||||
|
void shell_input(char *command);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Quit the shell.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
void shell_quit(char *);
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Print a string to the shell window.
|
||||||
|
*
|
||||||
|
* This function is implemented by the shell GUI / telnet server and
|
||||||
|
* can be called by the shell back-end to output a string in the
|
||||||
|
* shell window. The string is automatically appended with a linebreak.
|
||||||
|
*
|
||||||
|
* \param str1 The first half of the string to be output.
|
||||||
|
* \param str2 The second half of the string to be output.
|
||||||
|
*/
|
||||||
|
void shell_output(char *str1, char *str2);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Print a prompt to the shell window.
|
||||||
|
*
|
||||||
|
* This function can be used by the shell back-end to print out a
|
||||||
|
* prompt to the shell window.
|
||||||
|
*
|
||||||
|
* \param prompt The prompt to be printed.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
void shell_prompt(char *prompt);
|
||||||
|
|
||||||
|
#endif /* __SHELL_H__ */
|
||||||
@@ -0,0 +1,336 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2003, Adam Dunkels.
|
||||||
|
* 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. 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 uIP TCP/IP stack
|
||||||
|
*
|
||||||
|
* $Id: telnetd.c,v 1.1.1.1 2007-08-26 23:07:06 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
|
||||||
|
#include "telnetd.h"
|
||||||
|
#include "shell.h"
|
||||||
|
|
||||||
|
#define ISO_nl 0x0a
|
||||||
|
#define ISO_cr 0x0d
|
||||||
|
|
||||||
|
#define STATE_NORMAL 0
|
||||||
|
#define STATE_IAC 1
|
||||||
|
#define STATE_WILL 2
|
||||||
|
#define STATE_WONT 3
|
||||||
|
#define STATE_DO 4
|
||||||
|
#define STATE_DONT 5
|
||||||
|
#define STATE_CLOSE 6
|
||||||
|
|
||||||
|
static struct telnetd_state s;
|
||||||
|
|
||||||
|
#define TELNET_IAC 255
|
||||||
|
#define TELNET_WILL 251
|
||||||
|
#define TELNET_WONT 252
|
||||||
|
#define TELNET_DO 253
|
||||||
|
#define TELNET_DONT 254
|
||||||
|
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
shell_quit(char *str)
|
||||||
|
{
|
||||||
|
s.state = STATE_CLOSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
sendline(char *line)
|
||||||
|
{
|
||||||
|
static unsigned int i;
|
||||||
|
|
||||||
|
for(i = 0; i < TELNETD_CONF_NUMLINES; ++i) {
|
||||||
|
if(s.lines[i] == NULL) {
|
||||||
|
s.lines[i] = line;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(i == TELNETD_CONF_NUMLINES) {
|
||||||
|
free(line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
shell_prompt(char *str)
|
||||||
|
{
|
||||||
|
char *line;
|
||||||
|
line = (char*)malloc(TELNETD_CONF_LINELEN);
|
||||||
|
if(line != NULL) {
|
||||||
|
strncpy(line, str, TELNETD_CONF_LINELEN);
|
||||||
|
/* petsciiconv_toascii(line, TELNETD_CONF_LINELEN);*/
|
||||||
|
sendline(line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
shell_output(char *str1, char *str2)
|
||||||
|
{
|
||||||
|
static unsigned len;
|
||||||
|
char *line;
|
||||||
|
|
||||||
|
line = (char*)malloc(TELNETD_CONF_LINELEN);
|
||||||
|
if(line != NULL) {
|
||||||
|
len = strlen(str1);
|
||||||
|
strncpy(line, str1, TELNETD_CONF_LINELEN);
|
||||||
|
if(len < TELNETD_CONF_LINELEN) {
|
||||||
|
strncpy(line + len, str2, TELNETD_CONF_LINELEN - len);
|
||||||
|
}
|
||||||
|
len = strlen(line);
|
||||||
|
if(len < TELNETD_CONF_LINELEN - 2) {
|
||||||
|
line[len] = ISO_cr;
|
||||||
|
line[len+1] = ISO_nl;
|
||||||
|
line[len+2] = 0;
|
||||||
|
}
|
||||||
|
/* petsciiconv_toascii(line, TELNETD_CONF_LINELEN);*/
|
||||||
|
sendline(line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
void
|
||||||
|
telnetd_init(void)
|
||||||
|
{
|
||||||
|
uip_listen(HTONS(23));
|
||||||
|
shell_init();
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
acked(void)
|
||||||
|
{
|
||||||
|
static unsigned int i;
|
||||||
|
|
||||||
|
while(s.numsent > 0) {
|
||||||
|
free(s.lines[0]);
|
||||||
|
for(i = 1; i < TELNETD_CONF_NUMLINES; ++i) {
|
||||||
|
s.lines[i - 1] = s.lines[i];
|
||||||
|
}
|
||||||
|
s.lines[TELNETD_CONF_NUMLINES - 1] = NULL;
|
||||||
|
--s.numsent;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
senddata(void)
|
||||||
|
{
|
||||||
|
static char *bufptr, *lineptr;
|
||||||
|
static int buflen, linelen;
|
||||||
|
|
||||||
|
bufptr = uip_appdata;
|
||||||
|
buflen = 0;
|
||||||
|
for(s.numsent = 0; s.numsent < TELNETD_CONF_NUMLINES &&
|
||||||
|
s.lines[s.numsent] != NULL ; ++s.numsent) {
|
||||||
|
lineptr = s.lines[s.numsent];
|
||||||
|
linelen = strlen(lineptr);
|
||||||
|
if(linelen > TELNETD_CONF_LINELEN) {
|
||||||
|
linelen = TELNETD_CONF_LINELEN;
|
||||||
|
}
|
||||||
|
if(buflen + linelen < uip_mss()) {
|
||||||
|
memcpy(bufptr, lineptr, linelen);
|
||||||
|
bufptr += linelen;
|
||||||
|
buflen += linelen;
|
||||||
|
} else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
uip_send(uip_appdata, buflen);
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
closed(void)
|
||||||
|
{
|
||||||
|
static unsigned int i;
|
||||||
|
|
||||||
|
for(i = 0; i < TELNETD_CONF_NUMLINES; ++i) {
|
||||||
|
if(s.lines[i] != NULL) {
|
||||||
|
free(s.lines[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
get_char(uint8 c)
|
||||||
|
{
|
||||||
|
if(c == ISO_cr) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
s.buf[(int)s.bufptr] = c;
|
||||||
|
if(s.buf[(int)s.bufptr] == ISO_nl ||
|
||||||
|
s.bufptr == sizeof(s.buf) - 1) {
|
||||||
|
if(s.bufptr > 0) {
|
||||||
|
s.buf[(int)s.bufptr] = 0;
|
||||||
|
/* petsciiconv_topetscii(s.buf, TELNETD_CONF_LINELEN);*/
|
||||||
|
}
|
||||||
|
shell_input(s.buf);
|
||||||
|
s.bufptr = 0;
|
||||||
|
} else {
|
||||||
|
++s.bufptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
sendopt(uint8 option, uint8 value)
|
||||||
|
{
|
||||||
|
char *line;
|
||||||
|
line = (char*)malloc(TELNETD_CONF_LINELEN);
|
||||||
|
if(line != NULL) {
|
||||||
|
line[0] = TELNET_IAC;
|
||||||
|
line[1] = option;
|
||||||
|
line[2] = value;
|
||||||
|
line[3] = 0;
|
||||||
|
sendline(line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
|
static void
|
||||||
|
newdata(void)
|
||||||
|
{
|
||||||
|
uint16 len;
|
||||||
|
uint8 c;
|
||||||
|
char *dataptr;
|
||||||
|
|
||||||
|
|
||||||
|
len = uip_datalen();
|
||||||
|
dataptr = (char *)uip_appdata;
|
||||||
|
|
||||||
|
while(len > 0 && s.bufptr < sizeof(s.buf)) {
|
||||||
|
c = *dataptr;
|
||||||
|
++dataptr;
|
||||||
|
--len;
|
||||||
|
switch(s.state) {
|
||||||
|
case STATE_IAC:
|
||||||
|
if(c == TELNET_IAC) {
|
||||||
|
get_char(c);
|
||||||
|
s.state = STATE_NORMAL;
|
||||||
|
} else {
|
||||||
|
switch(c) {
|
||||||
|
case TELNET_WILL:
|
||||||
|
s.state = STATE_WILL;
|
||||||
|
break;
|
||||||
|
case TELNET_WONT:
|
||||||
|
s.state = STATE_WONT;
|
||||||
|
break;
|
||||||
|
case TELNET_DO:
|
||||||
|
s.state = STATE_DO;
|
||||||
|
break;
|
||||||
|
case TELNET_DONT:
|
||||||
|
s.state = STATE_DONT;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
s.state = STATE_NORMAL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case STATE_WILL:
|
||||||
|
/* Reply with a DONT */
|
||||||
|
sendopt(TELNET_DONT, c);
|
||||||
|
s.state = STATE_NORMAL;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case STATE_WONT:
|
||||||
|
/* Reply with a DONT */
|
||||||
|
sendopt(TELNET_DONT, c);
|
||||||
|
s.state = STATE_NORMAL;
|
||||||
|
break;
|
||||||
|
case STATE_DO:
|
||||||
|
/* Reply with a WONT */
|
||||||
|
sendopt(TELNET_WONT, c);
|
||||||
|
s.state = STATE_NORMAL;
|
||||||
|
break;
|
||||||
|
case STATE_DONT:
|
||||||
|
/* Reply with a WONT */
|
||||||
|
sendopt(TELNET_WONT, c);
|
||||||
|
s.state = STATE_NORMAL;
|
||||||
|
break;
|
||||||
|
case STATE_NORMAL:
|
||||||
|
if(c == TELNET_IAC) {
|
||||||
|
s.state = STATE_IAC;
|
||||||
|
} else {
|
||||||
|
get_char(c);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* This function is called by the UIP interrupt handling logic whenevent an
|
||||||
|
* event of interest occurs.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_interrupt_event(void)
|
||||||
|
{
|
||||||
|
static unsigned int i;
|
||||||
|
if(uip_connected()) {
|
||||||
|
/* tcp_markconn(uip_conn, &s);*/
|
||||||
|
for(i = 0; i < TELNETD_CONF_NUMLINES; ++i) {
|
||||||
|
s.lines[i] = NULL;
|
||||||
|
}
|
||||||
|
s.bufptr = 0;
|
||||||
|
s.state = STATE_NORMAL;
|
||||||
|
|
||||||
|
shell_start();
|
||||||
|
}
|
||||||
|
|
||||||
|
if(s.state == STATE_CLOSE) {
|
||||||
|
s.state = STATE_NORMAL;
|
||||||
|
uip_close();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(uip_closed() ||
|
||||||
|
uip_aborted() ||
|
||||||
|
uip_timedout()) {
|
||||||
|
closed();
|
||||||
|
}
|
||||||
|
|
||||||
|
if(uip_acked()) {
|
||||||
|
acked();
|
||||||
|
}
|
||||||
|
|
||||||
|
if(uip_newdata()) {
|
||||||
|
newdata();
|
||||||
|
}
|
||||||
|
|
||||||
|
if(uip_rexmit() ||
|
||||||
|
uip_newdata() ||
|
||||||
|
uip_acked() ||
|
||||||
|
uip_connected() ||
|
||||||
|
uip_poll()) {
|
||||||
|
senddata();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/*---------------------------------------------------------------------------*/
|
||||||
@@ -0,0 +1,53 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2003, Adam Dunkels.
|
||||||
|
* 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. 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __TELNETD_H__
|
||||||
|
#define __TELNETD_H__
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <net/uip/uipopt.h>
|
||||||
|
|
||||||
|
#ifndef TELNETD_CONF_LINELEN
|
||||||
|
#define TELNETD_CONF_LINELEN 40
|
||||||
|
#endif
|
||||||
|
#ifndef TELNETD_CONF_NUMLINES
|
||||||
|
#define TELNETD_CONF_NUMLINES 16
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct telnetd_state
|
||||||
|
{
|
||||||
|
char *lines[TELNETD_CONF_NUMLINES];
|
||||||
|
char buf[TELNETD_CONF_LINELEN];
|
||||||
|
char bufptr;
|
||||||
|
uint8 numsent;
|
||||||
|
uint8 state;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif /* __TELNETD_H__ */
|
||||||
@@ -0,0 +1,37 @@
|
|||||||
|
############################################################################
|
||||||
|
# Make.defs
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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.
|
||||||
|
#
|
||||||
|
############################################################################
|
||||||
|
|
||||||
|
UIPLIB_ASRCS =
|
||||||
|
UIPLIB_CSRCS = uiplib.c
|
||||||
@@ -0,0 +1,73 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2004, Adam Dunkels and the Swedish Institute of
|
||||||
|
* Computer Science.
|
||||||
|
* 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. 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 uIP TCP/IP stack
|
||||||
|
*
|
||||||
|
* $Id: uiplib.c,v 1.1.1.1 2007-08-26 23:07:05 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
|
||||||
|
#include "uiplib.h"
|
||||||
|
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
|
unsigned char
|
||||||
|
uiplib_ipaddrconv(char *addrstr, unsigned char *ipaddr)
|
||||||
|
{
|
||||||
|
unsigned char tmp;
|
||||||
|
char c;
|
||||||
|
unsigned char i, j;
|
||||||
|
|
||||||
|
tmp = 0;
|
||||||
|
|
||||||
|
for(i = 0; i < 4; ++i) {
|
||||||
|
j = 0;
|
||||||
|
do {
|
||||||
|
c = *addrstr;
|
||||||
|
++j;
|
||||||
|
if(j > 4) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
if(c == '.' || c == 0) {
|
||||||
|
*ipaddr = tmp;
|
||||||
|
++ipaddr;
|
||||||
|
tmp = 0;
|
||||||
|
} else if(c >= '0' && c <= '9') {
|
||||||
|
tmp = (tmp * 10) + (c - '0');
|
||||||
|
} else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
++addrstr;
|
||||||
|
} while(c != '.' && c != 0);
|
||||||
|
}
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*-----------------------------------------------------------------------------------*/
|
||||||
@@ -0,0 +1,71 @@
|
|||||||
|
/**
|
||||||
|
* \file
|
||||||
|
* Various uIP library functions.
|
||||||
|
* \author
|
||||||
|
* Adam Dunkels <adam@sics.se>
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2002, Adam Dunkels.
|
||||||
|
* 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. 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 uIP TCP/IP stack
|
||||||
|
*
|
||||||
|
* $Id: uiplib.h,v 1.1.1.1 2007-08-26 23:07:05 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#ifndef __UIPLIB_H__
|
||||||
|
#define __UIPLIB_H__
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \addtogroup uipconvfunc
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert a textual representation of an IP address to a numerical representation.
|
||||||
|
*
|
||||||
|
* This function takes a textual representation of an IP address in
|
||||||
|
* the form a.b.c.d and converts it into a 4-byte array that can be
|
||||||
|
* used by other uIP functions.
|
||||||
|
*
|
||||||
|
* \param addrstr A pointer to a string containing the IP address in
|
||||||
|
* textual form.
|
||||||
|
*
|
||||||
|
* \param addr A pointer to a 4-byte array that will be filled in with
|
||||||
|
* the numerical representation of the address.
|
||||||
|
*
|
||||||
|
* \retval 0 If the IP address could not be parsed.
|
||||||
|
* \retval Non-zero If the IP address was parsed.
|
||||||
|
*/
|
||||||
|
unsigned char uiplib_ipaddrconv(char *addrstr, unsigned char *addr);
|
||||||
|
|
||||||
|
/** @} */
|
||||||
|
|
||||||
|
#endif /* __UIPLIB_H__ */
|
||||||
@@ -0,0 +1,37 @@
|
|||||||
|
############################################################################
|
||||||
|
# Make.defs
|
||||||
|
#
|
||||||
|
# Copyright (C) 2007 Gregory Nutt. All rights reserved.
|
||||||
|
# Author: Gregory Nutt <spudmonkey@racsa.co.cr>
|
||||||
|
#
|
||||||
|
# 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.
|
||||||
|
#
|
||||||
|
############################################################################
|
||||||
|
|
||||||
|
WEBCLIENT_ASRCS =
|
||||||
|
WEBCLIENT_CSRCS = webclient-strings.c webclient.c
|
||||||
Executable
+40
@@ -0,0 +1,40 @@
|
|||||||
|
#!/usr/bin/perl
|
||||||
|
|
||||||
|
|
||||||
|
sub stringify {
|
||||||
|
my $name = shift(@_);
|
||||||
|
open(OUTPUTC, "> $name.c");
|
||||||
|
open(OUTPUTH, "> $name.h");
|
||||||
|
|
||||||
|
open(FILE, "$name");
|
||||||
|
|
||||||
|
while(<FILE>) {
|
||||||
|
if(/(.+) "(.+)"/) {
|
||||||
|
$var = $1;
|
||||||
|
$data = $2;
|
||||||
|
|
||||||
|
$datan = $data;
|
||||||
|
$datan =~ s/\\r/\r/g;
|
||||||
|
$datan =~ s/\\n/\n/g;
|
||||||
|
$datan =~ s/\\01/\01/g;
|
||||||
|
$datan =~ s/\\0/\0/g;
|
||||||
|
|
||||||
|
printf(OUTPUTC "const char $var\[%d] = \n", length($datan) + 1);
|
||||||
|
printf(OUTPUTC "/* \"$data\" */\n");
|
||||||
|
printf(OUTPUTC "{");
|
||||||
|
for($j = 0; $j < length($datan); $j++) {
|
||||||
|
printf(OUTPUTC "%#02x, ", unpack("C", substr($datan, $j, 1)));
|
||||||
|
}
|
||||||
|
printf(OUTPUTC "0 };\n");
|
||||||
|
|
||||||
|
printf(OUTPUTH "extern const char $var\[%d];\n", length($datan) + 1);
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
close(OUTPUTC);
|
||||||
|
close(OUTPUTH);
|
||||||
|
}
|
||||||
|
stringify("webclient-strings");
|
||||||
|
|
||||||
|
exit 0;
|
||||||
|
|
||||||
@@ -0,0 +1,31 @@
|
|||||||
|
http_http "http://"
|
||||||
|
http_200 "200 "
|
||||||
|
http_301 "301 "
|
||||||
|
http_302 "302 "
|
||||||
|
http_get "GET "
|
||||||
|
http_10 "HTTP/1.0"
|
||||||
|
http_11 "HTTP/1.1"
|
||||||
|
http_content_type "content-type: "
|
||||||
|
http_texthtml "text/html"
|
||||||
|
http_location "location: "
|
||||||
|
http_host "host: "
|
||||||
|
http_crnl "\r\n"
|
||||||
|
http_index_html "/index.html"
|
||||||
|
http_404_html "/404.html"
|
||||||
|
http_content_type_html "Content-type: text/html\r\n\r\n"
|
||||||
|
http_content_type_css "Content-type: text/css\r\n\r\n"
|
||||||
|
http_content_type_text "Content-type: text/text\r\n\r\n"
|
||||||
|
http_content_type_png "Content-type: image/png\r\n\r\n"
|
||||||
|
http_content_type_gif "Content-type: image/gif\r\n\r\n"
|
||||||
|
http_content_type_jpg "Content-type: image/jpeg\r\n\r\n"
|
||||||
|
http_content_type_binary "Content-type: application/octet-stream\r\n\r\n"
|
||||||
|
http_html ".html"
|
||||||
|
http_shtml ".shtml"
|
||||||
|
http_htm ".htm"
|
||||||
|
http_css ".css"
|
||||||
|
http_png ".png"
|
||||||
|
http_gif ".gif"
|
||||||
|
http_jpg ".jpg"
|
||||||
|
http_text ".text"
|
||||||
|
http_txt ".txt"
|
||||||
|
http_user_agent_fields "Connection: close\r\nUser-Agent: uIP/1.0 (; http://www.sics.se/~adam/uip/)\r\n\r\n"
|
||||||
@@ -0,0 +1,93 @@
|
|||||||
|
const char http_http[8] =
|
||||||
|
/* "http://" */
|
||||||
|
{0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0 };
|
||||||
|
const char http_200[5] =
|
||||||
|
/* "200 " */
|
||||||
|
{0x32, 0x30, 0x30, 0x20, 0 };
|
||||||
|
const char http_301[5] =
|
||||||
|
/* "301 " */
|
||||||
|
{0x33, 0x30, 0x31, 0x20, 0 };
|
||||||
|
const char http_302[5] =
|
||||||
|
/* "302 " */
|
||||||
|
{0x33, 0x30, 0x32, 0x20, 0 };
|
||||||
|
const char http_get[5] =
|
||||||
|
/* "GET " */
|
||||||
|
{0x47, 0x45, 0x54, 0x20, 0 };
|
||||||
|
const char http_10[9] =
|
||||||
|
/* "HTTP/1.0" */
|
||||||
|
{0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x30, 0 };
|
||||||
|
const char http_11[9] =
|
||||||
|
/* "HTTP/1.1" */
|
||||||
|
{0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x31, 0 };
|
||||||
|
const char http_content_type[15] =
|
||||||
|
/* "content-type: " */
|
||||||
|
{0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x3a, 0x20, 0 };
|
||||||
|
const char http_texthtml[10] =
|
||||||
|
/* "text/html" */
|
||||||
|
{0x74, 0x65, 0x78, 0x74, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0 };
|
||||||
|
const char http_location[11] =
|
||||||
|
/* "location: " */
|
||||||
|
{0x6c, 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0 };
|
||||||
|
const char http_host[7] =
|
||||||
|
/* "host: " */
|
||||||
|
{0x68, 0x6f, 0x73, 0x74, 0x3a, 0x20, 0 };
|
||||||
|
const char http_crnl[3] =
|
||||||
|
/* "\r\n" */
|
||||||
|
{0xd, 0xa, 0 };
|
||||||
|
const char http_index_html[12] =
|
||||||
|
/* "/index.html" */
|
||||||
|
{0x2f, 0x69, 0x6e, 0x64, 0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0 };
|
||||||
|
const char http_404_html[10] =
|
||||||
|
/* "/404.html" */
|
||||||
|
{0x2f, 0x34, 0x30, 0x34, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0 };
|
||||||
|
const char http_content_type_html[28] =
|
||||||
|
/* "Content-type: text/html\r\n\r\n" */
|
||||||
|
{0x43, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0xd, 0xa, 0xd, 0xa, 0 };
|
||||||
|
const char http_content_type_css [27] =
|
||||||
|
/* "Content-type: text/css\r\n\r\n" */
|
||||||
|
{0x43, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74, 0x2f, 0x63, 0x73, 0x73, 0xd, 0xa, 0xd, 0xa, 0 };
|
||||||
|
const char http_content_type_text[28] =
|
||||||
|
/* "Content-type: text/text\r\n\r\n" */
|
||||||
|
{0x43, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74, 0x2f, 0x74, 0x65, 0x78, 0x74, 0xd, 0xa, 0xd, 0xa, 0 };
|
||||||
|
const char http_content_type_png [28] =
|
||||||
|
/* "Content-type: image/png\r\n\r\n" */
|
||||||
|
{0x43, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x3a, 0x20, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x2f, 0x70, 0x6e, 0x67, 0xd, 0xa, 0xd, 0xa, 0 };
|
||||||
|
const char http_content_type_gif [28] =
|
||||||
|
/* "Content-type: image/gif\r\n\r\n" */
|
||||||
|
{0x43, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x3a, 0x20, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x2f, 0x67, 0x69, 0x66, 0xd, 0xa, 0xd, 0xa, 0 };
|
||||||
|
const char http_content_type_jpg [29] =
|
||||||
|
/* "Content-type: image/jpeg\r\n\r\n" */
|
||||||
|
{0x43, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x3a, 0x20, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x2f, 0x6a, 0x70, 0x65, 0x67, 0xd, 0xa, 0xd, 0xa, 0 };
|
||||||
|
const char http_content_type_binary[43] =
|
||||||
|
/* "Content-type: application/octet-stream\r\n\r\n" */
|
||||||
|
{0x43, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x3a, 0x20, 0x61, 0x70, 0x70, 0x6c, 0x69, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x2f, 0x6f, 0x63, 0x74, 0x65, 0x74, 0x2d, 0x73, 0x74, 0x72, 0x65, 0x61, 0x6d, 0xd, 0xa, 0xd, 0xa, 0 };
|
||||||
|
const char http_html[6] =
|
||||||
|
/* ".html" */
|
||||||
|
{0x2e, 0x68, 0x74, 0x6d, 0x6c, 0 };
|
||||||
|
const char http_shtml[7] =
|
||||||
|
/* ".shtml" */
|
||||||
|
{0x2e, 0x73, 0x68, 0x74, 0x6d, 0x6c, 0 };
|
||||||
|
const char http_htm[5] =
|
||||||
|
/* ".htm" */
|
||||||
|
{0x2e, 0x68, 0x74, 0x6d, 0 };
|
||||||
|
const char http_css[5] =
|
||||||
|
/* ".css" */
|
||||||
|
{0x2e, 0x63, 0x73, 0x73, 0 };
|
||||||
|
const char http_png[5] =
|
||||||
|
/* ".png" */
|
||||||
|
{0x2e, 0x70, 0x6e, 0x67, 0 };
|
||||||
|
const char http_gif[5] =
|
||||||
|
/* ".gif" */
|
||||||
|
{0x2e, 0x67, 0x69, 0x66, 0 };
|
||||||
|
const char http_jpg[5] =
|
||||||
|
/* ".jpg" */
|
||||||
|
{0x2e, 0x6a, 0x70, 0x67, 0 };
|
||||||
|
const char http_text[6] =
|
||||||
|
/* ".text" */
|
||||||
|
{0x2e, 0x74, 0x65, 0x78, 0x74, 0 };
|
||||||
|
const char http_txt[5] =
|
||||||
|
/* ".txt" */
|
||||||
|
{0x2e, 0x74, 0x78, 0x74, 0 };
|
||||||
|
const char http_user_agent_fields[77] =
|
||||||
|
/* "Connection: close\r\nUser-Agent: uIP/1.0 (; http://www.sics.se/~adam/uip/)\r\n\r\n" */
|
||||||
|
{0x43, 0x6f, 0x6e, 0x6e, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63, 0x6c, 0x6f, 0x73, 0x65, 0xd, 0xa, 0x55, 0x73, 0x65, 0x72, 0x2d, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x3a, 0x20, 0x75, 0x49, 0x50, 0x2f, 0x31, 0x2e, 0x30, 0x20, 0x28, 0x3b, 0x20, 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, 0x2e, 0x73, 0x69, 0x63, 0x73, 0x2e, 0x73, 0x65, 0x2f, 0x7e, 0x61, 0x64, 0x61, 0x6d, 0x2f, 0x75, 0x69, 0x70, 0x2f, 0x29, 0xd, 0xa, 0xd, 0xa, 0 };
|
||||||
@@ -0,0 +1,31 @@
|
|||||||
|
extern const char http_http[8];
|
||||||
|
extern const char http_200[5];
|
||||||
|
extern const char http_301[5];
|
||||||
|
extern const char http_302[5];
|
||||||
|
extern const char http_get[5];
|
||||||
|
extern const char http_10[9];
|
||||||
|
extern const char http_11[9];
|
||||||
|
extern const char http_content_type[15];
|
||||||
|
extern const char http_texthtml[10];
|
||||||
|
extern const char http_location[11];
|
||||||
|
extern const char http_host[7];
|
||||||
|
extern const char http_crnl[3];
|
||||||
|
extern const char http_index_html[12];
|
||||||
|
extern const char http_404_html[10];
|
||||||
|
extern const char http_content_type_html[28];
|
||||||
|
extern const char http_content_type_css [27];
|
||||||
|
extern const char http_content_type_text[28];
|
||||||
|
extern const char http_content_type_png [28];
|
||||||
|
extern const char http_content_type_gif [28];
|
||||||
|
extern const char http_content_type_jpg [29];
|
||||||
|
extern const char http_content_type_binary[43];
|
||||||
|
extern const char http_html[6];
|
||||||
|
extern const char http_shtml[7];
|
||||||
|
extern const char http_htm[5];
|
||||||
|
extern const char http_css[5];
|
||||||
|
extern const char http_png[5];
|
||||||
|
extern const char http_gif[5];
|
||||||
|
extern const char http_jpg[5];
|
||||||
|
extern const char http_text[6];
|
||||||
|
extern const char http_txt[5];
|
||||||
|
extern const char http_user_agent_fields[77];
|
||||||
@@ -0,0 +1,450 @@
|
|||||||
|
/* webclient.c
|
||||||
|
* Implementation of the HTTP client.
|
||||||
|
* Author: Adam Dunkels <adam@dunkels.com>
|
||||||
|
*
|
||||||
|
* This example shows a HTTP client that is able to download web pages
|
||||||
|
* and files from web servers. It requires a number of callback
|
||||||
|
* functions to be implemented by the module that utilizes the code:
|
||||||
|
* webclient_datahandler(), webclient_connected(),
|
||||||
|
* webclient_timedout(), webclient_aborted(), webclient_closed().
|
||||||
|
*
|
||||||
|
* Copyright (c) 2002, Adam Dunkels.
|
||||||
|
* 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. 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 uIP TCP/IP stack.
|
||||||
|
*
|
||||||
|
* $Id: webclient.c,v 1.1.1.1 2007-08-26 23:07:05 patacongo Exp $
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <net/uip/uip.h>
|
||||||
|
#include <net/uip/resolv.h>
|
||||||
|
|
||||||
|
#include "uiplib/uiplib.h"
|
||||||
|
#include "webclient.h"
|
||||||
|
|
||||||
|
#define WEBCLIENT_TIMEOUT 100
|
||||||
|
|
||||||
|
#define WEBCLIENT_STATE_STATUSLINE 0
|
||||||
|
#define WEBCLIENT_STATE_HEADERS 1
|
||||||
|
#define WEBCLIENT_STATE_DATA 2
|
||||||
|
#define WEBCLIENT_STATE_CLOSE 3
|
||||||
|
|
||||||
|
#define HTTPFLAG_NONE 0
|
||||||
|
#define HTTPFLAG_OK 1
|
||||||
|
#define HTTPFLAG_MOVED 2
|
||||||
|
#define HTTPFLAG_ERROR 3
|
||||||
|
|
||||||
|
|
||||||
|
#define ISO_nl 0x0a
|
||||||
|
#define ISO_cr 0x0d
|
||||||
|
#define ISO_space 0x20
|
||||||
|
|
||||||
|
|
||||||
|
static struct webclient_state s;
|
||||||
|
|
||||||
|
char *webclient_mimetype(void)
|
||||||
|
{
|
||||||
|
return s.mimetype;
|
||||||
|
}
|
||||||
|
|
||||||
|
char *webclient_filename(void)
|
||||||
|
{
|
||||||
|
return s.file;
|
||||||
|
}
|
||||||
|
|
||||||
|
char *webclient_hostname(void)
|
||||||
|
{
|
||||||
|
return s.host;
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned shortwebclient_port(void)
|
||||||
|
{
|
||||||
|
return s.port;
|
||||||
|
}
|
||||||
|
|
||||||
|
void webclient_init(void)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
static void init_connection(void)
|
||||||
|
{
|
||||||
|
s.state = WEBCLIENT_STATE_STATUSLINE;
|
||||||
|
|
||||||
|
s.getrequestleft = sizeof(http_get) - 1 + 1 +
|
||||||
|
sizeof(http_10) - 1 +
|
||||||
|
sizeof(http_crnl) - 1 +
|
||||||
|
sizeof(http_host) - 1 +
|
||||||
|
sizeof(http_crnl) - 1 +
|
||||||
|
strlen(http_user_agent_fields) +
|
||||||
|
strlen(s.file) + strlen(s.host);
|
||||||
|
s.getrequestptr = 0;
|
||||||
|
|
||||||
|
s.httpheaderlineptr = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void webclient_close(void)
|
||||||
|
{
|
||||||
|
s.state = WEBCLIENT_STATE_CLOSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned char webclient_get(char *host, uint16 port, char *file)
|
||||||
|
{
|
||||||
|
struct uip_conn *conn;
|
||||||
|
uip_ipaddr_t *ipaddr;
|
||||||
|
static uip_ipaddr_t addr;
|
||||||
|
|
||||||
|
/* First check if the host is an IP address. */
|
||||||
|
ipaddr = &addr;
|
||||||
|
if (uiplib_ipaddrconv(host, (unsigned char *)addr) == 0) {
|
||||||
|
ipaddr = (uip_ipaddr_t *)resolv_lookup(host);
|
||||||
|
|
||||||
|
if (ipaddr == NULL) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
conn = uip_connect(ipaddr, htons(port));
|
||||||
|
|
||||||
|
if (conn == NULL) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
s.port = port;
|
||||||
|
strncpy(s.file, file, sizeof(s.file));
|
||||||
|
strncpy(s.host, host, sizeof(s.host));
|
||||||
|
|
||||||
|
init_connection();
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static char *copy_string(char *dest, const char *src, int len)
|
||||||
|
{
|
||||||
|
strncpy(dest, src, len);
|
||||||
|
return dest + len;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void senddata(void)
|
||||||
|
{
|
||||||
|
uint16 len;
|
||||||
|
char *getrequest;
|
||||||
|
char *cptr;
|
||||||
|
|
||||||
|
if (s.getrequestleft > 0) {
|
||||||
|
cptr = getrequest = (char *)uip_appdata;
|
||||||
|
|
||||||
|
cptr = copy_string(cptr, http_get, sizeof(http_get) - 1);
|
||||||
|
cptr = copy_string(cptr, s.file, strlen(s.file));
|
||||||
|
*cptr++ = ISO_space;
|
||||||
|
cptr = copy_string(cptr, http_10, sizeof(http_10) - 1);
|
||||||
|
|
||||||
|
cptr = copy_string(cptr, http_crnl, sizeof(http_crnl) - 1);
|
||||||
|
|
||||||
|
cptr = copy_string(cptr, http_host, sizeof(http_host) - 1);
|
||||||
|
cptr = copy_string(cptr, s.host, strlen(s.host));
|
||||||
|
cptr = copy_string(cptr, http_crnl, sizeof(http_crnl) - 1);
|
||||||
|
|
||||||
|
cptr = copy_string(cptr, http_user_agent_fields,
|
||||||
|
strlen(http_user_agent_fields));
|
||||||
|
|
||||||
|
len = s.getrequestleft > uip_mss()?
|
||||||
|
uip_mss():
|
||||||
|
s.getrequestleft;
|
||||||
|
uip_send(&(getrequest[s.getrequestptr]), len);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void acked(void)
|
||||||
|
{
|
||||||
|
uint16 len;
|
||||||
|
|
||||||
|
if (s.getrequestleft > 0) {
|
||||||
|
len = s.getrequestleft > uip_mss()?
|
||||||
|
uip_mss():
|
||||||
|
s.getrequestleft;
|
||||||
|
s.getrequestleft -= len;
|
||||||
|
s.getrequestptr += len;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint16 parse_statusline(uint16 len)
|
||||||
|
{
|
||||||
|
char *cptr;
|
||||||
|
|
||||||
|
while(len > 0 && s.httpheaderlineptr < sizeof(s.httpheaderline))
|
||||||
|
{
|
||||||
|
char *pappdata = (char*)uip_appdata;
|
||||||
|
s.httpheaderline[s.httpheaderlineptr] = *pappdata++;
|
||||||
|
uip_appdata = (void*)pappdata;
|
||||||
|
len--;
|
||||||
|
|
||||||
|
if (s.httpheaderline[s.httpheaderlineptr] == ISO_nl)
|
||||||
|
{
|
||||||
|
if ((strncmp(s.httpheaderline, http_10, sizeof(http_10) - 1) == 0) ||
|
||||||
|
(strncmp(s.httpheaderline, http_11, sizeof(http_11) - 1) == 0))
|
||||||
|
{
|
||||||
|
cptr = &(s.httpheaderline[9]);
|
||||||
|
s.httpflag = HTTPFLAG_NONE;
|
||||||
|
if (strncmp(cptr, http_200, sizeof(http_200) - 1) == 0)
|
||||||
|
{
|
||||||
|
/* 200 OK */
|
||||||
|
s.httpflag = HTTPFLAG_OK;
|
||||||
|
}
|
||||||
|
else if (strncmp(cptr, http_301, sizeof(http_301) - 1) == 0 ||
|
||||||
|
strncmp(cptr, http_302, sizeof(http_302) - 1) == 0)
|
||||||
|
{
|
||||||
|
/* 301 Moved permanently or 302 Found. Location: header line
|
||||||
|
* will contain thw new location.
|
||||||
|
*/
|
||||||
|
|
||||||
|
s.httpflag = HTTPFLAG_MOVED;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
s.httpheaderline[s.httpheaderlineptr - 1] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
uip_abort();
|
||||||
|
webclient_aborted();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* We're done parsing the status line, so we reset the pointer
|
||||||
|
* and start parsing the HTTP headers.
|
||||||
|
*/
|
||||||
|
|
||||||
|
s.httpheaderlineptr = 0;
|
||||||
|
s.state = WEBCLIENT_STATE_HEADERS;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
++s.httpheaderlineptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
|
||||||
|
static char casecmp(char *str1, const char *str2, char len)
|
||||||
|
{
|
||||||
|
static char c;
|
||||||
|
|
||||||
|
while(len > 0) {
|
||||||
|
c = *str1;
|
||||||
|
/* Force lower-case characters. */
|
||||||
|
if (c & 0x40) {
|
||||||
|
c |= 0x20;
|
||||||
|
}
|
||||||
|
if (*str2 != c) {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
++str1;
|
||||||
|
++str2;
|
||||||
|
--len;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint16 parse_headers(uint16 len)
|
||||||
|
{
|
||||||
|
char *cptr;
|
||||||
|
static unsigned char i;
|
||||||
|
|
||||||
|
while(len > 0 && s.httpheaderlineptr < sizeof(s.httpheaderline))
|
||||||
|
{
|
||||||
|
char *pappdata = (char*)uip_appdata;
|
||||||
|
s.httpheaderline[s.httpheaderlineptr] = *pappdata++;
|
||||||
|
uip_appdata = (void*)pappdata;
|
||||||
|
len--;
|
||||||
|
|
||||||
|
if (s.httpheaderline[s.httpheaderlineptr] == ISO_nl)
|
||||||
|
{
|
||||||
|
/* We have an entire HTTP header line in s.httpheaderline, so
|
||||||
|
* we parse it.
|
||||||
|
*/
|
||||||
|
|
||||||
|
if (s.httpheaderline[0] == ISO_cr)
|
||||||
|
{
|
||||||
|
/* This was the last header line (i.e., and empty "\r\n"), so
|
||||||
|
* we are done with the headers and proceed with the actual
|
||||||
|
* data.
|
||||||
|
*/
|
||||||
|
|
||||||
|
s.state = WEBCLIENT_STATE_DATA;
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
|
||||||
|
s.httpheaderline[s.httpheaderlineptr - 1] = 0;
|
||||||
|
|
||||||
|
/* Check for specific HTTP header fields. */
|
||||||
|
if (casecmp(s.httpheaderline, http_content_type, sizeof(http_content_type) - 1) == 0)
|
||||||
|
{
|
||||||
|
/* Found Content-type field. */
|
||||||
|
cptr = strchr(s.httpheaderline, ';');
|
||||||
|
if (cptr != NULL)
|
||||||
|
{
|
||||||
|
*cptr = 0;
|
||||||
|
}
|
||||||
|
strncpy(s.mimetype, s.httpheaderline + sizeof(http_content_type) - 1, sizeof(s.mimetype));
|
||||||
|
}
|
||||||
|
else if (casecmp(s.httpheaderline, http_location, sizeof(http_location) - 1) == 0)
|
||||||
|
{
|
||||||
|
cptr = s.httpheaderline + sizeof(http_location) - 1;
|
||||||
|
|
||||||
|
if (strncmp(cptr, http_http, 7) == 0)
|
||||||
|
{
|
||||||
|
cptr += 7;
|
||||||
|
for(i = 0; i < s.httpheaderlineptr - 7; ++i)
|
||||||
|
{
|
||||||
|
if (*cptr == 0 || *cptr == '/' || *cptr == ' ' || *cptr == ':')
|
||||||
|
{
|
||||||
|
s.host[i] = 0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
s.host[i] = *cptr;
|
||||||
|
++cptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
strncpy(s.file, cptr, sizeof(s.file));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* We're done parsing, so we reset the pointer and start the
|
||||||
|
* next line.
|
||||||
|
*/
|
||||||
|
|
||||||
|
s.httpheaderlineptr = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
++s.httpheaderlineptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void newdata(void)
|
||||||
|
{
|
||||||
|
uint16 len;
|
||||||
|
|
||||||
|
len = uip_datalen();
|
||||||
|
|
||||||
|
if (s.state == WEBCLIENT_STATE_STATUSLINE) {
|
||||||
|
len = parse_statusline(len);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (s.state == WEBCLIENT_STATE_HEADERS && len > 0) {
|
||||||
|
len = parse_headers(len);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (len > 0 && s.state == WEBCLIENT_STATE_DATA &&
|
||||||
|
s.httpflag != HTTPFLAG_MOVED) {
|
||||||
|
webclient_datahandler((char *)uip_appdata, len);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* This function is called by the UIP interrupt handling logic whenevent an
|
||||||
|
* event of interest occurs.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void uip_interrupt_event(void)
|
||||||
|
{
|
||||||
|
if (uip_connected())
|
||||||
|
{
|
||||||
|
s.timer = 0;
|
||||||
|
s.state = WEBCLIENT_STATE_STATUSLINE;
|
||||||
|
senddata();
|
||||||
|
webclient_connected();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (s.state == WEBCLIENT_STATE_CLOSE)
|
||||||
|
{
|
||||||
|
webclient_closed();
|
||||||
|
uip_abort();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (uip_aborted())
|
||||||
|
{
|
||||||
|
webclient_aborted();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (uip_timedout())
|
||||||
|
{
|
||||||
|
webclient_timedout();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (uip_acked())
|
||||||
|
{
|
||||||
|
s.timer = 0;
|
||||||
|
acked();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (uip_newdata())
|
||||||
|
{
|
||||||
|
s.timer = 0;
|
||||||
|
newdata();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (uip_rexmit() || uip_newdata() || uip_acked())
|
||||||
|
{
|
||||||
|
senddata();
|
||||||
|
}
|
||||||
|
else if (uip_poll())
|
||||||
|
{
|
||||||
|
++s.timer;
|
||||||
|
if (s.timer == WEBCLIENT_TIMEOUT)
|
||||||
|
{
|
||||||
|
webclient_timedout();
|
||||||
|
uip_abort();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (uip_closed())
|
||||||
|
{
|
||||||
|
if (s.httpflag != HTTPFLAG_MOVED)
|
||||||
|
{
|
||||||
|
/* Send NULL data to signal EOF. */
|
||||||
|
webclient_datahandler(NULL, 0);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (resolv_lookup(s.host) == NULL)
|
||||||
|
{
|
||||||
|
resolv_query(s.host);
|
||||||
|
}
|
||||||
|
webclient_get(s.host, s.port, s.file);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user