• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* GLib testing framework examples and tests
2  *
3  * Copyright (C) 2008-2010 Red Hat, Inc.
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2.1 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General
16  * Public License along with this library; if not, see <http://www.gnu.org/licenses/>.
17  *
18  * Author: David Zeuthen <davidz@redhat.com>
19  */
20 
21 #include <locale.h>
22 #include <gio/gio.h>
23 
24 /* ---------------------------------------------------------------------------------------------------- */
25 
26 static void
on_notify_locked(GObject * object,GParamSpec * pspec,gpointer user_data)27 on_notify_locked (GObject    *object,
28                   GParamSpec *pspec,
29                   gpointer    user_data)
30 {
31   gint *count = user_data;
32   *count += 1;
33 }
34 
35 static void
message_lock(void)36 message_lock (void)
37 {
38   GDBusMessage *m;
39   gint count;
40 
41   count = 0;
42   m = g_dbus_message_new ();
43   g_signal_connect (m,
44                     "notify::locked",
45                     G_CALLBACK (on_notify_locked),
46                     &count);
47   g_assert (!g_dbus_message_get_locked (m));
48   g_dbus_message_lock (m);
49   g_assert (g_dbus_message_get_locked (m));
50   g_assert_cmpint (count, ==, 1);
51   g_dbus_message_lock (m);
52   g_assert (g_dbus_message_get_locked (m));
53   g_assert_cmpint (count, ==, 1);
54 
55   g_test_expect_message (G_LOG_DOMAIN, G_LOG_LEVEL_WARNING,
56                          "*Attempted to modify a locked message*");
57   g_dbus_message_set_serial (m, 42);
58   g_test_assert_expected_messages ();
59 
60   g_test_expect_message (G_LOG_DOMAIN, G_LOG_LEVEL_WARNING,
61                          "*Attempted to modify a locked message*");
62   g_dbus_message_set_byte_order (m, G_DBUS_MESSAGE_BYTE_ORDER_BIG_ENDIAN);
63   g_test_assert_expected_messages ();
64 
65   g_test_expect_message (G_LOG_DOMAIN, G_LOG_LEVEL_WARNING,
66                          "*Attempted to modify a locked message*");
67   g_dbus_message_set_message_type (m, G_DBUS_MESSAGE_TYPE_METHOD_CALL);
68   g_test_assert_expected_messages ();
69 
70   g_test_expect_message (G_LOG_DOMAIN, G_LOG_LEVEL_WARNING,
71                          "*Attempted to modify a locked message*");
72   g_dbus_message_set_flags (m, G_DBUS_MESSAGE_FLAGS_NONE);
73   g_test_assert_expected_messages ();
74 
75   g_test_expect_message (G_LOG_DOMAIN, G_LOG_LEVEL_WARNING,
76                          "*Attempted to modify a locked message*");
77   g_dbus_message_set_body (m, NULL);
78   g_test_assert_expected_messages ();
79 
80   g_test_expect_message (G_LOG_DOMAIN, G_LOG_LEVEL_WARNING,
81                          "*Attempted to modify a locked message*");
82   g_dbus_message_set_header (m, 0, NULL);
83   g_test_assert_expected_messages ();
84 
85   g_object_unref (m);
86 }
87 
88 /* ---------------------------------------------------------------------------------------------------- */
89 
90 static void
message_copy(void)91 message_copy (void)
92 {
93   GDBusMessage *m;
94   GDBusMessage *copy;
95   GError *error;
96   guchar *m_headers;
97   guchar *copy_headers;
98   guint n;
99 
100   m = g_dbus_message_new_method_call ("org.example.Name",
101                                       "/org/example/Object",
102                                       "org.example.Interface",
103                                       "Method");
104   g_dbus_message_set_serial (m, 42);
105   g_dbus_message_set_byte_order (m, G_DBUS_MESSAGE_BYTE_ORDER_BIG_ENDIAN);
106 
107   error = NULL;
108   copy = g_dbus_message_copy (m, &error);
109   g_assert_no_error (error);
110   g_assert (G_IS_DBUS_MESSAGE (copy));
111   g_assert (m != copy);
112   g_assert_cmpint (G_OBJECT (m)->ref_count, ==, 1);
113   g_assert_cmpint (G_OBJECT (copy)->ref_count, ==, 1);
114 
115   g_assert_cmpint (g_dbus_message_get_serial (copy), ==, g_dbus_message_get_serial (m));
116   g_assert_cmpint (g_dbus_message_get_byte_order (copy), ==, g_dbus_message_get_byte_order (m));
117   g_assert_cmpint (g_dbus_message_get_flags (copy), ==, g_dbus_message_get_flags (m));
118   g_assert_cmpint (g_dbus_message_get_message_type (copy), ==, g_dbus_message_get_message_type (m));
119   m_headers = g_dbus_message_get_header_fields (m);
120   copy_headers = g_dbus_message_get_header_fields (copy);
121   g_assert (m_headers != NULL);
122   g_assert (copy_headers != NULL);
123   for (n = 0; m_headers[n] != 0; n++)
124     {
125       GVariant *m_val;
126       GVariant *copy_val;
127       m_val = g_dbus_message_get_header (m, m_headers[n]);
128       copy_val = g_dbus_message_get_header (m, m_headers[n]);
129       g_assert (m_val != NULL);
130       g_assert (copy_val != NULL);
131       g_assert_cmpvariant (m_val, copy_val);
132     }
133   g_assert_cmpint (n, >, 0); /* make sure we actually compared headers etc. */
134   g_assert_cmpint (copy_headers[n], ==, 0);
135   g_free (m_headers);
136   g_free (copy_headers);
137 
138   g_object_unref (copy);
139   g_object_unref (m);
140 }
141 
142 /* ---------------------------------------------------------------------------------------------------- */
143 
144 /* Test g_dbus_message_bytes_needed() returns correct results for a variety of
145  * arbitrary binary inputs.*/
146 static void
message_bytes_needed(void)147 message_bytes_needed (void)
148 {
149   const struct
150     {
151       const guint8 blob[16];
152       gssize expected_bytes_needed;
153     }
154   vectors[] =
155     {
156       /* Little endian with header rounding */
157       { { 'l', 0, 0, 1,  /* endianness, message type, flags, protocol version */
158           50, 0, 0, 0,  /* body length */
159           1, 0, 0, 0,  /* message serial */
160           7, 0, 0, 0  /* header length */}, 74 },
161       /* Little endian without header rounding */
162       { { 'l', 0, 0, 1,  /* endianness, message type, flags, protocol version */
163           50, 0, 0, 0,  /* body length */
164           1, 0, 0, 0,  /* message serial */
165           8, 0, 0, 0  /* header length */}, 74 },
166       /* Big endian with header rounding */
167       { { 'B', 0, 0, 1,  /* endianness, message type, flags, protocol version */
168           0, 0, 0, 50,  /* body length */
169           0, 0, 0, 1,  /* message serial */
170           0, 0, 0, 7  /* header length */}, 74 },
171       /* Big endian without header rounding */
172       { { 'B', 0, 0, 1,  /* endianness, message type, flags, protocol version */
173           0, 0, 0, 50,  /* body length */
174           0, 0, 0, 1,  /* message serial */
175           0, 0, 0, 8  /* header length */}, 74 },
176       /* Invalid endianness */
177       { { '!', 0, 0, 1,  /* endianness, message type, flags, protocol version */
178           0, 0, 0, 50,  /* body length */
179           0, 0, 0, 1,  /* message serial */
180           0, 0, 0, 8  /* header length */}, -1 },
181       /* Oversized */
182       { { 'l', 0, 0, 1,  /* endianness, message type, flags, protocol version */
183           0, 0, 0, 0x08,  /* body length (128MiB) */
184           1, 0, 0, 0,  /* message serial */
185           7, 0, 0, 0  /* header length */}, -1 },
186     };
187   gsize i;
188 
189   for (i = 0; i < G_N_ELEMENTS (vectors); i++)
190     {
191       gssize bytes_needed;
192       GError *local_error = NULL;
193 
194       g_test_message ("Vector: %" G_GSIZE_FORMAT, i);
195 
196       bytes_needed = g_dbus_message_bytes_needed ((guchar *) vectors[i].blob,
197                                                   G_N_ELEMENTS (vectors[i].blob),
198                                                   &local_error);
199 
200       if (vectors[i].expected_bytes_needed < 0)
201         g_assert_error (local_error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
202       else
203         g_assert_no_error (local_error);
204       g_assert_cmpint (bytes_needed, ==, vectors[i].expected_bytes_needed);
205 
206       g_clear_error (&local_error);
207     }
208 }
209 
210 /* ---------------------------------------------------------------------------------------------------- */
211 
212 int
main(int argc,char * argv[])213 main (int   argc,
214       char *argv[])
215 {
216   setlocale (LC_ALL, "C");
217 
218   g_test_init (&argc, &argv, NULL);
219 
220   g_test_add_func ("/gdbus/message/lock", message_lock);
221   g_test_add_func ("/gdbus/message/copy", message_copy);
222   g_test_add_func ("/gdbus/message/bytes-needed", message_bytes_needed);
223 
224   return g_test_run ();
225 }
226