Skip to content

handoff: P4 fallback=0 セッション (2026-06-27) — #32 codegen根治継続 (3.0.7/3.0.8/3.0.9 release) / 残り C=var宣言・型推論 #44

Description

@opaopa6969

このセッションの成果(全て landing / Central 公開済み)

#40 を継承。P4 fallback=0(#32)に向け、生成マッパーの AST 経路忠実度を root から潰すサイクルを継続。unlaxer-dsl を 3.0.7 → 3.0.8 → 3.0.9 と3回リリースし、tinyexpression を各々追従。

リリース済み(unlaxer-parser、Central公開 + master マージ)

tinyexpression(master マージ済み、master @ 733293f、unlaxer-dsl 3.0.9)

計測(if-source shadow OFF の純 AST 経路、-Dp4.disableIfSourceShadow=true 一時トグルで evalIfExpr を計測 → 計測後 revert)

🎯 残り = C のみ(最後の if-off 失敗): var 宣言 / 型推論(testTypeInference)

これは codegen バグでなく「機能」。testTypeInference block 1:

var $name as string set if not exists 'opa' description='名前だよ!';
if($name == $remitterAccountHolderKana){1}else{0}

(ctx: $name 未設定, $remitter='opai'。期待 0)

根本原因(精査済み)

var 宣言は @mapping 無し@declares のみ)。P4 mapper の findBestMappedToken は Expression だけを残し宣言を捨てる。よって純 AST 経路では宣言が提供する2つが欠落:

  1. $name='opa'(set if not exists)
  2. as string$name == $remitter文字列比較にすべき情報

型情報が無く $name == $remitter は構造的に数値寄り比較にマップされ、'opa'/'opai' を数値比較 → 誤って等価 → 1(期待 0)。

必要な作業(専用の機能開発。恐らく 3.0.10)

  • VariableDeclaration ルール群を AST にマップ(codegen)or 宣言トークンを別経路で抽出
  • context へ set-if-not-exists を適用
  • 宣言型を比較オペランドの型解決に通す(StringComparison vs 数値 ComparisonExpr の選択)
  • 文法: tools/tinyexpression-p4-lsp-vscode/grammar/tinyexpression-p4.ubnfVariableDeclaration / *VariableDeclaration(41-93行)。legacy 側の実装は evaluator/javacode/VariableTypeResolver.java, TinyExpressionTokens.java, parser.javalang.VariableDeclarationParser が参考。

#32 fallback=0 のもう一つのゲート: パース性能(#38/#20

if-shadow を実際に外すには、巨大ネスト if 式(不正検知 fraud formula)のパースが遅すぎる問題も要解決。P4AstEvaluatorCalculatorTest は if-ON でも ~1263s(パース時間が支配的、eval ではない)。unlaxer-parser のメモ化(packrat, unlaxer-parser#40)導入待ち。

ビルド/検証コマンド

  • tinyexpression フル: mvn -o verify -Dmaven.test.failure.ignore=true -Dtinyexpression.skipRailroad=true -Dgpg.skip=true -Dmaven.javadoc.skip=true -Dspotbugs.skip=true -Derrorprone.skip=true
  • 緑判定ゲート: bash tools/ci/check-test-baseline.shmvn test 自体は既知失敗で BUILD FAILURE。test-baseline.txt の唯一の既知失敗=perf: 生成パーサの指数バックトラック — 二重カッコ三項/ソース再パース経路で秒〜分単位の遅延 #38
  • 再生成: rm -rf target/generated-sources target/classes
  • unlaxer-dsl をローカル検証: revision を 3.0.10-SNAPSHOT 等にして cd unlaxer-parser && mvn -o -q install -pl .,unlaxer-common,unlaxer-dsl -DskipTests -Dgpg.skip=true ...公開済み revision を汚さない)。tinyexpression の pom も同 SNAPSHOT に。
  • unlaxer-dsl 内部フルビルド検証(ubnf/tinycalc 生成+compile): mvn -o -q test-compile -pl unlaxer-dsl/ubnf-vscode,unlaxer-dsl/tinycalc-vscode ...、dsl テスト: mvn -o test -pl unlaxer-dsl ...golden 変更時は更新)。
  • golden 再生成: mvn -o -q exec:java -pl unlaxer-dsl -Dexec.mainClass=org.unlaxer.dsl.codegen.SnapshotFixtureWriter -Dexec.args="--output-dir <dir>" -Dexec.classpathScope=test(temp に出力→diff 確認→src/test/resources/golden/ へ copy)。
  • if-off 計測: evalIfExpr 先頭を if (!Boolean.getBoolean("p4.disableIfSourceShadow")) { ...既存... } で包む → mvn -o test -Dtest='P4AstEvaluatorCalculatorTest#testTypeInference' -Dp4.disableIfSourceShadow=true ...計測後 git checkout -- で revert
  • Central デプロイ: cd unlaxer-parser && mvn -B -pl .,unlaxer-common,unlaxer-dsl clean deploy(autoPublish、GPG loopback 設定済み)。不可逆な公開操作は権限ゲートあり=実行前にユーザー確認。CHANGELOG 起票必須。

codegen 実装メモ(今回の重要箇所)

  • unlaxer-dsl/.../codegen/MapperRuleEmitter.java: findCapturedToken(直接子優先・bounded fallback)、findDescendantsBoundedemitPlainMappingBody/emitPlainMappingResolution(多ルール dispatch)、emitUtilities(parsersClass, mappedRuleNames)
  • MapperElementUtil.java: parserClassLiteral の identifier トークンは FQN 条件分岐(FQN→<Parsers>.<Token>Parser ラッパー、短縮名→base org.unlaxer.parser.clang.IdentifierParser)。短縮名トークン(CompileVerificationTest の TINYCALC_GRAMMAR token IDENTIFIER = IdentifierParser)はラッパー非生成なので base 必須。
  • MapperTypeResolver.isTransparentMappedChoice(≥2 異種 @mapping)、ASTGenerator/MapperTypeResolverinferTypeFromElement が透過 choice を Object 推論。

運用メモ(ユーザー方針)

  • 速度優先: ローカル緑なら admin-merge 可。Central→repo1 同期ラグで downstream PR の CI が一時赤になるのは許容(同期後 gh run rerun)。
  • 不可逆な公開操作(Central deploy)・issueコメント投稿は権限ゲートあり。
  • .flattened-pom.xml / package-lock.json はビルド生成物。コミット前に git checkout -- で戻す。scratch ログも掃除。

関連 issue / memory

#32(fallback=0計画), #35(workaround真っ当化/load-bearing shadow), #22(機能ギャップ/dotメソッドリテラル受け手), #38(perf:指数バックトラック), unlaxer-parser #40(packrat)/#41/#42。前 handoff #40
memory: p4-issue32-stringconcat-blocker, p4-issue35-cycle-landscape(C のスコープ・3.0.7/3.0.8/3.0.9 成果・gotcha を記録), tinyexpression-ci-baseline-gate, workflow-speed-over-green-ci, p4-fallback-zero-project

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions