summaryrefslogtreecommitdiff
path: root/qmake/tools/qdatastream.cpp
Unidiff
Diffstat (limited to 'qmake/tools/qdatastream.cpp') (more/less context) (ignore whitespace changes)
-rw-r--r--qmake/tools/qdatastream.cpp1024
1 files changed, 1024 insertions, 0 deletions
diff --git a/qmake/tools/qdatastream.cpp b/qmake/tools/qdatastream.cpp
new file mode 100644
index 0000000..9c573c7
--- a/dev/null
+++ b/qmake/tools/qdatastream.cpp
@@ -0,0 +1,1024 @@
1/****************************************************************************
2** $Id$
3**
4** Implementation of QDataStream class
5**
6** Created : 930831
7**
8** Copyright (C) 1992-2000 Trolltech AS. All rights reserved.
9**
10** This file is part of the tools module of the Qt GUI Toolkit.
11**
12** This file may be distributed under the terms of the Q Public License
13** as defined by Trolltech AS of Norway and appearing in the file
14** LICENSE.QPL included in the packaging of this file.
15**
16** This file may be distributed and/or modified under the terms of the
17** GNU General Public License version 2 as published by the Free Software
18** Foundation and appearing in the file LICENSE.GPL included in the
19** packaging of this file.
20**
21** Licensees holding valid Qt Enterprise Edition or Qt Professional Edition
22** licenses may use this file in accordance with the Qt Commercial License
23** Agreement provided with the Software.
24**
25** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
26** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
27**
28** See http://www.trolltech.com/pricing.html or email sales@trolltech.com for
29** information about Qt Commercial License Agreements.
30** See http://www.trolltech.com/qpl/ for QPL licensing information.
31** See http://www.trolltech.com/gpl/ for GPL licensing information.
32**
33** Contact info@trolltech.com if any conditions of this licensing are
34** not clear to you.
35**
36**********************************************************************/
37
38#include "qdatastream.h"
39
40#ifndef QT_NO_DATASTREAM
41#include "qbuffer.h"
42#include <stdio.h>
43#include <ctype.h>
44#include <stdlib.h>
45
46/*!
47 \class QDataStream qdatastream.h
48 \reentrant
49 \brief The QDataStream class provides serialization of binary data
50 to a QIODevice.
51
52 \ingroup io
53
54 A data stream is a binary stream of encoded information which is
55 100% independent of the host computer's operating system, CPU or
56 byte order. For example, a data stream that is written by a PC
57 under Windows can be read by a Sun SPARC running Solaris.
58
59 You can also use a data stream to read/write \link #raw raw
60 unencoded binary data\endlink. If you want a "parsing" input
61 stream, see QTextStream.
62
63 The QDataStream class implements serialization of primitive types,
64 like \c char, \c short, \c int, \c char* etc. Serialization of
65 more complex data is accomplished by breaking up the data into
66 primitive units.
67
68 A data stream cooperates closely with a QIODevice. A QIODevice
69 represents an input/output medium one can read data from and write
70 data to. The QFile class is an example of an IO device.
71
72 Example (write binary data to a stream):
73 \code
74 QFile file( "file.dat" );
75 file.open( IO_WriteOnly );
76 QDataStream stream( &file ); // we will serialize the data into the file
77 stream << "the answer is"; // serialize a string
78 stream << (Q_INT32)42; // serialize an integer
79 \endcode
80
81 Example (read binary data from a stream):
82 \code
83 QFile file( "file.dat" );
84 file.open( IO_ReadOnly );
85 QDataStream stream( &file ); // read the data serialized from the file
86 QString str;
87 Q_INT32 a;
88 stream >> str >> a; // extract "the answer is" and 42
89 \endcode
90
91 Each item written to the stream is written in a predefined binary
92 format that varies depending on the item's type. Supported Qt
93 types include QBrush, QColor, QDateTime, QFont, QPixmap, QString,
94 QVariant and many others. For the complete list of all Qt types
95 supporting data streaming see the \link datastreamformat.html
96 Format of the QDataStream operators \endlink.
97
98 To take one example, a \c char* string is written as a 32-bit
99 integer equal to the length of the string including the NUL byte
100 ('\0'), followed by all the characters of the string including the
101 NUL byte. When reading a \c char* string, 4 bytes are read to
102 create the 32-bit length value, then that many characters for the
103 \c char* string including the NUL are read.
104
105 The initial IODevice is usually set in the constructor, but can be
106 changed with setDevice(). If you've reached the end of the data
107 (or if there is no IODevice set) atEnd() will return TRUE.
108
109 If you want the data to be compatible with an earlier version of
110 Qt use setVersion().
111
112 If you want the data to be human-readable, e.g. for debugging, you
113 can set the data stream into printable data mode with
114 setPrintableData(). The data is then written slower, in a bloated
115 but human readable format.
116
117 If you are producing a new binary data format, such as a file
118 format for documents created by your application, you could use a
119 QDataStream to write the data in a portable format. Typically, you
120 would write a brief header containing a magic string and a version
121 number to give yourself room for future expansion. For example:
122
123 \code
124 QFile file( "file.xxx" );
125 file.open( IO_WriteOnly );
126 QDataStream stream( &file );
127
128 // Write a header with a "magic number" and a version
129 stream << (Q_UINT32)0xA0B0C0D0;
130 stream << (Q_INT32)123;
131
132 // Write the data
133 stream << [lots of interesting data]
134 \endcode
135
136 Then read it in with:
137
138 \code
139 QFile file( "file.xxx" );
140 file.open( IO_ReadOnly );
141 QDataStream stream( &file );
142
143 // Read and check the header
144 Q_UINT32 magic;
145 stream >> magic;
146 if ( magic != 0xA0B0C0D0 )
147 return XXX_BAD_FILE_FORMAT;
148
149 // Read the version
150 Q_INT32 version;
151 stream >> version;
152 if ( version < 100 )
153 return XXX_BAD_FILE_TOO_OLD;
154 if ( version > 123 )
155 return XXX_BAD_FILE_TOO_NEW;
156 if ( version <= 110 )
157 stream.setVersion(1);
158
159 // Read the data
160 stream >> [lots of interesting data];
161 if ( version > 120 )
162 stream >> [data new in XXX version 1.2];
163 stream >> [other interesting data];
164 \endcode
165
166 You can select which byte order to use when serializing data. The
167 default setting is big endian (MSB first). Changing it to little
168 endian breaks the portability (unless the reader also changes to
169 little endian). We recommend keeping this setting unless you have
170 special requirements.
171
172 \target raw
173 \section1 Reading and writing raw binary data
174
175 You may wish to read/write your own raw binary data to/from the
176 data stream directly. Data may be read from the stream into a
177 preallocated char* using readRawBytes(). Similarly data can be
178 written to the stream using writeRawBytes(). Notice that any
179 encoding/decoding of the data must be done by you.
180
181 A similar pair of functions is readBytes() and writeBytes(). These
182 differ from their \e raw counterparts as follows: readBytes()
183 reads a Q_UINT32 which is taken to be the length of the data to be
184 read, then that number of bytes is read into the preallocated
185 char*; writeBytes() writes a Q_UINT32 containing the length of the
186 data, followed by the data. Notice that any encoding/decoding of
187 the data (apart from the length Q_UINT32) must be done by you.
188
189 \sa QTextStream QVariant
190*/
191
192/*!
193 \enum QDataStream::ByteOrder
194
195 The byte order used for reading/writing the data.
196
197 \value BigEndian the default
198 \value LittleEndian
199*/
200
201
202/*****************************************************************************
203 QDataStream member functions
204 *****************************************************************************/
205
206#if defined(QT_CHECK_STATE)
207#undef CHECK_STREAM_PRECOND
208 #define CHECK_STREAM_PRECOND if ( !dev ) { \
209 qWarning( "QDataStream: No device" );\
210 return *this; }
211#else
212#define CHECK_STREAM_PRECOND
213#endif
214
215static int systemWordSize = 0;
216static bool systemBigEndian;
217
218static const int DefaultStreamVersion = 5;
219// 5 is default in Qt 3.1
220// 4 is default in Qt 3.0
221// 3 is default in Qt 2.1
222// 2 is the Qt 2.0.x format
223// 1 is the Qt 1.x format
224
225/*!
226 Constructs a data stream that has no IO device.
227
228 \sa setDevice()
229*/
230
231QDataStream::QDataStream()
232{
233 if ( systemWordSize == 0 ) // get system features
234 qSysInfo( &systemWordSize, &systemBigEndian );
235 dev = 0; // no device set
236 owndev = FALSE;
237 byteorder = BigEndian; // default byte order
238 printable = FALSE;
239 ver = DefaultStreamVersion;
240 noswap = systemBigEndian;
241}
242
243/*!
244 Constructs a data stream that uses the IO device \a d.
245
246 \warning If you use QSocket or QSocketDevice as the IO device \a d
247 for reading data, you must make sure that enough data is available
248 on the socket for the operation to successfully proceed;
249 QDataStream does not have any means to handle or recover from
250 short-reads.
251
252 \sa setDevice(), device()
253*/
254
255QDataStream::QDataStream( QIODevice *d )
256{
257 if ( systemWordSize == 0 ) // get system features
258 qSysInfo( &systemWordSize, &systemBigEndian );
259 dev = d; // set device
260 owndev = FALSE;
261 byteorder = BigEndian; // default byte order
262 printable = FALSE;
263 ver = DefaultStreamVersion;
264 noswap = systemBigEndian;
265}
266
267/*!
268 Constructs a data stream that operates on a byte array, \a a,
269 through an internal QBuffer device. The \a mode is a
270 QIODevice::mode(), usually either \c IO_ReadOnly or \c
271 IO_WriteOnly.
272
273 Example:
274 \code
275 static char bindata[] = { 231, 1, 44, ... };
276 QByteArray a;
277 a.setRawData( bindata, sizeof(bindata) );// a points to bindata
278 QDataStream stream( a, IO_ReadOnly );// open on a's data
279 stream >> [something]; // read raw bindata
280 a.resetRawData( bindata, sizeof(bindata) ); // finished
281 \endcode
282
283 The QByteArray::setRawData() function is not for the inexperienced.
284*/
285
286QDataStream::QDataStream( QByteArray a, int mode )
287{
288 if ( systemWordSize == 0 ) // get system features
289 qSysInfo( &systemWordSize, &systemBigEndian );
290 dev = new QBuffer( a ); // create device
291 ((QBuffer *)dev)->open( mode ); // open device
292 owndev = TRUE;
293 byteorder = BigEndian; // default byte order
294 printable = FALSE;
295 ver = DefaultStreamVersion;
296 noswap = systemBigEndian;
297}
298
299/*!
300 Destroys the data stream.
301
302 The destructor will not affect the current IO device, unless it is
303 an internal IO device processing a QByteArray passed in the \e
304 constructor, in which case the internal IO device is destroyed.
305*/
306
307QDataStream::~QDataStream()
308{
309 if ( owndev )
310 delete dev;
311}
312
313
314/*!
315 \fn QIODevice *QDataStream::device() const
316
317 Returns the IO device currently set.
318
319 \sa setDevice(), unsetDevice()
320*/
321
322/*!
323 void QDataStream::setDevice(QIODevice *d )
324
325 Sets the IO device to \a d.
326
327 \sa device(), unsetDevice()
328*/
329
330void QDataStream::setDevice(QIODevice *d )
331{
332 if ( owndev ) {
333 delete dev;
334 owndev = FALSE;
335 }
336 dev = d;
337}
338
339/*!
340 Unsets the IO device. This is the same as calling setDevice( 0 ).
341
342 \sa device(), setDevice()
343*/
344
345void QDataStream::unsetDevice()
346{
347 setDevice( 0 );
348}
349
350
351/*!
352 \fn bool QDataStream::atEnd() const
353
354 Returns TRUE if the IO device has reached the end position (end of
355 the stream or file) or if there is no IO device set; otherwise
356 returns FALSE, i.e. if the current position of the IO device is
357 before the end position.
358
359 \sa QIODevice::atEnd()
360*/
361
362/*!\fn bool QDataStream::eof() const
363
364 \obsolete
365
366 Returns TRUE if the IO device has reached the end position (end of
367 stream or file) or if there is no IO device set.
368
369 Returns FALSE if the current position of the read/write head of the IO
370 device is somewhere before the end position.
371
372 \sa QIODevice::atEnd()
373*/
374
375/*!
376 \fn int QDataStream::byteOrder() const
377
378 Returns the current byte order setting -- either \c BigEndian or
379 \c LittleEndian.
380
381 \sa setByteOrder()
382*/
383
384/*!
385 Sets the serialization byte order to \a bo.
386
387 The \a bo parameter can be \c QDataStream::BigEndian or \c
388 QDataStream::LittleEndian.
389
390 The default setting is big endian. We recommend leaving this
391 setting unless you have special requirements.
392
393 \sa byteOrder()
394*/
395
396void QDataStream::setByteOrder( int bo )
397{
398 byteorder = bo;
399 if ( systemBigEndian )
400 noswap = byteorder == BigEndian;
401 else
402 noswap = byteorder == LittleEndian;
403}
404
405
406/*!
407 \fn bool QDataStream::isPrintableData() const
408
409 Returns TRUE if the printable data flag has been set; otherwise
410 returns FALSE.
411
412 \sa setPrintableData()
413*/
414
415/*!
416 \fn void QDataStream::setPrintableData( bool enable )
417
418 If \a enable is TRUE, data will be output in a human readable
419 format. If \a enable is FALSE, data will be output in a binary
420 format.
421
422 If \a enable is TRUE, the write functions will generate output
423 that consists of printable characters (7 bit ASCII). This output
424 will typically be a lot larger than the default binary output, and
425 consequently slower to write.
426
427 We recommend only enabling printable data for debugging purposes.
428*/
429
430
431/*!
432 \fn int QDataStream::version() const
433
434 Returns the version number of the data serialization format. In Qt
435 3.1, this number is 5.
436
437 \sa setVersion()
438*/
439
440/*!
441 \fn void QDataStream::setVersion( int v )
442
443 Sets the version number of the data serialization format to \a v.
444
445 You don't need to set a version if you are using the current
446 version of Qt.
447
448 In order to accommodate new functionality, the datastream
449 serialization format of some Qt classes has changed in some
450 versions of Qt. If you want to read data that was created by an
451 earlier version of Qt, or write data that can be read by a program
452 that was compiled with an earlier version of Qt, use this function
453 to modify the serialization format of QDataStream.
454
455 \table
456 \header \i Qt Version \i QDataStream Version
457 \row \i Qt 3.1 \i11 5
458 \row \i Qt 3.0 \i11 4
459 \row \i Qt 2.1.x and Qt 2.2.x \i11 3
460 \row \i Qt 2.0.x \i11 2
461 \row \i Qt 1.x \i11 1
462 \endtable
463
464 \sa version()
465*/
466
467/*****************************************************************************
468 QDataStream read functions
469 *****************************************************************************/
470
471
472static Q_INT32 read_int_ascii( QDataStream *s )
473{
474 register int n = 0;
475 char buf[40];
476 for ( ;; ) {
477 buf[n] = s->device()->getch();
478 if ( buf[n] == '\n' || n > 38 ) // $-terminator
479 break;
480 n++;
481 }
482 buf[n] = '\0';
483 return atol( buf );
484}
485
486
487/*!
488 \overload QDataStream &QDataStream::operator>>( Q_UINT8 &i )
489
490 Reads an unsigned byte from the stream into \a i, and returns a
491 reference to the stream.
492*/
493
494/*!
495 Reads a signed byte from the stream into \a i, and returns a
496 reference to the stream.
497*/
498
499QDataStream &QDataStream::operator>>( Q_INT8 &i )
500{
501 CHECK_STREAM_PRECOND
502 if ( printable ) { // printable data
503 i = (Q_INT8)dev->getch();
504 if ( i == '\\' ) { // read octal code
505 char buf[4];
506 dev->readBlock( buf, 3 );
507 i = (buf[2] & 0x07)+((buf[1] & 0x07) << 3)+((buf[0] & 0x07) << 6);
508 }
509 } else { // data or text
510 i = (Q_INT8)dev->getch();
511 }
512 return *this;
513}
514
515
516/*!
517 \overload QDataStream &QDataStream::operator>>( Q_UINT16 &i )
518
519 Reads an unsigned 16-bit integer from the stream into \a i, and
520 returns a reference to the stream.
521*/
522
523/*!
524 \overload
525
526 Reads a signed 16-bit integer from the stream into \a i, and
527 returns a reference to the stream.
528*/
529
530QDataStream &QDataStream::operator>>( Q_INT16 &i )
531{
532 CHECK_STREAM_PRECOND
533 if ( printable ) { // printable data
534 i = (Q_INT16)read_int_ascii( this );
535 } else if ( noswap ) { // no conversion needed
536 dev->readBlock( (char *)&i, sizeof(Q_INT16) );
537 } else { // swap bytes
538 register uchar *p = (uchar *)(&i);
539 char b[2];
540 dev->readBlock( b, 2 );
541 *p++ = b[1];
542 *p = b[0];
543 }
544 return *this;
545}
546
547
548/*!
549 \overload QDataStream &QDataStream::operator>>( Q_UINT32 &i )
550
551 Reads an unsigned 32-bit integer from the stream into \a i, and
552 returns a reference to the stream.
553*/
554
555/*!
556 \overload
557
558 Reads a signed 32-bit integer from the stream into \a i, and
559 returns a reference to the stream.
560*/
561
562QDataStream &QDataStream::operator>>( Q_INT32 &i )
563{
564 CHECK_STREAM_PRECOND
565 if ( printable ) { // printable data
566 i = read_int_ascii( this );
567 } else if ( noswap ) { // no conversion needed
568 dev->readBlock( (char *)&i, sizeof(Q_INT32) );
569 } else { // swap bytes
570 uchar *p = (uchar *)(&i);
571 char b[4];
572 dev->readBlock( b, 4 );
573 *p++ = b[3];
574 *p++ = b[2];
575 *p++ = b[1];
576 *p = b[0];
577 }
578 return *this;
579}
580
581/*!
582 \overload QDataStream &QDataStream::operator>>( Q_ULONG &i )
583
584 Reads an unsigned integer of the system's word length from the
585 stream, into \a i, and returns a reference to the stream.
586*/
587
588/*!
589 \overload
590
591 Reads a signed integer of the system's word length from the stream
592 into \a i, and returns a reference to the stream.
593*/
594
595QDataStream &QDataStream::operator>>( Q_LONG &i )
596{
597 CHECK_STREAM_PRECOND
598 if ( printable ) { // printable data
599 i = read_int_ascii( this );
600 } else if ( noswap ) { // no conversion needed
601 dev->readBlock( (char *)&i, sizeof(Q_LONG) );
602 } else { // swap bytes
603 register uchar *p = (uchar *)(&i);
604 char b[sizeof(Q_LONG)];
605 dev->readBlock( b, sizeof(Q_LONG) );
606 for ( int j = sizeof(Q_LONG); j; )
607 *p++ = b[--j];
608 }
609 return *this;
610}
611
612static double read_double_ascii( QDataStream *s )
613{
614 register int n = 0;
615 char buf[80];
616 for ( ;; ) {
617 buf[n] = s->device()->getch();
618 if ( buf[n] == '\n' || n > 78 ) // $-terminator
619 break;
620 n++;
621 }
622 buf[n] = '\0';
623 return atof( buf );
624}
625
626
627/*!
628 \overload
629
630 Reads a 32-bit floating point number from the stream into \a f,
631 using the standard IEEE754 format. Returns a reference to the
632 stream.
633*/
634
635QDataStream &QDataStream::operator>>( float &f )
636{
637 CHECK_STREAM_PRECOND
638 if ( printable ) { // printable data
639 f = (float)read_double_ascii( this );
640 } else if ( noswap ) { // no conversion needed
641 dev->readBlock( (char *)&f, sizeof(float) );
642 } else { // swap bytes
643 uchar *p = (uchar *)(&f);
644 char b[4];
645 dev->readBlock( b, 4 );
646 *p++ = b[3];
647 *p++ = b[2];
648 *p++ = b[1];
649 *p = b[0];
650 }
651 return *this;
652}
653
654
655/*!
656 \overload
657
658 Reads a 64-bit floating point number from the stream into \a f,
659 using the standard IEEE754 format. Returns a reference to the
660 stream.
661*/
662
663QDataStream &QDataStream::operator>>( double &f )
664{
665 CHECK_STREAM_PRECOND
666 if ( printable ) { // printable data
667 f = read_double_ascii( this );
668 } else if ( noswap ) { // no conversion needed
669 dev->readBlock( (char *)&f, sizeof(double) );
670 } else { // swap bytes
671 register uchar *p = (uchar *)(&f);
672 char b[8];
673 dev->readBlock( b, 8 );
674 *p++ = b[7];
675 *p++ = b[6];
676 *p++ = b[5];
677 *p++ = b[4];
678 *p++ = b[3];
679 *p++ = b[2];
680 *p++ = b[1];
681 *p = b[0];
682 }
683 return *this;
684}
685
686
687/*!
688 \overload
689
690 Reads the '\0'-terminated string \a s from the stream and returns
691 a reference to the stream.
692
693 Space for the string is allocated using \c new -- the caller must
694 destroy it with delete[].
695*/
696
697QDataStream &QDataStream::operator>>( char *&s )
698{
699 uint len = 0;
700 return readBytes( s, len );
701}
702
703
704/*!
705 Reads the buffer \a s from the stream and returns a reference to
706 the stream.
707
708 The buffer \a s is allocated using \c new. Destroy it with the \c
709 delete[] operator. If the length is zero or \a s cannot be
710 allocated, \a s is set to 0.
711
712 The \a l parameter will be set to the length of the buffer.
713
714 The serialization format is a Q_UINT32 length specifier first,
715 then \a l bytes of data. Note that the data is \e not encoded.
716
717 \sa readRawBytes(), writeBytes()
718*/
719
720QDataStream &QDataStream::readBytes( char *&s, uint &l )
721{
722 CHECK_STREAM_PRECOND
723 Q_UINT32 len;
724 *this >> len; // first read length spec
725 l = (uint)len;
726 if ( len == 0 || eof() ) {
727 s = 0;
728 return *this;
729 } else {
730 s = new char[len]; // create char array
731 Q_CHECK_PTR( s );
732 if ( !s ) // no memory
733 return *this;
734 return readRawBytes( s, (uint)len );
735 }
736}
737
738
739/*!
740 Reads \a len bytes from the stream into \a s and returns a
741 reference to the stream.
742
743 The buffer \a s must be preallocated. The data is \e not encoded.
744
745 \sa readBytes(), QIODevice::readBlock(), writeRawBytes()
746*/
747
748QDataStream &QDataStream::readRawBytes( char *s, uint len )
749{
750 CHECK_STREAM_PRECOND
751 if ( printable ) { // printable data
752 register Q_INT8 *p = (Q_INT8*)s;
753 while ( len-- )
754 *this >> *p++;
755 } else { // read data char array
756 dev->readBlock( s, len );
757 }
758 return *this;
759}
760
761
762/*****************************************************************************
763 QDataStream write functions
764 *****************************************************************************/
765
766
767/*!
768 \overload QDataStream &QDataStream::operator<<( Q_UINT8 i )
769
770 Writes an unsigned byte, \a i, to the stream and returns a
771 reference to the stream.
772*/
773
774/*!
775 Writes a signed byte, \a i, to the stream and returns a reference
776 to the stream.
777*/
778
779QDataStream &QDataStream::operator<<( Q_INT8 i )
780{
781 CHECK_STREAM_PRECOND
782 if ( printable && (i == '\\' || !isprint((uchar) i)) ) {
783 char buf[6]; // write octal code
784 buf[0] = '\\';
785 buf[1] = '0' + ((i >> 6) & 0x07);
786 buf[2] = '0' + ((i >> 3) & 0x07);
787 buf[3] = '0' + (i & 0x07);
788 buf[4] = '\0';
789 dev->writeBlock( buf, 4 );
790 } else {
791 dev->putch( i );
792 }
793 return *this;
794}
795
796
797/*!
798 \overload QDataStream &QDataStream::operator<<( Q_UINT16 i )
799
800 Writes an unsigned 16-bit integer, \a i, to the stream and returns
801 a reference to the stream.
802*/
803
804/*!
805 \overload
806
807 Writes a signed 16-bit integer, \a i, to the stream and returns a
808 reference to the stream.
809*/
810
811QDataStream &QDataStream::operator<<( Q_INT16 i )
812{
813 CHECK_STREAM_PRECOND
814 if ( printable ) { // printable data
815 char buf[16];
816 sprintf( buf, "%d\n", i );
817 dev->writeBlock( buf, strlen(buf) );
818 } else if ( noswap ) { // no conversion needed
819 dev->writeBlock( (char *)&i, sizeof(Q_INT16) );
820 } else { // swap bytes
821 register uchar *p = (uchar *)(&i);
822 char b[2];
823 b[1] = *p++;
824 b[0] = *p;
825 dev->writeBlock( b, 2 );
826 }
827 return *this;
828}
829
830/*!
831 \overload
832
833 Writes a signed 32-bit integer, \a i, to the stream and returns a
834 reference to the stream.
835*/
836
837QDataStream &QDataStream::operator<<( Q_INT32 i )
838{
839 CHECK_STREAM_PRECOND
840 if ( printable ) { // printable data
841 char buf[16];
842 sprintf( buf, "%d\n", i );
843 dev->writeBlock( buf, strlen(buf) );
844 } else if ( noswap ) { // no conversion needed
845 dev->writeBlock( (char *)&i, sizeof(Q_INT32) );
846 } else { // swap bytes
847 register uchar *p = (uchar *)(&i);
848 char b[4];
849 b[3] = *p++;
850 b[2] = *p++;
851 b[1] = *p++;
852 b[0] = *p;
853 dev->writeBlock( b, 4 );
854 }
855 return *this;
856}
857
858/*!
859 \overload QDataStream &QDataStream::operator<<( Q_ULONG i )
860
861 Writes an unsigned integer \a i, of the system's word length, to
862 the stream and returns a reference to the stream.
863*/
864
865/*!
866 \overload
867
868 Writes a signed integer \a i, of the system's word length, to the
869 stream and returns a reference to the stream.
870*/
871
872QDataStream &QDataStream::operator<<( Q_LONG i )
873{
874 CHECK_STREAM_PRECOND
875 if ( printable ) { // printable data
876 char buf[20];
877 sprintf( buf, "%ld\n", i );
878 dev->writeBlock( buf, strlen(buf) );
879 } else if ( noswap ) { // no conversion needed
880 dev->writeBlock( (char *)&i, sizeof(Q_LONG) );
881 } else { // swap bytes
882 register uchar *p = (uchar *)(&i);
883 char b[sizeof(Q_LONG)];
884 for ( int j = sizeof(Q_LONG); j; )
885 b[--j] = *p++;
886 dev->writeBlock( b, sizeof(Q_LONG) );
887 }
888 return *this;
889}
890
891/*!
892 \overload QDataStream &QDataStream::operator<<( Q_UINT32 i )
893
894 Writes an unsigned integer, \a i, to the stream as a 32-bit
895 unsigned integer (Q_UINT32). Returns a reference to the stream.
896*/
897
898/*!
899 \overload
900
901 Writes a 32-bit floating point number, \a f, to the stream using
902 the standard IEEE754 format. Returns a reference to the stream.
903*/
904
905QDataStream &QDataStream::operator<<( float f )
906{
907 CHECK_STREAM_PRECOND
908 if ( printable ) { // printable data
909 char buf[32];
910 sprintf( buf, "%g\n", (double)f );
911 dev->writeBlock( buf, strlen(buf) );
912 } else {
913 float g = f; // fixes float-on-stack problem
914 if ( noswap ) { // no conversion needed
915 dev->writeBlock( (char *)&g, sizeof(float) );
916 } else { // swap bytes
917 register uchar *p = (uchar *)(&g);
918 char b[4];
919 b[3] = *p++;
920 b[2] = *p++;
921 b[1] = *p++;
922 b[0] = *p;
923 dev->writeBlock( b, 4 );
924 }
925 }
926 return *this;
927}
928
929
930/*!
931 \overload
932
933 Writes a 64-bit floating point number, \a f, to the stream using
934 the standard IEEE754 format. Returns a reference to the stream.
935*/
936
937QDataStream &QDataStream::operator<<( double f )
938{
939 CHECK_STREAM_PRECOND
940 if ( printable ) { // printable data
941 char buf[32];
942 sprintf( buf, "%g\n", f );
943 dev->writeBlock( buf, strlen(buf) );
944 } else if ( noswap ) { // no conversion needed
945 dev->writeBlock( (char *)&f, sizeof(double) );
946 } else { // swap bytes
947 register uchar *p = (uchar *)(&f);
948 char b[8];
949 b[7] = *p++;
950 b[6] = *p++;
951 b[5] = *p++;
952 b[4] = *p++;
953 b[3] = *p++;
954 b[2] = *p++;
955 b[1] = *p++;
956 b[0] = *p;
957 dev->writeBlock( b, 8 );
958 }
959 return *this;
960}
961
962
963/*!
964 \overload
965
966 Writes the '\0'-terminated string \a s to the stream and returns a
967 reference to the stream.
968
969 The string is serialized using writeBytes().
970*/
971
972QDataStream &QDataStream::operator<<( const char *s )
973{
974 if ( !s ) {
975 *this << (Q_UINT32)0;
976 return *this;
977 }
978 uint len = qstrlen( s ) + 1; // also write null terminator
979 *this << (Q_UINT32)len; // write length specifier
980 return writeRawBytes( s, len );
981}
982
983
984/*!
985 Writes the length specifier \a len and the buffer \a s to the
986 stream and returns a reference to the stream.
987
988 The \a len is serialized as a Q_UINT32, followed by \a len bytes
989 from \a s. Note that the data is \e not encoded.
990
991 \sa writeRawBytes(), readBytes()
992*/
993
994QDataStream &QDataStream::writeBytes(const char *s, uint len)
995{
996 CHECK_STREAM_PRECOND
997 *this << (Q_UINT32)len; // write length specifier
998 if ( len )
999 writeRawBytes( s, len );
1000 return *this;
1001}
1002
1003
1004/*!
1005 Writes \a len bytes from \a s to the stream and returns a
1006 reference to the stream. The data is \e not encoded.
1007
1008 \sa writeBytes(), QIODevice::writeBlock(), readRawBytes()
1009*/
1010
1011QDataStream &QDataStream::writeRawBytes( const char *s, uint len )
1012{
1013 CHECK_STREAM_PRECOND
1014 if ( printable ) { // write printable
1015 register Q_INT8 *p = (Q_INT8*)s;
1016 while ( len-- )
1017 *this << *p++;
1018 } else { // write data char array
1019 dev->writeBlock( s, len );
1020 }
1021 return *this;
1022}
1023
1024#endif // QT_NO_DATASTREAM