Beispiel #1
0
static int dlist_int_test()
{
    printf("double list test ... MAX=%d\n", MAX);
    int arr[MAX];
    int i;
    int sum = 0;
    int max = INT_MIN;
    printf("MAX = %d\n", MAX);
    struct dlist *list = dlist_init();
    if (list) {
        /*
         * init arr
         */
        for (i = 0; i < MAX; i++) {
            arr[i] = i;
        }

        /*
         * dlist_add/dlist_length test
         */
        for (i = 0; i < MAX; i++) {
            dlist_add(list, arr + i);
            assert(dlist_length(list) == i + 1);
        }

        /*
         * dlist_serch test
         */
        for (i = 0; i < MAX; i++) {
            assert(dlist_search(list, arr + i) == DLIST_RET_OK);
        }
    
        /*
         * dlist_printf test
         */
        assert(dlist_printf(list, user_printf) == DLIST_RET_OK);
        assert(dlist_foreach(list, sum_cb, &sum) == DLIST_RET_OK);
        assert(dlist_foreach(list, max_cb, &max) == DLIST_RET_OK);

        /*
         * dlist_delete test
         */
        for (i = MAX - 1; i >= 0; i--) {
            assert(dlist_length(list) == i + 1);
            assert(dlist_delete(list, arr + i) == DLIST_RET_OK);
            assert(dlist_length(list) == i);
        }

        /*
         * dlist_destroy test
         */
        assert(dlist_destroy(list) == DLIST_RET_OK);
    }

    printf("sum = %d\n", sum);
    printf("max = %d\n", max);

    return 0;
}
Beispiel #2
0
static void test_int_dlist(void)
{
	int i = 0;
	int n = 100;
	int data = 0;
	DList* dlist = dlist_create(NULL, NULL, NULL);

	for(i = 0; i < n; i++)
	{
		assert(dlist_append(dlist, (void*)i) == RET_OK);
		assert(dlist_length(dlist) == (i + 1));
		assert(dlist_get_by_index(dlist, i, (void**)&data) == RET_OK);
		assert(data == i);
		assert(dlist_set_by_index(dlist, i, (void*)(2*i)) == RET_OK);
		assert(dlist_get_by_index(dlist, i, (void**)&data) == RET_OK);
		assert(data == 2*i);
		assert(dlist_set_by_index(dlist, i, (void*)i) == RET_OK);
		assert(dlist_find(dlist, cmp_int, (void*)i) == i);
	}

	for(i = 0; i < n; i++)
	{
		assert(dlist_get_by_index(dlist, 0, (void**)&data) == RET_OK);
		assert(data == (i));
		assert(dlist_length(dlist) == (n-i));
		assert(dlist_delete(dlist, 0) == RET_OK);
		assert(dlist_length(dlist) == (n-i-1));
		if((i + 1) < n)
		{
			assert(dlist_get_by_index(dlist, 0, (void**)&data) == RET_OK);
			assert((int)data == (i+1));
		}
	}
	
	assert(dlist_length(dlist) == 0);

	for(i = 0; i < n; i++)
	{
		assert(dlist_prepend(dlist, (void*)i) == RET_OK);
		assert(dlist_length(dlist) == (i + 1));
		assert(dlist_get_by_index(dlist, 0, (void**)&data) == RET_OK);
		assert(data == i);
		assert(dlist_set_by_index(dlist, 0, (void*)(2*i)) == RET_OK);
		assert(dlist_get_by_index(dlist, 0, (void**)&data) == RET_OK);
		assert(data == 2*i);
		assert(dlist_set_by_index(dlist, 0, (void*)i) == RET_OK);
	}

	i = n - 1;
	assert(dlist_foreach(dlist, check_and_dec_int, &i) == RET_OK);

	dlist_destroy(dlist);

	return;
}
Beispiel #3
0
/* FIXME */
void u_command(client c) {
	dstr pkey, skey;
	dlist_t dlist;

	if (dstr_length(c->argv[0]) == 1) {
		add_reply_error(c, "index can't be empty\r\n");
		return;
	}
	pkey = dstr_new(c->argv[0] + 1);
	skey = dstr_new(pkey);
	if (c->argc > 1) {
		int i;

		for (i = 1; i < c->argc; ++i) {
			skey = dstr_cat(skey, ",");
			skey = dstr_cat(skey, c->argv[i]);
		}
	}
	table_rwlock_wrlock(subscribers);
	if ((dlist = table_get_value(subscribers, pkey))) {
		struct kvd *kvd;

		if (NEW(kvd)) {
			dlist_node_t node, node2;

			kvd->key = skey;
			if ((node = dlist_find(dlist, kvd))) {
				FREE(kvd);
				kvd = (struct kvd *)dlist_node_value(node);
				if ((node2 = dlist_find(kvd->u.dlist, c)))
					dlist_remove(kvd->u.dlist, node2);
				if (dlist_length(kvd->u.dlist) == 0) {
					dlist_remove(dlist, node);
					kdfree(kvd);
				}
				if (dlist_length(dlist) == 0) {
					table_remove(subscribers, pkey);
					dlist_free(&dlist);
				}
			} else
				FREE(kvd);
		} else
			add_reply_error(c, "error allocating memory for kvd");
	}
	table_rwlock_unlock(subscribers);
	dstr_free(skey);
	dstr_free(pkey);
	add_reply_string(c, "\r\n", 2);
}
Beispiel #4
0
int
parse_interval_qualifier(mvc *sql, struct dlist *pers, int *sk, int *ek, int *sp, int *ep)
{
	*sk = iyear;
	*ek = isec;

	if (pers) {
		dlist *s = pers->h->data.lval;

		assert(s->h->type == type_int);
		*ek = *sk = s->h->data.i_val;
		*ep = *sp = s->h->next->data.i_val;

		if (dlist_length(pers) == 2) {
			dlist *e = pers->h->next->data.lval;

			assert(e->h->type == type_int);
			*ek = e->h->data.i_val;
			*ep = e->h->next->data.i_val;
		}
	}
	if (*sk > *ek) {
		snprintf(sql->errstr, ERRSIZE, _("End interval field is larger than the start field\n"));
		return -1;
	}
	if ((*sk == iyear || *sk == imonth) && *ek > imonth) {
		snprintf(sql->errstr, ERRSIZE, _("Correct interval ranges are year-month or day-seconds\n"));
		return -1;
	}
	if (*sk == iyear || *sk == imonth)
		return 0;
	return 1;
}
Ret packet_transfer_reset(PacketTransfer *thiz)
{
    return_val_if_fail(thiz != NULL, RET_INVALID_PARAMS);

    int i;
    int j;
    int size;

    /* 删除命令集合中的所有命令 */
    for (i = 0; i < NODE_NUM; i++)
    {
        size = dlist_length(thiz->command_set[i]);
        for (j = 0; i < size; j++)
        {
            dlist_delete(thiz->command_set[i], j);
        }
    }

    /* 重置回应 */
    memset(&thiz->response, 0, sizeof(thiz->response));

    /* 关闭与上位机连接 */
    if (thiz->uploader_socket != -1)
    {
        close(thiz->uploader_socket);
    }
    thiz->uploader_socket = -1;

    return RET_OK;
}
Beispiel #6
0
int dlist_insert(DList* thiz, int index, void* data)
{
	DListNode* node = NULL;
	DListNode* cursor = NULL;

	if((node = dlist_node_create(data)) == NULL)	return -1;

	if(thiz->first == NULL) {
		thiz->first = node;
		return 0;
	}

	cursor = dlist_get_node(thiz, index, 1);

	if(index < dlist_length(thiz)) {
		if(thiz->first == cursor) {
			thiz->first = node;
		} else {
			cursor->prev->next = node;
			node->prev = cursor->prev;
		}
		node->next = cursor;
		cursor->prev = node;
	} else {
		cursor->next = node;
		node->prev = cursor;
	}

	return 0;
}
Beispiel #7
0
/* FIXME */
void uall_command(client c) {
	dstr res = get_indices();
	dstr *fields = NULL;
	int nfield = 0, i;

	RTRIM(res);
	fields = dstr_split_len(res, dstr_length(res), ",", 1, &nfield);
	for (i = 1; i < nfield; ++i) {
		dstr pkey = dstr_new(fields[i]);
		dstr skey = dstr_new(pkey);
		dlist_t dlist;

		table_rwlock_wrlock(subscribers);
		if ((dlist = table_get_value(subscribers, pkey))) {
			struct kvd *kvd;

			if (NEW(kvd)) {
				dlist_node_t node, node2;

				kvd->key = skey;
				if ((node = dlist_find(dlist, kvd))) {
					FREE(kvd);
					kvd = (struct kvd *)dlist_node_value(node);
					if ((node2 = dlist_find(kvd->u.dlist, c)))
						dlist_remove(kvd->u.dlist, node2);
					if (dlist_length(kvd->u.dlist) == 0) {
						dlist_remove(dlist, node);
						kdfree(kvd);
					}
					if (dlist_length(dlist) == 0) {
						table_remove(subscribers, pkey);
						dlist_free(&dlist);
					}
				} else
					FREE(kvd);
			} else
				add_reply_error(c, "error allocating memory for kvd");
		}
		table_rwlock_unlock(subscribers);
		dstr_free(skey);
		dstr_free(pkey);
	}
	add_reply_string(c, "\r\n", 2);
	dstr_free(res);
}
Beispiel #8
0
void
list_plugins(const char *const nick)
{
    notice(nick, "%d plugins loaded:", dlist_length(&plugins));
    DLINK_FOREACH(node, dlist_head(&plugins)) {
        const struct plugin_handle_t *const p = dlink_data(node);
        notice(nick, "%s - %s", p->plugin->name, p->file_name);
    }
}
Beispiel #9
0
void register_diff(Dlist* p_list, int descSock , char* reponse){
  printf("Nouvelle connexion...\n");
  int retour;
  char id [TAILLE_ID+1];
  char ip1 [TAILLE_ADDRESS+1];
  char port1 [TAILLE_PORT+1];
  char ip2 [TAILLE_ADDRESS+1];
  char port2 [TAILLE_PORT+1];

  if (strlen(reponse) != 57){
    printf("WARNING: Mauvais format REGI\n");
    char regi_message[57];
    format_regi(regi_message, reponse);
    strcpy(reponse, regi_message);
  }
  else if(dlist_length(p_list)>= NBR_DIFF){
    retour = send(descSock, "RENO\r\n", strlen("RENO") + 2 * sizeof(char), 0);
    printf("Mauvais format de message reçu, reçu: %s\n", reponse);
    if (retour == -1){
      perror (strerror (errno));
      exit (1);
    }
  }
  snprintf(id,    TAILLE_ID+1,      "%s", reponse + REGI+1);
  if(verbose)
  printf("id :  %s\n", id);
  snprintf(ip1,   TAILLE_ADDRESS+1, "%s", reponse + REGI+1 + TAILLE_ID+1);
  if(verbose)
  printf("ip1 : %s\n", ip1);
  snprintf(port1, TAILLE_PORT+1,    "%s", reponse + REGI+1 + TAILLE_ID+1 + TAILLE_ADDRESS+1);
  if(verbose)
  printf("port1 : %s\n", port1);
  snprintf(ip2,   TAILLE_ADDRESS+1, "%s", reponse + REGI+1 + TAILLE_ID+1 + TAILLE_ADDRESS+1 + TAILLE_PORT+1);
  if(verbose)
  printf("ip2 : %s\n", ip2);
  snprintf(port2, TAILLE_PORT+1,    "%s", reponse + REGI+1 + TAILLE_ID+1 + TAILLE_ADDRESS+1 + TAILLE_PORT+1 + TAILLE_ADDRESS+1);
  if(verbose)
  printf("port2 : %s\n", port2);
  struct node* p_new;
  if ((p_new = dlist_append(p_list, id, ip1, port1, ip2, port2)) != NULL){
    retour = send(descSock, "REOK\r\n", strlen("REOK") + 2 * sizeof(char), 0);
    printf("REOK\n");
    if (retour == -1){
      perror (strerror (errno));
      exit (1);
    }
    ask_RUOK(p_list, descSock, p_new);
  }
  else{
      retour = send(descSock, "RENO\r\n", strlen("RENO") + 2 * sizeof(char), 0);
      printf("RENO\n");
  }
}
Beispiel #10
0
static int dlist_char_test()
{
    char str[] = "dlist";
    char str2[] = "thinking";
    struct dlist *list = dlist_init();

    assert(list != NULL);
    return_val_if_fail(dlist_length(list) == 0, -1);
    char *pstr = NULL;
    dlist_add(list, str);
    return_val_if_fail(dlist_length(list) == 1, -1);
    dlist_add(list, str2);
    dlist_add(list, pstr = strdup("test"));
    dlist_foreach(list, string_toupper_cb, NULL);
    dlist_printf(list, string_printf);
    dlist_destroy(list);
    list = NULL;
    free(pstr);

    return 0;
}
Beispiel #11
0
static void* reader(void* param)
{
    int i = 0;
    DList* dlist = (DList*)param;

    for (i = 0; i < NR; i++) {
        int length = dlist_length(dlist);
        dlist_find(dlist, cmp_int, (void*)i);
    }

    return NULL;
}
Beispiel #12
0
int main()
{

    struct DList* list = dlist_create();
    
    dlist_print(list);
    printf("list length = %d\n", dlist_length(list));
    dlist_append(list, 5);
    printf("list length = %d\n", dlist_length(list));
    dlist_append(list, 7);
    printf("list length = %d\n", dlist_length(list));
    dlist_append(list, 8);
    printf("list length = %d\n", dlist_length(list));
    dlist_print(list);
	dlist_print_reverse(list);
	
	dlist_remove(list, 1);
	printf("list length = %d\n", dlist_length(list));
	dlist_print(list);
	dlist_print_reverse(list);
	dlist_insert(list, 0, 5);
	printf("list length = %d\n", dlist_length(list));
	dlist_print(list);
	dlist_print_reverse(list);
	
    dlist_delete(list);
    return 0;
}
Beispiel #13
0
Ret dlist_insert(DList* thiz, size_t index, void* data)
{
	Ret ret = RET_OK;
	DListNode* node = NULL;
	DListNode* cursor = NULL;

	return_val_if_fail(thiz != NULL, RET_INVALID_PARAMS); 

	dlist_lock(thiz);

	do
	{
		if((node = dlist_create_node(thiz, data)) == NULL)
		{
			ret = RET_OOM;
			break;
		}

		if(thiz->first == NULL)
		{
			thiz->first = node;
			break;
		}

		cursor = dlist_get_node(thiz, index, 1);
		
		if(index < dlist_length(thiz))
		{
			node->next = cursor;
			if(cursor->prev != NULL)
			{
				cursor->prev->next = node;
			}
			cursor->prev = node;
			if(thiz->first == cursor)
			{
				thiz->first = node;
			}
		}
		else
		{
			cursor->next = node;
			node->prev = cursor;
		}
	}while(0);

	dlist_unlock(thiz);

	return ret;
}
static void *consumer_thread(void *arg)
{
	int i = 0;
	DList *dlist = (DList *)arg;
	
	printf("consumer thread executed!\n");
	for(i = 0; i < 2000; i++) {
		usleep(20);
		printf("dlist length = %d\n", dlist_length(dlist));
		dlist_find(dlist, cmp_int, (void *)i);
	}
	
	return NULL;
}
Beispiel #15
0
static void test_invalid_params(void)
{
	printf("===========Warning is normal begin==============\n");
	assert(dlist_length(NULL) == 0);
	assert(dlist_prepend(NULL, 0) == RET_INVALID_PARAMS);
	assert(dlist_append(NULL, 0) == RET_INVALID_PARAMS);
	assert(dlist_delete(NULL, 0) == RET_INVALID_PARAMS);
	assert(dlist_insert(NULL, 0, 0) == RET_INVALID_PARAMS);
	assert(dlist_set_by_index(NULL, 0, 0) == RET_INVALID_PARAMS);
	assert(dlist_get_by_index(NULL, 0, NULL) == RET_INVALID_PARAMS);
	assert(dlist_find(NULL, NULL, NULL) < 0);
	assert(dlist_foreach(NULL, NULL, NULL) == RET_INVALID_PARAMS);
	printf("===========Warning is normal end==============\n");

	return;
}
Beispiel #16
0
size_t   hash_table_length(HashTable* thiz)
{
	size_t i = 0;
	size_t nr = 0;

	return_val_if_fail(thiz != NULL, 0);

	for(i = 0; i < thiz->slot_nr; i++)
	{
		if(thiz->slots[i] != NULL)
		{
			nr += dlist_length(thiz->slots[i]);
		}
	}

	return nr;
}
Beispiel #17
0
/*
 * FUNCTION:	compose_stripe_within_hba(devconfig_t *request,
 *			dlist_t *hbas, uint64_t nbytes,
 *			int maxcomp, int mincomp, dlist_t **stripe)
 *
 * INPUT:	request	- pointer to a devconfig_t of the current request
 *		hbas	- pointer to a list of available HBAs
 *		nbytes	- the desired capacity for the stripe
 *		maxcomp - the maximum number of stripe components
 *		mincomp - the minimum number of stripe components
 *
 * OUTPUT:	stripe	- pointer to a stripe devconfig_t result
 *
 * RETURNS:	int	- 0 on success
 *			 !0 otherwise.
 *
 * PURPOSE:	Layout function which compose a stripe of the desired size
 *		using available disks within any single HBA from the input list.
 *
 *		The number of components within the composed stripe will be
 *		in the range of min to max, preferring more components
 *		over fewer.
 *
 * 		All input HBAs are expected to have at least mincomp
 *		available disks and total space sufficient for the stripe.
 *
 *		If the stripe can be composed, a pointer to it is returned in
 *		the stripe devconfig_t *.
 *
 *
 *		while (more hbas and stripe not composed) {
 *		    select HBA
 *		    if (not enough available space on this HBA) {
 *			continue;
 *		    }
 *		    get available disks for HBA
 *		    use # disks as max # of stripe components
 *		    try to compose stripe
 *		}
 *
 */
static int
compose_stripe_within_hba(
	devconfig_t	*request,
	dlist_t		*hbas,
	uint64_t	nbytes,
	uint16_t	min,
	uint16_t	max,
	devconfig_t	**stripe)
{
	int		error = 0;

	dlist_t		*iter = NULL;

	*stripe = NULL;

	for (iter = hbas;
	    (iter != NULL) && (error == 0) && (*stripe == NULL);
	    iter = iter->next) {

	    dm_descriptor_t hba = (uintptr_t)iter->obj;
	    dlist_t	*disks = NULL;
	    uint64_t	space = 0;
	    uint16_t	ncomp = 0;
	    char	*name;

	    ((error = get_display_name(hba, &name)) != 0) ||
	    (error = hba_get_avail_disks_and_space(request,
		    hba, &disks, &space));

	    if (error == 0) {
		if (space >= nbytes) {
		    ncomp = dlist_length(disks);
		    ncomp = ((ncomp > max) ? max : ncomp);
		    error = compose_stripe(
			    request, nbytes, disks, ncomp,
			    min, NULL, stripe);
		} else {
		    print_hba_insufficient_space_msg(name, space);
		}
	    }

	    dlist_free_items(disks, NULL);
	}

	return (error);
}
Beispiel #18
0
DListRet dlist_insert(DList* thiz, size_t index, void* data)
{
	DListNode* node = NULL;
	DListNode* cursor = NULL;

	if((node = dlist_create_node(thiz, data)) == NULL)
	{
		return DLIST_RET_OOM; 
	}

	if(thiz->first == NULL)
	{
		thiz->first = node;

		return DLIST_RET_OK;
	}

	cursor = dlist_get_node(thiz, index, 1);
	
	if(index < dlist_length(thiz))
	{
		if(thiz->first == cursor)
		{
			thiz->first = node;
		}
		else
		{
			cursor->prev->next = node;
			node->prev = cursor->prev;
		}
		node->next = cursor;
		cursor->prev = node;
	}
	else
	{
		cursor->next = node;
		node->prev = cursor;
	}

	return DLIST_RET_OK;
}
Beispiel #19
0
static void multi_thread_test(void)
{
    pthread_t consumer_tid = 0;
    pthread_t producer_tid = 0;
    pthread_t reader_tid = 0;
    Locker* rw_locker = locker_pthread_create();
    Locker* rd_locker = locker_pthread_create();
    DList* dlist = dlist_create(NULL, NULL,
                                rw_locker_create(rw_locker, rd_locker));

    pthread_create(&producer_tid, NULL, producer, dlist);
    pthread_create(&consumer_tid, NULL, consumer, dlist);
    pthread_create(&reader_tid, NULL, reader, dlist);

    pthread_join(consumer_tid, NULL);
    pthread_join(producer_tid, NULL);
    pthread_join(reader_tid, NULL);
    printf("length=%d\n", dlist_length(dlist));
    dlist_destroy(dlist);

    return;
}
Beispiel #20
0
static int server_cron(event_loop el, unsigned long id, void *data) {
	dlist_iter_t iter;
	dlist_node_t node;
	NOT_USED(el);
	NOT_USED(id);
	NOT_USED(data);

	if (log_reload) {
		close_logger();
		if (init_logger("/var/log/xcb/xcb-dp2.log", __LOG_DEBUG) == 0) {
			const char *tmp;

			pthread_mutex_lock(&cfg_lock);
			if ((tmp = variable_retrieve(cfg, "general", "log_level"))) {
				if (!strcasecmp(tmp, "debug"))
					set_logger_level(__LOG_DEBUG);
				else if (!strcasecmp(tmp, "info"))
					set_logger_level(__LOG_INFO);
				else if (!strcasecmp(tmp, "notice"))
					set_logger_level(__LOG_NOTICE);
				else if (!strcasecmp(tmp, "warning"))
					set_logger_level(__LOG_WARNING);
			}
			pthread_mutex_unlock(&cfg_lock);
			log_reload = 0;
		}
		/* FIXME */
		if (addms)
			table_clear(times);
	}
	if (shut_down) {
		if (prepare_for_shutdown() == 0)
			exit(0);
		xcb_log(XCB_LOG_WARNING, "SIGTERM received, but errors trying to shutdown the server");
	}
	/* FIXME */
	iter = dlist_iter_new(clients_to_close, DLIST_START_HEAD);
	while ((node = dlist_next(iter))) {
		client c = (client)dlist_node_value(node);

		if (c->refcount == 0)
			client_free(c);
	}
	dlist_iter_free(&iter);
	/* FIXME */
	if (cronloops % 200 == 0) {
		char meme[] = "SU OT GNOLEB ERA ESAB RUOY LLA";
		int status;

		/* heartbeat */
		dlist_lock(clients);
		if (dlist_length(clients) > 0) {
			dstr res = dstr_new("HEARTBEAT|");
			dstr ip = getipv4();

			res = dstr_cat(res, ip);
			res = dstr_cat(res, "\r\n");
			iter = dlist_iter_new(clients, DLIST_START_HEAD);
			while ((node = dlist_next(iter))) {
				client c = (client)dlist_node_value(node);

				pthread_spin_lock(&c->lock);
				if (net_try_write(c->fd, res, dstr_length(res), 100, NET_NONBLOCK) == -1)
					xcb_log(XCB_LOG_WARNING, "Writing to client '%p': %s",
						c, strerror(errno));
				pthread_spin_unlock(&c->lock);
			}
			dlist_iter_free(&iter);
			dstr_free(ip);
			dstr_free(res);
		}
		dlist_unlock(clients);
		/* FIXME: trying to lower the high CPU load while idle */
		if ((status = pgm_send(pgm_sender, meme, sizeof meme, NULL)) != PGM_IO_STATUS_NORMAL)
			xcb_log(XCB_LOG_WARNING, "Communication test failed");
	}
	++cronloops;
	return 100;
}
Beispiel #21
0
/*
 * FUNCTION:	layout_stripe(devconfig_t *request, uint64_t nbytes,
 *			dlist_t **results)
 *
 * INPUT:	request	- pointer to a devconfig_t of the current request
 *		nbytes	- the desired capacity of the stripe
 *
 * OUPUT:	results	- pointer to a list of composed volumes
 *
 * RETURNS:	int	- 0 on success
 *			 !0 otherwise.
 *
 * PURPOSE:	Main layout driver for composing stripe volumes.
 *
 *		Attempts to construct a stripe of size nbytes.
 *
 *		Basic goal of all strategies is to build wide-thin stripes:
 *		build widest stripe possible across as many HBAs as possible.
 *
 *		Several different layout strategies are tried in order
 *		of preference until one succeeds or there are none left.
 *
 *		1 - stripe across similar HBAs
 *		    . number of components is driven by # of HBAs
 *		    . requires mincomp available HBAs
 *
 *		2 - stripe within a single HBA
 *		    . number of components is driven by # of disks
 *		    . requires at least 1 HBA with mincomp disks
 *
 *		3 - stripe across all available disks on similar HBAs
 *		    . number of components is driven by # of disk
 *		    . requires at least mincomp disks
 *
 *		4 - stripe across all available HBAs
 *		    . number of components is driven by # of HBAs
 *		    . requires at least mincomp HBAs
 *
 *		5 - stripe across all available disks on all HBAs
 *		    . number of components is driven by # of disks
 *		    . requires at least mincomp disks
 *
 *		Each strategy tries to compose a stripe with the
 *		maximum number of components first then reduces the
 *		number of components down to mincomp.
 *
 *		get allowed minimum number of stripe components
 *		get allowed maximum number of stripe components
 *		get available HBAs
 *
 *		group HBAs by characteristics
 *		for (each HBA grouping) and (stripe not composed) {
 *		    select next HBA group
 *		    for (strategy[1,2,3]) and (stripe not composed) {
 *			compose stripe using HBAs in group
 *		    }
 *		}
 *
 *		if (stripe not composed) {
 *		    for (strategy[4,5]) and (stripe not composed) {
 *			compose stripe using all HBAs
 *		    }
 *		}
 *
 *		if (stripe composed) {
 *		    append composed stripe to results
 *		}
 *
 */
int
layout_stripe(
	devconfig_t	*request,
	uint64_t	nbytes,
	dlist_t		**results)
{
	/*
	 * these enums define the # of strategies and the preference order
	 * in which they are tried
	 */
	typedef enum {
		STRIPE_ACROSS_SIMILAR_HBAS_DISK_PER = 0,
		STRIPE_WITHIN_SIMILAR_HBA,
		STRIPE_ACROSS_SIMILAR_HBAS,
		N_SIMILAR_HBA_STRATEGIES
	} similar_hba_strategy_order_t;

	typedef enum {
		STRIPE_ACROSS_ANY_HBAS_DISK_PER = 0,
		STRIPE_ACROSS_ANY_HBAS,
		N_ANY_HBA_STRATEGIES
	} any_hba_strategy_order_t;


	dlist_t		*usable_hbas = NULL;
	dlist_t		*similar_hba_groups = NULL;
	dlist_t		*iter = NULL;
	devconfig_t	*stripe = NULL;

	uint16_t	mincomp	= 0;
	uint16_t	maxcomp	= 0;

	int		error = 0;

	(error = get_usable_hbas(&usable_hbas));
	if (error != 0) {
	    return (error);
	}

	print_layout_volume_msg(devconfig_type_to_str(TYPE_STRIPE), nbytes);

	if (dlist_length(usable_hbas) == 0) {
	    print_no_hbas_msg();
	    volume_set_error(gettext("There are no usable HBAs."));
	    return (-1);
	}

	((error = group_similar_hbas(usable_hbas, &similar_hba_groups)) != 0) ||

	/*
	 * determine the min/max number of stripe components
	 * based on the request, the diskset defaults or the
	 * global defaults.  These are absolute limits, the
	 * actual values are determined by the number of HBAs
	 * and/or disks available.
	 */
	(error = get_stripe_min_comp(request, &mincomp)) ||
	(error = get_stripe_max_comp(request, &maxcomp));
	if (error != 0) {
	    return (error);
	}

	for (iter = similar_hba_groups;
	    (error == 0) && (stripe == NULL) && (iter != NULL);
	    iter = iter->next) {

	    dlist_t *hbas = (dlist_t *)iter->obj;

	    similar_hba_strategy_order_t order;

	    for (order = STRIPE_ACROSS_SIMILAR_HBAS_DISK_PER;
		(order < N_SIMILAR_HBA_STRATEGIES) &&
			(stripe == NULL) && (error == 0);
		order++) {

		dlist_t *selhbas = NULL;
		dlist_t	*disks = NULL;
		int	n = 0;

		switch (order) {

		case STRIPE_ACROSS_SIMILAR_HBAS_DISK_PER:

		    error = select_hbas_with_n_disks(
			    request, hbas, 1, &selhbas, &disks);

		    if (error == 0) {

/* BEGIN CSTYLED */
oprintf(OUTPUT_TERSE,
gettext("  -->Strategy 1: use 1 disk from %d-%d similar HBAs - stripe across HBAs\n"),
	mincomp, maxcomp);
/* END CSTYLED */

			if ((n = dlist_length(selhbas)) >= mincomp) {
			    n = ((n > maxcomp) ? maxcomp : n);
			    error = compose_stripe(
				    request, nbytes, disks, n,
				    mincomp, NULL, &stripe);
			} else {
			    print_insufficient_hbas_msg(n);
			}
		    }

		    break;

		case STRIPE_WITHIN_SIMILAR_HBA:

		    error = select_hbas_with_n_disks(
			    request, hbas, mincomp, &selhbas, &disks);

		    if (error == 0) {

/* BEGIN CSTYLED */
oprintf(OUTPUT_TERSE,
gettext("  -->Strategy 2: use %d-%d disks from any single HBA - stripe within HBA\n"),
	mincomp, maxcomp);
/* END CSTYLED */

			if ((n = dlist_length(selhbas)) > 0) {
			    error = compose_stripe_within_hba(
				    request, selhbas, nbytes,
				    mincomp, maxcomp, &stripe);
			} else {
			    print_insufficient_disks_msg(n);
			}
		    }

		    break;

		case STRIPE_ACROSS_SIMILAR_HBAS:

		    error = select_hbas_with_n_disks(
			    request, hbas, 1, &selhbas, &disks);

		    if (error == 0) {

/* BEGIN CSTYLED */
oprintf(OUTPUT_TERSE,
gettext("  -->Strategy 3: use %d-%d disks from %d similar HBAs - stripe across HBAs\n"),
	mincomp, maxcomp, dlist_length(hbas));
/* END CSTYLED */

			if ((n = dlist_length(selhbas)) > 0) {
			    if ((n = dlist_length(disks)) >= mincomp) {
				n = ((n > maxcomp) ? maxcomp : n);
				error = compose_stripe(
					request, nbytes, disks, n,
					mincomp, NULL, &stripe);
			    } else {
				print_insufficient_disks_msg(n);
			    }
			} else {
			    print_insufficient_hbas_msg(n);
			}
		    }

		    break;

		default:
		    break;
		}

		dlist_free_items(disks, NULL);
		dlist_free_items(selhbas, NULL);
	    }
	}

	for (iter = similar_hba_groups; iter != NULL; iter = iter->next) {
	    dlist_free_items((dlist_t *)iter->obj, NULL);
	}
	dlist_free_items(similar_hba_groups, NULL);

	/*
	 * if striping within similar HBA groups failed,
	 * try across all available HBAs
	 */
	if ((stripe == NULL) && (error == 0)) {

	    any_hba_strategy_order_t order;

	    for (order = STRIPE_ACROSS_ANY_HBAS_DISK_PER;
		(order < N_ANY_HBA_STRATEGIES) &&
			(stripe == NULL) && (error == 0);
		order++) {

		dlist_t	*selhbas = NULL;
		dlist_t	*disks = NULL;
		int	n = 0;

		switch (order) {

		case STRIPE_ACROSS_ANY_HBAS_DISK_PER:

		    error = select_hbas_with_n_disks(
			    request, usable_hbas, 1, &selhbas, &disks);

		    if (error == 0) {

/* BEGIN CSTYLED */
oprintf(OUTPUT_TERSE,
gettext("  -->Strategy 4: use 1 disk from %d-%d available HBAs - stripe across any HBAs\n"),
	mincomp, maxcomp);
/* END CSTYLED */

			if ((n = dlist_length(selhbas)) >= mincomp) {

			    n = ((n > maxcomp) ? maxcomp : n);
			    error = compose_stripe(
				    request, nbytes, disks, n,
				    mincomp, NULL, &stripe);

			} else {
			    print_insufficient_hbas_msg(n);
			}
		    }

		    break;

		case STRIPE_ACROSS_ANY_HBAS:

		    error = select_hbas_with_n_disks(
			    request, usable_hbas, 1, &selhbas, &disks);

		    if (error == 0) {

/* BEGIN CSTYLED */
oprintf(OUTPUT_TERSE,
gettext("  -->Strategy 5: use %d-%d disks from %d available HBA - stripe across any HBAs\n"),
	mincomp, maxcomp, dlist_length(selhbas));
/* END CSTYLED */

			if ((n = dlist_length(disks)) >= mincomp) {

			    n = ((n > maxcomp) ? maxcomp : n);
			    error = compose_stripe(
				    request, nbytes, disks, n,
				    mincomp, NULL, &stripe);

			} else {
			    print_insufficient_disks_msg(n);
			}
		    }

		    break;
		}

		dlist_free_items(disks, NULL);
		dlist_free_items(selhbas, NULL);
	    }
	}

	if (stripe != NULL) {

	    dlist_t *item = NULL;
	    if ((item = dlist_new_item(stripe)) == NULL) {
		error = ENOMEM;
	    } else {
		*results = dlist_append(item, *results, AT_TAIL);
		print_layout_success_msg();
	    }

	} else if (error != 0) {

	    print_debug_failure_msg(
		    devconfig_type_to_str(TYPE_STRIPE),
		    get_error_string(error));

	} else {

	    print_insufficient_resources_msg(
		    devconfig_type_to_str(TYPE_STRIPE));
	    error = -1;
	}

	return (error);
}
Beispiel #22
0
/* THE MAIN */
int main (const int argc, const char * argv[]) {

  /* Socket data */
  soc_token soc = init_soc;
  soc_host lan;
  soc_port port;
  int soc_fd, fd;

  /* Socket message */
  msg_type msg;

  /* Times and timeouts */
  timeout_t start_time, end_time, current_time;
  timeout_t wait_timeout;
  double local_time, remote_time;

  /* Dynamic list of server infos */
  dlist list;
  info_type info;

  /* Utilities */
  boolean for_read;
  char buff[256];
  int res;
  char *index;

  /*********/
  /* Start */
  /*********/
  /* Save prog name */
  strcpy (prog, argv[0]);
  strcpy (prog, basename (prog));

  /*******************/
  /* Parse arguments */
  /*******************/
  /* Check args */
  if (argc != 2) {
    error ("Invalid argument");
  }
  /* Parse IPM address and port */
  strcpy (buff, argv[1]);
  index = strstr (buff, ":");
  if (index == NULL) {
     error ("Invalid argument");
  }
  *index = '\0';
  index++;
  if (soc_str2host (buff, &lan) != SOC_OK) {
    sprintf (buff, "Invalid ipm address %s", buff);
    error (buff);
  }
  if (soc_str2port (index, &port) != SOC_OK) {
    sprintf (buff, "Invalid port num %s", index);
    error (buff);
  }

  /**************/
  /* Initialize */
  /**************/
  /* Init dynamic list */
  dlist_init (& list, sizeof(info_type));
  /* Init socket */
  if (soc_open (&soc, udp_socket) != SOC_OK) {
    perror ("opening socket");
    error ("Socket initialization failed");
  }
  if (soc_set_dest_host_port (soc, &lan, port) != SOC_OK) {
    perror ("setting destination");
    error ("Socket initialization failed");
  }
  if (soc_link_port (soc, port) != SOC_OK) {
    perror ("linking to port");
    error ("Socket initialization failed");
  }
  if (soc_get_dest_host (soc, &lan) != SOC_OK) {
    perror ("getting dest lan");
    error ("Socket initialization failed");
  }
  if (soc_get_dest_port (soc, &port) != SOC_OK) {
    perror ("getting dest port");
    error ("Socket initialization failed");
  }
  /* Add socket to waiting point */
  if (soc_get_id(soc, &soc_fd) != SOC_OK) {
    perror ("getting socket id");
    error ("Socket initialization failed");

  }
  if (evt_add_fd(soc_fd, TRUE) != WAIT_OK) {
    perror("Adding fd");
    error ("Socket initialization failed");
  }
  /* Activate signal catching */
  activate_signal_handling();
  /* Report starting */
  buff[0]='\0';
  addr_image (&lan, buff);
  printf ("%s mcasting at address %s on port %d.\n", prog, buff, (int) port);
  /* Init times */
  get_time (&start_time);
  current_time = start_time;
  end_time = start_time;
  incr_time (&end_time, DELAY_CLIENT_MS);
  /* Send initial ping request */
  msg.ping = TRUE;
  msg.time = start_time;
  if (soc_send (soc, (soc_message) &msg, sizeof(msg)) != SOC_OK) {
    perror ("sending ping");
    error ("Sending ping request failed");
  }

  /*************/
  /* Main loop */
  /*************/
  for (;;) {
    /* First step is to loop until timeout */
    if (wait_timeout.tv_sec != -1) {
      wait_timeout = end_time;
      res = sub_time (&wait_timeout, &current_time);
      if (res <= 0) {
        break;
      }
    }
    if (evt_wait (&fd, &for_read, &wait_timeout) != WAIT_OK) {
      perror ("waiting for event");
      error ("Waiting for events failed");
    }
    if (! for_read) {
      error ("Write event received");
    }
    /* Termination signal */
    if (fd == SIG_EVENT) {
      if (get_signal () == SIG_TERMINATE) {
        break;
      }
    } else if (fd == NO_EVENT) {
      /* Timeout: first step ends with a dump of servers */
      if (dlist_length(&list) != 0) {
        dlist_rewind (&list, TRUE);
        for (;;) {
          dlist_read (&list, &info);
          /* Get host name if possible, else dump address */
          res = soc_host_name_of (&info.host, buff, sizeof(buff));
          if (res != SOC_OK) {
            buff[0]='\0';
            addr_image (&info.host, buff);
          }
          /* Compute (Start_time + Reception_time) / 2 */
          local_time = (time_to_double (&start_time)
                        + time_to_double (&info.reception_time) ) / 2.0;
          remote_time = time_to_double (&info.server_time);
          printf ("Host %s is shifted by %4.03fs\n", buff, remote_time - local_time);

          /* Done when last record has been put */
          if (dlist_get_pos (&list, FALSE) == 1) {
            break;
          }
          dlist_move (&list, TRUE);
        }
      }
      /* Now entering second step: infinite timeout */
      wait_timeout.tv_sec = -1;
      wait_timeout.tv_usec = -1;
      printf ("%s ready.\n", prog);
    } else if (fd != soc_fd) {
      sprintf (buff, "Invalid fd %d received", fd);
      error (buff);
    } else {
      /* Now this is the socket, read message */
      res = soc_receive (soc, (soc_message) &msg, sizeof(msg), TRUE);
      if (res < 0) {
        perror ("reading from socket");
        error ("Reading message failed");
      } else if (res != sizeof(msg)) {
        sprintf (buff, "Invalid size received, expected %d, got %d",
                       (int)sizeof(msg), res);
        error (buff);
      }
      get_time (&current_time);
      /* Client and server different behaviours */
      if ((wait_timeout.tv_sec != -1) && !msg.ping) {
        /* First step: store the address and time of server, if pong */
        if (soc_get_dest_host (soc, &(info.host)) != SOC_OK) {
          perror ("getting dest host");
          error ("Getting server address failed");
        }
        info.server_time = msg.time;
        info.reception_time = current_time;
        dlist_insert (&list, &info, TRUE);

      } else if ( (wait_timeout.tv_sec == -1) && msg.ping) {
        /* Second step: reply pong and time to ping */
        msg.time = current_time;
        msg.ping = FALSE;
        if (soc_send (soc, (soc_message) &msg, sizeof(msg)) != SOC_OK) {
          perror ("sending pong");
          error ("Sending pong request failed");
        }
      }
    }
  } /* End of main loop */


  /* Clean - Close */
  dlist_delete_all (&list);
  (void) evt_del_fd (soc_fd, TRUE);
  (void) soc_close (&soc);
  printf ("Done.\n");
  exit (0);
}
Beispiel #23
0
#include "helpers.h"

TEST(copy_works_on_empty_list) {
    USING(dlist_new(sizeof(int))) {
        dlist_t *copy = dlist_copy(list);
        assertEquals(dlist_length(copy), 0);
        assertEquals(dlist_size(copy), dlist_size(list));
        assertEquals(dlist_verify(copy), 0);
        dlist_free(copy);
    }

    USING(dlist_new(sizeof(float))) {
        dlist_t *copy = dlist_copy(list);
        assertEquals(dlist_length(copy), 0);
        assertEquals(dlist_size(copy), dlist_size(list));
        assertEquals(dlist_verify(copy), 0);
        dlist_free(copy);
    }
}

TEST(copy_works_on_full_list) {
    int one = 1, two = 2, three = 3, four = 4;

    USING(dlist_new(sizeof(int))) {
        dlist_append(list, &one);

        dlist_t *copy = dlist_copy(list);
        assertNotEquals(copy, NULL);
        assertEquals(dlist_verify(copy), 0);
        assertEquals(dlist_length(copy), dlist_length(list));
        assertEquals(dlist_size(copy), dlist_size(list));
Beispiel #24
0
int test_dlist()
{
	puts("##########################################");	
	puts("starting double linked list tests");
	puts("##########################################");
	
	int value = 0;
	struct DList *dlist = dlist_create();
	
	puts("empty double list created");
	
	if (dlist_length(dlist) != 0) {
		printf("dlist_length of empty list should be zero\n");
		return 0;
	}

	puts("dlist_length ok");
	
	// Insert value 101 and test functions
	dlist_insert(dlist, 0, 101);
	if (dlist_length(dlist) != 1) {
		printf("dlist_length should be 1\n");
		return 0;
	}

	if (dlist_get(dlist, 0, &value) == 0) {
		printf("Error in dlist_get (1)\n");
		return 0;
	}
	if (value != 101) {
		printf("dlist_get should return value 101\n");
		return 0;
	}

	// Insert value 202 and test functions
	dlist_insert(dlist, 0, 202);
	if (dlist_length(dlist) != 2) {
		printf("dlist_length should return 2\n");
		return 0;
	}

	if (dlist_get(dlist, 0, &value) == 0) {
		printf("Error in dlist_length (2)\n");
		return 0;
	}
	if (value != 202) {
		printf("dlist_get should return 202\n");
		return 0;
	}

	puts("dlist_get ok");
	
	// Test remove function

	if (dlist_remove(dlist, 1) == 0) {
		printf("Error in dlist_remove\n");
		return 0;
	}

	if (dlist_length(dlist) != 1) {
		printf("dlist_length should return 1 (after remove)\n");
		return 0;
	}

	if (dlist_remove(dlist, 1) != 0) {
		printf("Error in dlist_remove\n");
		return 0;
	}

	if (dlist_length(dlist) != 1) {
		printf("dlist_length should return 1 (after remove)\n");
		return 0;
	}

	if (dlist_remove(dlist, 0) == 0) {
		printf("Error in dlist_remove\n");
		return 0;
	}

	if (dlist_length(dlist) != 0) {
		printf("dlist_length should return 0 (after remove)\n");
		return 0;
	}

	if (dlist_remove(dlist, 0) != 0) {
		printf("Error in dlist_remove\n");
		return 0;
	}

	if (dlist_length(dlist) != 0) {
		printf("dlist_length should return 0 (after remove)\n");
		return 0;
	}
	
	puts("dlist_remove ok");
	
	// test dlist_append()
	
	dlist_append(dlist, -5);
	dlist_append(dlist, 1);
	dlist_append(dlist, 15);
	
	if (dlist_length(dlist) != 3) {
		printf("dlist_length should return 0\n");
		return 0;
	}
	
	if (dlist_get(dlist, 0, &value) != 1) {
		printf("Error in dlist_append\n");
		return 0;
	}
	
	if (value != -5) {
		printf("dlist_get should return -5\n");
		return 0;
	}
	
	if (dlist_get(dlist, 1, &value) != 1) {
		printf("Error in dlist_append\n");
		return 0;
	}
	
	if (value != 1) {
		printf("dlist_get should return 1\n");
		return 0;
	}

	if (dlist_get(dlist, 2, &value) != 1) {
		printf("Error in dlist_append\n");
		return 0;
	}
	
	if (value != 15) {
		printf("dlist_get should return 15\n");
		return 0;
	}
	
	puts("dlist_append ok");
	
	// test dlist insert
	
	dlist_insert(dlist, -5, 0);
	
	if (dlist_length(dlist) != 4) {
		printf("dlist_length should return 4\n");
		return 0;
	}
	
	if (dlist_get(dlist, 0, &value) != 1) {
		printf("Error in dlist_append\n");
		return 0;
	}
	
	if (value != 0) {
		printf("dlist_get should return 0\n");
		return 0;
	}
	
	dlist_insert(dlist, 1, 100);

	if (dlist_length(dlist) != 5) {
		printf("dlist_length should return 5\n");
		return 0;
	}
	
	if (dlist_get(dlist, 1, &value) != 1) {
		printf("Error in dlist_append\n");
		return 0;
	}
	
	if (value != 100) {
		printf("dlist_get should return 100\n");
		return 0;
	}
	
	dlist_insert(dlist, 10, 500);
	
	if (dlist_length(dlist) != 6) {
		printf("dlist_length should return 6\n");
		return 0;
	}

	if (dlist_get(dlist, 5, &value) != 1) {
		printf("Error in dlist_append\n");
		return 0;
	}
	
	if (value != 500) {
		printf("dlist_get should return 500\n");
		return 0;
	}
	
	puts("dlist_insert ok");
	
	// test print and  print reversed
	
	puts("print current dlist");
	
	dlist_print(dlist);
	
	puts("printing reversed dlist");
	
	dlist_print_reverse(dlist);
	
	puts("check print and print_reversed for yourself!");
		
	puts("##########################################");	
	puts("all tests of double linked lists completed");
	puts("##########################################");
	puts("------------------------------------------");
	
	dlist_delete(dlist);

	return 1;
}
Beispiel #25
0
#include "helpers.h"

TEST(purge_does_nothing_on_empty_list)
{
    USING(dlist_new(sizeof(int))) {
        assertEquals(dlist_purge(list), list);
        assertEquals(dlist_length(list), 0);
        assertEquals(dlist_size(list), sizeof(int));
    }
}

TEST(purge_removes_all_elements_of_list) {
    USING(dlist_new(sizeof(int))) {
        assertNotEquals(dlist_append(list, NULL), NULL);
        assertEquals(dlist_length(list), 1);
        assertEquals(dlist_purge(list), list);
        assertEquals(dlist_length(list), 0);
        assertEquals(dlist_size(list), sizeof(int));
    }

    USING(dlist_new(sizeof(int))) {
        assertNotEquals(dlist_append(list, NULL), NULL);
        assertNotEquals(dlist_append(list, NULL), NULL);
        assertEquals(dlist_length(list), 2);
        assertEquals(dlist_purge(list), list);
        assertEquals(dlist_length(list), 0);
        assertEquals(dlist_size(list), sizeof(int));
    }

    USING(dlist_new(sizeof(int))) {
        assertNotEquals(dlist_append(list, NULL), NULL);
Beispiel #26
0
/* SET variable = value and set (variable1, .., variableN) = (query) */
static sql_exp *
psm_set_exp(mvc *sql, dnode *n)
{
	symbol *val = n->next->data.sym;
	sql_exp *e = NULL;
	int level = 0, is_last = 0;
	sql_subtype *tpe = NULL;
	sql_rel *rel = NULL;
	sql_exp *res = NULL;
	int single = (n->type == type_string);


	if (single) {
		exp_kind ek = {type_value, card_value, FALSE};
		const char *name = n->data.sval;
		/* name can be 
			'parameter of the function' (ie in the param list)
			or a local or global variable, declared earlier
		*/

		/* check if variable is known from the stack */
		if (!stack_find_var(sql, name)) {
			sql_arg *a = sql_bind_param(sql, name);

			if (!a) /* not parameter, ie local var ? */
				return sql_error(sql, 01, SQLSTATE(42000) "Variable %s unknown", name);
			tpe = &a->type;
		} else { 
			tpe = stack_find_type(sql, name);
		}

		e = rel_value_exp2(sql, &rel, val, sql_sel, ek, &is_last);
		if (!e || (rel && e->card > CARD_AGGR))
			return NULL;

		level = stack_find_frame(sql, name);
		e = rel_check_type(sql, tpe, e, type_cast); 
		if (!e)
			return NULL;
		if (rel) {
			sql_exp *er = exp_rel(sql, rel);
			list *b = sa_list(sql->sa);

			append(b, er);
			append(b, exp_set(sql->sa, name, e, level));
			res = exp_rel(sql, rel_psm_block(sql->sa, b));
		} else {
			res = exp_set(sql->sa, name, e, level);
		}
	} else { /* multi assignment */
		exp_kind ek = {type_value, (single)?card_column:card_relation, FALSE};
		sql_rel *rel_val = rel_subquery(sql, NULL, val, ek, APPLY_JOIN);
		dlist *vars = n->data.lval;
		dnode *m;
		node *n;
		list *b;

		if (!rel_val || !is_project(rel_val->op) ||
			    dlist_length(vars) != list_length(rel_val->exps)) {
			return sql_error(sql, 02, SQLSTATE(42000) "SET: Number of variables not equal to number of supplied values");
		}

	       	b = sa_list(sql->sa);
		if (rel_val) {
			sql_exp *er = exp_rel(sql, rel_val);

			append(b, er);
		}

		for(m = vars->h, n = rel_val->exps->h; n && m; n = n->next, m = m->next) {
			char *vname = m->data.sval;
			sql_exp *v = n->data;

			if (!stack_find_var(sql, vname)) {
				sql_arg *a = sql_bind_param(sql, vname);

				if (!a) /* not parameter, ie local var ? */
					return sql_error(sql, 01, SQLSTATE(42000) "Variable %s unknown", vname);
				tpe = &a->type;
			} else { 
				tpe = stack_find_type(sql, vname);
			}

			if (!exp_name(v))
				exp_label(sql->sa, v, ++sql->label);
			v = exp_column(sql->sa, exp_relname(v), exp_name(v), exp_subtype(v), v->card, has_nil(v), is_intern(v));

			level = stack_find_frame(sql, vname);
			v = rel_check_type(sql, tpe, v, type_cast); 
			if (!v)
				return NULL;
			if (v->card > CARD_AGGR) {
				sql_subaggr *zero_or_one = sql_bind_aggr(sql->sa, sql->session->schema, "zero_or_one", exp_subtype(v));
				assert(zero_or_one);
				v = exp_aggr1(sql->sa, v, zero_or_one, 0, 0, CARD_ATOM, 0);
			}
			append(b, exp_set(sql->sa, vname, v, level));
		}
		res = exp_rel(sql, rel_psm_block(sql->sa, b));
	}
	return res;
}
Beispiel #27
0
void process_quote(void *data) {
	Quote *quote;
	struct msg *msg;

	quote = (Quote *)data;
	if (quote->thyquote.m_nLen == sizeof (tHYQuote)) {
		dlist_iter_t iter;
		dlist_node_t node;
		int tlen;

		quote->thyquote.m_cJYS[sizeof quote->thyquote.m_cJYS - 1] = '\0';
		quote->thyquote.m_cHYDM[sizeof quote->thyquote.m_cHYDM - 1] = '\0';
		quote->m_nMSec = 0;
		/* in case of multiple monitors */
		dlist_rwlock_rdlock(monitors);
		if (dlist_length(monitors) > 0) {
			char res[512];

			snprintf(res, sizeof res, "RX '%d,%s,%s,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,"
				"%.2f,%.2f,%d,%.2f,%d,%d,%.2f,%d,%.2f,%d'\r\n",
				quote->thyquote.m_nTime,
				quote->thyquote.m_cHYDM,
				quote->thyquote.m_cJYS,
				quote->thyquote.m_dZXJ,
				quote->thyquote.m_dJKP,
				quote->thyquote.m_dZGJ,
				quote->thyquote.m_dZDJ,
				quote->thyquote.m_dZSP,
				quote->thyquote.m_dJSP,
				quote->thyquote.m_dZJSJ,
				quote->thyquote.m_dJJSJ,
				quote->thyquote.m_nCJSL,
				quote->thyquote.m_dCJJE,
				quote->thyquote.m_nZCCL,
				quote->thyquote.m_nCCL,
				quote->thyquote.m_dMRJG1,
				quote->thyquote.m_nMRSL1,
				quote->thyquote.m_dMCJG1,
				quote->thyquote.m_nMCSL1);
			iter = dlist_iter_new(monitors, DLIST_START_HEAD);
			while ((node = dlist_next(iter))) {
				client c = (client)dlist_node_value(node);

				pthread_spin_lock(&c->lock);
				if (!(c->flags & CLIENT_CLOSE_ASAP)) {
					if (net_try_write(c->fd, res, strlen(res),
						10, NET_NONBLOCK) == -1) {
						xcb_log(XCB_LOG_WARNING, "Writing to client '%p': %s",
							c, strerror(errno));
						if (++c->eagcount >= 3)
							client_free_async(c);
					} else if (c->eagcount)
						c->eagcount = 0;
				}
				pthread_spin_unlock(&c->lock);
			}
			dlist_iter_free(&iter);
		}
		dlist_rwlock_unlock(monitors);
		/* FIXME */
		if (quote->thyquote.m_nTime == 999999999) {
			FREE(data);
			return;
		/* idiosyncrasy of different timestamps */
		} else if ((tlen = intlen(quote->thyquote.m_nTime)) < 10) {
			int hour;
			struct tm lt;

			hour = quote->thyquote.m_nTime / 10000000;
			if (tv.tv_sec == 0 || hour == 9 || hour == 21)
				gettimeofday(&tv, NULL);
			if (prev_hour == 23 && hour == 0)
				tv.tv_sec += 24 * 60 * 60;
			prev_hour = hour;
			localtime_r(&tv.tv_sec, &lt);
			if (quote->thyquote.m_cHYDM[0] == 'S' && quote->thyquote.m_cHYDM[1] == 'P')
				quote->thyquote.m_nTime *= 1000;
			else if (tlen == 6 || tlen == 7)
				quote->thyquote.m_nTime *= 100;
			lt.tm_sec  = quote->thyquote.m_nTime % 100000   / 1000;
			lt.tm_min  = quote->thyquote.m_nTime % 10000000 / 100000;
			lt.tm_hour = hour;
			quote->m_nMSec = quote->thyquote.m_nTime % 1000;
			quote->thyquote.m_nTime = mktime(&lt);
		}
		/* FIXME: no millisecond field in some exchanges' quotes */
		if (addms) {
			struct timeval tv;
			dstr contract = dstr_new(quote->thyquote.m_cHYDM);
			struct sms *sms;

			gettimeofday(&tv, NULL);
			if ((sms = table_get_value(times, contract)) == NULL) {
				if (NEW(sms)) {
					sms->qsec = quote->thyquote.m_nTime;
					sms->sec  = tv.tv_sec;
					sms->msec = tv.tv_usec / 1000;
					table_insert(times, contract, sms);
				}
			} else if (sms->qsec != quote->thyquote.m_nTime) {
				sms->qsec = quote->thyquote.m_nTime;
				sms->sec  = tv.tv_sec;
				sms->msec = tv.tv_usec / 1000;
				dstr_free(contract);
			} else {
				int32_t offset;

				if ((offset = (tv.tv_sec - sms->sec) * 1000 +
					tv.tv_usec / 1000 - sms->msec) > 999)
					offset = 999;
				quote->m_nMSec = offset;
				dstr_free(contract);
			}
		}
		if (get_logger_level() == __LOG_DEBUG) {
			time_t t = (time_t)quote->thyquote.m_nTime;
			char datestr[64];

			strftime(datestr, sizeof datestr, "%F %T", localtime(&t));
			xcb_log(XCB_LOG_DEBUG, "%s.%03d,%s,%s,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,"
				"%d,%.2f,%d,%d,%.2f,%d,%.2f,%d",
				datestr,
				quote->m_nMSec,
				quote->thyquote.m_cHYDM,
				quote->thyquote.m_cJYS,
				quote->thyquote.m_dZXJ,
				quote->thyquote.m_dJKP,
				quote->thyquote.m_dZGJ,
				quote->thyquote.m_dZDJ,
				quote->thyquote.m_dZSP,
				quote->thyquote.m_dJSP,
				quote->thyquote.m_dZJSJ,
				quote->thyquote.m_dJJSJ,
				quote->thyquote.m_nCJSL,
				quote->thyquote.m_dCJJE,
				quote->thyquote.m_nZCCL,
				quote->thyquote.m_nCCL,
				quote->thyquote.m_dMRJG1,
				quote->thyquote.m_nMRSL1,
				quote->thyquote.m_dMCJG1,
				quote->thyquote.m_nMCSL1);
		}
	} else
		xcb_log(XCB_LOG_DEBUG, "Data '%s' received", data);
	if (NEW0(msg) == NULL) {
		FREE(data);
		return;
	}
	msg->data     = data;
	msg->refcount = 1;
	thrpool_queue(tp, send_quote, msg, NULL, msgfree, NULL);
}
Beispiel #28
0
static int send_quote(void *data, void *data2) {
	struct msg *msg = (struct msg *)data;
	Quote *quote;
	int status;
	NOT_USED(data2);

	quote = (Quote *)msg->data;
	if (quote->thyquote.m_nLen == sizeof (THYQuote)) {
		if (get_logger_level() == __LOG_DEBUG) {
			time_t t = (time_t)quote->thyquote.m_nTime;
			char datestr[64];

			strftime(datestr, sizeof datestr, "%F %T", localtime(&t));
			xcb_log(XCB_LOG_DEBUG, "%s.%03d,%s,%s,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,"
				"%d,%.2f,%d,%d,%.2f,%d,%.2f,%d",
				datestr,
				quote->m_nMSec,
				quote->thyquote.m_cHYDM,
				quote->thyquote.m_cJYS,
				quote->thyquote.m_dZXJ,
				quote->thyquote.m_dJKP,
				quote->thyquote.m_dZGJ,
				quote->thyquote.m_dZDJ,
				quote->thyquote.m_dZSP,
				quote->thyquote.m_dJSP,
				quote->thyquote.m_dZJSJ,
				quote->thyquote.m_dJJSJ,
				quote->thyquote.m_nCJSL,
				quote->thyquote.m_dCJJE,
				quote->thyquote.m_nZCCL,
				quote->thyquote.m_nCCL,
				quote->thyquote.m_dMRJG1,
				quote->thyquote.m_nMRSL1,
				quote->thyquote.m_dMCJG1,
				quote->thyquote.m_nMCSL1);
		}
		/* for testing */
		dlist_rwlock_rdlock(monitors);
		if (dlist_length(monitors) > 0) {
			char res[512];
			dlist_iter_t iter = dlist_iter_new(monitors, DLIST_START_HEAD);
			dlist_node_t node;

			snprintf(res, sizeof res, "TX '%d,%s,%s,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,"
				"%d,%.2f,%d,%d,%.2f,%d,%.2f,%d'\r\n",
				quote->thyquote.m_nTime,
				quote->thyquote.m_cHYDM,
				quote->thyquote.m_cJYS,
				quote->thyquote.m_dZXJ,
				quote->thyquote.m_dJKP,
				quote->thyquote.m_dZGJ,
				quote->thyquote.m_dZDJ,
				quote->thyquote.m_dZSP,
				quote->thyquote.m_dJSP,
				quote->thyquote.m_dZJSJ,
				quote->thyquote.m_dJJSJ,
				quote->thyquote.m_nCJSL,
				quote->thyquote.m_dCJJE,
				quote->thyquote.m_nZCCL,
				quote->thyquote.m_nCCL,
				quote->thyquote.m_dMRJG1,
				quote->thyquote.m_nMRSL1,
				quote->thyquote.m_dMCJG1,
				quote->thyquote.m_nMCSL1);
			while ((node = dlist_next(iter))) {
				client c = (client)dlist_node_value(node);

				pthread_spin_lock(&c->lock);
				if (c->flags & CLIENT_CLOSE_ASAP) {
					pthread_spin_unlock(&c->lock);
					continue;
				}
				if (net_try_write(c->fd, res, strlen(res), 10, NET_NONBLOCK) == -1) {
					xcb_log(XCB_LOG_WARNING, "Writing to client '%p': %s",
						c, strerror(errno));
					if (++c->eagcount >= 10)
						client_free_async(c);
				} else if (c->eagcount)
					c->eagcount = 0;
				pthread_spin_unlock(&c->lock);
			}
			dlist_iter_free(&iter);
		}
		dlist_rwlock_unlock(monitors);
	}
	/* FIXME */
	if ((status = pgm_send(pgm_sender, msg->data, sizeof (Quote), NULL)) != PGM_IO_STATUS_NORMAL)
		xcb_log(XCB_LOG_WARNING, "Sending data failed");
	msg_decr(msg);
	return 0;
}
static size_t linear_container_dlist_length(LinearContainer* thiz)
{
	PrivInfo* priv = (PrivInfo*)thiz->priv;

	return dlist_length(priv->dlist);
}
Beispiel #30
0
static void read_quote(event_loop el, int fd, int mask, void *data) {
	char *buf;
	struct sockaddr_in si;
	socklen_t slen = sizeof si;
	int nread;
	NOT_USED(el);
	NOT_USED(mask);
	NOT_USED(data);

	if ((buf = CALLOC(1, sizeof (Quote))) == NULL)
		return;
	/* FIXME */
	if ((nread = recvfrom(fd, buf, sizeof (Quote), 0, (struct sockaddr *)&si, &slen)) > 0) {
		Quote *quote;
		struct msg *msg;

		quote = (Quote *)buf;
		if (quote->thyquote.m_nLen == sizeof (THYQuote)) {
			int tlen;

			quote->thyquote.m_cJYS[sizeof quote->thyquote.m_cJYS - 1] = '\0';
			quote->thyquote.m_cHYDM[sizeof quote->thyquote.m_cHYDM - 1] = '\0';
			quote->m_nMSec = 0;
			/* for testing */
			dlist_rwlock_rdlock(monitors);
			if (dlist_length(monitors) > 0) {
				char res[512];
				dlist_iter_t iter = dlist_iter_new(monitors, DLIST_START_HEAD);
				dlist_node_t node;

				snprintf(res, sizeof res, "RX '%d,%s,%s,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,"
					"%.2f,%.2f,%d,%.2f,%d,%d,%.2f,%d,%.2f,%d'\r\n",
					quote->thyquote.m_nTime,
					quote->thyquote.m_cHYDM,
					quote->thyquote.m_cJYS,
					quote->thyquote.m_dZXJ,
					quote->thyquote.m_dJKP,
					quote->thyquote.m_dZGJ,
					quote->thyquote.m_dZDJ,
					quote->thyquote.m_dZSP,
					quote->thyquote.m_dJSP,
					quote->thyquote.m_dZJSJ,
					quote->thyquote.m_dJJSJ,
					quote->thyquote.m_nCJSL,
					quote->thyquote.m_dCJJE,
					quote->thyquote.m_nZCCL,
					quote->thyquote.m_nCCL,
					quote->thyquote.m_dMRJG1,
					quote->thyquote.m_nMRSL1,
					quote->thyquote.m_dMCJG1,
					quote->thyquote.m_nMCSL1);
				while ((node = dlist_next(iter))) {
					client c = (client)dlist_node_value(node);

					pthread_spin_lock(&c->lock);
					if (c->flags & CLIENT_CLOSE_ASAP) {
						pthread_spin_unlock(&c->lock);
						continue;
					}
					if (net_try_write(c->fd, res, strlen(res), 10, NET_NONBLOCK) == -1) {
						xcb_log(XCB_LOG_WARNING, "Writing to client '%p': %s",
							c, strerror(errno));
						if (++c->eagcount >= 10)
							client_free_async(c);
					} else if (c->eagcount)
						c->eagcount = 0;
					pthread_spin_unlock(&c->lock);
				}
				dlist_iter_free(&iter);
			}
			dlist_rwlock_unlock(monitors);
			/* FIXME */
			if (quote->thyquote.m_nTime == 999999999) {
				FREE(buf);
				return;
			} else if ((tlen = intlen(quote->thyquote.m_nTime)) < 10) {
				struct timeval tv;
				struct tm lt;

				gettimeofday(&tv, NULL);
				localtime_r(&tv.tv_sec, &lt);
				if (quote->thyquote.m_cHYDM[0] == 'S' && quote->thyquote.m_cHYDM[1] == 'P')
					quote->thyquote.m_nTime *= 1000;
				else if (tlen == 6 || tlen == 7)
					quote->thyquote.m_nTime *= 100;
				lt.tm_hour = quote->thyquote.m_nTime / 10000000;
				lt.tm_min  = quote->thyquote.m_nTime % 10000000 / 100000;
				lt.tm_sec  = quote->thyquote.m_nTime % 100000   / 1000;
				quote->m_nMSec = quote->thyquote.m_nTime % 1000;
				quote->thyquote.m_nTime = mktime(&lt);
			}
			/* FIXME */
			if (addms) {
				struct timeval tv;
				dstr contract = dstr_new(quote->thyquote.m_cHYDM);
				struct sms *sms;

				gettimeofday(&tv, NULL);
				if ((sms = table_get_value(times, contract)) == NULL) {
					if (NEW(sms)) {
						sms->qsec = quote->thyquote.m_nTime;
						sms->sec  = tv.tv_sec;
						sms->msec = tv.tv_usec / 1000;
						table_insert(times, contract, sms);
					}
				} else if (sms->qsec != quote->thyquote.m_nTime) {
					sms->qsec = quote->thyquote.m_nTime;
					sms->sec  = tv.tv_sec;
					sms->msec = tv.tv_usec / 1000;
					dstr_free(contract);
				} else {
					int32_t offset;

					if ((offset = (tv.tv_sec - sms->sec) * 1000 +
						tv.tv_usec / 1000 - sms->msec) > 999)
						offset = 999;
					quote->m_nMSec = offset;
					dstr_free(contract);
				}
			}
		}
		if (NEW0(msg) == NULL) {
			FREE(buf);
			return;
		}
		msg->data     = buf;
		msg->refcount = 1;
		thrpool_queue(tp, send_quote, msg, NULL, msgfree, NULL);
	} else
		FREE(buf);
}