BASE91.BAS contains fast Base-91 Encoding/Decoding functions you can use to convert binary files to text. This updated version is greatly improved over the previous one I shared at the forum a while back, the speed increase being really huge, now encodes over 43,800 percent faster. A 1MB file takes only .2 seconds to encode now (not 96 seconds as before). Description and more info are in the code comments for you to read more about what this does.
NOTE: This does not produce standard Base-91 encoded text as it uses an custom 91-Character set - one that outputs text that should be OK to put in code here at the forum (I replaced the @ symbol and a couple others that may be a problem with forum posts).
- Dav
NOTE: This does not produce standard Base-91 encoded text as it uses an custom 91-Character set - one that outputs text that should be OK to put in code here at the forum (I replaced the @ symbol and a couple others that may be a problem with forum posts).
- Dav
Code: (Select All)
'==========
'BASE91.BAS v1.1
'==========
'Base-91 Encoder/Decoder Functions.
'Coded by Dav for QB64-PE, DEC/2025
'New for v1.1 - HUGE increase in encoding/decoding speed!
' Previous version took 96.8 secs to encode 1MB,
' This one takes only .2 sec - a 43,800% increase.
'Like Base-64/Base-85 encoding, Base-91 is a way of encoding binary
'data to viewable text so it can be included in messages or code.
'It can later be decoded back into the original binary data safely.
'Base-91 encoding is more efficient than Base-64, producing smaller
'encoded output as the demo program here will show.
'First part of demo: compare Base-64 & Base-91 output size.
'We will encode/decode in both Base-64 and base-91 to compare them.
'The Base-64 results in about a 33% size increase, Base-91 is only
'14% increase. The downside to using these Base-91 functions over
'QB64-PE's built in_Base64Encode/Decode functions are in the speed.
'Base-91 is a little slower, but not that much - a 1MB file can be
'encoded/decoded in .2 sec on my T470s Thinkpad - almost instantly.
'The Base-64 functions in QB64-PE do work instantly (0 seconds).
'Second part of demo: Ensure Base-91 encode/decode safely.
'We will enter a loop of testing encode/decoding random data to
'ensure Base-91 functions are encode/decoding data safely. Press
'the ESC key to stop the loop of data testing. If data errors are
'found, the loop will stop automatically.
'NOTE: This is using a modified Base-91 character set so the output
'won't include symbols that may conflict with QB64-PE forum posting.
'==================================================================
Screen 12: _FullScreen
_ControlChr Off
Color 15, 1
Print "Making 1MB test data to use."
a$ = String$(1000000, 0)
Print "Original byte size ="; Len(a$)
Color 7, 0
Print
t1 = Timer
e$ = _Base64Encode$(a$)
Print "Base-64 Encoded in"; Timer - t1; "secs, bytes ="; Len(e$)
t1 = Timer
d$ = _Base64Decode$(e$)
Print "Base-64 Decoded in"; Timer - t1; "secs, bytes ="; Len(d$)
If Len(a$) = Len(d$) Then
Print "Original and Base-64 decoded sizes match!"
Else
Print "Original and Base-64 decoded sizes DO NOT match."
End If
If a$ = d$ Then
Print "Original and Base-64 decoded data match!"
Else
Print "Original and Base-64 decoded data DO NOT match."
End If
Print "Size increase:"; Int((Len(e$) - Len(a$)) / Len(a$) * 100); "%"
Print
t1 = Timer
e$ = Base91Encode$(a$)
Print "Base-91 Encoded in"; Timer - t1; "secs, bytes ="; Len(e$)
t1 = Timer
d$ = Base91Decode$(e$)
Print "Base-91 Decoded in"; Timer - t1; "secs, bytes ="; Len(d$)
If Len(a$) = Len(d$) Then
Print "Original and Base-91 decoded sizes match!"
Else
Print "Original and Base-91 decoded sizes DO NOT match."
End If
If a$ = d$ Then
Print "Original and Base-91 decoded data match!"
Else
Print "Original and Base-91 decoded data DO NOT match."
End If
Print "Size increase:"; Int((Len(e$) - Len(a$)) / Len(a$) * 100); "%"
Print
Print "PRESS ANY KEY TO GO TO NEXT TEST..."
Sleep
Do
Cls
Color 15, 1: Print "Checking bytes loop -- Hit ESC key to stop checking ..."
a$ = ""
Print
Color 7, 0: Print "Original:"
bytes = 200 + Int(Rnd * 55)
For i = 0 To bytes
a$ = a$ + Chr$(Int(Rnd * 255))
Next
Print a$
Print Len(a$); "bytes"
Print
Print "Encoded:"
a2$ = Base91Encode$(a$): Print a2$
Print Len(a2$); "bytes"
Print
Print "Decoded:"
a3$ = Base91Decode$(a2$): Print a3$
Print Len(a3$); "bytes"
Print
If Len(a$) <> Len(a3$) Then Color 12, 0: Print "Size don't match!"; t: End
If a$ <> a3$ Then Color 12, 0: Print "Bytes don't match!"; t: End
_Display
_Limit 10
If _KeyHit = 27 Then Exit Do
loopcount = loopcount + 1
bytecount = bytecount + bytes
Loop
Print
Print "No data encoding/decoding errors detected!"
Function Base91Encode$ (in$)
'Build 91 characters to use
For i = 33 To 126
If i <> 34 And i <> 64 And i <> 96 Then Chars$ = Chars$ + Chr$(i)
Next
out$ = Space$(Int(Len(in$) * 1.3)): opos = 0
nbits = 0
For i& = 1 To Len(in$)
bits = bits Or (_ShL(Asc(Mid$(in$, i&, 1)), nbits))
nbits = nbits + 8
If nbits > 13 Then
value = bits Mod 8192
If value > 88 Then
bits = (bits \ 8192)
nbits = nbits - 13
Else
value = bits Mod 16384
bits = (bits \ 16384)
nbits = nbits - 14
End If
Mid$(out$, opos + 1, 2) = Mid$(Chars$, (value Mod 91) + 1, 1) + Mid$(Chars$, (value \ 91) + 1, 1)
opos = opos + 2
End If
Next
If nbits > 0 Then
Mid$(out$, opos + 1, 1) = Mid$(Chars$, (bits Mod 91) + 1, 1)
opos = opos + 1
If nbits > 7 Or bits > 90 Then
Mid$(out$, opos + 1, 1) = Mid$(Chars$, (bits \ 91) + 1, 1)
opos = opos + 1
End If
End If
Base91Encode$ = Mid$(out$, 1, opos)
End Function
Function Base91Decode$ (in$)
'Build 91 characters to use
For i = 33 To 126
If i <> 34 And i <> 64 And i <> 96 Then Chars$ = Chars$ + Chr$(i)
Next
out$ = Space$(Len(in$)): opos = 0
value = -1: nbits = 0
For i& = 1 To Len(in$)
ascii = InStr(Chars$, Mid$(in$, i&, 1)) - 1
If value < 0 Then
value = ascii
Else
value = value + (ascii * 91)
bits = bits Or _ShL(value, nbits)
nbits = nbits + 13 + (((value And 8191) <= 88) * -1)
Do Until (nbits > 7) = 0
Mid$(out$, opos + 1, 1) = Chr$(bits And 255)
opos = opos + 1
bits = _ShR(bits, 8)
nbits = nbits - 8
Loop
value = -1
End If
Next
If (value + 1) Then
Mid$(out$, opos + 1, 1) = Chr$((bits Or _ShL(value, nbits)) And 255)
opos = opos + 1
End If
Base91Decode$ = Mid$(out$, 1, opos)
End Function



