aboutsummaryrefslogtreecommitdiffstats
path: root/tests/it_q/it_q_test.c
blob: 6025e3926074ae0393ae5b6a5dd27a335e3a554d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
#include <stdio.h>
#include <errno.h>

#include <osmocom/core/talloc.h>
#include <osmocom/core/utils.h>
#include <osmocom/core/it_q.h>

struct it_q_test1 {
	struct llist_head list;
	int *foo;
};

struct it_q_test2 {
	int foo;
	struct llist_head list;
};

#define ENTER_TC	printf("\n== Entering test case %s\n", __func__)

static void tc_alloc(void)
{
	struct osmo_it_q *q1, *q2;

	ENTER_TC;

	printf("allocating q1\n");
	q1 = osmo_it_q_alloc(OTC_GLOBAL, "q1", 3, NULL, NULL);
	OSMO_ASSERT(q1);

	/* ensure that no duplicate allocation for the */
	printf("attempting duplicate allocation of qa\n");
	q2 = osmo_it_q_alloc(OTC_GLOBAL, "q1", 3, NULL, NULL);
	OSMO_ASSERT(!q2);

	/* ensure that same name can be re-created after destroying old one */
	osmo_it_q_destroy(q1);
	printf("re-allocating q1\n");
	q1 = osmo_it_q_alloc(OTC_GLOBAL, "q1", 3, NULL, NULL);
	OSMO_ASSERT(q1);

	osmo_it_q_destroy(q1);
}

static void tc_queue_length(void)
{
	struct osmo_it_q *q1;
	unsigned int qlen = 3;
	struct it_q_test1 *item;
	int i, rc;

	ENTER_TC;

	printf("allocating q1\n");
	q1 = osmo_it_q_alloc(OTC_GLOBAL, "q1", qlen, NULL, NULL);
	OSMO_ASSERT(q1);

	printf("adding queue entries up to the limit\n");
	for (i = 0; i < qlen; i++) {
		item = talloc_zero(OTC_GLOBAL, struct it_q_test1);
		rc = osmo_it_q_enqueue(q1, item, list);
		OSMO_ASSERT(rc == 0);
	}
	printf("attempting to add more than the limit\n");
	item = talloc_zero(OTC_GLOBAL, struct it_q_test1);
	rc = osmo_it_q_enqueue(q1, item, list);
	OSMO_ASSERT(rc == -ENOSPC);

	osmo_it_q_destroy(q1);
}

static void tc_enqueue_dequeue(void)
{
	const unsigned int qlen = 12;
	struct it_q_test1 *item;
	struct osmo_it_q *q1;
	int rc;

	ENTER_TC;

	printf("allocating q1\n");
	q1 = osmo_it_q_alloc(OTC_GLOBAL, "q1", 12, NULL, NULL);
	OSMO_ASSERT(q1);

	printf("try dequeueing from an empty queue\n");
	osmo_it_q_dequeue(q1, &item, list);
	OSMO_ASSERT(item == NULL);

	printf("adding queue entries up to the limit\n");
	for (unsigned int i = 0; i < qlen; i++) {
		item = talloc_zero(OTC_GLOBAL, struct it_q_test1);
		rc = osmo_it_q_enqueue(q1, item, list);
		OSMO_ASSERT(rc == 0);
	}

	printf("removing queue entries up to the limit\n");
	for (unsigned int i = 0; i < qlen; i++) {
		osmo_it_q_dequeue(q1, &item, list);
		OSMO_ASSERT(item != NULL);
		talloc_free(item);
	}

	printf("try dequeueing from an empty queue\n");
	osmo_it_q_dequeue(q1, &item, list);
	OSMO_ASSERT(item == NULL);

	osmo_it_q_destroy(q1);
}

static int g_read_cb_count;

static void q_read_cb(struct osmo_it_q *q, struct llist_head *item)
{
	struct it_q_test1 *it = container_of(item, struct it_q_test1, list);
	*it->foo += 1;
	talloc_free(item);
}

static void tc_eventfd(void)
{
	struct osmo_it_q *q1;
	unsigned int qlen = 30;
	struct it_q_test1 *item;
	int i, rc;

	ENTER_TC;

	printf("allocating q1\n");
	q1 = osmo_it_q_alloc(OTC_GLOBAL, "q1", qlen, q_read_cb, NULL);
	OSMO_ASSERT(q1);
	osmo_fd_register(&q1->event_ofd);

	/* ensure read-cb isn't called unless we enqueue something */
	osmo_select_main(1);
	OSMO_ASSERT(g_read_cb_count == 0);

	/* ensure read-cb is called for each enqueued msg once */
	printf("adding %u queue entries up to the limit\n", qlen);
	for (i = 0; i < qlen; i++) {
		item = talloc_zero(OTC_GLOBAL, struct it_q_test1);
		item->foo = &g_read_cb_count;
		rc = osmo_it_q_enqueue(q1, item, list);
		OSMO_ASSERT(rc == 0);
	}

	osmo_select_main(1);
	printf("%u entries were dequeued\n", qlen);
	OSMO_ASSERT(g_read_cb_count == qlen);

	osmo_it_q_destroy(q1);
}

int main(int argc, char **argv)
{
	tc_alloc();
	tc_queue_length();
	tc_enqueue_dequeue();
	tc_eventfd();
	return 0;
}