Module: Blusher::Native

Defined in:
lib/blusher/native.rb

Overview

The native boundary to the carmine engine. Coarse lex-or-decline contract: ‘Native.lex(table_json, input)` returns either

- an Array of [token_qualname, value] String pairs (carmine lexed it), or
- nil (a callback rule blocks native lexing → caller falls back to rouge).

Two backends, in preference order:

1. the rb-sys/magnus native extension (`blusher.{bundle,so}`), which
   builds the token Array DIRECTLY as Ruby objects — no JSON round-trip.
   This is the release path and the only one that beats rouge.
2. the `carmine-ffi` cdylib via Fiddle, marshaling tokens through JSON.
   A dependency-light bootstrap kept for environments without the
   precompiled ext; the JSON serialize/parse makes it a net loss vs rouge,
   so it exists for correctness/coverage, not speed.

Constant Summary collapse

DLEXT =
(RbConfig::CONFIG["host_os"] =~ /darwin/ ? "dylib" : "so")
EXT_CANDIDATES =

— backend 1: magnus native extension ——————————– The loadable object’s name must match the ‘Init_blusher` symbol and use the platform’s Ruby ext suffix (.bundle/.so) — ‘require` won’t load a raw cargo ‘.dylib`. `rake compile` stages it here from the cargo target dir.

[
  # gem-installed by rake-compiler: lib/blusher/blusher.<dlext>
  File.expand_path("blusher.#{RbConfig::CONFIG["DLEXT"]}", __dir__),
  # dev: `rake compile` stages the cargo build at lib/blusher.<dlext>
  File.expand_path("../blusher.#{RbConfig::CONFIG["DLEXT"]}", __dir__),
  File.expand_path("../blusher.bundle", __dir__),
  File.expand_path("../blusher.so", __dir__),
].freeze
FFI_CANDIDATES =
[
  File.expand_path("../../ext/libcarmine_ffi.#{DLEXT}", __dir__),
  File.expand_path("../../../target/release/libcarmine_ffi.#{DLEXT}", __dir__),
  File.expand_path("../../../target/debug/libcarmine_ffi.#{DLEXT}", __dir__),
].freeze
LIB =
Fiddle.dlopen(path)
FFI_LEX =
Fiddle::Function.new(
  LIB["carmine_lex"],
  [Fiddle::TYPE_VOIDP, Fiddle::TYPE_VOIDP, Fiddle::TYPE_SIZE_T],
  Fiddle::TYPE_VOIDP
)
FFI_FREE =
Fiddle::Function.new(LIB["carmine_free"], [Fiddle::TYPE_VOIDP], Fiddle::TYPE_VOID)

Class Attribute Summary collapse

Class Method Summary collapse

Class Attribute Details

.backendObject (readonly)

Returns the value of attribute backend.



72
73
74
# File 'lib/blusher/native.rb', line 72

def backend
  @backend
end

Class Method Details

.format_html(_tag, _table_json, _input, _shortname) ⇒ Object

The FFI/JSON backend can’t fuse profitably (it would re-cross the JSON boundary); decline so the shim uses rouge’s formatter on FFI tokens.



88
89
90
# File 'lib/blusher/native.rb', line 88

def self.format_html(tag, table_json, input, shortname)
  Blusher::Engine.format_html(tag, table_json, input, shortname)
end

.fused_html?Boolean

Returns:

  • (Boolean)


111
112
113
# File 'lib/blusher/native.rb', line 111

def self.fused_html?
  @backend == :ext
end

.lex(_tag, table_json, input, qualname) ⇒ Object



81
82
83
# File 'lib/blusher/native.rb', line 81

def self.lex(tag, table_json, input, qualname)
  Blusher::Engine.lex(tag, table_json, input, qualname)
end