Contiki 2.6

contiki-raven-main.c

Go to the documentation of this file.
00001 /*
00002  * Copyright (c) 2006, Technical University of Munich
00003  * All rights reserved.
00004  *
00005  * Redistribution and use in source and binary forms, with or without
00006  * modification, are permitted provided that the following conditions
00007  * are met:
00008  * 1. Redistributions of source code must retain the above copyright
00009  *    notice, this list of conditions and the following disclaimer.
00010  * 2. Redistributions in binary form must reproduce the above copyright
00011  *    notice, this list of conditions and the following disclaimer in the
00012  *    documentation and/or other materials provided with the distribution.
00013  * 3. Neither the name of the Institute nor the names of its contributors
00014  *    may be used to endorse or promote products derived from this software
00015  *    without specific prior written permission.
00016  *
00017  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
00018  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00019  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00020  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
00021  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
00022  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
00023  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
00024  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
00025  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
00026  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
00027  * SUCH DAMAGE.
00028  *
00029  * This file is part of the Contiki operating system.
00030  *
00031  * @(#)$$
00032  */
00033 
00034 /**
00035  * \file
00036  *         Contiki 2.4 kernel for Jackdaw USB stick
00037  *
00038  * \author
00039  *         Simon Barner <barner@in.tum.de>
00040  *         David Kopf <dak664@embarqmail.com>
00041  */
00042 
00043 #define DEBUG 0
00044 #if DEBUG
00045 #define PRINTD(FORMAT,args...) printf_P(PSTR(FORMAT),##args)
00046 #else
00047 #define PRINTD(...)
00048 #endif
00049 
00050 #include <avr/pgmspace.h>
00051 #include <avr/fuse.h>
00052 #include <avr/eeprom.h>
00053 #include <avr/wdt.h>
00054 #include <util/delay.h>
00055 #include <stdio.h>
00056 #include <string.h>
00057 
00058 #include "lib/mmem.h"
00059 #include "loader/symbols-def.h"
00060 #include "loader/symtab.h"
00061 
00062 #include "contiki.h"
00063 #include "contiki-net.h"
00064 #include "contiki-lib.h"
00065 #include "contiki-raven.h"
00066 
00067 /* Set ANNOUNCE to send boot messages to USB or RS232 serial port */
00068 #define ANNOUNCE 1
00069 
00070 /* But only if a serial port exists */
00071 #if USB_CONF_SERIAL||USB_CONF_RS232
00072 #define PRINTA(FORMAT,args...) printf_P(PSTR(FORMAT),##args)
00073 #else
00074 #define PRINTA(...)
00075 #endif
00076 
00077 #include "usb_task.h"
00078 #if USB_CONF_SERIAL
00079 #include "cdc_task.h"
00080 #endif
00081 #if USB_CONF_RS232
00082 #include "dev/rs232.h"
00083 #endif
00084 
00085 #include "rndis/rndis_task.h"
00086 #if USB_CONF_STORAGE
00087 #include "storage/storage_task.h"
00088 #endif
00089 
00090 #include "dev/watchdog.h"
00091 #include "dev/usb/usb_drv.h"
00092 
00093 #if JACKDAW_CONF_USE_SETTINGS
00094 #include "settings.h"
00095 #endif
00096 
00097 #if RF230BB           //radio driver using contiki core mac
00098 #include "radio/rf230bb/rf230bb.h"
00099 #include "net/mac/frame802154.h"
00100 #define UIP_IP_BUF ((struct uip_ip_hdr *)&uip_buf[UIP_LLH_LEN])
00101 rimeaddr_t macLongAddr;
00102 #define tmp_addr        macLongAddr
00103 #else                 //legacy radio driver using Atmel/Cisco 802.15.4'ish MAC
00104 #include <stdbool.h>
00105 #include "mac.h"
00106 #include "sicslowmac.h"
00107 #include "sicslowpan.h"
00108 #include "ieee-15-4-manager.h"
00109 #endif /* RF230BB */
00110 
00111 /* Test rtimers, also useful for pings, time stamps, routes, stack monitor */
00112 #define TESTRTIMER 0
00113 #if TESTRTIMER
00114 #define PINGS 0
00115 #define STAMPS 60
00116 #define ROUTES 120
00117 #define STACKMONITOR  600
00118 uint8_t rtimerflag=1;
00119 uint16_t rtime;
00120 struct rtimer rt;
00121 void rtimercycle(void) {rtimerflag=1;}
00122 #endif /* TESTRTIMER */
00123 
00124 #if UIP_CONF_IPV6_RPL
00125 /*---------------------------------------------------------------------------*/
00126 /*---------------------------------  RPL   ----------------------------------*/
00127 /*---------------------------------------------------------------------------*/
00128 /* TODO: Put rpl code into another file, once it stabilizes                  */
00129 /* Set up fallback interface links to direct stack tcpip output to ethernet  */
00130 static void
00131 init(void)
00132 {
00133 }
00134 void mac_LowpanToEthernet(void);
00135 static void
00136 output(void)
00137 {
00138 //  if(uip_ipaddr_cmp(&last_sender, &UIP_IP_BUF->srcipaddr)) {
00139     /* Do not bounce packets back over USB if the packet was received from USB */
00140 //    PRINTA("JACKDAW router: Destination off-link but no route\n");
00141  // } else {
00142     PRINTD("SUT: %u\n", uip_len);
00143     mac_LowpanToEthernet();  //bounceback trap is done in lowpanToEthernet
00144 //  }
00145 }
00146 const struct uip_fallback_interface rpl_interface = {
00147   init, output
00148 };
00149 
00150 #if RPL_BORDER_ROUTER
00151 #include "net/rpl/rpl.h"
00152 
00153 // avr-objdump --section .bss -x ravenusbstick.elf
00154 const uint16_t dag_id[] PROGMEM = {0x1111, 0x1100, 0, 0, 0, 0, 0, 0x0011};
00155 
00156 PROCESS(border_router_process, "RPL Border Router");
00157 PROCESS_THREAD(border_router_process, ev, data)
00158 {
00159 
00160   PROCESS_BEGIN();
00161 
00162   PROCESS_PAUSE();
00163 
00164 { rpl_dag_t *dag;
00165   char buf[sizeof(dag_id)];
00166   memcpy_P(buf,dag_id,sizeof(dag_id));
00167   dag = rpl_set_root(RPL_DEFAULT_INSTANCE,(uip_ip6addr_t *)buf);
00168 
00169 /* Assign separate addresses to the jackdaw uip stack and the host network interface, but with the same prefix */
00170 /* E.g. bbbb::200 to the jackdaw and bbbb::1 to the host network interface with $ip -6 address add bbbb::1/64 dev usb0 */
00171 /* Otherwise the host will trap packets intended for the jackdaw, just as the jackdaw will trap RF packets intended for the host */
00172 /* $ifconfig usb0 -arp on Ubuntu to skip the neighbor solicitations. Add explicit neighbors on other OSs */
00173   if(dag != NULL) {
00174     PRINTD("created a new RPL dag\n");
00175 
00176 #if UIP_CONF_ROUTER_RECEIVE_RA
00177 //Contiki stack will shut down until assigned an address from the interface RA
00178 //Currently this requires changes in the core rpl-icmp6.c to pass the link-local RA broadcast
00179 
00180 #else
00181     uip_ip6addr_t ipaddr;
00182     uip_ip6addr(&ipaddr, 0xbbbb, 0, 0, 0, 0, 0, 0, 0x200);
00183     uip_ds6_addr_add(&ipaddr, 0, ADDR_MANUAL);
00184     rpl_set_prefix(dag, &ipaddr, 64);
00185 #endif
00186   }
00187 }
00188   /* The border router runs with a 100% duty cycle in order to ensure high
00189      packet reception rates. */
00190  // NETSTACK_MAC.off(1);
00191 
00192   while(1) {
00193     PROCESS_YIELD();
00194     /* Local and global dag repair can be done from the jackdaw menu */
00195 
00196   }
00197 
00198   PROCESS_END();
00199 }
00200 #endif /* RPL_BORDER_ROUTER */
00201 
00202 #endif /* UIP_CONF_IPV6_RPL */
00203 
00204 /*-------------------------------------------------------------------------*/
00205 /*----------------------Configuration of the .elf file---------------------*/
00206 #if 1
00207 /* The proper way to set the signature is */
00208 #include <avr/signature.h>
00209 #else
00210 /* Older avr-gcc's may not define the needed SIGNATURE bytes. Do it manually if you get an error */
00211 typedef struct {const unsigned char B2;const unsigned char B1;const unsigned char B0;} __signature_t;
00212 #define SIGNATURE __signature_t __signature __attribute__((section (".signature")))
00213 SIGNATURE = {
00214   .B2 = 0x82,//SIGNATURE_2, //AT90USB128x
00215   .B1 = 0x97,//SIGNATURE_1, //128KB flash
00216   .B0 = 0x1E,//SIGNATURE_0, //Atmel
00217 };
00218 #endif
00219 
00220 FUSES ={.low = 0xde, .high = 0x99, .extended = 0xff,};
00221 
00222 /* Save the default settings into program flash memory */
00223 const uint8_t default_mac_address[8] PROGMEM = {0x02, 0x12, 0x13, 0xff, 0xfe, 0x14, 0x15, 0x16};
00224 #ifdef CHANNEL_802_15_4
00225 const uint8_t default_channel PROGMEM = CHANNEL_802_15_4;
00226 #else
00227 const uint8_t default_channel PROGMEM = 26;
00228 #endif
00229 #ifdef IEEE802154_PANID
00230 const uint16_t default_panid PROGMEM = IEEE802154_PANID;
00231 #else
00232 const uint16_t default_panid PROGMEM = 0xABCD;
00233 #endif
00234 #ifdef IEEE802154_PANADDR
00235 const uint16_t default_panaddr PROGMEM = IEEE802154_PANID;
00236 #else
00237 const uint16_t default_panaddr PROGMEM = 0;
00238 #endif
00239 #ifdef RF230_MAX_TX_POWER
00240 const uint8_t default_txpower PROGMEM = RF230_MAX_TX_POWER;
00241 #else
00242 const uint8_t default_txpower PROGMEM = 0;
00243 #endif
00244 
00245 #if JACKDAW_CONF_RANDOM_MAC
00246 #include "rng.h"
00247 static void
00248 generate_new_eui64(uint8_t eui64[8]) {
00249         eui64[0] = 0x02;
00250         eui64[1] = rng_get_uint8();
00251         eui64[2] = rng_get_uint8();
00252         eui64[3] = 0xFF;
00253         eui64[4] = 0xFE;
00254         eui64[5] = rng_get_uint8();
00255         eui64[6] = rng_get_uint8();
00256         eui64[7] = rng_get_uint8();
00257 }
00258 #endif /* JACKDAW_CONF_RANDOM_MAC */
00259 
00260 #if !JACKDAW_CONF_USE_SETTINGS
00261 /****************************No settings manager*****************************/
00262 /* If not using the settings manager, put the default values into EEMEM
00263  * These can be manually changed and kept over program reflash.
00264  * The channel and bit complement are used to check EEMEM integrity,
00265  * If corrupt all values will be rewritten with the default flash values.
00266  * To make this work, get the channel before anything else.
00267  */
00268 
00269 uint8_t eemem_mac_address[8] EEMEM = {0x02, 0x12, 0x13, 0xff, 0xfe, 0x14, 0x15, 0x16};
00270 #ifdef CHANNEL_802_15_4
00271 uint8_t eemem_channel[2] EEMEM = {CHANNEL_802_15_4, ~CHANNEL_802_15_4};
00272 #else
00273 uint8_t eemem_channel[2] EMEM = {26, ~26};
00274 #endif
00275 #ifdef IEEE802154_PANID
00276 uint16_t eemem_panid EEMEM = IEEE802154_PANID;
00277 #else
00278 uint16_t eemem_panid EEMEM = 0xABCD;
00279 #endif
00280 #ifdef IEEE802154_PANADDR
00281 uint16_t eemem_panaddr EEMEM = IEEE802154_PANADDR;
00282 #else
00283 uint16_t eemem_panaddr EEMEM = 0;
00284 #endif
00285 #ifdef RF230_MAX_TX_POWER
00286 uint8_t eemem_txpower EEMEM = RF230_MAX_TX_POWER;
00287 #else
00288 uint8_t eemem_txpower EEMEM = 0;
00289 #endif
00290 static uint8_t get_channel_from_eeprom() {
00291         uint8_t x[2];
00292         *(uint16_t *)x = eeprom_read_word ((uint16_t *)&eemem_channel);
00293     if((uint8_t)x[0]!=(uint8_t)~x[1]) {//~x[1] can promote comparison to 16 bit
00294 /* Verification fails, rewrite everything */
00295     uint8_t mac[8];
00296 #if JACKDAW_CONF_RANDOM_MAC
00297     PRINTA("Generating random MAC address.\n");
00298     generate_new_eui64(&mac);
00299 #else
00300     {uint8_t i; for (i=0;i<8;i++) mac[i] = pgm_read_byte_near(default_mac_address+i);}
00301 #endif
00302         eeprom_write_block(&mac,  &eemem_mac_address, 8);
00303         eeprom_write_word(&eemem_panid  , pgm_read_word_near(&default_panid));
00304         eeprom_write_word(&eemem_panaddr, pgm_read_word_near(&default_panaddr));
00305     eeprom_write_byte(&eemem_txpower, pgm_read_byte_near(&default_txpower));
00306     x[0] = pgm_read_byte_near(&default_channel);
00307     x[1]= ~x[0];
00308     eeprom_write_word((uint16_t *)&eemem_channel, *(uint16_t *)x);    
00309   }
00310   return x[0];
00311 }
00312 static bool get_eui64_from_eeprom(uint8_t macptr[8]) {
00313         eeprom_read_block ((void *)macptr, &eemem_mac_address, 8);
00314         return macptr[0]!=0xFF;
00315 }
00316 static uint16_t get_panid_from_eeprom(void) {
00317         return eeprom_read_word(&eemem_panid);
00318 }
00319 static uint16_t get_panaddr_from_eeprom(void) {
00320         return eeprom_read_word (&eemem_panaddr);
00321 }
00322 static uint8_t get_txpower_from_eeprom(void)
00323 {
00324         return eeprom_read_byte(&eemem_txpower);
00325 }
00326 
00327 #else /* !JACKDAW_CONF_USE_SETTINGS */
00328 /******************************Settings manager******************************/
00329 static uint8_t get_channel_from_eeprom() {
00330         uint8_t x = settings_get_uint8(SETTINGS_KEY_CHANNEL, 0);
00331         if(!x) x = pgm_read_byte_near(&default_channel);
00332         return x;
00333 }
00334 static bool get_eui64_from_eeprom(uint8_t macptr[8]) {
00335         size_t size = 8;
00336         if(settings_get(SETTINGS_KEY_EUI64, 0, (unsigned char*)macptr, &size)==SETTINGS_STATUS_OK) {
00337       PRINTD("<=Get EEPROM MAC address.\n");
00338       return true;              
00339     }
00340 #if JACKDAW_CONF_RANDOM_MAC
00341     PRINTA("--Generating random MAC address.\n");
00342     generate_new_eui64(macptr);
00343 #else
00344     {uint8_t i;for (i=0;i<8;i++) macptr[i] = pgm_read_byte_near(default_mac_address+i);}
00345 #endif
00346     settings_add(SETTINGS_KEY_EUI64,(unsigned char*)macptr,8);
00347     PRINTA("->Set EEPROM MAC address.\n");
00348         return true;
00349 }
00350 static uint16_t get_panid_from_eeprom(void) {
00351     uint16_t x;
00352     if (settings_check(SETTINGS_KEY_PAN_ID,0)) {
00353         x = settings_get_uint16(SETTINGS_KEY_PAN_ID,0);
00354         PRINTD("<-Get EEPROM PAN ID of %04x.\n",x);
00355     } else {
00356             x=pgm_read_word_near(&default_panid);
00357         if (settings_add_uint16(SETTINGS_KEY_PAN_ID,x)==SETTINGS_STATUS_OK) {
00358           PRINTA("->Set EEPROM PAN ID to %04x.\n",x);
00359         }
00360     }
00361         return x;
00362 }
00363 static uint16_t get_panaddr_from_eeprom(void) {
00364     uint16_t x;
00365     if (settings_check(SETTINGS_KEY_PAN_ADDR,0)) {
00366         x = settings_get_uint16(SETTINGS_KEY_PAN_ADDR,0);
00367         PRINTD("<-Get EEPROM PAN address of %04x.\n",x);
00368     } else {
00369             x=pgm_read_word_near(&default_panaddr);
00370         if (settings_add_uint16(SETTINGS_KEY_PAN_ADDR,x)==SETTINGS_STATUS_OK) {
00371           PRINTA("->Set EEPROM PAN address to %04x.\n",x);
00372         }
00373     }        
00374         return x;
00375 }
00376 static uint8_t get_txpower_from_eeprom(void) {
00377     uint8_t x;
00378     if (settings_check(SETTINGS_KEY_TXPOWER,0)) {
00379         x = settings_get_uint8(SETTINGS_KEY_TXPOWER,0);
00380         PRINTD("<-Get EEPROM tx power of %d. (0=max)\n",x);
00381     } else {
00382             x=pgm_read_byte_near(&default_txpower);
00383         if (settings_add_uint8(SETTINGS_KEY_TXPOWER,x)==SETTINGS_STATUS_OK) {
00384           PRINTA("->Set EEPROM tx power of %d. (0=max)\n",x);
00385         }
00386     }
00387         return x;
00388 }
00389 #endif /* !JACKDAW_CONF_USE_SETTINGS */
00390 
00391 /*-------------------------------------------------------------------------*/
00392 /*-----------------------------Low level initialization--------------------*/
00393 static void initialize(void) {
00394 
00395   watchdog_init();
00396   watchdog_start();
00397 
00398 #if CONFIG_STACK_MONITOR
00399   /* Simple stack pointer highwater monitor. The 'm' command in cdc_task.c
00400    * looks for the first overwritten magic number.
00401    */
00402 {
00403 extern uint16_t __bss_end;
00404 uint16_t p=(uint16_t)&__bss_end;
00405     do {
00406       *(uint16_t *)p = 0x4242;
00407       p+=100;
00408     } while (p<SP-100); //don't overwrite our own stack
00409 }
00410 #endif
00411 
00412   /* Initialize hardware */
00413   // Checks for "finger", jumps to DFU if present.
00414   init_lowlevel();
00415   
00416   /* Clock */
00417   clock_init();
00418 
00419   /* Leds are referred to by number to prevent any possible confusion :) */
00420   /* Led0 Blue Led1 Red Led2 Green Led3 Yellow */
00421   Leds_init();
00422   Led1_on();
00423 
00424 /* Get a random (or probably different) seed for the 802.15.4 packet sequence number.
00425  * Some layers will ignore duplicates found in a history (e.g. Contikimac)
00426  * causing the initial packets to be ignored after a short-cycle restart.
00427  */
00428   ADMUX =0x1E;              //Select AREF as reference, measure 1.1 volt bandgap reference.
00429   ADCSRA=1<<ADEN;           //Enable ADC, not free running, interrupt disabled, fastest clock
00430   ADCSRA|=1<<ADSC;          //Start conversion
00431   while (ADCSRA&(1<<ADSC)); //Wait till done
00432   PRINTD("ADC=%d\n",ADC);
00433   random_init(ADC);
00434   ADCSRA=0;                 //Disable ADC
00435   
00436 #if USB_CONF_RS232
00437   /* Use rs232 port for serial out (tx, rx, gnd are the three pads behind jackdaw leds */
00438   rs232_init(RS232_PORT_0, USART_BAUD_57600,USART_PARITY_NONE | USART_STOP_BITS_1 | USART_DATA_BITS_8);
00439   /* Redirect stdout to second port */
00440   rs232_redirect_stdout(RS232_PORT_0);
00441 #if ANNOUNCE
00442   PRINTA("\n\n*******Booting %s*******\n",CONTIKI_VERSION_STRING);
00443 #endif
00444 #endif
00445         
00446   /* rtimer init needed for low power protocols */
00447   rtimer_init();
00448 
00449   /* Process subsystem. */
00450   process_init();
00451 
00452   /* etimer process must be started before USB or ctimer init */
00453   process_start(&etimer_process, NULL);
00454 
00455   Led2_on();
00456   /* Now we can start USB enumeration */
00457   process_start(&usb_process, NULL);
00458 
00459   /* Start CDC enumeration, bearing in mind that it may fail */
00460   /* Hopefully we'll get a stdout for startup messages, if we don't already */
00461 #if USB_CONF_SERIAL
00462   process_start(&cdc_process, NULL);
00463 {unsigned short i;
00464   for (i=0;i<65535;i++) {
00465     process_run();
00466     watchdog_periodic();
00467     if (stdout) break;
00468   }
00469 #if !USB_CONF_RS232
00470   PRINTA("\n\n*******Booting %s*******\n",CONTIKI_VERSION_STRING);
00471 #endif
00472 }
00473 #endif
00474   if (!stdout) Led3_on();
00475   
00476 #if RF230BB
00477 #if JACKDAW_CONF_USE_SETTINGS
00478   PRINTA("Settings manager will be used.\n");
00479 #else
00480 {uint8_t x[2];
00481         *(uint16_t *)x = eeprom_read_word((uint16_t *)&eemem_channel);
00482         if((uint8_t)x[0]!=(uint8_t)~x[1]) {
00483         PRINTA("Invalid EEPROM settings detected. Rewriting with default values.\n");
00484         get_channel_from_eeprom();
00485     }
00486 }
00487 #endif
00488 
00489   ctimer_init();
00490   /* Start radio and radio receive process */
00491   /* Note this starts RF230 process, so must be done after process_init */
00492   NETSTACK_RADIO.init();
00493 
00494   /* Set addresses BEFORE starting tcpip process */
00495 
00496   memset(&tmp_addr, 0, sizeof(rimeaddr_t));
00497 
00498   if(get_eui64_from_eeprom(tmp_addr.u8));
00499    
00500   //Fix MAC address
00501   init_net();
00502 
00503 #if UIP_CONF_IPV6
00504   memcpy(&uip_lladdr.addr, &tmp_addr.u8, 8);
00505 #endif
00506 
00507   rf230_set_pan_addr(
00508         get_panid_from_eeprom(),
00509         get_panaddr_from_eeprom(),
00510         (uint8_t *)&tmp_addr.u8
00511   );
00512   
00513   rf230_set_channel(get_channel_from_eeprom());
00514   rf230_set_txpower(get_txpower_from_eeprom());
00515 
00516   rimeaddr_set_node_addr(&tmp_addr); 
00517 
00518   /* Initialize stack protocols */
00519   queuebuf_init();
00520   NETSTACK_RDC.init();
00521   NETSTACK_MAC.init();
00522   NETSTACK_NETWORK.init();
00523 
00524 #if ANNOUNCE
00525   PRINTA("MAC address %x:%x:%x:%x:%x:%x:%x:%x\n\r",tmp_addr.u8[0],tmp_addr.u8[1],tmp_addr.u8[2],tmp_addr.u8[3],tmp_addr.u8[4],tmp_addr.u8[5],tmp_addr.u8[6],tmp_addr.u8[7]);
00526   PRINTA("%s %s, channel %u",NETSTACK_MAC.name, NETSTACK_RDC.name,rf230_get_channel());
00527   if (NETSTACK_RDC.channel_check_interval) {
00528     unsigned short tmp;
00529     tmp=CLOCK_SECOND / (NETSTACK_RDC.channel_check_interval == 0 ? 1:\
00530                         NETSTACK_RDC.channel_check_interval());
00531     if (tmp<65535) PRINTA(", check rate %u Hz",tmp);
00532   }
00533   PRINTA("\n");
00534 #endif
00535 
00536 #if UIP_CONF_IPV6_RPL
00537 #if RPL_BORDER_ROUTER
00538   process_start(&tcpip_process, NULL);
00539   process_start(&border_router_process, NULL);
00540   PRINTD ("RPL Border Router Started\n");
00541 #else
00542   process_start(&tcpip_process, NULL);
00543   PRINTD ("RPL Started\n");
00544 #endif
00545 #if RPL_HTTPD_SERVER
00546   extern struct process httpd_process;
00547   process_start(&httpd_process, NULL);
00548   PRINTD ("Webserver Started\n");
00549 #endif
00550 #endif /* UIP_CONF_IPV6_RPL */
00551 
00552 #else  /* RF230BB */
00553 /* The order of starting these is important! */
00554   process_start(&mac_process, NULL);
00555   process_start(&tcpip_process, NULL);
00556 #endif /* RF230BB */
00557 
00558   /* Start ethernet network and storage process */
00559   process_start(&usb_eth_process, NULL);
00560 #if USB_CONF_STORAGE
00561   process_start(&storage_process, NULL);
00562 #endif
00563 
00564   /* Autostart other processes */
00565   /* There are none in the default build so autostart_processes will be unresolved in the link. */
00566   /* The AUTOSTART_PROCESSES macro which defines it can only be used in the .co module. */
00567   /* See /examples/ravenusbstick/ravenusb.c for an autostart template. */
00568 #if 0
00569   autostart_start(autostart_processes);
00570 #endif
00571 
00572 #if ANNOUNCE
00573 #if USB_CONF_RS232
00574   PRINTA("Online.\n");
00575 #else
00576   PRINTA("Online. Type ? for Jackdaw menu.\n");
00577 #endif
00578 #endif
00579 
00580 Leds_off();
00581 }
00582 
00583 /*-------------------------------------------------------------------------*/
00584 /*---------------------------------Main Routine----------------------------*/
00585 int
00586 main(void)
00587 {
00588   /* GCC depends on register r1 set to 0 (?) */
00589   asm volatile ("clr r1");
00590   
00591   /* Initialize in a subroutine to maximize stack space */
00592   initialize();
00593 
00594 #if DEBUG
00595 {struct process *p;
00596  for(p = PROCESS_LIST();p != NULL; p = ((struct process *)p->next)) {
00597   PRINTA("Process=%p Thread=%p  Name=\"%s\" \n",p,p->thread,PROCESS_NAME_STRING(p));
00598  }
00599 }
00600 #endif
00601 
00602   while(1) {
00603     process_run();
00604 
00605     watchdog_periodic();
00606 
00607 /* Print rssi of all received packets, useful for range testing */
00608 #ifdef RF230_MIN_RX_POWER
00609     uint8_t lastprint;
00610     if (rf230_last_rssi != lastprint) {        //can be set in halbb.c interrupt routine
00611         PRINTA("%u ",rf230_last_rssi);
00612         lastprint=rf230_last_rssi;
00613     }
00614 #endif
00615 
00616 #if 0
00617 /* Clock.c can trigger a periodic PLL calibration in the RF230BB driver.
00618  * This can show when that happens.
00619  */
00620     extern uint8_t rf230_calibrated;
00621     if (rf230_calibrated) {
00622       PRINTA("\nRF230 calibrated!\n");
00623       rf230_calibrated=0;
00624     }
00625 #endif
00626 
00627 #if TESTRTIMER
00628 /* Timeout can be increased up to 8 seconds maximum.
00629  * A one second cycle is convenient for triggering the various debug printouts.
00630  * The triggers are staggered to avoid printing everything at once.
00631  * My Jackdaw is 4% slow.
00632  */
00633     if (rtimerflag) {
00634       rtimer_set(&rt, RTIMER_NOW()+ RTIMER_ARCH_SECOND*1UL, 1,(void *) rtimercycle, NULL);
00635       rtimerflag=0;
00636 
00637 #if STAMPS
00638 if ((rtime%STAMPS)==0) {
00639   PRINTA("%us ",rtime);
00640   if (rtime%STAMPS*10) PRINTA("\n");
00641 }
00642 #endif
00643       rtime+=1;
00644 
00645 #if PINGS && UIP_CONF_IPV6_RPL
00646 extern void raven_ping6(void);
00647 if ((rtime%PINGS)==1) {
00648   PRINTA("**Ping\n");
00649   raven_ping6();
00650 }
00651 #endif
00652 
00653 #if ROUTES && UIP_CONF_IPV6_RPL
00654 if ((rtime%ROUTES)==2) {
00655       
00656 extern uip_ds6_nbr_t uip_ds6_nbr_cache[];
00657 extern uip_ds6_route_t uip_ds6_routing_table[];
00658 extern uip_ds6_netif_t uip_ds6_if;
00659 
00660   uint8_t i,j;
00661   PRINTA("\nAddresses [%u max]\n",UIP_DS6_ADDR_NB);
00662   for (i=0;i<UIP_DS6_ADDR_NB;i++) {
00663     if (uip_ds6_if.addr_list[i].isused) {
00664       uip_debug_ipaddr_print(&uip_ds6_if.addr_list[i].ipaddr);
00665       PRINTA("\n");
00666     }
00667   }
00668   PRINTA("\nNeighbors [%u max]\n",UIP_DS6_NBR_NB);
00669   for(i = 0,j=1; i < UIP_DS6_NBR_NB; i++) {
00670     if(uip_ds6_nbr_cache[i].isused) {
00671       uip_debug_ipaddr_print(&uip_ds6_nbr_cache[i].ipaddr);
00672       PRINTA("\n");
00673       j=0;
00674     }
00675   }
00676   if (j) PRINTA("  <none>");
00677   PRINTA("\nRoutes [%u max]\n",UIP_DS6_ROUTE_NB);
00678   for(i = 0,j=1; i < UIP_DS6_ROUTE_NB; i++) {
00679     if(uip_ds6_routing_table[i].isused) {
00680       uip_debug_ipaddr_print(&uip_ds6_routing_table[i].ipaddr);
00681       PRINTA("/%u (via ", uip_ds6_routing_table[i].length);
00682       uip_debug_ipaddr_print(&uip_ds6_routing_table[i].nexthop);
00683  //     if(uip_ds6_routing_table[i].state.lifetime < 600) {
00684         PRINTA(") %lus\n", uip_ds6_routing_table[i].state.lifetime);
00685  //     } else {
00686  //       PRINTA(")\n");
00687  //     }
00688       j=0;
00689     }
00690   }
00691   if (j) PRINTA("  <none>");
00692   PRINTA("\n---------\n");
00693 }
00694 #endif
00695 
00696 #if STACKMONITOR && CONFIG_STACK_MONITOR
00697 if ((rtime%STACKMONITOR)==3) {
00698   extern uint16_t __bss_end;
00699   uint16_t p=(uint16_t)&__bss_end;
00700   do {
00701     if (*(uint16_t *)p != 0x4242) {
00702       PRINTA("Never-used stack > %d bytes\n",p-(uint16_t)&__bss_end);
00703       break;
00704     }
00705     p+=100;
00706   } while (p<RAMEND-10);
00707 }
00708 #endif
00709 
00710     }
00711 #endif /* TESTRTIMER */
00712 
00713 //Use with RF230BB DEBUGFLOW to show path through driver
00714 #if RF230BB&&0
00715 extern uint8_t debugflowsize,debugflow[];  //in rf230bb.c
00716   if (debugflowsize) {
00717     debugflow[debugflowsize]=0;
00718     PRINTA("%s",debugflow);
00719     debugflowsize=0;
00720    }
00721 #endif
00722 
00723   }
00724   return 0;
00725 }