예제 #1
0
/*
 =======================================================================================================================
 =======================================================================================================================
 */
static PT_THREAD(handle_input (struct httpd_state *s))
{
	PSOCK_BEGIN(&s->sin);

	PSOCK_READTO(&s->sin, ISO_space);

	if(strncmp(s->inputbuf, http_get, 4) != 0)
	{
		PSOCK_CLOSE_EXIT(&s->sin);
	}

	PSOCK_READTO(&s->sin, ISO_space);

	if(s->inputbuf[0] != ISO_slash)
	{
		PSOCK_CLOSE_EXIT(&s->sin);
	}

	if(s->inputbuf[1] == ISO_space)
	{
		strncpy(s->filename, http_index_html, sizeof(s->filename));
	}
	else
	{
		s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;

		/* Process any form input being sent to the server. */
		{
			/*
			 * extern void vApplicationProcessFormInput( char *pcInputString, long
			 * xInputLength ); £
			 * vApplicationProcessFormInput( s->inputbuf, PSOCK_DATALEN(&s->sin) );
			 */
		}

		strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
	}

	/* httpd_log_file(uip_conn->ripaddr, s->filename); */
	s->state = STATE_OUTPUT;

	while(1)
	{
		PSOCK_READTO(&s->sin, ISO_nl);

		if(strncmp(s->inputbuf, http_referer, 8) == 0)
		{
			s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;

			/* httpd_log(&s->inputbuf[9]); */
		}
	}

	PSOCK_END(&s->sin);
}
/*---------------------------------------------------------------------------*/
static PT_THREAD( handle_input ( struct httpd_state *s ) )
{
	PSOCK_BEGIN( &s->sin );
	( void ) PT_YIELD_FLAG;
	PSOCK_READTO( &s->sin, ISO_space );

	if( strncmp(s->inputbuf, http_get, 4) != 0 )
	{
		PSOCK_CLOSE_EXIT( &s->sin );
	}

	PSOCK_READTO( &s->sin, ISO_space );

	if( s->inputbuf[0] != ISO_slash )
	{
		PSOCK_CLOSE_EXIT( &s->sin );
	}

	if( s->inputbuf[1] == ISO_space )
	{
		strncpy( s->filename, http_index_html, sizeof(s->filename) );
	}
	else
	{
		s->inputbuf[PSOCK_DATALEN( &s->sin ) - 1] = 0;
		
		/* Process any form input being sent to the server. */
		#if UIP_CONF_PROCESS_HTTPD_FORMS == 1
		{
			extern void vApplicationProcessFormInput( char *pcInputString );
			vApplicationProcessFormInput( s->inputbuf );
		}
		#endif
		
		strncpy( s->filename, &s->inputbuf[0], sizeof(s->filename) );
	}

	/*  httpd_log_file(uip_conn->ripaddr, s->filename);*/
	s->state = STATE_OUTPUT;

	while( 1 )
	{
		PSOCK_READTO( &s->sin, ISO_nl );

		if( strncmp(s->inputbuf, http_referer, 8) == 0 )
		{
			s->inputbuf[PSOCK_DATALEN( &s->sin ) - 2] = 0;

			/*      httpd_log(&s->inputbuf[9]);*/
		}
	}

	PSOCK_END( &s->sin );
}
예제 #3
0
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_input(struct httpd_state *s))
{
  char *LEDptr;

  PSOCK_BEGIN(&s->sin);

  PSOCK_READTO(&s->sin, ISO_space);

  
  if(strncmp(s->inputbuf, http_get, 4) == 0) {

  PSOCK_READTO(&s->sin, ISO_space);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

  if(s->inputbuf[1] == ISO_space) {
    strncpy(s->filename, http_index_html, sizeof(s->filename));
  } else {
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
  }

  // Renesas ++
  LEDptr = strstr(s->inputbuf, "LEDA");

  if (LEDptr !=NULL)
  {
      strncpy(LEDbuf, (const char *)(LEDptr), sizeof(LEDbuf));
      LEDflag = 1;
  }
  // End of Renesas ++

  /*  httpd_log_file(uip_conn->ripaddr, s->filename);*/

  s->state = STATE_OUTPUT;

  while(1) {
	PSOCK_READTO(&s->sin, ISO_nl);

    if(strncmp(s->inputbuf, http_referer, 8) == 0) {
	  s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
	  /*      httpd_log(&s->inputbuf[9]);*/
	}
    }
  }else {
  PSOCK_CLOSE_EXIT(&s->sin);
  }
  
  PSOCK_END(&s->sin);
}
예제 #4
0
static int handle_connection(struct webserver_state *s) {
  PSOCK_BEGIN(&s->p);
  
  /* the incoming GET request will have the following format:
   * GET / HTTP/1.1 ....
   * we have to parse this string to determine the resource being requested
   * if the requested resource is not the root webpage ('/') then,
   * GET /<resource name> HTTP/1.1 ....
   * we should parse the specific resource and react appropriately
   */
  
  // read incoming data until we read a space character
  PSOCK_READTO(&s->p, ISO_space);
  
  // parse the data to determine if it was a GET request
  if(strncmp(s->inputbuf, http_get, 4) != 0) {
    PSOCK_CLOSE_EXIT(&s->p);
  }
  
  // continue reading until the next space character
  PSOCK_READTO(&s->p, ISO_space);
  
  // determine the requested resource
  // in this case, we check if the request was for the '/' root page
  // AKA index.html
  if(s->inputbuf[0] != ISO_slash) {
    // request for unknown webpage, close and exit
    PSOCK_CLOSE_EXIT(&s->p);
  }
  
  // This is the web page served by the webserver
  PSOCK_SEND_STR(&s->p, "<!DOCTYPE html PUBLIC \"-//W3C//DTD HTML 4.01//EN\" \"http://www.w3.org/TR/html4/strict.dtd\">\r\n");
  PSOCK_SEND_STR(&s->p, "<HTML>\r\n<HEAD>\r\n\t<META http-equiv=\"Content-type\" content=\"text/html;charset=UTF-8\">\r\n\t<TITLE>Arduino WiShield 2.0</TITLE>\r\n");
  PSOCK_SEND_STR(&s->p, "\t<STYLE type=\"text/css\">\r\n\t\tP,H1 {text-align: center;}\r\n\t</STYLE>\r\n</HEAD>\r\n<BODY>\r\n");
  PSOCK_SEND_STR(&s->p, "\t<H1>Hello World!! I am an Arduino with a WiShield 2.0</H1>\r\n\t<P><A href=\"T\">Toggle LED</A></P>\r\n");
  
  if(s->inputbuf[1] != ISO_space) {
    // request for a resource
    if(s->inputbuf[1] != ISO_T) {
      // not supported
      PSOCK_SEND_STR(&s->p, "\t<P>Request not supported</P>\r\n");
    } else {
      PSOCK_SEND_STR(&s->p, "\t<P>TOGGLE LED command received</P>\r\n");
      // Toggle WiShield 2.0 Led status
      digitalWrite(9, !digitalRead(9));
    }
  }
  
  PSOCK_SEND_STR(&s->p, "</BODY>\r\n</HTML>");
  PSOCK_CLOSE(&s->p);
  PSOCK_END(&s->p);
}
예제 #5
0
파일: httpd.c 프로젝트: Ayesha-N/6lbr
static
PT_THREAD(handle_input(struct httpd_state *s))
{
  PSOCK_BEGIN(&s->sin);

  PSOCK_READTO(&s->sin, ISO_space);

  if(strncmp(s->inputbuf, http_get, 4) == 0) {
    s->request_type = REQUEST_TYPE_GET;
  } else if(strncmp(s->inputbuf, http_put, 4) == 0) {
    s->request_type = REQUEST_TYPE_PUT;
  } else if(strncmp(s->inputbuf, http_post, 5) == 0) {
    s->request_type = REQUEST_TYPE_POST;
  } else if(strncmp(s->inputbuf, http_delete, 7) == 0) {
    s->request_type = REQUEST_TYPE_DELETE;
  } else {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ISO_space);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  s->query = NULL;
#if URLCONV
  s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
  urlconv_tofilename(s->filename, &s->query, s->inputbuf, sizeof(s->filename));
  if(s->filename[1] == 0) {
    strncpy(s->filename, http_index_html, sizeof(s->filename));
  }
#else /* URLCONV */
  if(s->inputbuf[1] == ISO_space) {
    strncpy(s->filename, http_index_html, sizeof(s->filename));
  } else {
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, s->inputbuf, sizeof(s->filename));
  }
#endif /* URLCONV */
  if(s->query) {
    LOG6LBR_6ADDR(DEBUG, &uip_conn->ripaddr, "Request for '%s?%s' from ", s->filename, s->query);
  } else {
    LOG6LBR_6ADDR(DEBUG, &uip_conn->ripaddr, "Request for '%s' from ", s->filename);
  }

  s->state = STATE_OUTPUT;

  while(1) {
    PSOCK_READTO(&s->sin, ISO_nl);
  }

  PSOCK_END(&s->sin);
}
예제 #6
0
static
PT_THREAD(handle_input(struct httpd_state *s))
{

  PSOCK_BEGIN(&s->sin); 

  PSOCK_READTO(&s->sin, ISO_space);

  if(httpd_strncmp(s->inputbuf, httpd_get, 4) != 0) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ISO_space);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

  if(s->inputbuf[1] == ISO_space) {
    httpd_strcpy(s->filename, httpd_indexfn);
  } else {
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
{
    /* Look for ?, if found strip file name and send any following text to the LCD */
    uint8_t i;
    for (i=0;i<sizeof(s->inputbuf);i++) {
      if (s->inputbuf[i]=='?') {
        raven_lcd_show_text(&s->inputbuf[i]);
        if (i<sizeof(s->filename)) s->filename[i]=0;
 //     s->inputbuf[i]=0; //allow multiple beeps with multiple ?'s
      }
      if (s->inputbuf[i]==0) break;
    }
}
  }

  webserver_log_file(&uip_conn->ripaddr, s->filename);

  s->state = STATE_OUTPUT;

  while(1) {
    PSOCK_READTO(&s->sin, ISO_nl);

    if(httpd_strncmp(s->inputbuf, httpd_ref, 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
      petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2);
      webserver_log(s->inputbuf);
    }
  }
  PSOCK_END(&s->sin);
}
예제 #7
0
파일: httpd.c 프로젝트: j0t4/espardino
/*---------------------------------------------------------------------------*/
static PT_THREAD (handle_input (struct httpd_state *s))
{
  PSOCK_BEGIN (&s->sin);

  PSOCK_READTO (&s->sin, ISO_space);

  if (strncmp (s->inputbuf, http_get, 4) != 0)
    PSOCK_CLOSE_EXIT (&s->sin);
  
  PSOCK_READTO (&s->sin, ISO_space);

  if (s->inputbuf [0] != ISO_slash)
    PSOCK_CLOSE_EXIT (&s->sin);

  if (s->inputbuf [1] == ISO_space)
    strncpy (s->filename, http_index_html, sizeof (s->filename));
  else 
  {
    char *c;

    s->inputbuf [PSOCK_DATALEN (&s->sin) - 1] = 0;

    if ((c = strstr (s->inputbuf, "?")))
      *c++ = '\0';

    strncpy (s->filename, &s->inputbuf [0], sizeof (s->filename));

    if (!strcmp (s->filename, "/led.shtml"))
    {
      if (c && strstr (c, "LED2=1"))
        GPIO0_FIOCLR = GPIO_IO_P11;
      else
        GPIO0_FIOSET = GPIO_IO_P11;
    }
  }

  s->state = STATE_OUTPUT;

  while (1) 
  {
    PSOCK_READTO (&s->sin, ISO_nl);

    if (strncmp (s->inputbuf, http_referer, 8) == 0)
      s->inputbuf [PSOCK_DATALEN (&s->sin) - 2] = 0;
  }

  PSOCK_END (&s->sin);
}
/*
 * Timesynch functionality
 */
static
PT_THREAD(timesynch(struct psock *p))
{
  PSOCK_BEGIN(p);
  printf("TIME: %d\n",clock_time());
  static TimesynchSRMsg time_pkt;
  memset(&time_pkt,0,sizeof(time_pkt));

  PSOCK_WAIT_UNTIL(p,PSOCK_NEWDATA(p));
  if(PSOCK_NEWDATA(p)){
    clock_time_t t2 = clock_time();
    PSOCK_READBUF(p);
    memcpy(&time_pkt,buffer,sizeof(time_pkt));
    
    time_pkt.t1 = time_pkt.t1;
    time_pkt.t2 = t2;
    time_pkt.t3 = clock_time();
    
    printf("Clock print: %u\n",clock_time());
    PSOCK_SEND(p,&time_pkt,sizeof(time_pkt));
    printf("Clock print: %u\n",clock_time());

    printf("T1: %u\n",time_pkt.t1);
    printf("T2: %u\n",time_pkt.t2);
    printf("T3: %u\n",time_pkt.t3);

  } else {
    printf("Timed out!\n");
    PSOCK_CLOSE_EXIT(p);
  }
  state = 4;
  PSOCK_END(p);
}
예제 #9
0
/*
 * The definition of the process.
 */
PROCESS_THREAD(sensor_psock_server_process, ev, data)
{
    PROCESS_BEGIN();

    tcp_listen(UIP_HTONS(1010));

    while(1) {

        PROCESS_WAIT_EVENT_UNTIL(ev == tcpip_event);

        if(uip_connected()) {

            PSOCK_INIT(&ps, buffer, sizeof(buffer));

            while(!(uip_aborted() || uip_closed() || uip_timedout())) {

                PROCESS_WAIT_EVENT_UNTIL(ev == tcpip_event);
                handle_connection(&ps);
            }
            PSOCK_CLOSE(&ps);
        }
    }

    PSOCK_CLOSE_EXIT(&ps);
    PROCESS_END();
}
예제 #10
0
static int handle_connection(struct webserver_state *s)
{
	PSOCK_BEGIN(&s->p);

	// the incoming GET request will have the following format:
	// GET / HTTP/1.1 ....
	// we have to parse this string to determine the resource being requested
	// if the requested resource is not the root webpage ('/') then,
	// GET /<resource name> HTTP/1.1 ....
	// we should parse the specific resource and react appropriately

	// read incoming data until we read a space character
	PSOCK_READTO(&s->p, ISO_space);

	// parse the data to determine if it was a GET request
	if(strncmp(s->inputbuf, http_get, 4) != 0) {
		PSOCK_CLOSE_EXIT(&s->p);
	}

	// continue reading until the next space character
	PSOCK_READTO(&s->p, ISO_space);

	// determine the requested resource
	// in this case, we check if the request was for the '/' root page
	// AKA index.html
	if(s->inputbuf[0] != ISO_slash) {
		// request for unknown webpage, close and exit
		PSOCK_CLOSE_EXIT(&s->p);
	}

	if(s->inputbuf[1] != ISO_space) {
		// request for unavailable resource
		// not supported, modify to add support for additional resources
		PSOCK_CLOSE_EXIT(&s->p);
	}

	lockstate = lockstate+1;

        PSOCK_SEND_STR(&s->p, "HTTP/1.1 200 OK\r\n");
	PSOCK_SEND_STR(&s->p, "Content-Type: text/html\r\n");
	PSOCK_SEND_STR(&s->p, "\r\n");
	PSOCK_SEND_STR(&s->p, "Hello World, I am WiShield");
	PSOCK_SEND_STR(&s->p, "<center><h1>Hello World!! I am Matt's WiShield.  Find me in webserver.c under PSOCK_SEND_STR.</h1></center>");
        PSOCK_GENERATOR_SEND(&s->p, fill_buf, 0);
	PSOCK_CLOSE(&s->p);
	PSOCK_END(&s->p);
}
예제 #11
0
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_input(struct httpd_state *s))
{
  PSOCK_BEGIN(&s->sin);

  PSOCK_READTO(&s->sin, ISO_space);
  
  if(strncmp(s->inputbuf, http_get, 4) != 0) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ISO_space);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

#if URLCONV
  s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
  urlconv_tofilename(s->filename, s->inputbuf, sizeof(s->filename));
#else /* URLCONV */
  if(s->inputbuf[1] == ISO_space) {
    strncpy(s->filename, http_index_htm, sizeof(s->filename));
  } else {
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, s->inputbuf, sizeof(s->filename));
  }
#endif /* URLCONV */

  petsciiconv_topetscii(s->filename, sizeof(s->filename));
  webserver_log_file(&uip_conn->ripaddr, s->filename);
  petsciiconv_toascii(s->filename, sizeof(s->filename));
  s->state = STATE_OUTPUT;

  while(1) {
    PSOCK_READTO(&s->sin, ISO_nl);

    if(strncmp(s->inputbuf, http_referer, 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
      petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2);
      webserver_log(s->inputbuf);
    }
  }
  
  PSOCK_END(&s->sin);
}
예제 #12
0
파일: httpd.c 프로젝트: hericz/atinom_banyu
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_input(struct httpd_state *s))
{
  PSOCK_BEGIN(&s->sin);

  PSOCK_READTO(&s->sin, ISO_space);
	//printf("http 1: %s\r\n", s->inputbuf);
  if(strncmp(s->inputbuf, http_get, 4) != 0) {
	
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ISO_space);
  //printf("http 2: %s\r\n", s->inputbuf);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

  if(s->inputbuf[1] == ISO_space) {
    strncpy(s->filename, http_index_html, sizeof(s->filename));
  } else {
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
  }

  //*  
   //httpd_log_file(uip_conn->ripaddr, s->filename);
  //*/
  
  s->state = STATE_OUTPUT;

  while(1) {
    PSOCK_READTO(&s->sin, ISO_nl);

    if(strncmp(s->inputbuf, http_referer, 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
      /*      httpd_log(&s->inputbuf[9]);*/
    }
  }
  
  PSOCK_END(&s->sin);
  //nEth = 0;
}
예제 #13
0
static uint16_t handle_connection(struct simple_httpd_state *s)
{
	PSOCK_BEGIN(&s->p);

	int comp;

	// the incoming GET request will have the following format:
	// GET / HTTP/1.1 ....
	// we have to parse this string to determine the resource being requested
	// if the requested resource is not the root webpage ('/') then,
	// GET /<resource name> HTTP/1.1 ....
	// we should parse the specific resource and react appropriately

	// read incoming data until we read a space character
	PSOCK_READTO(&s->p, ISO_space);

	// parse the data to determine if it was a GET request
	if((comp = strncmp_P((const char *)(s->inputbuf), (const char *)http_get, 4)) != 0)
	{
		PSOCK_CLOSE_EXIT(&s->p);
	}

	// continue reading until the next space character
	PSOCK_READTO(&s->p, ISO_space);

	// determine the requested resource
	// in this case, we check if the request was for the '/' root page
	// AKA index.html
	if(s->inputbuf[0] != ISO_slash){
		PSOCK_CLOSE_EXIT(&s->p);				// request for unknown webpage, close and exit
	}

	// not supported, modify to add support for additional resources
	if(s->inputbuf[1] != ISO_space){
		PSOCK_CLOSE_EXIT(&s->p);				// request for unavailable resource, close and exit
	}

	PSOCK_GENERATOR_SEND(&s->p, fill_buf, 0); 	// generate the web page response with fill_buf from PSTR variable

	PSOCK_CLOSE(&s->p);
	PSOCK_END(&s->p);
}
예제 #14
0
static
PT_THREAD(handle_input(struct httpd_state *s))
{

  PSOCK_BEGIN(&s->sin); 

  PSOCK_READTO(&s->sin, ISO_space);

  if(httpd_strncmp(s->inputbuf, httpd_get, 4) != 0) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ISO_space);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

  if(s->inputbuf[1] == ISO_space) {
    httpd_strcpy(s->filename, httpd_indexfn);
  } else {
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
  }

  webserver_log_file(&uip_conn->ripaddr, s->filename);

  s->state = STATE_OUTPUT;

  while(1) {
    PSOCK_READTO(&s->sin, ISO_nl);

    if(httpd_strncmp(s->inputbuf, httpd_ref, 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
      petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2);
      webserver_log(s->inputbuf);
    }
  }
  PSOCK_END(&s->sin);
}
예제 #15
0
파일: httpd-cfs.c 프로젝트: EDAyele/ptunes
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_input(struct httpd_state *s))
{
  PSOCK_BEGIN(&s->sin);

  PSOCK_READTO(&s->sin, ' ');
  
  if(strncmp(s->inputbuf, "GET ", 4) != 0) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ' ');

  if(s->inputbuf[0] != '/') {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

  if(s->inputbuf[1] == ' ') {
    strncpy(s->filename, "index.html", sizeof(s->filename));
  } else {
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, &s->inputbuf[1], sizeof(s->filename));
  }

  //  webserver_log_file(&uip_conn->ripaddr, s->filename);
  libputs_arch(s->filename);
  s->state = STATE_OUTPUT;

  while(1) {
    PSOCK_READTO(&s->sin, '\n');

    if(strncmp(s->inputbuf, "Referer:", 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
      libputs_arch(&s->inputbuf[9]);
      //      webserver_log(&s->inputbuf[9]);
    }
  }
  
  PSOCK_END(&s->sin);
}
예제 #16
0
파일: httpd.c 프로젝트: EDAyele/ptunes
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_input(struct httpd_state *s))
{
  PSOCK_BEGIN(&s->sin);

  PSOCK_READTO(&s->sin, ISO_space);
  
  if(strncmp(s->inputbuf, http_get, 4) != 0) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ISO_space);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

  if(s->inputbuf[1] == ISO_space) {
    strncpy(s->filename, http_index_html, sizeof(s->filename));
  } else {
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
  }

  libputs_arch(s->filename);
  
  s->state = STATE_OUTPUT;

  while(1) {
    PSOCK_READTO(&s->sin, ISO_nl);

    if(strncmp(s->inputbuf, http_referer, 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
    }
  }
  
  PSOCK_END(&s->sin);
}
예제 #17
0
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_input(struct httpd_state *s))
{
  PSOCK_BEGIN(&s->sin);

  PSOCK_READTO(&s->sin, ISO_space);

  // GET Request
  if(!strncmp(s->inputbuf, http_get, 4)) {
  //PSOCK_CLOSE_EXIT(&s->sin);
		s->method = GET;
  } else {
		s->method = POST;
  }
  PSOCK_READTO(&s->sin, ISO_space);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

#if URLCONV
  s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
  urlconv_tofilename(s->filename, s->inputbuf, sizeof(s->filename));
#else /* URLCONV */
    s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
    strncpy(s->filename, s->inputbuf, sizeof(s->filename));
#endif /* URLCONV */

  //webserver_log_file(&uip_conn->ripaddr, s->filename);

  s->state = STATE_OUTPUT;

  while(1) {
    PSOCK_READTO(&s->sin, ISO_nl);
#if 0
    if(strncmp(s->inputbuf, http_referer, 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
      webserver_log(s->inputbuf);
    }
#endif
  }

  PSOCK_END(&s->sin);
}
예제 #18
0
/*---------------------------------------------------------------------------*/
static
PT_THREAD(send_headers(struct httpd_state *s, const char *statushdr))
{
  char *ptr;
  PSOCK_BEGIN(&s->sout);

  PSOCK_GENERATOR_SEND(&s->sout, generate_status, (char *) statushdr);

  ptr = strrchr(s->filename, ISO_period);
  if (httpd_strncmp("4", statushdr, 1) == 0) { //404
    PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_htm);
  } else if (ptr == NULL) {
#if WEBSERVER_CONF_BIN
    PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_bin);
#else
    PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_htm);
#endif 
  } else {
    ptr++;
#if WEBSERVER_CONF_INCLUDE || WEBSERVER_CONF_CGI
    if (httpd_strncmp(ptr, &httpd_mime_htm[5], 3) == 0 || httpd_strncmp(ptr, &httpd_str_shtml[1], 4) == 0) {
#else
    if (httpd_strncmp(ptr, &httpd_mime_htm[5], 3) == 0) {
#endif
      PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_htm);
#if WEBSEVER_CONF_CSS
    } else if (httpd_strcmp(ptr, &httpd_mime_css[5]) == 0) {
      PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_css);
#endif
#if WEBSERVER_CONF_PNG
    } else if (httpd_strcmp(ptr, &httpd_mime_png[6]) == 0) {
      PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_png);
#endif
#if WEBSERVER_CONF_GIF
    } else if (httpd_strcmp(ptr, &httpd_mime_gif[6]) == 0) {
      PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_gif);
#endif
#if WEBSERVER_CONF_JPG
    } else if (httpd_strcmp(ptr, httpd_mime_jpg) == 0) {
      PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_jpg);
#endif
#if WEBSERVER_CONF_TXT
    } else {
      PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_txt);
#endif
    }
  }
  PSOCK_END(&s->sout);
}
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_output(struct httpd_state *s))
{
  char *ptr;

  PT_BEGIN(&s->outputpt);

#if DEBUGLOGIC
  httpd_strcpy(s->filename, httpd_str_indexfn);
#endif

  s->fd = httpd_fs_open(s->filename, HTTPD_FS_READ);
  if (s->fd == -1) { // Opening file failed.

    /* TODO: try index.htm ? */
#if WEBSERVER_CONF_INCLUDE || WEBSERVER_CONF_CGI
    /* If index.html not found try index.htm */
    if (httpd_strcmp(s->filename, httpd_str_indexfn) == 0) {
      httpd_strcpy(s->filename, httpd_str_indexfn3);
    }
    s->fd = httpd_fs_open(s->filename, HTTPD_FS_READ);
    if (s->fd != -1) {
      goto sendfile;
    }
    /* If index.html not found try index.shtml */
    if (httpd_strcmp(s->filename, httpd_str_indexfn) == 0) {
      httpd_strcpy(s->filename, httpd_str_indexsfn);
    }
    s->fd = httpd_fs_open(s->filename, HTTPD_FS_READ);
    if (s->fd == -1) {
      PRINTD("Opening %s failed\n", s->filename);
      goto psock_close;
    } else {
      goto sendfile;
    }
#endif
    /* If nothing was found, send 404 page */
    httpd_strcpy(s->filename, httpd_str_404fn);
    s->fd = httpd_fs_open(s->filename, HTTPD_FS_READ);
    PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_str_404notf));
    PT_WAIT_THREAD(&s->outputpt, send_file(s));

  } else { // Opening file succeeded.

sendfile:
    PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_str_200ok));
#if WEBSERVER_CONF_INCLUDE || WEBSERVER_CONF_CGI
    /* If filename ends with .shtml, scan file for script includes or cgi */
    ptr = strchr(s->filename, ISO_period);
    if ((ptr != NULL && httpd_strncmp(ptr, httpd_str_shtml, 6) == 0)
            || httpd_strcmp(s->filename, httpd_str_indexfn) == 0) {
      PT_INIT(&s->scriptpt);
      PT_WAIT_THREAD(&s->outputpt, handle_scripts(s));
    } else {
#else
    if (1) {
#endif
      PT_WAIT_THREAD(&s->outputpt, send_file(s));
      httpd_fs_close(s->fd);
    }
  }
psock_close:
  PSOCK_CLOSE(<y & s->sout);
  PT_END(&s->outputpt);
}
/*---------------------------------------------------------------------------*/
#if WEBSERVER_CONF_PASSQUERY
char httpd_query[WEBSERVER_CONF_PASSQUERY];
#endif

static
PT_THREAD(handle_input(struct httpd_state *s))
{

  PSOCK_BEGIN(&s->sin);

  PSOCK_READTO(&s->sin, ISO_space);

  if (httpd_strncmp(s->inputbuf, httpd_str_get, 4) != 0) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ISO_space);

  if (s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

  if (s->inputbuf[1] == ISO_space) {
    httpd_strcpy(s->filename, httpd_str_indexfn);
  } else {
    uint8_t i;
    for (i = 0; i<sizeof (s->filename) + 1; i++) {
      if (i >= (PSOCK_DATALEN(&s->sin) - 1)) break;
      if (s->inputbuf[i] == ISO_space) break;
#if WEBSERVER_CONF_PASSQUERY
      /* Query string is left in the httpd_query buffer until zeroed by the application! */
      if (s->inputbuf[i] == ISO_qmark) {
        strncpy(httpd_query, &s->inputbuf[i + 1], sizeof (httpd_query));
        break;
      }
#endif
      s->filename[i] = s->inputbuf[i];
    }
    s->filename[i] = 0;
  }

#if WEBSERVER_CONF_LOG
  webserver_log_file(&uip_conn->ripaddr, s->filename);
  //  webserver_log(httpd_query);
#endif
#if WEBSERVER_CONF_LOADTIME
  s->pagetime = clock_time();
#endif
  s->state = STATE_OUTPUT;
  while (1) {
    PSOCK_READTO(&s->sin, ISO_nl);
#if WEBSERVER_CONF_LOG && WEBSERVER_CONF_REFERER
    if (httpd_strncmp(s->inputbuf, httpd_str_ref, 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
      petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2);
      webserver_log(s->inputbuf);
    }
#endif
  }
  PSOCK_END(&s->sin);
}
예제 #19
0
파일: httpd.c 프로젝트: jaseg/avr-uip
/*---------------------------------------------------------------------------*/
static
PT_THREAD(handle_input(struct httpd_state *s))
{
  PSOCK_BEGIN(&s->sin);
#if defined(HTTP_POST_SUPPORT)
  int cont_len = 0;
#endif

  PSOCK_READTO(&s->sin, ISO_space);

  if(strncmp_P(s->inputbuf, http_get, 3) == 0) {
    s->request_type = GET;
#if defined(HTTP_POST_SUPPORT)
  } else if(strncmp_P(s->inputbuf, http_post, 4) == 0) {
    s->request_type = POST;
#endif
  } else {
    PSOCK_CLOSE_EXIT(&s->sin);
  }
  PSOCK_READTO(&s->sin, ISO_space);

  if(s->inputbuf[0] != ISO_slash) {
    PSOCK_CLOSE_EXIT(&s->sin);
  }

    /* read and store the file name */
    if(s->inputbuf[1] == ISO_space) {
        strncpy_P(s->filename, http_index_html, sizeof(s->filename));
    } else {
        s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;

#if defined(HTTP_GET_PARAM_SUPPORT)
    // note this code block taken from uhttpd-avr project
        int i;
        for(i=0 ; s->inputbuf[i]!=0 && s->inputbuf[i] != ISO_question ; i++);

        if( s->inputbuf[i] == ISO_question )
        {
            s->inputbuf[i]=0;
            strncpy(s->param,&s->inputbuf[i+1],sizeof(s->param));
            s->param_len = strlen(s->param);
        }
        else
        {
            s->param[0] = 0;
            s->param_len = 0;
        }
    // end note
#endif                                                      
        strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
    }

  /*  httpd_log_file(uip_conn->ripaddr, s->filename);*/

  s->state = STATE_OUTPUT;

  /* read all of the clients input data */
  while(1) {
    PSOCK_READTO(&s->sin, ISO_nl);

#if defined(HTTP_POST_SUPPORT)
    if(s->request_type == POST) {
      if(cont_len != 0) {
          /* does this line contain any data */
          if(PSOCK_DATALEN(&s->sin) > 2) {
			s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
            strncpy(s->param,&s->inputbuf[0],sizeof(s->param));
            s->param_len = strlen(s->param);
			break;
          }
      }else if(strncmp_P(s->inputbuf, http_content_length, 15) == 0) {
        s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
        cont_len = atoi(&s->inputbuf[16]);
        if (cont_len > MAX_PARAM_DATA) {
            strncpy_P(s->filename, http_413_html, sizeof(s->filename));
			break;
        }
        s->param[0] = 0;
        s->param_len = 0;
      }
    }
#endif
#if 0 /* compile out but, leave as example */
    if(strncmp_P(s->inputbuf, http_referer, 8) == 0) {
      s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
      /*      httpd_log(&s->inputbuf[9]);*/
    }
#endif
  }
  
  PSOCK_END(&s->sin);
}
예제 #20
0
static
PT_THREAD(handle_input(struct httpd_state *s))
{
	int found = 0;

	PSOCK_BEGIN(&s->sin);

	PSOCK_READTO(&s->sin, ISO_space);

	if(httpd_strncmp(s->inputbuf, httpd_get, 4) == 0) {

		PSOCK_READTO(&s->sin, ISO_space);

		if(s->inputbuf[0] != ISO_slash) {
			PSOCK_CLOSE_EXIT(&s->sin);
		}

		if(s->inputbuf[1] == ISO_space) {
			httpd_strcpy(s->filename, httpd_indexfn);
		} else {
			s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
			strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));

			/* Look for ?, if found strip file name and send any following text to the LCD */
			uint8_t i;
			for (i=0;i<sizeof(s->inputbuf);i++) {
				if (s->inputbuf[i]=='?') {
					if (i<sizeof(s->filename)) s->filename[i]=0;
					//     s->inputbuf[i]=0; //allow multiple beeps with multiple ?'s
				}
				if (s->inputbuf[i]==0) break;
			}

		}
	}
	else if(httpd_strncmp(s->inputbuf, httpd_post, 5) == 0) {

		PSOCK_READTO(&s->sin, ISO_space);

		if(s->inputbuf[0] != ISO_slash) {
			PSOCK_CLOSE_EXIT(&s->sin);
		}
		if (httpd_strncmp(&s->inputbuf[1], httpd_config_file, sizeof(httpd_config_file)-1) == 0)  {

			s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
			strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
			/* Look for ?, if found strip file name*/
			uint8_t i;
			for (i=0;i<sizeof(s->inputbuf);i++) {
				if (s->inputbuf[i]=='?') {
					if (i<sizeof(s->filename)) s->filename[i]=0;
				}
				if (s->inputbuf[i]==0) break;
			}
			//parse config data
			found = 0;

			//look for the combination "\r\n\r\n"; the post data follow thereafter
			while (!found)
			{
				PSOCK_READTO(&s->sin, ISO_nl);
				PSOCK_READTO(&s->sin, ISO_cr);
				if (PSOCK_DATALEN(&s->sin) == 1)
				{
					PSOCK_READTO(&s->sin, ISO_nl);
					found=1;
				}
			}

			PSOCK_READTO(&s->sin, ISO_equal);
			//check for domain_name
			PSOCK_READTO(&s->sin, ISO_amper);
			if(s->inputbuf[0] != ISO_amper) {
				char tmp[nvm_size(domain_name)];
				memset(tmp, 0, sizeof (tmp));
				memcpy(tmp, s->inputbuf, PSOCK_DATALEN(&s->sin) - 1);
				nvm_write_block(domain_name, tmp, sizeof(tmp));
			}

			PSOCK_READTO(&s->sin, ISO_equal);
			//check for relay_default_state
			PSOCK_READTO(&s->sin, ISO_amper);
			if(s->inputbuf[0] == '1')
				set_relay_default(0);
			else if (s->inputbuf[0] == '0')
				set_relay_default(1);

#if S0_ENABLE
			PSOCK_READTO(&s->sin, ISO_equal);
			//check for s0 calibration value
			PSOCK_READTO(&s->sin, ISO_amper);
			if(s->inputbuf[0] != ISO_amper) {
                metering_set_s0_calibration((uint16_t)atoi(s->inputbuf));
            }
#endif
		}
		else if (httpd_strncmp(&s->inputbuf[1], httpd_socket_status_file, sizeof(httpd_socket_status_file)-1) == 0) {
			// toggle button has been pressed

			s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0;
			strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename));
			/* Look for ?, if found strip file name*/
			uint8_t i;
			for (i=0;i<sizeof(s->inputbuf);i++) {
				if (s->inputbuf[i]=='?') {
					if (i<sizeof(s->filename)) s->filename[i]=0;
				}
				if (s->inputbuf[i]==0) break;
			}

			relay_toggle();

	} else {
			PSOCK_CLOSE_EXIT(&s->sin);
		}
	}	else {
		PSOCK_CLOSE_EXIT(&s->sin);
	}
	webserver_log_file(&uip_conn->ripaddr, s->filename);

	s->state = (s->state == STATE_ERROR) ? STATE_OUTPUT_ERROR : STATE_OUTPUT;

	while(1) {
		PSOCK_READTO(&s->sin, ISO_nl);
		if(httpd_strncmp(s->inputbuf, httpd_ref, 8) == 0) {
			s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;
			petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2);
			webserver_log(s->inputbuf);
		}
	}
	PSOCK_END(&s->sin);
}
예제 #21
0
//处理HTTP输入数据
static PT_THREAD(handle_input(struct httpd_state *s))
{		    	  
	char *strx;
	u8 dbuf[17];
	PSOCK_BEGIN(&s->sin);		 
	PSOCK_READTO(&s->sin, ISO_space);	 
	if(strncmp(s->inputbuf, http_get, 4)!=0)PSOCK_CLOSE_EXIT(&s->sin);	//比较客户端浏览器输入的指令是否是申请WEB指令 “GET ” 	   
	PSOCK_READTO(&s->sin, ISO_space);		     						//" "
	if(s->inputbuf[0] != ISO_slash)PSOCK_CLOSE_EXIT(&s->sin);		 	//判断第一个(去掉IP地址之后)数据,是否是"/"
	if(s->inputbuf[1] == ISO_space||s->inputbuf[1] == '?') 				//第二个数据是空格/问号
	{ 
		if(s->inputbuf[1]=='?'&&s->inputbuf[6]==0x31)//LED1  
		{
			printf("Change LED0 Status\r\n");
			LED0 = !LED0;	
			strx=strstr((const char*)(data_index_html+13),"LED0状态");  
			if(strx)//存在"LED0状态"这个字符串
			{
				strx=strstr((const char*)strx,"color:#");//找到"color:#"字符串
				if(LED0)//LED0灭
				{
					strncpy(strx+7,"5B5B5B",6);	//灰色
					strncpy(strx+24,"灭",2);	//灭
					strx=strstr((const char*)strx,"http:");//找到"http:"字符串 
					strncpy(strx,(const char*)LED_OFF_PIC_ADDR,strlen((const char*)LED_OFF_PIC_ADDR));//LED0灭图片	  
				}else
				{
					strncpy(strx+7,"FF0000",6);	//红色
					strncpy(strx+24,"亮",2);	//"亮"
					strx=strstr((const char*)strx,"http:");//找到"http:"字符串 
					strncpy(strx,(const char*)LED0_ON_PIC_ADDR,strlen((const char*)LED0_ON_PIC_ADDR));//LED0亮图片	  
				}	
			}  
		}
		else if(s->inputbuf[1]=='?'&&s->inputbuf[6]==0x32)//LED2  
		{
			printf("Change LED1 Status\r\n");
			LED1 = !LED1;	
			strx=strstr((const char*)(data_index_html+13),"LED1状态");  
			if(strx)//存在"LED1状态"这个字符串
			{
				strx=strstr((const char*)strx,"color:#");//找到"color:#"字符串
				if(LED1)//LED1灭
				{
					strncpy(strx+7,"5B5B5B",6);	//灰色
					strncpy(strx+24,"灭",2);	//灭
					strx=strstr((const char*)strx,"http:");//找到"http:"字符串 
					strncpy(strx,(const char*)LED_OFF_PIC_ADDR,strlen((const char*)LED_OFF_PIC_ADDR));//LED1灭图片	  
				}else
				{
					strncpy(strx+7,"00FF00",6);	//绿色
					strncpy(strx+24,"亮",2);	//"亮"
					strx=strstr((const char*)strx,"http:");//找到"http:"字符串 
					strncpy(strx,(const char*)LED1_ON_PIC_ADDR,strlen((const char*)LED1_ON_PIC_ADDR));//LED1亮图片	  
				}	
			} 
		}
		
		strx = strstr((const char*)(data_index_html+13),"℃");//找到"℃"字符
		if(strx)
		{
//			get_temperature(dbuf);	//得到温度	  
			strncpy(strx-4,(const char*)dbuf,4);	//更新温度
			printf("Update Temperature\r\n");			
		}
		strx=strstr((const char*)strx,"RTC时间:");//找到"RTC时间:"字符
		if(strx)
		{
//			get_time(dbuf);			//得到时间  
			strncpy(strx+33,(const char*)dbuf,16);	//更新时间
			printf("Update RTC\r\n");
		}
		strncpy(s->filename, http_index_html, sizeof(s->filename));
	}
	else //如果不是' '/'?'
	{
		s->inputbuf[PSOCK_DATALEN(&s->sin)-1] = 0;
		strncpy(s->filename,&s->inputbuf[0],sizeof(s->filename));
	}   
	s->state = STATE_OUTPUT;	    
	while(1) 
	{
		PSOCK_READTO(&s->sin, ISO_nl);
		if(strncmp(s->inputbuf, http_referer, 8) == 0) 
		{
			s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0;		   
		}
	}								    
	PSOCK_END(&s->sin);
}
/*
 * A protosocket always requires a protothread. The protothread
 * contains the code that uses the protosocket. We define the
 * protothread here.
 */
static
PT_THREAD(connection_setup(struct psock *p))
{
  /*
   * A protosocket's protothread must start with a PSOCK_BEGIN(), with
   * the protosocket as argument.
   */
  PSOCK_BEGIN(p);
  printf("TIME: %d\n",clock_time());

  /*
   * Here we define all the thread local variables that we need to
   * utilize.
   */
  static ServerGreeting greet;
  static SetupResponseUAuth setup;
  static ServerStartMsg start;
  static int i;
  static int acceptedMode = 1;

  /* 
   * We configure the Server-Greeting that we want to send. Setting
   * the accepted modes to those we accept. The following modes are 
   * meaningful:
   * 1 - Unauthenticated
   * 2 - Authenticated
   * 3 - Encrypted
   * 0 - Do not wish to communicate.
   */
  memset(&greet, 0, sizeof(greet));
  greet.Modes = 1;
  /*
   * We generate random sequence of octects for the challenge and
   * salt. 
   */
  for (i = 0; i < 16; i++){
      greet.Challenge[i] = rand() % 16;
      }
  for (i = 0; i < 16; i++){
      greet.Salt[i] = rand() % 16;
      }
  /*
   * Count must be a power of 2 and be at least 1024.
   */
  //greet.Count = (1 << 12);
  /*
   * We set the MBZ octets to zero.
   */
  for (i = 0; i < 12; i++){
    greet.MBZ[i] = 0;
  }

  /*
   * Using PSOCK_SEND() we send the Server-Greeting to the connected
   * client.
   */
  PSOCK_SEND(p, &greet, sizeof(greet));

  /* 
   * We wait until we receive a server greeting from the server.
   * PSOCK_NEWDATA(p) returns 1 when new data has arrived in 
   * the protosocket.  
   */
  PSOCK_WAIT_UNTIL(p,PSOCK_NEWDATA(p));
  if(PSOCK_NEWDATA(p)){
    /*
     * We read data from the buffer now that it has arrived.
     * Using memcpy we store it in our local variable.
     */
    PSOCK_READBUF(p);
    memcpy(&setup,buffer,sizeof(setup));
    if(setup.Modes != acceptedMode){
      printf("Client did not match our modes!\n");
      PSOCK_CLOSE_EXIT(p);
    } else{
      /*
       * We have agreed upon the mode. Now we send the Server-Start
       * message.
       */
      memset(&start,0,sizeof(start));
      /* 
       * We set the MBZ octets to zero.
       */
      for (i = 0; i < 15; i++){
        start.MBZ1[i] = 0;
      }
      for (i = 0; i < 8; i++){
        start.MBZ2[i] = 0;
      }
      /*
       * The accept field is set to zero if the server wishes to continue
       * communicating. A non-zero value is defined as in RFC 4656.
       */
      start.Accept = 0;
      /*
       * Timestamp is set to the time the Server started.
       */
      double temp;
      start.timestamp.Second = clock_seconds();
      temp = (double) clock_time()/CLOCK_SECOND - start.timestamp.Second;
      start.timestamp.Fraction = temp*1000;
      /*
       * Using PSOCK_SEND() we send the Server-Start to the connected
       * client.
       */
      PSOCK_SEND(p, &start, sizeof(start));
      printf("Client agreed to mode: %d\n",setup.Modes);
    }
  } else {
    printf("Timed out!\n");
  }
  state = 2;
  
  PSOCK_END(p);
}
예제 #23
0
static PT_THREAD(handle_mqtt_connection(mqtt_state_t* state))
{
  static struct etimer keepalive_timer;

  uint8_t msg_type;
  uint8_t msg_qos;
  uint16_t msg_id;

  PSOCK_BEGIN(&state->ps);

  // Initialise and send CONNECT message
  mqtt_msg_init(&state->mqtt_connection, state->out_buffer, state->out_buffer_length);
  state->outbound_message =  mqtt_msg_connect(&state->mqtt_connection, state->connect_info);
  PSOCK_SEND(&state->ps, state->outbound_message->data, state->outbound_message->length);
  state->outbound_message = NULL;

  // Wait for CONACK message
  PSOCK_READBUF_LEN(&state->ps, 2);
  if(mqtt_get_type(state->in_buffer) != MQTT_MSG_TYPE_CONNACK)
    PSOCK_CLOSE_EXIT(&state->ps);
  
  // Tell the client we're connected
  mqtt_flags |= MQTT_FLAG_CONNECTED;
  complete_pending(state, MQTT_EVENT_TYPE_CONNECTED);

  // Setup the keep alive timer and enter main message processing loop
  etimer_set(&keepalive_timer, CLOCK_SECOND * state->connect_info->keepalive);
  while(1)
  {
    // Wait for something to happen: 
    //   new incoming data, 
    //   new outgoing data, 
    //   keep alive timer expired
    PSOCK_WAIT_UNTIL(&state->ps, PSOCK_NEWDATA(&state->ps) || 
                                 state->outbound_message != NULL ||
                                 etimer_expired(&keepalive_timer));

    // If there's a new message waiting to go out, then send it
    if(state->outbound_message != NULL)
    {
      PSOCK_SEND(&state->ps, state->outbound_message->data, state->outbound_message->length);
      state->outbound_message = NULL;

      // If it was a PUBLISH message with QoS-0 then tell the client it's done
      if(state->pending_msg_type == MQTT_MSG_TYPE_PUBLISH && state->pending_msg_id == 0)
        complete_pending(state, MQTT_EVENT_TYPE_PUBLISHED);

      // Reset the keepalive timer as we've just sent some data
      etimer_restart(&keepalive_timer);
      continue;
    }

    // If the keep-alive timer expired then prepare a ping for sending
    // and reset the timer
    if(etimer_expired(&keepalive_timer))
    {
      state->outbound_message = mqtt_msg_pingreq(&state->mqtt_connection);
      etimer_reset(&keepalive_timer);
      continue;
    }

    // If we get here we must have woken for new incoming data, 
    // read and process it.
    PSOCK_READBUF_LEN(&state->ps, 2);
    
    state->message_length_read = PSOCK_DATALEN(&state->ps);
    state->message_length = mqtt_get_total_length(state->in_buffer, state->message_length_read);

    msg_type = mqtt_get_type(state->in_buffer);
    msg_qos  = mqtt_get_qos(state->in_buffer);
    msg_id   = mqtt_get_id(state->in_buffer, state->in_buffer_length);
    switch(msg_type)
    {
      case MQTT_MSG_TYPE_SUBACK:
        if(state->pending_msg_type == MQTT_MSG_TYPE_SUBSCRIBE && state->pending_msg_id == msg_id)
          complete_pending(state, MQTT_EVENT_TYPE_SUBSCRIBED);
        break;
      case MQTT_MSG_TYPE_UNSUBACK:
        if(state->pending_msg_type == MQTT_MSG_TYPE_UNSUBSCRIBE && state->pending_msg_id == msg_id)
          complete_pending(state, MQTT_EVENT_TYPE_UNSUBSCRIBED);
        break;
      case MQTT_MSG_TYPE_PUBLISH:
        if(msg_qos == 1)
          state->outbound_message = mqtt_msg_puback(&state->mqtt_connection, msg_id);
        else if(msg_qos == 2)
          state->outbound_message = mqtt_msg_pubrec(&state->mqtt_connection, msg_id);

        deliver_publish(state, state->in_buffer, state->message_length_read);
        break;
      case MQTT_MSG_TYPE_PUBACK:
        if(state->pending_msg_type == MQTT_MSG_TYPE_PUBLISH && state->pending_msg_id == msg_id)
          complete_pending(state, MQTT_EVENT_TYPE_PUBLISHED);
        break;
      case MQTT_MSG_TYPE_PUBREC:
        state->outbound_message = mqtt_msg_pubrel(&state->mqtt_connection, msg_id);
        break;
      case MQTT_MSG_TYPE_PUBREL:
        state->outbound_message = mqtt_msg_pubcomp(&state->mqtt_connection, msg_id);
        break;
      case MQTT_MSG_TYPE_PUBCOMP:
        if(state->pending_msg_type == MQTT_MSG_TYPE_PUBLISH && state->pending_msg_id == msg_id)
          complete_pending(state, MQTT_EVENT_TYPE_PUBLISHED);
        break;
      case MQTT_MSG_TYPE_PINGREQ:
        state->outbound_message = mqtt_msg_pingresp(&state->mqtt_connection);
        break;
      case MQTT_MSG_TYPE_PINGRESP:
        // Ignore
        break;
    }

    // NOTE: this is done down here and not in the switch case above
    //       because the PSOCK_READBUF_LEN() won't work inside a switch
    //       statement due to the way protothreads resume.
    if(msg_type == MQTT_MSG_TYPE_PUBLISH)
    {
      uint16_t len;

      // adjust message_length and message_length_read so that
      // they only account for the publish data and not the rest of the 
      // message, this is done so that the offset passed with the
      // continuation event is the offset within the publish data and
      // not the offset within the message as a whole.
      len = state->message_length_read;
      mqtt_get_publish_data(state->in_buffer, &len);
      len = state->message_length_read - len;
      state->message_length -= len;
      state->message_length_read -= len;

      while(state->message_length_read < state->message_length)
      {
        PSOCK_READBUF_LEN(&state->ps, state->message_length - state->message_length_read);
        deliver_publish_continuation(state, state->message_length_read, state->in_buffer, PSOCK_DATALEN(&state->ps));
        state->message_length_read += PSOCK_DATALEN(&state->ps);
      }
    }
  }

  PSOCK_END(&state->ps);
}