Skip to content

[rustjava-string-on-the-error-path-p0] fix(jvm): 오류 경로가 필요로 하는 것은 «목록»이 아니라 «폐포»다 - #86

Merged
Jun025 merged 1 commit into
mainfrom
rustjava-string-on-the-error-path-p0
Sep 20, 2026
Merged

Jun025 merged 1 commit into
mainfrom
rustjava-string-on-the-error-path-p0

Conversation

@Jun025

@Jun025 Jun025 commented Sep 20, 2026

Copy link
Copy Markdown
Owner

채택 제안 2026-09-19-string-on-the-error-path#p0 (docs/worklog/2026-09-19-string-on-the-error-path.json).

제안이 물은 것, 그리고 답

제안 why 축자 — 「each found the next by reading the code and guessing … A sweep that hides each bootstrap-reachable name in turn and records which ones recurse would answer the whole question once.」
제안 tradeoff 축자 — 「If it turns out the answer is still just these two, the result is a recorded negative rather than a new check.」

★★**「still just these two」가 «아니다» — 그 가정이 반증됐다.**

후보를 손으로 적지 않고 유도했다(기록 로더로 정상 구성 1회): 요청 51 · 서로 다른 이름 42 · 배열 5 제외 ⇒ 37. 그 37개를 하나씩 숨겨 재구성했다.

분류 고침 전 고침 후
★재귀(바닥 없음) 5 ★0
이름을 들어 거절 7 12
한 번 묻고 깨끗이 실패 25 25
없어도 구성됨 0 0

재귀한 5개 = java/lang/Throwable · Error · LinkageError · CharSequence · Comparable.
★우연이 아니다 — 기존 두 이름의 상위형·인터페이스 폐포다. 클래스를 resolve 하면 상위형도 resolve 되고, ★거기서 난 결손은 «아직 resolve 중인 바로 그 두 클래스»로 보고된다.

처방 — 목록이 아니라 폐포

손으로 적은 assert! 둘 → 작업목록 루프 하나(씨앗 2개 · interface_names()·super_class_name() 을 밀어 넣는다). ★로더에 «직접» 묻는다 — resolve_class 는 질문을 Jvm::exception 에 넘기고 그것이 곧 순환이다.
★폐포 9개로 계산이 닫힌다: 이미 막힌 2 + 재귀 5 + bootstrap_classes 가 먼저 잡는 2(Object·Serializable) ⇒ 설명 안 되는 이름 0.

양방향 — 제품 호출부(사본 아님)

개악 결과
정상 없음 37 candidate(s): 0 recursed · 12 refused by name · 25 failed cleanly · 0 not needed · ok
개악 jvm/src/jvm.rs 의 pending.extend(...) 두 줄 제거(= 두 이름만 보던 고침 전 동작) ★**5 recursed · FAILED**
복원 되돌림 0 recursed · ok

★기존 잠금 jvm/tests/test_exception_fallback_recursion.rs 2건은 손대지 않고 통과한다 — 새 문안이 has no java/lang/String · has no java/lang/NoClassDefFoundError 를 그대로 담는다.

대가 — 숨기지 않는다

  • ★시작 비용 = 로더 질문 44 → 51(폐포 9회 ↔ 종전 2회). ★벽시계는 재지 않았다 — 전 회차가 같은 자리에서 재고 「이 호스트의 노이즈 아래」로 버렸다. 결정론적 수로만 말한다.
  • cargo test --all 에 스윕 ~15초(실측 13.98 / 15.92 / 29.26 · 부하에 따라 흔들린다). 일반화의 값이고 깎지 않았다.
  • ★배열 이름 5개 제외 — 근거는 의견이 아니라 측정: 부트스트랩 로더가 배열을 합성한다(define_array_class) ⇒ 어떤 클래스 집합도 배열을 빠뜨릴 수 없다. 그래도 쟀다 — [C 재귀(상한 20에 21질문) · ★[Ljava/lang/String; 는 그 상한에서도 스택 오버플로(순환이 로더로 돌아오지 않아 상한이 못 끝낸다) ⇒ in-process 로 못 도는 유일한 후보. 후속 #p1.
  • ★부트스트랩 6개를 숨기면 called Option::unwrap() on a None value — 구성 시점에 멈추니 옳지만 이름을 말하지 않는다(12건 중 5건). 별 계급이라 후속 #p0.

검증

  • DoD 9명령 전건 rc 0 (fmt · clippy · +beta clippy · wasm32 clippy · cargo test --all 487+ 전건 green · 파이썬 4종).
  • dod_parity: 「OK 두 축 모두 대칭차 0 — 명령 8개 · toolchain 2개로 «둘 다 일치»」.
  • git diff origin/main --summary: old mode/new mode 0.

🤖 Generated with Claude Code

…»이 아니라 «폐포»다

채택 제안 `2026-09-19-string-on-the-error-path#p0`.

제안의 가정 「still just these two」는 반증됐다. 후보를 손으로 적지 않고
기록 로더로 «유도»한 뒤(요청 51 · 서로 다른 이름 42 · 배열 5 제외 = 37)
하나씩 숨겨 재구성하니 5개가 더 재귀한다(바닥 없음):
java/lang/Throwable · Error · LinkageError · CharSequence · Comparable.

우연이 아니다 — 기존 두 이름의 상위형·인터페이스 폐포다. 클래스를 resolve 하면
상위형도 resolve 되고, 거기서 난 결손은 «아직 resolve 중인 그 두 클래스»로 보고된다.

그래서 손으로 적은 assert 둘을 작업목록 루프 하나로 바꿨다. 로더에 직접 묻는다 —
resolve_class 는 질문을 Jvm::exception 에 넘기고 그것이 곧 순환이다.
폐포 9개로 계산이 닫힌다: 이미 막힌 2 + 재귀 5 + bootstrap_classes 가 먼저 잡는 2.

양방향(제품 호출부): 0 recursed · ok ↔ pending.extend 두 줄 제거 → 5 recursed · FAILED
↔ 복원 ok. 기존 잠금 2건은 무수정 통과한다(문안이 `has no <name>` 을 그대로 담는다).

대가: 시작 비용 로더 질문 44 → 51 · cargo test --all 에 스윕 ~15초 ·
배열 5개는 제외(로더가 합성하므로 클래스 집합이 못 빠뜨린다 — 단 [Ljava/lang/String; 는
상한 20에서도 오버플로라 in-process 로 못 돈다) · 부트스트랩 6개는 이름 없는
unwrap 패닉으로 죽는다(후속 제안 #p0).

DoD 9명령 rc 0.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@Jun025
Jun025 merged commit 2b2a5b1 into main Sep 20, 2026
12 checks passed
@Jun025
Jun025 deleted the rustjava-string-on-the-error-path-p0 branch September 20, 2026 06:48
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant