Home | History | Annotate | Download | only in gio
      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 (at) 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 
     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
     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
    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
    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 *
    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
    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
    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
    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
    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
    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
    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
    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
    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
    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
    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