ascii85_native 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 29b779e3fe160aeafcecd06d79f661f9a4b0a992dd053af39515eacfa7e2f367
4
+ data.tar.gz: bbc6085d316adaea46f93095dbf738aea1441fb682c32736152c0674c33f7df2
5
+ SHA512:
6
+ metadata.gz: 0a4267955d024d17a5a540961e583bb498c4c70eddc9073d680925e3a8b9c10aeaed73a9ea07dbef6455c6dec62d308c61e465739312e67c5ff575f75de3bc4e
7
+ data.tar.gz: af7a04720ee115222ad4897af241ee305486bc2494aa9925acdddaefcb10aa8c5be8bcc723e92818237c04385207137a678cef777a8362dd8b7b9dff8db9c359
@@ -0,0 +1,103 @@
1
+ // a85.cpp
2
+ //
3
+ // Ascii85 C++ implementation pulled from https://github.com/larskholte/a85
4
+ // Original C++ Code License: Copy and use as you please. No attribution necessary.
5
+ //
6
+ // Adapted to C language
7
+
8
+ #include "ascii85_native.h"
9
+
10
+ int size_for_a85(int binlen, bool append_null) {
11
+ return (binlen * 5 + 3) / 4 + !!append_null;
12
+ }
13
+
14
+ void to_a85(const u8* data, int binlen, char* text, bool append_null) {
15
+ // Go to end of data and text buffers
16
+ data += binlen;
17
+ text += size_for_a85(binlen,append_null);
18
+ // Append null if requested
19
+ if (append_null) {
20
+ *(--text) = 0;
21
+ }
22
+ // If number of bytes is not divisible by 4, act as if null bytes were added to end of buffer
23
+ int rem = binlen & 3;
24
+ if (rem) {
25
+ u32 val = 0;
26
+ for (int i = 4 - rem; i < 4; i++) {
27
+ val |= *(--data) << (8 * i);
28
+ }
29
+ int i;
30
+ for (i = 0; i < 4 - rem; i++) {
31
+ val /= 85;
32
+ }
33
+ for (; i <= 4; i++) {
34
+ *(--text) = val % 85 + 33;
35
+ val /= 85;
36
+ }
37
+ binlen &= ~3;
38
+ }
39
+ while (binlen) {
40
+ // Process chunks of 4 bytes as 32-bit values
41
+ u32 val = *(--data);
42
+ val |= *(--data) << 8;
43
+ val |= *(--data) << 16;
44
+ val |= *(--data) << 24;
45
+ // Convert to base 85
46
+ *(--text) = val % 85 + 33;
47
+ val /= 85;
48
+ *(--text) = val % 85 + 33;
49
+ val /= 85;
50
+ *(--text) = val % 85 + 33;
51
+ val /= 85;
52
+ *(--text) = val % 85 + 33;
53
+ val /= 85;
54
+ *(--text) = val % 85 + 33;
55
+ binlen -= 4;
56
+ }
57
+ }
58
+
59
+ int size_for_bin(int textlen) {
60
+ return (textlen * 4) / 5;
61
+ }
62
+
63
+ void from_a85(const char* text, int textlen, u8* data) {
64
+ while (textlen) {
65
+
66
+ while (*text == 0 || (*text >= 10 && *text <= 13)) { text++; textlen--; }
67
+
68
+ if (textlen < 5) {
69
+ // Determine represented value in base 85
70
+ u32 val = 0;
71
+ int factor = 52200625; // 85^4
72
+ int i;
73
+ for (i = 0; i < textlen; i++) {
74
+ val += (*(text++) - 33) * factor;
75
+ factor /= 85;
76
+ }
77
+ for (; i < 5; i++) {
78
+ val += 'u' * factor;
79
+ factor /= 85;
80
+ }
81
+ int shift = 24;
82
+ for (i = 0; i < textlen - 1; i++) {
83
+ *(data++) = val >> shift;
84
+ shift -= 8;
85
+ }
86
+ break;
87
+ }
88
+
89
+ // Determine represented value in base 85
90
+ u32 val = (*(text++) - 33) * 52200625; // 85^4
91
+ val += (*(text++) - 33) * 614125; // 85^3
92
+ val += (*(text++) - 33) * 7225; // 85^2
93
+ val += (*(text++) - 33) * 85; // 85^1
94
+ val += (*(text++) - 33); // 85^0
95
+
96
+ // Write out in big-endian order
97
+ *(data++) = val >> 24;
98
+ *(data++) = val >> 16;
99
+ *(data++) = val >> 8;
100
+ *(data++) = val;
101
+ textlen -= 5;
102
+ }
103
+ }
@@ -0,0 +1,27 @@
1
+ // a85.h
2
+ //
3
+ // Ascii85 C++ implementation pulled from https://github.com/larskholte/a85
4
+ // Original C++ Code License: Copy and use as you please. No attribution necessary.
5
+ //
6
+ // Adapted to C language
7
+
8
+ #include <stdint.h>
9
+
10
+ typedef _Bool bool;
11
+ typedef uint8_t u8;
12
+ typedef uint32_t u32;
13
+
14
+ // Returns size of buffer required for to_a85 function.
15
+ int size_for_a85(int binlen, bool append_null);
16
+
17
+ // Translates the given binary data of the given size to Ascii85.
18
+ // Can translate in-place.
19
+ // Optionally appends a null character.
20
+ void to_a85(const u8* data, int binlen, char* text, bool append_null);
21
+
22
+ // Returns the size of buffer required for from_a85 function.
23
+ int size_for_bin(int textlen);
24
+
25
+ // Translates the given Ascii85 text to binary data.
26
+ // Can translate in-place.
27
+ void from_a85(const char* text, int textlen, u8* data);
@@ -0,0 +1,3 @@
1
+ require "mkmf"
2
+
3
+ create_makefile "ascii85_native"
@@ -0,0 +1,69 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'ffi'
4
+
5
+ module Ascii85Native
6
+ extend FFI::Library
7
+
8
+ ffi_lib File.join(File.dirname(__FILE__), 'ascii85_native.so')
9
+
10
+ #void to_a85(const u8* data, int binlen, char* text, bool append_null);
11
+ attach_function :to_a85, [:buffer_in, :int, :buffer_out, :bool], :void
12
+
13
+ #int size_for_a85(int binlen, bool append_null);
14
+ attach_function :size_for_a85, [:int, :bool], :int
15
+
16
+ #void from_a85(const char* text, int textlen, u8* data);
17
+ attach_function :from_a85, [:buffer_in, :int, :buffer_out], :void
18
+
19
+ #int size_for_bin(int textlen)
20
+ attach_function :size_for_bin, [:int], :int
21
+
22
+
23
+ def self.encode(input, include_delimiter=false)
24
+ if input.nil?
25
+ return '<~~>' if include_delimiter
26
+ return ''
27
+ end
28
+
29
+ if input.class == String
30
+ input_data = []
31
+ input.each_byte { |byte| input_data << byte }
32
+ else
33
+ input_data = input
34
+ end
35
+
36
+ FFI::MemoryPointer.new(:uint8, input_data.size) do |in_uint8|
37
+ in_uint8.write_array_of_type(FFI::TYPE_UINT8, :put_uint8, input_data)
38
+ out_size = self.size_for_a85(input_data.size, true)
39
+
40
+ FFI::MemoryPointer.new(:uint8, out_size) do |output|
41
+ self.to_a85(in_uint8, input_data.size, output, true)
42
+ if include_delimiter
43
+ return '<~' + (output.read_string() || '') + '~>'
44
+ else
45
+ return output.read_string()
46
+ end
47
+ end
48
+ end
49
+ end
50
+
51
+
52
+ def self.decode(input)
53
+ return "" if input.nil?
54
+
55
+ if input[0] == '<' && input[1] == '~' && input[-2] == '~' && input[-1] == '>'
56
+ input = input[2..-3]
57
+ end
58
+
59
+ FFI::MemoryPointer.new(:char, input.size) do |in_char|
60
+ in_char.write_string(input)
61
+ out_size = self.size_for_bin(input.size)
62
+
63
+ FFI::MemoryPointer.new(:uint8, out_size) do |output|
64
+ self.from_a85(in_char, input.size, output)
65
+ return output.read_string()
66
+ end
67
+ end
68
+ end
69
+ end
metadata ADDED
@@ -0,0 +1,89 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: ascii85_native
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Jason Crossfield
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2021-05-05 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: ffi
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '1.15'
20
+ - - ">="
21
+ - !ruby/object:Gem::Version
22
+ version: 1.15.0
23
+ type: :runtime
24
+ prerelease: false
25
+ version_requirements: !ruby/object:Gem::Requirement
26
+ requirements:
27
+ - - "~>"
28
+ - !ruby/object:Gem::Version
29
+ version: '1.15'
30
+ - - ">="
31
+ - !ruby/object:Gem::Version
32
+ version: 1.15.0
33
+ - !ruby/object:Gem::Dependency
34
+ name: rake
35
+ requirement: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - "~>"
38
+ - !ruby/object:Gem::Version
39
+ version: '13.0'
40
+ - - ">="
41
+ - !ruby/object:Gem::Version
42
+ version: 13.0.1
43
+ type: :development
44
+ prerelease: false
45
+ version_requirements: !ruby/object:Gem::Requirement
46
+ requirements:
47
+ - - "~>"
48
+ - !ruby/object:Gem::Version
49
+ version: '13.0'
50
+ - - ">="
51
+ - !ruby/object:Gem::Version
52
+ version: 13.0.1
53
+ description: A faster implementation of the Ascii85 Encode & Decode methods using
54
+ native C extensions to do the heavy lifting.
55
+ email: jason.crossfield@gmail.com
56
+ executables: []
57
+ extensions:
58
+ - ext/ascii85_native/extconf.rb
59
+ extra_rdoc_files: []
60
+ files:
61
+ - ext/ascii85_native/ascii85_native.c
62
+ - ext/ascii85_native/ascii85_native.h
63
+ - ext/ascii85_native/extconf.rb
64
+ - lib/ascii85_native.rb
65
+ homepage: https://github.com/AnomalousBit/ascii85_native
66
+ licenses:
67
+ - MIT
68
+ metadata: {}
69
+ post_install_message:
70
+ rdoc_options: []
71
+ require_paths:
72
+ - lib
73
+ - ext/ascii85_native
74
+ required_ruby_version: !ruby/object:Gem::Requirement
75
+ requirements:
76
+ - - ">="
77
+ - !ruby/object:Gem::Version
78
+ version: '0'
79
+ required_rubygems_version: !ruby/object:Gem::Requirement
80
+ requirements:
81
+ - - ">="
82
+ - !ruby/object:Gem::Version
83
+ version: '0'
84
+ requirements: []
85
+ rubygems_version: 3.1.2
86
+ signing_key:
87
+ specification_version: 4
88
+ summary: Ascii85 Encoder / Decoder with Native C Extensions
89
+ test_files: []