2026-05-29
날짜는 UTC 기준으로 나눴습니다(9월 22일부터는 한국 시간 기준). 커밋은 커미터 시각(committer date), PR은 생성·병합 시각으로 분류했습니다. 목록은 2026-10-06 KST에 GitHub에서 다시 조회해 보강했습니다. 공개 저장소의 기본 브랜치 활동만 포함합니다.
요약 (AI 작성)
zntc는 오전에 이슈 단위 버그 수정을 연달아 병합했습니다. 문자열 리터럴의 \u{} 이스케이프 범위 초과 검사(#3988), es5 다운레벨에서 기본값이 있는 중첩 구조 분해(#3989), exports·imports 와일드카드를 가장 긴 접두사로 고르는 해석과 명시적 null 대상 차단(#3993, #3994), 플러그인 실패 진단 문자열의 데이터 경쟁(#3995)을 고쳤습니다. 진단은 Expected X but found Y 형식으로 렌더하고 해석되지 않은 import 제안을 중립적인 hint로 바꿨습니다(#3991, #3992). 모듈 쪽에서는 순수 CJS star를 가진 ESM의 namespace import를 __toESM(require())로 처리하고(#3996) export*-from-CJS 멤버를 런타임에 구성하며 dev HMR에서도 빠지지 않게 했고(#4001, #4002), 실제로 없는 export만 missing_export로 보고하고(#3997) 모호한 export * 충돌을 명세대로 거부하거나 undefined로 처리했습니다(#3998).
저녁에는 Zig 0.15.2에서 0.16.0으로 옮기는 대형 마이그레이션(#4003)이 병합됐습니다. 빌드 시스템과 panic 경로부터 CLI, 번들러, dev 서버, NAPI, WASM, 테스트까지 파일 시스템·시간·스레딩 호출을 새 std.Io 기반으로 바꾸는 커밋 77개가 한꺼번에 main에 들어왔고, Thread.Pool은 Io.Group으로, mutex는 Io.Mutex나 io 없는 스핀락으로 바꿨습니다. 멀티스레드 wasm을 std 0.16이 지원하지 않아 wasm 번들러는 단일 스레드로 돌렸고, upstream 회귀를 피해 arm64-windows는 x64 호스트에서 교차 빌드하며 windows-msvc에는 advapi32를 명시적으로 링크했습니다. 후속으로 --jobs를 io async_limit에 연결하고(#4005) graph·emit 작업을 범위 단위로 묶어 0.16의 작업당 오버헤드를 줄였으며(#4008), MpscChannel 전송 OOM 시 멈춤이나 해제 후 사용 없이 실패하게 했습니다(#4010).
밤에는 export * as ns의 내부 이름이 일반 export *와 잘못 모호 판정되어 zod의 z.string이 undefined가 되던 회귀를 고치고(#4012), member-rewrite된 namespace의 없는 멤버 접근과 optional chain 멤버 접근이 끊어진 참조를 남기지 않게 했습니다(#4014, #4018). WASM 최적화 모드를 덮어쓰는 -Dwasm-optimize와 배포용 LTO를 켜는 -Denable-lto 옵션도 추가했습니다(#4016).
suji는 IPC 지연 응답의 해제 후 사용, 슬롯 고갈, 종류 혼동, TTL 문제를 고치고(#57) 리뷰 후속으로 eviction 경쟁과 타이머 누수를 없앴습니다(#59). Windows ReleaseSafe의 translate-c 미사용 지역 변수 오류(#58)와 패키징된 앱의 scheme handler가 해제된 메모리를 써서 죽던 문제를 요청별 참조 카운트로 고쳤습니다(#61). 블로그 저장소 ohah.github.io에는 5월 29일 요약 추가 커밋 1개가 있었습니다.
공개 커밋 107개, 해당일 생성 또는 병합된 PR 30개를 정리했습니다. PR 생성 30개·병합 30개는 같은 PR이 양쪽에 포함될 수 있습니다.
커밋
ohah/ohah.github.io
ohah/suji
- fix(cef): packaged scheme-handler UAF crash — per-request refcount (closes #60 part 1)
- fix(ipc): code-review max followup — remove eviction race + timer leak + harness robustness
- fix(build): Windows ReleaseSafe translate-c unused-local (closes #14)
- fix(ipc): deferred-response criticals — UAF, slot exhaustion, cross-kind, TTL (PR #54 review)
ohah/zntc
- fix(bundler): optional-chain namespace 멤버(ns?.x)도 member-rewrite (dangling 제거)
- feat(build): WASM 최적화 모드 오버라이드(-Dwasm-optimize) + 배포 LTO opt-in(-Denable-lto)
- fix(bundler): MpscChannel inline-async 안전성 불변식 명문화 + 단일 소비자 assert
- fix(bundler): member-rewrite 된 namespace 의 미존재 멤버 접근을 (void 0) 로 (dangling 참조 제거)
- fix(bundler): export*-as-ns inner 이름이 plain export* 와 false-ambiguous 충돌하던 회귀 수정 (zod z.string===undefined)
- fix(bundler): MpscChannel send OOM 시 graceful 실패 (hang/UAF 제거) (#4009)
- perf(bundler): graph/emit dispatch 를 range-task 로 배치해 0.16 per-task 오버헤드 amortize (#4007)
- test(browser-field): disabled 모듈 namespace 기대값을 esbuild-parity 로 교정
- feat(bundler): --jobs(max_threads) 를 io async_limit 에 연결 (#4004)
- ci: arm64-windows 를 x64 호스트에서 cross-build (upstream Zig 0.16 회귀 회피)
- fix(server,cli): 0.16 getsockname stdcall + createDirPath symlink 처리
- fix(build): windows-msvc 에 advapi32 명시 링크 (undefined symbol)
- fix(bundler): graph 가 entry_dir 를 소유하도록 변경 (dangling borrow)
- ci: setup-zig 버전 0.15.2→0.16.0 (전 워크플로우/액션) (#1514)
- style: zig fmt (0.16 마이그레이션 편집 후 포맷 정리) (#1514)
- fix(server): WS/SSE/Error broadcast 락을 Io.Mutex 로 (blocking write 중 busy-spin 회귀 제거, io 스레딩) (#1514)
- fix(review): sourcemap debugId 내용시드 + --jobs 주석 정정 + shutdown listen_ready acquire + RealReadFileCache.io in-lock + resolve_cache browser-override resolve_ptr (#1514)
- fix: realPathFileAlloc [:0]u8 sentinel-free 잔존 site 정리 (CLI options/main/dev_server/napi options) (#1514)
- fix(wasm): single-threaded 모듈에 맞춰 JS bridge shared:false + 0.16 신규 WASI stub(fd_filestat_set_*/path_filestat_set_times/fd_readdir) (#1514)
- docs(CLAUDE): Tech Stack Zig 0.16.0 표기 (#1514)
- fix(bench): napi-callback-bench Io.Mutex/Condition + Io.Timestamp + bench.zig fixed writer (#1514)
- fix: realPathFileAlloc [:0]u8 size-mismatch (federation dupe + dirPath [:0]u8) (#1514)
- fix(bundler): RealFS.realpath [:0]u8→정확크기 dupe (DebugAllocator size-mismatch) (#1514)
- fix(test): profile setIoForTest + DirEntryCache.io 주입 (3 fail + 2 crash) (#1514)
- wip(test): basic walker.next(io) + bench realPathFileAlloc (#1514)
- wip(test): Term.exited/openDir(io)/bench print/graph.build io 잔여 (#1514)
- wip(test): makeDir→createDir/process.run/rebuild/lookupPkgInfo/realPathFileAlloc/glob/findProjectRoot io (#1514)
- wip(test): 유닛테스트 0.16 std.Io 마이그레이션 (5그룹 병렬, std.testing.io) (#1514)
- fix(napi): captureEnvironFromLibc Windows GlobalBlock comptime 분기 (#1514)
- fix(wasm-bundler): single-threaded 전환 (0.16 멀티스레드 wasm std 미지원 우회) (#1514)
- wip(wasm-bundler): bundle io + smp_allocator 시도 (멀티스레드 wasm allocator std 0.16 갭 잔존) (#1514)
- wip(wasm): bufferDiagnostics Io.Writer.Allocating (#1514)
- wip(wasm/schema): wasmIo + emit_schema juicy main (#1514)
- wip(napi): watch 2nd scanRoot io (#1514)
- wip(napi): watch fs(Io.Dir/writeFile)+scanRoot io+IoTimer (#1514)
- wip(server): wyhash/TrackedFileSet io (#1514)
- wip(napi): transpile_entry Allocating + watch bundle io + findTsconfigPath io (#1514)
- wip(napi): loadFromPath/resolveThreadSafe io + Clock.Duration + serve start io + watch SpinLock (#1514)
- wip(napi): io 생성/env capture + bundle/buildApp/autodiscover io + plugin_bridge/watch Io.Event (#1514)
- fix(server): MtimeBackend io field + io.sleep (Windows cross-build green) (#1514)
- fix(server): InotifyBackend io field (Linux cross-build green) (#1514)
- wip(server): InotifyBackend libc inotify_init1/add_watch + Io.File.close (#1514)
- wip(cli): main watch getFileMtime io (#1514)
- wip(cli): main watch loop Thread.sleep→io.sleep (#1514)
- wip(cli): getFileMtime stat.mtime.toNanoseconds (#1514)
- wip: File.Flags + it.next(io) + getFileMtime io + SSE Io.Writer.fixed (#1514)
- wip(server): file_watcher kqueue→std.c + Io.File.close + FileWatcher.init io (#1514)
- wip(bundler): MF contract verification chain io (#1514)
- wip(bundler): transferModulesToStore io 호출 정정 (#1514)
- wip: ArrayList.writer→Io.Writer.Allocating/print + dead_store .empty (#1514)
- wip(emitter): emit Thread.Pool→Io.Group + emitWithTreeShaking io (#1514)
- wip(bundler): emit io 오버추가 정정 + resolveExistingModuleIndex/wireImplicitlyLoaded io (#1514)
- wip(bundler): RealReadFileCache io-field + IncrementalBundler rebuild io (#1514)
- wip(server): dev_server std.Io.net/Dir/process.spawn/Timestamp migration (#1514)
- wip(bundler): build_flow applyContextDepResults io (#1514)
- wip: test262 runner/main juicy main + bundler/federation deprecatedWriter+realpath io (#1514)
- wip(bundler): browser-override/getOrParse/statFile io cascade (#1514)
- wip(bundler): resolve_imports propagate/expand io (#1514)
- wip(bundler): glob/require_context/resolve_imports/assets io cascade (#1514)
- wip(bundler): resolver.zig per-instance io 필드 + fs/readFileAlloc 전환 (#1514)
- wip(bundler): resolve_cache resolve/browserOverrides io 스레딩 (#1514)
- wip(bundler): path.relative 5-arg + package_info/parser_setup io (#1514)
- wip(bundler): package_info/assets/resolve_imports io cascade (#1514)
- wip(bundler): assets/package_json/build_flow io + plugin json put allocator (#1514)
- wip(bundler): parse_module getMtime + json_module io (#1514)
- wip(bundler): parse_module/loaders/json_module io 스레딩 (#1514)
- wip(bundler): resolve_imports + module_registry.addModule io 스레딩 (#1514)
- wip(bundler): fs mtime/Timestamp + project_root/discovery_scan io (#1514)
- wip(bundler): mpsc_channel std.Io.Mutex/Condition + discovery_scan io 시그니처 (#1514)
- wip(bundler): build_flow Thread.Pool→Io.Group + io 스레딩 (#1514)
- fix(bundler): statFile/io 호출 인자 정정 (std.Io.Dir.statFile options) (#1514)
- wip(bundler): bundler.zig fs 자유함수 호출 io 전달 (#1514)
- wip(bundler): fs.zig io 스레딩 + double-check 스핀락 (0.16, #1514)
- wip(bundler): bundler.zig bundle/buildWorker io 스레딩 + Timer (0.16, #1514)
- refactor(bundler): trivial mutex → io-free 스핀락 (0.16, #1514)
- wip(cli): standalone + watch io 스레딩 0.16 (#1514)
- wip(app): app-builder(app/build.zig)+env.zig io 스레딩 (#1514)
- wip(cli,config): app/config/options io 스레딩 + realpath API (#1514)
- refactor: 0.16 비-io API 일괄 이관 — UUID/container empty (#1514)
- refactor: std.mem.trimRight/trimLeft → trimEnd/trimStart (0.16, #1514)
- wip(cli): bench.zig io + main writer unbuffered 전환 (#1514)
- wip(cli): main.zig 본문 fs/io 스레딩 0.16 전환 (#1514)
- wip(cli): main.zig 헬퍼 + root env_flag export 0.16 전환 (#1514)
- wip(cli): main.zig juicy main 진입부 0.16 전환 (#1514)
- refactor(profile,debug_log,env): 0.16 std.Io 시간측정 + env 접근 재설계 (#1514)
- chore(build): Zig 0.16.0 빌드 시스템 + panic 경로 마이그레이션 (#1514)
- fix(bundler): dev HMR 의 export*-from-CJS namespace 멤버 누락 수정 (#3975)
- fix(bundler): namespace import 의 export*-from-CJS 멤버를 런타임 구성 (#3975)
- fix(test): 범위초과 \u{} 이스케이프 통합 테스트를 expectError 로 교정 (#3980)
- test(bundler): ambiguous export* 게이트 차원별 회귀 보강 (#3982)
- fix(bundler): ambiguous export* 충돌을 spec 대로 거부/undefined 처리 (#3982)
- fix(bundler): 진짜 누락 export 만 missing_export 진단으로 surface (#3978)
- fix(bundler): namespace import of pure-CJS-star ESM 를 __toESM(require()) 로 처리 (#3975)
- fix(bundler): tryAddPluginFailureDiag 의 owned_diagnostic_strings append 를 diag_mutex 로 보호 (#3977)
- fix(resolver): 조건부 exports/imports 의 명시적 null target 을 차단 (#3981)
- fix(resolver): exports/imports 와일드카드를 longest-prefix 로 선택 (#3976)
- fix(cli): unresolved-import suggestion 을 'did you mean' 대신 중립 hint 로 렌더 (#3986)
- fix(diagnostic): expect()/jsx 진단을 'Expected X but found Y' 로 렌더 (#3985)
- fix(bundler): CompiledModule.dupe shared_ns_decls 루프 부분-채움 누수 가드 (#3983)
- fix(transformer): es5 다운레벨에서 default 있는 중첩 destructuring lowering (#3979)
- fix(lexer): string literal \u{} 이스케이프 범위초과 검사 추가 (#3980)
- fix(bundler): non-literal dynamic import 진단을 reason 메시지로 통일 (#3984)
PR (해당일 생성/머지)
상태는 조회 시점 기준입니다. merged는 아래 대상 브랜치에 병합됐다는 뜻이며, 기능 브랜치 병합과 main 반영을 구분합니다. 같은 PR이 생성일과 병합일 양쪽 기록에 나타날 수 있습니다.