class Epithet::Block58::Unrolled16
Specialised decoder for 16-byte blocks (22 digits) with a fully unrolled inner product.
Public Class Methods
Source
# File lib/epithet/block58.rb, line 96 def initialize(...) super raise ArgumentError, 'unrolled codec requires a 16-byte block' unless @size == 22 end
Calls superclass method
Epithet::Block58::new
Public Instance Methods
Source
# File lib/epithet/block58.rb, line 103 def s2i(str) # rubocop:disable Style/NumericLiterals, Lint/AmbiguousOperatorPrecedence, Layout # # By unrolling the chunks against literal coefficients, this tested with Ruby 4.0 # at ~1.5x faster under YJIT than the generic chunked Block58#s2i, and ~6x faster # than Horner's scheme. lut = @lut acc0 = lut.getbyte(str.getbyte(0)) * 7427658739644928 + lut.getbyte(str.getbyte(1)) * 128063081718016 + lut.getbyte(str.getbyte(2)) * 2207984167552 + lut.getbyte(str.getbyte(3)) * 38068692544 + lut.getbyte(str.getbyte(4)) * 656356768 + lut.getbyte(str.getbyte(5)) * 11316496 + lut.getbyte(str.getbyte(6)) * 195112 + lut.getbyte(str.getbyte(7)) * 3364 + lut.getbyte(str.getbyte(8)) * 58 + lut.getbyte(str.getbyte(9)) acc1 = lut.getbyte(str.getbyte(10)) * 7427658739644928 + lut.getbyte(str.getbyte(11)) * 128063081718016 + lut.getbyte(str.getbyte(12)) * 2207984167552 + lut.getbyte(str.getbyte(13)) * 38068692544 + lut.getbyte(str.getbyte(14)) * 656356768 + lut.getbyte(str.getbyte(15)) * 11316496 + lut.getbyte(str.getbyte(16)) * 195112 + lut.getbyte(str.getbyte(17)) * 3364 + lut.getbyte(str.getbyte(18)) * 58 + lut.getbyte(str.getbyte(19)) lut.getbyte(str.getbyte(21)) + lut.getbyte(str.getbyte(20)) * 58 + acc1 * 3364 + acc0 * 1449225352009601191936 # rubocop:enable Style/NumericLiterals, Lint/AmbiguousOperatorPrecedence, Layout end
Decode a 22-digit base58 string to an integer. Assumes the input passes #valid?, behaviour undefined if it doesnβt.