sl@0
|
1 |
/* Portion Copyright © 2008-09 Nokia Corporation and/or its subsidiary(-ies). All rights reserved. */
|
sl@0
|
2 |
#undef G_DISABLE_ASSERT
|
sl@0
|
3 |
#undef G_LOG_DOMAIN
|
sl@0
|
4 |
|
sl@0
|
5 |
#include <time.h>
|
sl@0
|
6 |
#include <stdlib.h>
|
sl@0
|
7 |
|
sl@0
|
8 |
#include <glib.h>
|
sl@0
|
9 |
#include <glib/gthread.h>
|
sl@0
|
10 |
|
sl@0
|
11 |
#define DEBUG_MSG(args)
|
sl@0
|
12 |
/* #define DEBUG_MSG(args) g_printerr args ; g_printerr ("\n"); */
|
sl@0
|
13 |
#define PRINT_MSG(args)
|
sl@0
|
14 |
/* #define PRINT_MSG(args) g_print args ; g_print ("\n"); */
|
sl@0
|
15 |
|
sl@0
|
16 |
#define MAX_THREADS 50
|
sl@0
|
17 |
#define MAX_SORTS 5 /* only applies if
|
sl@0
|
18 |
ASYC_QUEUE_DO_SORT is set to 1 */
|
sl@0
|
19 |
#define MAX_TIME 20 /* seconds */
|
sl@0
|
20 |
#define MIN_TIME 5 /* seconds */
|
sl@0
|
21 |
|
sl@0
|
22 |
#define SORT_QUEUE_AFTER 1
|
sl@0
|
23 |
#define SORT_QUEUE_ON_PUSH 1 /* if this is done, the
|
sl@0
|
24 |
SORT_QUEUE_AFTER is ignored */
|
sl@0
|
25 |
#define QUIT_WHEN_DONE 1
|
sl@0
|
26 |
|
sl@0
|
27 |
|
sl@0
|
28 |
#if SORT_QUEUE_ON_PUSH == 1
|
sl@0
|
29 |
# undef SORT_QUEUE_AFTER
|
sl@0
|
30 |
# define SORT_QUEUE_AFTER 0
|
sl@0
|
31 |
#endif
|
sl@0
|
32 |
|
sl@0
|
33 |
#ifdef SYMBIAN
|
sl@0
|
34 |
#include "mrt2_glib2_test.h"
|
sl@0
|
35 |
#endif /*SYMBIAN*/
|
sl@0
|
36 |
|
sl@0
|
37 |
|
sl@0
|
38 |
static GMainLoop *main_loop = NULL;
|
sl@0
|
39 |
static GThreadPool *thread_pool = NULL;
|
sl@0
|
40 |
static GAsyncQueue *async_queue = NULL;
|
sl@0
|
41 |
|
sl@0
|
42 |
|
sl@0
|
43 |
static gint
|
sl@0
|
44 |
sort_compare (gconstpointer p1, gconstpointer p2, gpointer user_data)
|
sl@0
|
45 |
{
|
sl@0
|
46 |
gint32 id1;
|
sl@0
|
47 |
gint32 id2;
|
sl@0
|
48 |
|
sl@0
|
49 |
id1 = GPOINTER_TO_INT (p1);
|
sl@0
|
50 |
id2 = GPOINTER_TO_INT (p2);
|
sl@0
|
51 |
|
sl@0
|
52 |
DEBUG_MSG (("comparing #1:%d and #2:%d, returning %d",
|
sl@0
|
53 |
id1, id2, (id1 > id2 ? +1 : id1 == id2 ? 0 : -1)));
|
sl@0
|
54 |
|
sl@0
|
55 |
return (id1 > id2 ? +1 : id1 == id2 ? 0 : -1);
|
sl@0
|
56 |
}
|
sl@0
|
57 |
|
sl@0
|
58 |
static gboolean
|
sl@0
|
59 |
sort_queue (gpointer user_data)
|
sl@0
|
60 |
{
|
sl@0
|
61 |
static gint sorts = 0;
|
sl@0
|
62 |
static gpointer last_p = NULL;
|
sl@0
|
63 |
gpointer p;
|
sl@0
|
64 |
gboolean can_quit = FALSE;
|
sl@0
|
65 |
gint sort_multiplier;
|
sl@0
|
66 |
gint len;
|
sl@0
|
67 |
gint i;
|
sl@0
|
68 |
|
sl@0
|
69 |
sort_multiplier = GPOINTER_TO_INT (user_data);
|
sl@0
|
70 |
|
sl@0
|
71 |
if (SORT_QUEUE_AFTER) {
|
sl@0
|
72 |
PRINT_MSG (("sorting async queue..."));
|
sl@0
|
73 |
g_async_queue_sort (async_queue, sort_compare, NULL);
|
sl@0
|
74 |
|
sl@0
|
75 |
sorts++;
|
sl@0
|
76 |
|
sl@0
|
77 |
if (sorts >= sort_multiplier) {
|
sl@0
|
78 |
can_quit = TRUE;
|
sl@0
|
79 |
}
|
sl@0
|
80 |
|
sl@0
|
81 |
g_async_queue_sort (async_queue, sort_compare, NULL);
|
sl@0
|
82 |
len = g_async_queue_length (async_queue);
|
sl@0
|
83 |
|
sl@0
|
84 |
PRINT_MSG (("sorted queue (for %d/%d times, size:%d)...", sorts, MAX_SORTS, len));
|
sl@0
|
85 |
} else {
|
sl@0
|
86 |
can_quit = TRUE;
|
sl@0
|
87 |
len = g_async_queue_length (async_queue);
|
sl@0
|
88 |
DEBUG_MSG (("printing queue (size:%d)...", len));
|
sl@0
|
89 |
}
|
sl@0
|
90 |
|
sl@0
|
91 |
for (i = 0, last_p = NULL; i < len; i++) {
|
sl@0
|
92 |
p = g_async_queue_pop (async_queue);
|
sl@0
|
93 |
DEBUG_MSG (("item %d ---> %d", i, GPOINTER_TO_INT (p)));
|
sl@0
|
94 |
|
sl@0
|
95 |
if (last_p) {
|
sl@0
|
96 |
g_assert (GPOINTER_TO_INT (last_p) <= GPOINTER_TO_INT (p));
|
sl@0
|
97 |
}
|
sl@0
|
98 |
|
sl@0
|
99 |
last_p = p;
|
sl@0
|
100 |
}
|
sl@0
|
101 |
|
sl@0
|
102 |
if (can_quit && QUIT_WHEN_DONE) {
|
sl@0
|
103 |
g_main_loop_quit (main_loop);
|
sl@0
|
104 |
}
|
sl@0
|
105 |
|
sl@0
|
106 |
return !can_quit;
|
sl@0
|
107 |
}
|
sl@0
|
108 |
|
sl@0
|
109 |
static void
|
sl@0
|
110 |
enter_thread (gpointer data, gpointer user_data)
|
sl@0
|
111 |
{
|
sl@0
|
112 |
gint len;
|
sl@0
|
113 |
gint id;
|
sl@0
|
114 |
gulong ms;
|
sl@0
|
115 |
|
sl@0
|
116 |
id = GPOINTER_TO_INT (data);
|
sl@0
|
117 |
|
sl@0
|
118 |
ms = g_random_int_range (MIN_TIME * 1000, MAX_TIME * 1000);
|
sl@0
|
119 |
DEBUG_MSG (("entered thread with id:%d, adding to queue in:%ld ms", id, ms));
|
sl@0
|
120 |
|
sl@0
|
121 |
g_usleep (ms * 1000);
|
sl@0
|
122 |
|
sl@0
|
123 |
if (SORT_QUEUE_ON_PUSH) {
|
sl@0
|
124 |
g_async_queue_push_sorted (async_queue, GINT_TO_POINTER (id), sort_compare, NULL);
|
sl@0
|
125 |
} else {
|
sl@0
|
126 |
g_async_queue_push (async_queue, GINT_TO_POINTER (id));
|
sl@0
|
127 |
}
|
sl@0
|
128 |
|
sl@0
|
129 |
len = g_async_queue_length (async_queue);
|
sl@0
|
130 |
|
sl@0
|
131 |
DEBUG_MSG (("thread id:%d added to async queue (size:%d)",
|
sl@0
|
132 |
id, len));
|
sl@0
|
133 |
}
|
sl@0
|
134 |
|
sl@0
|
135 |
int
|
sl@0
|
136 |
main (int argc, char *argv[])
|
sl@0
|
137 |
{
|
sl@0
|
138 |
|
sl@0
|
139 |
gint i;
|
sl@0
|
140 |
gint max_threads = MAX_THREADS;
|
sl@0
|
141 |
gint max_unused_threads = MAX_THREADS;
|
sl@0
|
142 |
gint sort_multiplier = MAX_SORTS;
|
sl@0
|
143 |
gint sort_interval;
|
sl@0
|
144 |
gchar *msg;
|
sl@0
|
145 |
|
sl@0
|
146 |
#ifdef SYMBIAN
|
sl@0
|
147 |
g_log_set_handler (NULL, G_LOG_FLAG_FATAL| G_LOG_FLAG_RECURSION | G_LOG_LEVEL_CRITICAL | G_LOG_LEVEL_WARNING | G_LOG_LEVEL_MESSAGE | G_LOG_LEVEL_INFO | G_LOG_LEVEL_DEBUG, &mrtLogHandler, NULL);
|
sl@0
|
148 |
#endif /*SYMBIAN*/
|
sl@0
|
149 |
g_thread_init (NULL);
|
sl@0
|
150 |
|
sl@0
|
151 |
PRINT_MSG (("creating async queue..."));
|
sl@0
|
152 |
async_queue = g_async_queue_new ();
|
sl@0
|
153 |
g_assert(async_queue != NULL);
|
sl@0
|
154 |
|
sl@0
|
155 |
g_return_val_if_fail (async_queue != NULL, EXIT_FAILURE);
|
sl@0
|
156 |
|
sl@0
|
157 |
PRINT_MSG (("creating thread pool with max threads:%d, max unused threads:%d...",
|
sl@0
|
158 |
max_threads, max_unused_threads));
|
sl@0
|
159 |
thread_pool = g_thread_pool_new (enter_thread,
|
sl@0
|
160 |
async_queue,
|
sl@0
|
161 |
max_threads,
|
sl@0
|
162 |
FALSE,
|
sl@0
|
163 |
NULL);
|
sl@0
|
164 |
|
sl@0
|
165 |
g_return_val_if_fail (thread_pool != NULL, EXIT_FAILURE);
|
sl@0
|
166 |
|
sl@0
|
167 |
g_thread_pool_set_max_unused_threads (max_unused_threads);
|
sl@0
|
168 |
|
sl@0
|
169 |
PRINT_MSG (("creating threads..."));
|
sl@0
|
170 |
for (i = 1; i <= max_threads; i++) {
|
sl@0
|
171 |
GError *error = NULL;
|
sl@0
|
172 |
|
sl@0
|
173 |
g_thread_pool_push (thread_pool, GINT_TO_POINTER (i), &error);
|
sl@0
|
174 |
|
sl@0
|
175 |
g_assert (error == NULL);
|
sl@0
|
176 |
}
|
sl@0
|
177 |
|
sl@0
|
178 |
if (!SORT_QUEUE_AFTER) {
|
sl@0
|
179 |
sort_multiplier = 1;
|
sl@0
|
180 |
}
|
sl@0
|
181 |
|
sl@0
|
182 |
sort_interval = ((MAX_TIME / sort_multiplier) + 2) * 1000;
|
sl@0
|
183 |
g_timeout_add (sort_interval, sort_queue, GINT_TO_POINTER (sort_multiplier));
|
sl@0
|
184 |
|
sl@0
|
185 |
if (SORT_QUEUE_ON_PUSH) {
|
sl@0
|
186 |
msg = "sorting when pushing into the queue, checking queue is sorted";
|
sl@0
|
187 |
} else {
|
sl@0
|
188 |
msg = "sorting";
|
sl@0
|
189 |
}
|
sl@0
|
190 |
|
sl@0
|
191 |
PRINT_MSG (("%s %d %s %d ms",
|
sl@0
|
192 |
msg,
|
sl@0
|
193 |
sort_multiplier,
|
sl@0
|
194 |
sort_multiplier == 1 ? "time in" : "times, once every",
|
sl@0
|
195 |
sort_interval));
|
sl@0
|
196 |
|
sl@0
|
197 |
DEBUG_MSG (("entering main event loop"));
|
sl@0
|
198 |
|
sl@0
|
199 |
main_loop = g_main_loop_new (NULL, FALSE);
|
sl@0
|
200 |
g_main_loop_run (main_loop);
|
sl@0
|
201 |
|
sl@0
|
202 |
|
sl@0
|
203 |
#if SYMBIAN
|
sl@0
|
204 |
testResultXml("asyncqueue-test");
|
sl@0
|
205 |
#endif /* EMULATOR */
|
sl@0
|
206 |
|
sl@0
|
207 |
return EXIT_SUCCESS;
|
sl@0
|
208 |
}
|