862f4dc9e2060cf6112ba6adbba916fd9ef719fb
[platform/upstream/gstreamer.git] / testsuite / refcounting / thread.c
1 #include <gst/gst.h>
2
3 #define ITERS 100000
4 #include <stdlib.h>
5 #include "mem.h"
6
7 GstStaticPadTemplate srctemplate = GST_STATIC_PAD_TEMPLATE ("src",
8     GST_PAD_SRC,
9     GST_PAD_ALWAYS,
10     GST_STATIC_CAPS_ANY);
11
12 GstStaticPadTemplate sinktemplate = GST_STATIC_PAD_TEMPLATE ("sink",
13     GST_PAD_SINK,
14     GST_PAD_ALWAYS,
15     GST_STATIC_CAPS_ANY);
16
17 static GstElement *
18 create_thread (void)
19 {
20   GstElement *thread;
21   GstElement *element;
22
23   thread = gst_thread_new ("testthread");
24   element = gst_element_new ();
25   gst_element_set_name (element, "test1");
26   gst_bin_add (GST_BIN (thread), element);
27   element = gst_element_new ();
28   gst_element_set_name (element, "test2");
29   gst_bin_add (GST_BIN (thread), element);
30
31   return thread;
32 }
33
34 static GstElement *
35 create_thread_ghostpads (void)
36 {
37   GstElement *thread;
38   GstElement *element1, *element2;
39
40   thread = gst_thread_new ("testthread");
41   element1 = gst_element_new ();
42   gst_element_set_name (element1, "test1");
43   gst_element_add_pad (element1,
44       gst_pad_new_from_template (gst_static_pad_template_get (&srctemplate),
45           "src1"));
46   gst_bin_add (GST_BIN (thread), element1);
47   element2 = gst_element_new ();
48   gst_element_set_name (element2, "test2");
49   gst_element_add_pad (element1,
50       gst_pad_new_from_template (gst_static_pad_template_get (&sinktemplate),
51           "sink1"));
52   gst_bin_add (GST_BIN (thread), element2);
53   gst_element_link (element1, "src1", element2, "sink1");
54   gst_element_add_ghost_pad (thread, gst_element_get_pad (element2, "sink1"),
55       "sink1");
56
57   return thread;
58 }
59
60 static void
61 add_remove_test1 (void)
62 {
63   GstElement *thread;
64   GstElement *element;
65
66   thread = gst_thread_new ("testthread");
67   element = gst_element_new ();
68   gst_element_set_name (element, "test1");
69   g_assert (GST_OBJECT_FLOATING (element));
70   gst_bin_add (GST_BIN (thread), element);
71   g_assert (!GST_OBJECT_FLOATING (element));
72   gst_bin_remove (GST_BIN (thread), element);
73
74   gst_object_unref (GST_OBJECT (thread));
75 }
76
77 static void
78 add_remove_test2 (void)
79 {
80   GstElement *thread;
81   GstElement *element;
82
83   thread = gst_thread_new ("testthread");
84   element = gst_element_new ();
85   gst_element_set_name (element, "test1");
86   gst_object_ref (GST_OBJECT (element));
87   g_assert (GST_OBJECT_FLOATING (element));
88   gst_bin_add (GST_BIN (thread), element);
89   g_assert (!GST_OBJECT_FLOATING (element));
90   gst_bin_remove (GST_BIN (thread), element);
91   g_assert (!GST_OBJECT_FLOATING (element));
92   g_assert (!GST_OBJECT_DESTROYED (element));
93
94   gst_object_unref (GST_OBJECT (element));
95   g_assert (GST_OBJECT_DESTROYED (element));
96   gst_object_unref (GST_OBJECT (element));
97
98   gst_object_unref (GST_OBJECT (thread));
99 }
100
101 static void
102 add_remove_test3 (void)
103 {
104   GstElement *thread;
105   GstElement *element;
106
107   thread = gst_thread_new ("testthread");
108   element = gst_element_new ();
109   gst_element_set_name (element, "test1");
110   g_assert (GST_OBJECT_FLOATING (element));
111   gst_bin_add (GST_BIN (thread), element);
112   g_assert (!GST_OBJECT_FLOATING (element));
113
114   gst_object_unref (GST_OBJECT (element));
115   g_assert (gst_bin_get_by_name (GST_BIN (thread), "test1") == NULL);
116
117   gst_object_unref (GST_OBJECT (thread));
118 }
119
120 static void
121 add_remove_test4 (void)
122 {
123   GstElement *thread, *thread2;
124   GstElement *element;
125
126   thread = gst_thread_new ("testthread");
127   element = gst_element_new ();
128   gst_element_set_name (element, "test1");
129   g_assert (GST_OBJECT_FLOATING (element));
130   gst_bin_add (GST_BIN (thread), element);
131   g_assert (!GST_OBJECT_FLOATING (element));
132
133   thread2 = create_thread ();
134   g_assert (GST_OBJECT_FLOATING (thread2));
135   gst_bin_add (GST_BIN (thread), thread2);
136   g_assert (!GST_OBJECT_FLOATING (thread2));
137
138   gst_object_unref (GST_OBJECT (thread2));
139   g_assert (gst_bin_get_by_name (GST_BIN (thread), "testthread") == NULL);
140   gst_object_unref (GST_OBJECT (element));
141   g_assert (gst_bin_get_by_name (GST_BIN (thread), "test1") == NULL);
142
143   gst_object_unref (GST_OBJECT (thread));
144 }
145
146 int
147 main (int argc, gchar * argv[])
148 {
149   GstElement *thread, *element;
150   long usage1;
151   gint i, iters;
152
153   gst_init (&argc, &argv);
154
155   if (argc == 2)
156     iters = atoi (argv[1]);
157   else
158     iters = ITERS;
159
160   g_print ("starting test\n");
161   usage1 = vmsize ();
162
163   thread = gst_thread_new ("somethread");
164   gst_object_unref (GST_OBJECT (thread));
165   g_print ("create/unref new thread %ld\n", vmsize () - usage1);
166
167   for (i = 0; i < iters; i++) {
168     thread = gst_thread_new ("somethread");
169     gst_object_unref (GST_OBJECT (thread));
170   }
171   g_print ("create/unref %d threads %ld\n", iters, vmsize () - usage1);
172
173   thread = gst_thread_new ("somethread");
174   g_assert (GST_OBJECT_FLOATING (thread));
175   gst_object_ref (GST_OBJECT (thread));
176   gst_object_sink (GST_OBJECT (thread));
177   g_assert (!GST_OBJECT_FLOATING (thread));
178   gst_object_unref (GST_OBJECT (thread));
179   g_print ("create/ref/sink/unref new thread %ld\n", vmsize () - usage1);
180
181
182   for (i = 0; i < iters; i++) {
183     thread = gst_thread_new ("somethread");
184     gst_object_ref (GST_OBJECT (thread));
185     gst_object_sink (GST_OBJECT (thread));
186     gst_object_unref (GST_OBJECT (thread));
187   }
188   g_print ("create/ref/sink/unref %d threads %ld\n", iters, vmsize () - usage1);
189
190   thread = gst_thread_new ("somethread");
191   g_assert (!GST_OBJECT_DESTROYED (thread));
192   gst_object_unref (GST_OBJECT (thread));
193   g_assert (GST_OBJECT_DESTROYED (thread));
194   gst_object_unref (GST_OBJECT (thread));
195   g_print ("create/destroy/unref new thread %ld\n", vmsize () - usage1);
196
197   for (i = 0; i < iters; i++) {
198     thread = gst_thread_new ("somethread");
199     gst_object_unref (GST_OBJECT (thread));
200     gst_object_unref (GST_OBJECT (thread));
201   }
202   g_print ("create/destroy/unref %d thread %ld\n", iters, vmsize () - usage1);
203
204   thread = gst_thread_new ("somethread");
205   gst_object_ref (GST_OBJECT (thread));
206   gst_object_unref (GST_OBJECT (thread));
207   gst_object_unref (GST_OBJECT (thread));
208   g_print ("create/ref/unref/unref new thread %ld\n", vmsize () - usage1);
209
210   for (i = 0; i < iters; i++) {
211     thread = gst_thread_new ("somethread");
212     gst_object_ref (GST_OBJECT (thread));
213     gst_object_unref (GST_OBJECT (thread));
214     gst_object_unref (GST_OBJECT (thread));
215   }
216   g_print ("create/ref/unref/unref %d thread %ld\n", iters, vmsize () - usage1);
217
218   thread = gst_thread_new ("somethread");
219   gst_object_ref (GST_OBJECT (thread));
220   gst_object_unref (GST_OBJECT (thread));
221   gst_object_unref (GST_OBJECT (thread));
222   gst_object_unref (GST_OBJECT (thread));
223   g_print ("craete/ref/destroy/unref/unref new thread %ld\n",
224       vmsize () - usage1);
225
226   for (i = 0; i < iters; i++) {
227     thread = gst_thread_new ("somethread");
228     gst_object_ref (GST_OBJECT (thread));
229     gst_object_unref (GST_OBJECT (thread));
230     gst_object_unref (GST_OBJECT (thread));
231     gst_object_unref (GST_OBJECT (thread));
232   }
233   g_print ("craete/ref/destroy/unref/unref %d threads %ld\n", iters,
234       vmsize () - usage1);
235
236   for (i = 0; i < iters; i++) {
237     thread = gst_thread_new ("somethread");
238     gst_object_ref (GST_OBJECT (thread));
239     gst_element_set_name (thread, "testing123");
240     gst_object_unref (GST_OBJECT (thread));
241     gst_element_set_name (thread, "testing123");
242     gst_object_unref (GST_OBJECT (thread));
243     gst_object_unref (GST_OBJECT (thread));
244   }
245   g_print ("craete/ref/destroy/unref/unref %d threads with name %ld\n", iters,
246       vmsize () - usage1);
247
248   thread = gst_thread_new ("somethread");
249   for (i = 0; i < iters; i++) {
250     gst_element_set_name (thread, "testing");
251   }
252   gst_object_unref (GST_OBJECT (thread));
253   g_print ("set name %d times %ld\n", iters, vmsize () - usage1);
254
255   for (i = 0; i < iters; i++) {
256     thread = gst_thread_new ("somethread");
257     element = gst_element_new ();
258     gst_element_set_name (element, "test1");
259     gst_bin_add (GST_BIN (thread), element);
260     gst_object_unref (GST_OBJECT (thread));
261   }
262   g_print ("create/unref %d thread with one element %ld\n", iters,
263       vmsize () - usage1);
264
265   for (i = 0; i < iters; i++) {
266     thread = create_thread ();
267     gst_object_unref (GST_OBJECT (thread));
268   }
269   g_print ("create/unref %d thread with children %ld\n", iters,
270       vmsize () - usage1);
271
272   for (i = 0; i < iters / 2; i++) {
273     thread = create_thread_ghostpads ();
274     gst_object_unref (GST_OBJECT (thread));
275   }
276   g_print ("create/unref %d thread with children and ghostpads %ld\n",
277       iters / 2, vmsize () - usage1);
278
279   for (i = 0; i < iters; i++) {
280     add_remove_test1 ();
281   }
282   g_print ("add/remove test1 %d in thread %ld\n", iters, vmsize () - usage1);
283
284   for (i = 0; i < iters; i++) {
285     add_remove_test2 ();
286   }
287   g_print ("add/remove test2 %d in thread %ld\n", iters, vmsize () - usage1);
288
289   for (i = 0; i < iters; i++) {
290     add_remove_test3 ();
291   }
292   g_print ("add/destroy/remove test3 %d in thread %ld\n", iters,
293       vmsize () - usage1);
294
295   for (i = 0; i < iters; i++) {
296     add_remove_test4 ();
297   }
298   g_print ("add/destroy/remove test4 %d in thread %ld\n", iters,
299       vmsize () - usage1);
300
301   g_print ("leaked: %ld\n", vmsize () - usage1);
302
303   return (vmsize () - usage1 ? -1 : 0);
304 }