diff options
Diffstat (limited to 'src/corelib/tools/qbytearray.cpp')
-rw-r--r-- | src/corelib/tools/qbytearray.cpp | 5020 |
1 files changed, 0 insertions, 5020 deletions
diff --git a/src/corelib/tools/qbytearray.cpp b/src/corelib/tools/qbytearray.cpp deleted file mode 100644 index ecbb4743af..0000000000 --- a/src/corelib/tools/qbytearray.cpp +++ /dev/null @@ -1,5020 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2019 The Qt Company Ltd. -** Copyright (C) 2016 Intel Corporation. -** Contact: https://www.qt.io/licensing/ -** -** This file is part of the QtCore module of the Qt Toolkit. -** -** $QT_BEGIN_LICENSE:LGPL$ -** Commercial License Usage -** Licensees holding valid commercial Qt licenses may use this file in -** accordance with the commercial license agreement provided with the -** Software or, alternatively, in accordance with the terms contained in -** a written agreement between you and The Qt Company. For licensing terms -** and conditions see https://www.qt.io/terms-conditions. For further -** information use the contact form at https://www.qt.io/contact-us. -** -** GNU Lesser General Public License Usage -** Alternatively, this file may be used under the terms of the GNU Lesser -** General Public License version 3 as published by the Free Software -** Foundation and appearing in the file LICENSE.LGPL3 included in the -** packaging of this file. Please review the following information to -** ensure the GNU Lesser General Public License version 3 requirements -** will be met: https://www.gnu.org/licenses/lgpl-3.0.html. -** -** GNU General Public License Usage -** Alternatively, this file may be used under the terms of the GNU -** General Public License version 2.0 or (at your option) the GNU General -** Public license version 3 or any later version approved by the KDE Free -** Qt Foundation. The licenses are as published by the Free Software -** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3 -** included in the packaging of this file. Please review the following -** information to ensure the GNU General Public License requirements will -** be met: https://www.gnu.org/licenses/gpl-2.0.html and -** https://www.gnu.org/licenses/gpl-3.0.html. -** -** $QT_END_LICENSE$ -** -****************************************************************************/ - -#include "qbytearray.h" -#include "qbytearraymatcher.h" -#include "qtools_p.h" -#include "qstring.h" -#include "qlist.h" -#include "qlocale.h" -#include "qlocale_p.h" -#include "qlocale_tools_p.h" -#include "private/qnumeric_p.h" -#include "private/qsimd_p.h" -#include "qstringalgorithms_p.h" -#include "qscopedpointer.h" -#include "qbytearray_p.h" -#include <qdatastream.h> -#include <qmath.h> - -#ifndef QT_NO_COMPRESS -#include <zconf.h> -#include <zlib.h> -#endif -#include <ctype.h> -#include <limits.h> -#include <string.h> -#include <stdlib.h> - -#define IS_RAW_DATA(d) ((d)->offset != sizeof(QByteArrayData)) - -QT_BEGIN_NAMESPACE - -// Latin 1 case system, used by QByteArray::to{Upper,Lower}() and qstr(n)icmp(): -/* -#!/usr/bin/perl -l -use feature "unicode_strings"; -for (0..255) { - $up = uc(chr($_)); - $up = chr($_) if ord($up) > 0x100 || length $up > 1; - printf "0x%02x,", ord($up); - print "" if ($_ & 0xf) == 0xf; -} -*/ -static const uchar latin1_uppercased[256] = { - 0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f, - 0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1a,0x1b,0x1c,0x1d,0x1e,0x1f, - 0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2a,0x2b,0x2c,0x2d,0x2e,0x2f, - 0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3a,0x3b,0x3c,0x3d,0x3e,0x3f, - 0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4a,0x4b,0x4c,0x4d,0x4e,0x4f, - 0x50,0x51,0x52,0x53,0x54,0x55,0x56,0x57,0x58,0x59,0x5a,0x5b,0x5c,0x5d,0x5e,0x5f, - 0x60,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4a,0x4b,0x4c,0x4d,0x4e,0x4f, - 0x50,0x51,0x52,0x53,0x54,0x55,0x56,0x57,0x58,0x59,0x5a,0x7b,0x7c,0x7d,0x7e,0x7f, - 0x80,0x81,0x82,0x83,0x84,0x85,0x86,0x87,0x88,0x89,0x8a,0x8b,0x8c,0x8d,0x8e,0x8f, - 0x90,0x91,0x92,0x93,0x94,0x95,0x96,0x97,0x98,0x99,0x9a,0x9b,0x9c,0x9d,0x9e,0x9f, - 0xa0,0xa1,0xa2,0xa3,0xa4,0xa5,0xa6,0xa7,0xa8,0xa9,0xaa,0xab,0xac,0xad,0xae,0xaf, - 0xb0,0xb1,0xb2,0xb3,0xb4,0xb5,0xb6,0xb7,0xb8,0xb9,0xba,0xbb,0xbc,0xbd,0xbe,0xbf, - 0xc0,0xc1,0xc2,0xc3,0xc4,0xc5,0xc6,0xc7,0xc8,0xc9,0xca,0xcb,0xcc,0xcd,0xce,0xcf, - 0xd0,0xd1,0xd2,0xd3,0xd4,0xd5,0xd6,0xd7,0xd8,0xd9,0xda,0xdb,0xdc,0xdd,0xde,0xdf, - 0xc0,0xc1,0xc2,0xc3,0xc4,0xc5,0xc6,0xc7,0xc8,0xc9,0xca,0xcb,0xcc,0xcd,0xce,0xcf, - 0xd0,0xd1,0xd2,0xd3,0xd4,0xd5,0xd6,0xf7,0xd8,0xd9,0xda,0xdb,0xdc,0xdd,0xde,0xff -}; - -/* -#!/usr/bin/perl -l -use feature "unicode_strings"; -for (0..255) { - $up = lc(chr($_)); - $up = chr($_) if ord($up) > 0x100 || length $up > 1; - printf "0x%02x,", ord($up); - print "" if ($_ & 0xf) == 0xf; -} -*/ -static const uchar latin1_lowercased[256] = { - 0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f, - 0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1a,0x1b,0x1c,0x1d,0x1e,0x1f, - 0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2a,0x2b,0x2c,0x2d,0x2e,0x2f, - 0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3a,0x3b,0x3c,0x3d,0x3e,0x3f, - 0x40,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6a,0x6b,0x6c,0x6d,0x6e,0x6f, - 0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x7a,0x5b,0x5c,0x5d,0x5e,0x5f, - 0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6a,0x6b,0x6c,0x6d,0x6e,0x6f, - 0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x7a,0x7b,0x7c,0x7d,0x7e,0x7f, - 0x80,0x81,0x82,0x83,0x84,0x85,0x86,0x87,0x88,0x89,0x8a,0x8b,0x8c,0x8d,0x8e,0x8f, - 0x90,0x91,0x92,0x93,0x94,0x95,0x96,0x97,0x98,0x99,0x9a,0x9b,0x9c,0x9d,0x9e,0x9f, - 0xa0,0xa1,0xa2,0xa3,0xa4,0xa5,0xa6,0xa7,0xa8,0xa9,0xaa,0xab,0xac,0xad,0xae,0xaf, - 0xb0,0xb1,0xb2,0xb3,0xb4,0xb5,0xb6,0xb7,0xb8,0xb9,0xba,0xbb,0xbc,0xbd,0xbe,0xbf, - 0xe0,0xe1,0xe2,0xe3,0xe4,0xe5,0xe6,0xe7,0xe8,0xe9,0xea,0xeb,0xec,0xed,0xee,0xef, - 0xf0,0xf1,0xf2,0xf3,0xf4,0xf5,0xf6,0xd7,0xf8,0xf9,0xfa,0xfb,0xfc,0xfd,0xfe,0xdf, - 0xe0,0xe1,0xe2,0xe3,0xe4,0xe5,0xe6,0xe7,0xe8,0xe9,0xea,0xeb,0xec,0xed,0xee,0xef, - 0xf0,0xf1,0xf2,0xf3,0xf4,0xf5,0xf6,0xf7,0xf8,0xf9,0xfa,0xfb,0xfc,0xfd,0xfe,0xff -}; - -int qFindByteArray( - const char *haystack0, int haystackLen, int from, - const char *needle0, int needleLen); - -/***************************************************************************** - Safe and portable C string functions; extensions to standard string.h - *****************************************************************************/ - -/*! \relates QByteArray - - Returns a duplicate string. - - Allocates space for a copy of \a src, copies it, and returns a - pointer to the copy. If \a src is \nullptr, it immediately returns - \nullptr. - - Ownership is passed to the caller, so the returned string must be - deleted using \c delete[]. -*/ - -char *qstrdup(const char *src) -{ - if (!src) - return nullptr; - char *dst = new char[strlen(src) + 1]; - return qstrcpy(dst, src); -} - -/*! \relates QByteArray - - Copies all the characters up to and including the '\\0' from \a - src into \a dst and returns a pointer to \a dst. If \a src is - \nullptr, it immediately returns \nullptr. - - This function assumes that \a dst is large enough to hold the - contents of \a src. - - \note If \a dst and \a src overlap, the behavior is undefined. - - \sa qstrncpy() -*/ - -char *qstrcpy(char *dst, const char *src) -{ - if (!src) - return nullptr; -#ifdef Q_CC_MSVC - const int len = int(strlen(src)); - // This is actually not secure!!! It will be fixed - // properly in a later release! - if (len >= 0 && strcpy_s(dst, len+1, src) == 0) - return dst; - return nullptr; -#else - return strcpy(dst, src); -#endif -} - -/*! \relates QByteArray - - A safe \c strncpy() function. - - Copies at most \a len bytes from \a src (stopping at \a len or the - terminating '\\0' whichever comes first) into \a dst and returns a - pointer to \a dst. Guarantees that \a dst is '\\0'-terminated. If - \a src or \a dst is \nullptr, returns \nullptr immediately. - - This function assumes that \a dst is at least \a len characters - long. - - \note If \a dst and \a src overlap, the behavior is undefined. - - \note When compiling with Visual C++ compiler version 14.00 - (Visual C++ 2005) or later, internally the function strncpy_s - will be used. - - \sa qstrcpy() -*/ - -char *qstrncpy(char *dst, const char *src, uint len) -{ - if (!src || !dst) - return nullptr; - if (len > 0) { -#ifdef Q_CC_MSVC - strncpy_s(dst, len, src, len - 1); -#else - strncpy(dst, src, len); -#endif - dst[len-1] = '\0'; - } - return dst; -} - -/*! \fn uint qstrlen(const char *str) - \relates QByteArray - - A safe \c strlen() function. - - Returns the number of characters that precede the terminating '\\0', - or 0 if \a str is \nullptr. - - \sa qstrnlen() -*/ - -/*! \fn uint qstrnlen(const char *str, uint maxlen) - \relates QByteArray - \since 4.2 - - A safe \c strnlen() function. - - Returns the number of characters that precede the terminating '\\0', but - at most \a maxlen. If \a str is \nullptr, returns 0. - - \sa qstrlen() -*/ - -/*! - \relates QByteArray - - A safe \c strcmp() function. - - Compares \a str1 and \a str2. Returns a negative value if \a str1 - is less than \a str2, 0 if \a str1 is equal to \a str2 or a - positive value if \a str1 is greater than \a str2. - - Special case 1: Returns 0 if \a str1 and \a str2 are both \nullptr. - - Special case 2: Returns an arbitrary non-zero value if \a str1 is - \nullptr or \a str2 is \nullptr (but not both). - - \sa qstrncmp(), qstricmp(), qstrnicmp(), {8-bit Character Comparisons}, - QByteArray::compare() -*/ -int qstrcmp(const char *str1, const char *str2) -{ - return (str1 && str2) ? strcmp(str1, str2) - : (str1 ? 1 : (str2 ? -1 : 0)); -} - -/*! \fn int qstrncmp(const char *str1, const char *str2, uint len); - - \relates QByteArray - - A safe \c strncmp() function. - - Compares at most \a len bytes of \a str1 and \a str2. - - Returns a negative value if \a str1 is less than \a str2, 0 if \a - str1 is equal to \a str2 or a positive value if \a str1 is greater - than \a str2. - - Special case 1: Returns 0 if \a str1 and \a str2 are both \nullptr. - - Special case 2: Returns a random non-zero value if \a str1 is \nullptr - or \a str2 is \nullptr (but not both). - - \sa qstrcmp(), qstricmp(), qstrnicmp(), {8-bit Character Comparisons}, - QByteArray::compare() -*/ - -/*! \relates QByteArray - - A safe \c stricmp() function. - - Compares \a str1 and \a str2 ignoring the case of the - characters. The encoding of the strings is assumed to be Latin-1. - - Returns a negative value if \a str1 is less than \a str2, 0 if \a - str1 is equal to \a str2 or a positive value if \a str1 is greater - than \a str2. - - Special case 1: Returns 0 if \a str1 and \a str2 are both \nullptr. - - Special case 2: Returns a random non-zero value if \a str1 is \nullptr - or \a str2 is \nullptr (but not both). - - \sa qstrcmp(), qstrncmp(), qstrnicmp(), {8-bit Character Comparisons}, - QByteArray::compare() -*/ - -int qstricmp(const char *str1, const char *str2) -{ - const uchar *s1 = reinterpret_cast<const uchar *>(str1); - const uchar *s2 = reinterpret_cast<const uchar *>(str2); - if (!s1) - return s2 ? -1 : 0; - if (!s2) - return 1; - - enum { Incomplete = 256 }; - qptrdiff offset = 0; - auto innerCompare = [=, &offset](qptrdiff max, bool unlimited) { - max += offset; - do { - uchar c = latin1_lowercased[s1[offset]]; - int res = c - latin1_lowercased[s2[offset]]; - if (Q_UNLIKELY(res)) - return res; - if (Q_UNLIKELY(!c)) - return 0; - ++offset; - } while (unlimited || offset < max); - return int(Incomplete); - }; - -#if defined(__SSE4_1__) && !(defined(__SANITIZE_ADDRESS__) || QT_HAS_FEATURE(address_sanitizer)) - enum { PageSize = 4096, PageMask = PageSize - 1 }; - const __m128i zero = _mm_setzero_si128(); - forever { - // Calculate how many bytes we can load until we cross a page boundary - // for either source. This isn't an exact calculation, just something - // very quick. - quintptr u1 = quintptr(s1 + offset); - quintptr u2 = quintptr(s2 + offset); - uint n = PageSize - ((u1 | u2) & PageMask); - - qptrdiff maxoffset = offset + n; - for ( ; offset + 16 <= maxoffset; offset += sizeof(__m128i)) { - // load 16 bytes from either source - __m128i a = _mm_loadu_si128(reinterpret_cast<const __m128i *>(s1 + offset)); - __m128i b = _mm_loadu_si128(reinterpret_cast<const __m128i *>(s2 + offset)); - - // compare the two against each oher - __m128i cmp = _mm_cmpeq_epi8(a, b); - - // find NUL terminators too - cmp = _mm_min_epu8(cmp, a); - cmp = _mm_cmpeq_epi8(cmp, zero); - - // was there any difference or a NUL? - uint mask = _mm_movemask_epi8(cmp); - if (mask) { - // yes, find out where - uint start = qCountTrailingZeroBits(mask); - uint end = sizeof(mask) * 8 - qCountLeadingZeroBits(mask); - Q_ASSUME(end >= start); - offset += start; - n = end - start; - break; - } - } - - // using SIMD could cause a page fault, so iterate byte by byte - int res = innerCompare(n, false); - if (res != Incomplete) - return res; - } -#endif - - return innerCompare(-1, true); -} - -/*! \relates QByteArray - - A safe \c strnicmp() function. - - Compares at most \a len bytes of \a str1 and \a str2 ignoring the - case of the characters. The encoding of the strings is assumed to - be Latin-1. - - Returns a negative value if \a str1 is less than \a str2, 0 if \a str1 - is equal to \a str2 or a positive value if \a str1 is greater than \a - str2. - - Special case 1: Returns 0 if \a str1 and \a str2 are both \nullptr. - - Special case 2: Returns a random non-zero value if \a str1 is \nullptr - or \a str2 is \nullptr (but not both). - - \sa qstrcmp(), qstrncmp(), qstricmp(), {8-bit Character Comparisons}, - QByteArray::compare() -*/ - -int qstrnicmp(const char *str1, const char *str2, uint len) -{ - const uchar *s1 = reinterpret_cast<const uchar *>(str1); - const uchar *s2 = reinterpret_cast<const uchar *>(str2); - int res; - uchar c; - if (!s1 || !s2) - return s1 ? 1 : (s2 ? -1 : 0); - for (; len--; s1++, s2++) { - if ((res = (c = latin1_lowercased[*s1]) - latin1_lowercased[*s2])) - return res; - if (!c) // strings are equal - break; - } - return 0; -} - -/*! - \internal - \since 5.12 - - A helper for QByteArray::compare. Compares \a len1 bytes from \a str1 to \a - len2 bytes from \a str2. If \a len2 is -1, then \a str2 is expected to be - '\\0'-terminated. - */ -int qstrnicmp(const char *str1, qsizetype len1, const char *str2, qsizetype len2) -{ - Q_ASSERT(str1); - Q_ASSERT(len1 >= 0); - Q_ASSERT(len2 >= -1); - const uchar *s1 = reinterpret_cast<const uchar *>(str1); - const uchar *s2 = reinterpret_cast<const uchar *>(str2); - if (!s2) - return len1 == 0 ? 0 : 1; - - int res; - uchar c; - if (len2 == -1) { - // null-terminated str2 - qsizetype i; - for (i = 0; i < len1; ++i) { - c = latin1_lowercased[s2[i]]; - if (!c) - return 1; - - res = latin1_lowercased[s1[i]] - c; - if (res) - return res; - } - c = latin1_lowercased[s2[i]]; - return c ? -1 : 0; - } else { - // not null-terminated - for (qsizetype i = 0; i < qMin(len1, len2); ++i) { - c = latin1_lowercased[s2[i]]; - res = latin1_lowercased[s1[i]] - c; - if (res) - return res; - } - if (len1 == len2) - return 0; - return len1 < len2 ? -1 : 1; - } -} - -/*! - \internal - ### Qt6: replace the QByteArray parameter with [pointer,len] pair - */ -int qstrcmp(const QByteArray &str1, const char *str2) -{ - if (!str2) - return str1.isEmpty() ? 0 : +1; - - const char *str1data = str1.constData(); - const char *str1end = str1data + str1.length(); - for ( ; str1data < str1end && *str2; ++str1data, ++str2) { - int diff = int(uchar(*str1data)) - uchar(*str2); - if (diff) - // found a difference - return diff; - } - - // Why did we stop? - if (*str2 != '\0') - // not the null, so we stopped because str1 is shorter - return -1; - if (str1data < str1end) - // we haven't reached the end, so str1 must be longer - return +1; - return 0; -} - -/*! - \internal - ### Qt6: replace the QByteArray parameter with [pointer,len] pair - */ -int qstrcmp(const QByteArray &str1, const QByteArray &str2) -{ - int l1 = str1.length(); - int l2 = str2.length(); - int ret = memcmp(str1.constData(), str2.constData(), qMin(l1, l2)); - if (ret != 0) - return ret; - - // they matched qMin(l1, l2) bytes - // so the longer one is lexically after the shorter one - return l1 - l2; -} - -// the CRC table below is created by the following piece of code -#if 0 -static void createCRC16Table() // build CRC16 lookup table -{ - unsigned int i; - unsigned int j; - unsigned short crc_tbl[16]; - unsigned int v0, v1, v2, v3; - for (i = 0; i < 16; i++) { - v0 = i & 1; - v1 = (i >> 1) & 1; - v2 = (i >> 2) & 1; - v3 = (i >> 3) & 1; - j = 0; -#undef SET_BIT -#define SET_BIT(x, b, v) (x) |= (v) << (b) - SET_BIT(j, 0, v0); - SET_BIT(j, 7, v0); - SET_BIT(j, 12, v0); - SET_BIT(j, 1, v1); - SET_BIT(j, 8, v1); - SET_BIT(j, 13, v1); - SET_BIT(j, 2, v2); - SET_BIT(j, 9, v2); - SET_BIT(j, 14, v2); - SET_BIT(j, 3, v3); - SET_BIT(j, 10, v3); - SET_BIT(j, 15, v3); - crc_tbl[i] = j; - } - printf("static const quint16 crc_tbl[16] = {\n"); - for (int i = 0; i < 16; i +=4) - printf(" 0x%04x, 0x%04x, 0x%04x, 0x%04x,\n", crc_tbl[i], crc_tbl[i+1], crc_tbl[i+2], crc_tbl[i+3]); - printf("};\n"); -} -#endif - -static const quint16 crc_tbl[16] = { - 0x0000, 0x1081, 0x2102, 0x3183, - 0x4204, 0x5285, 0x6306, 0x7387, - 0x8408, 0x9489, 0xa50a, 0xb58b, - 0xc60c, 0xd68d, 0xe70e, 0xf78f -}; - -/*! - \relates QByteArray - - Returns the CRC-16 checksum of the first \a len bytes of \a data. - - The checksum is independent of the byte order (endianness) and will be - calculated accorded to the algorithm published in ISO 3309 (Qt::ChecksumIso3309). - - \note This function is a 16-bit cache conserving (16 entry table) - implementation of the CRC-16-CCITT algorithm. -*/ -quint16 qChecksum(const char *data, uint len) -{ - return qChecksum(data, len, Qt::ChecksumIso3309); -} - -/*! - \relates QByteArray - \since 5.9 - - Returns the CRC-16 checksum of the first \a len bytes of \a data. - - The checksum is independent of the byte order (endianness) and will - be calculated accorded to the algorithm published in \a standard. - - \note This function is a 16-bit cache conserving (16 entry table) - implementation of the CRC-16-CCITT algorithm. -*/ -quint16 qChecksum(const char *data, uint len, Qt::ChecksumType standard) -{ - quint16 crc = 0x0000; - switch (standard) { - case Qt::ChecksumIso3309: - crc = 0xffff; - break; - case Qt::ChecksumItuV41: - crc = 0x6363; - break; - } - uchar c; - const uchar *p = reinterpret_cast<const uchar *>(data); - while (len--) { - c = *p++; - crc = ((crc >> 4) & 0x0fff) ^ crc_tbl[((crc ^ c) & 15)]; - c >>= 4; - crc = ((crc >> 4) & 0x0fff) ^ crc_tbl[((crc ^ c) & 15)]; - } - switch (standard) { - case Qt::ChecksumIso3309: - crc = ~crc; - break; - case Qt::ChecksumItuV41: - break; - } - return crc & 0xffff; -} - -/*! - \fn QByteArray qCompress(const QByteArray& data, int compressionLevel) - - \relates QByteArray - - Compresses the \a data byte array and returns the compressed data - in a new byte array. - - The \a compressionLevel parameter specifies how much compression - should be used. Valid values are between 0 and 9, with 9 - corresponding to the greatest compression (i.e. smaller compressed - data) at the cost of using a slower algorithm. Smaller values (8, - 7, ..., 1) provide successively less compression at slightly - faster speeds. The value 0 corresponds to no compression at all. - The default value is -1, which specifies zlib's default - compression. - - \sa qUncompress() -*/ - -/*! \relates QByteArray - - \overload - - Compresses the first \a nbytes of \a data at compression level - \a compressionLevel and returns the compressed data in a new byte array. -*/ - -#ifndef QT_NO_COMPRESS -QByteArray qCompress(const uchar* data, int nbytes, int compressionLevel) -{ - if (nbytes == 0) { - return QByteArray(4, '\0'); - } - if (!data) { - qWarning("qCompress: Data is null"); - return QByteArray(); - } - if (compressionLevel < -1 || compressionLevel > 9) - compressionLevel = -1; - - ulong len = nbytes + nbytes / 100 + 13; - QByteArray bazip; - int res; - do { - bazip.resize(len + 4); - res = ::compress2((uchar*)bazip.data()+4, &len, data, nbytes, compressionLevel); - - switch (res) { - case Z_OK: - bazip.resize(len + 4); - bazip[0] = (nbytes & 0xff000000) >> 24; - bazip[1] = (nbytes & 0x00ff0000) >> 16; - bazip[2] = (nbytes & 0x0000ff00) >> 8; - bazip[3] = (nbytes & 0x000000ff); - break; - case Z_MEM_ERROR: - qWarning("qCompress: Z_MEM_ERROR: Not enough memory"); - bazip.resize(0); - break; - case Z_BUF_ERROR: - len *= 2; - break; - } - } while (res == Z_BUF_ERROR); - - return bazip; -} -#endif - -/*! - \fn QByteArray qUncompress(const QByteArray &data) - - \relates QByteArray - - Uncompresses the \a data byte array and returns a new byte array - with the uncompressed data. - - Returns an empty QByteArray if the input data was corrupt. - - This function will uncompress data compressed with qCompress() - from this and any earlier Qt version, back to Qt 3.1 when this - feature was added. - - \b{Note:} If you want to use this function to uncompress external - data that was compressed using zlib, you first need to prepend a four - byte header to the byte array containing the data. The header must - contain the expected length (in bytes) of the uncompressed data, - expressed as an unsigned, big-endian, 32-bit integer. - - \sa qCompress() -*/ - -#ifndef QT_NO_COMPRESS -namespace { -struct QByteArrayDataDeleter -{ - static inline void cleanup(QTypedArrayData<char> *d) - { if (d) QTypedArrayData<char>::deallocate(d); } -}; -} - -static QByteArray invalidCompressedData() -{ - qWarning("qUncompress: Input data is corrupted"); - return QByteArray(); -} - -/*! \relates QByteArray - - \overload - - Uncompresses the first \a nbytes of \a data and returns a new byte - array with the uncompressed data. -*/ -QByteArray qUncompress(const uchar* data, int nbytes) -{ - if (!data) { - qWarning("qUncompress: Data is null"); - return QByteArray(); - } - if (nbytes <= 4) { - if (nbytes < 4 || (data[0]!=0 || data[1]!=0 || data[2]!=0 || data[3]!=0)) - qWarning("qUncompress: Input data is corrupted"); - return QByteArray(); - } - ulong expectedSize = uint((data[0] << 24) | (data[1] << 16) | - (data[2] << 8) | (data[3] )); - ulong len = qMax(expectedSize, 1ul); - const ulong maxPossibleSize = MaxAllocSize - sizeof(QByteArray::Data); - if (Q_UNLIKELY(len >= maxPossibleSize)) { - // QByteArray does not support that huge size anyway. - return invalidCompressedData(); - } - - QScopedPointer<QByteArray::Data, QByteArrayDataDeleter> d(QByteArray::Data::allocate(expectedSize + 1)); - if (Q_UNLIKELY(d.data() == nullptr)) - return invalidCompressedData(); - - d->size = expectedSize; - forever { - ulong alloc = len; - - int res = ::uncompress((uchar*)d->data(), &len, - data+4, nbytes-4); - - switch (res) { - case Z_OK: - Q_ASSERT(len <= alloc); - Q_UNUSED(alloc); - d->size = len; - d->data()[len] = 0; - { - QByteArrayDataPtr dataPtr = { d.take() }; - return QByteArray(dataPtr); - } - - case Z_MEM_ERROR: - qWarning("qUncompress: Z_MEM_ERROR: Not enough memory"); - return QByteArray(); - - case Z_BUF_ERROR: - len *= 2; - if (Q_UNLIKELY(len >= maxPossibleSize)) { - // QByteArray does not support that huge size anyway. - return invalidCompressedData(); - } else { - // grow the block - QByteArray::Data *p = QByteArray::Data::reallocateUnaligned(d.data(), len + 1); - if (Q_UNLIKELY(p == nullptr)) - return invalidCompressedData(); - d.take(); // don't free - d.reset(p); - } - continue; - - case Z_DATA_ERROR: - qWarning("qUncompress: Z_DATA_ERROR: Input data is corrupted"); - return QByteArray(); - } - } -} -#endif - -/*! - \class QByteArray - \inmodule QtCore - \brief The QByteArray class provides an array of bytes. - - \ingroup tools - \ingroup shared - \ingroup string-processing - - \reentrant - - QByteArray can be used to store both raw bytes (including '\\0's) - and traditional 8-bit '\\0'-terminated strings. Using QByteArray - is much more convenient than using \c{const char *}. Behind the - scenes, it always ensures that the data is followed by a '\\0' - terminator, and uses \l{implicit sharing} (copy-on-write) to - reduce memory usage and avoid needless copying of data. - - In addition to QByteArray, Qt also provides the QString class to - store string data. For most purposes, QString is the class you - want to use. It stores 16-bit Unicode characters, making it easy - to store non-ASCII/non-Latin-1 characters in your application. - Furthermore, QString is used throughout in the Qt API. The two - main cases where QByteArray is appropriate are when you need to - store raw binary data, and when memory conservation is critical - (e.g., with Qt for Embedded Linux). - - One way to initialize a QByteArray is simply to pass a \c{const - char *} to its constructor. For example, the following code - creates a byte array of size 5 containing the data "Hello": - - \snippet code/src_corelib_tools_qbytearray.cpp 0 - - Although the size() is 5, the byte array also maintains an extra - '\\0' character at the end so that if a function is used that - asks for a pointer to the underlying data (e.g. a call to - data()), the data pointed to is guaranteed to be - '\\0'-terminated. - - QByteArray makes a deep copy of the \c{const char *} data, so you - can modify it later without experiencing side effects. (If for - performance reasons you don't want to take a deep copy of the - character data, use QByteArray::fromRawData() instead.) - - Another approach is to set the size of the array using resize() - and to initialize the data byte per byte. QByteArray uses 0-based - indexes, just like C++ arrays. To access the byte at a particular - index position, you can use operator[](). On non-const byte - arrays, operator[]() returns a reference to a byte that can be - used on the left side of an assignment. For example: - - \snippet code/src_corelib_tools_qbytearray.cpp 1 - - For read-only access, an alternative syntax is to use at(): - - \snippet code/src_corelib_tools_qbytearray.cpp 2 - - at() can be faster than operator[](), because it never causes a - \l{deep copy} to occur. - - To extract many bytes at a time, use left(), right(), or mid(). - - A QByteArray can embed '\\0' bytes. The size() function always - returns the size of the whole array, including embedded '\\0' - bytes, but excluding the terminating '\\0' added by QByteArray. - For example: - - \snippet code/src_corelib_tools_qbytearray.cpp 48 - - If you want to obtain the length of the data up to and - excluding the first '\\0' character, call qstrlen() on the byte - array. - - After a call to resize(), newly allocated bytes have undefined - values. To set all the bytes to a particular value, call fill(). - - To obtain a pointer to the actual character data, call data() or - constData(). These functions return a pointer to the beginning of the data. - The pointer is guaranteed to remain valid until a non-const function is - called on the QByteArray. It is also guaranteed that the data ends with a - '\\0' byte unless the QByteArray was created from a \l{fromRawData()}{raw - data}. This '\\0' byte is automatically provided by QByteArray and is not - counted in size(). - - QByteArray provides the following basic functions for modifying - the byte data: append(), prepend(), insert(), replace(), and - remove(). For example: - - \snippet code/src_corelib_tools_qbytearray.cpp 3 - - The replace() and remove() functions' first two arguments are the - position from which to start erasing and the number of bytes that - should be erased. - - When you append() data to a non-empty array, the array will be - reallocated and the new data copied to it. You can avoid this - behavior by calling reserve(), which preallocates a certain amount - of memory. You can also call capacity() to find out how much - memory QByteArray actually allocated. Data appended to an empty - array is not copied. - - A frequent requirement is to remove whitespace characters from a - byte array ('\\n', '\\t', ' ', etc.). If you want to remove - whitespace from both ends of a QByteArray, use trimmed(). If you - want to remove whitespace from both ends and replace multiple - consecutive whitespaces with a single space character within the - byte array, use simplified(). - - If you want to find all occurrences of a particular character or - substring in a QByteArray, use indexOf() or lastIndexOf(). The - former searches forward starting from a given index position, the - latter searches backward. Both return the index position of the - character or substring if they find it; otherwise, they return -1. - For example, here's a typical loop that finds all occurrences of a - particular substring: - - \snippet code/src_corelib_tools_qbytearray.cpp 4 - - If you simply want to check whether a QByteArray contains a - particular character or substring, use contains(). If you want to - find out how many times a particular character or substring - occurs in the byte array, use count(). If you want to replace all - occurrences of a particular value with another, use one of the - two-parameter replace() overloads. - - \l{QByteArray}s can be compared using overloaded operators such as - operator<(), operator<=(), operator==(), operator>=(), and so on. - The comparison is based exclusively on the numeric values - of the characters and is very fast, but is not what a human would - expect. QString::localeAwareCompare() is a better choice for - sorting user-interface strings. - - For historical reasons, QByteArray distinguishes between a null - byte array and an empty byte array. A \e null byte array is a - byte array that is initialized using QByteArray's default - constructor or by passing (const char *)0 to the constructor. An - \e empty byte array is any byte array with size 0. A null byte - array is always empty, but an empty byte array isn't necessarily - null: - - \snippet code/src_corelib_tools_qbytearray.cpp 5 - - All functions except isNull() treat null byte arrays the same as - empty byte arrays. For example, data() returns a valid pointer - (\e not nullptr) to a '\\0' character for a byte array - and QByteArray() compares equal to QByteArray(""). We recommend - that you always use isEmpty() and avoid isNull(). - - \section1 Maximum size and out-of-memory conditions - - The current version of QByteArray is limited to just under 2 GB (2^31 - bytes) in size. The exact value is architecture-dependent, since it depends - on the overhead required for managing the data block, but is no more than - 32 bytes. Raw data blocks are also limited by the use of \c int type in the - current version to 2 GB minus 1 byte. - - In case memory allocation fails, QByteArray will throw a \c std::bad_alloc - exception. Out of memory conditions in the Qt containers are the only case - where Qt will throw exceptions. - - Note that the operating system may impose further limits on applications - holding a lot of allocated memory, especially large, contiguous blocks. - Such considerations, the configuration of such behavior or any mitigation - are outside the scope of the QByteArray API. - - \section1 Notes on Locale - - \section2 Number-String Conversions - - Functions that perform conversions between numeric data types and - strings are performed in the C locale, irrespective of the user's - locale settings. Use QString to perform locale-aware conversions - between numbers and strings. - - \section2 8-bit Character Comparisons - - In QByteArray, the notion of uppercase and lowercase and of which - character is greater than or less than another character is - locale dependent. This affects functions that support a case - insensitive option or that compare or lowercase or uppercase - their arguments. Case insensitive operations and comparisons will - be accurate if both strings contain only ASCII characters. (If \c - $LC_CTYPE is set, most Unix systems do "the right thing".) - Functions that this affects include contains(), indexOf(), - lastIndexOf(), operator<(), operator<=(), operator>(), - operator>=(), isLower(), isUpper(), toLower() and toUpper(). - - This issue does not apply to \l{QString}s since they represent - characters using Unicode. - - \sa QString, QBitArray -*/ - -/*! - \enum QByteArray::Base64Option - \since 5.2 - - This enum contains the options available for encoding and decoding Base64. - Base64 is defined by \l{RFC 4648}, with the following options: - - \value Base64Encoding (default) The regular Base64 alphabet, called simply "base64" - \value Base64UrlEncoding An alternate alphabet, called "base64url", which replaces two - characters in the alphabet to be more friendly to URLs. - \value KeepTrailingEquals (default) Keeps the trailing padding equal signs at the end - of the encoded data, so the data is always a size multiple of - four. - \value OmitTrailingEquals Omits adding the padding equal signs at the end of the encoded - data. - - QByteArray::fromBase64() ignores the KeepTrailingEquals and - OmitTrailingEquals options and will not flag errors in case they are - missing or if there are too many of them. -*/ - -/*! \fn QByteArray::iterator QByteArray::begin() - - Returns an \l{STL-style iterators}{STL-style iterator} pointing to the first character in - the byte-array. - - \sa constBegin(), end() -*/ - -/*! \fn QByteArray::const_iterator QByteArray::begin() const - - \overload begin() -*/ - -/*! \fn QByteArray::const_iterator QByteArray::cbegin() const - \since 5.0 - - Returns a const \l{STL-style iterators}{STL-style iterator} pointing to the first character - in the byte-array. - - \sa begin(), cend() -*/ - -/*! \fn QByteArray::const_iterator QByteArray::constBegin() const - - Returns a const \l{STL-style iterators}{STL-style iterator} pointing to the first character - in the byte-array. - - \sa begin(), constEnd() -*/ - -/*! \fn QByteArray::iterator QByteArray::end() - - Returns an \l{STL-style iterators}{STL-style iterator} pointing to the imaginary character - after the last character in the byte-array. - - \sa begin(), constEnd() -*/ - -/*! \fn QByteArray::const_iterator QByteArray::end() const - - \overload end() -*/ - -/*! \fn QByteArray::const_iterator QByteArray::cend() const - \since 5.0 - - Returns a const \l{STL-style iterators}{STL-style iterator} pointing to the imaginary - character after the last character in the list. - - \sa cbegin(), end() -*/ - -/*! \fn QByteArray::const_iterator QByteArray::constEnd() const - - Returns a const \l{STL-style iterators}{STL-style iterator} pointing to the imaginary - character after the last character in the list. - - \sa constBegin(), end() -*/ - -/*! \fn QByteArray::reverse_iterator QByteArray::rbegin() - \since 5.6 - - Returns a \l{STL-style iterators}{STL-style} reverse iterator pointing to the first - character in the byte-array, in reverse order. - - \sa begin(), crbegin(), rend() -*/ - -/*! \fn QByteArray::const_reverse_iterator QByteArray::rbegin() const - \since 5.6 - \overload -*/ - -/*! \fn QByteArray::const_reverse_iterator QByteArray::crbegin() const - \since 5.6 - - Returns a const \l{STL-style iterators}{STL-style} reverse iterator pointing to the first - character in the byte-array, in reverse order. - - \sa begin(), rbegin(), rend() -*/ - -/*! \fn QByteArray::reverse_iterator QByteArray::rend() - \since 5.6 - - Returns a \l{STL-style iterators}{STL-style} reverse iterator pointing to one past - the last character in the byte-array, in reverse order. - - \sa end(), crend(), rbegin() -*/ - -/*! \fn QByteArray::const_reverse_iterator QByteArray::rend() const - \since 5.6 - \overload -*/ - -/*! \fn QByteArray::const_reverse_iterator QByteArray::crend() const - \since 5.6 - - Returns a const \l{STL-style iterators}{STL-style} reverse iterator pointing to one - past the last character in the byte-array, in reverse order. - - \sa end(), rend(), rbegin() -*/ - -/*! \fn void QByteArray::push_back(const QByteArray &other) - - This function is provided for STL compatibility. It is equivalent - to append(\a other). -*/ - -/*! \fn void QByteArray::push_back(const char *str) - - \overload - - Same as append(\a str). -*/ - -/*! \fn void QByteArray::push_back(char ch) - - \overload - - Same as append(\a ch). -*/ - -/*! \fn void QByteArray::push_front(const QByteArray &other) - - This function is provided for STL compatibility. It is equivalent - to prepend(\a other). -*/ - -/*! \fn void QByteArray::push_front(const char *str) - - \overload - - Same as prepend(\a str). -*/ - -/*! \fn void QByteArray::push_front(char ch) - - \overload - - Same as prepend(\a ch). -*/ - -/*! \fn void QByteArray::shrink_to_fit() - \since 5.10 - - This function is provided for STL compatibility. It is equivalent to - squeeze(). -*/ - -/*! \fn QByteArray::QByteArray(const QByteArray &other) - - Constructs a copy of \a other. - - This operation takes \l{constant time}, because QByteArray is - \l{implicitly shared}. This makes returning a QByteArray from a - function very fast. If a shared instance is modified, it will be - copied (copy-on-write), taking \l{linear time}. - - \sa operator=() -*/ - -/*! - \fn QByteArray::QByteArray(QByteArray &&other) - - Move-constructs a QByteArray instance, making it point at the same - object that \a other was pointing to. - - \since 5.2 -*/ - -/*! \fn QByteArray::QByteArray(QByteArrayDataPtr dd) - - \internal - - Constructs a byte array pointing to the same data as \a dd. -*/ - -/*! \fn QByteArray::~QByteArray() - Destroys the byte array. -*/ - -/*! - Assigns \a other to this byte array and returns a reference to - this byte array. -*/ -QByteArray &QByteArray::operator=(const QByteArray & other) noexcept -{ - other.d->ref.ref(); - if (!d->ref.deref()) - Data::deallocate(d); - d = other.d; - return *this; -} - - -/*! - \overload - - Assigns \a str to this byte array. -*/ - -QByteArray &QByteArray::operator=(const char *str) -{ - Data *x; - if (!str) { - x = Data::sharedNull(); - } else if (!*str) { - x = Data::allocate(0); - } else { - const int len = int(strlen(str)); - const uint fullLen = len + 1; - if (d->ref.isShared() || fullLen > d->alloc - || (len < d->size && fullLen < uint(d->alloc >> 1))) - reallocData(fullLen, d->detachFlags()); - x = d; - memcpy(x->data(), str, fullLen); // include null terminator - x->size = len; - } - x->ref.ref(); - if (!d->ref.deref()) - Data::deallocate(d); - d = x; - return *this; -} - -/*! - \fn QByteArray &QByteArray::operator=(QByteArray &&other) - - Move-assigns \a other to this QByteArray instance. - - \since 5.2 -*/ - -/*! \fn void QByteArray::swap(QByteArray &other) - \since 4.8 - - Swaps byte array \a other with this byte array. This operation is very - fast and never fails. -*/ - -/*! \fn int QByteArray::size() const - - Returns the number of bytes in this byte array. - - The last byte in the byte array is at position size() - 1. In addition, - QByteArray ensures that the byte at position size() is always '\\0', so - that you can use the return value of data() and constData() as arguments to - functions that expect '\\0'-terminated strings. If the QByteArray object - was created from a \l{fromRawData()}{raw data} that didn't include the - trailing null-termination character then QByteArray doesn't add it - automaticall unless the \l{deep copy} is created. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 6 - - \sa isEmpty(), resize() -*/ - -/*! \fn bool QByteArray::isEmpty() const - - Returns \c true if the byte array has size 0; otherwise returns \c false. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 7 - - \sa size() -*/ - -/*! \fn int QByteArray::capacity() const - - Returns the maximum number of bytes that can be stored in the - byte array without forcing a reallocation. - - The sole purpose of this function is to provide a means of fine - tuning QByteArray's memory usage. In general, you will rarely - ever need to call this function. If you want to know how many - bytes are in the byte array, call size(). - - \sa reserve(), squeeze() -*/ - -/*! \fn void QByteArray::reserve(int size) - - Attempts to allocate memory for at least \a size bytes. If you - know in advance how large the byte array will be, you can call - this function, and if you call resize() often you are likely to - get better performance. If \a size is an underestimate, the worst - that will happen is that the QByteArray will be a bit slower. - - The sole purpose of this function is to provide a means of fine - tuning QByteArray's memory usage. In general, you will rarely - ever need to call this function. If you want to change the size - of the byte array, call resize(). - - \sa squeeze(), capacity() -*/ - -/*! \fn void QByteArray::squeeze() - - Releases any memory not required to store the array's data. - - The sole purpose of this function is to provide a means of fine - tuning QByteArray's memory usage. In general, you will rarely - ever need to call this function. - - \sa reserve(), capacity() -*/ - -/*! \fn QByteArray::operator const char *() const - \fn QByteArray::operator const void *() const - - \obsolete Use constData() instead. - - Returns a pointer to the data stored in the byte array. The - pointer can be used to access the bytes that compose the array. - The data is '\\0'-terminated. The pointer remains valid as long - as the array isn't reallocated or destroyed. - - This operator is mostly useful to pass a byte array to a function - that accepts a \c{const char *}. - - You can disable this operator by defining \c - QT_NO_CAST_FROM_BYTEARRAY when you compile your applications. - - Note: A QByteArray can store any byte values including '\\0's, - but most functions that take \c{char *} arguments assume that the - data ends at the first '\\0' they encounter. - - \sa constData() -*/ - -/*! - \macro QT_NO_CAST_FROM_BYTEARRAY - \relates QByteArray - - Disables automatic conversions from QByteArray to - const char * or const void *. - - \sa QT_NO_CAST_TO_ASCII, QT_NO_CAST_FROM_ASCII -*/ - -/*! \fn char *QByteArray::data() - - Returns a pointer to the data stored in the byte array. The - pointer can be used to access and modify the bytes that compose - the array. The data is '\\0'-terminated, i.e. the number of - bytes in the returned character string is size() + 1 for the - '\\0' terminator. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 8 - - The pointer remains valid as long as the byte array isn't - reallocated or destroyed. For read-only access, constData() is - faster because it never causes a \l{deep copy} to occur. - - This function is mostly useful to pass a byte array to a function - that accepts a \c{const char *}. - - The following example makes a copy of the char* returned by - data(), but it will corrupt the heap and cause a crash because it - does not allocate a byte for the '\\0' at the end: - - \snippet code/src_corelib_tools_qbytearray.cpp 46 - - This one allocates the correct amount of space: - - \snippet code/src_corelib_tools_qbytearray.cpp 47 - - Note: A QByteArray can store any byte values including '\\0's, - but most functions that take \c{char *} arguments assume that the - data ends at the first '\\0' they encounter. - - \sa constData(), operator[]() -*/ - -/*! \fn const char *QByteArray::data() const - - \overload -*/ - -/*! \fn const char *QByteArray::constData() const - - Returns a pointer to the data stored in the byte array. The pointer can be - used to access the bytes that compose the array. The data is - '\\0'-terminated unless the QByteArray object was created from raw data. - The pointer remains valid as long as the byte array isn't reallocated or - destroyed. - - This function is mostly useful to pass a byte array to a function - that accepts a \c{const char *}. - - Note: A QByteArray can store any byte values including '\\0's, - but most functions that take \c{char *} arguments assume that the - data ends at the first '\\0' they encounter. - - \sa data(), operator[](), fromRawData() -*/ - -/*! \fn void QByteArray::detach() - - \internal -*/ - -/*! \fn bool QByteArray::isDetached() const - - \internal -*/ - -/*! \fn bool QByteArray::isSharedWith(const QByteArray &other) const - - \internal -*/ - -/*! \fn char QByteArray::at(int i) const - - Returns the character at index position \a i in the byte array. - - \a i must be a valid index position in the byte array (i.e., 0 <= - \a i < size()). - - \sa operator[]() -*/ - -/*! \fn QByteRef QByteArray::operator[](int i) - - Returns the byte at index position \a i as a modifiable reference. - - If an assignment is made beyond the end of the byte array, the - array is extended with resize() before the assignment takes - place. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 9 - - The return value is of type QByteRef, a helper class for - QByteArray. When you get an object of type QByteRef, you can use - it as if it were a char &. If you assign to it, the assignment - will apply to the character in the QByteArray from which you got - the reference. - - \note Before Qt 5.14 it was possible to use this operator to access - a character at an out-of-bounds position in the byte array, and - then assign to such a position, causing the byte array to be - automatically resized. Furthermore, assigning a value to the - returned QByteRef would cause a detach of the byte array, even if the - byte array has been copied in the meanwhile (and the QByteRef kept - alive while the copy was taken). These behaviors are deprecated, - and will be changed in a future version of Qt. - - \sa at() -*/ - -/*! \fn char QByteArray::operator[](int i) const - - \overload - - Same as at(\a i). -*/ - -/*! \fn QByteRef QByteArray::operator[](uint i) - - \overload -*/ - -/*! \fn char QByteArray::operator[](uint i) const - - \overload -*/ - -/*! - \fn char QByteArray::front() const - \since 5.10 - - Returns the first character in the byte array. - Same as \c{at(0)}. - - This function is provided for STL compatibility. - - \warning Calling this function on an empty byte array constitutes - undefined behavior. - - \sa back(), at(), operator[]() -*/ - -/*! - \fn char QByteArray::back() const - \since 5.10 - - Returns the last character in the byte array. - Same as \c{at(size() - 1)}. - - This function is provided for STL compatibility. - - \warning Calling this function on an empty byte array constitutes - undefined behavior. - - \sa front(), at(), operator[]() -*/ - -/*! - \fn QByteRef QByteArray::front() - \since 5.10 - - Returns a reference to the first character in the byte array. - Same as \c{operator[](0)}. - - This function is provided for STL compatibility. - - \warning Calling this function on an empty byte array constitutes - undefined behavior. - - \sa back(), at(), operator[]() -*/ - -/*! - \fn QByteRef QByteArray::back() - \since 5.10 - - Returns a reference to the last character in the byte array. - Same as \c{operator[](size() - 1)}. - - This function is provided for STL compatibility. - - \warning Calling this function on an empty byte array constitutes - undefined behavior. - - \sa front(), at(), operator[]() -*/ - -/*! \fn bool QByteArray::contains(const QByteArray &ba) const - - Returns \c true if the byte array contains an occurrence of the byte - array \a ba; otherwise returns \c false. - - \sa indexOf(), count() -*/ - -/*! \fn bool QByteArray::contains(const char *str) const - - \overload - - Returns \c true if the byte array contains the string \a str; - otherwise returns \c false. -*/ - -/*! \fn bool QByteArray::contains(char ch) const - - \overload - - Returns \c true if the byte array contains the character \a ch; - otherwise returns \c false. -*/ - -/*! - - Truncates the byte array at index position \a pos. - - If \a pos is beyond the end of the array, nothing happens. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 10 - - \sa chop(), resize(), left() -*/ -void QByteArray::truncate(int pos) -{ - if (pos < d->size) - resize(pos); -} - -/*! - - Removes \a n bytes from the end of the byte array. - - If \a n is greater than size(), the result is an empty byte - array. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 11 - - \sa truncate(), resize(), left() -*/ - -void QByteArray::chop(int n) -{ - if (n > 0) - resize(d->size - n); -} - - -/*! \fn QByteArray &QByteArray::operator+=(const QByteArray &ba) - - Appends the byte array \a ba onto the end of this byte array and - returns a reference to this byte array. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 12 - - Note: QByteArray is an \l{implicitly shared} class. Consequently, - if you append to an empty byte array, then the byte array will just - share the data held in \a ba. In this case, no copying of data is done, - taking \l{constant time}. If a shared instance is modified, it will - be copied (copy-on-write), taking \l{linear time}. - - If the byte array being appended to is not empty, a deep copy of the - data is performed, taking \l{linear time}. - - This operation typically does not suffer from allocation overhead, - because QByteArray preallocates extra space at the end of the data - so that it may grow without reallocating for each append operation. - - \sa append(), prepend() -*/ - -/*! \fn QByteArray &QByteArray::operator+=(const QString &str) - - \overload - - Appends the string \a str onto the end of this byte array and - returns a reference to this byte array. The Unicode data is - converted into 8-bit characters using QString::toUtf8(). - - You can disable this function by defining \c QT_NO_CAST_TO_ASCII when you - compile your applications. You then need to call QString::toUtf8() (or - QString::toLatin1() or QString::toLocal8Bit()) explicitly if you want to - convert the data to \c{const char *}. -*/ - -/*! \fn QByteArray &QByteArray::operator+=(const char *str) - - \overload - - Appends the string \a str onto the end of this byte array and - returns a reference to this byte array. -*/ - -/*! \fn QByteArray &QByteArray::operator+=(char ch) - - \overload - - Appends the character \a ch onto the end of this byte array and - returns a reference to this byte array. -*/ - -/*! \fn int QByteArray::length() const - - Same as size(). -*/ - -/*! \fn bool QByteArray::isNull() const - - Returns \c true if this byte array is null; otherwise returns \c false. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 13 - - Qt makes a distinction between null byte arrays and empty byte - arrays for historical reasons. For most applications, what - matters is whether or not a byte array contains any data, - and this can be determined using isEmpty(). - - \sa isEmpty() -*/ - -/*! \fn QByteArray::QByteArray() - - Constructs an empty byte array. - - \sa isEmpty() -*/ - -/*! - Constructs a byte array containing the first \a size bytes of - array \a data. - - If \a data is 0, a null byte array is constructed. - - If \a size is negative, \a data is assumed to point to a - '\\0'-terminated string and its length is determined dynamically. - The terminating \\0 character is not considered part of the - byte array. - - QByteArray makes a deep copy of the string data. - - \sa fromRawData() -*/ - -QByteArray::QByteArray(const char *data, int size) -{ - if (!data) { - d = Data::sharedNull(); - } else { - if (size < 0) - size = int(strlen(data)); - if (!size) { - d = Data::allocate(0); - } else { - d = Data::allocate(uint(size) + 1u); - Q_CHECK_PTR(d); - d->size = size; - memcpy(d->data(), data, size); - d->data()[size] = '\0'; - } - } -} - -/*! - Constructs a byte array of size \a size with every byte set to - character \a ch. - - \sa fill() -*/ - -QByteArray::QByteArray(int size, char ch) -{ - if (size <= 0) { - d = Data::allocate(0); - } else { - d = Data::allocate(uint(size) + 1u); - Q_CHECK_PTR(d); - d->size = size; - memset(d->data(), ch, size); - d->data()[size] = '\0'; - } -} - -/*! - \internal - - Constructs a byte array of size \a size with uninitialized contents. -*/ - -QByteArray::QByteArray(int size, Qt::Initialization) -{ - d = Data::allocate(uint(size) + 1u); - Q_CHECK_PTR(d); - d->size = size; - d->data()[size] = '\0'; -} - -/*! - Sets the size of the byte array to \a size bytes. - - If \a size is greater than the current size, the byte array is - extended to make it \a size bytes with the extra bytes added to - the end. The new bytes are uninitialized. - - If \a size is less than the current size, bytes are removed from - the end. - - \sa size(), truncate() -*/ -void QByteArray::resize(int size) -{ - if (size < 0) - size = 0; - - if (IS_RAW_DATA(d) && !d->ref.isShared() && size < d->size) { - d->size = size; - return; - } - - if (size == 0 && !d->capacityReserved) { - Data *x = Data::allocate(0); - if (!d->ref.deref()) - Data::deallocate(d); - d = x; - } else if (d->size == 0 && d->ref.isStatic()) { - // - // Optimize the idiom: - // QByteArray a; - // a.resize(sz); - // ... - // which is used in place of the Qt 3 idiom: - // QByteArray a(sz); - // - Data *x = Data::allocate(uint(size) + 1u); - Q_CHECK_PTR(x); - x->size = size; - x->data()[size] = '\0'; - d = x; - } else { - if (d->ref.isShared() || uint(size) + 1u > d->alloc - || (!d->capacityReserved && size < d->size - && uint(size) + 1u < uint(d->alloc >> 1))) - reallocData(uint(size) + 1u, d->detachFlags() | Data::Grow); - if (d->alloc) { - d->size = size; - d->data()[size] = '\0'; - } - } -} - -/*! - Sets every byte in the byte array to character \a ch. If \a size - is different from -1 (the default), the byte array is resized to - size \a size beforehand. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 14 - - \sa resize() -*/ - -QByteArray &QByteArray::fill(char ch, int size) -{ - resize(size < 0 ? d->size : size); - if (d->size) - memset(d->data(), ch, d->size); - return *this; -} - -void QByteArray::reallocData(uint alloc, Data::AllocationOptions options) -{ - if (d->ref.isShared() || IS_RAW_DATA(d)) { - Data *x = Data::allocate(alloc, options); - Q_CHECK_PTR(x); - x->size = qMin(int(alloc) - 1, d->size); - ::memcpy(x->data(), d->data(), x->size); - x->data()[x->size] = '\0'; - if (!d->ref.deref()) - Data::deallocate(d); - d = x; - } else { - Data *x = Data::reallocateUnaligned(d, alloc, options); - Q_CHECK_PTR(x); - d = x; - } -} - -void QByteArray::expand(int i) -{ - resize(qMax(i + 1, d->size)); -} - -/*! - \internal - Return a QByteArray that is sure to be '\\0'-terminated. - - By default, all QByteArray have an extra NUL at the end, - guaranteeing that assumption. However, if QByteArray::fromRawData - is used, then the NUL is there only if the user put it there. We - can't be sure. -*/ -QByteArray QByteArray::nulTerminated() const -{ - // is this fromRawData? - if (!IS_RAW_DATA(d)) - return *this; // no, then we're sure we're zero terminated - - QByteArray copy(*this); - copy.detach(); - return copy; -} - -/*! - Prepends the byte array \a ba to this byte array and returns a - reference to this byte array. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 15 - - This is the same as insert(0, \a ba). - - Note: QByteArray is an \l{implicitly shared} class. Consequently, - if you prepend to an empty byte array, then the byte array will just - share the data held in \a ba. In this case, no copying of data is done, - taking \l{constant time}. If a shared instance is modified, it will - be copied (copy-on-write), taking \l{linear time}. - - If the byte array being prepended to is not empty, a deep copy of the - data is performed, taking \l{linear time}. - - \sa append(), insert() -*/ - -QByteArray &QByteArray::prepend(const QByteArray &ba) -{ - if (d->size == 0 && d->ref.isStatic() && !IS_RAW_DATA(ba.d)) { - *this = ba; - } else if (ba.d->size != 0) { - QByteArray tmp = *this; - *this = ba; - append(tmp); - } - return *this; -} - -/*! - \overload - - Prepends the string \a str to this byte array. -*/ - -QByteArray &QByteArray::prepend(const char *str) -{ - return prepend(str, qstrlen(str)); -} - -/*! - \overload - \since 4.6 - - Prepends \a len bytes of the string \a str to this byte array. -*/ - -QByteArray &QByteArray::prepend(const char *str, int len) -{ - if (str) { - if (d->ref.isShared() || uint(d->size + len) + 1u > d->alloc) - reallocData(uint(d->size + len) + 1u, d->detachFlags() | Data::Grow); - memmove(d->data()+len, d->data(), d->size); - memcpy(d->data(), str, len); - d->size += len; - d->data()[d->size] = '\0'; - } - return *this; -} - -/*! \fn QByteArray &QByteArray::prepend(int count, char ch) - - \overload - \since 5.7 - - Prepends \a count copies of character \a ch to this byte array. -*/ - -/*! - \overload - - Prepends the character \a ch to this byte array. -*/ - -QByteArray &QByteArray::prepend(char ch) -{ - if (d->ref.isShared() || uint(d->size) + 2u > d->alloc) - reallocData(uint(d->size) + 2u, d->detachFlags() | Data::Grow); - memmove(d->data()+1, d->data(), d->size); - d->data()[0] = ch; - ++d->size; - d->data()[d->size] = '\0'; - return *this; -} - -/*! - Appends the byte array \a ba onto the end of this byte array. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 16 - - This is the same as insert(size(), \a ba). - - Note: QByteArray is an \l{implicitly shared} class. Consequently, - if you append to an empty byte array, then the byte array will just - share the data held in \a ba. In this case, no copying of data is done, - taking \l{constant time}. If a shared instance is modified, it will - be copied (copy-on-write), taking \l{linear time}. - - If the byte array being appended to is not empty, a deep copy of the - data is performed, taking \l{linear time}. - - This operation typically does not suffer from allocation overhead, - because QByteArray preallocates extra space at the end of the data - so that it may grow without reallocating for each append operation. - - \sa operator+=(), prepend(), insert() -*/ - -QByteArray &QByteArray::append(const QByteArray &ba) -{ - if (d->size == 0 && d->ref.isStatic() && !IS_RAW_DATA(ba.d)) { - *this = ba; - } else if (ba.d->size != 0) { - if (d->ref.isShared() || uint(d->size + ba.d->size) + 1u > d->alloc) - reallocData(uint(d->size + ba.d->size) + 1u, d->detachFlags() | Data::Grow); - memcpy(d->data() + d->size, ba.d->data(), ba.d->size); - d->size += ba.d->size; - d->data()[d->size] = '\0'; - } - return *this; -} - -/*! \fn QByteArray &QByteArray::append(const QString &str) - - \overload - - Appends the string \a str to this byte array. The Unicode data is - converted into 8-bit characters using QString::toUtf8(). - - You can disable this function by defining \c QT_NO_CAST_TO_ASCII when you - compile your applications. You then need to call QString::toUtf8() (or - QString::toLatin1() or QString::toLocal8Bit()) explicitly if you want to - convert the data to \c{const char *}. -*/ - -/*! - \overload - - Appends the string \a str to this byte array. -*/ - -QByteArray& QByteArray::append(const char *str) -{ - if (str) { - const int len = int(strlen(str)); - if (d->ref.isShared() || uint(d->size + len) + 1u > d->alloc) - reallocData(uint(d->size + len) + 1u, d->detachFlags() | Data::Grow); - memcpy(d->data() + d->size, str, len + 1); // include null terminator - d->size += len; - } - return *this; -} - -/*! - \overload append() - - Appends the first \a len characters of the string \a str to this byte - array and returns a reference to this byte array. - - If \a len is negative, the length of the string will be determined - automatically using qstrlen(). If \a len is zero or \a str is - null, nothing is appended to the byte array. Ensure that \a len is - \e not longer than \a str. -*/ - -QByteArray &QByteArray::append(const char *str, int len) -{ - if (len < 0) - len = qstrlen(str); - if (str && len) { - if (d->ref.isShared() || uint(d->size + len) + 1u > d->alloc) - reallocData(uint(d->size + len) + 1u, d->detachFlags() | Data::Grow); - memcpy(d->data() + d->size, str, len); // include null terminator - d->size += len; - d->data()[d->size] = '\0'; - } - return *this; -} - -/*! \fn QByteArray &QByteArray::append(int count, char ch) - - \overload - \since 5.7 - - Appends \a count copies of character \a ch to this byte - array and returns a reference to this byte array. - - If \a count is negative or zero nothing is appended to the byte array. -*/ - -/*! - \overload - - Appends the character \a ch to this byte array. -*/ - -QByteArray& QByteArray::append(char ch) -{ - if (d->ref.isShared() || uint(d->size) + 2u > d->alloc) - reallocData(uint(d->size) + 2u, d->detachFlags() | Data::Grow); - d->data()[d->size++] = ch; - d->data()[d->size] = '\0'; - return *this; -} - -/*! - \internal - Inserts \a len bytes from the array \a arr at position \a pos and returns a - reference the modified byte array. -*/ -static inline QByteArray &qbytearray_insert(QByteArray *ba, - int pos, const char *arr, int len) -{ - Q_ASSERT(pos >= 0); - - if (pos < 0 || len <= 0 || arr == nullptr) - return *ba; - - int oldsize = ba->size(); - ba->resize(qMax(pos, oldsize) + len); - char *dst = ba->data(); - if (pos > oldsize) - ::memset(dst + oldsize, 0x20, pos - oldsize); - else - ::memmove(dst + pos + len, dst + pos, oldsize - pos); - memcpy(dst + pos, arr, len); - return *ba; -} - -/*! - Inserts the byte array \a ba at index position \a i and returns a - reference to this byte array. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 17 - - \sa append(), prepend(), replace(), remove() -*/ - -QByteArray &QByteArray::insert(int i, const QByteArray &ba) -{ - QByteArray copy(ba); - return qbytearray_insert(this, i, copy.d->data(), copy.d->size); -} - -/*! - \fn QByteArray &QByteArray::insert(int i, const QString &str) - - \overload - - Inserts the string \a str at index position \a i in the byte - array. The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - If \a i is greater than size(), the array is first extended using - resize(). - - You can disable this function by defining \c QT_NO_CAST_TO_ASCII when you - compile your applications. You then need to call QString::toUtf8() (or - QString::toLatin1() or QString::toLocal8Bit()) explicitly if you want to - convert the data to \c{const char *}. -*/ - -/*! - \overload - - Inserts the string \a str at position \a i in the byte array. - - If \a i is greater than size(), the array is first extended using - resize(). -*/ - -QByteArray &QByteArray::insert(int i, const char *str) -{ - return qbytearray_insert(this, i, str, qstrlen(str)); -} - -/*! - \overload - \since 4.6 - - Inserts \a len bytes of the string \a str at position - \a i in the byte array. - - If \a i is greater than size(), the array is first extended using - resize(). -*/ - -QByteArray &QByteArray::insert(int i, const char *str, int len) -{ - return qbytearray_insert(this, i, str, len); -} - -/*! - \overload - - Inserts character \a ch at index position \a i in the byte array. - If \a i is greater than size(), the array is first extended using - resize(). -*/ - -QByteArray &QByteArray::insert(int i, char ch) -{ - return qbytearray_insert(this, i, &ch, 1); -} - -/*! \fn QByteArray &QByteArray::insert(int i, int count, char ch) - - \overload - \since 5.7 - - Inserts \a count copies of character \a ch at index position \a i in the - byte array. - - If \a i is greater than size(), the array is first extended using resize(). -*/ - -QByteArray &QByteArray::insert(int i, int count, char ch) -{ - if (i < 0 || count <= 0) - return *this; - - int oldsize = size(); - resize(qMax(i, oldsize) + count); - char *dst = d->data(); - if (i > oldsize) - ::memset(dst + oldsize, 0x20, i - oldsize); - else if (i < oldsize) - ::memmove(dst + i + count, dst + i, oldsize - i); - ::memset(dst + i, ch, count); - return *this; -} - -/*! - Removes \a len bytes from the array, starting at index position \a - pos, and returns a reference to the array. - - If \a pos is out of range, nothing happens. If \a pos is valid, - but \a pos + \a len is larger than the size of the array, the - array is truncated at position \a pos. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 18 - - \sa insert(), replace() -*/ - -QByteArray &QByteArray::remove(int pos, int len) -{ - if (len <= 0 || uint(pos) >= uint(d->size)) - return *this; - detach(); - if (len >= d->size - pos) { - resize(pos); - } else { - memmove(d->data() + pos, d->data() + pos + len, d->size - pos - len); - resize(d->size - len); - } - return *this; -} - -/*! - Replaces \a len bytes from index position \a pos with the byte - array \a after, and returns a reference to this byte array. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 19 - - \sa insert(), remove() -*/ - -QByteArray &QByteArray::replace(int pos, int len, const QByteArray &after) -{ - if (len == after.d->size && (pos + len <= d->size)) { - detach(); - memmove(d->data() + pos, after.d->data(), len*sizeof(char)); - return *this; - } else { - QByteArray copy(after); - // ### optimize me - remove(pos, len); - return insert(pos, copy); - } -} - -/*! \fn QByteArray &QByteArray::replace(int pos, int len, const char *after) - - \overload - - Replaces \a len bytes from index position \a pos with the - '\\0'-terminated string \a after. - - Notice: this can change the length of the byte array. -*/ -QByteArray &QByteArray::replace(int pos, int len, const char *after) -{ - return replace(pos,len,after,qstrlen(after)); -} - -/*! \fn QByteArray &QByteArray::replace(int pos, int len, const char *after, int alen) - - \overload - - Replaces \a len bytes from index position \a pos with \a alen bytes - from the string \a after. \a after is allowed to have '\\0' characters. - - \since 4.7 -*/ -QByteArray &QByteArray::replace(int pos, int len, const char *after, int alen) -{ - if (len == alen && (pos + len <= d->size)) { - detach(); - memcpy(d->data() + pos, after, len*sizeof(char)); - return *this; - } else { - remove(pos, len); - return qbytearray_insert(this, pos, after, alen); - } -} - -// ### optimize all other replace method, by offering -// QByteArray::replace(const char *before, int blen, const char *after, int alen) - -/*! - \overload - - Replaces every occurrence of the byte array \a before with the - byte array \a after. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 20 -*/ - -QByteArray &QByteArray::replace(const QByteArray &before, const QByteArray &after) -{ - if (isNull() || before.d == after.d) - return *this; - - QByteArray aft = after; - if (after.d == d) - aft.detach(); - - return replace(before.constData(), before.size(), aft.constData(), aft.size()); -} - -/*! - \fn QByteArray &QByteArray::replace(const char *before, const QByteArray &after) - \overload - - Replaces every occurrence of the string \a before with the - byte array \a after. -*/ - -QByteArray &QByteArray::replace(const char *c, const QByteArray &after) -{ - QByteArray aft = after; - if (after.d == d) - aft.detach(); - - return replace(c, qstrlen(c), aft.constData(), aft.size()); -} - -/*! - \fn QByteArray &QByteArray::replace(const char *before, int bsize, const char *after, int asize) - \overload - - Replaces every occurrence of the string \a before with the string \a after. - Since the sizes of the strings are given by \a bsize and \a asize, they - may contain zero characters and do not need to be '\\0'-terminated. -*/ - -QByteArray &QByteArray::replace(const char *before, int bsize, const char *after, int asize) -{ - if (isNull() || (before == after && bsize == asize)) - return *this; - - // protect against before or after being part of this - const char *a = after; - const char *b = before; - if (after >= d->data() && after < d->data() + d->size) { - char *copy = (char *)malloc(asize); - Q_CHECK_PTR(copy); - memcpy(copy, after, asize); - a = copy; - } - if (before >= d->data() && before < d->data() + d->size) { - char *copy = (char *)malloc(bsize); - Q_CHECK_PTR(copy); - memcpy(copy, before, bsize); - b = copy; - } - - QByteArrayMatcher matcher(before, bsize); - int index = 0; - int len = d->size; - char *d = data(); - - if (bsize == asize) { - if (bsize) { - while ((index = matcher.indexIn(*this, index)) != -1) { - memcpy(d + index, after, asize); - index += bsize; - } - } - } else if (asize < bsize) { - uint to = 0; - uint movestart = 0; - uint num = 0; - while ((index = matcher.indexIn(*this, index)) != -1) { - if (num) { - int msize = index - movestart; - if (msize > 0) { - memmove(d + to, d + movestart, msize); - to += msize; - } - } else { - to = index; - } - if (asize) { - memcpy(d + to, after, asize); - to += asize; - } - index += bsize; - movestart = index; - num++; - } - if (num) { - int msize = len - movestart; - if (msize > 0) - memmove(d + to, d + movestart, msize); - resize(len - num*(bsize-asize)); - } - } else { - // the most complex case. We don't want to lose performance by doing repeated - // copies and reallocs of the string. - while (index != -1) { - uint indices[4096]; - uint pos = 0; - while(pos < 4095) { - index = matcher.indexIn(*this, index); - if (index == -1) - break; - indices[pos++] = index; - index += bsize; - // avoid infinite loop - if (!bsize) - index++; - } - if (!pos) - break; - - // we have a table of replacement positions, use them for fast replacing - int adjust = pos*(asize-bsize); - // index has to be adjusted in case we get back into the loop above. - if (index != -1) - index += adjust; - int newlen = len + adjust; - int moveend = len; - if (newlen > len) { - resize(newlen); - len = newlen; - } - d = this->d->data(); - - while(pos) { - pos--; - int movestart = indices[pos] + bsize; - int insertstart = indices[pos] + pos*(asize-bsize); - int moveto = insertstart + asize; - memmove(d + moveto, d + movestart, (moveend - movestart)); - if (asize) - memcpy(d + insertstart, after, asize); - moveend = movestart - bsize; - } - } - } - - if (a != after) - ::free(const_cast<char *>(a)); - if (b != before) - ::free(const_cast<char *>(b)); - - - return *this; -} - - -/*! - \fn QByteArray &QByteArray::replace(const QByteArray &before, const char *after) - \overload - - Replaces every occurrence of the byte array \a before with the - string \a after. -*/ - -/*! \fn QByteArray &QByteArray::replace(const QString &before, const QByteArray &after) - - \overload - - Replaces every occurrence of the string \a before with the byte - array \a after. The Unicode data is converted into 8-bit - characters using QString::toUtf8(). - - You can disable this function by defining \c QT_NO_CAST_TO_ASCII when you - compile your applications. You then need to call QString::toUtf8() (or - QString::toLatin1() or QString::toLocal8Bit()) explicitly if you want to - convert the data to \c{const char *}. -*/ - -/*! \fn QByteArray &QByteArray::replace(const QString &before, const char *after) - \overload - - Replaces every occurrence of the string \a before with the string - \a after. -*/ - -/*! \fn QByteArray &QByteArray::replace(const char *before, const char *after) - - \overload - - Replaces every occurrence of the string \a before with the string - \a after. -*/ - -/*! - \overload - - Replaces every occurrence of the character \a before with the - byte array \a after. -*/ - -QByteArray &QByteArray::replace(char before, const QByteArray &after) -{ - char b[2] = { before, '\0' }; - QByteArray cb = fromRawData(b, 1); - return replace(cb, after); -} - -/*! \fn QByteArray &QByteArray::replace(char before, const QString &after) - - \overload - - Replaces every occurrence of the character \a before with the - string \a after. The Unicode data is converted into 8-bit - characters using QString::toUtf8(). - - You can disable this function by defining \c QT_NO_CAST_TO_ASCII when you - compile your applications. You then need to call QString::toUtf8() (or - QString::toLatin1() or QString::toLocal8Bit()) explicitly if you want to - convert the data to \c{const char *}. -*/ - -/*! \fn QByteArray &QByteArray::replace(char before, const char *after) - - \overload - - Replaces every occurrence of the character \a before with the - string \a after. -*/ - -/*! - \overload - - Replaces every occurrence of the character \a before with the - character \a after. -*/ - -QByteArray &QByteArray::replace(char before, char after) -{ - if (d->size) { - char *i = data(); - char *e = i + d->size; - for (; i != e; ++i) - if (*i == before) - * i = after; - } - return *this; -} - -/*! - Splits the byte array into subarrays wherever \a sep occurs, and - returns the list of those arrays. If \a sep does not match - anywhere in the byte array, split() returns a single-element list - containing this byte array. -*/ - -QList<QByteArray> QByteArray::split(char sep) const -{ - QList<QByteArray> list; - int start = 0; - int end; - while ((end = indexOf(sep, start)) != -1) { - list.append(mid(start, end - start)); - start = end + 1; - } - list.append(mid(start)); - return list; -} - -/*! - \since 4.5 - - Returns a copy of this byte array repeated the specified number of \a times. - - If \a times is less than 1, an empty byte array is returned. - - Example: - - \snippet code/src_corelib_tools_qbytearray.cpp 49 -*/ -QByteArray QByteArray::repeated(int times) const -{ - if (d->size == 0) - return *this; - - if (times <= 1) { - if (times == 1) - return *this; - return QByteArray(); - } - - const int resultSize = times * d->size; - - QByteArray result; - result.reserve(resultSize); - if (result.d->alloc != uint(resultSize) + 1u) - return QByteArray(); // not enough memory - - memcpy(result.d->data(), d->data(), d->size); - - int sizeSoFar = d->size; - char *end = result.d->data() + sizeSoFar; - - const int halfResultSize = resultSize >> 1; - while (sizeSoFar <= halfResultSize) { - memcpy(end, result.d->data(), sizeSoFar); - end += sizeSoFar; - sizeSoFar <<= 1; - } - memcpy(end, result.d->data(), resultSize - sizeSoFar); - result.d->data()[resultSize] = '\0'; - result.d->size = resultSize; - return result; -} - -#define REHASH(a) \ - if (ol_minus_1 < sizeof(uint) * CHAR_BIT) \ - hashHaystack -= (a) << ol_minus_1; \ - hashHaystack <<= 1 - -/*! - Returns the index position of the first occurrence of the byte - array \a ba in this byte array, searching forward from index - position \a from. Returns -1 if \a ba could not be found. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 21 - - \sa lastIndexOf(), contains(), count() -*/ - -int QByteArray::indexOf(const QByteArray &ba, int from) const -{ - const int ol = ba.d->size; - if (ol == 0) - return from; - if (ol == 1) - return indexOf(*ba.d->data(), from); - - const int l = d->size; - if (from > d->size || ol + from > l) - return -1; - - return qFindByteArray(d->data(), d->size, from, ba.d->data(), ol); -} - -/*! \fn int QByteArray::indexOf(const QString &str, int from) const - - \overload - - Returns the index position of the first occurrence of the string - \a str in the byte array, searching forward from index position - \a from. Returns -1 if \a str could not be found. - - The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - You can disable this function by defining \c QT_NO_CAST_TO_ASCII when you - compile your applications. You then need to call QString::toUtf8() (or - QString::toLatin1() or QString::toLocal8Bit()) explicitly if you want to - convert the data to \c{const char *}. -*/ - -/*! \fn int QByteArray::indexOf(const char *str, int from) const - - \overload - - Returns the index position of the first occurrence of the string - \a str in the byte array, searching forward from index position \a - from. Returns -1 if \a str could not be found. -*/ -int QByteArray::indexOf(const char *c, int from) const -{ - const int ol = qstrlen(c); - if (ol == 1) - return indexOf(*c, from); - - const int l = d->size; - if (from > d->size || ol + from > l) - return -1; - if (ol == 0) - return from; - - return qFindByteArray(d->data(), d->size, from, c, ol); -} - -/*! - \overload - - Returns the index position of the first occurrence of the - character \a ch in the byte array, searching forward from index - position \a from. Returns -1 if \a ch could not be found. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 22 - - \sa lastIndexOf(), contains() -*/ - -int QByteArray::indexOf(char ch, int from) const -{ - if (from < 0) - from = qMax(from + d->size, 0); - if (from < d->size) { - const char *n = d->data() + from - 1; - const char *e = d->data() + d->size; - while (++n != e) - if (*n == ch) - return n - d->data(); - } - return -1; -} - - -static int lastIndexOfHelper(const char *haystack, int l, const char *needle, int ol, int from) -{ - int delta = l - ol; - if (from < 0) - from = delta; - if (from < 0 || from > l) - return -1; - if (from > delta) - from = delta; - - const char *end = haystack; - haystack += from; - const uint ol_minus_1 = ol - 1; - const char *n = needle + ol_minus_1; - const char *h = haystack + ol_minus_1; - uint hashNeedle = 0, hashHaystack = 0; - int idx; - for (idx = 0; idx < ol; ++idx) { - hashNeedle = ((hashNeedle<<1) + *(n-idx)); - hashHaystack = ((hashHaystack<<1) + *(h-idx)); - } - hashHaystack -= *haystack; - while (haystack >= end) { - hashHaystack += *haystack; - if (hashHaystack == hashNeedle && memcmp(needle, haystack, ol) == 0) - return haystack - end; - --haystack; - REHASH(*(haystack + ol)); - } - return -1; - -} - -/*! - \fn int QByteArray::lastIndexOf(const QByteArray &ba, int from) const - - Returns the index position of the last occurrence of the byte - array \a ba in this byte array, searching backward from index - position \a from. If \a from is -1 (the default), the search - starts at the last byte. Returns -1 if \a ba could not be found. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 23 - - \sa indexOf(), contains(), count() -*/ - -int QByteArray::lastIndexOf(const QByteArray &ba, int from) const -{ - const int ol = ba.d->size; - if (ol == 1) - return lastIndexOf(*ba.d->data(), from); - - return lastIndexOfHelper(d->data(), d->size, ba.d->data(), ol, from); -} - -/*! \fn int QByteArray::lastIndexOf(const QString &str, int from) const - - \overload - - Returns the index position of the last occurrence of the string \a - str in the byte array, searching backward from index position \a - from. If \a from is -1 (the default), the search starts at the - last (size() - 1) byte. Returns -1 if \a str could not be found. - - The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - You can disable this function by defining \c QT_NO_CAST_TO_ASCII when you - compile your applications. You then need to call QString::toUtf8() (or - QString::toLatin1() or QString::toLocal8Bit()) explicitly if you want to - convert the data to \c{const char *}. -*/ - -/*! \fn int QByteArray::lastIndexOf(const char *str, int from) const - \overload - - Returns the index position of the last occurrence of the string \a - str in the byte array, searching backward from index position \a - from. If \a from is -1 (the default), the search starts at the - last (size() - 1) byte. Returns -1 if \a str could not be found. -*/ -int QByteArray::lastIndexOf(const char *str, int from) const -{ - const int ol = qstrlen(str); - if (ol == 1) - return lastIndexOf(*str, from); - - return lastIndexOfHelper(d->data(), d->size, str, ol, from); -} - -/*! - \overload - - Returns the index position of the last occurrence of character \a - ch in the byte array, searching backward from index position \a - from. If \a from is -1 (the default), the search starts at the - last (size() - 1) byte. Returns -1 if \a ch could not be found. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 24 - - \sa indexOf(), contains() -*/ - -int QByteArray::lastIndexOf(char ch, int from) const -{ - if (from < 0) - from += d->size; - else if (from > d->size) - from = d->size-1; - if (from >= 0) { - const char *b = d->data(); - const char *n = d->data() + from + 1; - while (n-- != b) - if (*n == ch) - return n - b; - } - return -1; -} - -/*! - Returns the number of (potentially overlapping) occurrences of - byte array \a ba in this byte array. - - \sa contains(), indexOf() -*/ - -int QByteArray::count(const QByteArray &ba) const -{ - int num = 0; - int i = -1; - if (d->size > 500 && ba.d->size > 5) { - QByteArrayMatcher matcher(ba); - while ((i = matcher.indexIn(*this, i + 1)) != -1) - ++num; - } else { - while ((i = indexOf(ba, i + 1)) != -1) - ++num; - } - return num; -} - -/*! - \overload - - Returns the number of (potentially overlapping) occurrences of - string \a str in the byte array. -*/ - -int QByteArray::count(const char *str) const -{ - return count(fromRawData(str, qstrlen(str))); -} - -/*! - \overload - - Returns the number of occurrences of character \a ch in the byte - array. - - \sa contains(), indexOf() -*/ - -int QByteArray::count(char ch) const -{ - int num = 0; - const char *i = d->data() + d->size; - const char *b = d->data(); - while (i != b) - if (*--i == ch) - ++num; - return num; -} - -/*! \fn int QByteArray::count() const - - \overload - - Same as size(). -*/ - -/*! - \fn int QByteArray::compare(const char *c, Qt::CaseSensitivity cs = Qt::CaseSensitive) const - \since 5.12 - - Returns an integer less than, equal to, or greater than zero depending on - whether this QByteArray sorts before, at the same position, or after the - string pointed to by \a c. The comparison is performed according to case - sensitivity \a cs. - - \sa operator== -*/ - -/*! - \fn int QByteArray::compare(const QByteArray &a, Qt::CaseSensitivity cs = Qt::CaseSensitive) const - \overload - \since 5.12 - - Returns an integer less than, equal to, or greater than zero depending on - whether this QByteArray sorts before, at the same position, or after the - QByteArray \a a. The comparison is performed according to case sensitivity - \a cs. - - \sa operator== -*/ - -/*! - Returns \c true if this byte array starts with byte array \a ba; - otherwise returns \c false. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 25 - - \sa endsWith(), left() -*/ -bool QByteArray::startsWith(const QByteArray &ba) const -{ - if (d == ba.d || ba.d->size == 0) - return true; - if (d->size < ba.d->size) - return false; - return memcmp(d->data(), ba.d->data(), ba.d->size) == 0; -} - -/*! \overload - - Returns \c true if this byte array starts with string \a str; - otherwise returns \c false. -*/ -bool QByteArray::startsWith(const char *str) const -{ - if (!str || !*str) - return true; - const int len = int(strlen(str)); - if (d->size < len) - return false; - return qstrncmp(d->data(), str, len) == 0; -} - -/*! \overload - - Returns \c true if this byte array starts with character \a ch; - otherwise returns \c false. -*/ -bool QByteArray::startsWith(char ch) const -{ - if (d->size == 0) - return false; - return d->data()[0] == ch; -} - -/*! - Returns \c true if this byte array ends with byte array \a ba; - otherwise returns \c false. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 26 - - \sa startsWith(), right() -*/ -bool QByteArray::endsWith(const QByteArray &ba) const -{ - if (d == ba.d || ba.d->size == 0) - return true; - if (d->size < ba.d->size) - return false; - return memcmp(d->data() + d->size - ba.d->size, ba.d->data(), ba.d->size) == 0; -} - -/*! \overload - - Returns \c true if this byte array ends with string \a str; otherwise - returns \c false. -*/ -bool QByteArray::endsWith(const char *str) const -{ - if (!str || !*str) - return true; - const int len = int(strlen(str)); - if (d->size < len) - return false; - return qstrncmp(d->data() + d->size - len, str, len) == 0; -} - -/* - Returns true if \a c is an uppercase Latin1 letter. - \note The multiplication sign 0xD7 and the sz ligature 0xDF are not - treated as uppercase Latin1. - */ -static inline bool isUpperCaseLatin1(char c) -{ - if (c >= 'A' && c <= 'Z') - return true; - - return (uchar(c) >= 0xC0 && uchar(c) <= 0xDE && uchar(c) != 0xD7); -} - -/*! - Returns \c true if this byte array contains only uppercase letters, - otherwise returns \c false. The byte array is interpreted as a Latin-1 - encoded string. - \since 5.12 - - \sa isLower(), toUpper() -*/ -bool QByteArray::isUpper() const -{ - if (isEmpty()) - return false; - - const char *d = data(); - - for (int i = 0, max = size(); i < max; ++i) { - if (!isUpperCaseLatin1(d[i])) - return false; - } - - return true; -} - -/* - Returns true if \a c is an lowercase Latin1 letter. - \note The division sign 0xF7 is not treated as lowercase Latin1, - but the small y dieresis 0xFF is. - */ -static inline bool isLowerCaseLatin1(char c) -{ - if (c >= 'a' && c <= 'z') - return true; - - return (uchar(c) >= 0xD0 && uchar(c) != 0xF7); -} - -/*! - Returns \c true if this byte array contains only lowercase letters, - otherwise returns \c false. The byte array is interpreted as a Latin-1 - encoded string. - \since 5.12 - - \sa isUpper(), toLower() - */ -bool QByteArray::isLower() const -{ - if (isEmpty()) - return false; - - const char *d = data(); - - for (int i = 0, max = size(); i < max; ++i) { - if (!isLowerCaseLatin1(d[i])) - return false; - } - - return true; -} - -/*! \overload - - Returns \c true if this byte array ends with character \a ch; - otherwise returns \c false. -*/ -bool QByteArray::endsWith(char ch) const -{ - if (d->size == 0) - return false; - return d->data()[d->size - 1] == ch; -} - -/*! - Returns a byte array that contains the leftmost \a len bytes of - this byte array. - - The entire byte array is returned if \a len is greater than - size(). - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 27 - - \sa startsWith(), right(), mid(), chopped(), chop(), truncate() -*/ - -QByteArray QByteArray::left(int len) const -{ - if (len >= d->size) - return *this; - if (len < 0) - len = 0; - return QByteArray(d->data(), len); -} - -/*! - Returns a byte array that contains the rightmost \a len bytes of - this byte array. - - The entire byte array is returned if \a len is greater than - size(). - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 28 - - \sa endsWith(), left(), mid(), chopped(), chop(), truncate() -*/ - -QByteArray QByteArray::right(int len) const -{ - if (len >= d->size) - return *this; - if (len < 0) - len = 0; - return QByteArray(d->data() + d->size - len, len); -} - -/*! - Returns a byte array containing \a len bytes from this byte array, - starting at position \a pos. - - If \a len is -1 (the default), or \a pos + \a len >= size(), - returns a byte array containing all bytes starting at position \a - pos until the end of the byte array. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 29 - - \sa left(), right(), chopped(), chop(), truncate() -*/ - -QByteArray QByteArray::mid(int pos, int len) const -{ - using namespace QtPrivate; - switch (QContainerImplHelper::mid(size(), &pos, &len)) { - case QContainerImplHelper::Null: - return QByteArray(); - case QContainerImplHelper::Empty: - { - QByteArrayDataPtr empty = { Data::allocate(0) }; - return QByteArray(empty); - } - case QContainerImplHelper::Full: - return *this; - case QContainerImplHelper::Subset: - return QByteArray(d->data() + pos, len); - } - Q_UNREACHABLE(); - return QByteArray(); -} - -/*! - \fn QByteArray::chopped(int len) const - \since 5.10 - - Returns a byte array that contains the leftmost size() - \a len bytes of - this byte array. - - \note The behavior is undefined if \a len is negative or greater than size(). - - \sa endsWith(), left(), right(), mid(), chop(), truncate() -*/ - -/*! - \fn QByteArray QByteArray::toLower() const - - Returns a lowercase copy of the byte array. The bytearray is - interpreted as a Latin-1 encoded string. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 30 - - \sa isLower(), toUpper(), {8-bit Character Comparisons} -*/ - -// prevent the compiler from inlining the function in each of -// toLower and toUpper when the only difference is the table being used -// (even with constant propagation, there's no gain in performance). -template <typename T> -Q_NEVER_INLINE -static QByteArray toCase_template(T &input, const uchar * table) -{ - // find the first bad character in input - const char *orig_begin = input.constBegin(); - const char *firstBad = orig_begin; - const char *e = input.constEnd(); - for ( ; firstBad != e ; ++firstBad) { - uchar ch = uchar(*firstBad); - uchar converted = table[ch]; - if (ch != converted) - break; - } - - if (firstBad == e) - return std::move(input); - - // transform the rest - QByteArray s = std::move(input); // will copy if T is const QByteArray - char *b = s.begin(); // will detach if necessary - char *p = b + (firstBad - orig_begin); - e = b + s.size(); - for ( ; p != e; ++p) { - *p = char(uchar(table[uchar(*p)])); - } - return s; -} - -QByteArray QByteArray::toLower_helper(const QByteArray &a) -{ - return toCase_template(a, latin1_lowercased); -} - -QByteArray QByteArray::toLower_helper(QByteArray &a) -{ - return toCase_template(a, latin1_lowercased); -} - -/*! - \fn QByteArray QByteArray::toUpper() const - - Returns an uppercase copy of the byte array. The bytearray is - interpreted as a Latin-1 encoded string. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 31 - - \sa isUpper(), toLower(), {8-bit Character Comparisons} -*/ - -QByteArray QByteArray::toUpper_helper(const QByteArray &a) -{ - return toCase_template(a, latin1_uppercased); -} - -QByteArray QByteArray::toUpper_helper(QByteArray &a) -{ - return toCase_template(a, latin1_uppercased); -} - -/*! \fn void QByteArray::clear() - - Clears the contents of the byte array and makes it null. - - \sa resize(), isNull() -*/ - -void QByteArray::clear() -{ - if (!d->ref.deref()) - Data::deallocate(d); - d = Data::sharedNull(); -} - -#if !defined(QT_NO_DATASTREAM) || (defined(QT_BOOTSTRAPPED) && !defined(QT_BUILD_QMAKE)) - -/*! \relates QByteArray - - Writes byte array \a ba to the stream \a out and returns a reference - to the stream. - - \sa {Serializing Qt Data Types} -*/ - -QDataStream &operator<<(QDataStream &out, const QByteArray &ba) -{ - if (ba.isNull() && out.version() >= 6) { - out << (quint32)0xffffffff; - return out; - } - return out.writeBytes(ba.constData(), ba.size()); -} - -/*! \relates QByteArray - - Reads a byte array into \a ba from the stream \a in and returns a - reference to the stream. - - \sa {Serializing Qt Data Types} -*/ - -QDataStream &operator>>(QDataStream &in, QByteArray &ba) -{ - ba.clear(); - quint32 len; - in >> len; - if (len == 0xffffffff) - return in; - - const quint32 Step = 1024 * 1024; - quint32 allocated = 0; - - do { - int blockSize = qMin(Step, len - allocated); - ba.resize(allocated + blockSize); - if (in.readRawData(ba.data() + allocated, blockSize) != blockSize) { - ba.clear(); - in.setStatus(QDataStream::ReadPastEnd); - return in; - } - allocated += blockSize; - } while (allocated < len); - - return in; -} -#endif // QT_NO_DATASTREAM - -/*! \fn bool QByteArray::operator==(const QString &str) const - - Returns \c true if this byte array is equal to string \a str; - otherwise returns \c false. - - The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - The comparison is case sensitive. - - You can disable this operator by defining \c - QT_NO_CAST_FROM_ASCII when you compile your applications. You - then need to call QString::fromUtf8(), QString::fromLatin1(), - or QString::fromLocal8Bit() explicitly if you want to convert the byte - array to a QString before doing the comparison. -*/ - -/*! \fn bool QByteArray::operator!=(const QString &str) const - - Returns \c true if this byte array is not equal to string \a str; - otherwise returns \c false. - - The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - The comparison is case sensitive. - - You can disable this operator by defining \c - QT_NO_CAST_FROM_ASCII when you compile your applications. You - then need to call QString::fromUtf8(), QString::fromLatin1(), - or QString::fromLocal8Bit() explicitly if you want to convert the byte - array to a QString before doing the comparison. -*/ - -/*! \fn bool QByteArray::operator<(const QString &str) const - - Returns \c true if this byte array is lexically less than string \a - str; otherwise returns \c false. - - The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - The comparison is case sensitive. - - You can disable this operator by defining \c - QT_NO_CAST_FROM_ASCII when you compile your applications. You - then need to call QString::fromUtf8(), QString::fromLatin1(), - or QString::fromLocal8Bit() explicitly if you want to convert the byte - array to a QString before doing the comparison. -*/ - -/*! \fn bool QByteArray::operator>(const QString &str) const - - Returns \c true if this byte array is lexically greater than string - \a str; otherwise returns \c false. - - The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - The comparison is case sensitive. - - You can disable this operator by defining \c - QT_NO_CAST_FROM_ASCII when you compile your applications. You - then need to call QString::fromUtf8(), QString::fromLatin1(), - or QString::fromLocal8Bit() explicitly if you want to convert the byte - array to a QString before doing the comparison. -*/ - -/*! \fn bool QByteArray::operator<=(const QString &str) const - - Returns \c true if this byte array is lexically less than or equal - to string \a str; otherwise returns \c false. - - The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - The comparison is case sensitive. - - You can disable this operator by defining \c - QT_NO_CAST_FROM_ASCII when you compile your applications. You - then need to call QString::fromUtf8(), QString::fromLatin1(), - or QString::fromLocal8Bit() explicitly if you want to convert the byte - array to a QString before doing the comparison. -*/ - -/*! \fn bool QByteArray::operator>=(const QString &str) const - - Returns \c true if this byte array is greater than or equal to string - \a str; otherwise returns \c false. - - The Unicode data is converted into 8-bit characters using - QString::toUtf8(). - - The comparison is case sensitive. - - You can disable this operator by defining \c - QT_NO_CAST_FROM_ASCII when you compile your applications. You - then need to call QString::fromUtf8(), QString::fromLatin1(), - or QString::fromLocal8Bit() explicitly if you want to convert the byte - array to a QString before doing the comparison. -*/ - -/*! \fn bool operator==(const QByteArray &a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is equal to byte array \a a2; - otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator==(const QByteArray &a1, const char *a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is equal to string \a a2; - otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator==(const char *a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if string \a a1 is equal to byte array \a a2; - otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator!=(const QByteArray &a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is not equal to byte array \a a2; - otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator!=(const QByteArray &a1, const char *a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is not equal to string \a a2; - otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator!=(const char *a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if string \a a1 is not equal to byte array \a a2; - otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator<(const QByteArray &a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is lexically less than byte array - \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn inline bool operator<(const QByteArray &a1, const char *a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is lexically less than string - \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator<(const char *a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if string \a a1 is lexically less than byte array - \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator<=(const QByteArray &a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is lexically less than or equal - to byte array \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator<=(const QByteArray &a1, const char *a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is lexically less than or equal - to string \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator<=(const char *a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if string \a a1 is lexically less than or equal - to byte array \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator>(const QByteArray &a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is lexically greater than byte - array \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator>(const QByteArray &a1, const char *a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is lexically greater than string - \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator>(const char *a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if string \a a1 is lexically greater than byte array - \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator>=(const QByteArray &a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is lexically greater than or - equal to byte array \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator>=(const QByteArray &a1, const char *a2) - \relates QByteArray - - \overload - - Returns \c true if byte array \a a1 is lexically greater than or - equal to string \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn bool operator>=(const char *a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns \c true if string \a a1 is lexically greater than or - equal to byte array \a a2; otherwise returns \c false. - - \sa QByteArray::compare() -*/ - -/*! \fn const QByteArray operator+(const QByteArray &a1, const QByteArray &a2) - \relates QByteArray - - Returns a byte array that is the result of concatenating byte - array \a a1 and byte array \a a2. - - \sa QByteArray::operator+=() -*/ - -/*! \fn const QByteArray operator+(const QByteArray &a1, const char *a2) - \relates QByteArray - - \overload - - Returns a byte array that is the result of concatenating byte - array \a a1 and string \a a2. -*/ - -/*! \fn const QByteArray operator+(const QByteArray &a1, char a2) - \relates QByteArray - - \overload - - Returns a byte array that is the result of concatenating byte - array \a a1 and character \a a2. -*/ - -/*! \fn const QByteArray operator+(const char *a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns a byte array that is the result of concatenating string - \a a1 and byte array \a a2. -*/ - -/*! \fn const QByteArray operator+(char a1, const QByteArray &a2) - \relates QByteArray - - \overload - - Returns a byte array that is the result of concatenating character - \a a1 and byte array \a a2. -*/ - -/*! - \fn QByteArray QByteArray::simplified() const - - Returns a byte array that has whitespace removed from the start - and the end, and which has each sequence of internal whitespace - replaced with a single space. - - Whitespace means any character for which the standard C++ - \c isspace() function returns \c true in the C locale. This includes the ASCII - isspace() function returns \c true in the C locale. This includes the ASCII - characters '\\t', '\\n', '\\v', '\\f', '\\r', and ' '. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 32 - - \sa trimmed() -*/ -QByteArray QByteArray::simplified_helper(const QByteArray &a) -{ - return QStringAlgorithms<const QByteArray>::simplified_helper(a); -} - -QByteArray QByteArray::simplified_helper(QByteArray &a) -{ - return QStringAlgorithms<QByteArray>::simplified_helper(a); -} - -/*! - \fn QByteArray QByteArray::trimmed() const - - Returns a byte array that has whitespace removed from the start - and the end. - - Whitespace means any character for which the standard C++ - \c isspace() function returns \c true in the C locale. This includes the ASCII - characters '\\t', '\\n', '\\v', '\\f', '\\r', and ' '. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 33 - - Unlike simplified(), \l {QByteArray::trimmed()}{trimmed()} leaves internal whitespace alone. - - \sa simplified() -*/ -QByteArray QByteArray::trimmed_helper(const QByteArray &a) -{ - return QStringAlgorithms<const QByteArray>::trimmed_helper(a); -} - -QByteArray QByteArray::trimmed_helper(QByteArray &a) -{ - return QStringAlgorithms<QByteArray>::trimmed_helper(a); -} - - -/*! - Returns a byte array of size \a width that contains this byte - array padded by the \a fill character. - - If \a truncate is false and the size() of the byte array is more - than \a width, then the returned byte array is a copy of this byte - array. - - If \a truncate is true and the size() of the byte array is more - than \a width, then any bytes in a copy of the byte array - after position \a width are removed, and the copy is returned. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 34 - - \sa rightJustified() -*/ - -QByteArray QByteArray::leftJustified(int width, char fill, bool truncate) const -{ - QByteArray result; - int len = d->size; - int padlen = width - len; - if (padlen > 0) { - result.resize(len+padlen); - if (len) - memcpy(result.d->data(), d->data(), len); - memset(result.d->data()+len, fill, padlen); - } else { - if (truncate) - result = left(width); - else - result = *this; - } - return result; -} - -/*! - Returns a byte array of size \a width that contains the \a fill - character followed by this byte array. - - If \a truncate is false and the size of the byte array is more - than \a width, then the returned byte array is a copy of this byte - array. - - If \a truncate is true and the size of the byte array is more - than \a width, then the resulting byte array is truncated at - position \a width. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 35 - - \sa leftJustified() -*/ - -QByteArray QByteArray::rightJustified(int width, char fill, bool truncate) const -{ - QByteArray result; - int len = d->size; - int padlen = width - len; - if (padlen > 0) { - result.resize(len+padlen); - if (len) - memcpy(result.d->data()+padlen, data(), len); - memset(result.d->data(), fill, padlen); - } else { - if (truncate) - result = left(width); - else - result = *this; - } - return result; -} - -bool QByteArray::isNull() const { return d == QArrayData::sharedNull(); } - -static qlonglong toIntegral_helper(const char *data, bool *ok, int base, qlonglong) -{ - return QLocaleData::bytearrayToLongLong(data, base, ok); -} - -static qulonglong toIntegral_helper(const char *data, bool *ok, int base, qulonglong) -{ - return QLocaleData::bytearrayToUnsLongLong(data, base, ok); -} - -template <typename T> static inline -T toIntegral_helper(const char *data, bool *ok, int base) -{ - using Int64 = typename std::conditional<std::is_unsigned<T>::value, qulonglong, qlonglong>::type; - -#if defined(QT_CHECK_RANGE) - if (base != 0 && (base < 2 || base > 36)) { - qWarning("QByteArray::toIntegral: Invalid base %d", base); - base = 10; - } -#endif - - // we select the right overload by the last, unused parameter - Int64 val = toIntegral_helper(data, ok, base, Int64()); - if (T(val) != val) { - if (ok) - *ok = false; - val = 0; - } - return T(val); -} - -/*! - Returns the byte array converted to a \c {long long} using base \a - base, which is 10 by default and must be between 2 and 36, or 0. - - If \a base is 0, the base is determined automatically using the - following rules: If the byte array begins with "0x", it is assumed to - be hexadecimal; if it begins with "0", it is assumed to be octal; - otherwise it is assumed to be decimal. - - Returns 0 if the conversion fails. - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - \sa number() -*/ - -qlonglong QByteArray::toLongLong(bool *ok, int base) const -{ - return toIntegral_helper<qlonglong>(nulTerminated().constData(), ok, base); -} - -/*! - Returns the byte array converted to an \c {unsigned long long} - using base \a base, which is 10 by default and must be between 2 - and 36, or 0. - - If \a base is 0, the base is determined automatically using the - following rules: If the byte array begins with "0x", it is assumed to - be hexadecimal; if it begins with "0", it is assumed to be octal; - otherwise it is assumed to be decimal. - - Returns 0 if the conversion fails. - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - \sa number() -*/ - -qulonglong QByteArray::toULongLong(bool *ok, int base) const -{ - return toIntegral_helper<qulonglong>(nulTerminated().constData(), ok, base); -} - -/*! - Returns the byte array converted to an \c int using base \a - base, which is 10 by default and must be between 2 and 36, or 0. - - If \a base is 0, the base is determined automatically using the - following rules: If the byte array begins with "0x", it is assumed to - be hexadecimal; if it begins with "0", it is assumed to be octal; - otherwise it is assumed to be decimal. - - Returns 0 if the conversion fails. - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \snippet code/src_corelib_tools_qbytearray.cpp 36 - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - \sa number() -*/ - -int QByteArray::toInt(bool *ok, int base) const -{ - return toIntegral_helper<int>(nulTerminated().constData(), ok, base); -} - -/*! - Returns the byte array converted to an \c {unsigned int} using base \a - base, which is 10 by default and must be between 2 and 36, or 0. - - If \a base is 0, the base is determined automatically using the - following rules: If the byte array begins with "0x", it is assumed to - be hexadecimal; if it begins with "0", it is assumed to be octal; - otherwise it is assumed to be decimal. - - Returns 0 if the conversion fails. - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - \sa number() -*/ - -uint QByteArray::toUInt(bool *ok, int base) const -{ - return toIntegral_helper<uint>(nulTerminated().constData(), ok, base); -} - -/*! - \since 4.1 - - Returns the byte array converted to a \c long int using base \a - base, which is 10 by default and must be between 2 and 36, or 0. - - If \a base is 0, the base is determined automatically using the - following rules: If the byte array begins with "0x", it is assumed to - be hexadecimal; if it begins with "0", it is assumed to be octal; - otherwise it is assumed to be decimal. - - Returns 0 if the conversion fails. - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \snippet code/src_corelib_tools_qbytearray.cpp 37 - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - \sa number() -*/ -long QByteArray::toLong(bool *ok, int base) const -{ - return toIntegral_helper<long>(nulTerminated().constData(), ok, base); -} - -/*! - \since 4.1 - - Returns the byte array converted to an \c {unsigned long int} using base \a - base, which is 10 by default and must be between 2 and 36, or 0. - - If \a base is 0, the base is determined automatically using the - following rules: If the byte array begins with "0x", it is assumed to - be hexadecimal; if it begins with "0", it is assumed to be octal; - otherwise it is assumed to be decimal. - - Returns 0 if the conversion fails. - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - \sa number() -*/ -ulong QByteArray::toULong(bool *ok, int base) const -{ - return toIntegral_helper<ulong>(nulTerminated().constData(), ok, base); -} - -/*! - Returns the byte array converted to a \c short using base \a - base, which is 10 by default and must be between 2 and 36, or 0. - - If \a base is 0, the base is determined automatically using the - following rules: If the byte array begins with "0x", it is assumed to - be hexadecimal; if it begins with "0", it is assumed to be octal; - otherwise it is assumed to be decimal. - - Returns 0 if the conversion fails. - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - \sa number() -*/ - -short QByteArray::toShort(bool *ok, int base) const -{ - return toIntegral_helper<short>(nulTerminated().constData(), ok, base); -} - -/*! - Returns the byte array converted to an \c {unsigned short} using base \a - base, which is 10 by default and must be between 2 and 36, or 0. - - If \a base is 0, the base is determined automatically using the - following rules: If the byte array begins with "0x", it is assumed to - be hexadecimal; if it begins with "0", it is assumed to be octal; - otherwise it is assumed to be decimal. - - Returns 0 if the conversion fails. - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - \sa number() -*/ - -ushort QByteArray::toUShort(bool *ok, int base) const -{ - return toIntegral_helper<ushort>(nulTerminated().constData(), ok, base); -} - - -/*! - Returns the byte array converted to a \c double value. - - Returns an infinity if the conversion overflows or 0.0 if the - conversion fails for other reasons (e.g. underflow). - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \snippet code/src_corelib_tools_qbytearray.cpp 38 - - \warning The QByteArray content may only contain valid numerical characters - which includes the plus/minus sign, the character e used in scientific - notation, and the decimal point. Including the unit or additional characters - leads to a conversion error. - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - This function ignores leading and trailing whitespace. - - \sa number() -*/ - -double QByteArray::toDouble(bool *ok) const -{ - bool nonNullOk = false; - int processed = 0; - double d = qt_asciiToDouble(constData(), size(), - nonNullOk, processed, WhitespacesAllowed); - if (ok) - *ok = nonNullOk; - return d; -} - -/*! - Returns the byte array converted to a \c float value. - - Returns an infinity if the conversion overflows or 0.0 if the - conversion fails for other reasons (e.g. underflow). - - If \a ok is not \nullptr, failure is reported by setting *\a{ok} - to \c false, and success by setting *\a{ok} to \c true. - - \snippet code/src_corelib_tools_qbytearray.cpp 38float - - \warning The QByteArray content may only contain valid numerical characters - which includes the plus/minus sign, the character e used in scientific - notation, and the decimal point. Including the unit or additional characters - leads to a conversion error. - - \note The conversion of the number is performed in the default C locale, - irrespective of the user's locale. - - This function ignores leading and trailing whitespace. - - \sa number() -*/ - -float QByteArray::toFloat(bool *ok) const -{ - return QLocaleData::convertDoubleToFloat(toDouble(ok), ok); -} - -/*! - Returns a copy of the byte array, encoded as Base64. - - \snippet code/src_corelib_tools_qbytearray.cpp 39 - - The algorithm used to encode Base64-encoded data is defined in \l{RFC 4648}. - - \sa fromBase64() -*/ -QByteArray QByteArray::toBase64() const -{ - return toBase64(Base64Encoding); -} - -/*! - \since 5.2 - \overload - - Returns a copy of the byte array, encoded using the options \a options. - - \snippet code/src_corelib_tools_qbytearray.cpp 39bis - - The algorithm used to encode Base64-encoded data is defined in \l{RFC 4648}. - - \sa fromBase64() -*/ -QByteArray QByteArray::toBase64(Base64Options options) const -{ - const char alphabet_base64[] = "ABCDEFGH" "IJKLMNOP" "QRSTUVWX" "YZabcdef" - "ghijklmn" "opqrstuv" "wxyz0123" "456789+/"; - const char alphabet_base64url[] = "ABCDEFGH" "IJKLMNOP" "QRSTUVWX" "YZabcdef" - "ghijklmn" "opqrstuv" "wxyz0123" "456789-_"; - const char *const alphabet = options & Base64UrlEncoding ? alphabet_base64url : alphabet_base64; - const char padchar = '='; - int padlen = 0; - - QByteArray tmp((d->size + 2) / 3 * 4, Qt::Uninitialized); - - int i = 0; - char *out = tmp.data(); - while (i < d->size) { - // encode 3 bytes at a time - int chunk = 0; - chunk |= int(uchar(d->data()[i++])) << 16; - if (i == d->size) { - padlen = 2; - } else { - chunk |= int(uchar(d->data()[i++])) << 8; - if (i == d->size) - padlen = 1; - else - chunk |= int(uchar(data()[i++])); - } - - int j = (chunk & 0x00fc0000) >> 18; - int k = (chunk & 0x0003f000) >> 12; - int l = (chunk & 0x00000fc0) >> 6; - int m = (chunk & 0x0000003f); - *out++ = alphabet[j]; - *out++ = alphabet[k]; - - if (padlen > 1) { - if ((options & OmitTrailingEquals) == 0) - *out++ = padchar; - } else { - *out++ = alphabet[l]; - } - if (padlen > 0) { - if ((options & OmitTrailingEquals) == 0) - *out++ = padchar; - } else { - *out++ = alphabet[m]; - } - } - Q_ASSERT((options & OmitTrailingEquals) || (out == tmp.size() + tmp.data())); - if (options & OmitTrailingEquals) - tmp.truncate(out - tmp.data()); - return tmp; -} - -/*! - \fn QByteArray &QByteArray::setNum(int n, int base) - - Sets the byte array to the printed value of \a n in base \a base (10 - by default) and returns a reference to the byte array. The \a base can - be any value between 2 and 36. For bases other than 10, n is treated - as an unsigned integer. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 40 - - \note The format of the number is not localized; the default C locale - is used irrespective of the user's locale. - - \sa number(), toInt() -*/ - -/*! - \fn QByteArray &QByteArray::setNum(uint n, int base) - \overload - - \sa toUInt() -*/ - -/*! - \fn QByteArray &QByteArray::setNum(short n, int base) - \overload - - \sa toShort() -*/ - -/*! - \fn QByteArray &QByteArray::setNum(ushort n, int base) - \overload - - \sa toUShort() -*/ - -static char *qulltoa2(char *p, qulonglong n, int base) -{ -#if defined(QT_CHECK_RANGE) - if (base < 2 || base > 36) { - qWarning("QByteArray::setNum: Invalid base %d", base); - base = 10; - } -#endif - const char b = 'a' - 10; - do { - const int c = n % base; - n /= base; - *--p = c + (c < 10 ? '0' : b); - } while (n); - - return p; -} - -/*! - \overload - - \sa toLongLong() -*/ -QByteArray &QByteArray::setNum(qlonglong n, int base) -{ - const int buffsize = 66; // big enough for MAX_ULLONG in base 2 - char buff[buffsize]; - char *p; - - if (n < 0 && base == 10) { - p = qulltoa2(buff + buffsize, qulonglong(-(1 + n)) + 1, base); - *--p = '-'; - } else { - p = qulltoa2(buff + buffsize, qulonglong(n), base); - } - - clear(); - append(p, buffsize - (p - buff)); - return *this; -} - -/*! - \overload - - \sa toULongLong() -*/ - -QByteArray &QByteArray::setNum(qulonglong n, int base) -{ - const int buffsize = 66; // big enough for MAX_ULLONG in base 2 - char buff[buffsize]; - char *p = qulltoa2(buff + buffsize, n, base); - - clear(); - append(p, buffsize - (p - buff)); - return *this; -} - -/*! - \overload - - Sets the byte array to the printed value of \a n, formatted in format - \a f with precision \a prec, and returns a reference to the - byte array. - - The format \a f can be any of the following: - - \table - \header \li Format \li Meaning - \row \li \c e \li format as [-]9.9e[+|-]999 - \row \li \c E \li format as [-]9.9E[+|-]999 - \row \li \c f \li format as [-]9.9 - \row \li \c g \li use \c e or \c f format, whichever is the most concise - \row \li \c G \li use \c E or \c f format, whichever is the most concise - \endtable - - With 'e', 'E', and 'f', \a prec is the number of digits after the - decimal point. With 'g' and 'G', \a prec is the maximum number of - significant digits (trailing zeroes are omitted). - - \note The format of the number is not localized; the default C locale - is used irrespective of the user's locale. - - \sa toDouble() -*/ - -QByteArray &QByteArray::setNum(double n, char f, int prec) -{ - QLocaleData::DoubleForm form = QLocaleData::DFDecimal; - uint flags = QLocaleData::ZeroPadExponent; - - char lower = latin1_lowercased[uchar(f)]; - if (f != lower) - flags |= QLocaleData::CapitalEorX; - f = lower; - - switch (f) { - case 'f': - form = QLocaleData::DFDecimal; - break; - case 'e': - form = QLocaleData::DFExponent; - break; - case 'g': - form = QLocaleData::DFSignificantDigits; - break; - default: -#if defined(QT_CHECK_RANGE) - qWarning("QByteArray::setNum: Invalid format char '%c'", f); -#endif - break; - } - - *this = QLocaleData::c()->doubleToString(n, prec, form, -1, flags).toLatin1(); - return *this; -} - -/*! - \fn QByteArray &QByteArray::setNum(float n, char f, int prec) - \overload - - Sets the byte array to the printed value of \a n, formatted in format - \a f with precision \a prec, and returns a reference to the - byte array. - - \note The format of the number is not localized; the default C locale - is used irrespective of the user's locale. - - \sa toFloat() -*/ - -/*! - Returns a byte array containing the string equivalent of the - number \a n to base \a base (10 by default). The \a base can be - any value between 2 and 36. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 41 - - \note The format of the number is not localized; the default C locale - is used irrespective of the user's locale. - - \sa setNum(), toInt() -*/ -QByteArray QByteArray::number(int n, int base) -{ - QByteArray s; - s.setNum(n, base); - return s; -} - -/*! - \overload - - \sa toUInt() -*/ -QByteArray QByteArray::number(uint n, int base) -{ - QByteArray s; - s.setNum(n, base); - return s; -} - -/*! - \overload - - \sa toLongLong() -*/ -QByteArray QByteArray::number(qlonglong n, int base) -{ - QByteArray s; - s.setNum(n, base); - return s; -} - -/*! - \overload - - \sa toULongLong() -*/ -QByteArray QByteArray::number(qulonglong n, int base) -{ - QByteArray s; - s.setNum(n, base); - return s; -} - -/*! - \overload - - Returns a byte array that contains the printed value of \a n, - formatted in format \a f with precision \a prec. - - Argument \a n is formatted according to the \a f format specified, - which is \c g by default, and can be any of the following: - - \table - \header \li Format \li Meaning - \row \li \c e \li format as [-]9.9e[+|-]999 - \row \li \c E \li format as [-]9.9E[+|-]999 - \row \li \c f \li format as [-]9.9 - \row \li \c g \li use \c e or \c f format, whichever is the most concise - \row \li \c G \li use \c E or \c f format, whichever is the most concise - \endtable - - With 'e', 'E', and 'f', \a prec is the number of digits after the - decimal point. With 'g' and 'G', \a prec is the maximum number of - significant digits (trailing zeroes are omitted). - - \snippet code/src_corelib_tools_qbytearray.cpp 42 - - \note The format of the number is not localized; the default C locale - is used irrespective of the user's locale. - - \sa toDouble() -*/ -QByteArray QByteArray::number(double n, char f, int prec) -{ - QByteArray s; - s.setNum(n, f, prec); - return s; -} - -/*! - Constructs a QByteArray that uses the first \a size bytes of the - \a data array. The bytes are \e not copied. The QByteArray will - contain the \a data pointer. The caller guarantees that \a data - will not be deleted or modified as long as this QByteArray and any - copies of it exist that have not been modified. In other words, - because QByteArray is an \l{implicitly shared} class and the - instance returned by this function contains the \a data pointer, - the caller must not delete \a data or modify it directly as long - as the returned QByteArray and any copies exist. However, - QByteArray does not take ownership of \a data, so the QByteArray - destructor will never delete the raw \a data, even when the - last QByteArray referring to \a data is destroyed. - - A subsequent attempt to modify the contents of the returned - QByteArray or any copy made from it will cause it to create a deep - copy of the \a data array before doing the modification. This - ensures that the raw \a data array itself will never be modified - by QByteArray. - - Here is an example of how to read data using a QDataStream on raw - data in memory without copying the raw data into a QByteArray: - - \snippet code/src_corelib_tools_qbytearray.cpp 43 - - \warning A byte array created with fromRawData() is \e not - '\\0'-terminated, unless the raw data contains a 0 character at - position \a size. While that does not matter for QDataStream or - functions like indexOf(), passing the byte array to a function - accepting a \c{const char *} expected to be '\\0'-terminated will - fail. - - \sa setRawData(), data(), constData() -*/ - -QByteArray QByteArray::fromRawData(const char *data, int size) -{ - Data *x; - if (!data) { - x = Data::sharedNull(); - } else if (!size) { - x = Data::allocate(0); - } else { - x = Data::fromRawData(data, size); - Q_CHECK_PTR(x); - } - QByteArrayDataPtr dataPtr = { x }; - return QByteArray(dataPtr); -} - -/*! - \since 4.7 - - Resets the QByteArray to use the first \a size bytes of the - \a data array. The bytes are \e not copied. The QByteArray will - contain the \a data pointer. The caller guarantees that \a data - will not be deleted or modified as long as this QByteArray and any - copies of it exist that have not been modified. - - This function can be used instead of fromRawData() to re-use - existing QByteArray objects to save memory re-allocations. - - \sa fromRawData(), data(), constData() -*/ -QByteArray &QByteArray::setRawData(const char *data, uint size) -{ - if (d->ref.isShared() || d->alloc) { - *this = fromRawData(data, size); - } else { - if (data) { - d->size = size; - d->offset = data - reinterpret_cast<char *>(d); - } else { - d->offset = sizeof(QByteArrayData); - d->size = 0; - } - } - return *this; -} - -/*! - Returns a decoded copy of the Base64 array \a base64. Input is not checked - for validity; invalid characters in the input are skipped, enabling the - decoding process to continue with subsequent characters. - - For example: - - \snippet code/src_corelib_tools_qbytearray.cpp 44 - - The algorithm used to decode Base64-encoded data is defined in \l{RFC 4648}. - - \sa toBase64() -*/ -QByteArray QByteArray::fromBase64(const QByteArray &base64) -{ - return fromBase64(base64, Base64Encoding); -} - -/*! - \since 5.2 - \overload - - Returns a decoded copy of the Base64 array \a base64, using the alphabet - defined by \a options. Input is not checked for validity; invalid - characters in the input are skipped, enabling the decoding process to - continue with subsequent characters. - - For example: - - \snippet code/src_corelib_tools_qbytearray.cpp 44bis - - The algorithm used to decode Base64-encoded data is defined in \l{RFC 4648}. - - \sa toBase64() -*/ -QByteArray QByteArray::fromBase64(const QByteArray &base64, Base64Options options) -{ - unsigned int buf = 0; - int nbits = 0; - QByteArray tmp((base64.size() * 3) / 4, Qt::Uninitialized); - - int offset = 0; - for (int i = 0; i < base64.size(); ++i) { - int ch = base64.at(i); - int d; - - if (ch >= 'A' && ch <= 'Z') - d = ch - 'A'; - else if (ch >= 'a' && ch <= 'z') - d = ch - 'a' + 26; - else if (ch >= '0' && ch <= '9') - d = ch - '0' + 52; - else if (ch == '+' && (options & Base64UrlEncoding) == 0) - d = 62; - else if (ch == '-' && (options & Base64UrlEncoding) != 0) - d = 62; - else if (ch == '/' && (options & Base64UrlEncoding) == 0) - d = 63; - else if (ch == '_' && (options & Base64UrlEncoding) != 0) - d = 63; - else - d = -1; - - if (d != -1) { - buf = (buf << 6) | d; - nbits += 6; - if (nbits >= 8) { - nbits -= 8; - tmp[offset++] = buf >> nbits; - buf &= (1 << nbits) - 1; - } - } - } - - tmp.truncate(offset); - return tmp; -} - -/*! - Returns a decoded copy of the hex encoded array \a hexEncoded. Input is not checked - for validity; invalid characters in the input are skipped, enabling the - decoding process to continue with subsequent characters. - - For example: - - \snippet code/src_corelib_tools_qbytearray.cpp 45 - - \sa toHex() -*/ -QByteArray QByteArray::fromHex(const QByteArray &hexEncoded) -{ - QByteArray res((hexEncoded.size() + 1)/ 2, Qt::Uninitialized); - uchar *result = (uchar *)res.data() + res.size(); - - bool odd_digit = true; - for (int i = hexEncoded.size() - 1; i >= 0; --i) { - uchar ch = uchar(hexEncoded.at(i)); - int tmp = QtMiscUtils::fromHex(ch); - if (tmp == -1) - continue; - if (odd_digit) { - --result; - *result = tmp; - odd_digit = false; - } else { - *result |= tmp << 4; - odd_digit = true; - } - } - - res.remove(0, result - (const uchar *)res.constData()); - return res; -} - -/*! - Returns a hex encoded copy of the byte array. The hex encoding uses the numbers 0-9 and - the letters a-f. - - \sa fromHex() -*/ -QByteArray QByteArray::toHex() const -{ - return toHex('\0'); -} - -/*! \overload - \since 5.9 - - Returns a hex encoded copy of the byte array. The hex encoding uses the numbers 0-9 and - the letters a-f. - - If \a separator is not '\0', the separator character is inserted between the hex bytes. - - Example: - \snippet code/src_corelib_tools_qbytearray.cpp 50 - - \sa fromHex() -*/ -QByteArray QByteArray::toHex(char separator) const -{ - if (!d->size) - return QByteArray(); - - const int length = separator ? (d->size * 3 - 1) : (d->size * 2); - QByteArray hex(length, Qt::Uninitialized); - char *hexData = hex.data(); - const uchar *data = (const uchar *)d->data(); - for (int i = 0, o = 0; i < d->size; ++i) { - hexData[o++] = QtMiscUtils::toHexLower(data[i] >> 4); - hexData[o++] = QtMiscUtils::toHexLower(data[i] & 0xf); - - if ((separator) && (o < length)) - hexData[o++] = separator; - } - return hex; -} - -static void q_fromPercentEncoding(QByteArray *ba, char percent) -{ - if (ba->isEmpty()) - return; - - char *data = ba->data(); - const char *inputPtr = data; - - int i = 0; - int len = ba->count(); - int outlen = 0; - int a, b; - char c; - while (i < len) { - c = inputPtr[i]; - if (c == percent && i + 2 < len) { - a = inputPtr[++i]; - b = inputPtr[++i]; - - if (a >= '0' && a <= '9') a -= '0'; - else if (a >= 'a' && a <= 'f') a = a - 'a' + 10; - else if (a >= 'A' && a <= 'F') a = a - 'A' + 10; - - if (b >= '0' && b <= '9') b -= '0'; - else if (b >= 'a' && b <= 'f') b = b - 'a' + 10; - else if (b >= 'A' && b <= 'F') b = b - 'A' + 10; - - *data++ = (char)((a << 4) | b); - } else { - *data++ = c; - } - - ++i; - ++outlen; - } - - if (outlen != len) - ba->truncate(outlen); -} - -void q_fromPercentEncoding(QByteArray *ba) -{ - q_fromPercentEncoding(ba, '%'); -} - -/*! - \since 4.4 - - Returns a decoded copy of the URI/URL-style percent-encoded \a input. - The \a percent parameter allows you to replace the '%' character for - another (for instance, '_' or '='). - - For example: - \snippet code/src_corelib_tools_qbytearray.cpp 51 - - \note Given invalid input (such as a string containing the sequence "%G5", - which is not a valid hexadecimal number) the output will be invalid as - well. As an example: the sequence "%G5" could be decoded to 'W'. - - \sa toPercentEncoding(), QUrl::fromPercentEncoding() -*/ -QByteArray QByteArray::fromPercentEncoding(const QByteArray &input, char percent) -{ - if (input.isNull()) - return QByteArray(); // preserve null - if (input.isEmpty()) - return QByteArray(input.data(), 0); - - QByteArray tmp = input; - q_fromPercentEncoding(&tmp, percent); - return tmp; -} - -/*! \fn QByteArray QByteArray::fromStdString(const std::string &str) - \since 5.4 - - Returns a copy of the \a str string as a QByteArray. - - \sa toStdString(), QString::fromStdString() -*/ - -/*! - \fn std::string QByteArray::toStdString() const - \since 5.4 - - Returns a std::string object with the data contained in this - QByteArray. - - This operator is mostly useful to pass a QByteArray to a function - that accepts a std::string object. - - \sa fromStdString(), QString::toStdString() -*/ - -static inline bool q_strchr(const char str[], char chr) -{ - if (!str) return false; - - const char *ptr = str; - char c; - while ((c = *ptr++)) - if (c == chr) - return true; - return false; -} - -static void q_toPercentEncoding(QByteArray *ba, const char *dontEncode, const char *alsoEncode, char percent) -{ - if (ba->isEmpty()) - return; - - QByteArray input = *ba; - int len = input.count(); - const char *inputData = input.constData(); - char *output = nullptr; - int length = 0; - - for (int i = 0; i < len; ++i) { - unsigned char c = *inputData++; - if (((c >= 0x61 && c <= 0x7A) // ALPHA - || (c >= 0x41 && c <= 0x5A) // ALPHA - || (c >= 0x30 && c <= 0x39) // DIGIT - || c == 0x2D // - - || c == 0x2E // . - || c == 0x5F // _ - || c == 0x7E // ~ - || q_strchr(dontEncode, c)) - && !q_strchr(alsoEncode, c)) { - if (output) - output[length] = c; - ++length; - } else { - if (!output) { - // detach now - ba->resize(len*3); // worst case - output = ba->data(); - } - output[length++] = percent; - output[length++] = QtMiscUtils::toHexUpper((c & 0xf0) >> 4); - output[length++] = QtMiscUtils::toHexUpper(c & 0xf); - } - } - if (output) - ba->truncate(length); -} - -void q_toPercentEncoding(QByteArray *ba, const char *exclude, const char *include) -{ - q_toPercentEncoding(ba, exclude, include, '%'); -} - -void q_normalizePercentEncoding(QByteArray *ba, const char *exclude) -{ - q_fromPercentEncoding(ba, '%'); - q_toPercentEncoding(ba, exclude, nullptr, '%'); -} - -/*! - \since 4.4 - - Returns a URI/URL-style percent-encoded copy of this byte array. The - \a percent parameter allows you to override the default '%' - character for another. - - By default, this function will encode all characters that are not - one of the following: - - ALPHA ("a" to "z" and "A" to "Z") / DIGIT (0 to 9) / "-" / "." / "_" / "~" - - To prevent characters from being encoded pass them to \a - exclude. To force characters to be encoded pass them to \a - include. The \a percent character is always encoded. - - Example: - - \snippet code/src_corelib_tools_qbytearray.cpp 52 - - The hex encoding uses the numbers 0-9 and the uppercase letters A-F. - - \sa fromPercentEncoding(), QUrl::toPercentEncoding() -*/ -QByteArray QByteArray::toPercentEncoding(const QByteArray &exclude, const QByteArray &include, - char percent) const -{ - if (isNull()) - return QByteArray(); // preserve null - if (isEmpty()) - return QByteArray(data(), 0); - - QByteArray include2 = include; - if (percent != '%') // the default - if ((percent >= 0x61 && percent <= 0x7A) // ALPHA - || (percent >= 0x41 && percent <= 0x5A) // ALPHA - || (percent >= 0x30 && percent <= 0x39) // DIGIT - || percent == 0x2D // - - || percent == 0x2E // . - || percent == 0x5F // _ - || percent == 0x7E) // ~ - include2 += percent; - - QByteArray result = *this; - q_toPercentEncoding(&result, exclude.nulTerminated().constData(), include2.nulTerminated().constData(), percent); - - return result; -} - -/*! \typedef QByteArray::ConstIterator - \internal -*/ - -/*! \typedef QByteArray::Iterator - \internal -*/ - -/*! \typedef QByteArray::const_iterator - - This typedef provides an STL-style const iterator for QByteArray. - - \sa QByteArray::const_reverse_iterator, QByteArray::iterator -*/ - -/*! \typedef QByteArray::iterator - - This typedef provides an STL-style non-const iterator for QByteArray. - - \sa QByteArray::reverse_iterator, QByteArray::const_iterator -*/ - -/*! \typedef QByteArray::const_reverse_iterator - \since 5.6 - - This typedef provides an STL-style const reverse iterator for QByteArray. - - \sa QByteArray::reverse_iterator, QByteArray::const_iterator -*/ - -/*! \typedef QByteArray::reverse_iterator - \since 5.6 - - This typedef provides an STL-style non-const reverse iterator for QByteArray. - - \sa QByteArray::const_reverse_iterator, QByteArray::iterator -*/ - -/*! \typedef QByteArray::size_type - \internal -*/ - -/*! \typedef QByteArray::difference_type - \internal -*/ - -/*! \typedef QByteArray::const_reference - \internal -*/ - -/*! \typedef QByteArray::reference - \internal -*/ - -/*! \typedef QByteArray::const_pointer - \internal -*/ - -/*! \typedef QByteArray::pointer - \internal -*/ - -/*! \typedef QByteArray::value_type - \internal - */ - -/*! - \fn DataPtr &QByteArray::data_ptr() - \internal -*/ - -/*! - \typedef QByteArray::DataPtr - \internal -*/ - -/*! - \macro QByteArrayLiteral(ba) - \relates QByteArray - - The macro generates the data for a QByteArray out of the string literal - \a ba at compile time. Creating a QByteArray from it is free in this case, and - the generated byte array data is stored in the read-only segment of the - compiled object file. - - For instance: - - \snippet code/src_corelib_tools_qbytearray.cpp 53 - - Using QByteArrayLiteral instead of a double quoted plain C++ string literal - can significantly speed up creation of QByteArray instances from data known - at compile time. - - \sa QStringLiteral -*/ - -namespace QtPrivate { -namespace DeprecatedRefClassBehavior { -void warn(WarningType w, EmittingClass c) -{ - static const char deprecatedBehaviorString[] = - "The corresponding behavior is deprecated, and will be changed" - " in a future version of Qt."; - - const char *emittingClassName = nullptr; - const char *containerClassName = nullptr; - - switch (c) { - case EmittingClass::QByteRef: - emittingClassName = "QByteRef"; - containerClassName = "QByteArray"; - break; - case EmittingClass::QCharRef: - emittingClassName = "QCharRef"; - containerClassName = "QString"; - break; - } - - switch (w) { - case WarningType::OutOfRange: - qWarning("Using %s with an index pointing outside the valid range of a %s. %s", - emittingClassName, containerClassName, deprecatedBehaviorString); - break; - case WarningType::DelayedDetach: - qWarning("Using %s with on a %s that is not already detached. %s", - emittingClassName, containerClassName, deprecatedBehaviorString); - break; - } -} -} // namespace DeprecatedRefClassBehavior -} // namespace QtPrivate - - -QT_END_NAMESPACE |