diff --git a/lang/luajit2/Makefile b/lang/luajit2/Makefile index 86dc280187..756381374e 100644 --- a/lang/luajit2/Makefile +++ b/lang/luajit2/Makefile @@ -1,12 +1,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=luajit2 -PKG_VERSION:=2.1-20230410 +PKG_VERSION:=2.1-20231006 PKG_RELEASE:=1 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz PKG_SOURCE_URL:=https://github.com/openresty/luajit2/archive/refs/tags/v$(PKG_VERSION).tar.gz? -PKG_HASH:=77bbcbb24c3c78f51560017288f3118d995fe71240aa379f5818ff6b166712ff +PKG_HASH:=41530b3f00d3f284e771cfd09add2a0c672f1214f8780644ca9261da9e4d9310 PKG_MAINTAINER:=Javier Marcet PKG_LICENSE:=MIT diff --git a/lang/luajit2/patches/010-lua-path.patch b/lang/luajit2/patches/010-lua-path.patch index f752002d22..dccdee2140 100644 --- a/lang/luajit2/patches/010-lua-path.patch +++ b/lang/luajit2/patches/010-lua-path.patch @@ -8,6 +8,6 @@ -#define LUA_LUADIR "/lua/5.1/" +#define LUA_LROOT "/usr" +#define LUA_LUADIR "/lua/" - #define LUA_LJDIR "/luajit-2.1.0-beta3/" + #define LUA_LJDIR "/luajit-2.1/" #ifdef LUA_ROOT diff --git a/lang/python/python-texttable/Makefile b/lang/python/python-texttable/Makefile index 98f6ec98ea..20fec724cf 100644 --- a/lang/python/python-texttable/Makefile +++ b/lang/python/python-texttable/Makefile @@ -1,11 +1,11 @@ include $(TOPDIR)/rules.mk PKG_NAME:=python-texttable -PKG_VERSION:=1.6.7 +PKG_VERSION:=1.7.0 PKG_RELEASE:=1 PYPI_NAME:=texttable -PKG_HASH:=290348fb67f7746931bcdfd55ac7584ecd4e5b0846ab164333f0794b121760f2 +PKG_HASH:=2d2068fb55115807d3ac77a4ca68fa48803e84ebb0ee2340f858107a36522638 PKG_MAINTAINER:=Javier Marcet PKG_LICENSE:=MIT diff --git a/lang/python/python-websocket-client/Makefile b/lang/python/python-websocket-client/Makefile index 3044b2eb59..c3173ce1ed 100644 --- a/lang/python/python-websocket-client/Makefile +++ b/lang/python/python-websocket-client/Makefile @@ -1,11 +1,11 @@ include $(TOPDIR)/rules.mk PKG_NAME:=python-websocket-client -PKG_VERSION:=1.6.2 +PKG_VERSION:=1.6.4 PKG_RELEASE:=1 PYPI_NAME:=websocket-client -PKG_HASH:=53e95c826bf800c4c465f50093a8c4ff091c7327023b10bfaff40cf1ef170eaa +PKG_HASH:=b3324019b3c28572086c4a319f91d1dcd44e6e11cd340232978c684a7650d0df PKG_MAINTAINER:=Javier Marcet PKG_LICENSE:=Apache-2.0 diff --git a/lang/rust/Makefile b/lang/rust/Makefile index 7785e95f13..f3189b5bf7 100644 --- a/lang/rust/Makefile +++ b/lang/rust/Makefile @@ -5,12 +5,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=rust -PKG_VERSION:=1.72.0 -PKG_RELEASE:=3 +PKG_VERSION:=1.73.0 +PKG_RELEASE:=1 PKG_SOURCE:=rustc-$(PKG_VERSION)-src.tar.gz PKG_SOURCE_URL:=https://static.rust-lang.org/dist/ -PKG_HASH:=ea9d61bbb51d76b6ea681156f69f0e0596b59722f04414b01c6e100b4b5be3a1 +PKG_HASH:=96d62e6d1f2d21df7ac8acb3b9882411f9e7c7036173f7f2ede9e1f1f6b1bb3a HOST_BUILD_DIR:=$(BUILD_DIR)/host/rustc-$(PKG_VERSION)-src PKG_MAINTAINER:=Luca Barbato @@ -52,6 +52,7 @@ TARGET_CONFIGURE_ARGS = \ --set=target.$(RUSTC_TARGET_ARCH).cxx=$(TARGET_CXX_NOCACHE) \ --set=target.$(RUSTC_TARGET_ARCH).linker=$(TARGET_CC_NOCACHE) \ --set=target.$(RUSTC_TARGET_ARCH).ranlib=$(TARGET_RANLIB) \ + --set=target.$(RUSTC_TARGET_ARCH).crt-static=false \ $(if $(CONFIG_USE_MUSL),--set=target.$(RUSTC_TARGET_ARCH).musl-root=$(TOOLCHAIN_DIR)) # CARGO_HOME is an environmental diff --git a/lang/rust/patches/0001-Update-xz2-and-use-it-static.patch b/lang/rust/patches/0001-Update-xz2-and-use-it-static.patch index c5266669db..f2a40f76b9 100644 --- a/lang/rust/patches/0001-Update-xz2-and-use-it-static.patch +++ b/lang/rust/patches/0001-Update-xz2-and-use-it-static.patch @@ -11,7 +11,7 @@ Subject: [PATCH] Update xz2 and use it static --- a/src/bootstrap/Cargo.lock +++ b/src/bootstrap/Cargo.lock -@@ -430,9 +430,9 @@ dependencies = [ +@@ -434,9 +434,9 @@ dependencies = [ [[package]] name = "lzma-sys" @@ -23,7 +23,7 @@ Subject: [PATCH] Update xz2 and use it static dependencies = [ "cc", "libc", -@@ -899,9 +899,9 @@ dependencies = [ +@@ -903,9 +903,9 @@ dependencies = [ [[package]] name = "xz2" diff --git a/lang/rust/patches/0002-rustc-bootstrap-cache.patch b/lang/rust/patches/0002-rustc-bootstrap-cache.patch index 670ba11628..9f434fc8df 100644 --- a/lang/rust/patches/0002-rustc-bootstrap-cache.patch +++ b/lang/rust/patches/0002-rustc-bootstrap-cache.patch @@ -1,6 +1,6 @@ --- a/src/bootstrap/bootstrap.py +++ b/src/bootstrap/bootstrap.py -@@ -543,7 +543,7 @@ class RustBuild(object): +@@ -546,7 +546,7 @@ class RustBuild(object): shutil.rmtree(bin_root) key = self.stage0_compiler.date @@ -11,7 +11,7 @@ os.makedirs(rustc_cache) --- a/src/bootstrap/download.rs +++ b/src/bootstrap/download.rs -@@ -507,7 +507,10 @@ impl Config { +@@ -520,7 +520,10 @@ impl Config { key: &str, destination: &str, ) { @@ -23,10 +23,10 @@ let cache_dir = cache_dst.join(key); if !cache_dir.exists() { t!(fs::create_dir_all(&cache_dir)); -@@ -627,7 +630,10 @@ download-rustc = false +@@ -647,7 +650,10 @@ download-rustc = false let llvm_assertions = self.llvm_assertions; - let cache_prefix = format!("llvm-{}-{}", llvm_sha, llvm_assertions); + let cache_prefix = format!("llvm-{llvm_sha}-{llvm_assertions}"); - let cache_dst = self.out.join("cache"); + let cache_dst = match env::var_os("OPENWRT_RUSTC_BOOTSTRAP_CACHE") { + Some(v) => PathBuf::from(v), diff --git a/lang/rust/patches/0003-bump-libc-deps-to-0.2.146.patch b/lang/rust/patches/0003-bump-libc-deps-to-0.2.146.patch new file mode 100644 index 0000000000..bd1c4b589a --- /dev/null +++ b/lang/rust/patches/0003-bump-libc-deps-to-0.2.146.patch @@ -0,0 +1,156 @@ +This patch bumps all libc dependencies and checksums to 0.2.146, which includes the fix for musl 1.2.4. + +--- a/vendor/addr2line-0.20.0/Cargo.lock ++++ b/vendor/addr2line-0.20.0/Cargo.lock +@@ -246,9 +246,9 @@ checksum = "e2abad23fbc42b3700f2f279844d + + [[package]] + name = "libc" +-version = "0.2.141" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "3304a64d199bb964be99741b7a14d26972741915b3649639149b2479bb46f4b5" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "libtest-mimic" +--- a/vendor/backtrace-0.3.67/Cargo.lock ++++ b/vendor/backtrace-0.3.67/Cargo.lock +@@ -64,9 +64,9 @@ checksum = "dec7af912d60cdbd3677c1af9352 + + [[package]] + name = "libc" +-version = "0.2.138" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "db6d7e329c562c5dfab7a46a2afabc8b987ab9a4834c9d1ca04dc54c1546cef8" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "libloading" +--- a/vendor/bstr/Cargo.lock ++++ b/vendor/bstr/Cargo.lock +@@ -34,9 +34,9 @@ dependencies = [ + + [[package]] + name = "libc" +-version = "0.2.138" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "db6d7e329c562c5dfab7a46a2afabc8b987ab9a4834c9d1ca04dc54c1546cef8" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "memchr" +--- a/vendor/cranelift-jit/Cargo.lock ++++ b/vendor/cranelift-jit/Cargo.lock +@@ -224,9 +224,9 @@ dependencies = [ + + [[package]] + name = "libc" +-version = "0.2.141" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "3304a64d199bb964be99741b7a14d26972741915b3649639149b2479bb46f4b5" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "log" +--- a/vendor/crossbeam-channel/Cargo.lock ++++ b/vendor/crossbeam-channel/Cargo.lock +@@ -50,9 +50,9 @@ dependencies = [ + + [[package]] + name = "libc" +-version = "0.2.141" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "3304a64d199bb964be99741b7a14d26972741915b3649639149b2479bb46f4b5" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "num_cpus" +--- a/vendor/elasticlunr-rs/Cargo.lock ++++ b/vendor/elasticlunr-rs/Cargo.lock +@@ -555,9 +555,9 @@ checksum = "e2abad23fbc42b3700f2f279844d + + [[package]] + name = "libc" +-version = "0.2.140" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "99227334921fae1a979cf0bfdfcc6b3e5ce376ef57e16fb6fb3ea2ed6095f80c" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "lindera" +--- a/vendor/handlebars/Cargo.lock ++++ b/vendor/handlebars/Cargo.lock +@@ -550,9 +550,9 @@ checksum = "e2abad23fbc42b3700f2f279844d + + [[package]] + name = "libc" +-version = "0.2.140" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "99227334921fae1a979cf0bfdfcc6b3e5ce376ef57e16fb6fb3ea2ed6095f80c" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "lock_api" +--- a/vendor/icu_locid/Cargo.lock ++++ b/vendor/icu_locid/Cargo.lock +@@ -318,9 +318,9 @@ checksum = "e2abad23fbc42b3700f2f279844d + + [[package]] + name = "libc" +-version = "0.2.141" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "3304a64d199bb964be99741b7a14d26972741915b3649639149b2479bb46f4b5" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "litemap" +--- a/vendor/libffi/Cargo.lock ++++ b/vendor/libffi/Cargo.lock +@@ -10,9 +10,9 @@ checksum = "50d30906286121d95be3d479533b + + [[package]] + name = "libc" +-version = "0.2.140" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "99227334921fae1a979cf0bfdfcc6b3e5ce376ef57e16fb6fb3ea2ed6095f80c" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "libffi" +--- a/vendor/terminal_size/Cargo.lock ++++ b/vendor/terminal_size/Cargo.lock +@@ -47,9 +47,9 @@ dependencies = [ + + [[package]] + name = "libc" +-version = "0.2.140" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "99227334921fae1a979cf0bfdfcc6b3e5ce376ef57e16fb6fb3ea2ed6095f80c" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "linux-raw-sys" +--- a/vendor/tracing-tree/Cargo.lock ++++ b/vendor/tracing-tree/Cargo.lock +@@ -100,9 +100,9 @@ checksum = "e2abad23fbc42b3700f2f279844d + + [[package]] + name = "libc" +-version = "0.2.141" ++version = "0.2.146" + source = "registry+https://github.com/rust-lang/crates.io-index" +-checksum = "3304a64d199bb964be99741b7a14d26972741915b3649639149b2479bb46f4b5" ++checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" + + [[package]] + name = "log" diff --git a/libs/h2o/Makefile b/libs/h2o/Makefile index 30241356fa..9ff131de36 100644 --- a/libs/h2o/Makefile +++ b/libs/h2o/Makefile @@ -2,7 +2,7 @@ include $(TOPDIR)/rules.mk PKG_NAME:=h2o PKG_VERSION:=2.2.6 -PKG_RELEASE:=14 +PKG_RELEASE:=15 PKG_SOURCE_URL:=https://codeload.github.com/h2o/h2o/tar.gz/v${PKG_VERSION}? PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz diff --git a/libs/h2o/patches/900-cve-2023-44487.patch b/libs/h2o/patches/900-cve-2023-44487.patch new file mode 100644 index 0000000000..d5489d5a62 --- /dev/null +++ b/libs/h2o/patches/900-cve-2023-44487.patch @@ -0,0 +1,203 @@ +commit d07b601a5549798f8e500582336756e04dfd25c5 +Author: Remi Gacogne +Date: Tue Oct 10 15:47:57 2023 +0200 + + [http2] delay processing requests upon observing suspicious behavior + + Backport of 94fbc54b6c9309912fe3d53e7b63408bbe9a1b0d to v2.2.x + +--- a/include/h2o.h ++++ b/include/h2o.h +@@ -378,6 +378,10 @@ struct st_h2o_globalconf_t { + * list of callbacks + */ + h2o_protocol_callbacks_t callbacks; ++ /** ++ * milliseconds to delay processing requests when suspicious behavior is detected ++ */ ++ uint64_t dos_delay; + } http2; + + struct { +@@ -590,6 +594,10 @@ struct st_h2o_context_t { + * timeout entry used for graceful shutdown + */ + h2o_timeout_entry_t _graceful_shutdown_timeout; ++ /* ++ * dos timeout ++ */ ++ h2o_timeout_t dos_delay_timeout; + struct { + /** + * counter for http2 errors internally emitted by h2o +--- a/include/h2o/http2_internal.h ++++ b/include/h2o/http2_internal.h +@@ -179,6 +179,7 @@ struct st_h2o_http2_stream_t { + h2o_linklist_t link; + h2o_http2_scheduler_openref_t scheduler; + } _refs; ++ unsigned reset_by_peer : 1; + h2o_send_state_t send_state; /* state of the ostream, only used in push mode */ + /* placed at last since it is large and has it's own ctor */ + h2o_req_t req; +@@ -232,6 +233,13 @@ struct st_h2o_http2_conn_t { + } _write; + h2o_cache_t *push_memo; + h2o_http2_casper_t *casper; ++ /** ++ * DoS mitigation; the idea here is to delay processing requests when observing suspicious behavior ++ */ ++ struct { ++ h2o_timeout_entry_t process_delay; ++ size_t reset_budget; /* RST_STREAM frames are considered suspicious when this value goes down to zero */ ++ } dos_mitigation; + }; + + int h2o_http2_update_peer_settings(h2o_http2_settings_t *settings, const uint8_t *src, size_t len, const char **err_desc); +--- a/lib/core/config.c ++++ b/lib/core/config.c +@@ -196,6 +196,7 @@ void h2o_config_init(h2o_globalconf_t *c + config->http2.latency_optimization.min_rtt = 50; // milliseconds + config->http2.latency_optimization.max_additional_delay = 10; + config->http2.latency_optimization.max_cwnd = 65535; ++ config->http2.dos_delay = 100; /* 100ms processing delay when observing suspicious behavior */ + config->http2.callbacks = H2O_HTTP2_CALLBACKS; + // config->mimemap = h2o_mimemap_create(); + +--- a/lib/core/configurator.c ++++ b/lib/core/configurator.c +@@ -531,6 +531,12 @@ static int on_config_http2_casper(h2o_co + return 0; + } + ++ ++static int on_config_http2_dos_delay(h2o_configurator_command_t *cmd, h2o_configurator_context_t *ctx, yoml_t *node) ++{ ++ return config_timeout(cmd, node, &ctx->globalconf->http2.dos_delay); ++} ++ + static int assert_is_mimetype(h2o_configurator_command_t *cmd, yoml_t *node) + { + if (node->type != YOML_TYPE_SCALAR) { +@@ -910,6 +916,9 @@ void h2o_configurator__init_core(h2o_glo + on_config_http2_push_preload); + h2o_configurator_define_command(&c->super, "http2-casper", H2O_CONFIGURATOR_FLAG_GLOBAL | H2O_CONFIGURATOR_FLAG_HOST, + on_config_http2_casper); ++ h2o_configurator_define_command(&c->super, "http2-dos-delay", ++ H2O_CONFIGURATOR_FLAG_GLOBAL | H2O_CONFIGURATOR_FLAG_EXPECT_SCALAR, ++ on_config_http2_dos_delay); + h2o_configurator_define_command(&c->super, "file.mime.settypes", + (H2O_CONFIGURATOR_FLAG_ALL_LEVELS & ~H2O_CONFIGURATOR_FLAG_EXTENSION) | + H2O_CONFIGURATOR_FLAG_EXPECT_MAPPING, +--- a/lib/core/context.c ++++ b/lib/core/context.c +@@ -101,6 +101,7 @@ void h2o_context_init(h2o_context_t *ctx + h2o_linklist_init_anchor(&ctx->http1._conns); + h2o_timeout_init(ctx->loop, &ctx->http2.idle_timeout, config->http2.idle_timeout); + h2o_timeout_init(ctx->loop, &ctx->http2.graceful_shutdown_timeout, config->http2.graceful_shutdown_timeout); ++ h2o_timeout_init(ctx->loop, &ctx->http2.dos_delay_timeout, config->http2.dos_delay); + h2o_linklist_init_anchor(&ctx->http2._conns); + ctx->proxy.client_ctx.loop = loop; + h2o_timeout_init(ctx->loop, &ctx->proxy.io_timeout, config->proxy.io_timeout); +@@ -146,6 +147,7 @@ void h2o_context_dispose(h2o_context_t * + h2o_timeout_dispose(ctx->loop, &ctx->http1.req_timeout); + h2o_timeout_dispose(ctx->loop, &ctx->http2.idle_timeout); + h2o_timeout_dispose(ctx->loop, &ctx->http2.graceful_shutdown_timeout); ++ h2o_timeout_dispose(ctx->loop, &ctx->http2.dos_delay_timeout); + h2o_timeout_dispose(ctx->loop, &ctx->proxy.io_timeout); + /* what should we do here? assert(!h2o_linklist_is_empty(&ctx->http2._conns); */ + +--- a/lib/http2/connection.c ++++ b/lib/http2/connection.c +@@ -161,7 +161,6 @@ static void update_idle_timeout(h2o_http + h2o_timeout_unlink(&conn->_timeout_entry); + + if (conn->num_streams.pull.half_closed + conn->num_streams.push.half_closed == 0) { +- assert(h2o_linklist_is_empty(&conn->_pending_reqs)); + conn->_timeout_entry.cb = on_idle_timeout; + h2o_timeout_link(conn->super.ctx->loop, &conn->super.ctx->http2.idle_timeout, &conn->_timeout_entry); + } +@@ -175,6 +174,9 @@ static int can_run_requests(h2o_http2_co + + static void run_pending_requests(h2o_http2_conn_t *conn) + { ++ if (h2o_timeout_is_linked(&conn->dos_mitigation.process_delay)) ++ return; ++ + while (!h2o_linklist_is_empty(&conn->_pending_reqs) && can_run_requests(conn)) { + /* fetch and detach a pending stream */ + h2o_http2_stream_t *stream = H2O_STRUCT_FROM_MEMBER(h2o_http2_stream_t, _refs.link, conn->_pending_reqs.next); +@@ -226,6 +228,16 @@ void h2o_http2_conn_unregister_stream(h2 + assert(h2o_http2_scheduler_is_open(&stream->_refs.scheduler)); + h2o_http2_scheduler_close(&stream->_refs.scheduler); + ++ /* Decrement reset_budget if the stream was reset by peer, otherwise increment. By doing so, we penalize connections that ++ * generate resets for >50% of requests. */ ++ if (stream->reset_by_peer) { ++ if (conn->dos_mitigation.reset_budget > 0) ++ --conn->dos_mitigation.reset_budget; ++ } else { ++ if (conn->dos_mitigation.reset_budget < conn->super.ctx->globalconf->http2.max_concurrent_requests_per_connection) ++ ++conn->dos_mitigation.reset_budget; ++ } ++ + switch (stream->state) { + case H2O_HTTP2_STREAM_STATE_IDLE: + case H2O_HTTP2_STREAM_STATE_RECV_HEADERS: +@@ -272,6 +284,8 @@ void close_connection_now(h2o_http2_conn + h2o_hpack_dispose_header_table(&conn->_output_header_table); + assert(h2o_linklist_is_empty(&conn->_pending_reqs)); + h2o_timeout_unlink(&conn->_timeout_entry); ++ if (h2o_timeout_is_linked(&conn->dos_mitigation.process_delay)) ++ h2o_timeout_unlink(&conn->dos_mitigation.process_delay); + h2o_buffer_dispose(&conn->_write.buf); + if (conn->_write.buf_in_flight != NULL) + h2o_buffer_dispose(&conn->_write.buf_in_flight); +@@ -797,11 +811,19 @@ static int handle_rst_stream_frame(h2o_h + return H2O_HTTP2_ERROR_PROTOCOL; + } + +- stream = h2o_http2_conn_get_stream(conn, frame->stream_id); +- if (stream != NULL) { ++ if ((stream = h2o_http2_conn_get_stream(conn, frame->stream_id)) == NULL) ++ return 0; ++ + /* reset the stream */ ++ stream->reset_by_peer = 1; + h2o_http2_stream_reset(conn, stream); +- } ++ ++ /* setup process delay if we've just ran out of reset budget */ ++ if (conn->dos_mitigation.reset_budget == 0 && conn->super.ctx->globalconf->http2.dos_delay != 0 && ++ !h2o_timeout_is_linked(&conn->dos_mitigation.process_delay)) ++ h2o_timeout_link(conn->super.ctx->loop, &conn->super.ctx->http2.dos_delay_timeout, ++ &conn->dos_mitigation.process_delay); ++ + /* TODO log */ + + return 0; +@@ -1204,6 +1226,14 @@ static h2o_iovec_t log_priority_actual_w + return h2o_iovec_init(s, len); + } + ++static void on_dos_process_delay(h2o_timeout_entry_t *timer) ++{ ++ h2o_http2_conn_t *conn = H2O_STRUCT_FROM_MEMBER(h2o_http2_conn_t, dos_mitigation.process_delay, timer); ++ ++ assert(!h2o_timeout_is_linked(&conn->dos_mitigation.process_delay)); ++ run_pending_requests(conn); ++} ++ + static h2o_http2_conn_t *create_conn(h2o_context_t *ctx, h2o_hostconf_t **hosts, h2o_socket_t *sock, struct timeval connected_at) + { + static const h2o_conn_callbacks_t callbacks = { +@@ -1240,6 +1270,9 @@ static h2o_http2_conn_t *create_conn(h2o + conn->_write.timeout_entry.cb = emit_writereq; + h2o_http2_window_init(&conn->_write.window, &conn->peer_settings); + ++ conn->dos_mitigation.process_delay.cb = on_dos_process_delay; ++ conn->dos_mitigation.reset_budget = conn->super.ctx->globalconf->http2.max_concurrent_requests_per_connection; ++ + return conn; + } + diff --git a/libs/h2o/patches/901-bump-soname.patch b/libs/h2o/patches/901-bump-soname.patch new file mode 100644 index 0000000000..6ae3c225ba --- /dev/null +++ b/libs/h2o/patches/901-bump-soname.patch @@ -0,0 +1,35 @@ +commit e47cd15ff1fec9211088c809cb92593800dd4da2 +Author: Peter van Dijk +Date: Wed Oct 11 11:39:48 2023 +0200 + + bump soname + +--- a/CMakeLists.txt ++++ b/CMakeLists.txt +@@ -29,9 +29,9 @@ SET(VERSION_MINOR "2") + SET(VERSION_PATCH "6") + SET(VERSION_PRERELEASE "") + SET(VERSION "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}${VERSION_PRERELEASE}") +-SET(LIBRARY_VERSION_MAJOR "0") +-SET(LIBRARY_VERSION_MINOR "13") +-SET(LIBRARY_VERSION_PATCH "6") ++SET(LIBRARY_VERSION_MAJOR "1") ++SET(LIBRARY_VERSION_MINOR "0") ++SET(LIBRARY_VERSION_PATCH "0") + SET(LIBRARY_VERSION "${LIBRARY_VERSION_MAJOR}.${LIBRARY_VERSION_MINOR}.${LIBRARY_VERSION_PATCH}${VERSION_PRERELEASE}") + SET(LIBRARY_SOVERSION "${LIBRARY_VERSION_MAJOR}.${LIBRARY_VERSION_MINOR}") + +--- a/include/h2o/version.h ++++ b/include/h2o/version.h +@@ -28,8 +28,8 @@ + #define H2O_VERSION_MINOR 2 + #define H2O_VERSION_PATCH 6 + +-#define H2O_LIBRARY_VERSION_MAJOR 0 +-#define H2O_LIBRARY_VERSION_MINOR 13 +-#define H2O_LIBRARY_VERSION_PATCH 6 ++#define H2O_LIBRARY_VERSION_MAJOR 1 ++#define H2O_LIBRARY_VERSION_MINOR 0 ++#define H2O_LIBRARY_VERSION_PATCH 0 + + #endif diff --git a/libs/openblas/Makefile b/libs/openblas/Makefile index 3894788581..0b403f21bf 100644 --- a/libs/openblas/Makefile +++ b/libs/openblas/Makefile @@ -5,12 +5,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=OpenBLAS -PKG_VERSION:=0.3.23 +PKG_VERSION:=0.3.24 PKG_RELEASE:=1 PKG_SOURCE:=OpenBLAS-$(PKG_VERSION).tar.gz PKG_SOURCE_URL:=https://github.com/xianyi/OpenBLAS/releases/download/v$(PKG_VERSION)/ -PKG_HASH:=5d9491d07168a5d00116cdc068a40022c3455bf9293c7cb86a65b1054d7e5114 +PKG_HASH:=ceadc5065da97bd92404cac7254da66cc6eb192679cf1002098688978d4d5132 PKG_LICENSE:=BSD 3-Clause PKG_MAINTAINER:=Alexandru Ardelean diff --git a/net/dnsdist/Makefile b/net/dnsdist/Makefile index 50b0cfacb5..34b12e12e8 100644 --- a/net/dnsdist/Makefile +++ b/net/dnsdist/Makefile @@ -1,12 +1,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=dnsdist -PKG_VERSION:=1.8.1 +PKG_VERSION:=1.8.2 PKG_RELEASE:=1 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.bz2 PKG_SOURCE_URL:=https://downloads.powerdns.com/releases/ -PKG_HASH:=05f356fcce29c4ece03c2d8df046adff3aaab0b036d6801c1a311c6d5bb3c07f +PKG_HASH:=6688f09b2c52f9bf935f0769f4ee28dd0760e5622dade7b3f4e6fa3776f07ab8 PKG_MAINTAINER:=Peter van Dijk PKG_LICENSE:=GPL-2.0-only diff --git a/net/netbird/Makefile b/net/netbird/Makefile index 637df8dedd..729564d429 100644 --- a/net/netbird/Makefile +++ b/net/netbird/Makefile @@ -1,12 +1,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=netbird -PKG_VERSION:=0.23.6 +PKG_VERSION:=0.23.9 PKG_RELEASE:=1 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz PKG_SOURCE_URL:=https://codeload.github.com/netbirdio/netbird/tar.gz/v$(PKG_VERSION)? -PKG_HASH:=cb29e237652634f3a2a5774fdc239f615d46cf9339811c707744d1e03797126d +PKG_HASH:=1b037f35d3e426d8cbeba17e4d89d12265cd7e6fbd7c975ce552293e468db35a PKG_MAINTAINER:=Oskari Rauta PKG_LICENSE:=BSD-3-Clause diff --git a/net/nginx/patches/nginx-mod-lua/101-bugfix-don-t-include-pcre.h-with-PCRE2-used.patch b/net/nginx/patches/nginx-mod-lua/101-bugfix-don-t-include-pcre.h-with-PCRE2-used.patch new file mode 100644 index 0000000000..da3c4607da --- /dev/null +++ b/net/nginx/patches/nginx-mod-lua/101-bugfix-don-t-include-pcre.h-with-PCRE2-used.patch @@ -0,0 +1,27 @@ +From f968d74c3af8259f325090d282aeb64854cdddf9 Mon Sep 17 00:00:00 2001 +From: Christian Marangi +Date: Fri, 13 Oct 2023 20:23:51 +0200 +Subject: [PATCH] bugfix: don't include pcre.h with PCRE2 used + +pcre.h is a PCRE header and is not exposed by PCRE2 library causing +compilation error as the header is not found. + +Don't include pcre.h if nginx is compiled with PCRE2 support enabled. + +Fixes: cb83e33e2657 ("feature: support pcre2") +Signed-off-by: Christian Marangi +--- + nginx-mod-lua/src/ngx_http_lua_common.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/nginx-mod-lua/src/ngx_http_lua_common.h ++++ b/nginx-mod-lua/src/ngx_http_lua_common.h +@@ -54,7 +54,7 @@ typedef struct { + #endif + + +-#if (NGX_PCRE) ++#if defined(NGX_PCRE) && !(NGX_PCRE2) + #include + # if (PCRE_MAJOR > 8) || (PCRE_MAJOR == 8 && PCRE_MINOR >= 21) + # define LUA_HAVE_PCRE_JIT 1 diff --git a/utils/catatonit/Makefile b/utils/catatonit/Makefile index 5d78af25e7..973c171a3c 100644 --- a/utils/catatonit/Makefile +++ b/utils/catatonit/Makefile @@ -1,21 +1,19 @@ include $(TOPDIR)/rules.mk PKG_NAME:=catatonit -PKG_VERSION:=0.1.7 +PKG_VERSION:=0.2.0 PKG_RELEASE:=1 -PKG_SOURCE_PROTO:=git -PKG_SOURCE_URL:=https://github.com/openSUSE/catatonit.git -PKG_SOURCE_DATE:=2022-03-07 -PKG_SOURCE_VERSION:=d8d72fea155c144ed3bf298a35a1aba5625a5656 -PKG_MIRROR_HASH:=5dfec105de2b1e674db55e12007aa66cf67769d38e3f294fbca54fc3e9b78674 +PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz +PKG_SOURCE_URL:=https://codeload.github.com/openSUSE/catatonit/tar.gz/v$(PKG_VERSION)? +PKG_HASH:=d0cf1feffdc89c9fb52af20fc10127887a408bbd99e0424558d182b310a3dc92 PKG_BUILD_PARALLEL:=1 PKG_FIXUP:=autoreconf PKG_INSTALL:=1 PKG_MAINTAINER:=Oskari Rauta -PKG_LICENSE:=GPL-3.0-or-later +PKG_LICENSE:=GPL-2.0-or-later PKG_LICENSE_FILES:=COPYING include $(INCLUDE_DIR)/package.mk diff --git a/utils/podman/Makefile b/utils/podman/Makefile index 11afb8765c..7a785f5370 100644 --- a/utils/podman/Makefile +++ b/utils/podman/Makefile @@ -1,12 +1,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=podman -PKG_VERSION:=4.7.0 +PKG_VERSION:=4.7.1 PKG_RELEASE:=1 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz PKG_SOURCE_URL:=https://github.com/containers/podman/archive/v$(PKG_VERSION) -PKG_HASH:=8fbeab8a821c59ac10ade87c9597d7bb13be4f7868b438278a9f6a17c50bf20d +PKG_HASH:=b785fe69041a0f222a8e1f8165816d767cb9bff5418f3f559547da82c0c279cc PKG_LICENSE:=Apache-2.0 PKG_LICENSE_FILES:=LICENSE diff --git a/utils/podman/patches/020-fix-build-with-musl-1.2.4.patch b/utils/podman/patches/020-fix-build-with-musl-1.2.4.patch new file mode 100644 index 0000000000..9d56ca780b --- /dev/null +++ b/utils/podman/patches/020-fix-build-with-musl-1.2.4.patch @@ -0,0 +1,16 @@ +From https://github.com/mattn/go-sqlite3/pull/1177/commits/65d6085c5d87280c0d6883c884ddb25f9273942f Mon Sep 17 00:00:00 2001 +From: leso-kn +Date: Mon, 10 Jul 2023 14:58:52 +0200 +Subject: [PATCH] Fix musl build (#1164) + +--- a/vendor/github.com/mattn/go-sqlite3/sqlite3.go ++++ b/vendor/github.com/mattn/go-sqlite3/sqlite3.go +@@ -21,7 +21,7 @@ package sqlite3 + #cgo CFLAGS: -DSQLITE_DEFAULT_WAL_SYNCHRONOUS=1 + #cgo CFLAGS: -DSQLITE_ENABLE_UPDATE_DELETE_LIMIT + #cgo CFLAGS: -Wno-deprecated-declarations +-#cgo linux,!android CFLAGS: -DHAVE_PREAD64=1 -DHAVE_PWRITE64=1 ++#cgo linux,!android CFLAGS: -DHAVE_PREAD=1 -DHAVE_PWRITE=1 + #cgo openbsd CFLAGS: -I/usr/local/include + #cgo openbsd LDFLAGS: -L/usr/local/lib + #ifndef USE_LIBSQLITE3 diff --git a/utils/prometheus-node-exporter-lua/Makefile b/utils/prometheus-node-exporter-lua/Makefile index a69f5320d6..3ac56eefac 100644 --- a/utils/prometheus-node-exporter-lua/Makefile +++ b/utils/prometheus-node-exporter-lua/Makefile @@ -4,7 +4,7 @@ include $(TOPDIR)/rules.mk PKG_NAME:=prometheus-node-exporter-lua -PKG_VERSION:=2022.08.08 +PKG_VERSION:=2023.05.14 PKG_RELEASE:=1 PKG_MAINTAINER:=Etienne CHAMPETIER @@ -158,6 +158,17 @@ define Package/prometheus-node-exporter-lua-textfile/install $(INSTALL_BIN) ./files/usr/lib/lua/prometheus-collectors/textfile.lua $(1)/usr/lib/lua/prometheus-collectors/ endef +define Package/prometheus-node-exporter-lua-thermal + $(call Package/prometheus-node-exporter-lua/Default) + TITLE+= (thermal collector) + DEPENDS:=prometheus-node-exporter-lua +endef + +define Package/prometheus-node-exporter-lua-thermal/install + $(INSTALL_DIR) $(1)/usr/lib/lua/prometheus-collectors + $(INSTALL_BIN) ./files/usr/lib/lua/prometheus-collectors/thermal.lua $(1)/usr/lib/lua/prometheus-collectors/ +endef + define Package/prometheus-node-exporter-lua-ubnt-manager $(call Package/prometheus-node-exporter-lua/Default) TITLE+= (ubnt-manager collector) @@ -234,6 +245,7 @@ $(eval $(call BuildPackage,prometheus-node-exporter-lua-nat_traffic)) $(eval $(call BuildPackage,prometheus-node-exporter-lua-netstat)) $(eval $(call BuildPackage,prometheus-node-exporter-lua-openwrt)) $(eval $(call BuildPackage,prometheus-node-exporter-lua-textfile)) +$(eval $(call BuildPackage,prometheus-node-exporter-lua-thermal)) $(eval $(call BuildPackage,prometheus-node-exporter-lua-ubnt-manager)) $(eval $(call BuildPackage,prometheus-node-exporter-lua-uci_dhcp_host)) $(eval $(call BuildPackage,prometheus-node-exporter-lua-wifi)) diff --git a/utils/prometheus-node-exporter-lua/files/usr/lib/lua/prometheus-collectors/thermal.lua b/utils/prometheus-node-exporter-lua/files/usr/lib/lua/prometheus-collectors/thermal.lua new file mode 100644 index 0000000000..3996ea581b --- /dev/null +++ b/utils/prometheus-node-exporter-lua/files/usr/lib/lua/prometheus-collectors/thermal.lua @@ -0,0 +1,46 @@ +-- thermal collector +local function scrape() + local i = 0 + local temp_metric = metric("node_thermal_zone_temp", "gauge") + + while true do + local zonePath = "/sys/class/thermal/thermal_zone" .. i + + -- required attributes + + local typ = string.match(get_contents(zonePath .. "/type"), "^%s*(.-)%s*$") + if not typ then + break + end + + local policy = string.match(get_contents(zonePath .. "/policy"), "^%s*(.-)%s*$") + if not policy then + break + end + + local temp = string.match(get_contents(zonePath .. "/temp"), "(%d+)") + if not temp then + break + end + + local labels = {zone = i, type = typ, policy = policy} + + -- optional attributes + + local mode = string.match(get_contents(zonePath .. "/mode"), "^%s*(.-)%s*$") + if mode then + labels.mode = mode + end + + local passive = string.match(get_contents(zonePath .. "/passive"), "(%d+)") + if passive then + labels.passive = passive + end + + temp_metric(labels, temp / 1000) + + i = i + 1 + end +end + +return { scrape = scrape } diff --git a/utils/zsh/Makefile b/utils/zsh/Makefile index 6fc713a5db..e894bc6eeb 100644 --- a/utils/zsh/Makefile +++ b/utils/zsh/Makefile @@ -9,7 +9,7 @@ include $(TOPDIR)/rules.mk PKG_NAME:=zsh PKG_VERSION:=5.9 -PKG_RELEASE:=1 +PKG_RELEASE:=2 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.xz PKG_SOURCE_URL:=@SF/zsh @@ -20,10 +20,19 @@ PKG_LICENSE:=ZSH PKG_LICENSE_FILES:=LICENCE PKG_CPE_ID:=cpe:/a:zsh_project:zsh +PKG_FIXUP:=autoreconf PKG_BUILD_PARALLEL:=1 PKG_INSTALL:=1 PKG_BUILD_FLAGS:=gc-sections lto +# zsh include custom macro in the default aclocal.m4 +# When autoreconf PKG_FIXUP is used, if PKG_REMOVE_FILES +# is not defined, it's set to remove the file aclocak.m4 +# by default resulting in problem with the custom macro +# AC_PROG_LN +# To prevent this, declare empty PKG_REMOVE_FILES +PKG_REMOVE_FILES:= + include $(INCLUDE_DIR)/package.mk define Package/zsh @@ -31,7 +40,7 @@ define Package/zsh CATEGORY:=Utilities SUBMENU:=Shells TITLE:=The Z shell - DEPENDS:=+libcap +libncurses +libncursesw +libpcre +librt + DEPENDS:=+libcap +libncurses +libncursesw +libpcre2 +librt URL:=https://www.zsh.org/ endef diff --git a/utils/zsh/patches/001-50658-test-Enable-to-switch-between-C-UTF-8-locales-.patch b/utils/zsh/patches/001-50658-test-Enable-to-switch-between-C-UTF-8-locales-.patch new file mode 100644 index 0000000000..79e352a994 --- /dev/null +++ b/utils/zsh/patches/001-50658-test-Enable-to-switch-between-C-UTF-8-locales-.patch @@ -0,0 +1,71 @@ +From 1b421e4978440234fb73117c8505dad1ccc68d46 Mon Sep 17 00:00:00 2001 +From: Jun-ichi Takimoto +Date: Mon, 26 Sep 2022 10:52:50 +0900 +Subject: [PATCH] 50658 + test: Enable to switch between C/UTF-8 locales in + PCRE + +--- + ChangeLog | 5 +++++ + Src/Modules/pcre.c | 10 ++-------- + Test/V07pcre.ztst | 11 +++++++++++ + 3 files changed, 18 insertions(+), 8 deletions(-) + +# diff --git a/ChangeLog b/ChangeLog +# index 48c65d01b..77345c050 100644 +# --- a/ChangeLog +# +++ b/ChangeLog +# @@ -1,3 +1,8 @@ +# +2022-09-26 Jun-ichi Takimoto +# + +# + * 50658 + test: Src/Modules/pcre.c, Test/V07pcre.ztst: Enable to +# + switch between C/UTF-8 locales in PCRE +# + +# 2022-09-25 Peter Stephenson + +# * 50648: Functions/Misc/zcalc: Julian Prein: Use ZCALC_HISTFILE +--- a/Src/Modules/pcre.c ++++ b/Src/Modules/pcre.c +@@ -47,8 +47,6 @@ zpcre_utf8_enabled(void) + #if defined(MULTIBYTE_SUPPORT) && defined(HAVE_NL_LANGINFO) && defined(CODESET) + static int have_utf8_pcre = -1; + +- /* value can toggle based on MULTIBYTE, so don't +- * be too eager with caching */ + if (have_utf8_pcre < -1) + return 0; + +@@ -56,15 +54,11 @@ zpcre_utf8_enabled(void) + return 0; + + if ((have_utf8_pcre == -1) && +- (!strcmp(nl_langinfo(CODESET), "UTF-8"))) { +- +- if (pcre_config(PCRE_CONFIG_UTF8, &have_utf8_pcre)) ++ (pcre_config(PCRE_CONFIG_UTF8, &have_utf8_pcre))) { + have_utf8_pcre = -2; /* erk, failed to ask */ + } + +- if (have_utf8_pcre < 0) +- return 0; +- return have_utf8_pcre; ++ return (have_utf8_pcre == 1) && (!strcmp(nl_langinfo(CODESET), "UTF-8")); + + #else + return 0; +--- a/Test/V07pcre.ztst ++++ b/Test/V07pcre.ztst +@@ -174,3 +174,14 @@ + echo $match[2] ) + 0:regression for segmentation fault, workers/38307 + >test ++ ++ LANG_SAVE=$LANG ++ [[ é =~ '^.\z' ]]; echo $? ++ LANG=C ++ [[ é =~ '^..\z' ]]; echo $? ++ LANG=$LANG_SAVE ++ [[ é =~ '^.\z' ]]; echo $? ++0:swich between C/UTF-8 locales ++>0 ++>0 ++>0 diff --git a/utils/zsh/patches/002-51723-migrate-pcre-module-to-pcre2.patch b/utils/zsh/patches/002-51723-migrate-pcre-module-to-pcre2.patch new file mode 100644 index 0000000000..6e0b7f1e85 --- /dev/null +++ b/utils/zsh/patches/002-51723-migrate-pcre-module-to-pcre2.patch @@ -0,0 +1,540 @@ +From b62e911341c8ec7446378b477c47da4256053dc0 Mon Sep 17 00:00:00 2001 +From: Oliver Kiddle +Date: Sat, 13 May 2023 00:53:32 +0200 +Subject: [PATCH] 51723: migrate pcre module to pcre2 + +--- + ChangeLog | 3 + + Src/Modules/pcre.c | 223 ++++++++++++++++++--------------------------- + Test/V07pcre.ztst | 13 ++- + configure.ac | 20 ++-- + 4 files changed, 110 insertions(+), 149 deletions(-) + +# diff --git a/ChangeLog b/ChangeLog +# index f5c77f801..285b73b2c 100644 +# --- a/ChangeLog +# +++ b/ChangeLog +# @@ -1,5 +1,8 @@ +# 2023-05-13 Oliver Kiddle + +# + * 51723: Src/Modules/pcre.c, Test/V07pcre.ztst, configure.ac: +# + migrate pcre module to pcre2 +# + +# * Felipe Contreras: 50612: Misc/vcs_info-examples: fix typo + +# * github #98: Vidhan Bhatt: Completion/Darwin/Command/_shortcuts: +--- a/Src/Modules/pcre.c ++++ b/Src/Modules/pcre.c +@@ -34,11 +34,11 @@ + #define CPCRE_PLAIN 0 + + /**/ +-#if defined(HAVE_PCRE_COMPILE) && defined(HAVE_PCRE_EXEC) +-#include ++#if defined(HAVE_PCRE2_COMPILE_8) && defined(HAVE_PCRE2_H) ++#define PCRE2_CODE_UNIT_WIDTH 8 ++#include + +-static pcre *pcre_pattern; +-static pcre_extra *pcre_hints; ++static pcre2_code *pcre_pattern; + + /**/ + static int +@@ -54,8 +54,8 @@ zpcre_utf8_enabled(void) + return 0; + + if ((have_utf8_pcre == -1) && +- (pcre_config(PCRE_CONFIG_UTF8, &have_utf8_pcre))) { +- have_utf8_pcre = -2; /* erk, failed to ask */ ++ (pcre2_config(PCRE2_CONFIG_UNICODE, &have_utf8_pcre))) { ++ have_utf8_pcre = -2; /* erk, failed to ask */ + } + + return (have_utf8_pcre == 1) && (!strcmp(nl_langinfo(CODESET), "UTF-8")); +@@ -69,47 +69,38 @@ zpcre_utf8_enabled(void) + static int + bin_pcre_compile(char *nam, char **args, Options ops, UNUSED(int func)) + { +- int pcre_opts = 0, pcre_errptr, target_len; +- const char *pcre_error; ++ uint32_t pcre_opts = 0; ++ int target_len; ++ int pcre_error; ++ PCRE2_SIZE pcre_offset; + char *target; + +- if(OPT_ISSET(ops,'a')) pcre_opts |= PCRE_ANCHORED; +- if(OPT_ISSET(ops,'i')) pcre_opts |= PCRE_CASELESS; +- if(OPT_ISSET(ops,'m')) pcre_opts |= PCRE_MULTILINE; +- if(OPT_ISSET(ops,'x')) pcre_opts |= PCRE_EXTENDED; +- if(OPT_ISSET(ops,'s')) pcre_opts |= PCRE_DOTALL; ++ if (OPT_ISSET(ops, 'a')) pcre_opts |= PCRE2_ANCHORED; ++ if (OPT_ISSET(ops, 'i')) pcre_opts |= PCRE2_CASELESS; ++ if (OPT_ISSET(ops, 'm')) pcre_opts |= PCRE2_MULTILINE; ++ if (OPT_ISSET(ops, 'x')) pcre_opts |= PCRE2_EXTENDED; ++ if (OPT_ISSET(ops, 's')) pcre_opts |= PCRE2_DOTALL; + + if (zpcre_utf8_enabled()) +- pcre_opts |= PCRE_UTF8; +- +-#ifdef HAVE_PCRE_STUDY +- if (pcre_hints) +-#ifdef PCRE_CONFIG_JIT +- pcre_free_study(pcre_hints); +-#else +- pcre_free(pcre_hints); +-#endif +- pcre_hints = NULL; +-#endif ++ pcre_opts |= PCRE2_UTF; + + if (pcre_pattern) +- pcre_free(pcre_pattern); ++ pcre2_code_free(pcre_pattern); + pcre_pattern = NULL; + + target = ztrdup(*args); + unmetafy(target, &target_len); + +- if ((int)strlen(target) != target_len) { +- zwarnnam(nam, "embedded NULs in PCRE pattern terminate pattern"); +- } +- +- pcre_pattern = pcre_compile(target, pcre_opts, &pcre_error, &pcre_errptr, NULL); ++ pcre_pattern = pcre2_compile((PCRE2_SPTR) target, (PCRE2_SIZE) target_len, ++ pcre_opts, &pcre_error, &pcre_offset, NULL); + + free(target); + + if (pcre_pattern == NULL) + { +- zwarnnam(nam, "error in regex: %s", pcre_error); ++ PCRE2_UCHAR buffer[256]; ++ pcre2_get_error_message(pcre_error, buffer, sizeof(buffer)); ++ zwarnnam(nam, "error in regex: %s", buffer); + return 1; + } + +@@ -117,67 +108,48 @@ bin_pcre_compile(char *nam, char **args, + } + + /**/ +-#ifdef HAVE_PCRE_STUDY +- +-/**/ + static int + bin_pcre_study(char *nam, UNUSED(char **args), UNUSED(Options ops), UNUSED(int func)) + { +- const char *pcre_error; +- + if (pcre_pattern == NULL) + { + zwarnnam(nam, "no pattern has been compiled for study"); + return 1; + } +- +- if (pcre_hints) +-#ifdef PCRE_CONFIG_JIT +- pcre_free_study(pcre_hints); +-#else +- pcre_free(pcre_hints); +-#endif +- pcre_hints = NULL; + +- pcre_hints = pcre_study(pcre_pattern, 0, &pcre_error); +- if (pcre_error != NULL) +- { +- zwarnnam(nam, "error while studying regex: %s", pcre_error); +- return 1; ++ int jit = 0; ++ if (!pcre2_config(PCRE2_CONFIG_JIT, &jit) && jit) { ++ if (pcre2_jit_compile(pcre_pattern, PCRE2_JIT_COMPLETE) < 0) { ++ zwarnnam(nam, "error while studying regex"); ++ return 1; ++ } + } + + return 0; + } + +-/**/ +-#else /* !HAVE_PCRE_STUDY */ +- +-# define bin_pcre_study bin_notavail +- +-/**/ +-#endif /* !HAVE_PCRE_STUDY */ +- +-/**/ + static int +-zpcre_get_substrings(char *arg, int *ovec, int captured_count, char *matchvar, +- char *substravar, int want_offset_pair, int matchedinarr, +- int want_begin_end) ++zpcre_get_substrings(char *arg, pcre2_match_data *mdata, int captured_count, ++ char *matchvar, char *substravar, int want_offset_pair, ++ int matchedinarr, int want_begin_end) + { +- char **captures, *match_all, **matches; ++ PCRE2_SIZE *ovec; ++ char *match_all, **matches; + char offset_all[50]; + int capture_start = 1; + + if (matchedinarr) { +- /* bash-style captures[0] entire-matched string in the array */ ++ /* bash-style ovec[0] entire-matched string in the array */ + capture_start = 0; + } + +- /* captures[0] will be entire matched string, [1] first substring */ +- if (!pcre_get_substring_list(arg, ovec, captured_count, (const char ***)&captures)) { +- int nelem = arrlen(captures)-1; ++ /* ovec[0] will be entire matched string, [1] first substring */ ++ ovec = pcre2_get_ovector_pointer(mdata); ++ if (ovec) { ++ int nelem = captured_count - 1; + /* Set to the offsets of the complete match */ + if (want_offset_pair) { +- sprintf(offset_all, "%d %d", ovec[0], ovec[1]); ++ sprintf(offset_all, "%ld %ld", ovec[0], ovec[1]); + setsparam("ZPCRE_OP", ztrdup(offset_all)); + } + /* +@@ -186,7 +158,7 @@ zpcre_get_substrings(char *arg, int *ove + * ovec is length 2*(1+capture_list_length) + */ + if (matchvar) { +- match_all = metafy(captures[0], ovec[1] - ovec[0], META_DUP); ++ match_all = metafy(arg + ovec[0], ovec[1] - ovec[0], META_DUP); + setsparam(matchvar, match_all); + } + /* +@@ -201,16 +173,12 @@ zpcre_get_substrings(char *arg, int *ove + */ + if (substravar && + (!want_begin_end || nelem)) { +- char **x, **y; ++ char **x; + int vec_off, i; +- y = &captures[capture_start]; + matches = x = (char **) zalloc(sizeof(char *) * (captured_count+1-capture_start)); +- for (i = capture_start; i < captured_count; i++, y++) { ++ for (i = capture_start; i < captured_count; i++) { + vec_off = 2*i; +- if (*y) +- *x++ = metafy(*y, ovec[vec_off+1]-ovec[vec_off], META_DUP); +- else +- *x++ = NULL; ++ *x++ = metafy(arg + ovec[vec_off], ovec[vec_off+1]-ovec[vec_off], META_DUP); + } + *x = NULL; + setaparam(substravar, matches); +@@ -247,7 +215,8 @@ zpcre_get_substrings(char *arg, int *ove + setiparam("MEND", offs + !isset(KSHARRAYS) - 1); + if (nelem) { + char **mbegin, **mend, **bptr, **eptr; +- int i, *ipair; ++ int i; ++ size_t *ipair; + + bptr = mbegin = zalloc(sizeof(char*)*(nelem+1)); + eptr = mend = zalloc(sizeof(char*)*(nelem+1)); +@@ -287,8 +256,6 @@ zpcre_get_substrings(char *arg, int *ove + setaparam("mend", mend); + } + } +- +- pcre_free_substring_list((const char **)captures); + } + + return 0; +@@ -314,7 +281,8 @@ getposint(char *instr, char *nam) + static int + bin_pcre_match(char *nam, char **args, Options ops, UNUSED(int func)) + { +- int ret, capcount, *ovec, ovecsize, c; ++ int ret, c; ++ pcre2_match_data *pcre_mdata = NULL; + char *matched_portion = NULL; + char *plaintext = NULL; + char *receptacle = NULL; +@@ -344,36 +312,30 @@ bin_pcre_match(char *nam, char **args, O + /* For the entire match, 'Return' the offset byte positions instead of the matched string */ + if(OPT_ISSET(ops,'b')) want_offset_pair = 1; + +- if ((ret = pcre_fullinfo(pcre_pattern, pcre_hints, PCRE_INFO_CAPTURECOUNT, &capcount))) +- { +- zwarnnam(nam, "error %d in fullinfo", ret); +- return 1; +- } +- +- ovecsize = (capcount+1)*3; +- ovec = zalloc(ovecsize*sizeof(int)); +- + plaintext = ztrdup(*args); + unmetafy(plaintext, &subject_len); + + if (offset_start > 0 && offset_start >= subject_len) +- ret = PCRE_ERROR_NOMATCH; +- else +- ret = pcre_exec(pcre_pattern, pcre_hints, plaintext, subject_len, offset_start, 0, ovec, ovecsize); ++ ret = PCRE2_ERROR_NOMATCH; ++ else { ++ pcre_mdata = pcre2_match_data_create_from_pattern(pcre_pattern, NULL); ++ ret = pcre2_match(pcre_pattern, (PCRE2_SPTR) plaintext, subject_len, ++ offset_start, 0, pcre_mdata, NULL); ++ } + + if (ret==0) return_value = 0; +- else if (ret==PCRE_ERROR_NOMATCH) /* no match */; ++ else if (ret == PCRE2_ERROR_NOMATCH) /* no match */; + else if (ret>0) { +- zpcre_get_substrings(plaintext, ovec, ret, matched_portion, receptacle, ++ zpcre_get_substrings(plaintext, pcre_mdata, ret, matched_portion, receptacle, + want_offset_pair, 0, 0); + return_value = 0; + } + else { +- zwarnnam(nam, "error in pcre_exec [%d]", ret); ++ zwarnnam(nam, "error in pcre2_match [%d]", ret); + } + +- if (ovec) +- zfree(ovec, ovecsize*sizeof(int)); ++ if (pcre_mdata) ++ pcre2_match_data_free(pcre_mdata); + zsfree(plaintext); + + return return_value; +@@ -383,17 +345,19 @@ bin_pcre_match(char *nam, char **args, O + static int + cond_pcre_match(char **a, int id) + { +- pcre *pcre_pat; +- const char *pcre_err; ++ pcre2_code *pcre_pat = NULL; ++ int pcre_err; ++ PCRE2_SIZE pcre_erroff; + char *lhstr, *rhre, *lhstr_plain, *rhre_plain, *avar, *svar; +- int r = 0, pcre_opts = 0, pcre_errptr, capcnt, *ov, ovsize; ++ int r = 0, pcre_opts = 0; ++ pcre2_match_data *pcre_mdata = NULL; + int lhstr_plain_len, rhre_plain_len; + int return_value = 0; + + if (zpcre_utf8_enabled()) +- pcre_opts |= PCRE_UTF8; ++ pcre_opts |= PCRE2_UTF; + if (isset(REMATCHPCRE) && !isset(CASEMATCH)) +- pcre_opts |= PCRE_CASELESS; ++ pcre_opts |= PCRE2_CASELESS; + + lhstr = cond_str(a,0,0); + rhre = cond_str(a,1,0); +@@ -401,9 +365,6 @@ cond_pcre_match(char **a, int id) + rhre_plain = ztrdup(rhre); + unmetafy(lhstr_plain, &lhstr_plain_len); + unmetafy(rhre_plain, &rhre_plain_len); +- pcre_pat = NULL; +- ov = NULL; +- ovsize = 0; + + if (isset(BASHREMATCH)) { + svar = NULL; +@@ -415,27 +376,27 @@ cond_pcre_match(char **a, int id) + + switch(id) { + case CPCRE_PLAIN: +- if ((int)strlen(rhre_plain) != rhre_plain_len) { +- zwarn("embedded NULs in PCRE pattern terminate pattern"); +- } +- pcre_pat = pcre_compile(rhre_plain, pcre_opts, &pcre_err, &pcre_errptr, NULL); +- if (pcre_pat == NULL) { +- zwarn("failed to compile regexp /%s/: %s", rhre, pcre_err); ++ if (!(pcre_pat = pcre2_compile((PCRE2_SPTR) rhre_plain, ++ (PCRE2_SIZE) rhre_plain_len, pcre_opts, ++ &pcre_err, &pcre_erroff, NULL))) ++ { ++ PCRE2_UCHAR buffer[256]; ++ pcre2_get_error_message(pcre_err, buffer, sizeof(buffer)); ++ zwarn("failed to compile regexp /%s/: %s", rhre, buffer); + break; + } +- pcre_fullinfo(pcre_pat, NULL, PCRE_INFO_CAPTURECOUNT, &capcnt); +- ovsize = (capcnt+1)*3; +- ov = zalloc(ovsize*sizeof(int)); +- r = pcre_exec(pcre_pat, NULL, lhstr_plain, lhstr_plain_len, 0, 0, ov, ovsize); +- /* r < 0 => error; r==0 match but not enough size in ov ++ pcre_mdata = pcre2_match_data_create_from_pattern(pcre_pat, NULL); ++ r = pcre2_match(pcre_pat, (PCRE2_SPTR8) lhstr_plain, lhstr_plain_len, ++ 0, 0, pcre_mdata, NULL); ++ /* r < 0 => error; r==0 match but not enough size in match data + * r > 0 => (r-1) substrings found; r==1 => no substrings + */ + if (r==0) { +- zwarn("reportable zsh problem: pcre_exec() returned 0"); ++ zwarn("reportable zsh problem: pcre2_match() returned 0"); + return_value = 1; + break; + } +- else if (r==PCRE_ERROR_NOMATCH) { ++ else if (r == PCRE2_ERROR_NOMATCH) { + return_value = 0; /* no match */ + break; + } +@@ -444,7 +405,7 @@ cond_pcre_match(char **a, int id) + break; + } + else if (r>0) { +- zpcre_get_substrings(lhstr_plain, ov, r, svar, avar, 0, ++ zpcre_get_substrings(lhstr_plain, pcre_mdata, r, svar, avar, 0, + isset(BASHREMATCH), + !isset(BASHREMATCH)); + return_value = 1; +@@ -457,10 +418,10 @@ cond_pcre_match(char **a, int id) + free(lhstr_plain); + if(rhre_plain) + free(rhre_plain); ++ if (pcre_mdata) ++ pcre2_match_data_free(pcre_mdata); + if (pcre_pat) +- pcre_free(pcre_pat); +- if (ov) +- zfree(ov, ovsize*sizeof(int)); ++ pcre2_code_free(pcre_pat); + + return return_value; + } +@@ -489,11 +450,11 @@ static struct builtin bintab[] = { + + static struct features module_features = { + bintab, sizeof(bintab)/sizeof(*bintab), +-#if defined(HAVE_PCRE_COMPILE) && defined(HAVE_PCRE_EXEC) ++#if defined(HAVE_PCRE2_COMPILE_8) && defined(HAVE_PCRE2_H) + cotab, sizeof(cotab)/sizeof(*cotab), +-#else /* !(HAVE_PCRE_COMPILE && HAVE_PCRE_EXEC) */ ++#else /* !(HAVE_PCRE2_COMPILE_8 && HAVE_PCRE2_H) */ + NULL, 0, +-#endif /* !(HAVE_PCRE_COMPILE && HAVE_PCRE_EXEC) */ ++#endif /* !(HAVE_PCRE2_COMPILE_8 && HAVE_PCRE2_H) */ + NULL, 0, + NULL, 0, + 0 +@@ -540,19 +501,9 @@ cleanup_(Module m) + int + finish_(UNUSED(Module m)) + { +-#if defined(HAVE_PCRE_COMPILE) && defined(HAVE_PCRE_EXEC) +-#ifdef HAVE_PCRE_STUDY +- if (pcre_hints) +-#ifdef PCRE_CONFIG_JIT +- pcre_free_study(pcre_hints); +-#else +- pcre_free(pcre_hints); +-#endif +- pcre_hints = NULL; +-#endif +- ++#if defined(HAVE_PCRE2_COMPILE_8) && defined(HAVE_PCRE2_H) + if (pcre_pattern) +- pcre_free(pcre_pattern); ++ pcre2_code_free(pcre_pattern); + pcre_pattern = NULL; + #endif + +--- a/Test/V07pcre.ztst ++++ b/Test/V07pcre.ztst +@@ -129,12 +129,17 @@ + >78884; ZPCRE_OP: 25 30 + >90210; ZPCRE_OP: 31 36 + +-# Embedded NULs allowed in plaintext, but not in RE (although \0 as two-chars allowed) ++# Embedded NULs allowed in plaintext, in RE, pcre supports \0 as two-chars + [[ $'a\0bc\0d' =~ '^(a\0.)(.+)$' ]] + print "${#MATCH}; ${#match[1]}; ${#match[2]}" + 0:ensure ASCII NUL passes in and out of matched plaintext + >6; 3; 3 + ++# PCRE2 supports NULs also in the RE ++ [[ $'a\0b\0c' =~ $'^(.\0)+' ]] && print "${#MATCH}; ${#match[1]}" ++0:ensure ASCII NUL works also in the regex ++>4; 2 ++ + # Ensure the long-form infix operator works + [[ foo -pcre-match ^f..$ ]] + print $? +@@ -181,7 +186,11 @@ + [[ é =~ '^..\z' ]]; echo $? + LANG=$LANG_SAVE + [[ é =~ '^.\z' ]]; echo $? +-0:swich between C/UTF-8 locales ++0:switch between C/UTF-8 locales + >0 + >0 + >0 ++ ++ [[ abc =~ 'a(d*)bc' ]] && print "$#MATCH; $#match; ${#match[1]}" ++0:empty capture ++>3; 1; 0 +--- a/configure.ac ++++ b/configure.ac +@@ -438,7 +438,7 @@ fi], + + dnl Do you want to look for pcre support? + AC_ARG_ENABLE(pcre, +-AS_HELP_STRING([--enable-pcre],[enable the search for the pcre library (may create run-time library dependencies)])) ++AS_HELP_STRING([--enable-pcre],[enable the search for the pcre2 library (may create run-time library dependencies)])) + + dnl Do you want to look for capability support? + AC_ARG_ENABLE(cap, +@@ -662,13 +662,12 @@ AC_HEADER_SYS_WAIT + + oldcflags="$CFLAGS" + if test x$enable_pcre = xyes; then +-AC_CHECK_PROG([PCRECONF], pcre-config, pcre-config) +-dnl Typically (meaning on this single RedHat 9 box in front of me) +-dnl pcre-config --cflags produces a -I output which needs to go into ++AC_CHECK_PROG([PCRECONF], pcre2-config, pcre2-config) ++dnl pcre2-config --cflags may produce a -I output which needs to go into + dnl CPPFLAGS else configure's preprocessor tests don't pick it up, + dnl producing a warning. +-if test "x$ac_cv_prog_PCRECONF" = xpcre-config; then +- CPPFLAGS="$CPPFLAGS `pcre-config --cflags`" ++if test "x$ac_cv_prog_PCRECONF" = xpcre2-config; then ++ CPPFLAGS="$CPPFLAGS `pcre2-config --cflags`" + fi + fi + +@@ -678,9 +677,10 @@ AC_CHECK_HEADERS(sys/time.h sys/times.h + locale.h errno.h stdio.h stdarg.h varargs.h stdlib.h \ + unistd.h sys/capability.h \ + utmp.h utmpx.h sys/types.h pwd.h grp.h poll.h sys/mman.h \ +- netinet/in_systm.h pcre.h langinfo.h wchar.h stddef.h \ ++ netinet/in_systm.h langinfo.h wchar.h stddef.h \ + sys/stropts.h iconv.h ncurses.h ncursesw/ncurses.h \ + ncurses/ncurses.h) ++AC_CHECK_HEADERS([pcre2.h],,,[#define PCRE2_CODE_UNIT_WIDTH 8]) + if test x$dynamic = xyes; then + AC_CHECK_HEADERS(dlfcn.h) + AC_CHECK_HEADERS(dl.h) +@@ -958,9 +958,7 @@ if test "x$ac_found_iconv" = "xyes"; the + fi + + if test x$enable_pcre = xyes; then +-dnl pcre-config should probably be employed here +-dnl AC_SEARCH_LIBS(pcre_compile, pcre) +- LIBS="`$ac_cv_prog_PCRECONF --libs` $LIBS" ++ LIBS="`$ac_cv_prog_PCRECONF --libs8` $LIBS" + fi + + dnl --------------------- +@@ -1323,7 +1321,7 @@ AC_CHECK_FUNCS(strftime strptime mktime + pathconf sysconf \ + tgetent tigetflag tigetnum tigetstr setupterm initscr resize_term \ + getcchar setcchar waddwstr wget_wch win_wch use_default_colors \ +- pcre_compile pcre_study pcre_exec \ ++ pcre2_compile_8 \ + nl_langinfo \ + erand48 open_memstream \ + posix_openpt \ diff --git a/utils/zsh/patches/003-51728-assign-pcre-named-capture-groups-to-a-hash.patch b/utils/zsh/patches/003-51728-assign-pcre-named-capture-groups-to-a-hash.patch new file mode 100644 index 0000000000..4b59218b3b --- /dev/null +++ b/utils/zsh/patches/003-51728-assign-pcre-named-capture-groups-to-a-hash.patch @@ -0,0 +1,180 @@ +From f3f371deb376478176866fd770fbcf9bc0d0609f Mon Sep 17 00:00:00 2001 +From: Oliver Kiddle +Date: Sat, 13 May 2023 00:56:48 +0200 +Subject: [PATCH] 51728: assign pcre named capture groups to a hash + +--- + ChangeLog | 3 +++ + Doc/Zsh/mod_pcre.yo | 10 ++++++---- + Src/Modules/pcre.c | 43 +++++++++++++++++++++++++++++++++---------- + Test/V07pcre.ztst | 14 ++++++++++++++ + 4 files changed, 56 insertions(+), 14 deletions(-) + +# diff --git a/ChangeLog b/ChangeLog +# index 285b73b2c..2835a9405 100644 +# --- a/ChangeLog +# +++ b/ChangeLog +# @@ -1,5 +1,8 @@ +# 2023-05-13 Oliver Kiddle + +# + * 51728: Doc/Zsh/mod_pcre.yo, Src/Modules/pcre.c, +# + Test/V07pcre.ztst: assign pcre named capture groups to a hash +# + +# * 51723: Src/Modules/pcre.c, Test/V07pcre.ztst, configure.ac: +# migrate pcre module to pcre2 + +--- a/Doc/Zsh/mod_pcre.yo ++++ b/Doc/Zsh/mod_pcre.yo +@@ -20,12 +20,12 @@ including those that indicate newline. + ) + findex(pcre_study) + item(tt(pcre_study))( +-Studies the previously-compiled PCRE which may result in faster +-matching. ++Requests JIT compilation for the previously-compiled PCRE which ++may result in faster matching. + ) + findex(pcre_match) + item(tt(pcre_match) [ tt(-v) var(var) ] [ tt(-a) var(arr) ] \ +-[ tt(-n) var(offset) ] [ tt(-b) ] var(string))( ++[ tt(-A) var(assoc) ] [ tt(-n) var(offset) ] [ tt(-b) ] var(string))( + Returns successfully if tt(string) matches the previously-compiled + PCRE. + +@@ -36,7 +36,9 @@ substrings, unless the tt(-a) option is + case it will set the array var(arr). Similarly, the variable + tt(MATCH) will be set to the entire matched portion of the + string, unless the tt(-v) option is given, in which case the variable +-var(var) will be set. ++var(var) will be set. Furthermore, any named captures will ++be stored in the associative array tt(.pcre.match) unless an ++alternative is given with tt(-A). + No variables are altered if there is no successful match. + A tt(-n) option starts searching for a match from the + byte var(offset) position in var(string). If the tt(-b) option is given, +--- a/Src/Modules/pcre.c ++++ b/Src/Modules/pcre.c +@@ -129,14 +129,17 @@ bin_pcre_study(char *nam, UNUSED(char ** + } + + static int +-zpcre_get_substrings(char *arg, pcre2_match_data *mdata, int captured_count, +- char *matchvar, char *substravar, int want_offset_pair, +- int matchedinarr, int want_begin_end) ++zpcre_get_substrings(pcre2_code *pat, char *arg, pcre2_match_data *mdata, ++ int captured_count, char *matchvar, char *substravar, char *namedassoc, ++ int want_offset_pair, int matchedinarr, int want_begin_end) + { + PCRE2_SIZE *ovec; + char *match_all, **matches; + char offset_all[50]; + int capture_start = 1; ++ int vec_off; ++ PCRE2_SPTR ntable; /* table of named captures */ ++ uint32_t ncount, nsize; + + if (matchedinarr) { + /* bash-style ovec[0] entire-matched string in the array */ +@@ -174,7 +177,7 @@ zpcre_get_substrings(char *arg, pcre2_ma + if (substravar && + (!want_begin_end || nelem)) { + char **x; +- int vec_off, i; ++ int i; + matches = x = (char **) zalloc(sizeof(char *) * (captured_count+1-capture_start)); + for (i = capture_start; i < captured_count; i++) { + vec_off = 2*i; +@@ -184,6 +187,23 @@ zpcre_get_substrings(char *arg, pcre2_ma + setaparam(substravar, matches); + } + ++ if (!pcre2_pattern_info(pat, PCRE2_INFO_NAMECOUNT, &ncount) && ncount ++ && !pcre2_pattern_info(pat, PCRE2_INFO_NAMEENTRYSIZE, &nsize) ++ && !pcre2_pattern_info(pat, PCRE2_INFO_NAMETABLE, &ntable)) ++ { ++ char **hash, **hashptr; ++ uint32_t nidx; ++ hashptr = hash = (char **)zshcalloc((ncount+1)*2*sizeof(char *)); ++ for (nidx = 0; nidx < ncount; nidx++) { ++ vec_off = (ntable[nsize * nidx] << 9) + 2 * ntable[nsize * nidx + 1]; ++ /* would metafy the key but pcre limits characters in the name */ ++ *hashptr++ = ztrdup((char *) ntable + nsize * nidx + 2); ++ *hashptr++ = metafy(arg + ovec[vec_off], ++ ovec[vec_off+1]-ovec[vec_off], META_DUP); ++ } ++ sethparam(namedassoc, hash); ++ } ++ + if (want_begin_end) { + /* + * cond-infix rather than builtin; also not bash; so we set a bunch +@@ -286,6 +306,7 @@ bin_pcre_match(char *nam, char **args, O + char *matched_portion = NULL; + char *plaintext = NULL; + char *receptacle = NULL; ++ char *named = ".pcre.match"; + int return_value = 1; + /* The subject length and offset start are both int values in pcre_exec */ + int subject_len; +@@ -305,6 +326,9 @@ bin_pcre_match(char *nam, char **args, O + if(OPT_HASARG(ops,c='v')) { + matched_portion = OPT_ARG(ops,c); + } ++ if (OPT_HASARG(ops, c='A')) { ++ named = OPT_ARG(ops, c); ++ } + if(OPT_HASARG(ops,c='n')) { /* The offset position to start the search, in bytes. */ + if ((offset_start = getposint(OPT_ARG(ops,c), nam)) < 0) + return 1; +@@ -326,8 +350,8 @@ bin_pcre_match(char *nam, char **args, O + if (ret==0) return_value = 0; + else if (ret == PCRE2_ERROR_NOMATCH) /* no match */; + else if (ret>0) { +- zpcre_get_substrings(plaintext, pcre_mdata, ret, matched_portion, receptacle, +- want_offset_pair, 0, 0); ++ zpcre_get_substrings(pcre_pattern, plaintext, pcre_mdata, ret, matched_portion, ++ receptacle, named, want_offset_pair, 0, 0); + return_value = 0; + } + else { +@@ -405,9 +429,8 @@ cond_pcre_match(char **a, int id) + break; + } + else if (r>0) { +- zpcre_get_substrings(lhstr_plain, pcre_mdata, r, svar, avar, 0, +- isset(BASHREMATCH), +- !isset(BASHREMATCH)); ++ zpcre_get_substrings(pcre_pat, lhstr_plain, pcre_mdata, r, svar, avar, ++ ".pcre.match", 0, isset(BASHREMATCH), !isset(BASHREMATCH)); + return_value = 1; + break; + } +@@ -443,7 +466,7 @@ static struct conddef cotab[] = { + + static struct builtin bintab[] = { + BUILTIN("pcre_compile", 0, bin_pcre_compile, 1, 1, 0, "aimxs", NULL), +- BUILTIN("pcre_match", 0, bin_pcre_match, 1, 1, 0, "a:v:n:b", NULL), ++ BUILTIN("pcre_match", 0, bin_pcre_match, 1, 1, 0, "A:a:v:n:b", NULL), + BUILTIN("pcre_study", 0, bin_pcre_study, 0, 0, 0, NULL, NULL) + }; + +--- a/Test/V07pcre.ztst ++++ b/Test/V07pcre.ztst +@@ -194,3 +194,17 @@ + [[ abc =~ 'a(d*)bc' ]] && print "$#MATCH; $#match; ${#match[1]}" + 0:empty capture + >3; 1; 0 ++ ++ [[ category/name-12345 =~ '(?x)^ ++ (? [^/]* ) / ++ (? ++ (? \w+ ) - ++ (? \d+ ))$' ]] ++ typeset -p1 .pcre.match ++0:named captures ++>typeset -g -A .pcre.match=( ++> [category]=category ++> [name]=name ++> [package]=name-12345 ++> [version]=12345 ++>) diff --git a/utils/zsh/patches/004-51738-support-pcre-s-alternative-DFA-matching-algori.patch b/utils/zsh/patches/004-51738-support-pcre-s-alternative-DFA-matching-algori.patch new file mode 100644 index 0000000000..8e06745fe7 --- /dev/null +++ b/utils/zsh/patches/004-51738-support-pcre-s-alternative-DFA-matching-algori.patch @@ -0,0 +1,156 @@ +From b4d1c756f50909b4a13e5c8fe5f26f71e9d54f63 Mon Sep 17 00:00:00 2001 +From: Oliver Kiddle +Date: Sat, 13 May 2023 00:59:00 +0200 +Subject: [PATCH] 51738: support pcre's alternative DFA matching algorithm + +--- + ChangeLog | 3 +++ + Doc/Zsh/mod_pcre.yo | 6 ++++- + Src/Modules/pcre.c | 53 ++++++++++++++++++++++++++++++--------------- + Test/V07pcre.ztst | 5 +++++ + 4 files changed, 49 insertions(+), 18 deletions(-) + +# diff --git a/ChangeLog b/ChangeLog +# index 2835a9405..18bc4a698 100644 +# --- a/ChangeLog +# +++ b/ChangeLog +# @@ -1,5 +1,8 @@ +# 2023-05-13 Oliver Kiddle + +# + * 51738: Doc/Zsh/mod_pcre.yo, Src/Modules/pcre.c, +# + Test/V07pcre.ztst: support pcre's DFA matching algorithm +# + +# * 51728: Doc/Zsh/mod_pcre.yo, Src/Modules/pcre.c, +# Test/V07pcre.ztst: assign pcre named capture groups to a hash + +--- a/Doc/Zsh/mod_pcre.yo ++++ b/Doc/Zsh/mod_pcre.yo +@@ -25,7 +25,7 @@ may result in faster matching. + ) + findex(pcre_match) + item(tt(pcre_match) [ tt(-v) var(var) ] [ tt(-a) var(arr) ] \ +-[ tt(-A) var(assoc) ] [ tt(-n) var(offset) ] [ tt(-b) ] var(string))( ++[ tt(-A) var(assoc) ] [ tt(-n) var(offset) ] [ tt(-bd) ] var(string))( + Returns successfully if tt(string) matches the previously-compiled + PCRE. + +@@ -69,6 +69,10 @@ print -l $accum) + ) + enditem() + ++The option tt(-d) uses the alternative breadth-first DFA search algorithm of ++pcre. This sets tt(match), or the array given with tt(-a), to all the matches ++found from the same start point in the subject. ++ + The tt(zsh/pcre) module makes available the following test condition: + + startitem() +--- a/Src/Modules/pcre.c ++++ b/Src/Modules/pcre.c +@@ -305,30 +305,29 @@ bin_pcre_match(char *nam, char **args, O + pcre2_match_data *pcre_mdata = NULL; + char *matched_portion = NULL; + char *plaintext = NULL; +- char *receptacle = NULL; +- char *named = ".pcre.match"; ++ char *receptacle; ++ char *named = NULL; + int return_value = 1; + /* The subject length and offset start are both int values in pcre_exec */ + int subject_len; + int offset_start = 0; + int want_offset_pair = 0; ++ int use_dfa = 0; + + if (pcre_pattern == NULL) { + zwarnnam(nam, "no pattern has been compiled"); + return 1; + } + +- matched_portion = "MATCH"; +- receptacle = "match"; +- if(OPT_HASARG(ops,c='a')) { +- receptacle = OPT_ARG(ops,c); +- } +- if(OPT_HASARG(ops,c='v')) { +- matched_portion = OPT_ARG(ops,c); +- } +- if (OPT_HASARG(ops, c='A')) { +- named = OPT_ARG(ops, c); ++ if (!(use_dfa = OPT_ISSET(ops, 'd'))) { ++ matched_portion = OPT_HASARG(ops, c='v') ? OPT_ARG(ops, c) : "MATCH"; ++ named = OPT_HASARG(ops, c='A') ? OPT_ARG(ops, c) : ".pcre.match"; ++ } else if (OPT_HASARG(ops, c='v') || OPT_HASARG(ops, c='A')) { ++ zwarnnam(nam, "-d cannot be combined with -%c", c); ++ return 1; + } ++ receptacle = OPT_HASARG(ops, 'a') ? OPT_ARG(ops, 'a') : "match"; ++ + if(OPT_HASARG(ops,c='n')) { /* The offset position to start the search, in bytes. */ + if ((offset_start = getposint(OPT_ARG(ops,c), nam)) < 0) + return 1; +@@ -341,7 +340,25 @@ bin_pcre_match(char *nam, char **args, O + + if (offset_start > 0 && offset_start >= subject_len) + ret = PCRE2_ERROR_NOMATCH; +- else { ++ else if (use_dfa) { ++ PCRE2_SIZE old, wscount = 128, capcount = 128; ++ void *workspace = zhalloc(sizeof(int) * wscount); ++ pcre_mdata = pcre2_match_data_create(capcount, NULL); ++ do { ++ ret = pcre2_dfa_match(pcre_pattern, (PCRE2_SPTR) plaintext, subject_len, ++ offset_start, 0, pcre_mdata, NULL, (int *) workspace, wscount); ++ if (ret == PCRE2_ERROR_DFA_WSSIZE) { ++ old = wscount; ++ wscount += wscount / 2; ++ workspace = hrealloc(workspace, sizeof(int) * old, sizeof(int) * wscount); ++ } else if (ret == 0) { ++ capcount += capcount / 2; ++ pcre2_match_data_free(pcre_mdata); ++ pcre_mdata = pcre2_match_data_create(capcount, NULL); ++ } else ++ break; ++ } while(1); ++ } else { + pcre_mdata = pcre2_match_data_create_from_pattern(pcre_pattern, NULL); + ret = pcre2_match(pcre_pattern, (PCRE2_SPTR) plaintext, subject_len, + offset_start, 0, pcre_mdata, NULL); +@@ -350,12 +367,14 @@ bin_pcre_match(char *nam, char **args, O + if (ret==0) return_value = 0; + else if (ret == PCRE2_ERROR_NOMATCH) /* no match */; + else if (ret>0) { +- zpcre_get_substrings(pcre_pattern, plaintext, pcre_mdata, ret, matched_portion, +- receptacle, named, want_offset_pair, 0, 0); ++ zpcre_get_substrings(pcre_pattern, plaintext, pcre_mdata, ret, ++ matched_portion, receptacle, named, want_offset_pair, use_dfa, 0); + return_value = 0; + } + else { +- zwarnnam(nam, "error in pcre2_match [%d]", ret); ++ PCRE2_UCHAR buffer[256]; ++ pcre2_get_error_message(ret, buffer, sizeof(buffer)); ++ zwarnnam(nam, "error in pcre matching for /%s/: %s", plaintext, buffer); + } + + if (pcre_mdata) +@@ -466,7 +485,7 @@ static struct conddef cotab[] = { + + static struct builtin bintab[] = { + BUILTIN("pcre_compile", 0, bin_pcre_compile, 1, 1, 0, "aimxs", NULL), +- BUILTIN("pcre_match", 0, bin_pcre_match, 1, 1, 0, "A:a:v:n:b", NULL), ++ BUILTIN("pcre_match", 0, bin_pcre_match, 1, 1, 0, "A:a:v:n:bd", NULL), + BUILTIN("pcre_study", 0, bin_pcre_study, 0, 0, 0, NULL, NULL) + }; + +--- a/Test/V07pcre.ztst ++++ b/Test/V07pcre.ztst +@@ -208,3 +208,8 @@ + > [package]=name-12345 + > [version]=12345 + >) ++ ++ pcre_compile 'cat(er(pillar)?)?' ++ pcre_match -d 'the caterpillar catchment' && print $match ++0:pcre_match -d ++>caterpillar cater cat diff --git a/utils/zsh/patches/005-51877-do-not-build-pcre-module-if-pcre2-config-is-no.patch b/utils/zsh/patches/005-51877-do-not-build-pcre-module-if-pcre2-config-is-no.patch new file mode 100644 index 0000000000..81632e7c16 --- /dev/null +++ b/utils/zsh/patches/005-51877-do-not-build-pcre-module-if-pcre2-config-is-no.patch @@ -0,0 +1,111 @@ +From 10bdbd8b5b0b43445aff23dcd412f25cf6aa328a Mon Sep 17 00:00:00 2001 +From: Jun-ichi Takimoto +Date: Tue, 20 Jun 2023 18:14:27 +0900 +Subject: [PATCH] 51877: do not build pcre module if pcre2-config is not found + +--- + ChangeLog | 5 +++++ + Src/Modules/pcre.mdd | 2 +- + configure.ac | 31 +++++++++++++++++++------------ + 3 files changed, 25 insertions(+), 13 deletions(-) + +# diff --git a/ChangeLog b/ChangeLog +# index 14349dcf2..e89ffee1b 100644 +# --- a/ChangeLog +# +++ b/ChangeLog +# @@ -1,3 +1,8 @@ +# +2023-06-20 Jun-ichi Takimoto +# + +# + * 51877: Src/Modules/pcre.mdd, configure.ac: do not build pcre +# + module if pcre2-config is not available. +# + +# 2023-06-19 Jun-ichi Takimoto + +# * 51862: Doc/Makefile.in, configure.ac: support texinfo-7.0 +--- a/Src/Modules/pcre.mdd ++++ b/Src/Modules/pcre.mdd +@@ -1,5 +1,5 @@ + name=zsh/pcre +-link=`if test x$enable_pcre = xyes && (pcre-config --version >/dev/null 2>/dev/null); then echo dynamic; else echo no; fi` ++link=`if test x$enable_pcre = xyes; then echo dynamic; else echo no; fi` + load=no + + autofeatures="b:pcre_compile b:pcre_study b:pcre_match" +--- a/configure.ac ++++ b/configure.ac +@@ -440,6 +440,17 @@ dnl Do you want to look for pcre support + AC_ARG_ENABLE(pcre, + AS_HELP_STRING([--enable-pcre],[enable the search for the pcre2 library (may create run-time library dependencies)])) + ++AC_ARG_VAR(PCRE_CONFIG, [pathname of pcre2-config if it is not in PATH]) ++if test "x$enable_pcre" = xyes; then ++ AC_CHECK_PROG([PCRE_CONFIG], pcre2-config, pcre2-config) ++ if test "x$PCRE_CONFIG" = x; then ++ enable_pcre=no ++ AC_MSG_WARN([pcre2-config not found: pcre module is disabled.]) ++ AC_MSG_NOTICE( ++ [Set PCRE_CONFIG to pathname of pcre2-config if it is not in PATH.]) ++ fi ++fi ++ + dnl Do you want to look for capability support? + AC_ARG_ENABLE(cap, + AS_HELP_STRING([--enable-cap],[enable the search for POSIX capabilities (may require additional headers to be added by hand)])) +@@ -660,15 +671,12 @@ AC_HEADER_DIRENT + AC_HEADER_STAT + AC_HEADER_SYS_WAIT + +-oldcflags="$CFLAGS" +-if test x$enable_pcre = xyes; then +-AC_CHECK_PROG([PCRECONF], pcre2-config, pcre2-config) + dnl pcre2-config --cflags may produce a -I output which needs to go into + dnl CPPFLAGS else configure's preprocessor tests don't pick it up, + dnl producing a warning. +-if test "x$ac_cv_prog_PCRECONF" = xpcre2-config; then +- CPPFLAGS="$CPPFLAGS `pcre2-config --cflags`" +-fi ++if test "x$enable_pcre" = xyes; then ++ CPPFLAGS="`$PCRE_CONFIG --cflags` $CPPFLAGS" ++ AC_CHECK_HEADERS([pcre2.h],,,[#define PCRE2_CODE_UNIT_WIDTH 8]) + fi + + AC_CHECK_HEADERS(sys/time.h sys/times.h sys/select.h termcap.h termio.h \ +@@ -680,7 +688,6 @@ AC_CHECK_HEADERS(sys/time.h sys/times.h + netinet/in_systm.h langinfo.h wchar.h stddef.h \ + sys/stropts.h iconv.h ncurses.h ncursesw/ncurses.h \ + ncurses/ncurses.h) +-AC_CHECK_HEADERS([pcre2.h],,,[#define PCRE2_CODE_UNIT_WIDTH 8]) + if test x$dynamic = xyes; then + AC_CHECK_HEADERS(dlfcn.h) + AC_CHECK_HEADERS(dl.h) +@@ -957,10 +964,6 @@ if test "x$ac_found_iconv" = "xyes"; the + [Define as const if the declaration of iconv() needs const.]) + fi + +-if test x$enable_pcre = xyes; then +- LIBS="`$ac_cv_prog_PCRECONF --libs8` $LIBS" +-fi +- + dnl --------------------- + dnl CHECK TERMCAP LIBRARY + dnl --------------------- +@@ -1321,7 +1324,6 @@ AC_CHECK_FUNCS(strftime strptime mktime + pathconf sysconf \ + tgetent tigetflag tigetnum tigetstr setupterm initscr resize_term \ + getcchar setcchar waddwstr wget_wch win_wch use_default_colors \ +- pcre2_compile_8 \ + nl_langinfo \ + erand48 open_memstream \ + posix_openpt \ +@@ -1376,6 +1378,11 @@ if test x$zsh_cv_func_realpath_accepts_n + AC_DEFINE(REALPATH_ACCEPTS_NULL) + fi + ++if test x$enable_pcre = xyes; then ++ LIBS="`$PCRE_CONFIG --libs8` $LIBS" ++ AC_CHECK_FUNCS(pcre2_compile_8) ++fi ++ + if test x$enable_cap = xyes; then + AC_CHECK_FUNCS(cap_get_proc) + fi