Skip to content

feat: pure C API isolation layer for cross-compiler compatibility#1

Merged
boybook merged 5 commits intomainfrom
feat/c-api-isolation
Mar 7, 2026
Merged

feat: pure C API isolation layer for cross-compiler compatibility#1
boybook merged 5 commits intomainfrom
feat/c-api-isolation

Conversation

@boybook
Copy link
Owner

@boybook boybook commented Mar 7, 2026

Summary

  • Add pure C ABI boundary between C++/Fortran core library and Node.js N-API binding
  • Solve Windows crash: MSVC-compiled Node.js can now load MinGW-compiled native extensions
  • Architecture: .node (N-API) → C ABI → wsjtx_core shared library (C++/Fortran)
  • CI workflow simplified from 773 to ~200 lines

Changes

  • New: native/wsjtx_c_api.h and .cpp — pure C interface with opaque handle
  • Modified: wsjtx_wrapper to use C API instead of C++ direct linking
  • Rewritten: CMakeLists.txt with dual-target build (wsjtx_core + .node)
  • Windows: two-phase build (MinGW core DLL + MSVC .node)
  • Linux/macOS: single cmake build produces both targets

Test plan

  • Windows local: MSVC Node.js loads .node without crash
  • Windows local: 23/23 basic tests pass
  • CI: Linux x64 build + test
  • CI: Linux ARM64 build + test
  • CI: macOS ARM64 build + test
  • CI: macOS x64 build + test
  • CI: Windows x64 two-phase build + test

🤖 Generated with Claude Code

boybook and others added 5 commits March 7, 2026 12:12
Introduce a pure C ABI boundary between the C++/Fortran core library
(wsjtx_core) and the Node.js N-API binding (.node). This solves the
Windows crash where MSVC-compiled Node.js failed to load MinGW-compiled
native extensions due to ABI incompatibility.

Architecture: .node (N-API) -> C ABI -> wsjtx_core shared library (C++/Fortran)

- New: native/wsjtx_c_api.h and .cpp (pure C interface with opaque handle)
- Modified: wsjtx_wrapper to use C API instead of C++ direct linking
- Rewritten: CMakeLists.txt with dual-target build (wsjtx_core + .node)
- Windows: two-phase build (MinGW core DLL + MSVC .node)
- Linux/macOS: single cmake build produces both targets
- CI workflow simplified from 773 to ~200 lines

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Linux/macOS build failed because std::invalid_argument needs <stdexcept>
  (MSVC includes it transitively, GCC does not)
- macOS packaging failed because libwsjtx_core.dylib was manually copied
  before dylibbundler tried to copy it as a dependency. Removed manual copy,
  added build/Release to search paths, and use -of flag for overwrite safety.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
dylibbundler already follows transitive dependencies when processing .node,
so it bundles libwsjtx_core.dylib and all its deps (fftw, gfortran, etc.)
in a single pass. The second dylibbundler call was redundant and failed
because it tried to copy already-bundled files onto themselves.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Add `publish` job to build.yml: triggers only on v* tag push,
  downloads prebuilds from collect-artifacts, validates all 5 platforms,
  runs npm publish, and creates GitHub Release with platform archives
- Simplify prepublishOnly to just build:ts (CI handles validation)
- Remove manual scripts/create-release.sh (now integrated in CI)
- Update PUBLISHING.md to reflect the new one-step workflow

New release flow: npm version patch && git push --tags → fully automated.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add npm run test:full to CI test steps, which runs the comprehensive
test suite including FT8 encode→WAV→decode round-trip verification.
This ensures the native binaries actually work end-to-end, not just load.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@boybook boybook merged commit e7f9894 into main Mar 7, 2026
7 checks passed
@boybook boybook deleted the feat/c-api-isolation branch March 7, 2026 06:29
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