Hacktoberfest 2026: những issue maintainer đã đánh dấu cho tháng Mười, đang mở và phù hợp người mới. Xem issue Hacktoberfest

[Proposal / discussion] Optional libvips backend for webp_transform

Đang mở
#13,773 0 bình luận 0 reaction 0 người được giao Xem trên GitHub

Maintainer thường phản hồi trong vòng 2 ngày

Chưa có ai nhận issue này.

Đánh giá

Độ khó
5/5
Thời gian dự kiến
Hơn một tuần
Mức phù hợp với người mới
25/100
Loại issue
Tính năng
Độ rõ ràng
Cần làm rõ
Mức độ hoạt động
Sôi nổi
Công nghệ
cmake, cpp
Lĩnh vực
backend, build-system

Hướng nghiên cứu

Start with ImageTransform.cc and the proposed CMake builds, then review the libvips and ImageMagick backend trade-offs described in the issue. Done means reaching a decision on whether to pursue libvips, which plugin form to use, and how to handle licensing, RSS behavior, and the experimental/magick relationship.

Do mô hình lập chỉ mục viết ra từ nội dung của issue.

Mô tả

New Feature

This is a proposal for discussion, not a request to merge. It summarizes an evaluation of libvips as an alternative to ImageMagick for webp_transform, including trade-offs that argue against switching. Input from the community is wanted on whether to pursue it and in what form.

Motivation: attack surface

webp_transform decodes untrusted origin bodies on ET_NET threads. The case for libvips is security, not speed.

Advisory history, counted on the same basis for both libraries:

source ImageMagick libvips
NVD keyword match about 860 about 29 (many assigned by VulDB in 2026)
GitHub security advisories the 100 most recent span 2026-05-30 to 2026-09-27 12 in total, since 2023

ImageMagick:

  • Several recent advisories appear, from their descriptions, to be reachable through plain JPEG/PNG/WebP reads that a security policy cannot block. This has not been verified against the plugin's code path.
    • XMP profile parsing: DoS, infinite loop, use-after-free, over-read
    • JPEG decoder information disclosure
    • 8BIM use-after-free (identify path)
  • Image::read() sniffs the format itself, so a coder allowlist depends on a correct policy.xml.

libvips:

  • In a build with only jpeg/png/webp/exif enabled, one of the 12 GitHub advisories is reachable: an EXIF NULL dereference, fixed in 8.18.2.
  • The rest are in tiff, heif, svg, pdf, gif, radiance, ppm-source, the vips native format, and conversion ops the plugin doesn't call.
  • The plugin already knows the format from its signature check, so it can call vips_jpegload_buffer / vips_pngload_buffer / vips_webpload_buffer directly. libvips never sniffs.
  • vips_operation_block_set() can block every other loader as defence in depth.
  • New third-party parsers come with it: libexif (24 NVD entries, 4 in 2026; optional, though disabling it drops EXIF passthrough), lcms2 (needed only for CMYK JPEGs) and GLib.

Not a motivation: speed or output size

  • Throughput and CPU are a tie. libjpeg and libwebp do the work in both.
    • At matched quality, standalone per-image latency is within about ±10% across image classes (measured against ImageMagick 7.1.0-1).
    • Inside traffic_server with 16 clients, throughput is the same: 88–100 rps for ImageMagick 7.1.2-32 vs 92 rps for libvips, on 8 vCPU.
  • Output size at equal quality matches within 1–4%.

Memory: better per image, worse per process (open risk)

Peak memory per transcode is 28–48% lower with libvips. ImageMagick 7 (Q16 HDRI) holds pixels as floats.

image ImageMagick libvips
1920x1277 JPEG -> WebP 55 MB 29 MB

Inside traffic_server, process RSS is worse with libvips (jemalloc linked, default settings, 8 ET_NET threads, sustained transform load):

setup mean RSS
ImageMagick 411 MB
libvips 631 MB
libvips + jemalloc narenas:8 344 MB
ImageMagick + jemalloc narenas:8 351 MB
  • Cause: libvips does pixel work on its own worker threads. jemalloc's default of 4 arenas per CPU then keeps freed memory in many arenas. Allocator tuning closes the gap, but that is a process-wide setting.
  • Unknown: behaviour on hosts with many more cores.
  • Hazard: capping libvips' thread pool (VIPS_MAX_THREADS=8) hung traffic_server under load. The cause wasn't confirmed (no thread dump was taken). The plugin wouldn't set it, but it is a sharp edge.

Licensing

  • libvips and GLib are LGPL-2.1+, Category X under ASF policy.
  • A libvips backend can only be an optional, separately installed dependency, never bundled: "the component is only needed for optional features" (https://www.apache.org/legal/resolved.html).
  • webp_transform is already built only when its image library is found.

What a prototype looks like

  • Interface: a small Transcoder interface (init(), transcode()) with ImageMagick and libvips implementations. ImageTransform.cc keeps all HTTP logic.
  • Builds: CMake builds webp_transform.so (ImageMagick) and/or webp_transform_vips.so (libvips >= 8.13 via pkg-config).
  • libvips settings:
    • vips_concurrency_set(1)
    • vips_cache_set_max(0)
    • vips_block_untrusted_set(TRUE)
    • all loaders blocked except the three buffer loaders
    • sequential access with fail_on=error
    • dimensions checked from the header before any pixels are decoded
  • Behaviour matches the ImageMagick backend on the edge cases tested:
    • oversized, truncated and mislabeled bodies pass through
    • CMYK converts with lcms2 (colours differ slightly for CMYK files without an embedded profile)
    • EXIF orientation is preserved
  • Differences to account for:
    • Error log strings differ. webp_transform_decode_limit matches ImageMagick.. error.
    • libvips writes an EXIF block, so its JPEGs have no JFIF APP0 marker. webp_transform_invalid_input checks for JFIF.
    • Output quality must be explicit, because libvips has no source-quality estimate. This fits the quality proposal in #13772.

Related: experimental/magick

plugins/experimental/magick runs ImageMagick command lines (MagickCommandGenesis), which can't be ported to libvips. A libvips webp_transform would not remove ImageMagick from builds that enable experimental plugins.

Questions for discussion

  1. Is reduced attack surface worth an LGPL optional dependency (libvips + GLib) and a second backend to maintain?
  2. If yes, should libvips be an alternative build of the same plugin, a separate plugin, or eventually the only backend?
  3. Can we accept the RSS behaviour under default jemalloc settings, or would we need guidance or tuning? Data from larger hosts would help.
  4. Should experimental/magick stay as is, independent of this?

Method

  • Host: 8 vCPU (Ice Lake), EL9, gcc 11.
  • Libraries: ImageMagick 7.1.2-32 (Q16 HDRI, OpenMP, open policy; standalone latency also on 7.1.0-1); libvips 8.18.7 (meson, jpeg/png/webp/exif/lcms2 only).
  • Codecs: libwebp 1.2.0, libpng 1.6.37, libjpeg-turbo 2.0.90.
  • Corpus:
    • 36 web JPEGs (500–1920 px)
    • 24 Kodak PNGs
    • 8 RGBA logos
    • 28 WebP
    • edge cases
  • Test: traffic_server master (RelWithDebInfo, jemalloc 5.2.1), cache off for load runs, 16 clients for 60 s, RSS sampled every second.
  • Harness and full data available on request.
Ngôn ngữ chính
C++
Star
2k
Fork
878
Merge trung bình
3 ngày 16 giờ
Pull request đã merge (30 ngày)
95

Chuẩn bị môi trường

Bắt đầu từ đâu

  1. Đọc hết issue, rồi đọc hướng dẫn đóng góp của dự án.
  2. Bình luận trên issue rằng bạn sẽ nhận — tránh hai người làm cùng một việc.
  3. Fork repository và làm thay đổi trên một nhánh.
  4. Mở pull request có tham chiếu số hiệu của issue.

Issue khác của apache/trafficserver

Tất cả issue của apache/trafficserver

Issue tương tự

Thêm issue về C++

Nhận issue mới trong hộp thư của bạn

Bản tóm tắt ngắn những issue GitHub phù hợp với người mới.