diff --git a/examples/ipv6/z1-websense/Makefile b/examples/ipv6/z1-websense/Makefile new file mode 100644 index 000000000..cefb94f5d --- /dev/null +++ b/examples/ipv6/z1-websense/Makefile @@ -0,0 +1,24 @@ +all: sky-websense + +CONTIKI=../../.. + +WITH_UIP6=1 +UIP_CONF_IPV6=1 + +APPS += webserver webbrowser + +CFLAGS += -DPROJECT_CONF_H=1 +CONTIKI_SOURCEFILES += wget.c +PROJECTDIRS += ../rpl-border-router +PROJECT_SOURCEFILES += httpd-simple.c + +include $(CONTIKI)/Makefile.include + +$(CONTIKI)/tools/tunslip6: $(CONTIKI)/tools/tunslip6.c + (cd $(CONTIKI)/tools && $(MAKE) tunslip6) + +connect-router: $(CONTIKI)/tools/tunslip6 + sudo $(CONTIKI)/tools/tunslip6 aaaa::1/64 + +connect-router-cooja: $(CONTIKI)/tools/tunslip6 + sudo $(CONTIKI)/tools/tunslip6 -a 127.0.0.1 aaaa::1/64 diff --git a/examples/ipv6/z1-websense/Makefile.target b/examples/ipv6/z1-websense/Makefile.target new file mode 100644 index 000000000..ff66066d4 --- /dev/null +++ b/examples/ipv6/z1-websense/Makefile.target @@ -0,0 +1 @@ +TARGET = z1 diff --git a/examples/ipv6/z1-websense/README b/examples/ipv6/z1-websense/README new file mode 100644 index 000000000..c42235683 --- /dev/null +++ b/examples/ipv6/z1-websense/README @@ -0,0 +1,36 @@ +This example features a simple webserver running on top of the IPv6 +contiki stack on Sky motes to provide sensor values, and with a RPL +border router to bridge the sensor network to Internet. + + +To test the example in COOJA under Linux +---------------------------------------- + +1. Start COOJA and load the simulation "example-z1-websense.csc" +> make TARGET=cooja example-z1-websense.csc + +2. Connect to the COOJA simulation using tunslip6: +> make connect-router-cooja + +3. You should now be able to browse to the nodes using your web browser: + Router: http://[aaaa::0212:7401:0001:0101]/ + Node 2: http://[aaaa::0212:7402:0002:0202]/ + + +To run the example on real nodes under Linux +-------------------------------------------- + +1. Program the nodes with the websense application +> make TARGET=z1 z1-websense.upload + +2. Disconnect the nodes and program one node with the RPL border router +> (cd ../rpl-border-router && make TARGET=z1 border-router.upload) + +3. Connect to the border router using tunslip6: +> make connect-router + +4. Reboot the router and note the router IP address + +5. You should now be able to browse to your router node using your web + browser: http://[]/. On this page you should + see a list of all accessible nodes with their IP adresses. diff --git a/examples/ipv6/z1-websense/example-z1-websense.csc b/examples/ipv6/z1-websense/example-z1-websense.csc new file mode 100644 index 000000000..4a4268bc4 --- /dev/null +++ b/examples/ipv6/z1-websense/example-z1-websense.csc @@ -0,0 +1,207 @@ + + + [CONTIKI_DIR]/tools/cooja/apps/mrm + [CONTIKI_DIR]/tools/cooja/apps/mspsim + [CONTIKI_DIR]/tools/cooja/apps/avrora + [CONTIKI_DIR]/tools/cooja/apps/serial_socket + + Sky Websense with RPL router + 0 + 123456 + 1000000 + + se.sics.cooja.radiomediums.UDGM + 50.0 + 50.0 + 1.0 + 1.0 + + + 40000 + + + se.sics.cooja.mspmote.SkyMoteType + rplroot + Sky RPL Root + [CONTIKI_DIR]/examples/ipv6/rpl-border-router/border-router.c + make border-router.sky TARGET=sky + [CONTIKI_DIR]/examples/ipv6/rpl-border-router/border-router.sky + se.sics.cooja.interfaces.Position + se.sics.cooja.interfaces.RimeAddress + se.sics.cooja.interfaces.IPAddress + se.sics.cooja.interfaces.Mote2MoteRelations + se.sics.cooja.interfaces.MoteAttributes + se.sics.cooja.mspmote.interfaces.MspClock + se.sics.cooja.mspmote.interfaces.MspMoteID + se.sics.cooja.mspmote.interfaces.SkyButton + se.sics.cooja.mspmote.interfaces.SkyFlash + se.sics.cooja.mspmote.interfaces.SkyCoffeeFilesystem + se.sics.cooja.mspmote.interfaces.SkyByteRadio + se.sics.cooja.mspmote.interfaces.MspSerial + se.sics.cooja.mspmote.interfaces.SkyLED + se.sics.cooja.mspmote.interfaces.MspDebugOutput + se.sics.cooja.mspmote.interfaces.SkyTemperature + + + se.sics.cooja.mspmote.SkyMoteType + skyweb + Sky Websense + [CONTIKI_DIR]/examples/ipv6/sky-websense/sky-websense.c + make sky-websense.sky TARGET=sky + [CONTIKI_DIR]/examples/ipv6/sky-websense/sky-websense.sky + se.sics.cooja.interfaces.Position + se.sics.cooja.interfaces.RimeAddress + se.sics.cooja.interfaces.IPAddress + se.sics.cooja.interfaces.Mote2MoteRelations + se.sics.cooja.interfaces.MoteAttributes + se.sics.cooja.mspmote.interfaces.MspClock + se.sics.cooja.mspmote.interfaces.MspMoteID + se.sics.cooja.mspmote.interfaces.SkyButton + se.sics.cooja.mspmote.interfaces.SkyFlash + se.sics.cooja.mspmote.interfaces.SkyCoffeeFilesystem + se.sics.cooja.mspmote.interfaces.SkyByteRadio + se.sics.cooja.mspmote.interfaces.MspSerial + se.sics.cooja.mspmote.interfaces.SkyLED + se.sics.cooja.mspmote.interfaces.MspDebugOutput + se.sics.cooja.mspmote.interfaces.SkyTemperature + + + + + se.sics.cooja.interfaces.Position + 33.260163187353555 + 30.643217359962595 + 0.0 + + + se.sics.cooja.mspmote.interfaces.MspMoteID + 1 + + rplroot + + + + + se.sics.cooja.interfaces.Position + 62.239287566073514 + 34.43810269527116 + 0.0 + + + se.sics.cooja.mspmote.interfaces.MspMoteID + 2 + + skyweb + + + + + se.sics.cooja.interfaces.Position + 56.71945435107925 + 20.293530081848317 + 0.0 + + + se.sics.cooja.mspmote.interfaces.MspMoteID + 3 + + skyweb + + + + + se.sics.cooja.interfaces.Position + 75.34889145168493 + 24.43340499309403 + 0.0 + + + se.sics.cooja.mspmote.interfaces.MspMoteID + 4 + + skyweb + + + + + se.sics.cooja.interfaces.Position + 92.59837024854205 + 38.57797760651687 + 0.0 + + + se.sics.cooja.mspmote.interfaces.MspMoteID + 5 + + skyweb + + + + + se.sics.cooja.interfaces.Position + 47.68359039801751 + 47.26544238238854 + 0.0 + + + se.sics.cooja.mspmote.interfaces.MspMoteID + 6 + + skyweb + + + + se.sics.cooja.plugins.SimControl + 259 + 4 + 179 + 0 + 0 + + + se.sics.cooja.plugins.Visualizer + + se.sics.cooja.plugins.skins.IDVisualizerSkin + se.sics.cooja.plugins.skins.UDGMVisualizerSkin + se.sics.cooja.plugins.skins.MoteTypeVisualizerSkin + 2.898638306051894 0.0 0.0 2.898638306051894 -68.40918308040007 -27.82360366026197 + + 258 + 2 + 209 + 0 + 178 + + + se.sics.cooja.plugins.LogListener + + + + 1024 + 3 + 311 + 0 + 385 + + + se.sics.cooja.plugins.RadioLogger + + 150 + + + 769 + 0 + 342 + 255 + -1 + + + SerialSocketServer + 0 + 422 + 1 + 74 + 601 + 310 + + diff --git a/examples/ipv6/z1-websense/project-conf.h b/examples/ipv6/z1-websense/project-conf.h new file mode 100644 index 000000000..ecfad3a69 --- /dev/null +++ b/examples/ipv6/z1-websense/project-conf.h @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2010, 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. + * + * $Id: project-conf.h,v 1.1 2010/11/03 15:46:41 adamdunkels Exp $ + */ + +#ifndef __PROJECT_RPL_WEB_CONF_H__ +#define __PROJECT_RPL_WEB_CONF_H__ + +#undef QUEUEBUF_CONF_NUM +#define QUEUEBUF_CONF_NUM 6 + +#undef UIP_CONF_BUFFER_SIZE +#define UIP_CONF_BUFFER_SIZE 140 + +#undef UIP_CONF_RECEIVE_WINDOW +#define UIP_CONF_RECEIVE_WINDOW 60 + +#undef WEBSERVER_CONF_CFS_CONNS +#define WEBSERVER_CONF_CFS_CONNS 2 + +#endif /* __PROJECT_RPL_WEB_CONF_H__ */ diff --git a/examples/ipv6/z1-websense/websense-remote.c b/examples/ipv6/z1-websense/websense-remote.c new file mode 100644 index 000000000..aad3022f7 --- /dev/null +++ b/examples/ipv6/z1-websense/websense-remote.c @@ -0,0 +1,174 @@ +/* + * Copyright (c) 2010, 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. + * + * $Id: websense-remote.c,v 1.2 2010/06/14 14:12:43 nifi Exp $ + */ + +/** + * \file + * A simple example using HTTP to control and be controlled + * \author + * Niclas Finne + * Joakim Eriksson + */ + +#include "contiki.h" +#include "dev/button-sensor.h" +#include "dev/leds.h" +#include "wget.h" +#include "webserver-nogui.h" +#include "httpd-simple.h" +#include + +/* The address of the server to register the services for this node */ +#define SERVER "aaaa::1" + +/* This command registers two services (/0 and /1) to turn the leds on or off */ +#define REGISTER_COMMAND "/r?p=0&d=Turn%20off%20leds&p=1&d=Turn%20on%20leds" + +/* The address of the other node to control */ +#define OTHER_NODE "aaaa::212:7403:3:303" + +/* The commands to send to the other node */ +#define SET_LEDS_ON "/1" +#define SET_LEDS_OFF "/0" + +PROCESS(websense_remote_process, "Websense Remote"); + +AUTOSTART_PROCESSES(&websense_remote_process); + +/*---------------------------------------------------------------------------*/ +static const char *TOP = "Contiki Websense Remote\n"; +static const char *BOTTOM = "\n"; +/*---------------------------------------------------------------------------*/ +static +PT_THREAD(handle_command(struct httpd_state *s)) +{ + PSOCK_BEGIN(&s->sout); + + SEND_STRING(&s->sout, TOP); + + if(s->filename[1] == '0') { + /* Turn off leds */ + leds_off(LEDS_ALL); + SEND_STRING(&s->sout, "Turned off leds!"); + } else if(s->filename[1] == '1') { + /* Turn on leds */ + leds_on(LEDS_ALL); + SEND_STRING(&s->sout, "Turned on leds!"); + } else { + SEND_STRING(&s->sout, "Unknown command"); + } + + SEND_STRING(&s->sout, BOTTOM); + + PSOCK_END(&s->sout); +} +/*---------------------------------------------------------------------------*/ +httpd_simple_script_t +httpd_simple_get_script(const char *name) +{ + return handle_command; +} +/*---------------------------------------------------------------------------*/ +static void +wget_done(int status) +{ + switch(status) { + case WGET_OK: + printf("Command sent.\n"); + break; + case WGET_TIMEDOUT: + printf("Command timedout.\n"); + break; + case WGET_ABORTED: + printf("Connection aborted.\n"); + break; + case WGET_CONNECT_FAILED: + printf("Failed to connect.\n"); + break; + } +} +static const struct wget_callbacks callbacks = { + NULL, wget_done +}; +static void +send_command(const char *server, const char *command) +{ + int ret; + printf("Sending to [%s]: %s\n", server, command); + ret = wget_get(server, 80, command, &callbacks); + if(ret != WGET_OK) { + if(ret == WGET_ALREADY_RUNNING) { + printf("Waiting for previous command to finish.\n"); + } else { + printf("Failed to send command: %u\n", ret); + } + } +} +/*---------------------------------------------------------------------------*/ +PROCESS_THREAD(websense_remote_process, ev, data) +{ + static int mode; + static struct etimer timer; + + PROCESS_BEGIN(); + + mode = 0; + wget_init(); + process_start(&webserver_nogui_process, NULL); + + SENSORS_ACTIVATE(button_sensor); + + /* Give the node some time to join the network before registering + the available services. */ + etimer_set(&timer, CLOCK_SECOND * 30); + + while(1) { + PROCESS_WAIT_EVENT(); + + if(ev == sensors_event && data == &button_sensor) { + /* The button has been pressed. Send command to the other node. */ + if(mode) { + /* Turn on leds */ + send_command(OTHER_NODE, SET_LEDS_OFF); + } else { + send_command(OTHER_NODE, SET_LEDS_ON); + } + /* Alternate between the two commands */ + mode = !mode; + + } else if(ev == PROCESS_EVENT_TIMER && etimer_expired(&timer)) { + printf("Registering services\n"); + send_command(SERVER, REGISTER_COMMAND); + } + } + + PROCESS_END(); +} +/*---------------------------------------------------------------------------*/ diff --git a/examples/ipv6/z1-websense/wget.c b/examples/ipv6/z1-websense/wget.c new file mode 100644 index 000000000..cf28758a1 --- /dev/null +++ b/examples/ipv6/z1-websense/wget.c @@ -0,0 +1,204 @@ +/* + * Copyright (c) 2010, 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. + * + * $Id: wget.c,v 1.2 2010/06/14 14:12:43 nifi Exp $ + */ + +/** + * \file + * A simple wget implementation + * \author + * Niclas Finne + * Joakim Eriksson + */ + +#include "webclient.h" +#include "wget.h" +#include "dev/leds.h" + +#define DEBUG DEBUG_NONE +#include "net/uip-debug.h" + +#define DEBUG_LEDS 0 +#undef LEDS_ON +#undef LEDS_OFF +#if DEBUG_LEDS +#define LEDS_ON(led) leds_on(led) +#define LEDS_OFF(led) leds_off(led) +#else +#define LEDS_ON(led) +#define LEDS_OFF(led) +#endif /* DEBUG */ + +static int fetch_running; + +#define STATS ((DEBUG) & DEBUG_PRINT) && 1 +#if STATS +static clock_time_t fetch_started; +static unsigned long fetch_counter; +#endif /* STATUS */ + +static const char *server; +static const char *file; +static uint16_t port; +static const struct wget_callbacks *callbacks; + +PROCESS(wget_process, "wget"); + +/*---------------------------------------------------------------------------*/ +static void +call_done(int status) +{ + if(callbacks != NULL && callbacks->done != NULL) { + callbacks->done(status); + } +} +/*---------------------------------------------------------------------------*/ +PROCESS_THREAD(wget_process, ev, data) +{ + PROCESS_BEGIN(); + + PRINTF("wget: fetching %s\n", file); +#if STATS + fetch_counter = 0; + fetch_started = clock_time(); +#endif /* STATS */ + LEDS_ON(LEDS_YELLOW); + if(webclient_get(server, port, file) == 0) { + PRINTF("wget: failed to connect\n"); + LEDS_OFF(LEDS_YELLOW); + fetch_running = 0; + call_done(WGET_CONNECT_FAILED); + } else { + while(fetch_running) { + PROCESS_WAIT_EVENT(); + if(ev == tcpip_event) { + webclient_appcall(data); + } + } + } + + PROCESS_END(); +} +/*---------------------------------------------------------------------------*/ +void +webclient_datahandler(char *data, u16_t len) +{ + if(len == 0) { +#if STATS + clock_time_t elapsed; + elapsed = clock_time() - fetch_started; + PRINTF("wget: recv %lu bytes during %lu sec (", + fetch_counter, (elapsed / CLOCK_SECOND)); +#if CLOCK_SECOND == 128 + PRINTF("%lu.%02lus, ", (unsigned long) elapsed >> 7, + (unsigned long)((elapsed & 127) * 100) / 128); + PRINTF("%lu byte/sec ", (fetch_counter * 128L) / elapsed); +#endif + PRINTF("%lu tick): ", (unsigned long) elapsed); + if(elapsed > CLOCK_SECOND) { + PRINTF("%lu", fetch_counter / (elapsed / CLOCK_SECOND)); + } else { + PRINTF("-"); + } + PRINTF(" byte/sec\n"); +#else /* STATS */ + PRINTF("wget: complete\n"); +#endif /* STATS */ + + fetch_running = 0; + call_done(WGET_OK); + LEDS_OFF(LEDS_RED|LEDS_YELLOW); + } else { +#if STATS + fetch_counter += len; +#endif /* STATS */ + if(callbacks != NULL && callbacks->data != NULL) { + /* Assume the buffer is large enough for ending zero */ + data[len] = '\0'; + callbacks->data(data, len); + } + } +} +/*---------------------------------------------------------------------------*/ +void +webclient_connected(void) +{ + LEDS_OFF(LEDS_YELLOW); + LEDS_ON(LEDS_RED); +} +/*---------------------------------------------------------------------------*/ +void +webclient_timedout(void) +{ + PRINTF("wget: timedout\n"); + LEDS_OFF(LEDS_RED|LEDS_YELLOW); + fetch_running = 0; + call_done(WGET_TIMEDOUT); +} +/*---------------------------------------------------------------------------*/ +void +webclient_aborted(void) +{ + PRINTF("wget: aborted\n"); + LEDS_OFF(LEDS_RED|LEDS_YELLOW); + fetch_running = 0; + call_done(WGET_ABORTED); +} +/*---------------------------------------------------------------------------*/ +void +webclient_closed(void) +{ + PRINTF("wget: closed\n"); + fetch_running = 0; + LEDS_OFF(LEDS_RED|LEDS_YELLOW); + call_done(WGET_CLOSED); +} +/*---------------------------------------------------------------------------*/ +void +wget_init(void) +{ + webclient_init(); +} +/*---------------------------------------------------------------------------*/ +int +wget_get(const char *s, uint16_t p, const char *f, + const struct wget_callbacks *c) +{ + if(fetch_running) { + return WGET_ALREADY_RUNNING; + } + fetch_running = 1; + server = s; + port = p; + file = f; + callbacks = c; + process_start(&wget_process, NULL); + return WGET_OK; +} +/*---------------------------------------------------------------------------*/ diff --git a/examples/ipv6/z1-websense/wget.h b/examples/ipv6/z1-websense/wget.h new file mode 100644 index 000000000..c5b023def --- /dev/null +++ b/examples/ipv6/z1-websense/wget.h @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2010, 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. + * + * $Id: wget.h,v 1.2 2010/06/14 14:12:43 nifi Exp $ + */ + +/** + * \file + * A simple wget implementation + * \author + * Niclas Finne + * Joakim Eriksson + */ + +#ifndef __WGET_H__ +#define __WGET_H__ + +#include "contiki.h" + +struct wget_callbacks { + void (* data)(const char *data, uint16_t len); + void (* done)(int status); +}; + +void wget_init(void); +int wget_get(const char *server, uint16_t port, const char *file, + const struct wget_callbacks *c); + +enum { + WGET_OK, + WGET_ALREADY_RUNNING, + WGET_TIMEDOUT, + WGET_ABORTED, + WGET_CONNECT_FAILED, + WGET_CLOSED +}; + +#endif /* __WGET_H__ */ diff --git a/examples/ipv6/z1-websense/z1-websense.c b/examples/ipv6/z1-websense/z1-websense.c new file mode 100644 index 000000000..9220d43b9 --- /dev/null +++ b/examples/ipv6/z1-websense/z1-websense.c @@ -0,0 +1,177 @@ +/* + * Copyright (c) 2010, 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. + * + * $Id: sky-websense.c,v 1.3 2010/06/08 13:27:06 nifi Exp $ + */ + +/** + * \file + * Light and temperatur sensor web demo + * \author + * Niclas Finne + * Joakim Eriksson + * Joel Hoglund + */ + +#include "contiki.h" +#include "httpd-simple.h" +#include "webserver-nogui.h" +//#include "dev/sht11-sensor.h" +//#include "dev/light-sensor.h" + #include "dev/temperature-sensor.h" + #include "dev/battery-sensor.h" + #include "dev/cc2420.h" +#include "dev/leds.h" +#include + + +PROCESS(web_sense_process, "Sense Web Demo"); + +AUTOSTART_PROCESSES(&web_sense_process); + +#define HISTORY 16 +static int temperature[HISTORY]; +static int battery1[HISTORY]; +static int sensors_pos; + +/*---------------------------------------------------------------------------*/ +static int +get_battery(void) +{ + //return 10 * light_sensor.value(LIGHT_SENSOR_PHOTOSYNTHETIC) / 7; + return battery_sensor.value(0); +} +/*---------------------------------------------------------------------------*/ +static int +get_temp(void) +{ + //return ((sht11_sensor.value(SHT11_SENSOR_TEMP) / 10) - 396) / 10; + return temperature_sensor.value(0); +} +/*---------------------------------------------------------------------------*/ +static const char *TOP = "Contiki Web Sense\n"; +static const char *BOTTOM = "\n"; +/*---------------------------------------------------------------------------*/ +/* Only one single request at time */ +static char buf[256]; +static int blen; +#define ADD(...) do { \ + blen += snprintf(&buf[blen], sizeof(buf) - blen, __VA_ARGS__); \ + } while(0) +static void +generate_chart(const char *title, const char *unit, int min, int max, int *values) +{ + int i; + blen = 0; + ADD("

%s

\n" + " 0 ? "," : "", values[(sensors_pos + i) % HISTORY]); + } + ADD("\">"); +} +static +PT_THREAD(send_values(struct httpd_state *s)) +{ + PSOCK_BEGIN(&s->sout); + + SEND_STRING(&s->sout, TOP); + + if(strncmp(s->filename, "/index", 6) == 0 || + s->filename[1] == '\0') { + /* Default page: show latest sensor values as text (does not + require Internet connection to Google for charts). */ + blen = 0; + ADD("

Current readings

\n" + "Battery: %u
" + "Temperature: %u° C", + get_battery(), get_temp()); + SEND_STRING(&s->sout, buf); + + } else if(s->filename[1] == '0') { + /* Turn off leds */ + leds_off(LEDS_ALL); + SEND_STRING(&s->sout, "Turned off leds!"); + + } else if(s->filename[1] == '1') { + /* Turn on leds */ + leds_on(LEDS_ALL); + SEND_STRING(&s->sout, "Turned on leds!"); + + } else { + if(s->filename[1] != 't') { + generate_chart("Battery", "Battery", 0, 5000, battery1); + SEND_STRING(&s->sout, buf); + } + if(s->filename[1] != 'l') { + generate_chart("Temperature", "Celsius", 0, 50, temperature); + SEND_STRING(&s->sout, buf); + } + } + + SEND_STRING(&s->sout, BOTTOM); + + PSOCK_END(&s->sout); +} +/*---------------------------------------------------------------------------*/ +httpd_simple_script_t +httpd_simple_get_script(const char *name) +{ + return send_values; +} +/*---------------------------------------------------------------------------*/ +PROCESS_THREAD(web_sense_process, ev, data) +{ + static struct etimer timer; + PROCESS_BEGIN(); + cc2420_set_txpower(3); + + sensors_pos = 0; + process_start(&webserver_nogui_process, NULL); + + etimer_set(&timer, CLOCK_SECOND * 2); + //SENSORS_ACTIVATE(light_sensor); + //SENSORS_ACTIVATE(sht11_sensor); + SENSORS_ACTIVATE(battery_sensor); + SENSORS_ACTIVATE(temperature_sensor); + + while(1) { + PROCESS_WAIT_EVENT_UNTIL(etimer_expired(&timer)); + etimer_reset(&timer); + + battery1[sensors_pos] = get_battery();; + temperature[sensors_pos] = get_temp(); + sensors_pos = (sensors_pos + 1) % HISTORY; + } + + PROCESS_END(); +} +/*---------------------------------------------------------------------------*/ diff --git a/platform/z1/dev/temperature-sensor.h b/platform/z1/dev/temperature-sensor.h new file mode 100644 index 000000000..174612b17 --- /dev/null +++ b/platform/z1/dev/temperature-sensor.h @@ -0,0 +1,50 @@ +/* + * Copyright (c) 2010, 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. + * + * @(#)$Id: temperature-sensor.h,v 1.1 2010/08/25 19:34:07 nifi Exp $ + */ + +/** + * \file + * Temperature sensor header file. + * \author + * Adam Dunkels + * Joakim Eriksson + * Niclas Finne + */ + +#ifndef __TEMPERATURE_SENSOR_H__ +#define __TEMPERATURE_SENSOR_H__ + +#include "lib/sensors.h" + +extern const struct sensors_sensor temperature_sensor; + +#define TEMPERATURE_SENSOR "Temperature" + +#endif /* __TEMPERATURE_SENSOR_H__ */