Class: Shojiku::Engine

Inherits:
Object
  • Object
show all
Defined in:
lib/shojiku/engine.rb

Overview

The declared C surface, and the one place a call crosses into it.

Every function is declared with explicit argument and return types. Fiddle's default return type is a C int, which truncates every pointer this library hands back — a segfault that looks like a memory bug and is really a missing declaration.

Constant Summary collapse

VOIDP =
Fiddle::TYPE_VOIDP
SIZE_T =
Fiddle::TYPE_SIZE_T
INT =
Fiddle::TYPE_INT
VOID =
Fiddle::TYPE_VOID
INT32 =

Unpack directives that match the C types EXACTLY, rather than Ruby's native-width shorthands. l! is a native long, which is 8 bytes where int32_t is 4 — and unpack1 on a buffer shorter than its directive returns nil rather than raising, so every flag would silently read as false. l is int32 and these two are picked from the real size_t width, which differs from unsigned long on Windows.

"l"
SIZE =
Fiddle::SIZEOF_SIZE_T == 8 ? "Q" : "L"

Instance Method Summary collapse

Constructor Details

#initialize(library) ⇒ Engine

Only the lifecycle the SDK contract defines is bound: engine info, render, sign, verify. validate and preview are the authoring surface's, not an artifact lifecycle's — the Designer reaches them through the WASM bindings, and binding them here would be surface with no contract behind it.



41
42
43
44
45
46
47
48
49
50
51
# File 'lib/shojiku/engine.rb', line 41

def initialize(library)
  @library = library
  @info = library.function(:shojiku_engine_info, [VOIDP], INT)
  @render = library.function(:shojiku_render, [VOIDP, SIZE_T, VOIDP], INT)
  @sign = library.function(
    :shojiku_sign,
    [VOIDP, SIZE_T, VOIDP, SIZE_T, VOIDP, SIZE_T, VOIDP, SIZE_T, VOIDP], INT
  )
  @verify = library.function(:shojiku_verify, [VOIDP, SIZE_T, VOIDP, SIZE_T, VOIDP], INT)
  declare_accessors(library)
end

Instance Method Details

#engine_infoObject



53
54
55
# File 'lib/shojiku/engine.rb', line 53

def engine_info
  invoke { |out| @info.call(out) }
end

#render(request) ⇒ Object



57
58
59
# File 'lib/shojiku/engine.rb', line 57

def render(request)
  invoke { |out| @render.call(request, request.bytesize, out) }
end

#sign(pdf:, key:, certificate:, passphrase: nil) ⇒ Object



61
62
63
64
65
66
67
68
# File 'lib/shojiku/engine.rb', line 61

def sign(pdf:, key:, certificate:, passphrase: nil)
  invoke do |out|
    @sign.call(
      pdf, pdf.bytesize, key, key.bytesize, certificate, certificate.bytesize,
      passphrase, passphrase ? passphrase.bytesize : 0, out
    )
  end
end

#verify(pdf:, anchors:) ⇒ Object



70
71
72
# File 'lib/shojiku/engine.rb', line 70

def verify(pdf:, anchors:)
  invoke { |out| @verify.call(pdf, pdf.bytesize, anchors, anchors.bytesize, out) }
end