mirror of
https://repo.dactyloidae.xyz/Dactyloidae/UXP.git
synced 2026-10-02 05:17:31 +09:00
Issue #1859 - Part 3: Replace bzip2 handling in MAR files with xz.
Since there really is no need to add file detection logic to the updater if updating through AUS is old->new only anyway, replacing bzip2 handling with xz handling is fine, instead of adding it. Considering the far superior compression of LZMA and MAR not being a common archive format anyway, let's just K.I.S.S. it :)
This commit is contained in:
parent
fc95b11fae
commit
a195efca40
6 changed files with 64 additions and 37 deletions
|
|
@ -109,7 +109,7 @@ int mar_enum_items(MarFile *mar, MarItemCallback callback, void *data);
|
||||||
* @return The number of bytes written or a negative value if an
|
* @return The number of bytes written or a negative value if an
|
||||||
* error occurs.
|
* error occurs.
|
||||||
*/
|
*/
|
||||||
int mar_read(MarFile *mar, const MarItem *item, int offset, char *buf,
|
int mar_read(MarFile *mar, const MarItem *item, int offset, uint8_t *buf,
|
||||||
int bufsize);
|
int bufsize);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
|
|
@ -37,7 +37,7 @@ static int mar_ensure_parent_dir(const char *path)
|
||||||
|
|
||||||
static int mar_test_callback(MarFile *mar, const MarItem *item, void *unused) {
|
static int mar_test_callback(MarFile *mar, const MarItem *item, void *unused) {
|
||||||
FILE *fp;
|
FILE *fp;
|
||||||
char buf[BLOCKSIZE];
|
uint8_t buf[BLOCKSIZE];
|
||||||
int fd, len, offset = 0;
|
int fd, len, offset = 0;
|
||||||
|
|
||||||
if (mar_ensure_parent_dir(item->name))
|
if (mar_ensure_parent_dir(item->name))
|
||||||
|
|
|
||||||
|
|
@ -530,7 +530,7 @@ int mar_enum_items(MarFile *mar, MarItemCallback callback, void *closure) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int mar_read(MarFile *mar, const MarItem *item, int offset, char *buf,
|
int mar_read(MarFile *mar, const MarItem *item, int offset, uint8_t *buf,
|
||||||
int bufsize) {
|
int bufsize) {
|
||||||
int nr;
|
int nr;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -46,7 +46,7 @@
|
||||||
#define WRITE_ERROR_ACCESS_DENIED 35
|
#define WRITE_ERROR_ACCESS_DENIED 35
|
||||||
// #define WRITE_ERROR_SHARING_VIOLATION 36 // Replaced with errors 46-48
|
// #define WRITE_ERROR_SHARING_VIOLATION 36 // Replaced with errors 46-48
|
||||||
#define WRITE_ERROR_CALLBACK_APP 37
|
#define WRITE_ERROR_CALLBACK_APP 37
|
||||||
#define UNEXPECTED_BZIP_ERROR 39
|
#define UNEXPECTED_XZ_ERROR 39
|
||||||
#define UNEXPECTED_MAR_ERROR 40
|
#define UNEXPECTED_MAR_ERROR 40
|
||||||
#define UNEXPECTED_BSPATCH_ERROR 41
|
#define UNEXPECTED_BSPATCH_ERROR 41
|
||||||
#define UNEXPECTED_FILE_OPERATION_ERROR 42
|
#define UNEXPECTED_FILE_OPERATION_ERROR 42
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,4 @@
|
||||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
/* vim:set ts=2 sw=2 sts=2 et cindent: */
|
|
||||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||||
|
|
@ -15,6 +14,9 @@
|
||||||
#include "updatehelper.h"
|
#include "updatehelper.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#define XZ_USE_CRC64
|
||||||
|
#include "xz.h"
|
||||||
|
|
||||||
// These are generated at compile time based on the DER file for the channel
|
// These are generated at compile time based on the DER file for the channel
|
||||||
// being used
|
// being used
|
||||||
#ifdef MOZ_VERIFY_MAR_SIGNATURE
|
#ifdef MOZ_VERIFY_MAR_SIGNATURE
|
||||||
|
|
@ -36,10 +38,10 @@
|
||||||
# include <io.h>
|
# include <io.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
static int inbuf_size = 262144;
|
static size_t inbuf_size = 262144;
|
||||||
static int outbuf_size = 262144;
|
static size_t outbuf_size = 262144;
|
||||||
static char *inbuf = nullptr;
|
static uint8_t *inbuf = nullptr;
|
||||||
static char *outbuf = nullptr;
|
static uint8_t *outbuf = nullptr;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Performs a verification on the opened MAR file with the passed in
|
* Performs a verification on the opened MAR file with the passed in
|
||||||
|
|
@ -182,22 +184,22 @@ ArchiveReader::Open(const NS_tchar *path)
|
||||||
Close();
|
Close();
|
||||||
|
|
||||||
if (!inbuf) {
|
if (!inbuf) {
|
||||||
inbuf = (char *)malloc(inbuf_size);
|
inbuf = (uint8_t *)malloc(inbuf_size);
|
||||||
if (!inbuf) {
|
if (!inbuf) {
|
||||||
// Try again with a smaller buffer.
|
// Try again with a smaller buffer.
|
||||||
inbuf_size = 1024;
|
inbuf_size = 1024;
|
||||||
inbuf = (char *)malloc(inbuf_size);
|
inbuf = (uint8_t *)malloc(inbuf_size);
|
||||||
if (!inbuf)
|
if (!inbuf)
|
||||||
return ARCHIVE_READER_MEM_ERROR;
|
return ARCHIVE_READER_MEM_ERROR;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!outbuf) {
|
if (!outbuf) {
|
||||||
outbuf = (char *)malloc(outbuf_size);
|
outbuf = (uint8_t *)malloc(outbuf_size);
|
||||||
if (!outbuf) {
|
if (!outbuf) {
|
||||||
// Try again with a smaller buffer.
|
// Try again with a smaller buffer.
|
||||||
outbuf_size = 1024;
|
outbuf_size = 1024;
|
||||||
outbuf = (char *)malloc(outbuf_size);
|
outbuf = (uint8_t *)malloc(outbuf_size);
|
||||||
if (!outbuf)
|
if (!outbuf)
|
||||||
return ARCHIVE_READER_MEM_ERROR;
|
return ARCHIVE_READER_MEM_ERROR;
|
||||||
}
|
}
|
||||||
|
|
@ -211,6 +213,9 @@ ArchiveReader::Open(const NS_tchar *path)
|
||||||
if (!mArchive)
|
if (!mArchive)
|
||||||
return READ_ERROR;
|
return READ_ERROR;
|
||||||
|
|
||||||
|
xz_crc32_init();
|
||||||
|
xz_crc64_init();
|
||||||
|
|
||||||
return OK;
|
return OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -273,12 +278,21 @@ ArchiveReader::ExtractItemToStream(const MarItem *item, FILE *fp)
|
||||||
{
|
{
|
||||||
/* decompress the data chunk by chunk */
|
/* decompress the data chunk by chunk */
|
||||||
|
|
||||||
bz_stream strm;
|
int offset, inlen, ret = OK;
|
||||||
int offset, inlen, outlen, ret = OK;
|
struct xz_buf strm = { 0 };
|
||||||
|
enum xz_ret xz_rv = XZ_OK;
|
||||||
|
|
||||||
memset(&strm, 0, sizeof(strm));
|
struct xz_dec * dec = xz_dec_init(XZ_DYNALLOC, 64 * 1024 * 1024);
|
||||||
if (BZ2_bzDecompressInit(&strm, 0, 0) != BZ_OK)
|
if (!dec) {
|
||||||
return UNEXPECTED_BZIP_ERROR;
|
return UNEXPECTED_XZ_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
strm.in = inbuf;
|
||||||
|
strm.in_pos = 0;
|
||||||
|
strm.in_size = 0;
|
||||||
|
strm.out = outbuf;
|
||||||
|
strm.out_pos = 0;
|
||||||
|
strm.out_size = outbuf_size;
|
||||||
|
|
||||||
offset = 0;
|
offset = 0;
|
||||||
for (;;) {
|
for (;;) {
|
||||||
|
|
@ -287,38 +301,50 @@ ArchiveReader::ExtractItemToStream(const MarItem *item, FILE *fp)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (offset < (int) item->length && strm.avail_in == 0) {
|
if (offset < (int) item->length && strm.in_pos == strm.in_size) {
|
||||||
inlen = mar_read(mArchive, item, offset, inbuf, inbuf_size);
|
inlen = mar_read(mArchive, item, offset, inbuf, inbuf_size);
|
||||||
if (inlen <= 0)
|
if (inlen <= 0) {
|
||||||
return READ_ERROR;
|
ret = READ_ERROR;
|
||||||
offset += inlen;
|
|
||||||
strm.next_in = inbuf;
|
|
||||||
strm.avail_in = inlen;
|
|
||||||
}
|
|
||||||
|
|
||||||
strm.next_out = outbuf;
|
|
||||||
strm.avail_out = outbuf_size;
|
|
||||||
|
|
||||||
ret = BZ2_bzDecompress(&strm);
|
|
||||||
if (ret != BZ_OK && ret != BZ_STREAM_END) {
|
|
||||||
ret = UNEXPECTED_BZIP_ERROR;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
offset += inlen;
|
||||||
|
strm.in_size = inlen;
|
||||||
|
strm.in_pos = 0;
|
||||||
|
}
|
||||||
|
|
||||||
outlen = outbuf_size - strm.avail_out;
|
xz_rv = xz_dec_run(dec, &strm);
|
||||||
if (outlen) {
|
|
||||||
if (fwrite(outbuf, outlen, 1, fp) != 1) {
|
if (strm.out_pos == outbuf_size) {
|
||||||
|
if (fwrite(outbuf, 1, strm.out_pos, fp) != strm.out_pos) {
|
||||||
ret = WRITE_ERROR_EXTRACT;
|
ret = WRITE_ERROR_EXTRACT;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
strm.out_pos = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ret == BZ_STREAM_END) {
|
if (xz_rv == XZ_OK) {
|
||||||
ret = OK;
|
// There is still more data to decompress.
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
// The return value of xz_dec_run is not XZ_OK and if it isn't XZ_STREAM_END
|
||||||
|
// an error has occured.
|
||||||
|
if (xz_rv != XZ_STREAM_END) {
|
||||||
|
ret = UNEXPECTED_XZ_ERROR;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Write out the remainder of the decompressed data. In the case of
|
||||||
|
// strm.out_pos == 0 this is needed to create empty files included in the
|
||||||
|
// mar file.
|
||||||
|
if (fwrite(outbuf, 1, strm.out_pos, fp) != strm.out_pos) {
|
||||||
|
ret = WRITE_ERROR_EXTRACT;
|
||||||
}
|
}
|
||||||
|
|
||||||
BZ2_bzDecompressEnd(&strm);
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
xz_dec_end(dec);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -57,6 +57,7 @@ else:
|
||||||
|
|
||||||
USE_LIBS += [
|
USE_LIBS += [
|
||||||
'mar',
|
'mar',
|
||||||
|
'xz-embedded',
|
||||||
]
|
]
|
||||||
|
|
||||||
if CONFIG['MOZ_SYSTEM_BZ2']:
|
if CONFIG['MOZ_SYSTEM_BZ2']:
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue