using Zstd on TEV; bumping Aircompressor to 2.0.2

This commit is contained in:
minjaesong
2025-09-01 20:48:21 +09:00
parent eb6dfef5ec
commit 680b545590
7 changed files with 32 additions and 57 deletions

View File

@@ -33,7 +33,6 @@
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-glfw-3.3.3.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/js-22.3.1-javadoc.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/js-22.3.1-sources.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/aircompressor-0.25.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/gdx-1.12.1-javadoc.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/gdx-1.12.1-sources.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/icu4j-71.1-javadoc.jar" path-in-jar="/" />
@@ -59,8 +58,6 @@
<element id="extracted-dir" path="$PROJECT_DIR$/lib/gdx-backend-lwjgl3-1.12.1.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-3.3.3-natives-linux.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-3.3.3-natives-macos.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/aircompressor-0.25-javadoc.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/aircompressor-0.25-sources.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-openal-3.3.3-javadoc.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-openal-3.3.3-sources.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-opengl-3.3.3-javadoc.jar" path-in-jar="/" />
@@ -122,6 +119,9 @@
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-jemalloc-3.3.3-natives-linux-arm64.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-jemalloc-3.3.3-natives-macos-arm64.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/lwjgl-jemalloc-3.3.3-natives-windows-x86.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/aircompressor-2.0.2.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/aircompressor-2.0.2-javadoc.jar" path-in-jar="/" />
<element id="extracted-dir" path="$PROJECT_DIR$/lib/aircompressor-2.0.2-sources.jar" path-in-jar="/" />
</root>
</artifact>
</component>

Binary file not shown.

Binary file not shown.

View File

@@ -3,11 +3,11 @@
CC = gcc
CFLAGS = -std=c99 -Wall -Wextra -O2 -D_GNU_SOURCE
LIBS = -lm -lz
LIBS = -lm -lzstd
# Source files and targets
SOURCES = encoder_tev.c encoder_tev_xyb.c
TARGETS = encoder_tev encoder_tev_xyb
SOURCES = encoder_tev.c
TARGETS = encoder_tev
# Build all encoders
all: $(TARGETS)
@@ -17,11 +17,6 @@ encoder_tev: encoder_tev.c
rm -f encoder_tev
$(CC) $(CFLAGS) -o $@ $< $(LIBS)
# Build XYB encoder
encoder_tev_xyb: encoder_tev_xyb.c
rm -f encoder_tev_xyb
$(CC) $(CFLAGS) -o $@ $< $(LIBS)
# Default target
$(TARGETS): all
@@ -40,8 +35,8 @@ install: $(TARGETS)
# Check for required dependencies
check-deps:
@echo "Checking dependencies..."
@echo "libzstd no longer required - using gzip compression instead"
@pkg-config --exists zlib || (echo "Error: zlib-dev not found. Install with: sudo apt install zlib1g-dev" && exit 1)
@echo "Using Zstd compression for better efficiency"
@pkg-config --exists libzstd || (echo "Error: libzstd-dev not found. Install with: sudo apt install libzstd-dev" && exit 1)
@echo "All dependencies found."
# Help

View File

@@ -6,7 +6,7 @@
#include <stddef.h>
#include <string.h>
#include <math.h>
#include <zlib.h>
#include <zstd.h>
#include <unistd.h>
#include <sys/wait.h>
#include <getopt.h>
@@ -63,6 +63,8 @@ int KEYFRAME_INTERVAL = 60;
#define HALF_BLOCK_SIZE 8
#define HALF_BLOCK_SIZE_SQR 64
#define ZSTD_COMPRESSON_LEVEL 15
static float jpeg_quality_to_mult(int q) {
return ((q < 50) ? 5000.f / q : 200.f - 2*q) / 100.f;
}
@@ -177,7 +179,7 @@ typedef struct {
float *y_workspace, *co_workspace, *cg_workspace;
float *dct_workspace; // DCT coefficients
tev_block_t *block_data; // Encoded block data
uint8_t *compressed_buffer; // Gzip output
uint8_t *compressed_buffer; // Zstd output
// Audio handling
FILE *mp2_file;
@@ -189,7 +191,7 @@ typedef struct {
int target_audio_buffer_size;
// Compression context
z_stream gzip_stream;
ZSTD_CCtx *zstd_context;
// FFmpeg processes
FILE *ffmpeg_video_pipe;
@@ -1508,19 +1510,18 @@ static int alloc_encoder_buffers(tev_encoder_t *enc) {
return -1;
}
// Initialize gzip compression stream
enc->gzip_stream.zalloc = Z_NULL;
enc->gzip_stream.zfree = Z_NULL;
enc->gzip_stream.opaque = Z_NULL;
int gzip_init_result = deflateInit2(&enc->gzip_stream, Z_DEFAULT_COMPRESSION,
Z_DEFLATED, 15 + 16, 8, Z_DEFAULT_STRATEGY); // 15+16 for gzip format
if (gzip_init_result != Z_OK) {
fprintf(stderr, "Failed to initialize gzip compression\n");
// Initialize Zstd compression context
enc->zstd_context = ZSTD_createCCtx();
if (!enc->zstd_context) {
fprintf(stderr, "Failed to initialize Zstd compression\n");
return 0;
}
// Set reasonable compression level and memory limits
ZSTD_CCtx_setParameter(enc->zstd_context, ZSTD_c_compressionLevel, ZSTD_COMPRESSON_LEVEL);
ZSTD_CCtx_setParameter(enc->zstd_context, ZSTD_c_windowLog, 24); // 16MB window (should be plenty to hold an entire frame; interframe compression is unavailable)
ZSTD_CCtx_setParameter(enc->zstd_context, ZSTD_c_hashLog, 16);
// Initialize previous frame to black
memset(enc->previous_rgb, 0, pixels * 3);
@@ -1531,7 +1532,7 @@ static int alloc_encoder_buffers(tev_encoder_t *enc) {
static void free_encoder(tev_encoder_t *enc) {
if (!enc) return;
deflateEnd(&enc->gzip_stream);
ZSTD_freeCCtx(enc->zstd_context);
free(enc->current_rgb);
free(enc->previous_rgb);
@@ -1657,41 +1658,20 @@ static int encode_frame(tev_encoder_t *enc, FILE *output, int frame_num) {
}
}
// Compress block data using gzip (compatible with TSVM decoder)
// Compress block data using Zstd (compatible with TSVM decoder)
size_t block_data_size = blocks_x * blocks_y * sizeof(tev_block_t);
// Initialize fresh gzip stream for each frame (since Z_FINISH terminates the stream)
z_stream frame_stream;
frame_stream.zalloc = Z_NULL;
frame_stream.zfree = Z_NULL;
frame_stream.opaque = Z_NULL;
// Compress using Zstd with controlled memory usage
size_t compressed_size = ZSTD_compressCCtx(enc->zstd_context,
enc->compressed_buffer, block_data_size * 2,
enc->block_data, block_data_size,
ZSTD_COMPRESSON_LEVEL);
int init_result = deflateInit2(&frame_stream, Z_DEFAULT_COMPRESSION,
Z_DEFLATED, 15 + 16, 8, Z_DEFAULT_STRATEGY); // 15+16 for gzip format
if (init_result != Z_OK) {
fprintf(stderr, "Failed to initialize gzip compression for frame\n");
if (ZSTD_isError(compressed_size)) {
fprintf(stderr, "Zstd compression failed: %s\n", ZSTD_getErrorName(compressed_size));
return 0;
}
// Set up compression stream
frame_stream.next_in = (Bytef*)enc->block_data;
frame_stream.avail_in = block_data_size;
frame_stream.next_out = (Bytef*)enc->compressed_buffer;
frame_stream.avail_out = block_data_size * 2;
int result = deflate(&frame_stream, Z_FINISH);
if (result != Z_STREAM_END) {
fprintf(stderr, "Gzip compression failed: %d\n", result);
deflateEnd(&frame_stream);
return 0;
}
size_t compressed_size = frame_stream.total_out;
// Clean up frame stream
deflateEnd(&frame_stream);
// Write frame packet header (rate control factor now per-block)
uint8_t packet_type = is_keyframe ? TEV_PACKET_IFRAME : TEV_PACKET_PFRAME;
uint32_t payload_size = compressed_size; // Rate control factor now per-block, not per-packet