示例#1
0
    bool run()
    {
        static uint8_t led = 0;

        static uint8_t data;

        static uint16_t value = 0;

        PT_BEGIN();

        while (true)
        {

            PT_WAIT_UNTIL(Uart::read(data));

            if (data != 0xff)
                continue;

            PT_WAIT_UNTIL(Uart::read(data));

            if (data != 0xaa)
                continue;

            PT_WAIT_UNTIL(Uart::read(data));

            if (data != 0x55)
                continue;

            PT_WAIT_UNTIL(Uart::read(data));

            if (data != 0x00)
                continue;

            // if we reach this point we read all four prefix bytes and can now
            // read led values
            for (led = 0; led < 30; led++)
            {
                value = 0;
                PT_WAIT_UNTIL(Uart::read(data));
                value = data << 8;
                PT_WAIT_UNTIL(Uart::read(data));
                value |= data;
                leds[led].red = value;

                value = 0;
                PT_WAIT_UNTIL(Uart::read(data));
                value = data << 8;
                PT_WAIT_UNTIL(Uart::read(data));
                value |= data;
                leds[led].green = value;

                value = 0;
                PT_WAIT_UNTIL(Uart::read(data));
                value = data << 8;
                PT_WAIT_UNTIL(Uart::read(data));
                value |= data;
                leds[led].blue = value;
            }
        }

        PT_END();
    }
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_dhcp(void))
{
  PT_BEGIN(&s.pt);
  
  /* try_again:*/
  s.state = STATE_SENDING;
  s.ticks = CLOCK_SECOND;

  do {
    send_discover();
    timer_set(&s.timer, s.ticks);
    PT_YIELD_UNTIL(&s.pt, uip_newdata() || timer_expired(&s.timer));

    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_request();
    timer_set(&s.timer, s.ticks);
    PT_YIELD_UNTIL(&s.pt, uip_newdata() || timer_expired(&s.timer));

    if(uip_newdata() && parse_msg() == DHCPACK) {
      s.state = STATE_CONFIG_RECEIVED;
      break;
    }

    if(s.ticks <= CLOCK_SECOND * 10) {
      s.ticks += CLOCK_SECOND;
    } else {
      PT_RESTART(&s.pt);
    }
  } while(s.state != STATE_CONFIG_RECEIVED);
  
#if 0
  printf("Got IP address %d.%d.%d.%d\n",
	 uip_ipaddr1(s.ipaddr), uip_ipaddr2(s.ipaddr),
	 uip_ipaddr3(s.ipaddr), uip_ipaddr4(s.ipaddr));
  printf("Got netmask %d.%d.%d.%d\n",
	 uip_ipaddr1(s.netmask), uip_ipaddr2(s.netmask),
	 uip_ipaddr3(s.netmask), uip_ipaddr4(s.netmask));
  printf("Got DNS server %d.%d.%d.%d\n",
	 uip_ipaddr1(s.dnsaddr), uip_ipaddr2(s.dnsaddr),
	 uip_ipaddr3(s.dnsaddr), uip_ipaddr4(s.dnsaddr));
  printf("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));
  printf("Lease expires in %ld seconds\n",
	 ntohs(s.lease_time[0])*65536ul + ntohs(s.lease_time[1]));
#endif

  dhcpc_configured(&s);
  
  /*  timer_stop(&s.timer);*/

  /*
   * PT_END restarts the thread so we do this instead. Eventually we
   * should reacquire expired leases here.
   */
  while(1) {
    PT_YIELD(&s.pt);
  }

  PT_END(&s.pt);
}
示例#3
0
文件: lpp.c 项目: EDAyele/wsn430
/**
 * Duty cycle the radio and send probes. This function is called
 * repeatedly by a ctimer. The function restart_dutycycle() is used to
 * (re)start the duty cycling.
 */
static int
dutycycle(void *ptr)
{
  struct ctimer *t = ptr;
#if WITH_PENDING_BROADCAST
  struct queue_list_item *p;
#endif

  PT_BEGIN(&dutycycle_pt);

  while(1) {

#if WITH_PENDING_BROADCAST
    {
	/* Before sending the probe, we mark all broadcast packets in
	   our output queue to be pending. This means that they are
	   ready to be sent, once we know that no neighbor is
	   currently broadcasting. */
      for(p = list_head(queued_packets_list); p != NULL; p = list_item_next(p)) {
	  if(p->broadcast_flag == BROADCAST_FLAG_WAITING) {
	    PRINTF("wait -> pending\n");
	    set_broadcast_flag(p, BROADCAST_FLAG_PENDING);
	  }
	}
      }
#endif /* WITH_PENDING_BROADCAST */

    /* Turn on the radio for sending a probe packet and
       anticipating a data packet from a neighbor. */
    turn_radio_on();

    /* Send a probe packet. */
    send_probe();

    /* Set a timer so that we keep the radio on for LISTEN_TIME. */
    ctimer_set(t, LISTEN_TIME, (void (*)(void *))dutycycle, t);
    PT_YIELD(&dutycycle_pt);

#if WITH_PENDING_BROADCAST
    {
      struct queue_list_item *p;
      /* Go through the list of packets we are waiting to send, and
	 check if there are any pending broadcasts in the list. If
	 there are pending broadcasts, and we did not receive any
	 broadcast packets from a neighbor in response to our probe,
	 we mark the broadcasts as being ready to send. */
      for(p = list_head(queued_packets_list); p != NULL; p = list_item_next(p)) {
	if(p->broadcast_flag == BROADCAST_FLAG_PENDING) {
	  PRINTF("pending -> send\n");
	  set_broadcast_flag(p, BROADCAST_FLAG_SEND);
	  turn_radio_on();
	}
      }
    }
#endif /* WITH_PENDING_BROADCAST */

    /* If we have no packets to send (indicated by the list length of
       queued_packets_list being zero), we should turn the radio
       off. Othersize, we keep the radio on. */
    if(num_packets_to_send() == 0) {

      /* If we are not listening for announcements, we turn the radio
	 off and wait until we send the next probe. */
      if(is_listening == 0) {
        int current_off_time;
        if(!NETSTACK_RADIO.receiving_packet()) {
          turn_radio_off();
          compower_accumulate(&compower_idle_activity);
        }
        current_off_time = off_time - off_time_adjustment;
        if(current_off_time < LISTEN_TIME * 2) {
          current_off_time = LISTEN_TIME * 2;
        }
        off_time_adjustment = 0;
	ctimer_set(t, current_off_time, (void (*)(void *))dutycycle, t);
	PT_YIELD(&dutycycle_pt);

#if WITH_ADAPTIVE_OFF_TIME
	off_time += LOWEST_OFF_TIME;
	if(off_time > OFF_TIME) {
	  off_time = OFF_TIME;
	}
#endif /* WITH_ADAPTIVE_OFF_TIME */

      } else {
	/* We are listening for annonucements, so we count down the
	   listen time, and keep the radio on. */
	is_listening--;
	ctimer_set(t, OFF_TIME, (void (*)(void *))dutycycle, t);
	PT_YIELD(&dutycycle_pt);
      }
    } else {
      /* We had pending packets to send, so we do not turn the radio off. */

      ctimer_set(t, off_time, (void (*)(void *))dutycycle, t);
      PT_YIELD(&dutycycle_pt);
    }
  }

  PT_END(&dutycycle_pt);
}
示例#4
0
/*---------------------------------------------------------------------*/
static
PT_THREAD(recv_tcpthread(struct pt *pt))
{
  uint8_t *dataptr;
  struct codeprop_tcphdr *th;
  int datalen = uip_datalen();
  
  PT_BEGIN(pt);

  while(1) {
    
    PT_WAIT_UNTIL(pt, uip_connected());
    
    s.state = STATE_RECEIVING_TCPDATA;
    
    s.addr = 0;
    s.count = 0;
    process_post(PROCESS_BROADCAST, codeprop_event_quit, (process_data_t)NULL);


    /* Read the header. */
    PT_WAIT_UNTIL(pt, uip_newdata() && uip_datalen() > 0);
    dataptr = uip_appdata;

    if(uip_datalen() < sizeof(struct codeprop_tcphdr)) {
      PRINTF(("codeprop: header not found in first tcp segment\n"));
      uip_abort();
    }
    th = (struct codeprop_tcphdr *)uip_appdata;
    s.len = uip_htons(th->len);
    s.addr = 0;
    uip_appdata += sizeof(struct codeprop_tcphdr);
    datalen = uip_datalen() - sizeof(struct codeprop_tcphdr);

    /* Read the rest of the data. */
    do {
      if(datalen > 0) {
	/*	printf("Got %d bytes\n", uip_len);*/
	eeprom_write(EEPROMFS_ADDR_CODEPROP + s.addr,
		     uip_appdata,
		     datalen);
	s.addr += datalen;
      }
      if(s.addr < s.len) {
	PT_YIELD_UNTIL(pt, uip_newdata());
      }
    } while(s.addr < s.len);

    /* Print out the "ok" message. */
    do {
      uip_send("ok\r\n", 4);
      PT_WAIT_UNTIL(pt, uip_acked() || uip_rexmit() || uip_closed());
    } while(uip_rexmit());

    /* Close the connection. */
    uip_close();
    
    ++s.id;
    s.state = STATE_SENDING_UDPDATA;
    tcpip_poll_udp(udp_conn);

    codeprop_start_program();
    
    PT_WAIT_UNTIL(pt, s.state != STATE_SENDING_UDPDATA);
    /*    printf("recv_tcpthread: unblocked\n");*/
  }
  
  PT_END(pt);
}
示例#5
0
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_dhcp(void))
{
  PT_BEGIN(&s.pt);

  /* try_again:*/
  s.state = STATE_SENDING;
  s.ticks = CLOCK_SECOND;

  do {
    send_discover();
    /* Sending does not clear the NEWDATA flag.  The packet doesn't
       actually get sent until we yield at least once.  If we don't
       clear the flag ourselves, we will enter an infinite loop here.
       This is arguably a bug in uip.c and the uip_send() function
       should probably clear the NEWDATA flag. */
    uip_flags=uip_flags&(~UIP_NEWDATA);
    timer_set(&s.timer, s.ticks);
    PT_WAIT_UNTIL(&s.pt, uip_newdata() || timer_expired(&s.timer));

    if(uip_newdata() && parse_msg() == DHCPOFFER) {
      s.state = STATE_OFFER_RECEIVED;
      break;
    }

    if(s.ticks < CLOCK_SECOND * 20) {
      s.ticks *= 2;
    }
  } while(s.state != STATE_OFFER_RECEIVED);

  s.ticks = CLOCK_SECOND;
  do {
    send_request();
    uip_flags=uip_flags&(~UIP_NEWDATA);
    timer_set(&s.timer, s.ticks);
    PT_WAIT_UNTIL(&s.pt, uip_newdata() || timer_expired(&s.timer));

    if(uip_newdata() && parse_msg() == DHCPACK) {
      s.state = STATE_CONFIG_RECEIVED;
      break;
    }

    if(s.ticks <= CLOCK_SECOND * 10) {
      s.ticks += CLOCK_SECOND;
    } else {
      PT_RESTART(&s.pt);
    }
  } while(s.state != STATE_CONFIG_RECEIVED);
  
#if 0
  printf("Got IP address %d.%d.%d.%d\n", uip_ipaddr_to_quad(&s.ipaddr));
  printf("Got netmask %d.%d.%d.%d\n",	 uip_ipaddr_to_quad(&s.netmask));
  printf("Got DNS server %d.%d.%d.%d\n", uip_ipaddr_to_quad(&s.dnsaddr));
  printf("Got default router %d.%d.%d.%d\n",
	 uip_ipaddr_to_quad(&s.default_router));
  printf("Lease expires in %ld seconds\n",
	 uip_ntohs(s.lease_time[0])*65536ul + uip_ntohs(s.lease_time[1]));
#endif

  dhcpc_configured(&s);
  
  /*  timer_stop(&s.timer);*/

  /*
   * PT_END restarts the thread so we do this instead. Eventually we
   * should reacquire expired leases here.
   */
  while(1) {
    PT_YIELD(&s.pt);
  }

  PT_END(&s.pt);
}
示例#6
0
文件: acc-sl.c 项目: aoboy/acc-slight
/**
 * @brief power_cycle
 * @param rt
 * @param ptr
 * @return
 */
static char power_cycle(struct rtimer *rt, void* ptr){


    //start protothread function
    PT_BEGIN(&pt);

    //watchdog_stop();
    //watchdog_periodic();
    
    while(1){

        if(rand_offset_wait_flag){

            for(slot_counter = 0; slot_counter < node_slots_offset; slot_counter++){
                rtimer_clock_t tnow_wait = RTIMER_NOW();

                schedule_fixed(rt, tnow_wait + TS);
                PT_YIELD(&pt);
            }

            //random slots offset is over.. disable flag
            rand_offset_wait_flag = 0;
            COOJA_DEBUG_PRINTF("END oF RANDOM OFFSET:%u..%u\n", rounds_counter,node_slots_offset);
        }//else{}

        static rtimer_clock_t t0;
        //rtimer_clock_t tnow;

	watchdog_periodic();
        //for(slot_counter = 0; slot_counter < slot_counter_upperB+2; slot_counter++){
        for(slot_counter = 0; slot_counter <= slot_upperBound; slot_counter++){

            //at this time, everyone receives new neighbors.
            //if(slot_counter!= 0 && (slot_counter % GROUP_MERGE_TIME) == 0){

                   //cc2420_set_channel(i3e154_channels[0]);
            	   /*if(rimeaddr_node_addr.u8[0] == 10){
          	     cc2420_set_channel(i3e154_channels[0]);
                   }*/
            //}*/
	    
	    //watchdog_periodic();
	    
	    //watchdog_stop();
	    
            //this offset is transmitted
            probe_offset = slot_counter%period_length;

            if(slot_counter != 0 && (slot_counter % period_length) == 0){

                anchor_time = slot_counter - probe_offset;

                //update j coeficient of neighbor nodes
                neighs_jfactor_update();
		
		//reset extra slots counter.. a new period will commence here.
		extra_slots_k_counter = 0;
            }
            //txPacketFlag
            //this is an anchor slot..
            if(slot_counter == 0 || (slot_counter%period_length) == 0){

                isAnchorFlag       = 1; //ANCHOR flag
                txPacketFlag       = 1;  //Set beacon Flag to TRUE

                //Compute next probe
                //probe_slot_counter = random_int(period_length/2+2);

                probe_slot_counter = 2*probe_jfact + 2;
                probe_time = slot_counter + probe_slot_counter;

                probe_jfact = (1+probe_jfact)%(period_length/4+1);

                energy_per_period++;

                //reset overflow_flag only used for indirect discovery
                overflow_flag = 0;

                /**COOJA_DEBUG_PRINTF("AnchorID:%u, ProbeID:%u\n", 
                slot_counter, probe_slot_counter);*/
            }else{//ELSE OF (slot_counter%period_length)
                //check it is a probe slot..
                if(slot_counter == probe_time){

                    isAnchorFlag  = 0; //RESET Anchor Flag
                    txPacketFlag  = 1;  //Set beacon Flag to TRUE

                    /**the probe offset on a probe slot is based on the
                    probe slot counter.. bcz of strip-probbing.*/
                    probe_offset  = probe_slot_counter;

                    energy_per_period++;

                    //reset overflow_flag only used for indirect discovery
                    overflow_flag = 0;

                    //COOJA_DEBUG_PRINTF("ProbeID:%u, time:%u\n", probe_slot_counter, probe_time);
                }else{//ELSE slot_counter == probe_time

                    //probe also possible Hop 2 neighbors
		    if(list_access_flag == 0){
			  list_access_flag = 1;
			  
			if(isthere_anchor(extra_slots_k, slot_counter) &&
			  (extra_slots_k_counter < extra_slots_k)){

			    isAnchorFlag  = 0; //RESET Anchor Flag
			    txPacketFlag  = 1; //Set beacon Flag to TRUE
			    
			    extra_slots_k_counter++;

			    extra_probe_counter++;

			    extra_probe_per_period++;

			    //reset overflow_flag only used for indirect discovery
			    overflow_flag = 1;

			    //COOJA_DEBUG_PRINTF("TgT_ID:%u, time:%u\n",  probe_offset, slot_counter + probe_offset);
			} //END of
			//reset flag..
		        list_access_flag = 0;
		      }
                } //END OF slot_counter == probe_time

            }//END OF (slot_counter%period_length)

            if(txPacketFlag){

                txPacketFlag = 0;//RESET txPacketFlag

                //total energy
                energy_counter++;

                //COOJA_DEBUG_PRINTF("PACKET_TX_INIT:%u,%u\n", slot_counter, RTIMER_NOW());

                rtimer_clock_t tnow = RTIMER_NOW();

                //cc2420_set_channel(i3e154_channels[0]);

                if(radio_is_on_flag == 0){
                    //COOJA_DEBUG_PRINTF("b17\n");
                    on();
                }


                //send first beacon without offset
                beacon_2_flag = 0;

                //transmit beacon packet
		transmit_epidemic();
		
		
                //wait for sometime to receive some packets
                schedule_fixed(rt, tnow + 3*TS_20P);
                PT_YIELD(&pt);

                //Once the cycle returns, it is time to send the second beacon
                //transmit Anchor Probe Here
                tnow = RTIMER_NOW();

                //send second beacon with offset
                beacon_2_flag = 1;

                //trabsmit beacon packet
		if(list_access_flag == 0)
		    transmit_epidemic();
				

                //here we schedule to comence the next time slot.
                schedule_fixed(rt, tnow + 2*TS_20P +overflow_flag*TS_20P);
                PT_YIELD(&pt);

                //we need to switch the radio off..
                if(radio_is_on_flag == 1){
                    //COOJA_DEBUG_PRINTF("b17\n");
		    /**if(node_id == 16)
		      COOJA_DEBUG_PRINTF("b17\n");*/
                    off();
                }                
                
                //RESET txPacketFlag
                txPacketFlag = 0;//RESET txPacketFlag
                
            }else{ //END if(txPacketFlag)

                //turn radio off
                if(radio_is_on_flag == 1){
                    //COOJA_DEBUG_PRINTF("b17\n");
                    off();
                }

		if(sort_gains_flag){
		  
		      sort_gains_flag = 0;
		      /*get current number of neighbors..
		       ACC: compute updates here..*/
		      uint8_t tmp_num_neighs = 0;		      		      
		      
		      //if(list_access_flag == 0){
			  //list_access_flag = 1;
			  //tmp_num_neighs = compute_slot_gain(probe_offset);
			  
			  //sort slot gains here..
			  sort_slot_gains();
			  
			  //list_access_flag = 0;

			  tmp_num_neighs = neighs_num_nodes();
			  
			  if(curr_frac_nodes < tmp_num_neighs){
			      ///set current number of neighbors
			      curr_frac_nodes = tmp_num_neighs;

			      process_post(&output_process,PROCESS_EVENT_CONTINUE, NULL);
			  }
			  			  
		      //} //end of list_access_flag == 0	
		}                
                //here we schedule to comence the next time slot.
                schedule_fixed(rt, RTIMER_NOW() + TS);
                PT_YIELD(&pt);
		

            } //END if(txPacketFlag)

            //print energy consumption
            if(slot_counter != 0 && (slot_counter % period_length) == 0){

                //print energy consumption values
                ////print_nodes(1);
	      
                //process_post(&output_process,PROCESS_EVENT_CONTINUE, energyPrint);

                //energy_per_period = 0;
                //extra_probe_per_period = 0;
            }

        } //END for LOOP

        COOJA_DEBUG_PRINTF("END oF DISCOVERY CYCLE:%u\n", rounds_counter);
        //AN UPPER_BOUND HAVE BEEN REACHED.. Exit the
	
        discovery_is_on = 0;
        restart_discovery();

        //cycle is over, YIELD waiting for another call..
        PT_YIELD(&pt);

    }//end of WHILE(1)

    //end protothread function:AG
    PT_END(&pt);
}
/*---------------------------------------------------------------------------*/
static PT_THREAD( handle_script ( struct httpd_state *s ) )
{
	char	*ptr;

	PT_BEGIN( &s->scriptpt );
	( void ) PT_YIELD_FLAG;
	while( s->file.len > 0 )
	{
		/* Check if we should start executing a script. */
		if( *s->file.data == ISO_percent && *(s->file.data + 1) == ISO_bang )
		{
			s->scriptptr = s->file.data + 3;
			s->scriptlen = s->file.len - 3;
			if( *(s->scriptptr - 1) == ISO_colon )
			{
				httpd_fs_open( s->scriptptr + 1, &s->file );
				PT_WAIT_THREAD( &s->scriptpt, send_file(s) );
			}
			else
			{
				PT_WAIT_THREAD( &s->scriptpt, httpd_cgi(s->scriptptr) (s, s->scriptptr) );
			}

			next_scriptstate( s );

			/* The script is over, so we reset the pointers and continue
	 		sending the rest of the file. */
			s->file.data = s->scriptptr;
			s->file.len = s->scriptlen;
		}
		else
		{
			/* See if we find the start of script marker in the block of HTML
	 to be sent. */
			if( s->file.len > uip_mss() )
			{
				s->len = uip_mss();
			}
			else
			{
				s->len = s->file.len;
			}

			if( *s->file.data == ISO_percent )
			{
				ptr = strchr( s->file.data + 1, ISO_percent );
			}
			else
			{
				ptr = strchr( s->file.data, ISO_percent );
			}

			if( ptr != NULL && ptr != s->file.data )
			{
				s->len = ( int ) ( ptr - s->file.data );
				if( s->len >= uip_mss() )
				{
					s->len = uip_mss();
				}
			}

			PT_WAIT_THREAD( &s->scriptpt, send_part_of_file(s) );
			s->file.data += s->len;
			s->file.len -= s->len;
		}
	}

	PT_END( &s->scriptpt );
}
示例#8
0
文件: httpd.c 项目: jaseg/avr-uip
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_script(struct httpd_state *s))
{


  PGM_P ptr;
  
  PT_BEGIN(&s->scriptpt);


  while(s->file.len > 0) {

    /* Check if we should start executing a script. */
    if(pgm_read_byte_near(s->file.data) == ISO_percent &&
       pgm_read_byte_near(s->file.data + 1) == ISO_bang) {
      s->scriptptr = s->file.data + 3;
      s->scriptlen = s->file.len - 3;

      if(pgm_read_byte_near(s->scriptptr - 1) == ISO_colon) {

            strncpy_P(s->tmp_str, s->scriptptr + 1, sizeof(s->tmp_str) -1);
			if(httpd_fs_open(s->tmp_str, &s->file) ||
				httpd_fs_open(s->tmp_str + 1 , &s->file)) {
				PT_WAIT_THREAD(&s->scriptpt, 
           send_file(s));
			} else {
            // could not open the file.
			}

      } else {
            strncpy_P(s->tmp_str, s->scriptptr, sizeof(s->tmp_str) -1);
			((s->tmp_str)[sizeof(s->tmp_str) - 1]) = '\0';
					PT_WAIT_THREAD(&s->scriptpt, 
           httpd_cgi(s->tmp_str)(s, s->tmp_str));
      }
      next_scriptstate(s);
      
      /* The script is over, so we reset the pointers and continue
    	 sending the rest of the file. */
      s->file.data = s->scriptptr;
      s->file.len = s->scriptlen;
    } else {
      /* See if we find the start of script marker in the block of HTML
	        to be sent. */

      if(s->file.len > uip_mss()) {
	      s->len = uip_mss();
      } else {
	      s->len = s->file.len;
      }

      if(pgm_read_byte_near(s->file.data) == ISO_percent) {
	      ptr = strchr_P(s->file.data + 1, ISO_percent);

      } else {
	      ptr = strchr_P(s->file.data, ISO_percent);

      }

      if(ptr != NULL &&
      	 ptr != s->file.data) {
        	s->len = (int)(ptr - s->file.data);
        	if(s->len >= uip_mss()) {
        	  s->len = uip_mss();
      	}
      }

      PT_WAIT_THREAD(&s->scriptpt, send_part_of_file(s));

      s->file.data += s->len;
      s->file.len -= s->len;
      
    }
  }
  
  PT_END(&s->scriptpt);


	/*
  PGM_P ptr;
  
  PT_BEGIN(&s->scriptpt);

  while(s->file.len > 0) {
    // Check if we should start executing a script.
    if( (pgm_read_byte(s->file.data) == ISO_percent) &&
        (pgm_read_byte(s->file.data + 1) == ISO_bang)) {
      s->scriptptr = s->file.data + 3;
      s->scriptlen = s->file.len - 3;

      if(pgm_read_byte(s->scriptptr - 1) == ISO_colon) {
          strncpy_P(s->tmp_str, s->scriptptr + 1, sizeof(s->tmp_str) -1);
        if (httpd_fs_open(s->tmp_str, &s->file))
        {
	        PT_WAIT_THREAD(&s->scriptpt, send_file(s));
        }
      } else {
	    PT_WAIT_THREAD(&s->scriptpt,
		       httpd_cgi(s->scriptptr)(s, s->scriptptr));
      }

      next_scriptstate(s);
      
      // The script is over, so we reset the pointers and continue
	  // sending the rest of the file.
      s->file.data = s->scriptptr;
      s->file.len = s->scriptlen;
    } else {
      // See if we find the start of script marker in the block of HTML
	  //   to be sent. 

      if(s->file.len > uip_mss()) {
        s->len = uip_mss();
      } else {
        s->len = s->file.len;
      }

      if(pgm_read_byte(s->file.data) == ISO_percent) {
        ptr = strchr_P(s->file.data + 1, ISO_percent);
      } else {
        ptr = strchr_P(s->file.data, ISO_percent);
      }

      if(ptr != NULL &&
	     ptr != s->file.data) {
        s->len = (int)(ptr - s->file.data);

        if(s->len >= uip_mss()) {
            s->len = uip_mss();
        }
      }

      PT_WAIT_THREAD(&s->scriptpt, send_part_of_file(s));
      s->file.data += s->len;
      s->file.len -= s->len;
    }
  }
  
  PT_END(&s->scriptpt);
  */
}
示例#9
0
static 
PT_THREAD(data_activate_thread(struct pt *pt))
{
	PT_BEGIN(pt);

	char pdu[PDU_LENGTH];
    char dataBuf[PDU_LENGTH];
    int bufLen;
    int status;

	int sock;
	exosite_timer_t waitTimer;

	do
	{

		if(exosite_pal_load_cik(exoHttpContextQueue.cik,
								CIK_LENGTH))
			break;

		build_msg_activate(	pdu,
							sizeof(pdu),
							exoHttpContextQueue.vendor,
							exoHttpContextQueue.model,
							exoHttpContextQueue.sn);

		if(!exosite_pal_sock_connect(&sock))
		{
			exosite_pal_sock_close(&sock);
			break;
		}

		if(!exosite_pal_sock_write( &sock,
		                            pdu,
		                            strlen(pdu)))
		{
			exosite_pal_sock_close(&sock);
			break;
		}

		exosite_pal_timer_init(&waitTimer);
		exosite_pal_timer_countdown_ms(&waitTimer, WAIT_TIME_MS);

		while(1)
		{
			if(exosite_pal_timer_expired(&waitTimer))
			{
				exosite_pal_sock_close(&sock);
				break;
			}

			bufLen = sizeof(pdu);
			if(exosite_pal_sock_read(	&sock,
										dataBuf,
				                    	&bufLen)  > 0)
				break;
		}

		if(!parse_rsp_status(	dataBuf,
								bufLen,
								&status))
		{
			exosite_pal_sock_close(&sock);
			break;
		}

		if(status != 200)
		{
			exosite_pal_sock_close(&sock);
			break;
		}

		if(!parse_cik_info(	dataBuf,
							bufLen,
							exoHttpContextQueue.cik))
		{
			exosite_pal_sock_close(&sock);
			break;
		}

		exosite_pal_save_cik(	exoHttpContextQueue.cik,
								CIK_LENGTH);

		exosite_pal_sock_close(&sock);
	} while(false);

	PT_END(pt);
}
示例#10
0
文件: main.c 项目: PaulMougel/msp430
static PT_THREAD(thread_process_msg(struct pt *pt))
{
    PT_BEGIN(pt);

    while(1)
    {
        PT_WAIT_UNTIL(pt, radio_rx_flag == 1);

        //dump_message(radio_rx_buffer);

        /*if(radio_rx_buffer[MSG_BYTE_TYPE] == MSG_TYPE_ID_REQUEST)
        {
            prompt_node_id();
        }
        else if(radio_rx_buffer[MSG_BYTE_TYPE] == MSG_TYPE_ID_REPLY &&
            !timer_reached(TIMER_ID_INPUT, ID_INPUT_TIMEOUT_TICKS))
        {
            set_node_id(radio_rx_buffer[MSG_BYTE_CONTENT]);
        }
         forward packet as it hasn't been processed on this node
        else if(radio_rx_buffer[MSG_BYTE_HOPS] < MAX_HOPS)
        {
            /* prevent loops by not forwarding a packet
             * if we are among the last hops 
            int loop = 0;
            unsigned int i;
            for(i = MSG_BYTE_SRC_ROUTE; i < MSG_BYTE_SRC_ROUTE + radio_tx_buffer[MSG_BYTE_HOPS]; i++)
            {
                if(radio_tx_buffer[i] == node_id) {
                    loop = 1;
                }
            }

            if(loop == 0)
            {
                memcpy(radio_tx_buffer, radio_rx_buffer, PKTLEN);
                radio_tx_buffer[MSG_BYTE_SRC_ROUTE + radio_tx_buffer[MSG_BYTE_HOPS]] = node_id;
                radio_tx_buffer[MSG_BYTE_HOPS]++;

                /* this is probably the ugliest MAC protocol ever made
                 * (a packet send takes about 30 ms to complete, therefore
                 * we wait 40 ms * node_id before forwarding a packet
                 * to avoid collisions) 
                TIMER_RADIO_FORWARD = 0;
                PT_WAIT_UNTIL(pt, timer_reached(TIMER_RADIO_FORWARD, 4 * node_id));

                radio_send_message();
            }
        }*/
	if(radio_rx_buffer[MSG_BYTE_TYPE] == MSG_TYPE_TEMPERATURE)
    	{
		unsigned int temperature;
		char *pt = (char *) &temperature;
		pt[0] = radio_rx_buffer[MSG_BYTE_CONTENT + 1];
		pt[1] = radio_rx_buffer[MSG_BYTE_CONTENT];


		printf("node_id,%d,temperature,%d.%d,rssi,%d,help,%d\r\n", (unsigned char) radio_rx_buffer[MSG_BYTE_SRC_ROUTE], temperature / 10, temperature % 10, last_rssi, radio_rx_buffer[MSG_BYTE_HOPS]);
    	}
        radio_rx_flag = 0;
    }

    PT_END(pt);
}
示例#11
0
static PT_THREAD (handle_dhcp (void))
{
  PT_BEGIN (&dhcpcState->pt);

  dhcpcState->state = STATE_SENDING;
  dhcpcState->ticks = CLOCK_SECOND;

  do 
  {
    send_discover ();
    timer_set (&dhcpcState->timer, dhcpcState->ticks);

    PT_WAIT_UNTIL (&dhcpcState->pt, uip_newdata () || timer_expired (&dhcpcState->timer));

    if (uip_newdata () && (parse_msg () == DHCPOFFER)) 
    {
      uip_flags &= ~UIP_NEWDATA;
      dhcpcState->state = STATE_OFFER_RECEIVED;
      break;
    }

    uip_flags &= ~UIP_NEWDATA;

    if (dhcpcState->ticks < CLOCK_SECOND * 60)
      dhcpcState->ticks *= 2;
    else 
    {
      dhcpcState->ipaddr [0] = dhcpcState->ipaddr [1] = 0;
      goto dhcpcf;
    }
  } 
  while (dhcpcState->state != STATE_OFFER_RECEIVED);

  dhcpcState->ticks = CLOCK_SECOND;

  do 
  {
    send_request ();
    timer_set (&dhcpcState->timer, dhcpcState->ticks);

    PT_WAIT_UNTIL (&dhcpcState->pt, uip_newdata () || timer_expired (&dhcpcState->timer));

    if (uip_newdata () && (parse_msg () == DHCPACK))
    {
      uip_flags &= ~UIP_NEWDATA;
      dhcpcState->state = STATE_CONFIG_RECEIVED;
      break;
    }

    uip_flags &= ~UIP_NEWDATA;

    if (dhcpcState->ticks <= CLOCK_SECOND * 10)
      dhcpcState->ticks += CLOCK_SECOND;
    else
      PT_RESTART (&dhcpcState->pt);
  } 
  while (dhcpcState->state != STATE_CONFIG_RECEIVED);

dhcpcf:
  dhcpc_configured (dhcpcState);

  /*  timer_stop (&dhcpcState->timer);*/

  /*
   * PT_END restarts the thread so we do this instead. Eventually we
   * should reacquire expired leases here.
   */
  while (1)
    PT_YIELD (&dhcpcState->pt);

  PT_END (&dhcpcState->pt);
}
示例#12
0
文件: cc1101.c 项目: ADVANSEE/mist
/*---------------------------------------------------------------------------*/
static int
input_byte(uint8_t byte)
{
  int crc;

  if(timer_expired(&rxstate.timer)) {
    restart_input();
  }
  PT_BEGIN(&rxstate.pt);

  /* The first incoming byte is the length of the packet. */

  rxstate.receiving = 1;
  rxstate.len = byte;

  if(byte == 0) {
#if DEBUG
    printf("Bad len 0, state %d rxbytes %d\n", state(), read_rxbytes());
#endif /* DEBUG */
    flushrx();
    PT_EXIT(&rxstate.pt);
  }

  timer_set(&rxstate.timer, PACKET_LIFETIME);
  for(rxstate.ptr = 0;
      rxstate.ptr < rxstate.len;
      rxstate.ptr++) {

    /* Wait for the next data byte to be received. */
    PT_YIELD(&rxstate.pt);
    rxstate.buf[rxstate.ptr] = byte;
  }

  /* Receive two more bytes from the FIFO: the RSSI value and the LQI/CRC */
  PT_YIELD(&rxstate.pt);
  rxstate.buf[rxstate.ptr] = byte;
  rxstate.ptr++;
  PT_YIELD(&rxstate.pt);
  rxstate.buf[rxstate.ptr] = byte;
  crc = (byte & 0x80);
  rxstate.ptr++;

  if(crc == 0) {
#if DEBUG
    printf("bad crc\n");
#endif /* DEBUG */
    flushrx();
  } else if(packet_rx_len > 0) {
#if DEBUG
    printf("Packet in the buffer (%d), dropping %d bytes\n", packet_rx_len, rxstate.len);
#endif /* DEBUG */
    flushrx();
    process_poll(&cc1101_process);
  } else if(rxstate.len < ACK_LEN) {
    /* Drop packets that are way too small: less than ACK_LEN (3) bytes
       long. */
#if DEBUG
    printf("!");
#endif /* DEBUG */
  } else {
    /* Read out the first three bytes to determine if we should send an
       ACK or not. */

    /* Send a link-layer ACK before reading the full packet. */
    if(rxstate.len >= ACK_LEN) {
      /* Try to parse the incoming frame as a 802.15.4 header. */
      frame802154_t info154;
      if(frame802154_parse(rxstate.buf, rxstate.len, &info154) != 0) {

        /* XXX Potential optimization here: we could check if the
           frame is destined for us, or for the broadcast address and
           discard the packet if it isn't for us. */
  if(1) {

    /* For dataframes that has the ACK request bit set and that
       is destined for us, we send an ack. */
    if(info154.fcf.frame_type == FRAME802154_DATAFRAME &&
       info154.fcf.ack_required != 0 &&
       rimeaddr_cmp((rimeaddr_t *)&info154.dest_addr,
        &rimeaddr_node_addr)) {
      send_ack(info154.seq);

      /* Make sure that we don't put the radio in the IDLE state
         before the ACK has been fully transmitted. */
      BUSYWAIT_UNTIL((state() != CC1101_STATE_TX), RTIMER_SECOND / 10);
      ENERGEST_OFF(ENERGEST_TYPE_TRANSMIT);
      ENERGEST_ON(ENERGEST_TYPE_LISTEN);
      if(state() == CC1101_STATE_TX) {
#if DEBUG
        printf("didn't end ack tx (in %d, txbytes %d)\n", state(), txbytes());
#endif /* DEBUG */
        check_txfifo();
        flushrx();
      }
    }
    memcpy((void *)packet_rx, rxstate.buf,
           rxstate.len + AUX_LEN);
    packet_rx_len = rxstate.len + AUX_LEN; /* including AUX */

    process_poll(&cc1101_process);
#if DEBUG
    printf("#");
#endif /* DEBUG */
  }
      }
    }
  }
  rxstate.receiving = 0;

  PT_END(&rxstate.pt);
}
示例#13
0
文件: xmac.c 项目: kincki/contiki
/*---------------------------------------------------------------------------*/
static char 
powercycle(struct rtimer *t, void *ptr)
{
  int r;
#if WITH_TIMESYNCH
  rtimer_clock_t should_be, adjust;
#endif /* WITH_TIMESYNCH */

  CPRINTF("*");
  
  PT_BEGIN(&pt);

  while(1) {
    /* Only wait for some cycles to pass for someone to start sending */
    if(someone_is_sending > 0) {
      someone_is_sending--;
    }

    if(xmac_config.off_time > 0) {
      if(waiting_for_packet == 0) {
	if(we_are_sending == 0) {
	  off();
	}
      } else {
	waiting_for_packet++;
	if(waiting_for_packet > 2) {
	  /* We should not be awake for more than two consecutive
	     power cycles without having heard a packet, so we turn off
	     the radio. */
	  waiting_for_packet = 0;
#if WITH_TIMETABLE
	  TIMETABLE_TIMESTAMP(xmac_timetable, "off waiting");
#endif
	  off();
	}
      }

#if WITH_TIMESYNCH
#define NUM_SLOTS 8
      should_be = ((timesynch_rtimer_to_time(RTIMER_TIME(t)) +
		    xmac_config.off_time) &
		   ~(xmac_config.off_time + xmac_config.on_time - 1)) +
	(rimeaddr_node_addr.u8[0] % NUM_SLOTS *
	 ((xmac_config.off_time + xmac_config.on_time) / NUM_SLOTS));

      should_be = timesynch_time_to_rtimer(should_be);

      if(should_be - RTIMER_TIME(t) > xmac_config.off_time) {
	adjust = xmac_config.off_time / 2;
      } else {
	adjust = should_be - RTIMER_TIME(t);
      }
      r = rtimer_set(t, RTIMER_TIME(t) + adjust, 1,
		     (void (*)(struct rtimer *, void *))powercycle, ptr);
#else /* WITH_TIMESYNCH */
      r = rtimer_set(t, RTIMER_TIME(t) + xmac_config.off_time, 1,
		     TC(powercycle), ptr);
#endif /* WITH_TIMESYNCH */
      if(r) {
	PRINTF("xmac: 1 could not set rtimer %d\n", r);
      }
      PT_YIELD(&pt);
    }

    if(we_are_sending == 0 &&
       waiting_for_packet == 0) {
      on();
    }
    r = rtimer_set(t, RTIMER_TIME(t) + xmac_config.on_time, 1,
		   TC(powercycle), ptr);
    if(r) {
      PRINTF("xmac: 3 could not set rtimer %d\n", r);
    }

    PT_YIELD(&pt);
  }

  PT_END(&pt);
}
示例#14
0
bool DWM1000_Tag::dispatch(Msg& msg) {
	PT_BEGIN()
	PT_WAIT_UNTIL(msg.is(0, SIG_INIT));
	init();

	POLL_SEND: {
		while (true) {
			timeout(1000);				// delay  between POLL
			PT_YIELD_UNTIL(timeout());
			/* Write frame data to DW1000 and prepare transmission. See NOTE 7 below. */
			tx_poll_msg[ALL_MSG_SN_IDX] = frame_seq_nb;
			dwt_writetxdata(sizeof(tx_poll_msg), tx_poll_msg, 0);
			dwt_writetxfctrl(sizeof(tx_poll_msg), 0);

			/* Start transmission, indicating that a response is expected so that reception is enabled automatically after the frame is sent and the delay
			 * set by dwt_setrxaftertxdelay() has elapsed. */
			LOG<< " Start TXF " << FLUSH;
			dwt_starttx(DWT_START_TX_IMMEDIATE | DWT_RESPONSE_EXPECTED);// SEND POLL MSG
			dwt_setinterrupt(DWT_INT_TFRS, 0);
			dwt_setinterrupt(DWT_INT_RFCG, 1);	// enable
			clearInterrupt();
			_timeoutCounter = 0;

			/* We assume that the transmission is achieved correctly, poll for reception of a frame or error/timeout. See NOTE 8 below. */
			timeout(10);
			PT_YIELD_UNTIL(timeout() || isInterruptDetected());	// WAIT RESP MSG

			if (isInterruptDetected())
				LOG<< " INTERRUPT DETECTED " << FLUSH;

			status_reg = dwt_read32bitreg(SYS_STATUS_ID);
			LOG<< HEX <<" SYS_STATUS " << status_reg << FLUSH;
			if (status_reg == 0xDEADDEAD) {
				init();
			} else if (status_reg & SYS_STATUS_RXFCG)
				goto RESP_RECEIVED;
			else if (status_reg & SYS_STATUS_ALL_RX_ERR) {

				if (status_reg & SYS_STATUS_RXRFTO)
					INFO(" RX Timeout");
				else
					INFO(" RX error ");
				dwt_write32bitreg(SYS_STATUS_ID, SYS_STATUS_ALL_RX_ERR); /* Clear RX error events in the DW1000 status register. */

			}
		}

	}
	RESP_RECEIVED: {

		LOG<< " Received " <<FLUSH;

		frame_seq_nb++; /* Increment frame sequence number after transmission of the poll message (modulo 256). */
		uint32 frame_len;

		/* Clear good RX frame event and TX frame sent in the DW1000 status register. */
		dwt_write32bitreg(SYS_STATUS_ID,
				SYS_STATUS_RXFCG | SYS_STATUS_TXFRS);

		/* A frame has been received, read iCHANGEt into the local buffer. */
		frame_len =
		dwt_read32bitreg(RX_FINFO_ID) & RX_FINFO_RXFLEN_MASK;
		if (frame_len <= RX_BUF_LEN) {
			dwt_readrxdata(rx_buffer, frame_len, 0);
		}

		/* Check that the frame is the expected response from the companion "DS TWR responder" example.
		 * As the sequence number field of the frame is not relevant, it is cleared to simplify the validation of the frame. */
		rx_buffer[ALL_MSG_SN_IDX] = 0;
		if (memcmp(rx_buffer, rx_resp_msg, ALL_MSG_COMMON_LEN) == 0) {	// CHECK RESP MSG
			uint32 final_tx_time;

			/* Retrieve poll transmission and response reception timestamp. */
			poll_tx_ts = get_tx_timestamp_u64();
			resp_rx_ts = get_rx_timestamp_u64();

			/* Compute final message transmission time. See NOTE 9 below. */
			final_tx_time = (resp_rx_ts
					+ (RESP_RX_TO_FINAL_TX_DLY_UUS * UUS_TO_DWT_TIME))
			>> 8;
			dwt_setdelayedtrxtime(final_tx_time);

			/* Final TX timestamp is the transmission time we programmed plus the TX antenna delay. */
			final_tx_ts = (((uint64) (final_tx_time & 0xFFFFFFFE)) << 8)
			+ TX_ANT_DLY;

			/* Write all timestamps in the final message. See NOTE 10 below. */
			final_msg_set_ts(&tx_final_msg[FINAL_MSG_POLL_TX_TS_IDX],
					poll_tx_ts);
			final_msg_set_ts(&tx_final_msg[FINAL_MSG_RESP_RX_TS_IDX],
					resp_rx_ts);
			final_msg_set_ts(&tx_final_msg[FINAL_MSG_FINAL_TX_TS_IDX],
					final_tx_ts);

			/* Write and send final message. See NOTE 7 below. */
			tx_final_msg[ALL_MSG_SN_IDX] = frame_seq_nb;
			dwt_writetxdata(sizeof(tx_final_msg), tx_final_msg, 0);
			dwt_writetxfctrl(sizeof(tx_final_msg), 0);
			dwt_starttx(DWT_START_TX_DELAYED);				// SEND FINAL MSG

			/* Poll DW1000 until TX frame sent event set. See NOTE 8 below. */
			timeout(10);
			PT_YIELD_UNTIL((dwt_read32bitreg(SYS_STATUS_ID) & SYS_STATUS_TXFRS) || timeout());;
			/* Clear TXFRS event. */
			dwt_write32bitreg(SYS_STATUS_ID, SYS_STATUS_TXFRS);

			/* Increment frame sequence number after transmission of the final message (modulo 256). */
			frame_seq_nb++;
		} else {
示例#15
0
/*---------------------------------------------------------------------------*/
static
PT_THREAD(connect_pt(struct pt* pt, struct mqtt_connection* conn))
{
  PT_BEGIN(pt);

  DBG("MQTT - Sending CONNECT message...\r\n");

  /* Set up FHDR */
  conn->out_packet.fhdr = MQTT_FHDR_MSG_TYPE_CONNECT;
  conn->out_packet.remaining_length = 0;
  conn->out_packet.remaining_length += MQTT_connect_vhdr_flags_SIZE;
  conn->out_packet.remaining_length += MQTT_STRING_LENGTH(&conn->client_id);
  conn->out_packet.remaining_length += MQTT_STRING_LENGTH(&conn->credentials.username);
  conn->out_packet.remaining_length += MQTT_STRING_LENGTH(&conn->credentials.password);
  conn->out_packet.remaining_length += MQTT_STRING_LENGTH(&conn->will.topic);
  conn->out_packet.remaining_length += MQTT_STRING_LENGTH(&conn->will.message);
  encode_remaining_length(conn->out_packet.remaining_length_enc,
                          &conn->out_packet.remaining_length_enc_bytes,
                          conn->out_packet.remaining_length);
  if(conn->out_packet.remaining_length_enc_bytes > 4) {
    call_event(conn, MQTT_EVENT_PROTOCOL_ERROR, NULL);
    printf("MQTT - Error, remaining length > 4 bytes\r\n");
    PT_EXIT(pt);
  }

  /* Write Fixed Header */
  PT_MQTT_WRITE_BYTE(conn, conn->out_packet.fhdr);
  PT_MQTT_WRITE_BYTES(conn,
                      conn->out_packet.remaining_length_enc,
                      conn->out_packet.remaining_length_enc_bytes);
  PT_MQTT_WRITE_BYTE(conn, 0);
  PT_MQTT_WRITE_BYTE(conn, 6);
  PT_MQTT_WRITE_BYTES(conn, (uint8_t*)MQTT_PROTOCOL_NAME, 6);
  PT_MQTT_WRITE_BYTE(conn, MQTT_PROTOCOL_VERSION);
  PT_MQTT_WRITE_BYTE(conn, conn->connect_vhdr_flags);
  PT_MQTT_WRITE_BYTE(conn, (conn->keep_alive >> 8));
  PT_MQTT_WRITE_BYTE(conn, (conn->keep_alive & 0x00FF));
  PT_MQTT_WRITE_BYTE(conn, conn->client_id.length << 8);
  PT_MQTT_WRITE_BYTE(conn, conn->client_id.length & 0x00FF);
  PT_MQTT_WRITE_BYTES(conn, conn->client_id.string, conn->client_id.length);
  if(conn->connect_vhdr_flags & MQTT_VHDR_WILL_FLAG) {
    PT_MQTT_WRITE_BYTE(conn, conn->will.topic.length << 8);
    PT_MQTT_WRITE_BYTE(conn, conn->will.topic.length & 0x00FF);
    PT_MQTT_WRITE_BYTES(conn, conn->will.topic.string, conn->will.topic.length);
    PT_MQTT_WRITE_BYTE(conn, conn->will.message.length << 8);
    PT_MQTT_WRITE_BYTE(conn, conn->will.message.length & 0x00FF);
    PT_MQTT_WRITE_BYTES(conn, conn->will.message.string, conn->will.message.length);
    DBG("MQTT - Setting will topic to '%s' %i bytes and message to '%s' %i bytes\r\n",
        conn->will.topic.string,
        conn->will.topic.length,
        conn->will.message.string,
        conn->will.message.length);
  }
  if(conn->connect_vhdr_flags & MQTT_VHDR_USERNAME_FLAG) {
    DBG("MQTT - Setting username\r\n");
    PT_MQTT_WRITE_BYTE(conn, conn->credentials.username.length << 8);
    PT_MQTT_WRITE_BYTE(conn, conn->credentials.username.length & 0x00FF);
    PT_MQTT_WRITE_BYTES(conn,
                        conn->credentials.username.string,
                        conn->credentials.username.length);
  }
  if(conn->connect_vhdr_flags & MQTT_VHDR_PASSWORD_FLAG) {
    DBG("MQTT - Setting password\r\n");    
    PT_MQTT_WRITE_BYTE(conn, conn->credentials.password.length << 8);
    PT_MQTT_WRITE_BYTE(conn, conn->credentials.password.length & 0x00FF);
    PT_MQTT_WRITE_BYTES(conn,
                        conn->credentials.password.string,
                        conn->credentials.password.length);
  }

  /* Send out buffer */
  send_out_buffer(conn);
  conn->state = MQTT_CONN_STATE_CONNECTING_TO_BROKER;

  /* Wait for CONNACK */
  reset_packet(&conn->in_packet);
  do {
    PT_WAIT_UNTIL(pt, conn->out_packet.qos_state == MQTT_QOS_STATE_GOT_ACK);
  } while(conn->out_packet.qos_state != MQTT_QOS_STATE_GOT_ACK);
  reset_packet(&conn->in_packet);

  DBG("MQTT - Done sending CONNECT since we got CONNACK!\r\n");

#if DEBUG_MQTT == 1
  DBG("MQTT - Sending CONNECT message: \r\n");
  uint16_t i;
  for( i = 0; i < (conn->out_buffer_ptr - conn->out_buffer); i++ ) {
    DBG( "%02X ", conn->out_buffer[i] );
  }
  DBG("\r\n");
#endif

  PT_END(pt);
}
示例#16
0
static 
PT_THREAD(data_write_thread(struct pt *pt))
{
PT_BEGIN(pt);

	char dataBuf[4096];

	static exosite_http_context_t *opContext;
	int status;

	do
	{
		printf("data_write_thread():\r\n");
		if(!is_http_op_context_existed(EXO_OP_MODE_WRITE))
			break;

		opContext = get_http_op_context(EXO_OP_MODE_WRITE);

		if(exoHttpContextQueue.deviceStatus != EXO_DEVICE_STATE_INITIALIZED)
		{
			struct pt actPt;

			PT_SPAWN(pt, &actPt, data_activate_thread(&actPt));

			exoHttpContextQueue.deviceStatus = EXO_DEVICE_STATE_INITIALIZED;
		}

		if(!build_http_msg(opContext))
		{
			release_op(opContext);
			break;
		}

		if(!exosite_pal_sock_write( &opContext->sock,
									opContext->pdu,
									strlen(opContext->pdu)))
		{
			opContext->opStatus = -1;

			opContext->resultCallback(	NULL,
										opContext->opStatus);

			close_socket(&opContext->sock);
			release_op(opContext);
			break;
		}

		PT_YIELD(pt);

		memset(dataBuf, 0, sizeof(dataBuf));
		size_t bufLen = sizeof(dataBuf);

		exosite_pal_timer_init(&opContext->waitTimer);
		exosite_pal_timer_countdown_ms(&opContext->waitTimer, WAIT_TIME_MS);

		bool isReadData = true;
		while(exosite_pal_sock_read(	&opContext->sock,
										dataBuf,
										&bufLen) == 0)
		{
			PT_YIELD(pt);
			if(exosite_pal_timer_expired(&opContext->waitTimer))
			{
				opContext->opStatus = -1;

				opContext->resultCallback(	NULL,
											opContext->opStatus);

				close_socket(&opContext->sock);
				release_op(opContext);

				isReadData = false;
				break;
			}
		}

		if(!isReadData)
			break;

		printf("data_write_thread(): got rsp\r\n");


		if(parse_rsp_status(dataBuf,
							bufLen,
							&status))
		{
			opContext->opStatus = status;
			opContext->resultCallback(	NULL,
										opContext->opStatus);

			release_op(opContext);

			check_http_error_status_to_determine_if_reset_cik(status);
		}

		printf("rsp status = %d\r\n", status);

		if(status == 401 || status == 403)
		{
			struct pt actPt;

			PT_SPAWN(pt, &actPt, data_activate_thread(&actPt));
		}
	} while(false);

PT_END(pt);
}
示例#17
0
/*---------------------------------------------------------------------------*/
static
PT_THREAD(publish_pt(struct pt* pt, struct mqtt_connection* conn))
{
  PT_BEGIN(pt);

  DBG("MQTT - Sending publish message! topic %s topic_length %i\r\n",
      conn->out_packet.topic,
      conn->out_packet.topic_length);
  DBG("MQTT - Buffer space is %i \r\n",
      &conn->out_buffer[MQTT_TCP_OUTPUT_BUFF_SIZE] - conn->out_buffer_ptr);



  /* Set up FHDR */
  conn->out_packet.fhdr = MQTT_FHDR_MSG_TYPE_PUBLISH |
                          conn->out_packet.qos << 1;
  if(conn->out_packet.retain == MQTT_RETAIN_ON) {
    conn->out_packet.fhdr |= MQTT_FHDR_RETAIN_FLAG;
  }
  conn->out_packet.remaining_length = MQTT_STRING_LEN_SIZE +
                                      conn->out_packet.topic_length +
                                      conn->out_packet.payload_size;
  if(conn->out_packet.qos > MQTT_QOS_LEVEL_0) {
    conn->out_packet.remaining_length += MQTT_MID_SIZE;
  }
  encode_remaining_length(conn->out_packet.remaining_length_enc,
                          &conn->out_packet.remaining_length_enc_bytes,
                          conn->out_packet.remaining_length);
  if(conn->out_packet.remaining_length_enc_bytes > 4) {
    call_event(conn, MQTT_EVENT_PROTOCOL_ERROR, NULL);
    printf("MQTT - Error, remaining length > 4 bytes\r\n");
    PT_EXIT(pt);
  }

  /* Write Fixed Header */
  PT_MQTT_WRITE_BYTE(conn, conn->out_packet.fhdr);
  PT_MQTT_WRITE_BYTES(conn,
                      conn->out_packet.remaining_length_enc,
                      conn->out_packet.remaining_length_enc_bytes);
  /* Write Variable Header */
  PT_MQTT_WRITE_BYTE(conn, (conn->out_packet.topic_length >> 8));
  PT_MQTT_WRITE_BYTE(conn, (conn->out_packet.topic_length & 0x00FF));
  PT_MQTT_WRITE_BYTES(conn,
                      conn->out_packet.topic,
                      conn->out_packet.topic_length);
  if(conn->out_packet.qos > MQTT_QOS_LEVEL_0) {
    PT_MQTT_WRITE_BYTE(conn, (conn->out_packet.mid << 8));
    PT_MQTT_WRITE_BYTE(conn, (conn->out_packet.mid & 0x00FF));
  }
  /* Write Payload */
  PT_MQTT_WRITE_BYTES(conn,
                      conn->out_packet.payload,
                      conn->out_packet.payload_size);


  send_out_buffer(conn);

  /* If QoS is zero then wait until the message has been sent, since there is
   * no ACK to wait for.
   *
   * Also notify the app will not be notified via PUBACK or PUBCOMP */
  if(conn->out_packet.qos == 0) {
    PT_WAIT_UNTIL(pt, conn->out_buffer_sent);
    process_post(conn->app_process, mqtt_update_event, NULL);
  }
  if(conn->out_packet.qos == 1) {
    /* Wait for PUBACK */
    reset_packet(&conn->in_packet);
    do {
      PT_WAIT_UNTIL(pt, conn->out_packet.qos_state == MQTT_QOS_STATE_GOT_ACK);
    } while(conn->out_packet.qos_state != MQTT_QOS_STATE_GOT_ACK);
    if(conn->in_packet.mid != conn->out_packet.mid) {
      DBG("MQTT - Warning, got PUBACK with none matching MID. Currently there is"
          "no support for several concurrent PUBLISH messages.\r\n");
    }
  }
  if(conn->out_packet.qos == 2) {
    DBG("MQTT - QoS not implemented yet.\r\n");
    /* Should wait for PUBREC, send PUBREL and then wait for PUBCOMP */

  }
  reset_packet(&conn->in_packet);

  /* This is clear after the entire transaction is complete */
  conn->out_queue_full = 0;



  DBG("MQTT - Done writing publish message to out buffer!\r\n");
  PT_END(pt);
}
示例#18
0
static PT_THREAD (protothread_cmd(struct pt *pt))
{
    PT_BEGIN(pt);
      while(1) {
          
            // send the prompt via DMA to serial
            sprintf(PT_send_buffer,"cmd>");
            // by spawning a print thread
            PT_SPAWN(pt, &pt_DMA_output, PT_DMA_PutSerialBuffer(&pt_DMA_output) );
 
          //spawn a thread to handle terminal input
            // the input thread waits for input
            // -- BUT does NOT block other threads
            // string is returned in "PT_term_buffer"
            PT_SPAWN(pt, &pt_input, PT_GetSerialBuffer(&pt_input) );
            // returns when the thread dies
            // in this case, when <enter> is pushed
            // now parse the string
             sscanf(PT_term_buffer, "%s %d", cmd, &value);
         

             
              if (cmd[0]=='d' ) {
                //set mux to DSP chip
                mPORTAClearBits(BIT_4);
                mPORTBClearBits(BIT_13);
                mPORTASetBits(BIT_4);
                mPORTBClearBits(BIT_3 | BIT_7 | BIT_8 | BIT_9);
                 
                 if(((value << 6) & (0x0040))){
                     mPORTBSetBits(BIT_3);
                 }
                     //select sound effect
                 mPORTBSetBits(value << 6);
                 }
             if (cmd[0] == 's'){ //distortion
                 //set mux to Distortion
                mPORTAClearBits(BIT_4);
                mPORTBClearBits(BIT_13);
             }
             if (cmd[0] == 'n'){ //normal: only tone stack
                 //set mux to channel 0
                mPORTAClearBits(BIT_4);
                mPORTBClearBits(BIT_13);
                mPORTBSetBits(BIT_13);
             }
             //pots
             if (cmd[0] == 't'){ //treble
                // CS low to start transaction
                mPORTBClearBits(BIT_4); // start transaction
                deliverSPICh1Datum(value);
                // CS high
                mPORTBSetBits(BIT_4); // end transaction
             }
             if (cmd[0] == 'b'){ //bass
                // CS low to start transaction
                mPORTAClearBits(BIT_0); // start transaction
                deliverSPICh1Datum(value);
                // CS high
                mPORTASetBits(BIT_0); // end transaction
            }
            if (cmd[0] == 'v'){ //level
                // CS low to start transaction
                    mPORTAClearBits(BIT_2); // start transaction
                    deliverSPICh1Datum(value);                              
                     // CS high
                    mPORTASetBits(BIT_2); // end transaction
            }
            if (cmd[0] == 'm'){ //mid
                // CS low to start transaction
                mPORTAClearBits(BIT_3); // start transaction
                deliverSPICh1Datum(value);
                // CS high
                mPORTASetBits(BIT_3); // end transaction
            }
                          
            // never exit while
      } // END WHILE(1)
  PT_END(pt);
} // thread 3
示例#19
0
/*---------------------------------------------------------------------*/
static
PT_THREAD(recv_tcpthread(struct pt *pt))
{
  register int ret;
  
  PT_BEGIN(pt);

  /* Read the header. */
  PT_WAIT_UNTIL(pt, uip_newdata() && uip_datalen() > 0);

  if(uip_datalen() < sizeof(struct codeprop_tcphdr)) {
    PRINTF(("codeprop: header not found in first tcp segment\n"));
    uip_abort();
    goto thread_done;
  }

  s.len = htons(((struct codeprop_tcphdr *)uip_appdata)->len);
  s.addr = 0;
  uip_appdata += sizeof(struct codeprop_tcphdr);
  uip_len -= sizeof(struct codeprop_tcphdr);

  ret = xmem_erase(XMEM_ERASE_UNIT_SIZE, EEPROMFS_ADDR_CODEPROP);
  assert(ret == 0);

  /* Read the rest of the data. */
  do {      
    if(uip_len > 0) {
      ret = xmem_pwrite(uip_appdata, uip_len, EEPROMFS_ADDR_CODEPROP + s.addr);
      assert(ret = uip_len);
      s.addr += uip_len;
    }
    if(s.addr < s.len) {
      PT_YIELD_UNTIL(pt, uip_newdata());
    }	
  } while(s.addr < s.len);

  /* Kill old program. */
  cmod_unload(0);

  /* Link, load, and start new program. */
  int s;
  static char msg[30 + 10];
  cle_scratch elfloader_unknown;
  s = cmod_load(0, elfloader_unknown, xmem_pread, EEPROMFS_ADDR_CODEPROP);
  if (s == CMOD_OK)
    sprintf(msg, "ok\n");
  else
    sprintf(msg, "err %d %s\n", s, elfloader_unknown);
    
  /* Return "ok" message. */
  do {
    s = strlen(msg);
    uip_send(msg, s);
    PT_WAIT_UNTIL(pt, uip_acked() || uip_rexmit() || uip_closed());
  } while(uip_rexmit());

  /* Close the connection. */
  uip_close();
    
 thread_done:;
  PT_END(pt);
}
示例#20
0
static
PT_THREAD(handle_script(struct httpd_state *s))
{
	/* Note script includes will attach a leading : to the filename and a trailing zero */
	static char scriptname[MAX_SCRIPT_NAME_LENGTH+1],*pptr;
	static uint16_t filelength;

	PT_BEGIN(&s->scriptpt);

	filelength=s->file.len;
	while(s->file.len > 0) {
		/* Sanity check */
		if (s->file.len > filelength) break;

		/* Check if we should start executing a script, flagged by %! */
		if(httpd_fs_getchar(s->file.data) == ISO_percent &&
				httpd_fs_getchar(s->file.data + 1) == ISO_bang) {

			/* Extract name, if starts with colon include file else call cgi */
			s->scriptptr=get_scriptname(scriptname,s->file.data+2);
			s->scriptlen=s->file.len-(s->scriptptr-s->file.data);
			PRINTF("httpd: Handle script named %s\n",scriptname);
			if(scriptname[0] == ISO_colon) {
				if (httpd_fs_open(&scriptname[1], &s->file)) {
					PT_WAIT_THREAD(&s->scriptpt, send_file(s));
				}
			} else {
				PT_WAIT_THREAD(&s->scriptpt,httpd_cgi(scriptname)(s, s->scriptptr));
			}
			next_scriptstate(s);

			/* Reset the pointers and continue sending the current file. */
			s->file.data = s->scriptptr;
			s->file.len  = s->scriptlen;
		} else {

			/* Send file up to the next potential script */
			if(s->file.len > uip_mss()) {
				s->len = uip_mss();
			} else {
				s->len = s->file.len;
			}

			if(httpd_fs_getchar(s->file.data) == ISO_percent) {
				pptr = (char *) httpd_fs_strchr(s->file.data + 1, ISO_percent);
			} else {
				pptr = (char *) httpd_fs_strchr(s->file.data, ISO_percent);
			}

			if(pptr != NULL && pptr != s->file.data) {
				s->len = (int)(pptr - s->file.data);
				if(s->len >= uip_mss()) {
					s->len = uip_mss();
				}
			}
			PRINTF("httpd: Sending %u bytes from 0x%04x\n",s->file.len,(unsigned int)s->file.data);
			PT_WAIT_THREAD(&s->scriptpt, send_part_of_file(s));
			s->file.data += s->len;
			s->file.len  -= s->len;
		}
	}

	PT_END(&s->scriptpt);
}
示例#21
0
/*---------------------------------------------------------------------*/
static
PT_THREAD(recv_udpthread(struct pt *pt))
{
  int len;
  struct codeprop_udphdr *uh = (struct codeprop_udphdr *)uip_appdata;
  
  /*  if(uip_newdata()) {
    PRINTF(("recv_udpthread: id %d uh->id %d\n", s.id, uip_htons(uh->id)));
    }*/
  
  PT_BEGIN(pt);
  
  while(1) {

    do {
      PT_WAIT_UNTIL(pt, uip_newdata() &&
		    uh->type == UIP_HTONS(TYPE_DATA) &&
		    uip_htons(uh->id) > s.id);
      
      if(uip_htons(uh->addr) != 0) {
	s.addr = 0;
	send_nack(uh, 0);
      }
      
    } while(uip_htons(uh->addr) != 0);

    leds_on(LEDS_YELLOW);
    
    s.addr = 0;
    s.id = uip_htons(uh->id);
    s.len = uip_htons(uh->len);
    
    timer_set(&s.timer, CONNECTION_TIMEOUT);
    process_post(PROCESS_BROADCAST, codeprop_event_quit, (process_data_t)NULL);

    while(s.addr < s.len) {
            
      if(uip_htons(uh->addr) == s.addr) {
	leds_blink();
	len = uip_datalen() - UDPHEADERSIZE;
	if(len > 0) {
	  eeprom_write(EEPROMFS_ADDR_CODEPROP + s.addr,
		       &uh->data[0], len);
	  PRINTF(("Saved %d bytes at address %d, %d bytes left\n",
		  uip_datalen() - UDPHEADERSIZE, s.addr,
		  s.len - s.addr));
	  
	  s.addr += len;
	}
	
      } else if(uip_htons(uh->addr) > s.addr) {
	PRINTF(("sending nack since 0x%x != 0x%x\n", uip_htons(uh->addr), s.addr));
	send_nack(uh, s.addr);
      }

      if(s.addr < s.len) {

	/*	timer_set(&s.nacktimer, NACK_TIMEOUT);*/

	do {
	  timer_set(&s.nacktimer, HIT_NACK_TIMEOUT);
	  PT_YIELD_UNTIL(pt, timer_expired(&s.nacktimer) ||
			 (uip_newdata() &&
			  uh->type == UIP_HTONS(TYPE_DATA) &&
			  uip_htons(uh->id) == s.id));
	  if(timer_expired(&s.nacktimer)) {
	    send_nack(uh, s.addr);
	  }
	} while(timer_expired(&s.nacktimer));
      }
      
    }

    leds_off(LEDS_YELLOW);
    /*    printf("Received entire bunary over udr\n");*/
    process_post(PROCESS_BROADCAST, codeprop_event_quit, (process_data_t)NULL);
    process_post(&codeprop_process, EVENT_START_PROGRAM, NULL);
    PT_EXIT(pt);
  }
  
  PT_END(pt);
}
示例#22
0
static
PT_THREAD(recv_tcpthread(struct pt *pt))
{
  struct codeprop_tcphdr *th;
  int datalen = uip_datalen();
  PT_BEGIN(pt);

  while(1) {

    PT_WAIT_UNTIL(pt, uip_connected());

    codeprop_exit_program();
    
    s.state = STATE_RECEIVING_TCPDATA;

    s.addr = 0;
    s.count = 0;

    /* Read the header. */
    PT_WAIT_UNTIL(pt, uip_newdata() && uip_datalen() > 0);

    if(uip_datalen() < CODEPROP_TCPHDR_SIZE) {
      PRINTF(("codeprop: header not found in first tcp segment\n"));
      uip_abort();
    }
    th = (struct codeprop_tcphdr *)uip_appdata;
    s.len = uip_htons(th->len);
    s.addr = 0;
    uip_appdata += CODEPROP_TCPHDR_SIZE;
    datalen -= CODEPROP_TCPHDR_SIZE;
    
    /* Read the rest of the data. */
    do {
      if(datalen > 0) {
	/* printf("Got %d bytes\n", datalen); */

	if (cfs_seek(fd, s.addr, CFS_SEEK_SET) != s.addr) {
	   PRINTF(("codeprop: seek in buffer file failed\n"));
	   uip_abort();
	}
					     
	if (cfs_write(fd, uip_appdata, datalen) != datalen) {
	  PRINTF(("codeprop: write to buffer file failed\n"));
	  uip_abort();
	}
	s.addr += datalen;
      }
      if(s.addr < s.len) {
	PT_YIELD_UNTIL(pt, uip_newdata());
      }
    } while(s.addr < s.len);
#if 1
    
    {
      static int err;
      
      err = codeprop_start_program();
      
      /* Print out the "OK"/error message. */
      do {
	if (err >= 0 && err < sizeof(err_msgs)/sizeof(char*)) {
	  uip_send(err_msgs[err], strlen(err_msgs[err]));
	} else {
	  uip_send("Unknown error\r\n", 15);
	}
	PT_WAIT_UNTIL(pt, uip_acked() || uip_rexmit() || uip_closed());
      } while(uip_rexmit());
      
      /* Close the connection. */
      uip_close();
    }
#endif
    ++s.id;
    s.state = STATE_SENDING_UDPDATA;
    tcpip_poll_udp(udp_conn);

    PT_WAIT_UNTIL(pt, s.state != STATE_SENDING_UDPDATA);
    /*    printf("recv_tcpthread: unblocked\n");*/
  }

  PT_END(pt);
}
示例#23
0
/*---------------------------------------------------------------------------*/
static char
powercycle(struct rtimer *t, void *ptr)
{
  PT_BEGIN(&pt);

  cycle_start = RTIMER_NOW();
  
  while(1) {
    static uint8_t packet_seen;
    static rtimer_clock_t t0;
    static uint8_t count;

    cycle_start += CYCLE_TIME;

    if(WITH_STREAMING && is_streaming) {
      if(!RTIMER_CLOCK_LT(RTIMER_NOW(), stream_until)) {
        is_streaming = 0;
        rimeaddr_copy(&is_streaming_to, &rimeaddr_null);
        rimeaddr_copy(&is_streaming_to_too, &rimeaddr_null);
      }
    }

    packet_seen = 0;

    do {
      for(count = 0; count < CCA_COUNT_MAX; ++count) {
        t0 = RTIMER_NOW();
        if(we_are_sending == 0) {
          powercycle_turn_radio_on();
          /* Check if a packet is seen in the air. If so, we keep the
             radio on for a while (LISTEN_TIME_AFTER_PACKET_DETECTED) to
             be able to receive the packet. We also continuously check
             the radio medium to make sure that we wasn't woken up by a
             false positive: a spurious radio interference that was not
             caused by an incoming packet. */
          if(NETSTACK_RADIO.channel_clear() == 0) {
            packet_seen = 1;
            break;
          }
          powercycle_turn_radio_off();
        }
        schedule_powercycle_fixed(t, RTIMER_NOW() + CCA_SLEEP_TIME);
        PT_YIELD(&pt);
      }

      if(packet_seen) {
        static rtimer_clock_t start;
        static uint8_t silence_periods, periods;
        start = RTIMER_NOW();
        
        periods = silence_periods = 0;
        while(we_are_sending == 0 && radio_is_on &&
              RTIMER_CLOCK_LT(RTIMER_NOW(),
                              (start + LISTEN_TIME_AFTER_PACKET_DETECTED))) {
          
          /* Check for a number of consecutive periods of
             non-activity. If we see two such periods, we turn the
             radio off. Also, if a packet has been successfully
             received (as indicated by the
             NETSTACK_RADIO.pending_packet() function), we stop
             snooping. */
          if(NETSTACK_RADIO.channel_clear()) {
            ++silence_periods;
          } else {
            silence_periods = 0;
          }
          
          ++periods;
        
          if(NETSTACK_RADIO.receiving_packet()) {
            silence_periods = 0;
          }
          if(silence_periods > MAX_SILENCE_PERIODS) {
            powercycle_turn_radio_off();
            break;
          }
          if(WITH_FAST_SLEEP &&
             periods > MAX_NONACTIVITY_PERIODS &&
             !(NETSTACK_RADIO.receiving_packet() ||
               NETSTACK_RADIO.pending_packet())) {
            powercycle_turn_radio_off();
            break;
          }
          if(NETSTACK_RADIO.pending_packet()) {
            break;
          }
          
          schedule_powercycle(t, CCA_CHECK_TIME + CCA_SLEEP_TIME);
          PT_YIELD(&pt);
        }
        if(radio_is_on) {
          if(!(NETSTACK_RADIO.receiving_packet() ||
               NETSTACK_RADIO.pending_packet()) ||
             !RTIMER_CLOCK_LT(RTIMER_NOW(),
                              (start + LISTEN_TIME_AFTER_PACKET_DETECTED))) {
            powercycle_turn_radio_off();
          }
        }
      }
    } while((is_snooping || is_streaming) &&
            RTIMER_CLOCK_LT(RTIMER_NOW() - cycle_start, CYCLE_TIME - CHECK_TIME * 8));

    if(RTIMER_CLOCK_LT(RTIMER_NOW() - cycle_start, CYCLE_TIME - CHECK_TIME * 4)) {
      schedule_powercycle_fixed(t, CYCLE_TIME + cycle_start);
      PT_YIELD(&pt);
    }
  }

  PT_END(&pt);
}
示例#24
0
/*---------------------------------------------------------------------*/
static
PT_THREAD(recv_tcpthread(struct pt *pt))
{
  PT_BEGIN(pt);

  /* Read the header. */
  PT_WAIT_UNTIL(pt, uip_newdata() && uip_datalen() > 0);

  if(uip_datalen() < sizeof(struct codeprop_tcphdr)) {
    PRINTF(("codeprop: header not found in first tcp segment\n"));
    uip_abort();
    goto thread_done;
  }

  /* Kill old program. */
  rudolph0_stop(&rudolph0);
  /*  elfloader_unload();*/
  
  s.len = htons(((struct codeprop_tcphdr *)uip_appdata)->len);
  s.addr = 0;
  uip_appdata += sizeof(struct codeprop_tcphdr);
  uip_len -= sizeof(struct codeprop_tcphdr);

  s.fd = cfs_open("codeprop.out", CFS_WRITE);
  cfs_close(s.fd);
  /*  xmem_erase(XMEM_ERASE_UNIT_SIZE, EEPROMFS_ADDR_CODEPROP);*/

  /* Read the rest of the data. */
  do {
    leds_toggle(LEDS_RED);
    if(uip_len > 0) {
      s.fd = cfs_open("codeprop.out", CFS_WRITE + CFS_APPEND);
      cfs_seek(s.fd, s.addr, CFS_SEEK_SET);
      /*      xmem_pwrite(uip_appdata, uip_len, EEPROMFS_ADDR_CODEPROP + s.addr);*/
      cfs_write(s.fd, uip_appdata, uip_len);
      cfs_close(s.fd);
      
      PRINTF("Wrote %d bytes to file\n", uip_len);
      s.addr += uip_len;
    }
    if(s.addr < s.len) {
      PT_YIELD_UNTIL(pt, uip_newdata());
    }
  } while(s.addr < s.len);
  leds_off(LEDS_RED);

#if DEBUG
  {
    int i, fd, j;
    printf("Contents of file:\n");
    fd = cfs_open("codeprop.out", CFS_READ);
    j = 0;
    printf("\n0x%04x: ", 0);
    for(i = 0; i < s.len; ++i) {
      unsigned char byte;
      cfs_read(fd, &byte, 1);
      printf("0x%02x, ", byte);
      ++j;
      if(j == 8) {
	printf("\n0x%04x: ", i + 1);
	j = 0;
      }
      clock_delay(400);
    }
    cfs_close(fd);
  }
#endif

  int ret;
  
  ret = start_program();
  
#if CONTIKI_TARGET_NETSIM
  rudolph0_send(&rudolph0, CLOCK_SECOND / 4);
#else /* CONTIKI_TARGET_NETSIM */
  if(ret == ELFLOADER_OK) {
    /* Propagate program. */
    rudolph0_send(&rudolph0, CLOCK_SECOND / 4);
  }
#endif /* CONTIKI_TARGET_NETSIM */
  
  /* Return "ok" message. */
  do {
    ret = strlen(msg);
    uip_send(msg, ret);
    PT_WAIT_UNTIL(pt, uip_acked() || uip_rexmit() || uip_closed());
  } while(uip_rexmit());

  /* Close the connection. */
  uip_close();

    
 thread_done:;
  PT_END(pt);
}
示例#25
0
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_dhcp(process_event_t ev, void *data))
{
  clock_time_t ticks;

  PT_BEGIN(&s.pt);
  
 init:
  xid++;
  s.state = STATE_SENDING;
  s.ticks = CLOCK_SECOND * 4;
  while(1) {
    while(ev != tcpip_event) {
      tcpip_poll_udp(s.conn);
      PT_YIELD(&s.pt);
    }
    send_discover();
    etimer_set(&s.etimer, s.ticks);
    do {
      PT_YIELD(&s.pt);
      if(ev == tcpip_event && uip_newdata() && msg_for_me() == DHCPOFFER) {
	parse_msg();
	s.state = STATE_OFFER_RECEIVED;
	goto selecting;
      }
    } while(!etimer_expired(&s.etimer));

    if(s.ticks < CLOCK_SECOND * 60) {
      s.ticks *= 2;
    }
  }
  
 selecting:
  s.ticks = CLOCK_SECOND;
  do {
    while(ev != tcpip_event) {
      tcpip_poll_udp(s.conn);
      PT_YIELD(&s.pt);
    }
    send_request();
    etimer_set(&s.etimer, s.ticks);
    do {
      PT_YIELD(&s.pt);
      if(ev == tcpip_event && uip_newdata() && msg_for_me() == DHCPACK) {
	parse_msg();
	s.state = STATE_CONFIG_RECEIVED;
	goto bound;
      }
    } while (!etimer_expired(&s.etimer));

    if(s.ticks <= CLOCK_SECOND * 10) {
      s.ticks += CLOCK_SECOND;
    } else {
      goto init;
    }
  } while(s.state != STATE_CONFIG_RECEIVED);
  
 bound:
#if 0
  printf("Got IP address %d.%d.%d.%d\n", uip_ipaddr_to_quad(&s.ipaddr));
  printf("Got netmask %d.%d.%d.%d\n",	 uip_ipaddr_to_quad(&s.netmask));
  printf("Got DNS server %d.%d.%d.%d\n", uip_ipaddr_to_quad(&s.dnsaddr));
  printf("Got default router %d.%d.%d.%d\n",
	 uip_ipaddr_to_quad(&s.default_router));
  printf("Lease expires in %ld seconds\n",
	 uip_ntohs(s.lease_time[0])*65536ul + uip_ntohs(s.lease_time[1]));
#endif

  ip64_dhcpc_configured(&s);
  
#define MAX_TICKS (~((clock_time_t)0) / 2)
#define MAX_TICKS32 (~((uint32_t)0))
#define IMIN(a, b) ((a) < (b) ? (a) : (b))

  if((uip_ntohs(s.lease_time[0])*65536ul + uip_ntohs(s.lease_time[1]))*CLOCK_SECOND/2
     <= MAX_TICKS32) {
    s.ticks = (uip_ntohs(s.lease_time[0])*65536ul + uip_ntohs(s.lease_time[1])
	       )*CLOCK_SECOND/2;
  } else {
    s.ticks = MAX_TICKS32;
  }

  while(s.ticks > 0) {
    ticks = IMIN(s.ticks, MAX_TICKS);
    s.ticks -= ticks;
    etimer_set(&s.etimer, ticks);
    PT_YIELD_UNTIL(&s.pt, etimer_expired(&s.etimer));
  }

  if((uip_ntohs(s.lease_time[0])*65536ul + uip_ntohs(s.lease_time[1]))*CLOCK_SECOND/2
     <= MAX_TICKS32) {
    s.ticks = (uip_ntohs(s.lease_time[0])*65536ul + uip_ntohs(s.lease_time[1])
	       )*CLOCK_SECOND/2;
  } else {
    s.ticks = MAX_TICKS32;
  }

  /* renewing: */
  do {
    while(ev != tcpip_event) {
      tcpip_poll_udp(s.conn);
      PT_YIELD(&s.pt);
    }
    send_request();
    ticks = IMIN(s.ticks / 2, MAX_TICKS);
    s.ticks -= ticks;
    etimer_set(&s.etimer, ticks);
    do {
      PT_YIELD(&s.pt);
      if(ev == tcpip_event && uip_newdata() && msg_for_me() == DHCPACK) {
	parse_msg();
	goto bound;
      }
    } while(!etimer_expired(&s.etimer));
  } while(s.ticks >= CLOCK_SECOND*3);

  /* rebinding: */

  /* lease_expired: */
  ip64_dhcpc_unconfigured(&s);
  goto init;

  PT_END(&s.pt);
}
static PT_THREAD(handle_bl(void))
{
	PT_BEGIN(&s.pt);
	s.retries = 3;
	do
	{
		flash_init();
		tftpc_init();
		tftpc_get(FIRMWARE_FILENAME);

		PT_WAIT_UNTIL(&s.pt, !tftpc_busy());

		uint8_t rc = tftpc_result();
		if(rc == TFTPC_FLASH_ERROR)
		{
			// any flash write errors, make sure the code doesn't run
			invalidate_code();
		}

		// valid app code in place?
		if(!check_valid_code())
		{
			// figure out what happened
			// and set indicator
			switch(rc) {
			case TFTPC_SUCCESS:
				diag_set(1);
				s.retries--;
				break;
			case TFTPC_SERVER_DOWN:
				diag_set(2);
				break;
			case TFTPC_FILE_NOT_FOUND:
				diag_set(3);
				break;
			case TFTPC_ERROR:
				diag_set(4);
				s.retries--;
				break;
			case TFTPC_FLASH_ERROR:
				diag_set(5);
				s.retries--;
				break;
			}

		}
		else
		{
			run_app();
		}

		timer_set(&s.timer, RETRY_TIME);
		PT_WAIT_UNTIL(&s.pt, timer_expired(&s.timer));
	} while (s.retries > 0);

	while(1)
	{
		PT_YIELD(&s.pt);
	}

	PT_END(&s.pt);
}
示例#27
0
/*---------------------------------------------------------------------------*/
static char
powercycle(struct rtimer *t, void *ptr)
{
#if SYNC_CYCLE_STARTS
  static volatile rtimer_clock_t sync_cycle_start;
  static volatile uint8_t sync_cycle_phase;
#endif

  PT_BEGIN(&pt);

#if SYNC_CYCLE_STARTS
  sync_cycle_start = RTIMER_NOW();
#else
  cycle_start = RTIMER_NOW();
#endif

  while(1) {
    static uint8_t packet_seen;
    static rtimer_clock_t t0;
    static uint8_t count;

#if SYNC_CYCLE_STARTS
    /* Compute cycle start when RTIMER_ARCH_SECOND is not a multiple
       of CHANNEL_CHECK_RATE */
    if(sync_cycle_phase++ == NETSTACK_RDC_CHANNEL_CHECK_RATE) {
      sync_cycle_phase = 0;
      sync_cycle_start += RTIMER_ARCH_SECOND;
      cycle_start = sync_cycle_start;
    } else {
#if (RTIMER_ARCH_SECOND * NETSTACK_RDC_CHANNEL_CHECK_RATE) > 65535
      cycle_start = sync_cycle_start + ((unsigned long)(sync_cycle_phase*RTIMER_ARCH_SECOND))/NETSTACK_RDC_CHANNEL_CHECK_RATE;
#else
      cycle_start = sync_cycle_start + (sync_cycle_phase*RTIMER_ARCH_SECOND)/NETSTACK_RDC_CHANNEL_CHECK_RATE;
#endif
    }
#else
    cycle_start += CYCLE_TIME;
#endif

    packet_seen = 0;

    for(count = 0; count < CCA_COUNT_MAX; ++count) {
      t0 = RTIMER_NOW();
      if(we_are_sending == 0 && we_are_receiving_burst == 0) {
        powercycle_turn_radio_on();
        /* Check if a packet is seen in the air. If so, we keep the
             radio on for a while (LISTEN_TIME_AFTER_PACKET_DETECTED) to
             be able to receive the packet. We also continuously check
             the radio medium to make sure that we wasn't woken up by a
             false positive: a spurious radio interference that was not
             caused by an incoming packet. */
        if(NETSTACK_RADIO.channel_clear() == 0) {
          packet_seen = 1;
          break;
        }
        powercycle_turn_radio_off();
      }
      schedule_powercycle_fixed(t, RTIMER_NOW() + CCA_SLEEP_TIME);
      PT_YIELD(&pt);
    }

    if(packet_seen) {
      static rtimer_clock_t start;
      static uint8_t silence_periods, periods;
      start = RTIMER_NOW();

      periods = silence_periods = 0;
      while(we_are_sending == 0 && radio_is_on &&
            RTIMER_CLOCK_LT(RTIMER_NOW(),
                            (start + LISTEN_TIME_AFTER_PACKET_DETECTED))) {

        /* Check for a number of consecutive periods of
             non-activity. If we see two such periods, we turn the
             radio off. Also, if a packet has been successfully
             received (as indicated by the
             NETSTACK_RADIO.pending_packet() function), we stop
             snooping. */
#if !RDC_CONF_HARDWARE_CSMA
       /* A cca cycle will disrupt rx on some radios, e.g. mc1322x, rf230 */
       /*TODO: Modify those drivers to just return the internal RSSI when already in rx mode */
        if(NETSTACK_RADIO.channel_clear()) {
          ++silence_periods;
        } else {
          silence_periods = 0;
        }
#endif

        ++periods;

        if(NETSTACK_RADIO.receiving_packet()) {
          silence_periods = 0;
        }
        if(silence_periods > MAX_SILENCE_PERIODS) {
          powercycle_turn_radio_off();
          break;
        }
        if(WITH_FAST_SLEEP &&
            periods > MAX_NONACTIVITY_PERIODS &&
            !(NETSTACK_RADIO.receiving_packet() ||
              NETSTACK_RADIO.pending_packet())) {
          powercycle_turn_radio_off();
          break;
        }
        if(NETSTACK_RADIO.pending_packet()) {
          break;
        }

        schedule_powercycle(t, CCA_CHECK_TIME + CCA_SLEEP_TIME);
        PT_YIELD(&pt);
      }
      if(radio_is_on) {
        if(!(NETSTACK_RADIO.receiving_packet() ||
             NETSTACK_RADIO.pending_packet()) ||
             !RTIMER_CLOCK_LT(RTIMER_NOW(),
                 (start + LISTEN_TIME_AFTER_PACKET_DETECTED))) {
          powercycle_turn_radio_off();
        }
      }
    }

    if(RTIMER_CLOCK_LT(RTIMER_NOW() - cycle_start, CYCLE_TIME - CHECK_TIME * 4)) {
      /* Schedule the next powercycle interrupt, or sleep the mcu
	 until then.  Sleeping will not exit from this interrupt, so
	 ensure an occasional wake cycle or foreground processing will
	 be blocked until a packet is detected */
#if RDC_CONF_MCU_SLEEP
      static uint8_t sleepcycle;
      if((sleepcycle++ < 16) && !we_are_sending && !radio_is_on) {
        rtimer_arch_sleep(CYCLE_TIME - (RTIMER_NOW() - cycle_start));
      } else {
        sleepcycle = 0;
        schedule_powercycle_fixed(t, CYCLE_TIME + cycle_start);
        PT_YIELD(&pt);
      }
#else
      schedule_powercycle_fixed(t, CYCLE_TIME + cycle_start);
      PT_YIELD(&pt);
#endif
    }
  }

  PT_END(&pt);
}
static char
powercycle(struct rtimer *t, void *ptr)
{
  PT_BEGIN(&pt);

  while(1) {
    static uint8_t packet_seen;
    static rtimer_clock_t t0;
    static uint8_t count;

    cycle_start = RTIMER_NOW();

    if(WITH_STREAMING && is_streaming) {
#if NURTIMER
      if(!RTIMER_CLOCK_LT(cycle_start, RTIMER_NOW(), stream_until))
#else
        if(!RTIMER_CLOCK_LT(RTIMER_NOW(), stream_until))
#endif
          {
            is_streaming = 0;
            rimeaddr_copy(&is_streaming_to, &rimeaddr_null);
            rimeaddr_copy(&is_streaming_to_too, &rimeaddr_null);
          }
    }

    packet_seen = 0;

    do {
      for(count = 0; count < CCA_COUNT_MAX; ++count) {
        t0 = RTIMER_NOW();
        if(we_are_sending == 0) {
          powercycle_turn_radio_on();
#if 0
#if NURTIMER
          while(RTIMER_CLOCK_LT(t0, RTIMER_NOW(), t0 + CCA_CHECK_TIME));
#else
          while(RTIMER_CLOCK_LT(RTIMER_NOW(), t0 + CCA_CHECK_TIME));
#endif
#endif /* 0 */
          /* Check if a packet is seen in the air. If so, we keep the
             radio on for a while (LISTEN_TIME_AFTER_PACKET_DETECTED) to
             be able to receive the packet. We also continuously check
             the radio medium to make sure that we wasn't woken up by a
             false positive: a spurious radio interference that was not
             caused by an incoming packet. */
          if(NETSTACK_RADIO.channel_clear() == 0) {
            packet_seen = 1;
            break;
          }
          powercycle_turn_radio_off();
        }
        schedule_powercycle_fixed(t, RTIMER_NOW() + CCA_SLEEP_TIME);
        /*        COOJA_DEBUG_STR("yield\n");*/
        PT_YIELD(&pt);
      }
      
      if(packet_seen) {
        static rtimer_clock_t start;
        static uint8_t silence_periods, periods;
        start = RTIMER_NOW();
        
        periods = silence_periods = 0;
        while(we_are_sending == 0 && radio_is_on &&
              RTIMER_CLOCK_LT(RTIMER_NOW(), (start + LISTEN_TIME_AFTER_PACKET_DETECTED))) {
          
          /* Check for a number of consecutive periods of
             non-activity. If we see two such periods, we turn the
             radio off. Also, if a packet has been successfully
             received (as indicated by the
             NETSTACK_RADIO.pending_packet() function), we stop
             snooping. */
          if(NETSTACK_RADIO.channel_clear()) {
            ++silence_periods;
          } else {
            silence_periods = 0;
          }
          
          ++periods;
        
          if(NETSTACK_RADIO.receiving_packet()) {
            silence_periods = 0;
          }
          if(silence_periods > MAX_SILENCE_PERIODS) {
            LEDS_ON(LEDS_RED);
            powercycle_turn_radio_off();
#if CONTIKIMAC_CONF_COMPOWER
            compower_accumulate(&compower_idle_activity);
#endif /* CONTIKIMAC_CONF_COMPOWER */
            LEDS_OFF(LEDS_RED);
            break;
          }
#if 1
          if(periods > MAX_NONACTIVITY_PERIODIC && !(NETSTACK_RADIO.receiving_packet() ||
                                                     NETSTACK_RADIO.pending_packet())) {
            LEDS_ON(LEDS_GREEN);
            powercycle_turn_radio_off();
#if CONTIKIMAC_CONF_COMPOWER
            compower_accumulate(&compower_idle_activity);
#endif /* CONTIKIMAC_CONF_COMPOWER */
            
            LEDS_OFF(LEDS_GREEN);
            break;
          }
#endif /* 0 */
          if(NETSTACK_RADIO.pending_packet()) {
            break;
          }
          
          schedule_powercycle(t, CCA_CHECK_TIME + CCA_SLEEP_TIME);
          LEDS_ON(LEDS_BLUE);
          PT_YIELD(&pt);
          LEDS_OFF(LEDS_BLUE);
        }
        if(radio_is_on && !(NETSTACK_RADIO.receiving_packet() ||
                            NETSTACK_RADIO.pending_packet())) {
          LEDS_ON(LEDS_RED + LEDS_GREEN);
          powercycle_turn_radio_off();
#if CONTIKIMAC_CONF_COMPOWER
          compower_accumulate(&compower_idle_activity);
#endif /* CONTIKIMAC_CONF_COMPOWER */
          LEDS_OFF(LEDS_RED + LEDS_GREEN);
        }
      } else {
#if CONTIKIMAC_CONF_COMPOWER
        compower_accumulate(&compower_idle_activity);
#endif /* CONTIKIMAC_CONF_COMPOWER */
      }
    } while(is_snooping &&
            RTIMER_CLOCK_LT(RTIMER_NOW() - cycle_start, CYCLE_TIME - CHECK_TIME));

    if(is_snooping) {
      LEDS_ON(LEDS_RED);
    }
    if(RTIMER_CLOCK_LT(RTIMER_NOW() - cycle_start, CYCLE_TIME)) {
      /*      schedule_powercycle(t, CYCLE_TIME - (RTIMER_NOW() - cycle_start));*/
      schedule_powercycle_fixed(t, CYCLE_TIME + cycle_start);
      /*      printf("cycle_start 0x%02x now 0x%02x wait 0x%02x\n",
              cycle_start, RTIMER_NOW(), CYCLE_TIME - (RTIMER_NOW() - cycle_start));*/
      PT_YIELD(&pt);
    }
    LEDS_OFF(LEDS_RED);
  }

  PT_END(&pt);
}
示例#29
0
bool  Wifi::dispatch(Msg& msg) {
//	INFO("line : %d ",_ptLine);
// INFO("msg : %d:%d",msg.src(),msg.signal());
PT_BEGIN();
INIT : {
	PT_WAIT_UNTIL(msg.is(0,SIG_INIT));
	struct station_config stationConf;

	INFO("WIFI_INIT");
	if ( wifi_set_opmode(STATION_MODE) ){
		; // STATIONAP_MODE was STATION_MODE
		INFO("line : %d",__LINE__);
		if ( wifi_set_phy_mode(PHY_MODE_11B)) {
			os_memset(&stationConf, 0, sizeof(struct station_config));
			ets_strncpy((char*)stationConf.ssid,_ssid,sizeof(stationConf.ssid));
			ets_strncpy((char*)stationConf.password,_pswd,sizeof(stationConf.password));
			stationConf.bssid_set=0;
			INFO("line : %d",__LINE__);
			if ( wifi_station_set_config(&stationConf) ){
				if ( wifi_station_connect() ){
					INFO("line : %d",__LINE__);
					goto DISCONNECTED;//	wifi_station_set_auto_connect(TRUE);
				}
			}
		}
	}
	//	wifi_station_set_auto_connect(FALSE);
	INFO(" WIFI INIT failed , retrying... ");
	goto INIT;
};
DISCONNECTED: {
	while(true) {
		timeout(1000);
		PT_YIELD_UNTIL(timeout());
		struct ip_info ipConfig;
		wifi_get_ip_info(STATION_IF, &ipConfig);
		wifiStatus = wifi_station_get_connect_status();
		if ( wifi_station_get_connect_status()== STATION_NO_AP_FOUND || wifi_station_get_connect_status()==STATION_WRONG_PASSWORD || wifi_station_get_connect_status()==STATION_CONNECT_FAIL)
		{
			INFO(" NOT CONNECTED ");
			wifi_station_connect();
		} else if (wifiStatus == STATION_GOT_IP && ipConfig.ip.addr != 0) {
			_connections++;
			union {
				uint32_t addr;
				uint8_t ip[4];
			} v;
			v.addr = ipConfig.ip.addr;
			INFO("  IP Address : %d.%d.%d.%d ",v.ip[0],v.ip[1],v.ip[2],v.ip[3]);
			INFO(" CONNECTED ");
			Msg::publish(this,SIG_CONNECTED);
			_connected=true;
			timeout(2000);
			goto CONNECTED;
		} else {
			INFO(" STATION_IDLE ");
		}
		timeout(500);
	}
};
CONNECTED : {
	while(true) {
		PT_YIELD_UNTIL(timeout());
		struct ip_info ipConfig;
		wifi_get_ip_info(STATION_IF, &ipConfig);
		wifiStatus = wifi_station_get_connect_status();
		if (wifiStatus != STATION_GOT_IP ) {
			Msg::publish(this,SIG_DISCONNECTED);
			timeout(500);
			_connected=false;
			goto DISCONNECTED;
		}
		timeout(2000);
	}

};
PT_END();

}
示例#30
0
/*---------------------------------------------------------------------------*/
static int
parse_header_byte(struct http_socket *s, char c)
{
  PT_BEGIN(&s->headerpt);

  memset(&s->header, -1, sizeof(s->header));

  /* Skip the HTTP response */
  while(c != ' ') {
    PT_YIELD(&s->headerpt);
  }

  /* Skip the space */
  PT_YIELD(&s->headerpt);
  /* Read three characters of HTTP status and convert to BCD */
  s->header.status_code = 0;
  for(s->header_chars = 0; s->header_chars < 3; s->header_chars++) {
    s->header.status_code = s->header.status_code << 4 | (c - '0');
    PT_YIELD(&s->headerpt);
  }

  if(s->header.status_code == 0x200 || s->header.status_code == 0x206) {
    /* Read headers until data */

    while(1) {
      /* Skip characters until end of line */
      do {
        while(c != '\r') {
          s->header_chars++;
          PT_YIELD(&s->headerpt);
        }
        s->header_chars++;
        PT_YIELD(&s->headerpt);
      } while(c != '\n');
      s->header_chars--;
      PT_YIELD(&s->headerpt);

      if(s->header_chars == 0) {
        /* This was an empty line, i.e. the end of headers */
        break;
      }

      /* Start of line */
      s->header_chars = 0;

      /* Read header field */
      while(c != ' ' && c != '\t' && c != ':' && c != '\r' &&
            s->header_chars < sizeof(s->header_field) - 1) {
        s->header_field[s->header_chars++] = c;
        PT_YIELD(&s->headerpt);
      }
      s->header_field[s->header_chars] = '\0';
      /* Skip linear white spaces */
      while(c == ' ' || c == '\t') {
        s->header_chars++;
        PT_YIELD(&s->headerpt);
      }
      if(c == ':') {
        /* Skip the colon */
        s->header_chars++;
        PT_YIELD(&s->headerpt);
        /* Skip linear white spaces */
        while(c == ' ' || c == '\t') {
          s->header_chars++;
          PT_YIELD(&s->headerpt);
        }
        if(!strcmp(s->header_field, "Content-Length")) {
          s->header.content_length = 0;
          while(isdigit((int)c)) {
            s->header.content_length = s->header.content_length * 10 + c - '0';
            s->header_chars++;
            PT_YIELD(&s->headerpt);
          }
        } else if(!strcmp(s->header_field, "Content-Range")) {
          /* Skip the bytes-unit token */
          while(c != ' ' && c != '\t') {
            s->header_chars++;
            PT_YIELD(&s->headerpt);
          }
          /* Skip linear white spaces */
          while(c == ' ' || c == '\t') {
            s->header_chars++;
            PT_YIELD(&s->headerpt);
          }
          s->header.content_range.first_byte_pos = 0;
          while(isdigit((int)c)) {
            s->header.content_range.first_byte_pos =
              s->header.content_range.first_byte_pos * 10 + c - '0';
            s->header_chars++;
            PT_YIELD(&s->headerpt);
          }
          /* Skip linear white spaces */
          while(c == ' ' || c == '\t') {
            s->header_chars++;
            PT_YIELD(&s->headerpt);
          }
          if(c == '-') {
            /* Skip the dash */
            s->header_chars++;
            PT_YIELD(&s->headerpt);
            /* Skip linear white spaces */
            while(c == ' ' || c == '\t') {
              s->header_chars++;
              PT_YIELD(&s->headerpt);
            }
            s->header.content_range.last_byte_pos = 0;
            while(isdigit((int)c)) {
              s->header.content_range.last_byte_pos =
                s->header.content_range.last_byte_pos * 10 + c - '0';
              s->header_chars++;
              PT_YIELD(&s->headerpt);
            }
            /* Skip linear white spaces */
            while(c == ' ' || c == '\t') {
              s->header_chars++;
              PT_YIELD(&s->headerpt);
            }
            if(c == '/') {
              /* Skip the slash */
              s->header_chars++;
              PT_YIELD(&s->headerpt);
              /* Skip linear white spaces */
              while(c == ' ' || c == '\t') {
                s->header_chars++;
                PT_YIELD(&s->headerpt);
              }
              if(c != '*') {
                s->header.content_range.instance_length = 0;
                while(isdigit((int)c)) {
                  s->header.content_range.instance_length =
                    s->header.content_range.instance_length * 10 + c - '0';
                  s->header_chars++;
                  PT_YIELD(&s->headerpt);
                }
              }
            }
          }
        }
      }
    }

    /* All headers read, now read data */
    call_callback(s, HTTP_SOCKET_HEADER, (void *)&s->header, sizeof(s->header));

    /* Should exit the pt here to indicate that all headers have been
       read */
    PT_EXIT(&s->headerpt);
  } else {
    if(s->header.status_code == 0x404) {
      printf("File not found\n");
    } else if(s->header.status_code == 0x301 || s->header.status_code == 0x302) {
      printf("File moved (not handled)\n");
    }

    call_callback(s, HTTP_SOCKET_ERR, (void *)&s->header, sizeof(s->header));
    tcp_socket_close(&s->s);
    removesocket(s);
    PT_EXIT(&s->headerpt);
  }


  PT_END(&s->headerpt);
}