v20251001-0022-experimental-zlib-gzip-compression.patch
text/x-patch
Filename: v20251001-0022-experimental-zlib-gzip-compression.patch
Type: text/x-patch
Part: 21
Patch
Same data as JSON:
GET /api/v1/attachments/:id/patch
the parsed metadata as JSON — format, series position, per-file stats; never the diff bytes.
API reference →
Format: format-patch
Series: patch v20251001-0022
Subject: experimental: zlib (gzip?) compression
| File | + | − |
|---|---|---|
| src/backend/storage/file/buffile.c | 50 | 0 |
| src/backend/utils/misc/guc_tables.c | 3 | 0 |
| src/include/storage/buffile.h | 2 | 1 |
From 55ca2b6123cb4dd7820b39ae4ef3bacfb00df81c Mon Sep 17 00:00:00 2001
From: Tomas Vondra <tomas@vondra.me>
Date: Wed, 1 Oct 2025 01:34:12 +0200
Subject: [PATCH v20251001 22/25] experimental: zlib (gzip?) compression
---
src/backend/storage/file/buffile.c | 50 +++++++++++++++++++++++++++++
src/backend/utils/misc/guc_tables.c | 3 ++
src/include/storage/buffile.h | 3 +-
3 files changed, 55 insertions(+), 1 deletion(-)
diff --git a/src/backend/storage/file/buffile.c b/src/backend/storage/file/buffile.c
index e3d4e2a342e..380537fb126 100644
--- a/src/backend/storage/file/buffile.c
+++ b/src/backend/storage/file/buffile.c
@@ -60,10 +60,15 @@
#include <lz4.h>
#endif
+#ifdef HAVE_LIBZ
+#include <zlib.h>
+#endif
+
/* Compression types */
#define TEMP_NONE_COMPRESSION 0
#define TEMP_PGLZ_COMPRESSION 1
#define TEMP_LZ4_COMPRESSION 2
+#define TEMP_GZIP_COMPRESSION 3
/*
* We break BufFiles into gigabyte-sized segments, regardless of RELSEG_SIZE.
@@ -294,6 +299,15 @@ BufFileCreateCompressTemp(bool interXact)
size = LZ4_compressBound(BLCKSZ) + sizeof(CompressHeader);
#endif
break;
+
+ case TEMP_GZIP_COMPRESSION:
+ {
+#ifdef HAVE_LIBZ
+ size = compressBound(BLCKSZ) + sizeof(CompressHeader);
+#endif
+ break;
+ }
+
case TEMP_PGLZ_COMPRESSION:
size = pglz_maximum_compressed_size(BLCKSZ, BLCKSZ) + sizeof(CompressHeader);
break;
@@ -689,6 +703,20 @@ BufFileLoadBuffer(BufFile *file)
#endif
break;
+ case TEMP_GZIP_COMPRESSION:
+#ifdef HAVE_LIBZ
+ int ret;
+ size_t len = sizeof(file->buffer);
+
+ ret = uncompress((uint8 *) file->buffer.data, &len,
+ (uint8 *) buff, header.len);
+ if (ret != Z_OK)
+ elog(ERROR, "uncompress failed");
+
+ file->nbytes = len;
+#endif
+ break;
+
case TEMP_PGLZ_COMPRESSION:
file->nbytes = pglz_decompress(buff, header.len,
file->buffer.data, header.raw_len, false);
@@ -785,6 +813,28 @@ BufFileDumpBuffer(BufFile *file)
errmsg_internal("compression failed, compressed size %d, original size %d",
cSize, nbytesOriginal)));
}
+#endif
+ break;
+ }
+ case TEMP_GZIP_COMPRESSION:
+ {
+#ifdef HAVE_LIBZ
+ int ret;
+ size_t len = compressBound(file->nbytes);
+
+ /* XXX maybe lower level? the default is pretty slow ... */
+ ret = compress2((uint8 *) (cData + sizeof(CompressHeader)), &len,
+ (uint8 *) file->buffer.data, file->nbytes,
+ Z_DEFAULT_COMPRESSION);
+ if (ret != Z_OK)
+ {
+ ereport(ERROR,
+ (errcode(ERRCODE_DATA_CORRUPTED),
+ errmsg_internal("compression failed, compressed size %d, original size %d",
+ cSize, nbytesOriginal)));
+ }
+
+ cSize = len;
#endif
break;
}
diff --git a/src/backend/utils/misc/guc_tables.c b/src/backend/utils/misc/guc_tables.c
index 2fb3891b730..88fbe405d59 100644
--- a/src/backend/utils/misc/guc_tables.c
+++ b/src/backend/utils/misc/guc_tables.c
@@ -473,6 +473,9 @@ static const struct config_enum_entry temp_file_compression_options[] = {
{"pglz", TEMP_PGLZ_COMPRESSION, false},
#ifdef USE_LZ4
{"lz4", TEMP_LZ4_COMPRESSION, false},
+#endif
+#ifdef HAVE_LIBZ
+ {"gzip", TEMP_GZIP_COMPRESSION, false},
#endif
{NULL, 0, false}
};
diff --git a/src/include/storage/buffile.h b/src/include/storage/buffile.h
index 49594f1948e..7a1bb1d6085 100644
--- a/src/include/storage/buffile.h
+++ b/src/include/storage/buffile.h
@@ -36,7 +36,8 @@ typedef enum
{
TEMP_NONE_COMPRESSION,
TEMP_PGLZ_COMPRESSION,
- TEMP_LZ4_COMPRESSION
+ TEMP_LZ4_COMPRESSION,
+ TEMP_GZIP_COMPRESSION
} TempCompression;
extern PGDLLIMPORT int temp_file_compression;
--
2.51.0