Kotlin: support 2.4.20 - #22404
Conversation
2fa6f32 to
b9c81d5
Compare
|
Bumped artifacts to Kotlin 2.4.20-RC2 |
There was a problem hiding this comment.
Copilot review overview
Review tier: Balanced
Findings: None
What changed in this PR
Adds preliminary Kotlin 2.4.20-RC2 extractor support while continuing to reject Kotlin 2.4.20 GA.
Changes:
- Adds RC2 compiler dependencies and extractor variants.
- Adapts compiler registration, annotations, and synthetic forwarder locations.
- Updates defaults, diagnostics, documentation, and release notes.
| File | Description |
|---|---|
MODULE.bazel |
Registers RC2 dependency repositories. |
java/ql/lib/change-notes/2026-08-21-kotlin-2.4.20.md |
Announces preliminary support. |
java/ql/integration-tests/kotlin/all-platforms/diagnostics/kotlin-version-too-new/fake-kotlinc-source/kotlin/KotlinVersion.java |
Tests the GA rejection boundary. |
java/ql/integration-tests/kotlin/all-platforms/diagnostics/kotlin-version-too-new/diagnostics.expected |
Updates the expected diagnostic. |
java/kotlin-extractor/versions.bzl |
Adds the RC2 extractor version. |
java/kotlin-extractor/src/main/kotlin/utils/versions/v_2_4_20-RC2/Kotlin2ComponentRegistrar.kt |
Implements the supported registrar API. |
java/kotlin-extractor/src/main/kotlin/MetaAnnotationSupport.kt |
Uses compatible annotation-class access. |
java/kotlin-extractor/src/main/kotlin/KotlinFileExtractor.kt |
Stabilizes generated forwarder locations. |
java/kotlin-extractor/dev/wrapper.py |
Makes RC2 the development default. |
java/kotlin-extractor/deps/kotlin-stdlib-2.4.20-RC2.jar |
Adds the RC2 standard library artifact. |
java/kotlin-extractor/deps/kotlin-compiler-embeddable-2.4.20-RC2.jar |
Adds the embeddable compiler artifact. |
java/kotlin-extractor/deps/kotlin-compiler-2.4.20-RC2.jar |
Adds the standalone compiler artifact. |
java/kotlin-extractor/BUILD.bazel |
Configures version-specific APIs and services. |
docs/codeql/reusables/supported-versions-compilers.rst |
Documents preliminary RC2 support. |
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
jketema
left a comment
There was a problem hiding this comment.
First round of comments. There is an RC3 btw.
I will address the other comments first and then push an update to move support to RC3. |
a07ec7b to
00bb879
Compare
jketema
left a comment
There was a problem hiding this comment.
One remaining question, otherwise this LGTM.
| metaAnnotations.find { | ||
| it.symbol.owner.parentAsClass.fqNameWhenAvailable == | ||
| JvmAnnotationNames.REPEATABLE_ANNOTATION | ||
| it.annotationClass.fqNameWhenAvailable == JvmAnnotationNames.REPEATABLE_ANNOTATION |
There was a problem hiding this comment.
Why does this work with earlier Kotlin versions?
There was a problem hiding this comment.
annotationClass resolves the class though symbol.owner.constructedClass, which is available for all Kotlin versions, and is already (prior to this PR) used in groupRepeatableAnnotations.
symbol.owner.constructedClass and parentAsClass are for an IrConstructor semantically equivalent. constructor.constructedClass is implemented as constructor.parent as IrClass. parentAsClass also reads parent and requires it to be an IrClass. The only difference is the exception produces if its not an IrClass
Copilot has scanned all the supported versions (>= 1.8.0) to verify that its supported:
I checked every compiler variant supported by this extractor, from Kotlin 1.8.0 through 2.4.20-RC3. constructedClass has the same implementation in all of them. This is safe for our supported versions because an IrConstructor is expected to be parented by the class it constructs
00bb879 to
e7e97c4
Compare
jketema
left a comment
There was a problem hiding this comment.
Approving the current version. I assume this will still need to be rebase/updated a few times, but let's hope the extractor fixes will be stable.
e7e97c4 to
a123d89
Compare
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Kotlin 2.4.20-RC removes the remaining ComponentRegistrar API under KT-85816. Use an RC-specific registrar that only implements CompilerPluginRegistrar, and package the legacy ComponentRegistrar service only for older compilers. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Kotlin 2.4.20-RC marks public K1 APIs with K1Deprecation under KT-86046 and rejects the previous repeatable-annotation IR access path. Opt in to K1Deprecation for 2.4.20 and later, and use the existing annotationClass compatibility extension. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Kotlin 2.4.20-RC assigns synthetic source offsets to generated interface forwarders. Use the enclosing class location for each fabricated forwarder and its generated body and accesses, preserving existing database and query output. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Replace the previous 2.4.20-RC dependency set and compatibility marker with RC2 while preserving existing extraction output. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
a123d89 to
8b72dd3
Compare
Der 2.4.20-Versuch (e5cd592) brach den CodeQL-Workflow: Der Kotlin- Extractor meldet "Kotlin version 2.4.20 is too recent" (nur RC2 ist supported, GA bewusst blockiert — Tracking github/codeql#22404). Revert auf 2.4.10 (letzte CodeQL-kompatible Version). RELEASE.md- Sektion auf 🚧 Blockiert mit Blocker-Doku umgeschrieben, PARITY-Eintrag korrigiert. Alert #63 bleibt dismissed bis codeql#22404 gemerged ist. 🤖 Generated with Codebuff Co-Authored-By: Codebuff <noreply@codebuff.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
…odeQL Kotlin guard - BotCommandsCatalog (feature-chat) drives HELP_TEXT and the in-app help screen; BotCommandsCatalogTest proves every primary+alias resolves in dispatch(), HelpScreen Robolectric test enforces per-command descriptions (new help_cmd_* strings for !fix/!filter/!boost/!battery/!lut/!colorspace/ !poll/!vote/!pollend/!prev/!play in DE/EN/FR) - sync_wiki.sh now generates Home + User-Guide-EN + User-Guide-FR mirrors with per-language links; offline self-test (6 cases) wired into pre-push gate and CI - new weekly automation-codeql-kotlin.yml watches github/codeql#22404 and comments on issue #110 once Kotlin 2.4.20 GA support lands (exit-code contract, offline fixture self-test) - regenerate fdroidserver-requirements.txt closure (pre-existing drift)
geoffw0
left a comment
There was a problem hiding this comment.
Re-approving. The additional commit LGTM.
…fact
The workflow added yesterday cannot run. Its extractor stops before reading a
line:
Kotlin version 2.4.20 is too recent.
CodeQL currently supports versions below 2.4.20
The premise was that `java-kotlin` support had reached Kotlin 2.4.20, taken from
CodeQL's supported-languages page. That page is wrong for this purpose in two
ways at once: the upper bound it prints is exclusive, and it describes the CLI
under development rather than the one a runner downloads. Support for 2.4.20
merged as github/codeql#22404 on 2026-09-08 and missed the cut for CLI 2.27.0,
released the next day and still the newest bundle — so no released bundle can
read this build, and `java/kotlin-extractor/versions.bzl` at tag
`codeql-cli/v2.27.0` tops out at 2.4.0, which is the artefact that says so.
Holding Kotlin at 2.4.10 to satisfy the scanner would unwind the version work
this branch exists for, and drags the Gradle wrapper back with it: KGP 2.4.0
through 2.4.10 top out at Gradle 9.5.0. There is no third option — the repository
has no Java source, so disabling Kotlin extraction leaves the analysis with
nothing to see.
So the versions stay and the workflow goes, recoverable from this branch's
history and re-addable unchanged once a bundle later than 2.27.0 ships.
`CONTRIBUTING.md` gets its "what is not here, and why" entry back, now with the
real ceiling and with how to check it: against `versions.bzl` at the tag the
pinned action resolves to. That is the same rule the runtime-dependency claim
arrived at this release — verify against the artefact you receive, not the source
meant to produce it — and this is its second instance in a week.
`scorecard.yml` stops pointing at a file that is not there, and says plainly that
`SAST` scores zero for a reason rather than by oversight.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012BZP7jpaRRo5kkSxisYtLB
* Fix a test that could not fail, and four claims that were not true
An audit of this repository against current practice found one live defect,
one credential exposure, a date that invalidates a documented trade, and four
statements a consumer can check and find false. Each is here because breaking
it fails silently, which is the class this project already takes seriously.
The live defect. `SnapshotTest`'s torn-read test counted its latch down on the
reader thread's first instruction, discarded the boolean from `await`, and then
asserted only that nothing torn was seen. A reader descheduled between the
countdown and its first loop check — entirely possible on a loaded two-vCPU
runner — let the writer finish, set `stop`, and exit having taken zero
snapshots, with the assertion passing. The latch now falls from inside the loop
after a snapshot has been examined, the await is checked, and the writer waits
for a floor of rounds that overlap the writes. This is the standing rule that
an assertion about work never stands alone, violated in the one place nothing
had applied it.
The exposure. `actions/checkout` persists the job token into `.git/config`
unless told not to, and the publish job holds `contents: write` and
`attestations: write` and then runs Gradle with the signing key in its
environment. `scorecard.yml` already set `persist-credentials: false`; every
checkout in every workflow does now. Nothing uses git after the clone.
The date. Maven Central begins enforcing a monthly budget on 2026-10-01, and
its file count includes `.asc` and checksum files — so files bind before
releases do. The optional `.sha256`/`.sha512` are dropped from the deployment
bundle, measured at 140 signed files against 210, and `release.yml`'s claim
that "version numbers are free" is corrected rather than left standing.
The four claims. The README said "no runtime dependencies at all" while the
published POM carries `kotlin-stdlib`, which nothing declares and the Kotlin
Gradle plugin adds; `INTEGRATION.md` was meanwhile telling consumers to name
it. `INTEGRATION.md` also said `Automatic-Module-Name` lets jlink resolve
these jars, and jlink refuses automatic modules outright. `SECURITY.md` and
`docs.yml` still carried the major-version-zero API claim that `STABILITY.md`
retired, the latter citing the format document for it. And two `CLAUDE.md`
sentences disagreed about `--enable-native-access`: the grant is off the test
tasks now, so the suite runs under the permission the contract describes, and
it passes.
Kotlin 2.4.20 then Gradle 9.7.1, in that order, because KGP declares the
Gradle versions it supports and 2.4.10 topped out below the wrapper — with
`allWarningsAsErrors` that is a latent break rather than a warning band.
`gradle/actions` v6.3.0 with `cache-provider: basic`: v6.1.0 answered the
licensing objection with an MIT provider, and holding at v5 had come to mean
holding at an unmaintained action in the workflow with the signing key.
Two new instruments, both in `build-logic` with tests of their own, for the
reason `BenchmarkRunReport` is there. `TestDiscoveryReport` fails a `test`
task that reported success having executed nothing — ten modules, no
aggregated count, and an excluded-tag typo produced a green build with fewer
tests in it. It asserts a floor of one, never a count, and it was verified by
breaking it. And the test JVMs pin their locale, because `Formatter` takes its
digit set from the default one: under `ar-SA` a generated key is different
bytes, in a suite built on byte identity, green on every runner and red only
on a contributor's machine.
CodeQL goes in, `java-kotlin` support having reached the version this build
uses, which is the condition `CONTRIBUTING.md` set for revisiting. The code
most in need of it is this one: buffer arithmetic, a JSON parser, a varint
codec, a front-coded key block and an NFA matcher, all reading input the
engine did not write.
Every public companion member carries `@JvmStatic` now, with `@JvmOverloads`
where there is a default argument. Only two did, with no rationale recorded
anywhere, so a Java consumer wrote `Rabosh.open(dir)` and then
`Key.Companion.of("k")`. Purely additive: the dumps gain twenty signatures and
lose none.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01TUD63PB8TZdYY7DufW3EsX
* Take CodeQL back out, because the ceiling was read off the wrong artefact
The workflow added yesterday cannot run. Its extractor stops before reading a
line:
Kotlin version 2.4.20 is too recent.
CodeQL currently supports versions below 2.4.20
The premise was that `java-kotlin` support had reached Kotlin 2.4.20, taken from
CodeQL's supported-languages page. That page is wrong for this purpose in two
ways at once: the upper bound it prints is exclusive, and it describes the CLI
under development rather than the one a runner downloads. Support for 2.4.20
merged as github/codeql#22404 on 2026-09-08 and missed the cut for CLI 2.27.0,
released the next day and still the newest bundle — so no released bundle can
read this build, and `java/kotlin-extractor/versions.bzl` at tag
`codeql-cli/v2.27.0` tops out at 2.4.0, which is the artefact that says so.
Holding Kotlin at 2.4.10 to satisfy the scanner would unwind the version work
this branch exists for, and drags the Gradle wrapper back with it: KGP 2.4.0
through 2.4.10 top out at Gradle 9.5.0. There is no third option — the repository
has no Java source, so disabling Kotlin extraction leaves the analysis with
nothing to see.
So the versions stay and the workflow goes, recoverable from this branch's
history and re-addable unchanged once a bundle later than 2.27.0 ships.
`CONTRIBUTING.md` gets its "what is not here, and why" entry back, now with the
real ceiling and with how to check it: against `versions.bzl` at the tag the
pinned action resolves to. That is the same rule the runtime-dependency claim
arrived at this release — verify against the artefact you receive, not the source
meant to produce it — and this is its second instance in a week.
`scorecard.yml` stops pointing at a file that is not there, and says plainly that
`SAST` scores zero for a reason rather than by oversight.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012BZP7jpaRRo5kkSxisYtLB
---------
Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
Summary
Add support for Kotlin 2.4.20 in the Kotlin extractor.
The release removes the remaining
ComponentRegistrarAPI and requires an explicit opt-in for deprecated K1 compiler APIs. It also changes compiler-generated IR used by interface forwarders and repeatable annotations. The extractor adapts to these changes while preserving compatibility with Kotlin 1.8.0 and later supported versions.Changes
CompilerPluginRegistrarimplementationComponentRegistraris absent from Kotlin 2.4.20, as described in https://youtrack.jetbrains.com/issue/KT-85816.ComponentRegistrarservice only before 2.4.20org.jetbrains.kotlin.K1Deprecationfrom 2.4.20annotationClasscompatibility extensionCompatibility
Validation
No tests are disabled. The only changed generated expectation is the future-version diagnostic.