Changeset 34949 in vbox for trunk/src/VBox
- Timestamp:
- Dec 10, 2010 1:29:32 PM (14 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Runtime/common/zip/tar.cpp
r34919 r34949 193 193 ******************************************************************************/ 194 194 195 DECLINLINE(void) rtTarSizeToRec(PRTTARRECORD pRecord, uint64_t cbSize) 196 { 197 /* Small enough for the standard octal string encoding? */ 198 if (cbSize <= 0x200000000) 199 RTStrPrintf(pRecord->h.size, sizeof(pRecord->h.size), "%0.11llo", cbSize); 200 else 201 { 202 /* 203 * Base 256 extension. Set the highest bit of the left most character. 204 * We don't deal with negatives here, cause the size have to be greater 205 * than zero. 206 */ 207 size_t cchField = sizeof(pRecord->h.size) - 1; 208 unsigned char *puchField = (unsigned char*)pRecord->h.size; 209 puchField[0] = 0x80; 210 do 211 { 212 puchField[cchField--] = cbSize & ((1 << 8) - 1); 213 cbSize = (cbSize >> 8); 214 } while (cchField); 215 } 216 } 217 218 DECLINLINE(uint64_t) rtTarRecToSize(PRTTARRECORD pRecord) 219 { 220 int64_t cbSize = 0; 221 if (pRecord->h.size[0] & 0x80) 222 { 223 size_t cchField = sizeof(pRecord->h.size); 224 unsigned char const *puchField = (unsigned char const *)pRecord->h.size; 225 /* 226 * The first byte has the bit 7 set to indicate base-256, while bit 6 227 * is the signed bit. Bits 5:0 are the most significant value bits. 228 */ 229 cbSize = !(0x40 & *puchField) ? 0 : -1; 230 cbSize = (cbSize << 6) | (*puchField & 0x3f); 231 cchField--; 232 puchField++; 233 /* 234 * The remaining bytes are used in full. 235 */ 236 while (cchField-- > 0) 237 { 238 if (RT_UNLIKELY( cbSize > INT64_MAX / 256 239 || cbSize < INT64_MIN / 256)) 240 { 241 cbSize = 0; 242 break; 243 } 244 cbSize = (cbSize << 8) | *puchField++; 245 } 246 }else 247 cbSize = rtTarRecToSize(pRecord); 248 249 if (cbSize < 0) 250 cbSize = 0; 251 252 return (uint64_t)cbSize; 253 } 254 195 255 DECLINLINE(int) rtTarCalcChkSum(PRTTARRECORD pRecord, uint32_t *pChkSum) 196 256 { … … 264 324 RTStrPrintf(pRecord->h.uid, sizeof(pRecord->h.uid), "%0.7o", uid); 265 325 RTStrPrintf(pRecord->h.gid, sizeof(pRecord->h.gid), "%0.7o", gid); 266 RTStrPrintf(pRecord->h.size, sizeof(pRecord->h.size), "%0.11llo", cbSize);326 rtTarSizeToRec(pRecord, cbSize); 267 327 RTStrPrintf(pRecord->h.mtime, sizeof(pRecord->h.mtime), "%0.11o", mtime); 268 328 RTStrPrintf(pRecord->h.magic, sizeof(pRecord->h.magic), "ustar "); … … 568 628 int rc = VINF_SUCCESS; 569 629 /* Seek over the data parts (512 bytes aligned) */ 570 int64_t offSeek = RT_ALIGN( RTStrToInt64(pRecord->h.size), sizeof(RTTARRECORD));630 int64_t offSeek = RT_ALIGN(rtTarRecToSize(pRecord), sizeof(RTTARRECORD)); 571 631 if (offSeek > 0) 572 632 rc = RTFileSeek(hFile, offSeek, RTFILE_SEEK_CURRENT, NULL); … … 595 655 { 596 656 /* Get the file size */ 597 rc = RTStrToUInt64Full(record.h.size, 8, pcbSize); 598 if (RT_FAILURE(rc)) 599 break; 600 657 *pcbSize = rtTarRecToSize(&record); 601 658 /* Seek back, to position the file pointer at the start of the header. */ 602 659 rc = RTFileSeek(hFile, -(int64_t)sizeof(RTTARRECORD), RTFILE_SEEK_CURRENT, poff); … … 642 699 if (!RTStrCmp(record.h.name, papszFiles[i])) 643 700 { 644 /* Get the file size */645 uint64_t cbSize = 0;646 rc = RTStrToUInt64Full(record.h.size, 8, &cbSize);647 648 701 /* Sum up the overall size */ 649 *pcbOverallSize += cbSize;702 *pcbOverallSize += rtTarRecToSize(&record); 650 703 ++cFound; 651 704 break; … … 1620 1673 1621 1674 /* Get the file size */ 1622 rc = RTStrToUInt64Full(record.h.size, 8, &pFileInt->cbSize); 1623 if (RT_FAILURE(rc)) 1624 break; 1625 1675 pFileInt->cbSize = rtTarRecToSize(&record); 1626 1676 /* The start is -512 from here. */ 1627 1677 pFileInt->offStart = RTFileTell(pInt->hTarFile) - sizeof(RTTARRECORD);
Note:
See TracChangeset
for help on using the changeset viewer.