File indexing completed on 2024-04-21 03:51:38
0001 /* 0002 This file is part of the KDE Baloo project. 0003 SPDX-FileCopyrightText: 2015 Vishesh Handa <vhanda@kde.org> 0004 SPDX-FileCopyrightText: 2011 The LevelDB Authors. All rights reserved. 0005 0006 SPDX-License-Identifier: LGPL-2.1-or-later AND BSD-3-Clause 0007 */ 0008 0009 #include "coding.h" 0010 0011 namespace Baloo { 0012 0013 static inline int encodeVarint32Internal(char* dst, quint32 v) { 0014 // Operate on characters as unsigneds 0015 unsigned char* ptr = reinterpret_cast<unsigned char*>(dst); 0016 static const int B = 128; 0017 if (v < (1<<7)) { 0018 ptr[0] = v; 0019 return 1; 0020 } 0021 if (v < (1<<14)) { 0022 ptr[0] = v | B; 0023 ptr[1] = v>>7; 0024 return 2; 0025 } 0026 if (v < (1<<21)) { 0027 ptr[0] = v | B; 0028 ptr[1] = (v>>7) | B; 0029 ptr[2] = v>>14; 0030 return 3; 0031 } 0032 if (v < (1<<28)) { 0033 ptr[0] = v | B; 0034 ptr[1] = (v>>7) | B; 0035 ptr[2] = (v>>14) | B; 0036 ptr[3] = v>>21; 0037 return 4; 0038 } 0039 0040 ptr[0] = v | B; 0041 ptr[1] = (v>>7) | B; 0042 ptr[2] = (v>>14) | B; 0043 ptr[3] = (v>>21) | B; 0044 ptr[4] = v>>28; 0045 return 5; 0046 } 0047 0048 static inline void putVarint32Internal(char* dst, quint32 v, int &pos) 0049 { 0050 pos += encodeVarint32Internal(&dst[pos], v); 0051 } 0052 0053 void putDifferentialVarInt32(QByteArray &temporaryStorage, QByteArray* dst, const QVector<quint32>& values) 0054 { 0055 temporaryStorage.resize((values.size() + 1) * 5); // max size, correct size will be held in pos 0056 int pos = 0; 0057 putVarint32Internal(temporaryStorage.data(), values.size(), pos); 0058 0059 quint32 v = 0; 0060 const auto itEnd = values.cend(); 0061 for (auto it = values.cbegin(); it != itEnd; ++it) { 0062 const quint32 n = *it; 0063 putVarint32Internal(temporaryStorage.data(), n - v, pos); 0064 v = n; 0065 } 0066 dst->append(temporaryStorage.constData(), pos); 0067 } 0068 0069 char* getDifferentialVarInt32(char* p, char* limit, QVector<quint32>* values) 0070 { 0071 quint32 size = 0; 0072 p = getVarint32Ptr(p, limit, &size); 0073 values->resize(size); 0074 0075 auto it = values->begin(); 0076 auto end = values->end(); 0077 0078 quint32 v = 0; 0079 while (p && it != end) { 0080 quint32 n = 0; 0081 p = getVarint32Ptr(p, limit, &n); 0082 0083 *it = (n + v); 0084 v += n; 0085 ++it; 0086 } 0087 values->erase(it, end); 0088 0089 return p; 0090 } 0091 0092 char* getVarint32PtrFallback(char* p, char* limit, quint32* value) 0093 { 0094 quint32 result = 0; 0095 for (quint32 shift = 0; shift <= 28 && p < limit; shift += 7) { 0096 quint32 byte = *(reinterpret_cast<const unsigned char*>(p)); 0097 p++; 0098 if (byte & 128) { 0099 // More bytes are present 0100 result |= ((byte & 127) << shift); 0101 } else { 0102 result |= (byte << shift); 0103 *value = result; 0104 return p; 0105 } 0106 } 0107 return nullptr; 0108 } 0109 0110 }