return f;
}
+static int parse_level(int* level, const char* mode) {
+ unsigned long value = 0;
+ char* p = NULL;
+
+ // We must have mode
+ if (!mode || *mode != 'w') {
+ errno = EINVAL;
+ return -1;
+ }
+
+ // Skip the w
+ mode++;
+
+ // Do nothing if we have reached the end of the string
+ if (!*mode)
+ return 0;
+
+ // Try parsing a number
+ value = strtoul(mode, &p, 10);
+
+ // Break on error
+ if (value == ULONG_MAX)
+ return -1;
+
+ // Check if we have parsed the entire string
+ if (p && *p) {
+ errno = EINVAL;
+ return -1;
+ }
+
+ // Otherwise we return the value and return
+ *level = value;
+ return 0;
+}
+
/*
gzip
*/
};
FILE* pakfire_xzfopen(FILE* f, const char* mode) {
+ int level = XZ_COMPRESSION_LEVEL;
lzma_ret ret;
+ int r;
if (!f) {
errno = EBADFD;
break;
case 'w':
- ret = lzma_easy_encoder(&cookie->stream, XZ_COMPRESSION_LEVEL, LZMA_CHECK_SHA256);
+ // Try parsing the level
+ r = parse_level(&level, mode);
+ if (r < 0)
+ return NULL;
+
+ ret = lzma_easy_encoder(&cookie->stream, level, LZMA_CHECK_SHA256);
break;
default:
FILE* pakfire_zstdfopen(FILE* f, const char* mode) {
struct zstd_cookie* cookie = NULL;
+ int level = ZSTD_COMPRESSION_LEVEL;
int r;
// Check for a valid file handle
break;
case 'w':
+ // Try parsing the level
+ r = parse_level(&level, mode);
+ if (r < 0)
+ return NULL;
+
// Allocate stream
cookie->cstream = ZSTD_createCStream();
if (!cookie->cstream)
goto ERROR;
// Initialize stream
- r = ZSTD_initCStream(cookie->cstream, ZSTD_COMPRESSION_LEVEL);
+ r = ZSTD_initCStream(cookie->cstream, level);
if (ZSTD_isError(r))
goto ERROR;