diff --git a/.github/android-consumer-test/settings.gradle.kts b/.github/android-consumer-test/settings.gradle.kts index f12957771..542f54fac 100644 --- a/.github/android-consumer-test/settings.gradle.kts +++ b/.github/android-consumer-test/settings.gradle.kts @@ -14,13 +14,13 @@ pluginManagement { gradlePluginPortal() } plugins { - // AGP 9.x requires Gradle >= 9.4.1 — see the gradle-version pins on the CI jobs + // AGP 9.3.x requires Gradle >= 9.5.0 — see the gradle-version pins on the CI jobs // that build this fixture in publish.yml (package-android-aar, test-android-emulator). - // 9.2.1 (not 9.2.0) is pinned: it fixes a real R8 regression + // Stay at >= 9.2.1: 9.2.1 (not 9.2.0) first fixed a real R8 regression // (java.lang.ClassNotFoundException on com.android.tools.r8.RecordTag after // upgrading Gradle to 9.x with AGP 9.2.0) that hits this fixture directly since - // buildTypes.release sets isMinifyEnabled = true. - id("com.android.application") version "9.2.1" + // buildTypes.release sets isMinifyEnabled = true; 9.3.0 carries that fix forward. + id("com.android.application") version "9.3.0" } } diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 8ea8e2ec4..2b6c89818 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -917,8 +917,8 @@ jobs: distribution: temurin - uses: gradle/actions/setup-gradle@v6 with: - # AGP 9.2.0 (the .github/android-consumer-test fixture) requires Gradle >= 9.4.1. - gradle-version: "9.4.1" + # AGP 9.3.0 (the .github/android-consumer-test fixture) requires Gradle >= 9.5.0. + gradle-version: "9.5.0" - name: Build core jar (byte-identical classes payload for the AAR) run: > mvn -B --no-transfer-progress -pl llama -am -DskipTests -Denforcer.skip=true @@ -1048,8 +1048,8 @@ jobs: distribution: temurin - uses: gradle/actions/setup-gradle@v6 with: - # AGP 9.2.0 (the .github/android-consumer-test fixture) requires Gradle >= 9.4.1. - gradle-version: "9.4.1" + # AGP 9.3.0 (the .github/android-consumer-test fixture) requires Gradle >= 9.5.0. + gradle-version: "9.5.0" - name: Enable KVM group permissions (GitHub-hosted runner) run: | echo 'KERNEL=="kvm", GROUP="kvm", MODE="0666", OPTIONS+="static_node=kvm"' | sudo tee /etc/udev/rules.d/99-kvm4all.rules @@ -1142,10 +1142,10 @@ jobs: distribution: temurin - uses: gradle/actions/setup-gradle@v6 with: - # AGP 9.2.0 (android-llmservice) requires Gradle >= 9.4.1; also satisfies Kotlin + # AGP 9.3.0 (android-llmservice) requires Gradle >= 9.5.0; also satisfies Kotlin # 2.4's Gradle-plugin floor. The AAR/lib-only jobs stay on an older Gradle since # they build no AGP project. - gradle-version: "9.4.1" + gradle-version: "9.5.0" - name: Build core jar + install llama-kotlin facade to mavenLocal # install (not package) so the app's Gradle build resolves llama-kotlin + # the core POM from mavenLocal. llama-kotlin's core dep is provided-scope, so the @@ -1228,8 +1228,8 @@ jobs: distribution: temurin - uses: gradle/actions/setup-gradle@v6 with: - # AGP 9.2.0 (android-llmservice) requires Gradle >= 9.4.1. - gradle-version: "9.4.1" + # AGP 9.3.0 (android-llmservice) requires Gradle >= 9.5.0. + gradle-version: "9.5.0" - name: Enable KVM group permissions (GitHub-hosted runner) run: | echo 'KERNEL=="kvm", GROUP="kvm", MODE="0666", OPTIONS+="static_node=kvm"' | sudo tee /etc/udev/rules.d/99-kvm4all.rules diff --git a/CLAUDE.md b/CLAUDE.md index 9d7ee1928..2a96de04a 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -6,7 +6,7 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co Java bindings for [llama.cpp](https://github.com/ggerganov/llama.cpp) via JNI, providing a high-level API for LLM inference in Java. The Java layer communicates with a native C++ library through JNI. -Current llama.cpp pinned version: **b10107** +Current llama.cpp pinned version: **b10154** ## Upgrading CUDA Version @@ -429,7 +429,7 @@ needs no extra step here, `build-webui` re-reads the tag and rebuilds the matchi ships no UI): ```bash # needs node/npm + network; embed.cpp is plain C++17 (no npm) -git clone --depth 1 --branch b10107 https://github.com/ggml-org/llama.cpp /tmp/lc +git clone --depth 1 --branch b10154 https://github.com/ggml-org/llama.cpp /tmp/lc ( cd /tmp/lc/tools/ui && npm ci && npm run build \ && ( cd dist && find . -type f -not -path './_gzip/*' \ | while read -r f; do mkdir -p "_gzip/$(dirname "$f")"; gzip -9 -c "$f" > "_gzip/$f"; done ) \ @@ -469,7 +469,7 @@ cache lives in **Depot Cache** over sccache's **WebDAV** backend: - `SCCACHE_WEBDAV_TOKEN: ${{ secrets.DEPOT_TOKEN }}` — a Depot **organization** token, stored as the repo secret **`DEPOT_TOKEN`**. -Because `sccache` is **content-addressed** and llama.cpp is pinned (`GIT_TAG b10107`), the +Because `sccache` is **content-addressed** and llama.cpp is pinned (`GIT_TAG b10154`), the ~280 upstream object files are byte-identical every run, so a warm cache recompiles only the *changed* files. Depot's cache is **shared across all branches** (unlike GitHub's per-branch `actions/cache`), so every branch builds incrementally; a `b` version bump @@ -580,7 +580,7 @@ Current patches: | `0001-win32-arg-parse-embed-guard.patch` | Windows JNI regression from llama.cpp **#24779** (introduced b9739): on Windows `common_params_parse` re-derived argv from the **process** command line (`GetCommandLineW`) and adopted it, so an embedded/JNI caller (`java.exe`) lost its `--model …` args → "Failed to parse model parameters". b9789 narrowed the unconditional override to a **count-guard** (`if (static_cast(utf8.buf.size()) == argc) { argv = utf8.ptrs.data(); }`), but that is exactly the variant the project already found breaks its Windows server-integration tests (when the embedded argv length coincides with `java.exe`'s). The patch carries the **complete upstream change** (so it can be submitted to llama.cpp verbatim and then dropped here): **(1)** `common_params_parse` parses **exactly the argv it is given** (no `GetCommandLineW` magic) and a new `common_params_parse_main()` wrapper holds the UTF-8 recovery for the standalone tools' `main()` (`common/arg.{cpp,h}`); **(2)** the **~34 standalone `main()` call sites** (every `common_params_parse(argc, argv, …)` across `tools/*`, `examples/*` and the `tests/*` programs) flip to `common_params_parse_main()`; **(3)** a `tests/test-arg-parser.cpp` regression case pins that `common_params_parse` honors a caller-supplied argv. The embedded caller (`jllama.cpp`) keeps calling `common_params_parse` and is never overridden. **Our subproject build compiles only the `arg.{cpp,h}` core** — `LLAMA_BUILD_TOOLS`/`LLAMA_BUILD_TESTS` are OFF for a FetchContent subproject — so the flips + test are applied-but-not-compiled here; they were validated via a one-off `-DLLAMA_BUILD_TOOLS=ON -DLLAMA_BUILD_TESTS=ON` build (the new test compiles and its asserts pass; `test-arg-parser`'s only red there is the live `ggml.ai` download check, which is sandbox-network, not the patch). Because it spans **37 files** it must be refreshed on every llama.cpp bump (the applier fails loud). | | `0002-server-preserve-caller-load-progress-callback.patch` | Load-progress-callback regression introduced in llama.cpp **b9789**: `server_context::load_model` (`tools/server/server-context.cpp`) now **unconditionally** installs the server's own load-progress reporter on `params_base.load_progress_callback` immediately before `common_init_from_params`, clobbering any callback the embedding caller already set. libjllama's `LoadProgressCallback` feature wires `common_params.load_progress_callback` to a JNI trampoline *before* calling `load_model`, so the bump silently killed it — `LoadProgressCallbackTest` saw zero progress updates and the abort-on-`false` path never threw. The patch guards the assignment with `if (params_base.load_progress_callback == nullptr)`, so the server installs its own reporter **only when the caller hasn't** — a caller-supplied callback survives and fires during load. Standalone `llama-server` (no caller callback, so the field is null) is unaffected. Same JNI-vs-standalone divergence class as `0001`. | | `0003-pr22393-server-add-slot-prompt-similarity-getter-setter.patch` | **Upstream-PR carry** of [ggml-org/llama.cpp#22393](https://github.com/ggml-org/llama.cpp/pull/22393) ("server : add slot_prompt_similarity getter/setter") while it is still open upstream. Purely additive: adds `server_context::get_slot_prompt_similarity()` / `set_slot_prompt_similarity(float)` (`tools/server/server-context.{cpp,h}`) so an embedding/JNI caller can query and tune the slot-selection threshold at runtime without reloading the model. Verbatim copy of the PR — drop it once a pinned `b` includes the change. | -| `0007-server-attach-http-frontend.patch` | **Adds `llama_server_attach(argc, argv, server_context&)`** so the `NativeServer` *attach mode* can serve an **already-loaded `LlamaModel`** over the full upstream HTTP frontend — no second model load, no `start_loop()`; the LlamaModel's worker keeps driving the shared `server_context` and the HTTP routes post tasks to its queue (the queue is the synchronization point). Mechanically: (1) extracts the common route table + the CORS-proxy/tools **route bindings** out of `llama_server()` into `llama_server_register_common_routes(...)` (shared, so the entry points cannot drift; returns `false` on tools-setup failure) — the per-caller **experimental-feature warnings** (upstream's b10015/#25655 `cors_origins` security warning + the router/MCP/tools `warn_names` block) stay in `llama_server` since they depend on router state the shared helper does not carry; (2) adds `llama_server_attach`, which parses only the HTTP-side argv via `common_params_parse`, starts `g_stream_sessions` GC + `server_http_context`, registers the common routes plus the non-router resumable-streaming handlers, marks ready immediately (model already loaded), and blocks on the HTTP thread until `llama_server_request_shutdown()` — never calling `common_init()`, backend init, `ctx_server.terminate()` or `llama_backend_free()` (the embedding caller owns those). Applies after `0001`+`0006` (same file); closes the "NativeServer — reuse an already-loaded LlamaModel" TODO. Upstream-submittable ("server: let embedding callers attach the HTTP frontend to an existing server_context"). | +| `0007-server-attach-http-frontend.patch` | **Adds `llama_server_attach(argc, argv, server_context&)`** so the `NativeServer` *attach mode* can serve an **already-loaded `LlamaModel`** over the upstream HTTP frontend — no second model load, no `start_loop()`; the LlamaModel's worker keeps driving the shared `server_context` and the HTTP routes post tasks to its queue (the queue is the synchronization point). Mechanically: (1) extracts the **pure core route table** (`health` … `slots`) out of `llama_server()` into `static void llama_server_register_common_routes(ctx_http, routes)` (shared, so the two entry points cannot drift on the core endpoint set). **Scope note (narrowed at the b10154 bump):** the helper deliberately carries **only** the stable, state-independent route table — **not** the resumable-streaming routes (their handlers differ between router / non-router), the GCP-compat shim, or the experimental **CORS-proxy / MCP-server / built-in-tools** wiring. b10154 (upstream MCP-server support) moved the streaming routes into the middle of that block and coupled tools/CORS to a per-call `server_mcp mcp_mgr` lifecycle, so the earlier contiguous "route-table + CORS-proxy + tools" extraction is no longer possible; `llama_server()` keeps all of that inline, **byte-identical to upstream b10154** (only the route-table block is factored out). (2) adds `llama_server_attach`, which parses only the HTTP-side argv via `common_params_parse`, starts the stream-session GC + `server_http_context`, registers the common route table, the **non-router** resumable-streaming handlers (upstream b10154 paths `/v1/stream` GET/DEL + `/v1/streams/lookup` POST), the GCP-compat shim, and **403 "disabled" stubs for `/cors-proxy` + `/tools`** (attach mode does not wire the experimental CORS-proxy / MCP / built-in-tools host — those belong to a full `llama-server`, not an embedded model), marks ready immediately (model already loaded), and blocks on the HTTP thread until `llama_server_request_shutdown()` — never calling `common_init()`, backend init, `ctx_server.terminate()` or `llama_backend_free()` (the embedding caller owns those). Applies after `0001`+`0006` (same file); closes the "NativeServer — reuse an already-loaded LlamaModel" TODO. Upstream-submittable ("server: let embedding callers attach the HTTP frontend to an existing server_context"). | | `0008-server-models-worker-cmd-override.patch` | **Makes router mode usable in-JVM.** The router (`server-models.cpp`) spawns each model worker by re-executing its own binary (`get_server_exec_path()` = `/proc/self/exe` & friends) — inside a JVM that binary is `java`, not a llama-server, so embedded router workers could never start. The patch adds env `LLAMA_SERVER_WORKER_CMD` (whitespace-split; read in `server_model_meta::update_args`) which replaces only the leading binary-path token of the rendered worker args, letting an embedding host relaunch workers through its own bootstrap — e.g. `java -cp app.jar net.ladenthin.llama.server.NativeServer` (each worker is then a fresh JVM running the classic single-model `NativeServer`). Exposed in Java as `NativeServer.setWorkerCommand(String...)` (JNI `setenv`); exercised by `RouterModeIntegrationTest` (Linux CI). Upstream-submittable (also useful for containerized/wrapped deployments). | | `0006-server-embed-native-server-jni.patch` | **Makes `server.cpp`'s `llama_server` embeddable in the JVM** so the `NativeServer` JNI bridge can run the full upstream HTTP server (WebUI included) inside `libjllama` — see "Two server modes" below. b9870 already exposes `int llama_server(int, char**)` (non-static; no `main` in the file), so the patch only adds embedded-mode support: (1) a `g_llama_server_embedded` flag + `llama_server_set_embedded()` / `llama_server_request_shutdown()` (declared in the committed `src/main/cpp/native_server_bridge.h`); (2) skips installing the process-wide SIGINT/SIGTERM handlers when embedded (they would hijack the JVM's); (3) in embedded mode parses the **forwarded** argv via `common_params_parse` instead of `common_params_parse_main` (whose `GetCommandLineW` recovery would pick up `java.exe`'s command line — the same Windows class of bug `0001` fixes). `llama_server_request_shutdown()` mirrors the SIGTERM path (invokes the installed `shutdown_handler` → `ctx_server.terminate()` unblocks `start_loop()`), giving JNI an out-of-band stop since `ctx_server` is loop-local. Applies **after `0001`** (which flips this call site to `common_params_parse_main`), so its context is the post-`0001` tree; regenerate against `0001`+source on a bump. Only touches `tools/server/server.cpp`. | @@ -1262,7 +1262,7 @@ ctest --test-dir build --output-on-failure -R "ResultsToJson" #### Upstream source location (in CMake build tree) -llama.cpp is fetched via CMake FetchContent, pinned to `GIT_TAG b10107`. +llama.cpp is fetched via CMake FetchContent, pinned to `GIT_TAG b10154`. **GoogleTest** is a separate `BUILD_TESTING`-only FetchContent (`GIT_TAG v1.17.0`), used solely by the `jllama_test` C++ unit-test binary — not by the shipped library, and not coupled to the @@ -1677,20 +1677,20 @@ compiles/loads the API); this one has a UI and is driven end-to-end. The name is domain is the only string that must be globally unique. Structure (mirrors the consumer-test's plumbing): -- **`settings.gradle.kts`** — `rootProject.name = "android-llmservice"`; pins AGP `9.2.1` + the - Compose compiler plugin (`2.4.0`); `mavenLocal()` first so the freshly-built AAR + façade - resolve there in CI (Maven Central for real users). `9.2.1` (not `9.2.0`) fixes a real R8 - regression (`ClassNotFoundException` on `com.android.tools.r8.RecordTag` after upgrading - Gradle to 9.x with AGP 9.2.0) that hits this project directly since `buildTypes.release` - sets `isMinifyEnabled = true`; the `.github/android-consumer-test` fixture is pinned the - same way for the same reason. AGP 9.x requires Gradle >= 9.4.1 and - JDK 17+; CI already runs JDK 21 everywhere (`env.JAVA_VERSION`), so only the `gradle-version` +- **`settings.gradle.kts`** — `rootProject.name = "android-llmservice"`; pins AGP `9.3.0` + the + Compose compiler plugin (`2.4.10`); `mavenLocal()` first so the freshly-built AAR + façade + resolve there in CI (Maven Central for real users). Stay at `>= 9.2.1`: `9.2.1` (not `9.2.0`) + first fixed a real R8 regression (`ClassNotFoundException` on `com.android.tools.r8.RecordTag` + after upgrading Gradle to 9.x with AGP 9.2.0) that hits this project directly since + `buildTypes.release` sets `isMinifyEnabled = true`; `9.3.0` carries that fix forward and the + `.github/android-consumer-test` fixture is pinned the same way. AGP 9.3.x requires Gradle >= 9.5.0 + and JDK 17+; CI already runs JDK 21 everywhere (`env.JAVA_VERSION`), so only the `gradle-version` pin on the jobs that build this project (and the `.github/android-consumer-test` fixture) - needed bumping. AGP 9.0+ has **built-in Kotlin support** (a runtime dependency on Kotlin - Gradle plugin 2.2.10+), so the standalone `org.jetbrains.kotlin.android` plugin is no longer + needed bumping (9.4.1 → 9.5.0). AGP 9.0+ has **built-in Kotlin support** (a runtime dependency on + Kotlin Gradle plugin 2.2.10+), so the standalone `org.jetbrains.kotlin.android` plugin is no longer applied — applying it now fails the build with "no longer required for Kotlin support since AGP 9.0" (`app/build.gradle.kts` line 7). The Compose compiler plugin still applies - separately and its 2.4.0 pin exceeds AGP's 2.2.10 floor, so no other version changed. + separately and its 2.4.10 pin exceeds AGP's 2.2.10 floor, so no other version changed. - **`app/build.gradle.kts`** — `namespace`/`applicationId` `net.ladenthin.android.llmservice`, `minSdk 28` (AAR floor), `compileSdk 37` (raised from 35 — Compose/lifecycle/activity AAR metadata now requires it), `targetSdk 35`, Jetpack Compose, `androidx.appcompat` (only for diff --git a/README.md b/README.md index 57bd8928d..2921e8a5a 100644 --- a/README.md +++ b/README.md @@ -11,7 +11,7 @@ **Build:** ![Java 8+](https://img.shields.io/badge/Java-8%2B-informational) ![Platform](https://img.shields.io/badge/Platform-Linux%20%7C%20macOS%20%7C%20Windows%20%7C%20Android-lightgrey) -[![llama.cpp b10107](https://img.shields.io/badge/llama.cpp-%23b10107-informational)](https://github.com/ggml-org/llama.cpp/releases/tag/b10107) +[![llama.cpp b10154](https://img.shields.io/badge/llama.cpp-%23b10154-informational)](https://github.com/ggml-org/llama.cpp/releases/tag/b10154) [![JPMS](https://img.shields.io/badge/JPMS-modular%20JAR-25A162)](https://openjdk.org/projects/jigsaw/) ![JUnit](https://img.shields.io/badge/tested%20with-JUnit6-25A162) [![JSpecify](https://img.shields.io/badge/JSpecify-1.0.0%20%40NullMarked-25A162)](https://jspecify.dev) diff --git a/android-llmservice/README.md b/android-llmservice/README.md index d0338585e..fc926623e 100644 --- a/android-llmservice/README.md +++ b/android-llmservice/README.md @@ -199,7 +199,7 @@ gradle -p android-llmservice connectedDebugAndroidTest -PjllamaVersion="$VERSION ``` android-llmservice/ -├── settings.gradle.kts # AGP 9.2.1 (built-in Kotlin) + Compose plugin 2.4.0, mavenLocal first +├── settings.gradle.kts # AGP 9.3.0 (built-in Kotlin) + Compose plugin 2.4.10, mavenLocal first ├── gradle.properties ├── requirements.md # spec of record: every feature the app implements today (no unit tests) ├── TODO.md # roadmap: not-yet-built features diff --git a/android-llmservice/settings.gradle.kts b/android-llmservice/settings.gradle.kts index 37ad3a125..bae0aad35 100644 --- a/android-llmservice/settings.gradle.kts +++ b/android-llmservice/settings.gradle.kts @@ -14,19 +14,20 @@ pluginManagement { gradlePluginPortal() } // Versions pinned here (KISS: no version catalog). AGP matches the consumer-test - // fixture. AGP 9.x requires Gradle >= 9.4.1 — see the gradle-version pins on the CI - // jobs that build this project in publish.yml. 9.2.1 (not 9.2.0) is pinned: it fixes - // a real R8 regression (java.lang.ClassNotFoundException on + // fixture. AGP 9.3.x requires Gradle >= 9.5.0 — see the gradle-version pins on the CI + // jobs that build this project in publish.yml. Stay at >= 9.2.1: 9.2.1 (not 9.2.0) + // first fixed a real R8 regression (java.lang.ClassNotFoundException on // com.android.tools.r8.RecordTag after upgrading Gradle to 9.x with AGP 9.2.0) that - // hits this project directly since buildTypes.release sets isMinifyEnabled = true. + // hits this project directly since buildTypes.release sets isMinifyEnabled = true; + // 9.3.0 carries that fix forward. // AGP 9.0+ has built-in Kotlin support (runtime dependency on Kotlin Gradle plugin // 2.2.10+), so the standalone org.jetbrains.kotlin.android plugin is no longer // applied/needed — see https://developer.android.com/build/migrate-to-built-in-kotlin. - // The Compose compiler plugin (2.4.0) still applies separately and exceeds AGP's + // The Compose compiler plugin (2.4.10) still applies separately and exceeds AGP's // 2.2.10 floor. plugins { - id("com.android.application") version "9.2.1" - id("org.jetbrains.kotlin.plugin.compose") version "2.4.0" + id("com.android.application") version "9.3.0" + id("org.jetbrains.kotlin.plugin.compose") version "2.4.10" } } diff --git a/docs/history/llama-cpp-breaking-changes.md b/docs/history/llama-cpp-breaking-changes.md index 9b2ff23a7..3eb658241 100644 --- a/docs/history/llama-cpp-breaking-changes.md +++ b/docs/history/llama-cpp-breaking-changes.md @@ -513,3 +513,5 @@ Used during `llama.cpp` version bumps: when upgrading, scan this file from the r | b10076–b10092 | upstream verification (sandbox) | All **six** patches (`0001`–`0003`, `0006`–`0008`) re-verified against a clean b10092 checkout (ggml/llama.cpp commit `3ce7da2c8`): applied in filename order via `git apply`, all clean — the `b10076...b10092` diff's two patch-target files (`common/arg.cpp`, `tools/server/server-context.cpp`) changed only outside the patched regions (`0001`'s `common_params_parse*` block and `0002`/`0003`'s `load_model`/getter regions untouched), `0006`/`0007`'s `tools/server/server.cpp` and `0008`'s `tools/server/server-models.cpp` unchanged (`0006`'s standalone `git apply --check` fails only because its context is the post-`0001` tree, as documented). The OuteTTS generator ran clean against `tools/tts/tts.cpp @ b10092` (all anchors held, generated TU written). Per-platform build + `ctest` confirmation by the CI pipeline. | | b10092–b10107 | `common/common.h` + `include/llama.h` (**public-API break**) + `common/{arg.cpp,chat.cpp,common.cpp,fit.cpp}` + `ggml/src/{ggml-cuda/{common.cuh,mmq.cu,mmq.cuh,quantize.cu,quantize.cuh},ggml-hexagon/**,ggml-metal/ggml-metal-device.m}` + `src/{llama.cpp,llama-model.cpp,llama-model-loader.{cpp,h},llama-quant.cpp}` + `tools/{llama-bench/llama-bench.cpp,mtmd/mtmd-helper.cpp}` + `examples/{training/finetune.cpp,diffusion/diffusion-cli.cpp}` + `tools/ui/**` | **First real public-API break in many ranges (80 files, ~39.5k insertions, 15 commits).** Upstream PR [#20834](https://github.com/ggml-org/llama.cpp/pull/20834) (commit `e6dd0e29`, "args: refactor mlock/mmap/directio into load-mode") **removed the `use_mmap` / `use_mlock` / `use_direct_io` booleans from both `common_params` (`common/common.h`) and `llama_model_params` (`include/llama.h`)** and replaced them with a single `enum llama_load_mode load_mode` (values `NONE`/`MMAP`/`MLOCK`/`DIRECT_IO`), plus new `llama_load_mode_name()` / `llama_load_mode_from_str()` API and a `load_mode` copy in `common_model_params_to_llama` (`common/common.cpp`). **Required one project source change:** `llama/src/main/cpp/train_engine.cpp` set `params.use_mmap = false` to force writable weights for training → now `params.load_mode = LLAMA_LOAD_MODE_NONE` (mirrors upstream `finetune.cpp`'s identical flip in the same range). The **Java layer is unaffected**: `ModelFlag.MLOCK` / `NO_MMAP` emit the `--mlock` / `--no-mmap` CLI flags, which `common/arg.cpp` still accepts (now deprecated, they set `load_mode`) — `common/arg.h` is byte-identical. The other **six** priority-8 headers (`common/{chat.h,speculative.h,arg.h,download.h}`, `tools/mtmd/mtmd.h`, `include/llama-cpp.h`) are **byte-identical**. No patch-target file changed (`common/arg.cpp` moved only in the deprecated-flag region, well away from `0001`'s parse block; `tools/server/{server.cpp,server-context.cpp,server-models.cpp}` all identical), so all **six** patches (`0001`–`0003`, `0006`–`0008`) apply unchanged. The bulk is ggml backend work (CUDA MMQ/quantize rework, Hexagon `act-ops` rewrite, Metal device tweak), an internal `llama-model-loader` refactor, a `llama-bench` cleanup, and the auto-followed `tools/ui` WebUI. No OuteTTS generator anchor touched (`tools/tts/tts.cpp` unchanged). b10107 is the topmost release at bump time. | | b10092–b10107 | project source change (`train_engine.cpp`) + upstream verification (sandbox) | `train_engine.cpp` updated for the `use_mmap`→`load_mode` API break (see the row above); `LLAMA_LOAD_MODE_NONE` resolves via the already-included `llama.h`. All **six** patches (`0001`–`0003`, `0006`–`0008`) re-verified against a clean b10107 checkout (ggml/llama.cpp commit `c0bc8591`): applied in filename order via `git apply`, all clean — no patch-target file changed in the range (`0006`'s standalone `git apply --check` fails only because its context is the post-`0001` tree, as documented). The OuteTTS generator anchors hold (`tools/tts/tts.cpp` unchanged). Per-platform build + `ctest` confirmation by the CI pipeline. | +| b10107–b10154 | `common/{common.h,chat.h,chat.cpp,arg.cpp,arg.h}` + `tools/server/server.cpp` (**patch-target restructure — MCP-server support**) + new `common/{subproc.*,trie.*}` + `ggml/**` backends + `tools/ui/**` | **Two local patches refreshed; no project-source change (47 commits, ~100 files, ~5k line changes).** Upstream added **MCP-server support** ([#26170](https://github.com/ggml-org/llama.cpp/pull/26170) et al.): `common/arg.{cpp,h}` gain `common_print_available_devices()` + `--mcp-servers-config`/`--mcp-servers-json`; `common/{common.h,chat.h,chat.cpp}` change `thinking_end_tag` → `thinking_end_tags` (vector) and add `mcp_servers_*` fields (reasoning-budget internals — inside upstream-compiled `llama-common`/chat TUs, not referenced by project source). In `tools/server/server.cpp`, `llama_server()` gains a `server_mcp mcp_mgr` lifecycle (`mcp_mgr.start()`, **2-arg** `tools.setup(server_tools, mcp_mgr)` — was 1-arg — `mcp_mgr.shutdown()` in the cleanup lambdas) + a "MCP servers (experimental)" warn branch, and the resumable-streaming routes were **renamed** `/v1/stream/:conv_id` → `/v1/stream` and **moved** into the middle of the route/CORS/tools block. **Patch `0001` refreshed:** one `common/arg.h` hunk drifted (b10154 inserted `common_print_available_devices()` between `common_params_parse` and `common_params_to_map`); the other 36 files (incl. `common/arg.cpp`, the ~34 `common_params_parse_main` call sites, `tests/test-arg-parser.cpp`, `tools/server/server.cpp`, `tools/tts/tts.cpp`) applied unchanged. **Patch `0007` reworked** (the MCP-server restructure broke its contiguous extraction): the shared helper `llama_server_register_common_routes()` was **narrowed to the pure core route table** (`health` … `slots`) — `llama_server()` now keeps the streaming/GCP/CORS-proxy/MCP/tools blocks inline, **byte-identical to upstream b10154** (only the route-table block is factored out) — and `llama_server_attach()` registers the route table + non-router streaming on the new `/v1/stream` paths + GCP compat + 403 stubs for the experimental `/cors-proxy` + `/tools` endpoints it does not wire. `0002`/`0003`/`0006`/`0008` applied unchanged. b10154 is the topmost release at bump time. | +| b10107–b10154 | patch refresh (`0001`,`0007`) + upstream verification (sandbox) | Both refreshed patches + `0002`/`0003`/`0006`/`0008` re-verified against a clean b10154 checkout (ggml/llama.cpp commit `0e4a03622`): applied in filename order via `git apply`, all clean, no rejects; the fail-loud `PATCH_COMMAND` (`apply-llama-patches.cmake`) and the OuteTTS generator (`tts.cpp @ b10154`, all anchors held) both passed on a fresh `cmake -B build -DBUILD_TESTING=ON`. **Full `jllama` shared-library build (compile + link) verified locally** (`libjllama.so`, `-O3`) — the reworked `server.cpp` (helper + `llama_server_attach`) and all project TUs compile and **link** against b10154 (no undefined references), confirming the MCP-server-era API surface. No project source needed changing (`train_engine.cpp`'s prior `load_mode` fix from b10092–b10107 still holds). Per-platform build + `ctest` confirmation by the CI pipeline. | diff --git a/llama/CMakeLists.txt b/llama/CMakeLists.txt index c3922e737..b94f16cc2 100644 --- a/llama/CMakeLists.txt +++ b/llama/CMakeLists.txt @@ -173,7 +173,7 @@ set(LLAMA_BUILD_APP OFF CACHE BOOL "" FORCE) FetchContent_Declare( llama.cpp GIT_REPOSITORY https://github.com/ggerganov/llama.cpp.git - GIT_TAG b10107 + GIT_TAG b10154 PATCH_COMMAND ${CMAKE_COMMAND} -DPATCH_DIR=${CMAKE_CURRENT_SOURCE_DIR}/patches -DLLAMA_SRC= @@ -196,7 +196,7 @@ execute_process( COMMAND ${CMAKE_COMMAND} -DTTS_SRC=${llama.cpp_SOURCE_DIR}/tools/tts/tts.cpp -DOUT_CPP=${JLLAMA_TTS_GEN_CPP} - -DLLAMA_TAG=b10107 + -DLLAMA_TAG=b10154 -P ${CMAKE_CURRENT_SOURCE_DIR}/cmake/generate-tts-upstream.cmake RESULT_VARIABLE JLLAMA_TTS_GEN_RESULT ) diff --git a/llama/patches/0001-win32-arg-parse-embed-guard.patch b/llama/patches/0001-win32-arg-parse-embed-guard.patch index 252451cdd..54a779f41 100644 --- a/llama/patches/0001-win32-arg-parse-embed-guard.patch +++ b/llama/patches/0001-win32-arg-parse-embed-guard.patch @@ -1,8 +1,8 @@ diff --git a/common/arg.cpp b/common/arg.cpp -index a26093199..61fdfabb1 100644 +index 79480e06f..ed7793b4d 100644 --- a/common/arg.cpp +++ b/common/arg.cpp -@@ -1051,14 +1051,10 @@ static utf8_argv make_utf8_argv() { +@@ -1201,14 +1201,10 @@ static utf8_argv make_utf8_argv() { #endif bool common_params_parse(int argc, char ** argv, common_params & params, llama_example ex, void(*print_usage)(int, char **)) { @@ -21,7 +21,7 @@ index a26093199..61fdfabb1 100644 auto ctx_arg = common_params_parser_init(params, ex, print_usage); const common_params params_org = ctx_arg.params; // the example can modify the default params -@@ -1091,6 +1087,21 @@ bool common_params_parse(int argc, char ** argv, common_params & params, llama_e +@@ -1242,6 +1238,21 @@ bool common_params_parse(int argc, char ** argv, common_params & params, llama_e return true; } @@ -44,7 +44,7 @@ index a26093199..61fdfabb1 100644 std::vector supported_tmpl; int32_t res = llama_chat_builtin_templates(nullptr, 0); diff --git a/common/arg.h b/common/arg.h -index 54a38b9cc..04e934f6c 100644 +index 8f609e356..62c615d29 100644 --- a/common/arg.h +++ b/common/arg.h @@ -123,6 +123,11 @@ struct common_params_context { @@ -56,8 +56,8 @@ index 54a38b9cc..04e934f6c 100644 +// callers that supply their own argv must call common_params_parse() directly. +bool common_params_parse_main(int argc, char ** argv, common_params & params, llama_example ex, void(*print_usage)(int, char **) = nullptr); + - // parse input arguments from CLI into a map - bool common_params_to_map(int argc, char ** argv, llama_example ex, std::map & out_map); + // load all backends and print the list of available (non-CPU) devices to stdout + void common_print_available_devices(); diff --git a/examples/batched/batched.cpp b/examples/batched/batched.cpp index 830e45f5a..15b6910d7 100644 @@ -86,7 +86,7 @@ index 761e7a2db..c955241ea 100644 } diff --git a/examples/diffusion/diffusion-cli.cpp b/examples/diffusion/diffusion-cli.cpp -index 86ebbf88c..a4d5b04bb 100644 +index d58d22eff..1ab28accd 100644 --- a/examples/diffusion/diffusion-cli.cpp +++ b/examples/diffusion/diffusion-cli.cpp @@ -108,7 +108,7 @@ int main(int argc, char ** argv) { @@ -255,7 +255,7 @@ index f7fa5e306..36f14bf45 100644 } diff --git a/examples/training/finetune.cpp b/examples/training/finetune.cpp -index 0a75ac110..bdf13ba6a 100644 +index 44b284391..f99918aa0 100644 --- a/examples/training/finetune.cpp +++ b/examples/training/finetune.cpp @@ -22,7 +22,7 @@ int main(int argc, char ** argv) { @@ -268,10 +268,10 @@ index 0a75ac110..bdf13ba6a 100644 } diff --git a/tests/test-arg-parser.cpp b/tests/test-arg-parser.cpp -index e83ee85dd..f8605657d 100644 +index 1d3584f90..48cf43fd8 100644 --- a/tests/test-arg-parser.cpp +++ b/tests/test-arg-parser.cpp -@@ -113,6 +113,15 @@ static void test(void) { +@@ -112,6 +112,15 @@ static void test(void) { assert(true == common_params_parse(argv.size(), list_str_to_char(argv).data(), params, LLAMA_EXAMPLE_COMMON)); assert(params.model.path == "model_file.gguf"); @@ -288,7 +288,7 @@ index e83ee85dd..f8605657d 100644 assert(true == common_params_parse(argv.size(), list_str_to_char(argv).data(), params, LLAMA_EXAMPLE_COMMON)); assert(params.cpuparams.n_threads == 1234); diff --git a/tests/test-export-graph-ops.cpp b/tests/test-export-graph-ops.cpp -index 7d8118dcd..88b76410f 100644 +index 46ded1398..d5f1cabe7 100644 --- a/tests/test-export-graph-ops.cpp +++ b/tests/test-export-graph-ops.cpp @@ -131,7 +131,7 @@ int main(int argc, char ** argv) { @@ -301,7 +301,7 @@ index 7d8118dcd..88b76410f 100644 } diff --git a/tests/test-recurrent-state-rollback.cpp b/tests/test-recurrent-state-rollback.cpp -index be19316db..26a041aea 100644 +index 8e2eace6a..d7a7afed9 100644 --- a/tests/test-recurrent-state-rollback.cpp +++ b/tests/test-recurrent-state-rollback.cpp @@ -44,7 +44,7 @@ int main(int argc, char ** argv) { @@ -314,10 +314,10 @@ index be19316db..26a041aea 100644 } diff --git a/tests/test-save-load-state.cpp b/tests/test-save-load-state.cpp -index b097d752a..bbafc5234 100644 +index 6e93ce6fb..9caab1653 100644 --- a/tests/test-save-load-state.cpp +++ b/tests/test-save-load-state.cpp -@@ -281,7 +281,7 @@ int main(int argc, char ** argv) { +@@ -358,7 +358,7 @@ int main(int argc, char ** argv) { common_init(); @@ -366,10 +366,10 @@ index e2dcd0b2e..0fdecd02c 100644 } diff --git a/tools/cli/cli.cpp b/tools/cli/cli.cpp -index d974a4019..98a1bdd75 100644 +index dcdb6aeac..0f4a2d188 100644 --- a/tools/cli/cli.cpp +++ b/tools/cli/cli.cpp -@@ -371,7 +371,7 @@ int llama_cli(int argc, char ** argv) { +@@ -37,7 +37,7 @@ int llama_cli(int argc, char ** argv) { common_init(); @@ -457,10 +457,10 @@ index b88a16f0f..db4facf3d 100644 } diff --git a/tools/mtmd/mtmd-cli.cpp b/tools/mtmd/mtmd-cli.cpp -index 8704ea79d..eecbaaeb0 100644 +index 08288c868..54ee01c66 100644 --- a/tools/mtmd/mtmd-cli.cpp +++ b/tools/mtmd/mtmd-cli.cpp -@@ -375,7 +375,7 @@ int main(int argc, char ** argv) { +@@ -376,7 +376,7 @@ int main(int argc, char ** argv) { common_init(); @@ -496,10 +496,10 @@ index f2179ed27..6d958a861 100644 } if (params.out_file.empty()) { diff --git a/tools/server/server.cpp b/tools/server/server.cpp -index 9e8603be6..e81ecba3f 100644 +index a3b2a8b0f..80d6a3ff6 100644 --- a/tools/server/server.cpp +++ b/tools/server/server.cpp -@@ -87,7 +87,7 @@ int llama_server(int argc, char ** argv) { +@@ -102,7 +102,7 @@ int llama_server(int argc, char ** argv) { // touch it. lifecycle is symmetric, stop_gc() runs in clean_up() before backend free server_stream_session_manager_start(); diff --git a/llama/patches/0007-server-attach-http-frontend.patch b/llama/patches/0007-server-attach-http-frontend.patch index 7ada3bb34..ebc03b7d8 100644 --- a/llama/patches/0007-server-attach-http-frontend.patch +++ b/llama/patches/0007-server-attach-http-frontend.patch @@ -1,5 +1,5 @@ diff --git a/tools/server/server.cpp b/tools/server/server.cpp -index dc9e718..47da913 100644 +index ce1d239c3..b242fc48a 100644 --- a/tools/server/server.cpp +++ b/tools/server/server.cpp @@ -63,6 +63,7 @@ int llama_server(int argc, char ** argv); @@ -10,22 +10,18 @@ index dc9e718..47da913 100644 void llama_server_terminate(); void llama_server_terminate() { if (shutdown_handler) { -@@ -107,6 +108,102 @@ static server_http_context::handler_t ex_wrapper(server_http_context::handler_t +@@ -107,6 +108,57 @@ static server_http_context::handler_t ex_wrapper(server_http_context::handler_t }; } -+// [jllama] Route table shared by the standalone single-model server, the router, and the -+// embedded attach mode (llama_server_attach below). Extracted verbatim from llama_server() so the -+// entry points cannot drift. The resumable-streaming routes are NOT registered here: their -+// handlers differ between router and non-router mode, so each entry point wires its own. The -+// experimental-feature WARNINGS (CORS/router/tools) are likewise logged per-entry-point, since -+// they depend on router state the helper does not carry; the helper only binds the routes. Returns -+// false when the experimental built-in tools were requested but failed to set up. -+[[nodiscard]] static bool llama_server_register_common_routes( -+ server_http_context & ctx_http, -+ server_routes & routes, -+ const common_params & params, -+ server_tools & tools) { ++// [jllama] Pure route table shared by the standalone single-model server and the embedded ++// attach mode (llama_server_attach below), extracted verbatim from llama_server() so the two ++// entry points cannot drift on the core endpoint set. Only the stable, state-independent ++// routes live here (health .. slots); the resumable-streaming routes (handlers differ by ++// router vs non-router), the GCP-compat shim and the experimental CORS-proxy / MCP / ++// built-in-tools wiring stay in each entry point, since upstream couples them to per-call ++// state (server_mcp mcp_mgr lifecycle, is_router_server). ++static void llama_server_register_common_routes(server_http_context & ctx_http, server_routes & routes) { + ctx_http.get ("/health", ex_wrapper(routes.get_health)); // public endpoint (no API key check) + ctx_http.get ("/v1/health", ex_wrapper(routes.get_health)); // public endpoint (no API key check) + ctx_http.get ("/metrics", ex_wrapper(routes.get_metrics)); @@ -67,53 +63,12 @@ index dc9e718..47da913 100644 + // Save & load slots + ctx_http.get ("/slots", ex_wrapper(routes.get_slots)); + ctx_http.post("/slots/:id_slot", ex_wrapper(routes.post_slots)); -+ -+ // Google Cloud Platform (Vertex AI) compat -+ ctx_http.register_gcp_compat(); -+ -+ // return 403 for disabled features -+ server_http_context::handler_t res_403 = [](const server_http_req &) { -+ auto res = std::make_unique(); -+ res->status = 403; -+ res->data = safe_json_to_str({ -+ {"error", { -+ {"message", "this feature is disabled"}, -+ {"type", "feature_disabled"}, -+ }} -+ }); -+ return res; -+ }; -+ -+ // CORS proxy (EXPERIMENTAL, only used by the Web UI for MCP) -+ if (params.ui_mcp_proxy) { -+ ctx_http.get ("/cors-proxy", ex_wrapper(proxy_handler_get)); -+ ctx_http.post("/cors-proxy", ex_wrapper(proxy_handler_post)); -+ } else { -+ ctx_http.get ("/cors-proxy", ex_wrapper(res_403)); -+ ctx_http.post("/cors-proxy", ex_wrapper(res_403)); -+ } -+ -+ // EXPERIMENTAL built-in tools -+ if (!params.server_tools.empty()) { -+ try { -+ tools.setup(params.server_tools); -+ } catch (const std::exception & e) { -+ SRV_ERR("tools setup failed: %s\n", e.what()); -+ return false; -+ } -+ ctx_http.get ("/tools", ex_wrapper(tools.handle_get)); -+ ctx_http.post("/tools", ex_wrapper(tools.handle_post)); -+ } else { -+ ctx_http.get ("/tools", ex_wrapper(res_403)); -+ ctx_http.post("/tools", ex_wrapper(res_403)); -+ } -+ return true; +} + int llama_server(int argc, char ** argv) { std::setlocale(LC_NUMERIC, "C"); -@@ -250,47 +347,9 @@ int llama_server(common_params & params, int argc, char ** argv) { +@@ -258,47 +310,7 @@ int llama_server(common_params & params, int argc, char ** argv) { ctx_http.del ("/models", ex_wrapper(models_routes->del_router_models)); } @@ -158,82 +113,16 @@ index dc9e718..47da913 100644 - // Save & load slots - ctx_http.get ("/slots", ex_wrapper(routes.get_slots)); - ctx_http.post("/slots/:id_slot", ex_wrapper(routes.post_slots)); -+ if (!llama_server_register_common_routes(ctx_http, routes, params, tools)) { -+ return 1; -+ } ++ llama_server_register_common_routes(ctx_http, routes); - // resumable streaming, the conversation_id is the session identity end to end. router and - // child wire different handlers under the same paths: a child binds the local session -@@ -315,22 +374,9 @@ int llama_server(common_params & params, int argc, char ** argv) { - ctx_http.post("/v1/streams/lookup", ex_wrapper(streams_lookup_h)); - ctx_http.del ("/v1/stream/:conv_id", ex_wrapper(stream_delete_h)); - -- // Google Cloud Platform (Vertex AI) compat -- ctx_http.register_gcp_compat(); -- -- // return 403 for disabled features -- server_http_context::handler_t res_403 = [](const server_http_req &) { -- auto res = std::make_unique(); -- res->status = 403; -- res->data = safe_json_to_str({ -- {"error", { -- {"message", "this feature is disabled"}, -- {"type", "feature_disabled"}, -- }} -- }); -- return res; -- }; -- -+ // experimental-feature warnings — the CORS-proxy, /tools and health...slots routes are all -+ // bound by llama_server_register_common_routes() above; only these log lines stay here because -+ // they depend on router state (is_router_server) the shared helper does not carry. - if (params.cors_origins == "*" && params.api_keys.empty()) { - SRV_WRN("%s", "-----------------\n"); - SRV_WRN("%s", "CORS is set to allow all origins ('*') and no API key is set\n"); -@@ -339,37 +385,16 @@ int llama_server(common_params & params, int argc, char ** argv) { - SRV_WRN("%s", "-----------------\n"); - } - -- // CORS proxy (EXPERIMENTAL, only used by the Web UI for MCP) - std::vector warn_names; - if (is_router_server) { - warn_names.push_back("router mode"); - } -- - if (params.ui_mcp_proxy) { -- ctx_http.get ("/cors-proxy", ex_wrapper(proxy_handler_get)); -- ctx_http.post("/cors-proxy", ex_wrapper(proxy_handler_post)); - warn_names.push_back("MCP proxy (experimental)"); -- } else { -- ctx_http.get ("/cors-proxy", ex_wrapper(res_403)); -- ctx_http.post("/cors-proxy", ex_wrapper(res_403)); - } -- -- // EXPERIMENTAL built-in tools - if (!params.server_tools.empty()) { -- try { -- tools.setup(params.server_tools); -- } catch (const std::exception & e) { -- SRV_ERR("tools setup failed: %s\n", e.what()); -- return 1; -- } -- ctx_http.get ("/tools", ex_wrapper(tools.handle_get)); -- ctx_http.post("/tools", ex_wrapper(tools.handle_post)); - warn_names.push_back("built-in tools (experimental)"); -- } else { -- ctx_http.get ("/tools", ex_wrapper(res_403)); -- ctx_http.post("/tools", ex_wrapper(res_403)); - } -- - if (warn_names.size() > 0) { - SRV_WRN("%s", "-----------------\n"); - SRV_WRN("%s", "the following feature(s) are enabled:\n"); -@@ -538,3 +563,68 @@ int llama_server(common_params & params, int argc, char ** argv) { + // resumable streaming: a child binds the local session factories, the router binds + // proxies that resolve the owning child, see server-stream.h +@@ -556,3 +568,89 @@ int llama_server(common_params & params, int argc, char ** argv) { return 0; } + -+// [jllama] Attach the upstream HTTP frontend — full route table, WebUI assets, resumable ++// [jllama] Attach the upstream HTTP frontend — full core route table, WebUI assets, resumable +// streaming — to an ALREADY-LOADED server_context owned by an embedding caller (a LlamaModel +// driven over JNI). Unlike llama_server(): no common_init(), no backend/NUMA init, no model +// load and no start_loop() — the caller's worker thread keeps driving the context, the HTTP @@ -241,7 +130,10 @@ index dc9e718..47da913 100644 +// HTTP-relevant argv (--host/--port/--api-key/...; no -m). Blocks until +// llama_server_request_shutdown(); never terminates the shared server_context or frees the +// backend — the embedding caller owns both. Shares shutdown_handler with llama_server(), so the -+// single-instance-per-process rule covers both entry points. ++// single-instance-per-process rule covers both entry points. The experimental CORS-proxy / MCP ++// server / built-in-tools endpoints are NOT wired in attach mode (they belong to a full ++// llama-server host, not an embedded model); they answer 403 "disabled" like a stock build with ++// those features off. +int llama_server_attach(int argc, char ** argv, server_context & ctx_server) { + std::setlocale(LC_NUMERIC, "C"); + @@ -262,16 +154,34 @@ index dc9e718..47da913 100644 + } + + server_routes routes(params, ctx_server); -+ server_tools tools; -+ if (!llama_server_register_common_routes(ctx_http, routes, params, tools)) { -+ server_stream_session_manager_stop(); -+ return 1; -+ } ++ llama_server_register_common_routes(ctx_http, routes); + -+ // single-model (non-router) resumable-streaming handlers -+ ctx_http.get ("/v1/stream/:conv_id", ex_wrapper(server_stream_make_get_handler())); ++ // single-model (non-router) resumable-streaming handlers (upstream b10154 paths) ++ ctx_http.get ("/v1/stream", ex_wrapper(server_stream_make_get_handler())); + ctx_http.post("/v1/streams/lookup", ex_wrapper(server_stream_make_lookup_handler())); -+ ctx_http.del ("/v1/stream/:conv_id", ex_wrapper(server_stream_make_delete_handler())); ++ ctx_http.del ("/v1/stream", ex_wrapper(server_stream_make_delete_handler())); ++ ++ // Google Cloud Platform (Vertex AI) compat — cheap, kept for parity with llama_server() ++ ctx_http.register_gcp_compat(); ++ ++ // return 403 for the experimental features attach mode does not wire (CORS proxy, built-in ++ // tools), so those paths answer "disabled" rather than 404 — matching a stock server built ++ // with the features off. ++ server_http_context::handler_t res_403 = [](const server_http_req &) { ++ auto res = std::make_unique(); ++ res->status = 403; ++ res->data = safe_json_to_str({ ++ {"error", { ++ {"message", "this feature is disabled"}, ++ {"type", "feature_disabled"}, ++ }} ++ }); ++ return res; ++ }; ++ ctx_http.get ("/cors-proxy", ex_wrapper(res_403)); ++ ctx_http.post("/cors-proxy", ex_wrapper(res_403)); ++ ctx_http.get ("/tools", ex_wrapper(res_403)); ++ ctx_http.post("/tools", ex_wrapper(res_403)); + + if (!ctx_http.start()) { + SRV_ERR("%s", "exiting due to HTTP server error\n"); diff --git a/llama/src/main/java/net/ladenthin/llama/value/LlamaCppVersion.java b/llama/src/main/java/net/ladenthin/llama/value/LlamaCppVersion.java index 48bf993fd..11ae43e90 100644 --- a/llama/src/main/java/net/ladenthin/llama/value/LlamaCppVersion.java +++ b/llama/src/main/java/net/ladenthin/llama/value/LlamaCppVersion.java @@ -10,13 +10,13 @@ * library was compiled against, exposed as a compile-time constant so callers can render a badge or * emit a startup log line without loading the native library. * - *

{@link #LLAMA_CPP_VERSION} is a pure-Java string ({@code "b10107"}) that mirrors the + *

{@link #LLAMA_CPP_VERSION} is a pure-Java string ({@code "b10154"}) that mirrors the * {@code GIT_TAG} in {@code llama/CMakeLists.txt}. It is available even when {@code libjllama} is * absent (pure-Java checkout, before {@code System.load}), which is what makes it suitable for a * lightweight version badge in Android or other UIs.

* *

For the authoritative value that is baked into the native binary — the build number - * plus the resolved upstream commit, e.g. {@code "b10107-"} — call + * plus the resolved upstream commit, e.g. {@code "b10154-"} — call * {@link net.ladenthin.llama.LlamaModel#getLlamaCppBuildInfo()} instead; that reads llama.cpp's own * {@code build-info} through JNI and therefore cannot drift from the compiled library (but requires * the native library to be loaded).

@@ -24,14 +24,14 @@ public final class LlamaCppVersion { /** - * The pinned llama.cpp release tag this library was built against, e.g. {@code "b10107"}. + * The pinned llama.cpp release tag this library was built against, e.g. {@code "b10154"}. * *

Kept in lockstep with {@code GIT_TAG} in {@code llama/CMakeLists.txt} — see the * "Upgrading/Downgrading llama.cpp Version" checklist in {@code CLAUDE.md}. This is the * compile-time pin; use {@link net.ladenthin.llama.LlamaModel#getLlamaCppBuildInfo()} for the * value actually linked into the native binary.

*/ - public static final String LLAMA_CPP_VERSION = "b10107"; + public static final String LLAMA_CPP_VERSION = "b10154"; // Constants holder — not instantiable. private LlamaCppVersion() {}