csm_service_list *
csm_services_init(void)
{
  csm_service_list *services = h_calloc(1, sizeof(csm_service_list));
  CHECK_MEM(services);
  
  co_obj_t *csm_services = co_list16_create();
  CHECK_MEM(csm_services);
  services->services = csm_services;
  hattach(services->services, services);
  
  co_obj_t *service_fields = co_list16_create();
  CHECK_MEM(service_fields);
  services->service_fields = service_fields;
  hattach(services->service_fields, services);
  
  co_obj_t *update_handlers = co_list16_create();
  CHECK_MEM(update_handlers);
  services->update_handlers = update_handlers;
  hattach(services->update_handlers, services);
  
  return services;
error:
  return NULL;
}
Esempio n. 2
0
static inline _treenode_t *
_co_tree_insert_r(_treenode_t *root, _treenode_t *current, const char *orig_key, const size_t orig_klen,  const char *key, const size_t klen, co_obj_t *value)
{
  if (current == NULL) 
  { 
    current = (_treenode_t *) h_calloc(1, sizeof(_treenode_t));
    if(root == NULL) 
    {
      root = current;
    } 
    else 
    {
      hattach(current, root);
    }
    current->splitchar = *key; 
  }

  if (*key < current->splitchar) 
  {
    current->low = _co_tree_insert_r(root, current->low, orig_key, orig_klen, key, klen, value); 
  } 
  else if (*key == current->splitchar) 
  { 
    if (klen > 1) 
    {
      // not done yet, keep going but one less
      current->equal = _co_tree_insert_r(root, current->equal, orig_key, orig_klen, key+1, klen - 1, value);
    } 
    else 
    {
      if(current->value != NULL)
      {
        co_obj_free(current->value);
      }
      if(current->key != NULL) 
      {
        co_obj_free(current->key);
      }
      current->value = value;
      current->key = co_str8_create(orig_key, orig_klen, 0);
      hattach(current->key, current);
      hattach(current->value, current);
      current->key->_ref++;
      current->value->_ref++;
    }
  } 
  else 
  {
    current->high = _co_tree_insert_r(root, current->high, orig_key, orig_klen, key, klen, value);
  }

  return current; 
}
Esempio n. 3
0
void
co_free(co_obj_t *object)
{
  hattach(object, NULL);
  co_obj_free(object);
  return;
}
Esempio n. 4
0
int connection_http_to_proxy(Connection *conn)
{
    Proxy *proxy = Request_get_action(conn->req, proxy);
    check(proxy != NULL, "Should have a proxy backend.");

    int proxy_fd = netdial(1, bdata(proxy->server), proxy->port);
    check(proxy_fd != -1, "Failed to connect to proxy backend %s:%d",
            bdata(proxy->server), proxy->port);

    if(!conn->proxy_iob) {
        conn->proxy_iob = IOBuf_create(BUFFER_SIZE, proxy_fd, IOBUF_SOCKET);
        check_mem(conn->proxy_iob);
    }

    if(!conn->client) {
        conn->client = h_calloc(sizeof(httpclient_parser), 1);
        check_mem(conn->client);
        hattach(conn->client, conn);
    }

    return CONNECT;

error:
    return FAILED;
}
int
csm_add_service(csm_service_list *services, csm_service *s, csm_ctx *ctx)
{
  // validate service fields against schema
  CHECK(csm_validate_fields(ctx, s), "Service doesn't validate");
  
  // attach service to service list
  s->parent = services;
//   co_obj_t *service_obj = co_service_create(s);
//   CHECK_MEM(service_obj);
  co_service_t *service_obj = container_of(s, co_service_t, service);
  CHECK(co_list_append(services->services, (co_obj_t *)service_obj),
	"Failed to add service to service list");
  
  co_obj_t *fields = s->fields;
  // detach s->fields from s before adding s->fields to services->service_fields
  hattach(fields, NULL);
  
  // add service fields to service list
  CHECK(co_list_append(services->service_fields, fields),
        "Failed to add service fields to service list");
  
  CHECK(csm_update_service(services, s, ctx, 0),
        "Failed to finalize service");
  
  return 1;
error:
  csm_remove_service(services, s);
//   csm_service_destroy(s);
  return 0;
}
Esempio n. 6
0
IOBuf *IOBuf_create(size_t len, int fd, IOBufType type)
{
    IOBuf *buf = h_calloc(sizeof(IOBuf), 1);
    check_mem(buf);

    buf->fd = fd;
    buf->len = len;

    buf->buf = h_malloc(len + 1);
    check_mem(buf->buf);

    hattach(buf->buf, buf);

    buf->type = type;

    if(type == IOBUF_SSL) {
        buf->use_ssl = 1;
        buf->handshake_performed = 0;
        ssl_init(&buf->ssl);
        ssl_set_endpoint(&buf->ssl, SSL_IS_SERVER);
        ssl_set_authmode(&buf->ssl, SSL_VERIFY_NONE);
        havege_init(&buf->hs);
        ssl_set_rng(&buf->ssl, havege_rand, &buf->hs);
        ssl_set_dbg(&buf->ssl, ssl_debug, NULL);
        ssl_set_bio(&buf->ssl, ssl_fdrecv_wrapper, buf, 
                    ssl_fdsend_wrapper, buf);
        ssl_set_session(&buf->ssl, 1, 0, &buf->ssn);
        memset(&buf->ssn, 0, sizeof(buf->ssn));

        buf->send = ssl_send;
        buf->recv = ssl_recv;
        buf->stream_file = ssl_stream_file;
    } else if(type == IOBUF_NULL) {
        buf->send = null_send;
        buf->recv = null_recv;
        buf->stream_file = null_stream_file;
    } else if(type == IOBUF_FILE) {
        buf->send = file_send;
        buf->recv = file_recv;
        buf->stream_file = plain_stream_file;
    } else if(type == IOBUF_SOCKET) {
        buf->send = plaintext_send;
        buf->recv = plaintext_recv;
        buf->stream_file = plain_stream_file;
    } else {
        sentinel("Invalid IOBufType given: %d", type);
    }

    return buf;

error:
    if(buf) h_free(buf);
    return NULL;
}
Esempio n. 7
0
int
co_init(void)
{
  CHECK(_pool == NULL, "Commotion API already initialized.");
  _pool = h_calloc(1, sizeof(_pool));
  _sockets = co_list16_create();
  hattach(_sockets, _pool);
  DEBUG("Commotion API initialized.");
  return 1;
error:
  return 0; 
}
Esempio n. 8
0
int
co_call(co_obj_t *connection, co_obj_t **response, const char *method, const size_t mlen, co_obj_t *request)
{
  CHECK(method != NULL && mlen > 0 && mlen < UINT8_MAX, "Invalid method name.");
  CHECK(connection != NULL && IS_SOCK(connection), "Invalid connection.");
  co_obj_t *params = NULL, *rlist = NULL, *rtree = NULL;
  int retval = 0;
  size_t reqlen = 0, resplen = 0;
  char req[REQUEST_MAX];
  char resp[RESPONSE_MAX];
  if(request != NULL)
  {
    CHECK(IS_LIST(request), "Not a valid request.");
    params = request;
  }
  else
  {
    params = co_list16_create();
  }
  co_obj_t *m = co_str8_create(method, mlen, 0);
  reqlen = co_request_alloc(req, sizeof(req), m, params);
  CHECK(((co_socket_t*)connection)->send((co_obj_t*)((co_socket_t*)connection)->fd, req, reqlen) != -1, "Send error!");
  if((resplen = ((co_socket_t*)connection)->receive(connection, (co_obj_t*)((co_socket_t*)connection)->fd, resp, sizeof(resp))) > 0) 
  {
    CHECK(co_list_import(&rlist, resp, resplen) > 0, "Failed to parse response.");
    rtree = co_list_element(rlist, 3);
    if(!IS_NIL(rtree))
    {
      retval = 1;
    }
    else
    {
      rtree = co_list_element(rlist, 2);
      retval = 0;
    }
    if(rtree != NULL && IS_TREE(rtree)) 
    {
      *response = rtree;
      hattach(*response, _pool);
    }
    else SENTINEL("Invalid response.");
  }
  else SENTINEL("Failed to receive data.");

  co_obj_free(m);
  if(params != request) co_obj_free(params);
  return retval;
  
error:
  co_obj_free(m);
  if(params != request) co_obj_free(params);
  return retval;
}
Esempio n. 9
0
co_obj_t *
co_connect(const char *uri, const size_t ulen)
{
  CHECK_MEM(_sockets);
  CHECK(uri != NULL && ulen > 0, "Invalid URI.");
  co_obj_t *socket = NEW(co_socket, unix_socket);
  hattach(socket, _pool);
  CHECK((((co_socket_t*)socket)->connect(socket, uri)), "Failed to connect to commotiond at %s\n", uri);
  co_list_append(_sockets, socket);
  return socket;
error:
  co_obj_free(socket);
  return NULL;
}
Esempio n. 10
0
HandlerParser *HandlerParser_create(size_t max_targets)
{
    HandlerParser *parser = h_calloc(sizeof(HandlerParser), 1);
    check_mem(parser);

    parser->target_max = max_targets;
    parser->targets = h_calloc(sizeof(unsigned long), max_targets);
    check_mem(parser->targets);
    hattach(parser->targets, parser);

    return parser;

error:
    return NULL;
}
Esempio n. 11
0
Heap *Heap_create(size_t capacity)
{
    Heap *h = (Heap *)h_calloc(sizeof(Heap), 1);
    check_mem(h);

    h->capacity = capacity;

    h->keys = h_calloc(sizeof(int), capacity);
    check_mem(h->keys);

    hattach(h, h->keys);
    return h;

error:
    Heap_destroy(h);
    return NULL;
}
Esempio n. 12
0
Route *Route_alloc(Route *parent, const char *name)
{
  Route *r = h_calloc(1, sizeof(Route));
  assert_mem(r);

  r->name = bfromcstr(name);
  assert_mem(r->name);

  r->members = Heap_create(NULL);
  r->children = Heap_create(Route_children_compare);

  // add it to the children mapping
  if(parent) {
    hattach(r, parent);
    Heap_add(parent->children, r);
  }

  return r;
}
Esempio n. 13
0
darray_t *darray_create(size_t element_size, size_t initial_max)
{
    darray_t *array = h_malloc(sizeof(darray_t));
    check_mem(array);

    array->contents = h_calloc(sizeof(void *), initial_max);
    check_mem(array->contents);
    hattach(array->contents, array);

    array->max = initial_max;
    array->end = 0;
    array->element_size = element_size;
    array->expand_rate = DEFAULT_EXPAND_RATE;

    return array;

error:
    if(array) h_free(array);
    return NULL;
}
Esempio n. 14
0
static inline _treenode_t *
_co_tree_delete_r(_treenode_t *root, _treenode_t *current, const char *key, const size_t klen, co_obj_t **value)
{
  DEBUG("Tree current: %s", key);
  if (*key < current->splitchar) 
  {
    current->low = _co_tree_delete_r(root, current->low, key, klen, value); 
  } 
  else if (*key == current->splitchar) 
  { 
    if (klen > 1) 
    {
      // not done yet, keep going but one less
      current->equal = _co_tree_delete_r(root, current->equal, key+1, klen - 1, value);
    } 
    else 
    {
      if(current->value != NULL)
      {
        DEBUG("Found current value.");
        hattach(current->value, NULL);
        current->value->_ref--;
        *value = current->value;
        current->value = NULL;
      }
    }
  } 
  else 
  {
    current->high = _co_tree_delete_r(root, current->high, key, klen, value);
  }

  if(current->low == NULL && current->high == NULL && current->equal == NULL && current->value == NULL)
  {
    h_free(current);
    return NULL;
  }
  else return current; 
}
Esempio n. 15
0
int
serval_open_keyring(svl_crypto_ctx *ctx)
{
  CHECK_ERR(ctx,"Invalid ctx");
  if (ctx->keyring_len == 0) {
    // if no keyring specified, use default keyring
    CHECK(serval_path,"Default Serval path not initialized");
    char keyring_path_str[PATH_MAX] = {0};
    strcpy(keyring_path_str, serval_path);
    if (serval_path[strlen(serval_path) - 1] != '/')
      strcat(keyring_path_str, "/");
    strcat(keyring_path_str, "serval.keyring");
    // Fetching SAS keys requires setting the SERVALINSTANCE_PATH environment variable
    CHECK_ERR(setenv("SERVALINSTANCE_PATH", serval_path, 1) == 0,
	      "Failed to set SERVALINSTANCE_PATH env variable");
    ctx->keyring_len = strlen(keyring_path_str);
    ctx->keyring_path = h_malloc(ctx->keyring_len + 1);
    strcpy(ctx->keyring_path,keyring_path_str);
    hattach(ctx->keyring_path,ctx);
  } else {
    // otherwise, use specified keyring (NOTE: if keyring does not exist, it will be created)
    CHECK(ctx->keyring_len < PATH_MAX, "Keyring length too long");
  }
  
  ctx->keyring_file = keyring_open(ctx->keyring_path);
  CHECK_ERR(ctx->keyring_file, "Failed to open specified keyring file");

  if (keyring_enter_pin(ctx->keyring_file, KEYRING_PIN) <= 0) {
    // put initial identity in if we don't have any visible
    CHECK_ERR(keyring_seed(ctx->keyring_file) == 0, "Failed to seed keyring");
  }
  
  return 1;
error:
  return 0;
}
Esempio n. 16
0
static int Server_load_ciphers(Server *srv, bstring ssl_ciphers_val)
{
    const struct tagbstring bstr_underscore = bsStatic("_");
    const struct tagbstring bstr_dash = bsStatic("-");

    struct bstrList *ssl_cipher_list = bsplit(ssl_ciphers_val, ' ');
    int i = 0, n = 0;
    int *ciphers = NULL;

    check(ssl_cipher_list != NULL && ssl_cipher_list->qty > 0,
            "Invalid cipher list, it must be separated by space ' ' characters "
            "and you need at least one.  Or, just leave it out for defaults.");

    ciphers = h_calloc(ssl_cipher_list->qty + 1, sizeof(int));
    check_mem(ciphers);

    for(i = 0; i < ssl_cipher_list->qty; i++) {
        bstring cipher = ssl_cipher_list->entry[i];

        int id = -1;

        // Replace underscores (used in old ciphers) with dashes
        bfindreplace(cipher, &bstr_underscore, &bstr_dash, 0);

        // Search legacy cipher list
        for(n = 0; legacy_cipher_table[n].name != NULL; ++n)
        {
            if(biseqcstr(cipher, legacy_cipher_table[n].name))
            {
                id = legacy_cipher_table[n].id;
                break;
            }
        }

        if(id != -1 && mbedtls_ssl_ciphersuite_from_id(id) != NULL)
        {
            ciphers[i] = id;
        }
        else
        {
            // Search polarssl cipher list
            const mbedtls_ssl_ciphersuite_t * suite =
                mbedtls_ssl_ciphersuite_from_string(bdata(cipher));

            if (suite != NULL)
                ciphers[i] = suite->id;
            else
                sentinel("Unrecognized cipher: %s", bdata(cipher));
        }
    }

    bstrListDestroy(ssl_cipher_list);
    ciphers[i] = 0;
    srv->ciphers = ciphers;
    hattach(ciphers, srv);

    return 0;
error:
    if(ssl_cipher_list) bstrListDestroy(ssl_cipher_list);
    if(ciphers != NULL) h_free(ciphers);
    return -1;
}
Esempio n. 17
0
void Server_queue_push(Server *srv)
{
    Server_queue_cleanup();
    darray_push(SERVER_QUEUE, srv);
    hattach(srv, SERVER_QUEUE);
}
int
csm_update_service(csm_service_list *services, csm_service *s, csm_ctx *ctx, int validate)
{
  if (validate)
    CHECK(csm_validate_fields(ctx, s), "Service doesn't validate");
//   assert(s->lifetime);
  long lifetime = s->lifetime;
  
  // check if service is attached to service_list
  CHECK(co_list_contains(services->services, (co_obj_t*)container_of(s, co_service_t, service)),
	"Cannot update service not in service list");
  
  // detach s->fields from s and attach to services->service_fields
  if (!co_list_contains(services->service_fields, s->fields)) {
    co_obj_t *fields = s->fields;
    hattach(fields, NULL);
    CHECK(co_list_append(services->service_fields, fields),
	  "Failed to add service fields to service list");
  }
  
  /* Create or verify signature */
  if (s->signature)
    CHECK(csm_verify_signature(s),"Invalid signature");
  else
    CHECK(csm_create_signature(s),"Failed to create signature");
  
  /* Set expiration timer on the service */
#ifdef USE_UCI
  long def_lifetime = default_lifetime();
  if (lifetime == 0 || (def_lifetime < lifetime && def_lifetime > 0))
    lifetime = def_lifetime;
#endif
  if (lifetime > 0) {
    struct timeval tv;
    avahi_elapse_time(&tv, 1000*lifetime, 0);
    time_t current_time = time(NULL);
    // create expiration event for service
    s->timeout = avahi_simple_poll_get(simple_poll)->timeout_new(avahi_simple_poll_get(simple_poll),
								       &tv,
								       _csm_expire_service,
								       s);
    /* Convert lifetime period into timestamp */
    if (current_time != ((time_t)-1)) {
      struct tm *timestr = localtime(&current_time);
      timestr->tm_sec += lifetime;
      current_time = mktime(timestr);
      char *c_time_string = ctime(&current_time);
      if (c_time_string) {
	c_time_string[strlen(c_time_string)-1] = '\0'; /* ctime adds \n to end of time string; remove it */
	s->expiration = h_strdup(c_time_string);
	CHECK_MEM(s->expiration);
	service_attach(s->expiration, s);
      }
    }
  }
  
  // finalize service by running update handlers
  csm_services_commit(services);
  
  return 1;
error:
  return 0;
}