Admin message

Due to a large amount of spam we do not allow new users to create repositories, they are "external" users. If you are a new user and want to create a repository, for example for forking GHC, open a new issue on ghc/ghc using the "get-verified" issue template

Free type variables in a static form are (wrongly) rejected
<!-- ══════════════════════════════════════════════════════════════════ Draft metadata (for Simon — strip before filing) Covers GlaHiCo finding f2 of snippet 6148. Finding f1 was DROPPED — see below. Suggested labels: ~"T::bug" ~renamer ~StaticPointers Suggested milestone: %9.14.2 (the warning ships there). The error side lives on master (4df0adf631) — arguably also/instead %10.0.1; mention on the 9.14.2 status thread either way. Related: #26718 (the warning's tracking ticket — maybe file as a comment there instead of a new ticket?), #26556 (proposal 732 umbrella), !15292 (source MR, still open), !16163 (backport MR that landed it on ghc-9.14) Commits: branch 1ee3466bf0db (cherry-pick of 6b7d6287c6ff from wip/T26178 via !15292 — NOT on master); master has the full 9.16 change 4df0adf631 where the same defect is a hard error. Reproducer: tickets/f2/ (run.sh; verified 2026-08-07, x86_64-linux): - ghc-9.14.1 (ghcup): silent success - 9.14.1.20260728 bindist = branch commit eddff3ab50 (includes 1ee3466bf): warning GHC-82529 naming tyvar 'a', exit 0 - master build 10.1.20260710 (d415f38a75, includes 4df0adf631): error GHC-88431, exit 1 f1 dropped (was: "warning also fires for lambda-bound vars, breaking RnStaticPointersFail01/03"): refuted empirically. TcRn warnings are suppressed when the module has errors (checked with ghc-9.14.1: an -Wx-partial warning disappears when the module also has a type error), and every not-let-bound offender also triggers the hard error GHC-88431, so the contradictory warning never reaches the user: the snapshot compiler shows only the old error for `f x = static x`, no warning. Branch CI agrees: pipeline 129003 on 39bc70bd67 ran the full testsuite (x86_64-windows job: 10892 tests, 0 unexpected failures; i386 job failed only T27131), so RnStaticPointersFail01/03 pass. The bad_fvs over-approximation for lambda-bound vars exists in the source but has no observable effect on the branch; the suggested fix below removes it anyway. ═══════════════════════════════════════════════════════════════════ --> *This ticket reports a possible bug found by an LLM-based code review (details under "Provenance" below). I, @sjakobi, have checked it for plausibility, but not verified it in depth. @simonpj subsequently rewrote it. ## Summary Following [GHC proposal 732: simplify static forms](https://github.com/ghc-proposals/ghc-proposals/blob/master/proposals/0732-simplify-static.rst) GHC is supposed to check all the free **term variables** of a static form are top-level bound. But the proposal explicitly allows free **type variables** (see Section 5.2). The proposal was implemented in !14994. But alas the implemention now rejects free type variables. Repro case below. Also: * Less importantly, this also affects the deprecation warning in the GHC 9.14 branch, which was added in !15292 * There are bogus references to `checkClosedInStaticForm` in the code; they should be removed. ## Reproducer ```haskell {-# LANGUAGE StaticPointers, ScopedTypeVariables #-} module Repro where import Data.Typeable import GHC.StaticPtr f :: forall a. Typeable a => StaticPtr (a -> a) f = static (id :: a -> a) ``` This is `TcStaticPointers02.f2` with an inline signature. Observed behaviour (x86_64-linux): * **GHC 9.14.1**: compiles silently. * **ghc-9.14 branch** (9.14.1.20260728 bindist, commit eddff3ab50, containing 1ee3466bf0db): compiles, but warns — ``` Repro.hs:8:5: warning: [GHC-82529] From GHC 9.16, static forms cannot mention nested let-bound variables Offending variables: a Solution: move these free variables to top level ``` `a` is not a let-bound variable and cannot be moved to top level; the warning has no flag, so `-Werror` users cannot get a clean build without changing (correct) code, e.g. dropping the inline annotation. * **master** (10.1.20260710 build, containing 4df0adf631 "Simplify the treatment of static forms", where the check is the real 9.16 error): the program is rejected — ``` Repro.hs:8:5: error: [GHC-88431] ‘a’ is used in a static form but it is not defined at top level ``` Proposal 732 restricts the free *term* variables of a static form; a type variable in an annotation should not make it ill-formed (without the annotation the same definition is accepted on master). ## Cure Because of required type arguments, we can't tell type variables from term variables in the renamer. So probably: * The renamer should put the free varaibles in the extension field of `HsStatic` * The typechecker should check that there are no term variables among them. ## Provenance Originally reported by [GlaHiCo](https://gitlab.haskell.org/sjakobi/GlaHiCo), an LLM-based code-review pipeline, while reviewing the 9.14.2-rc1 backports. The published review of 1ee3466bf0db (cherry-pick of master 6b7d6287c6ff from !15292, landed via !16163) is at https://gitlab.haskell.org/sjakobi/GlaHiCo/-/snippets/6148 (finding f2). The first draft of this ticket was also written by an LLM agent. **Subsequently edited by @simonpj to kill off bad suggestions (e.g. using the OccName to tell type variables)
issue