Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions compiler/tests/language_gaps.rs
Original file line number Diff line number Diff line change
Expand Up @@ -231,6 +231,12 @@ fn data_shapes_that_do_not_exist_yet() {
"host fn import",
"import fn host_log(x: i32)\nexport fn f(a: i32) -> i32 { return a }",
);
// SPEC-constants §0.3/§5 left `enum` (a new type, an ABI mapping, an exhaustiveness check)
// for later; until 2026-09-27 that was written only in the closed SPEC and §9-68.
rejected(
"enum declaration",
"enum S { A }\nexport fn f(a: i32) -> i32 { return a }",
);
// Four gaps the 2026-09-26 §7 sweep met in several domains, missing from the block that
// claims to hold every gap.
rejected("i64 type", "export fn f(x: i64) -> i64 { return x }");
Expand Down Expand Up @@ -274,6 +280,7 @@ const GAPS: &[(&str, &str)] = &[
("일반 `f64` 포맷", "f64 as string"),
("지역 변수", "string local"),
("struct", "struct declaration"),
("`enum`", "enum declaration"),
("option", "option type"),
("for", "for"),
("else", "else"),
Expand Down
1 change: 1 addition & 0 deletions docs/HISTORY.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@

---

### 9-74. 인계 정리 (2026-09-27, E2) — **측정 키트를 저장소 밖으로 옮겨 다시 쟀고, 닫힌 기록에만 있던 잔여를 살아 있는 문서로 옮겼다** → [본문](history/9-74.md)
### 9-73. 넓은 중간값 슬라이스 (2026-09-27, E2) — **`!` 문맥의 순수 산술 식은 정확히 계산되고, 뿌리에서 한 번 좁혀진다** → [본문](history/9-73.md)
### 9-72. 헬퍼 체크 전파 슬라이스 (2026-09-26, E2) — **`!`를 위해 실행되는 산술은 어디에 쓰여 있든 검사된다** → [본문](history/9-72.md)
### 9-71. 체크드 산술 다음을 쟀다 (2026-09-26, E2) — **헬퍼 체크 전파가 조용한 오답을 가장 많이 줄인다** → [본문](history/9-71.md)
Expand Down
4 changes: 4 additions & 0 deletions docs/HOST_ABI.md
Original file line number Diff line number Diff line change
Expand Up @@ -517,6 +517,10 @@ GetProcAddress 심볼 3개 전부 성공 -> 전부 성공
- 사용자 모듈이 export하는 함수: 별도 접두어(예: `mlx_`) 또는 모듈명 네임스페이스. `ml_`와 충돌 금지(D18).
- 모듈이 내보내는 이름 붙은 정수: 에러 코드는 `ML_<MODULE>_ERR_<NAME>`(Q14), `export const`는
`ML_<MODULE>_CONST_<NAME>`(SPEC-constants DP-K3). 둘 다 **값이지 심볼이 아니고** 지문에 든다.
**모듈 사이의 C 매크로 이름은 겹칠 수 있다** — 모듈 `a`의 상수 `ERR_Q`와 모듈 `a_const`의 에러 `Q`가 둘 다
`ML_A_CONST_ERR_Q`다(에러끼리도 `a`/`ERR_X` ↔ `a_err`/`X`). 막는 가드가 없어, 값이 다른 두 헤더를 한 번역 단위에
include하면 `C4005` 경고가 나고 참조 호스트처럼 `/WX`로 빌드하면 실패한다. Pascal 상수는 유닛 스코프라 겹치지 않는다
(SPEC-constants §5).

## 하지 말 것 (MVP)

Expand Down
4 changes: 3 additions & 1 deletion docs/LANGUAGE.md
Original file line number Diff line number Diff line change
Expand Up @@ -313,7 +313,9 @@
수 있으므로 **그 함수는 `!`가 된다** — 배열 인덱싱과 같은 규칙이다
(`slices/SPEC-string-slice-compare.md` DP-C2·DP-C5)
- struct/record, null 안전 또는 option
- `for`, `else`, `break`/`continue`, 복합 대입, 비트 연산자
- **`enum`·타입 있는 상수 집합** — 오늘은 이름 붙은 i32 리터럴(`const`·`export const`)뿐이다. 새 타입 · ABI 매핑 ·
완전성 검사를 여는 일이라 `slices/SPEC-constants.md` §0.3·§5가 남겼다
- `for`, `else`, `break`/`continue`, 비트 연산자
- **호스트 함수 import**(현재는 모듈 export 단방향), 재귀
- 다른 정수 폭 **`i64`**, **수학 내장 함수**(`pow`·`exp`·`ln`·`sqrt`·`abs`), **`min`/`max`**,
**지역 배열·배열 리터럴**(작업 배열) — 넷 다 우회는 된다(곱셈 루프 · 두 줄 내부 `fn` · 파라미터로
Expand Down
2 changes: 1 addition & 1 deletion docs/OPEN_QUESTIONS.md
Original file line number Diff line number Diff line change
Expand Up @@ -185,5 +185,5 @@ ABI 정수 상태코드+out-param, 표면 Result는 sugar. 남은 하위 → Q13

## Claude에게

Q1~Q5는 닫혔다. 남은 결정(**Q6~Q11** — **Q12·Q13·Q14·Q15는 닫혔다**)도 제안 시 장단점 표를 쓰고, 문서를 고치기 전에 사용자 확인을 받는다.
Q1~Q5는 닫혔다. 남은 결정(위 **미뤄도 되는 것** 절의 질문 전부 — **Q12·Q13·Q14·Q15는 닫혔다**)도 제안 시 장단점 표를 쓰고, 문서를 고치기 전에 사용자 확인을 받는다.
확인 없이 DECISIONS.md를 바꾸지 않는다.
43 changes: 29 additions & 14 deletions docs/STATUS.md
Original file line number Diff line number Diff line change
Expand Up @@ -102,16 +102,30 @@
푸는 것은 가산적 변경이며 SPEC 갱신이 따라야 한다. (SPEC-calls §5.1)
4. **생성 모듈의 패닉은 프로세스를 죽이지 않고 호출한 스레드를 무한히 돌린다.** ↓ §5-4

5·6은 갚았다(등록부). 아래 넷은 2026-09-27에 닫힌 기록·SPEC §5에서 옮겨 왔다 — 거기에만 있던 것이다(§9-74).

7. **`runtime/ml_abi.h`는 `-1`만 정의한다.** `-2`(`ML_ST_INDEX_OUT_OF_RANGE`, #200부터)·`-3`(`ML_ST_OVERFLOW`)은
생성 헤더에만 `#ifndef`로 있고, 그 파일의 *"the codes below are the whole allocation"* 은 낡았다. `hygiene.rs`의
대조도 `-1`만 본다. 고치는 PR: 헤더에 둘을 더하고 대조를 `mlc::abi`의 세 코드로 넓힌다(SPEC-checked-arithmetic §5).
8. **주변 `RUSTFLAGS=-D warnings`에서 기존 경고가 있는 모듈은 `mlc build`가 깨진다** — snake_case가 아닌 사용자 함수
이름(`fn a__b` → `non_snake_case`)과 아무도 부르지 않는 내부 함수(`dead_code`)는 측정됐고, 쓰지 않는 문자열 헬퍼도
같은 부류다. `allow`를 더하면 모든 모듈의 생성 Rust가 바뀌어 골든과 부딪히므로 따로 정한다(SPEC-helper-check-propagation §5).
9. **`!` 문맥 검사의 실행 속도는 잰 적이 없다** — 체크드 산술 · 헬퍼 체크 전파 · 넓은 중간값이 분기 · `Result` 반환 ·
i64 연산을 더했지만 잰 것은 `.text` 크기뿐이다(§9-70.4 · §9-71.4 · §9-73.3). 빠르다/느리다를 쓰기 전에 잰다.
10. **문서 가드의 알려 둔 사각 넷** — `live_documents_do_not_accumulate_correction_notes`는 날짜 없는 서술을 세지 못하고
`" 감사"` 뒤에 경계가 없다 · `protection.rs`의 "정확히 N개"는 부분 문자열 검사다 · 함수 본문 안의 긴 `//` 주석은
`every_guard_docstring_is_short` 밖이다(§9-66.7).

### 5-4. 생성 모듈의 패닉은 프로세스를 죽이지 않는다 — 스레드를 무한히 돈다

여러 문서가 `i32 /0`을 두고 "`no_std`+`panic=abort`니까 **호스트를 죽인다**"라고 적어 왔다.
**코드를 읽어 보니 틀렸다.** 생성 크레이트가 실제로 담는 것은:

| 무엇 | 어디 | 값 |
|---|---|---|
| no_std | `compiler/src/codegen.rs:39` | `#![no_std]` |
| 패닉 핸들러 | `compiler/src/codegen.rs:58` | `#[panic_handler] fn ml_panic(_: &core::panic::PanicInfo) -> ! { loop {} }` |
| 패닉 전략 | 생성 `Cargo.toml`(`codegen.rs:286`) | `[profile.release] panic = "abort"` |
| no_std | `compiler/src/codegen.rs`(생성 크레이트 머리) | `#![no_std]` |
| 패닉 핸들러 | `compiler/src/codegen.rs`(`ml_panic`) | `#[panic_handler] fn ml_panic(_: &core::panic::PanicInfo) -> ! { loop {} }` |
| 패닉 전략 | 생성 `Cargo.toml`(`codegen.rs`의 `CARGO_TOML_PROFILE`) | `[profile.release] panic = "abort"` |

`no_std`에서는 **`#[panic_handler]`가 곧 패닉 런타임**이다. `panic = "abort"`는 언와인딩 테이블을
없앨 뿐, `abort()`를 부르는 것이 아니다. 그래서 패닉은 `ml_panic`으로 들어가 **`loop {}`에 갇힌다** —
Expand Down Expand Up @@ -227,25 +241,26 @@

> ## ▶ 여기서 시작한다
>
> ### 2026-09-27 기준 — **넓은 중간값 슬라이스가 닫혔다: `!` 문맥의 순수 산술 식은 정확히 계산된다 (§9-73)**
> ### 2026-09-27 기준 (2) — **인계 정리: 측정 키트를 저장소 밖으로 옮겼고, 닫힌 기록에만 있던 잔여를 살아 있는 문서로 옮겼다 (§9-74)**
>
> SPEC을 권고안대로 확인받아 슬라이스로 닫았다(#341 SPEC · #342 구현). `!` 문맥의 순수 산술 식은 i64로 계산해 값이
> i32가 되어야 하는 자리에서 한 번 좁힌다. 참값이 드는데 `-3`인 행 59 → 20(626행, 시험 구현과 행마다 같다). 실제 C 호스트가
> 바꾼 `one_payment`로 곱이 i32 밖인 입력의 정답을 받는다. 지문·ABI·바인딩은 그대로다.
> 로컬 브랜치는 `main`만 남았다(실험 브랜치 둘은 번들로 백업). §9-69의 626행 코퍼스와 재측정 스크립트가 세션 임시 폴더에만
> 있어 저장소 밖으로 옮겼고, 옮긴 자리에서 다시 재 같은 표(543 · 44 · 20 · 18)를 얻었다. 닫힌 기록과 SPEC §5에만 있던 잔여는
> §5-7~§5-10 · `HOST_ABI.md` 네이밍 규약 · `LANGUAGE.md` 공백 블록 · `slices/README.md` 후보 목록으로 옮겼다.
>
> **▶ 다음 세션 — 여기서 시작한다.** 순서대로:
>
> 1. **강제되는 슬라이스가 없다 — 다음은 측정이다.** 참값이 드는데 `-3`으로 남은 20행 중 17행(FULL로도 남는 행)이
> 무엇인지 귀속하지 않았다(§9-73.7). 귀속이 `i64` 타입이나 다른 후보(`docs/slices/README.md`의 "다음 슬라이스" 절)를
> 가리키면 그때 SPEC을 쓴다.
> 2. **작은 항목**: C# 호스트(Phase 4) · LSP(Phase 3, 큰 일).
> 3. **외부**: `X1`·`X2` — Delphi가 있는 CI 러너. 이 저장소 안에서는 닫히지 않는다.
> 1. **참값이 드는데 `-3`인 20행 중 17행을 귀속한다 — 측정.** 키트는 저장소 밖 `D:\Source\Mathless-lab\kit-626\`(이 머신
> 전용)이고 재현 절차 · 함정은 그 README에, 20행 목록은 `loud_fits_20_at_b077cb9.txt`에 있다(3행은 배열 읽기).
> 귀속이 `i64` 타입이나 다른 후보를 가리키면 그때 SPEC을 쓴다.
> 2. **작은 부채 — 한 PR씩**: §5-7(`ml_abi.h`에 `-2`·`-3`, 대조를 세 코드로) · §5-8(`-D warnings` — 방향은 사용자 결정).
> 3. **작은 항목**: C# 호스트(Phase 4) · LSP(Phase 3, 큰 일).
> 4. **외부**: `X1`·`X2` — Delphi가 있는 CI 러너. 이 저장소 안에서는 닫히지 않는다.
>
> ⚠ **이 머신의 전체 게이트는 6회 중 2회 실패한다**(§9-63.5) — 실패를 보면 먼저 원인을 읽는다.
> 강한 신호는 CI 두 잡이다.
>
> 📌 **본문은 §9-73이다**(`docs/history/9-73.md`). 그 앞의 2026-09-26 (6) 항목(헬퍼 체크 전파 닫힘)은
> 바이트 그대로 옮겼다 — 지금은 `docs/history/start-block-054.md`다.
> 📌 **본문은 §9-74다**(`docs/history/9-74.md`). 그 앞의 2026-09-27 항목(넓은 중간값 닫힘)은
> 바이트 그대로 옮겼다 — 지금은 `docs/history/start-block-055.md`다.
>
>
> ### 그 앞의 항목들 — **본문은 `docs/history/start-block-NNN.md`로 옮긴다 (2026-09-23부터)**
Expand Down
66 changes: 66 additions & 0 deletions docs/history/9-74.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
### 9-74. 인계 정리 (2026-09-27, E2) — **측정 키트를 저장소 밖으로 옮겨 다시 쟀고, 닫힌 기록에만 있던 잔여를 살아 있는 문서로 옮겼다**

사용자 요청: *"로컬 브랜치 정리해주시고 후속및 잔여작업은 다음세션에서 할수 있게 정리"*. 워크플로 하나(에이전트 13)로
살아 있는 문서의 열린 항목(53)과 닫힌 기록 9-66~9-73 · 최근 SPEC 넷의 §5가 남긴 잔여(67)를 뽑아 대조하고, 측정 키트의
의존성을 추적한 뒤, 발견마다 반박 검증을 붙였다(9건 전부 성립 — 문구 · 번호 · 자리를 여럿 고쳐서).

#### 9-74.1. 로컬 정리

- 실험 브랜치 `exp/wide-local`(`3ed8778`) · `exp/wide2-local`(`9f67477`)을 전체 이력 번들로 떠서 **복원 시험**(클론한 머리의
SHA가 지우기 전과 같다) 뒤에 지웠다. 앞서 지운 `exp/checked-arith-local`의 번들(§9-71.1)도 같은 곳으로 옮겼다 —
세션 임시 폴더에 있었다. §9-73.6이 적은 *"남아 있다"* 는 이 줄로 끝난다.
- 원격 추적 참조 30개를 걷어냈다(`git fetch --prune` — 원격에는 `main`뿐이었다). 로컬 브랜치는 `main`뿐이고 worktree도
하나다.

#### 9-74.2. 측정 키트 — 세션 임시 폴더에만 있었다

§9-69의 626행 코퍼스와 재측정 · 집계 스크립트, 지금까지의 결과 JSON이 **이 세션의 임시 폴더(scratchpad)에만** 있었다.
STATUS ▶의 다음 할 일(17행 귀속)이 그것에 기대는데 새 세션은 그 폴더를 모른다.

- 저장소 밖 `D:\Source\Mathless-lab\`로 옮겼다(실험 코드 · 측정 데이터는 제품 코드와 섞지 않는다): `kit-626/`으로 옮긴 것이
1,181파일 7.0MB, 실행 파일 0개이고, 그 뒤 README · `tally.py` · 20행 목록 · 재측정 결과를 더했다. 번들 셋은 `bundles/`. 두 README가 무엇이 어디 있고 어떻게 다시 재는지 적는다.
- **옮긴 자리에서 다시 쟀다**: `main` c70e02d로 빌드한 `mlprobe`로 626행 — 맞음 543 · 조용한 오답 44 · 참값이 드는데 `-3`
20 · 기타 18, 판정 불명 0, b077cb9 기준선(§9-73.3)과 **출력이 다른 행 0**. 기존 집계 스크립트 둘도 옮긴 자리에서 같은
표를 냈다.
- 에이전트가 짚은 함정을 README에 옮겼다: `RM_OUT`의 기본값이 기준 데이터를 덮어쓴다 · 집계는 변형 목록이 코드에 박혀
있다(그래서 목록 없는 `tally.py`를 더했다) · 실험 빌드의 출력 JSON은 다시 만들 수 없다(`main`은 실험 스위치를 읽지 않는다).
- 다음 측정의 입력으로 20행 목록을 떠 두었다. 그중 3행(stateful R4-oob1~3)이 FULL과 다른 행이다 — §9-73.7의 *"3행은
배열 읽기"* 가 행 이름으로 확인됐다.

#### 9-74.3. 닫힌 기록에만 있던 잔여 — 살아 있는 자리로

| 잔여 | 출처 | 옮긴 자리 |
|---|---|---|
| `runtime/ml_abi.h`가 `-1`만 정의한다(`-2`는 #200부터, `-3`은 생성 헤더에만) | SPEC-checked-arithmetic §5 | STATUS §5-7 |
| 주변 `RUSTFLAGS=-D warnings`에서 기존 경고가 있는 모듈의 빌드가 깨진다 | §9-72.7 · SPEC-helper-check-propagation §5 | STATUS §5-8 |
| `!` 문맥 검사의 실행 속도는 잰 적이 없다 | 세 SPEC §5 | STATUS §5-9 |
| 문서 가드의 알려 둔 사각 넷 | §9-66.7 | STATUS §5-10 |
| 모듈 사이 C 매크로 이름이 겹칠 수 있다(`ML_A_CONST_ERR_Q`) | §9-68 · SPEC-constants §5 | `HOST_ABI.md` 네이밍 규약 |
| `enum`·타입 있는 상수 집합 | §9-68 · SPEC-constants §0.3·§5 | `LANGUAGE.md` 공백 블록 + `language_gaps.rs` + 후보 목록 |
| 상수식 오버플로 진단 | SPEC-checked-arithmetic DP-O9·§5 | `slices/README.md` 후보 목록 |

- 검증이 고친 것: `-D warnings`의 머리말이 너무 넓었다(경고 없는 모듈은 빌드된다 — 검증 에이전트가 쟀고, 쓰지 않는 내부
함수의 `dead_code`도 그때 측정됐다) · `C4005`는 경고이고 실패는 `/WX` 때문이다 · 속도 항목의 출처 하나(§9-69.6)는 다른
이야기였다 · STATUS §5의 다음 빈 번호는 7이다 · 가드 사각을 적는 문장에 그 가드가 세는 낱말을 쓰면 가드가 빨개진다.
- `enum` 행은 테스트부터 썼다: `GAPS`에 행을 더하자 첫 빨강이 *"블록이 '`enum`'을 적지 않는다"* 였고(메시지를 읽었다),
공백 블록에 항목을 더해 초록.

#### 9-74.4. 제자리에서 고친 낡은 문장

- `docs/phase1/WBS.md` 머리말의 *"Delphi만 미검증"*(같은 파일 아래가 로컬 게이트로 닫혔다고 적는다) · 같은 파일의
*"고정 workdir명 유지"*(#19가 갚았고 같은 파일의 표가 그렇게 적는다 — 형제 항목처럼 취소선 + 처리됨).
- `OPEN_QUESTIONS.md`의 "Claude에게"가 남은 결정을 Q6~Q11로 적어 Q16 · Q17이 빠졌다 — 번호 대신 그 절을 가리키게 했다.
- `LANGUAGE.md` 공백 블록이 복합 대입을 두 번 적었다 — 한 번으로.
- STATUS §5-4의 줄 번호 포인터 셋이 밀려 있었다(`codegen.rs:39` → 지금 140 등) — 가드가 없는 줄 번호 대신 심볼 이름으로.
- `docs/phase1/SPEC.md`도 *"Delphi 미검증"* 을 여섯 곳에 적지만 **설계 기록**이라(머리말) 고치지 않았다.

#### 9-74.5. 잔여가 아니었던 것 (대조가 걸러 낸 것)

지역 변수 폭(SPEC-wide-intermediates §2.6이 i32로 정했다) · C 백엔드의 실제 구현(Q6 · D19 · `LANGUAGE.md`의 요구) ·
비ASCII 비교(Q17의 재검토 조건) · `export const`의 f64 · bool · string과 상수 식(`LANGUAGE.md`가 제약으로 적는다) · 무한
함수를 호스트가 직접 부를 때의 오버플로(D17 — 채널이 없는 설계) · §9-69.6의 *"표본이 덮지 않은 것"*(표본의 경계이지 할
일이 아니다).

#### 9-74.6. 남은 것

STATUS ▶이 정본이다: 17행 귀속(키트 위치 포함) · §5-7과 §5-8 · C# 호스트 · LSP · X1 · X2.
20 changes: 20 additions & 0 deletions docs/history/start-block-055.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
> ### 2026-09-27 기준 — **넓은 중간값 슬라이스가 닫혔다: `!` 문맥의 순수 산술 식은 정확히 계산된다 (§9-73)**
>
> SPEC을 권고안대로 확인받아 슬라이스로 닫았다(#341 SPEC · #342 구현). `!` 문맥의 순수 산술 식은 i64로 계산해 값이
> i32가 되어야 하는 자리에서 한 번 좁힌다. 참값이 드는데 `-3`인 행 59 → 20(626행, 시험 구현과 행마다 같다). 실제 C 호스트가
> 바꾼 `one_payment`로 곱이 i32 밖인 입력의 정답을 받는다. 지문·ABI·바인딩은 그대로다.
>
> **▶ 다음 세션 — 여기서 시작한다.** 순서대로:
>
> 1. **강제되는 슬라이스가 없다 — 다음은 측정이다.** 참값이 드는데 `-3`으로 남은 20행 중 17행(FULL로도 남는 행)이
> 무엇인지 귀속하지 않았다(§9-73.7). 귀속이 `i64` 타입이나 다른 후보(`docs/slices/README.md`의 "다음 슬라이스" 절)를
> 가리키면 그때 SPEC을 쓴다.
> 2. **작은 항목**: C# 호스트(Phase 4) · LSP(Phase 3, 큰 일).
> 3. **외부**: `X1`·`X2` — Delphi가 있는 CI 러너. 이 저장소 안에서는 닫히지 않는다.
>
> ⚠ **이 머신의 전체 게이트는 6회 중 2회 실패한다**(§9-63.5) — 실패를 보면 먼저 원인을 읽는다.
> 강한 신호는 CI 두 잡이다.
>
> 📌 **본문은 §9-73이다**(`docs/history/9-73.md`). 그 앞의 2026-09-26 (6) 항목(헬퍼 체크 전파 닫힘)은
> 바이트 그대로 옮겼다 — 지금은 `docs/history/start-block-054.md`다.
>
1 change: 1 addition & 0 deletions docs/history/start-block-index.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@

> | 날짜 | 무엇을 했나 | 본문 |
> |---|---|---|
> | 2026-09-27 | **넓은 중간값 슬라이스가 닫혔다: `!` 문맥의 순수 산술 식은 정확히 계산된다** — 같은 날 인계 정리(§9-74) | §9-73 |
> | 2026-09-26 (6) | **헬퍼 체크 전파 슬라이스가 닫혔다: `!`를 위해 실행되는 산술은 어디서든 검사된다** — 다음 날 넓은 중간값 슬라이스로 닫혔다(§9-73) | §9-72 |
> | 2026-09-26 (5) | **체크드 산술 다음을 쟀다: 헬퍼 체크 전파가 조용한 오답을 가장 많이 줄인다** — 같은 날 슬라이스로 닫혔다(§9-72) | §9-71 |
> | 2026-09-26 (4) | **체크드 정수 산술 슬라이스가 닫혔다: `!` 본문의 오버플로가 `-3`이 됐다** — 같은 날 다음 후보를 쟀다(§9-71) | §9-70 |
Expand Down
Loading
Loading