1 /* GIO - GLib Input, Output and Streaming Library
2 *
3 * Copyright (C) 2006-2007 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 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, write to the
17 * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
18 * Boston, MA 02111-1307, USA.
19 *
20 * Author: Alexander Larsson <alexl@redhat.com>
21 */
22
23 #include "config.h"
24 #include <string.h>
25 #include "gdataoutputstream.h"
26 #include "gioenumtypes.h"
27 #include "glibintl.h"
28
29 #include "gioalias.h"
30
31 /**
32 * SECTION:gdataoutputstream
33 * @short_description: Data Output Stream
34 * @include: gio/gio.h
35 * @see_also: #GOutputStream
36 *
37 * Data output stream implements #GOutputStream and includes functions for
38 * writing data directly to an output stream.
39 *
40 **/
41
42
43
44 struct _GDataOutputStreamPrivate {
45 GDataStreamByteOrder byte_order;
46 };
47
48 enum {
49 PROP_0,
50 PROP_BYTE_ORDER
51 };
52
53 static void g_data_output_stream_set_property (GObject *object,
54 guint prop_id,
55 const GValue *value,
56 GParamSpec *pspec);
57 static void g_data_output_stream_get_property (GObject *object,
58 guint prop_id,
59 GValue *value,
60 GParamSpec *pspec);
61
G_DEFINE_TYPE(GDataOutputStream,g_data_output_stream,G_TYPE_FILTER_OUTPUT_STREAM)62 G_DEFINE_TYPE (GDataOutputStream,
63 g_data_output_stream,
64 G_TYPE_FILTER_OUTPUT_STREAM)
65
66
67 static void
68 g_data_output_stream_class_init (GDataOutputStreamClass *klass)
69 {
70 GObjectClass *object_class;
71
72 g_type_class_add_private (klass, sizeof (GDataOutputStreamPrivate));
73
74 object_class = G_OBJECT_CLASS (klass);
75 object_class->get_property = g_data_output_stream_get_property;
76 object_class->set_property = g_data_output_stream_set_property;
77
78 /**
79 * GDataOutputStream:byte-order:
80 *
81 * Determines the byte ordering that is used when writing
82 * multi-byte entities (such as integers) to the stream.
83 */
84 g_object_class_install_property (object_class,
85 PROP_BYTE_ORDER,
86 g_param_spec_enum ("byte-order",
87 P_("Byte order"),
88 P_("The byte order"),
89 G_TYPE_DATA_STREAM_BYTE_ORDER,
90 G_DATA_STREAM_BYTE_ORDER_BIG_ENDIAN,
91 G_PARAM_READWRITE|G_PARAM_STATIC_NAME|G_PARAM_STATIC_BLURB));
92
93 }
94
95 static void
g_data_output_stream_set_property(GObject * object,guint prop_id,const GValue * value,GParamSpec * pspec)96 g_data_output_stream_set_property (GObject *object,
97 guint prop_id,
98 const GValue *value,
99 GParamSpec *pspec)
100 {
101 GDataOutputStream *dstream;
102
103 dstream = G_DATA_OUTPUT_STREAM (object);
104
105 switch (prop_id)
106 {
107 case PROP_BYTE_ORDER:
108 g_data_output_stream_set_byte_order (dstream, g_value_get_enum (value));
109 break;
110
111 default:
112 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
113 break;
114 }
115 }
116
117 static void
g_data_output_stream_get_property(GObject * object,guint prop_id,GValue * value,GParamSpec * pspec)118 g_data_output_stream_get_property (GObject *object,
119 guint prop_id,
120 GValue *value,
121 GParamSpec *pspec)
122 {
123 GDataOutputStreamPrivate *priv;
124 GDataOutputStream *dstream;
125
126 dstream = G_DATA_OUTPUT_STREAM (object);
127 priv = dstream->priv;
128
129 switch (prop_id)
130 {
131 case PROP_BYTE_ORDER:
132 g_value_set_enum (value, priv->byte_order);
133 break;
134
135 default:
136 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
137 break;
138 }
139 }
140
141 static void
g_data_output_stream_init(GDataOutputStream * stream)142 g_data_output_stream_init (GDataOutputStream *stream)
143 {
144 stream->priv = G_TYPE_INSTANCE_GET_PRIVATE (stream,
145 G_TYPE_DATA_OUTPUT_STREAM,
146 GDataOutputStreamPrivate);
147
148 stream->priv->byte_order = G_DATA_STREAM_BYTE_ORDER_BIG_ENDIAN;
149 }
150
151 /**
152 * g_data_output_stream_new:
153 * @base_stream: a #GOutputStream.
154 *
155 * Creates a new data output stream for @base_stream.
156 *
157 * Returns: #GDataOutputStream.
158 **/
159 GDataOutputStream *
g_data_output_stream_new(GOutputStream * base_stream)160 g_data_output_stream_new (GOutputStream *base_stream)
161 {
162 GDataOutputStream *stream;
163
164 g_return_val_if_fail (G_IS_OUTPUT_STREAM (base_stream), NULL);
165
166 stream = g_object_new (G_TYPE_DATA_OUTPUT_STREAM,
167 "base-stream", base_stream,
168 NULL);
169
170 return stream;
171 }
172
173 /**
174 * g_data_output_stream_set_byte_order:
175 * @stream: a #GDataOutputStream.
176 * @order: a %GDataStreamByteOrder.
177 *
178 * Sets the byte order of the data output stream to @order.
179 **/
180 void
g_data_output_stream_set_byte_order(GDataOutputStream * stream,GDataStreamByteOrder order)181 g_data_output_stream_set_byte_order (GDataOutputStream *stream,
182 GDataStreamByteOrder order)
183 {
184 GDataOutputStreamPrivate *priv;
185 g_return_if_fail (G_IS_DATA_OUTPUT_STREAM (stream));
186 priv = stream->priv;
187 if (priv->byte_order != order)
188 {
189 priv->byte_order = order;
190 g_object_notify (G_OBJECT (stream), "byte-order");
191 }
192 }
193
194 /**
195 * g_data_output_stream_get_byte_order:
196 * @stream: a #GDataOutputStream.
197 *
198 * Gets the byte order for the stream.
199 *
200 * Returns: the #GDataStreamByteOrder for the @stream.
201 **/
202 GDataStreamByteOrder
g_data_output_stream_get_byte_order(GDataOutputStream * stream)203 g_data_output_stream_get_byte_order (GDataOutputStream *stream)
204 {
205 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), G_DATA_STREAM_BYTE_ORDER_HOST_ENDIAN);
206
207 return stream->priv->byte_order;
208 }
209
210 /**
211 * g_data_output_stream_put_byte:
212 * @stream: a #GDataOutputStream.
213 * @data: a #guchar.
214 * @cancellable: optional #GCancellable object, %NULL to ignore.
215 * @error: a #GError, %NULL to ignore.
216 *
217 * Puts a byte into the output stream.
218 *
219 * Returns: %TRUE if @data was successfully added to the @stream.
220 **/
221 gboolean
g_data_output_stream_put_byte(GDataOutputStream * stream,guchar data,GCancellable * cancellable,GError ** error)222 g_data_output_stream_put_byte (GDataOutputStream *stream,
223 guchar data,
224 GCancellable *cancellable,
225 GError **error)
226 {
227 gsize bytes_written;
228
229 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), FALSE);
230
231 return g_output_stream_write_all (G_OUTPUT_STREAM (stream),
232 &data, 1,
233 &bytes_written,
234 cancellable, error);
235 }
236
237 /**
238 * g_data_output_stream_put_int16:
239 * @stream: a #GDataOutputStream.
240 * @data: a #gint16.
241 * @cancellable: optional #GCancellable object, %NULL to ignore.
242 * @error: a #GError, %NULL to ignore.
243 *
244 * Puts a signed 16-bit integer into the output stream.
245 *
246 * Returns: %TRUE if @data was successfully added to the @stream.
247 **/
248 gboolean
g_data_output_stream_put_int16(GDataOutputStream * stream,gint16 data,GCancellable * cancellable,GError ** error)249 g_data_output_stream_put_int16 (GDataOutputStream *stream,
250 gint16 data,
251 GCancellable *cancellable,
252 GError **error)
253 {
254 gsize bytes_written;
255
256 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), FALSE);
257
258 switch (stream->priv->byte_order)
259 {
260 case G_DATA_STREAM_BYTE_ORDER_BIG_ENDIAN:
261 data = GINT16_TO_BE (data);
262 break;
263 case G_DATA_STREAM_BYTE_ORDER_LITTLE_ENDIAN:
264 data = GINT16_TO_LE (data);
265 break;
266 case G_DATA_STREAM_BYTE_ORDER_HOST_ENDIAN:
267 default:
268 break;
269 }
270
271 return g_output_stream_write_all (G_OUTPUT_STREAM (stream),
272 &data, 2,
273 &bytes_written,
274 cancellable, error);
275 }
276
277 /**
278 * g_data_output_stream_put_uint16:
279 * @stream: a #GDataOutputStream.
280 * @data: a #guint16.
281 * @cancellable: optional #GCancellable object, %NULL to ignore.
282 * @error: a #GError, %NULL to ignore.
283 *
284 * Puts an unsigned 16-bit integer into the output stream.
285 *
286 * Returns: %TRUE if @data was successfully added to the @stream.
287 **/
288 gboolean
g_data_output_stream_put_uint16(GDataOutputStream * stream,guint16 data,GCancellable * cancellable,GError ** error)289 g_data_output_stream_put_uint16 (GDataOutputStream *stream,
290 guint16 data,
291 GCancellable *cancellable,
292 GError **error)
293 {
294 gsize bytes_written;
295
296 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), FALSE);
297
298 switch (stream->priv->byte_order)
299 {
300 case G_DATA_STREAM_BYTE_ORDER_BIG_ENDIAN:
301 data = GUINT16_TO_BE (data);
302 break;
303 case G_DATA_STREAM_BYTE_ORDER_LITTLE_ENDIAN:
304 data = GUINT16_TO_LE (data);
305 break;
306 case G_DATA_STREAM_BYTE_ORDER_HOST_ENDIAN:
307 default:
308 break;
309 }
310
311 return g_output_stream_write_all (G_OUTPUT_STREAM (stream),
312 &data, 2,
313 &bytes_written,
314 cancellable, error);
315 }
316
317 /**
318 * g_data_output_stream_put_int32:
319 * @stream: a #GDataOutputStream.
320 * @data: a #gint32.
321 * @cancellable: optional #GCancellable object, %NULL to ignore.
322 * @error: a #GError, %NULL to ignore.
323 *
324 * Puts a signed 32-bit integer into the output stream.
325 *
326 * Returns: %TRUE if @data was successfully added to the @stream.
327 **/
328 gboolean
g_data_output_stream_put_int32(GDataOutputStream * stream,gint32 data,GCancellable * cancellable,GError ** error)329 g_data_output_stream_put_int32 (GDataOutputStream *stream,
330 gint32 data,
331 GCancellable *cancellable,
332 GError **error)
333 {
334 gsize bytes_written;
335
336 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), FALSE);
337
338 switch (stream->priv->byte_order)
339 {
340 case G_DATA_STREAM_BYTE_ORDER_BIG_ENDIAN:
341 data = GINT32_TO_BE (data);
342 break;
343 case G_DATA_STREAM_BYTE_ORDER_LITTLE_ENDIAN:
344 data = GINT32_TO_LE (data);
345 break;
346 case G_DATA_STREAM_BYTE_ORDER_HOST_ENDIAN:
347 default:
348 break;
349 }
350
351 return g_output_stream_write_all (G_OUTPUT_STREAM (stream),
352 &data, 4,
353 &bytes_written,
354 cancellable, error);
355 }
356
357 /**
358 * g_data_output_stream_put_uint32:
359 * @stream: a #GDataOutputStream.
360 * @data: a #guint32.
361 * @cancellable: optional #GCancellable object, %NULL to ignore.
362 * @error: a #GError, %NULL to ignore.
363 *
364 * Puts an unsigned 32-bit integer into the stream.
365 *
366 * Returns: %TRUE if @data was successfully added to the @stream.
367 **/
368 gboolean
g_data_output_stream_put_uint32(GDataOutputStream * stream,guint32 data,GCancellable * cancellable,GError ** error)369 g_data_output_stream_put_uint32 (GDataOutputStream *stream,
370 guint32 data,
371 GCancellable *cancellable,
372 GError **error)
373 {
374 gsize bytes_written;
375
376 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), FALSE);
377
378 switch (stream->priv->byte_order)
379 {
380 case G_DATA_STREAM_BYTE_ORDER_BIG_ENDIAN:
381 data = GUINT32_TO_BE (data);
382 break;
383 case G_DATA_STREAM_BYTE_ORDER_LITTLE_ENDIAN:
384 data = GUINT32_TO_LE (data);
385 break;
386 case G_DATA_STREAM_BYTE_ORDER_HOST_ENDIAN:
387 default:
388 break;
389 }
390
391 return g_output_stream_write_all (G_OUTPUT_STREAM (stream),
392 &data, 4,
393 &bytes_written,
394 cancellable, error);
395 }
396
397 /**
398 * g_data_output_stream_put_int64:
399 * @stream: a #GDataOutputStream.
400 * @data: a #gint64.
401 * @cancellable: optional #GCancellable object, %NULL to ignore.
402 * @error: a #GError, %NULL to ignore.
403 *
404 * Puts a signed 64-bit integer into the stream.
405 *
406 * Returns: %TRUE if @data was successfully added to the @stream.
407 **/
408 gboolean
g_data_output_stream_put_int64(GDataOutputStream * stream,gint64 data,GCancellable * cancellable,GError ** error)409 g_data_output_stream_put_int64 (GDataOutputStream *stream,
410 gint64 data,
411 GCancellable *cancellable,
412 GError **error)
413 {
414 gsize bytes_written;
415
416 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), FALSE);
417
418 switch (stream->priv->byte_order)
419 {
420 case G_DATA_STREAM_BYTE_ORDER_BIG_ENDIAN:
421 data = GINT64_TO_BE (data);
422 break;
423 case G_DATA_STREAM_BYTE_ORDER_LITTLE_ENDIAN:
424 data = GINT64_TO_LE (data);
425 break;
426 case G_DATA_STREAM_BYTE_ORDER_HOST_ENDIAN:
427 default:
428 break;
429 }
430
431 return g_output_stream_write_all (G_OUTPUT_STREAM (stream),
432 &data, 8,
433 &bytes_written,
434 cancellable, error);
435 }
436
437 /**
438 * g_data_output_stream_put_uint64:
439 * @stream: a #GDataOutputStream.
440 * @data: a #guint64.
441 * @cancellable: optional #GCancellable object, %NULL to ignore.
442 * @error: a #GError, %NULL to ignore.
443 *
444 * Puts an unsigned 64-bit integer into the stream.
445 *
446 * Returns: %TRUE if @data was successfully added to the @stream.
447 **/
448 gboolean
g_data_output_stream_put_uint64(GDataOutputStream * stream,guint64 data,GCancellable * cancellable,GError ** error)449 g_data_output_stream_put_uint64 (GDataOutputStream *stream,
450 guint64 data,
451 GCancellable *cancellable,
452 GError **error)
453 {
454 gsize bytes_written;
455
456 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), FALSE);
457
458 switch (stream->priv->byte_order)
459 {
460 case G_DATA_STREAM_BYTE_ORDER_BIG_ENDIAN:
461 data = GUINT64_TO_BE (data);
462 break;
463 case G_DATA_STREAM_BYTE_ORDER_LITTLE_ENDIAN:
464 data = GUINT64_TO_LE (data);
465 break;
466 case G_DATA_STREAM_BYTE_ORDER_HOST_ENDIAN:
467 default:
468 break;
469 }
470
471 return g_output_stream_write_all (G_OUTPUT_STREAM (stream),
472 &data, 8,
473 &bytes_written,
474 cancellable, error);
475 }
476
477 /**
478 * g_data_output_stream_put_string:
479 * @stream: a #GDataOutputStream.
480 * @str: a string.
481 * @cancellable: optional #GCancellable object, %NULL to ignore.
482 * @error: a #GError, %NULL to ignore.
483 *
484 * Puts a string into the output stream.
485 *
486 * Returns: %TRUE if @string was successfully added to the @stream.
487 **/
488 gboolean
g_data_output_stream_put_string(GDataOutputStream * stream,const char * str,GCancellable * cancellable,GError ** error)489 g_data_output_stream_put_string (GDataOutputStream *stream,
490 const char *str,
491 GCancellable *cancellable,
492 GError **error)
493 {
494 gsize bytes_written;
495
496 g_return_val_if_fail (G_IS_DATA_OUTPUT_STREAM (stream), FALSE);
497 g_return_val_if_fail (str != NULL, FALSE);
498
499 return g_output_stream_write_all (G_OUTPUT_STREAM (stream),
500 str, strlen (str),
501 &bytes_written,
502 cancellable, error);
503 }
504
505 #define __G_DATA_OUTPUT_STREAM_C__
506 #include "gioaliasdef.c"
507