Exemple #1
0
/**
 * Connect to MQTT broker.
 *
 * N.B. None-blocking call.
 */
mqtt_status_t
mqtt_connect(struct mqtt_connection* conn,
             const char* host,
             uint16_t port,
             uint16_t keep_alive)
{
  uip_ip6addr_t ip6addr;
  uip_ip4addr_t ip4addr;
  uip_ipaddr_t *ipaddr;
  ipaddr = &ip6addr;

  /* Sanity check */
  assert(conn != NULL &&
         host != NULL);

  /* Check if we are already trying to connect */
  if(conn->state > MQTT_CONN_STATE_NOT_CONNECTED) {
    return MQTT_STATUS_OK;
  }

  conn->server_host = host;
  conn->keep_alive = keep_alive;
  conn->server_port = port;
  conn->out_buffer_ptr = conn->out_buffer;
  conn->out_packet.qos_state = MQTT_QOS_STATE_NO_ACK;

  /* First check if the host is an IP address. If not, try to look it up. */
  if(uiplib_ip6addrconv(host, &ip6addr) == 0) {
    if(uiplib_ip4addrconv(host, &ip4addr) != 0) {
      ip64_addr_4to6(&ip4addr, &ip6addr);
    } else {
#if UIP_UDP
      ipaddr = mdns_lookup(host);

      if(ipaddr == NULL) {
        printf("MQTT - Resolving host...\r\n");
        mdns_query(host);
        conn->state = MQTT_CONN_STATE_DNS_LOOKUP;
        return MQTT_STATUS_OK;
      }
#else /* UIP_UDP */
      DBG("Error looking up hostname when mDNS is not used due to UIP_UDP = 0.");
      conn->state = MQTT_CONN_STATE_ERROR;
      return MQTT_STATUS_DNS_ERROR;
#endif /* UIP_UDP */
    }
  }
  uip_ipaddr_copy(&(conn->server_ip), ipaddr);

  /* Initiate the connection if the IP could be resolved. Otherwise the
   * connection will be initiated when the DNS lookup is finished, in the main
   * event loop.
   */
  process_post(&mqtt_process, mqtt_do_connect_tcp_event, conn);

  return MQTT_STATUS_OK;
}
Exemple #2
0
/*---------------------------------------------------------------------------*/
PROCESS_THREAD(http_socket_process, ev, data)
{
  PROCESS_BEGIN();

  while(1) {

    PROCESS_WAIT_EVENT();

    if(ev == mdns_event_found && data != NULL) {
      struct http_socket *s;
      const char *name = data;
      /* Either found a hostname, or not. We need to go through the
	 list of http sockets and figure out to which connection this
	 reply corresponds, then either restart the HTTP get, or kill
	 it (if no hostname was found). */
      for(s = list_head(socketlist);
	  s != NULL;
	  s = list_item_next(s)) {
	char host[MAX_HOSTLEN];
	if(parse_url(s->url, host, NULL, NULL) &&
	   strcmp(name, host) == 0) {
	  if(mdns_lookup(name) != NULL) {
	    /* Hostname found, restart get. */
            start_request(s);
	  } else {
	    /* Hostname not found, kill connection. */
            call_callback(s, HTTP_SOCKET_HOSTNAME_NOT_FOUND, NULL, 0);
            removesocket(s);
	  }
	}
      }
    } else if(ev == PROCESS_EVENT_TIMER) {
      struct http_socket *s;
      struct etimer *timeout_timer = data;
      /*
       * A socket time-out has occurred. We need to go through the list of HTTP
       * sockets and figure out to which socket this timer event corresponds,
       * then close this socket.
       */
      for(s = list_head(socketlist);
          s != NULL;
          s = list_item_next(s)) {
        if(timeout_timer == &s->timeout_timer && s->timeout_timer_started) {
          tcp_socket_close(&s->s);
          break;
        }
      }
    }
  }

  PROCESS_END();
}
/*-----------------------------------------------------------------------------------*/
unsigned char
websocket_http_client_get(struct websocket_http_client_state *s,
			  const char *host, uint16_t port, const char *file,
                          const char *subprotocol)
{
  struct uip_conn *conn;
  uip_ip6addr_t ip6addr;
  uip_ip4addr_t ip4addr;
  uip_ipaddr_t *ipaddr;

  ipaddr = &ip6addr;
  /* First check if the host is an IP address. */
  if(uiplib_ip6addrconv(host, &ip6addr) == 0) {
    if(uiplib_ip4addrconv(host, &ip4addr) != 0) {
      ip64_addr_4to6(&ip4addr, &ip6addr);
    } else {
#if UIP_UDP
      ipaddr = mdns_lookup(host);
      
      if(ipaddr == NULL) {
	return 0;
      }
#else /* UIP_UDP */
      return 0;
#endif /* UIP_UDP */
    }
  }
  
  conn = tcp_connect(ipaddr, uip_htons(port), NULL);
  
  if(conn == NULL) {
    return 0;
  }
  tcp_markconn(conn, s);
  s->conn = conn;
  s->port = port;
  strncpy(s->file, file, sizeof(s->file));
  strncpy(s->host, host, sizeof(s->host));
  strncpy(s->subprotocol, subprotocol, sizeof(s->subprotocol));
  init_connection(s);
  return 1;
}
Exemple #4
0
/*---------------------------------------------------------------------------*/
static int
start_request(struct http_socket *s)
{
  uip_ip4addr_t ip4addr;
  uip_ip6addr_t ip6addr;
  uip_ip6addr_t *addr;
  char host[MAX_HOSTLEN];
  char path[MAX_PATHLEN];
  uint16_t port;

  if(parse_url(s->url, host, &port, path)) {

    printf("url %s host %s port %d path %s\n\r",
           s->url, host, port, path);

    /* First check if the host is an IP address. */
    if(uiplib_ip6addrconv(host, &ip6addr) == 0) {
      if(uiplib_ip4addrconv(host, &ip4addr) != 0) {
        ip64_addr_4to6(&ip4addr, &ip6addr);
      } else {
        /* Try to lookup the hostname. If it fails, we initiate a hostname
           lookup. */
        addr = mdns_lookup(host);
        if(addr == NULL) {
          mdns_query(host);
          puts("Resolving host...");
          return HTTP_SOCKET_OK;
        }
        tcp_socket_connect(&s->s, addr, port);
        return HTTP_SOCKET_OK;
      }
    }
    tcp_socket_connect(&s->s, &ip6addr, port);
    return HTTP_SOCKET_OK;
  } else {
    return HTTP_SOCKET_ERR;
  }
}
/*-----------------------------------------------------------------------------------*/
void
websocket_http_client_appcall(void *state)
{
  char *dataptr;
  struct websocket_http_client_state *s = state;
  
  if(uip_connected()) {
    s->timer = 0;
    s->outputbufptr = 0;
    s->outputbuf_sendnext = 0;
    s->state = WEBSOCKET_HTTP_CLIENT_STATE_STATUSLINE;
    senddata(s);
    return;
  }

  if(uip_timedout()) {
    websocket_http_client_timedout(s);
  }

  if(uip_aborted()) {
    /*    printf("aborted\n"); */
    websocket_http_client_aborted(s);
  }

  if(state == NULL) {
    uip_abort();
    return;
  }

  if(s->state == WEBSOCKET_HTTP_CLIENT_STATE_CLOSE) {
    websocket_http_client_closed(s);
    uip_abort();
    return;
  }


  /* The acked() and newdata() functions may alter the uip_appdata
     ptr, so we need to store it in the "dataptr" variable so that we
     can restore it before the senddata() function is called. */  
  dataptr = uip_appdata;
  
  if(uip_acked()) {
    s->timer = 0;
    acked(s);
  }
  if(uip_newdata()) {
    s->timer = 0;
    newdata(s);
  }

  uip_appdata = dataptr;
  
  if(uip_rexmit() ||
     uip_newdata() ||
     uip_acked()) {
    senddata(s);
  } else if(uip_poll()) {
    senddata(s);
    ++s->timer;
    if(s->timer == WEBSOCKET_HTTP_CLIENT_TIMEOUT) {
      websocket_http_client_timedout(s);
      uip_abort();
      return;
    }
  }

  if(uip_closed()) {
    tcp_markconn(uip_conn, NULL);
    if(s->httpflag != HTTPFLAG_MOVED) {
      /* Send NULL data to signal EOF. */
      websocket_http_client_datahandler(s, NULL, 0);
    } else {
#if UIP_UDP
      if(mdns_lookup(s->host) == NULL) {
	mdns_query(s->host);
      }
#endif /* UIP_UDP */
      websocket_http_client_get(s, s->host, s->port, s->file,
                                s->subprotocol);
    }
  }
}
Exemple #6
0
/*---------------------------------------------------------------------------*/
PROCESS_THREAD(mqtt_process, ev, data)
{
  static struct mqtt_connection* conn;
  static uip_ipaddr_t* ipaddr = NULL;

  PROCESS_BEGIN();
  while(1) {
    PROCESS_WAIT_EVENT();

    if(ev == mqtt_do_connect_tcp_event) {
      conn = data;
      DBG("MQTT - Got mqtt_do_connect_tcp_event!\r\n");
      connect_tcp(conn);
    }
    if(ev == mqtt_do_connect_mqtt_event) {
      conn = data;
      DBG("MQTT - Got mqtt_do_connect_mqtt_event!\r\n");

      PT_INIT(&conn->out_proto_thread);
      while(connect_pt(&conn->out_proto_thread, conn) != PT_ENDED) {
        PT_MQTT_WAIT_SEND();
      }
    }
    if(ev == mqtt_do_disconnect_mqtt_event) {
      conn = data;
      DBG("MQTT - Got mqtt_do_disconnect_mqtt_event!\r\n");

      PT_INIT(&conn->out_proto_thread);
      while(disconnect_pt(&conn->out_proto_thread, conn) != PT_ENDED) {
        PT_MQTT_WAIT_SEND();
      }
    }
    if(ev == mqtt_do_pingreq_event) {
      conn = data;
      DBG("MQTT - Got mqtt_do_pingreq_event!\r\n");

      PT_INIT(&conn->out_proto_thread);
      while(pingreq_pt(&conn->out_proto_thread, conn) != PT_ENDED) {
        PT_MQTT_WAIT_SEND();
      }
    }
    if(ev == mqtt_do_subscribe_event) {
      conn = data;
      DBG("MQTT - Got mqtt_do_subscribe_mqtt_event!\r\n");

      PT_INIT(&conn->out_proto_thread);
      while(subscribe_pt(&conn->out_proto_thread, conn) != PT_ENDED) {
        PT_MQTT_WAIT_SEND();
      }
    }
    if(ev == mqtt_do_unsubscribe_event) {
        conn = data;
        DBG("MQTT - Got mqtt_do_unsubscribe_mqtt_event!\r\n");

        PT_INIT(&conn->out_proto_thread);
        while(unsubscribe_pt(&conn->out_proto_thread, conn) != PT_ENDED) {
          PT_MQTT_WAIT_SEND();
        }
      }
    if(ev == mqtt_do_publish_event) {
      conn = data;
      DBG("MQTT - Got mqtt_do_publish_mqtt_event!\r\n");

      PT_INIT(&conn->out_proto_thread);
      while(publish_pt(&conn->out_proto_thread, conn) != PT_ENDED) {
        PT_MQTT_WAIT_SEND();
      }
    }

#if 0
    if(ev == mqtt_do_publish_event) {

    }
#endif
    /* mDNS event - either found a hostname, or not. */
    if(ev == mdns_event_found) {
      if((char *)data != NULL && mdns_lookup((char *)data) != NULL) {
        ipaddr = mdns_lookup((char *)data);

        DBG("MQTT - Host found with ip %i %i %i %i TCP connecting...\r\n",
               ipaddr->u8[12],
               ipaddr->u8[13],
               ipaddr->u8[14],
               ipaddr->u8[15]);
      } else {
        printf("MQTT - Host not found, cannot continue.\r\n");
      }

      /* Find the connection(s) that are waiting for this lookup. Note that it
       * could possibly be more then one connection. */
      for(conn = list_head(mqtt_conn_list);
          conn != NULL;
          conn = list_item_next(conn)) {
        if( conn->state == MQTT_CONN_STATE_DNS_LOOKUP &&
            strcmp( (char*)data, conn->server_host ) == 0 ) {

          /* Update the connection of the DNS error or connect, depending on the
           * DNS lookup result.
           */
          if( ipaddr == NULL ) {
            conn->state = MQTT_CONN_STATE_DNS_ERROR;
            call_event(conn, MQTT_EVENT_DNS_ERROR, NULL);
          } else {
            uip_ipaddr_copy( &(conn->server_ip), ipaddr );
            process_post(&mqtt_process, mqtt_do_connect_tcp_event, conn);
          }
        }
      }
    }
  }
  PROCESS_END();
}