2024-11-21

Navigation

Skip Navigation Links

Hash algorithms

Asymmetric Algorithms

Symmetric Cipher Algorithms

Encoding Algorithms

Compression Algorithms

Pseudo Random Number Algorithms

Steganography

Library Wrappers

String Comparison

Others

Syntax highlighting by Prism
PBCrypto.com Mirror

CAST-128

Algorithm creator(s)

Entrust Inc.


PB author(s)

Greg Turgeon


Description

A DES-like Substitution-Permutation Network (SPN) cryptosystem which appears to have good resistance to differential cryptanalysis, linear cryptanalysis, and related-key cryptanalysis. This cipher also possesses a number of other desirable cryptographic properties, including avalanche, Strict Avalanche Criterion (SAC), Bit Independence Criterion (BIC), no complementation property, and an absence of weak and semi-weak keys. It thus appears to be a good candidate for general-purpose use throughout the Internet community wherever a cryptographically-strong, freely-available encryption algorithm is required.


Note

This sample source is compatible with PBWIN7 and uses macros.


Source

https://forum.powerbasic.com/forum/user-to-user-discussions/source-code/24038-cast-128-encryption-for-3-0-7-0?t=23413


See also


Source Code

Download source code file cast-128.bas (Right-click -> "Save as ...")

#IF 0 
=====================================================================
                        CAST-128 Encryption
===================================================================== 
The CAST-128 encryption algorithm (also known as CAST5) is patented by 
Entrust Technologies, which makes it freely available for both 
commercial and non-commercial use.  Information about the algorithm is 
available from Entrust at: http://www.ietf.org/rfc/rfc2144.txt 
The PowerBASIC implementation appearing here is based on RFC2144 and 
is hereby placed in the public domain.  Use it as you wish.  My hope 
is discourage reliance on home-grown encryption schemes in favor of 
well-examined, strong, freely available algorithms. 
In this posting, test-bed code appears below the CAST-128.BAS file 
contents.  All code requires compiler releases 3.0/7.0 or later.

Implementation Notes 
-- The algorithm operates on plaintext blocks of 8 bytes.  Encryption 
of shorter blocks is possible only by padding the plaintext (usually 
with zero bytes), which can be accomplished through several methods. 
The simplest of them assumes that the final byte of plaintext always 
identifies the number of bytes of padding added, including the final 
byte itself. 
Examples: 
   total plaintext bytes         = 30
   plaintext blocks encrypted:   = 4
   final block                   = chr$(x1 to x6) + chr$(0,2) 
   total plaintext bytes         = 40
   plaintext blocks encrypted:   = 6
   final block                   = chr$(0,0,0,0,0,0,0,8)
 
-- Encryption key lengths can range from 5 to 16 bytes.  Keys shorter 
than 16 bytes are padded to 16 by appending zero bytes.  For original 
key lengths shorter than 11 bytes (88 bits), the number of rounds of 
encryption is shortened from 16 to 12.  This procedure follows the 
specifications of RFC2144.
 
-- Implementation here is handled through an #INCLUDE file.  No global 
data is employed.
 
-- As presented, the code does not supply a ready-to-use encryption 
application.  It offers necessary pieces only, as well as an 
illustration of their use.  Always keep in mind that most encryption 
is broken because of implementation flaws and weaknesses.
 
-- Like most encryption algorithms, CAST-128 was designed on big-endian
systems.  For this reason, little-endian systems return correct test 
vector results only through considerable byte-swapping, with efficiency 
suffering as a result.  Because it adds nothing to the encryption 
security, an efficient implementation should avoid the byte-swapping.
(My own preference: #IF def%(%VERIFY_IMPLEMENTATION)...)
 
-- Because of its internal methods of data handling, PowerBASIC's 
DWORDs cannot be used efficiently with most encryption and hashing 
algorithms.  Long integers should be used instead, as they are here. 
Use of longs& assures correct bit-level results (as well as additional 
speed).
 
-- The large group of s-box constants which appears at the end of the 
#INCLUDE file is required and must not be altered.
 
-- Greg Turgeon 06/2002 
=====================================================================
#ENDIF 



'=====================================================================
'                           CAST-128.BAS
'===================================================================== 
%BLOCKSIZE      = 8
%KEY_SIZE       = 16
%SUBKEY_SIZE    = 16*2
%MIN_KEY_SIZE   = 5
%MAX_KEY_SIZE   = 16
%DEFAULT_ROUNDS = 16
%SHORT_ROUNDS   = 12 
'-- Note: Strings (UserKey, etc) are processed as 
'   four-byte sequences, so LONG PTRs required
TYPE ENCRYPTION_CONTEXT
Rounds         AS LONG
S_Box          AS LONG PTR
UserKeyLength  AS LONG
UserKey        AS LONG PTR
InBlock        AS LONG PTR
OutBlock       AS LONG PTR
K              AS LONG PTR                  '<-- pointer to subkey buffer
K_Buffer       AS STRING * (%SUBKEY_SIZE*4) '<-- subkey buffer itself
END TYPE 

DECLARE SUB CAST128_Init(Ctx AS ENCRYPTION_CONTEXT)
DECLARE FUNCTION Set_Key&(Ctx AS ENCRYPTION_CONTEXT)
DECLARE FUNCTION EncryptBlock&(Ctx AS ENCRYPTION_CONTEXT)
DECLARE FUNCTION DecryptBlock&(Ctx AS ENCRYPTION_CONTEXT) 
'--------------------

MACRO zbs(x) = string$(x,0) 
'--------------------

MACRO FUNCTION byte_reverse(x)
!  mov   eax, x
!  bswap eax
!  mov   x, eax
END MACRO = x 
'--------------------

MACRO get_keyblock(mem_ptr,kdata)
!  mov   edx, mem_ptr
!  mov   eax, [edx]
!  bswap eax
!  mov   kdata, eax
!  add   edx, 4
!  mov   mem_ptr, edx
END MACRO 
'--------------------

MACRO FUNCTION getbyte(x,idx)
retval = x
!  shr   retval, idx*8
END MACRO = (retval AND &HFF) 
'--------------------

MACRO unpack_bytes(value,byte1,byte2,byte3,byte4)
byte1=getbyte(value,3)
byte2=getbyte(value,2)
byte3=getbyte(value,1)
byte4=getbyte(value,0)
END MACRO 
'====================

FUNCTION Set_Key&(Ctx AS ENCRYPTION_CONTEXT)
LOCAL x0x1x2x3&, x4x5x6x7&, x8x9xAxB&, xCxDxExF&
LOCAL z0z1z2z3&, z4z5z6z7&, z8z9zAzB&, zCzDzEzF&
LOCAL x0&, x1&, x2&, x3&, x4&, x5&, x6&, x7&, x8&, x9&, xA&, xB&, xC&, xD&, xE&, xF&
LOCAL z0&, z1&, z2&, z3&, z4&, z5&, z6&, z7&, z8&, z9&, zA&, zB&, zC&, zD&, zE&, zF&
LOCAL s5 AS LONG PTR, s6 AS LONG PTR, s7 AS LONG PTR, s8 AS LONG PTR
LOCAL k AS LONG PTR  ' temp copy
LOCAL retval&        ' for macro use 
'-- Verify key length & abort if out of range
if (Ctx.UserkeyLength < %MIN_KEY_SIZE) OR (Ctx.UserkeyLength > %MAX_KEY_SIZE) then
   function = 0 : exit function
end if 
'-- Verify that CAST128_Init has been called
if Ctx.S_BOX = 0 then
   function = 0 : exit function
end if 
Ctx.Rounds = %DEFAULT_ROUNDS
if (Ctx.UserKeyLength) < %KEY_SIZE then
   '-- Pad to default %KEY_SIZE:
   '   Make copy of original UserKey & add padding
   LOCAL keybuff$
   keybuff$ = peek$(Ctx.UserKey, Ctx.UserKeyLength) + zbs(%KEY_SIZE - Ctx.UserKeyLength)
   '  Burn original UserKey
   poke$ Ctx.UserKey, zbs(Ctx.UserKeyLength)
   '  Point to new UserKey 
   Ctx.UserKey = strptr(keybuff$)
   '  Adjust rounds if necessary
   if Ctx.UserKeyLength < 11 then Ctx.Rounds = %SHORT_ROUNDS
   Ctx.UserKeyLength = %KEY_SIZE
end if 
'-- Load pointers to keygen s-boxes
s5 = Ctx.S_BOX+(256*4*4) : s6 = s5+(256*4) : s7 = s6+(256*4) : s8 = s7+(256*4) 
k = Ctx.UserKey   'local copy for macro use & to reduce overhead 
get_keyblock(k,x0x1x2x3) : unpack_bytes(x0x1x2x3,x0,x1,x2,x3)
get_keyblock(k,x4x5x6x7) : unpack_bytes(x4x5x6x7,x4,x5,x6,x7)
get_keyblock(k,x8x9xAxB) : unpack_bytes(x8x9xAxB,x8,x9,xA,xB)
get_keyblock(k,xCxDxExF) : unpack_bytes(xCxDxExF,xC,xD,xE,xF) 
k = Ctx.K         'point now to subkey buffer
poke$ k, zbs(sizeof(Ctx.K_Buffer)) 'and clear any previous key data 
z0z1z2z3 = x0x1x2x3 XOR @s5[xD] XOR @s6[xF] XOR @s7[xC] XOR @s8[xE] XOR @s7[x8]
unpack_bytes(z0z1z2z3,z0,z1,z2,z3)
z4z5z6z7 = x8x9xAxB XOR @s5[z0] XOR @s6[z2] XOR @s7[z1] XOR @s8[z3] XOR @s8[xA]
unpack_bytes(z4z5z6z7,z4,z5,z6,z7)
z8z9zAzB = xCxDxExF XOR @s5[z7] XOR @s6[z6] XOR @s7[z5] XOR @s8[z4] XOR @s5[x9]
unpack_bytes(z8z9zAzB,z8,z9,zA,zB)
zCzDzEzF = x4x5x6x7 XOR @s5[zA] XOR @s6[z9] XOR @s7[zB] XOR @s8[z8] XOR @s6[xB]
unpack_bytes(zCzDzEzF,zC,zD,zE,zF)
@k[0]  = @s5[z8] XOR @s6[z9] XOR @s7[z7] XOR @s8[z6] XOR @s5[z2]
@k[1]  = @s5[zA] XOR @s6[zB] XOR @s7[z5] XOR @s8[z4] XOR @s6[z6]
@k[2]  = @s5[zC] XOR @s6[zD] XOR @s7[z3] XOR @s8[z2] XOR @s7[z9]
@k[3]  = @s5[zE] XOR @s6[zF] XOR @s7[z1] XOR @s8[z0] XOR @s8[zC] 
x0x1x2x3 = z8z9zAzB XOR @s5[z5] XOR @s6[z7] XOR @s7[z4] XOR @s8[z6] XOR @s7[z0]
unpack_bytes(x0x1x2x3,x0,x1,x2,x3)
x4x5x6x7 = z0z1z2z3 XOR @s5[x0] XOR @s6[x2] XOR @s7[x1] XOR @s8[x3] XOR @s8[z2]
unpack_bytes(x4x5x6x7,x4,x5,x6,x7)
x8x9xAxB = z4z5z6z7 XOR @s5[x7] XOR @s6[x6] XOR @s7[x5] XOR @s8[x4] XOR @s5[z1]
unpack_bytes(x8x9xAxB,x8,x9,xA,xB)
xCxDxExF = zCzDzEzF XOR @s5[xA] XOR @s6[x9] XOR @s7[xB] XOR @s8[x8] XOR @s6[z3]
unpack_bytes(xCxDxExF,xC,xD,xE,xF)
@k[4]  = @s5[x3] XOR @s6[x2] XOR @s7[xC] XOR @s8[xD] XOR @s5[x8]
@k[5]  = @s5[x1] XOR @s6[x0] XOR @s7[xE] XOR @s8[xF] XOR @s6[xD]
@k[6]  = @s5[x7] XOR @s6[x6] XOR @s7[x8] XOR @s8[x9] XOR @s7[x3]
@k[7]  = @s5[x5] XOR @s6[x4] XOR @s7[xA] XOR @s8[xB] XOR @s8[x7] 
z0z1z2z3 = x0x1x2x3 XOR @s5[xD] XOR @s6[xF] XOR @s7[xC] XOR @s8[xE] XOR @s7[x8]
unpack_bytes(z0z1z2z3,z0,z1,z2,z3)
z4z5z6z7 = x8x9xAxB XOR @s5[z0] XOR @s6[z2] XOR @s7[z1] XOR @s8[z3] XOR @s8[xA]
unpack_bytes(z4z5z6z7,z4,z5,z6,z7)
z8z9zAzB = xCxDxExF XOR @s5[z7] XOR @s6[z6] XOR @s7[z5] XOR @s8[z4] XOR @s5[x9]
unpack_bytes(z8z9zAzB,z8,z9,zA,zB)
zCzDzEzF = x4x5x6x7 XOR @s5[zA] XOR @s6[z9] XOR @s7[zB] XOR @s8[z8] XOR @s6[xB]
unpack_bytes(zCzDzEzF,zC,zD,zE,zF)
@k[8]  = @s5[z3] XOR @s6[z2] XOR @s7[zC] XOR @s8[zD] XOR @s5[z9]
@k[9]  = @s5[z1] XOR @s6[z0] XOR @s7[zE] XOR @s8[zF] XOR @s6[zC]
@k[10] = @s5[z7] XOR @s6[z6] XOR @s7[z8] XOR @s8[z9] XOR @s7[z2]
@k[11] = @s5[z5] XOR @s6[z4] XOR @s7[zA] XOR @s8[zB] XOR @s8[z6] 
x0x1x2x3 = z8z9zAzB XOR @s5[z5] XOR @s6[z7] XOR @s7[z4] XOR @s8[z6] XOR @s7[z0]
unpack_bytes(x0x1x2x3,x0,x1,x2,x3)
x4x5x6x7 = z0z1z2z3 XOR @s5[x0] XOR @s6[x2] XOR @s7[x1] XOR @s8[x3] XOR @s8[z2]
unpack_bytes(x4x5x6x7,x4,x5,x6,x7)
x8x9xAxB = z4z5z6z7 XOR @s5[x7] XOR @s6[x6] XOR @s7[x5] XOR @s8[x4] XOR @s5[z1]
unpack_bytes(x8x9xAxB,x8,x9,xA,xB)
xCxDxExF = zCzDzEzF XOR @s5[xA] XOR @s6[x9] XOR @s7[xB] XOR @s8[x8] XOR @s6[z3]
unpack_bytes(xCxDxExF,xC,xD,xE,xF)
@k[12] = @s5[x8] XOR @s6[x9] XOR @s7[x7] XOR @s8[x6] XOR @s5[x3]
@k[13] = @s5[xA] XOR @s6[xB] XOR @s7[x5] XOR @s8[x4] XOR @s6[x7]
@k[14] = @s5[xC] XOR @s6[xD] XOR @s7[x3] XOR @s8[x2] XOR @s7[x8]
@k[15] = @s5[xE] XOR @s6[xF] XOR @s7[x1] XOR @s8[x0] XOR @s8[xD] 
z0z1z2z3 = x0x1x2x3 XOR @s5[xD] XOR @s6[xF] XOR @s7[xC] XOR @s8[xE] XOR @s7[x8]
unpack_bytes(z0z1z2z3,z0,z1,z2,z3)
z4z5z6z7 = x8x9xAxB XOR @s5[z0] XOR @s6[z2] XOR @s7[z1] XOR @s8[z3] XOR @s8[xA]
unpack_bytes(z4z5z6z7,z4,z5,z6,z7)
z8z9zAzB = xCxDxExF XOR @s5[z7] XOR @s6[z6] XOR @s7[z5] XOR @s8[z4] XOR @s5[x9]
unpack_bytes(z8z9zAzB,z8,z9,zA,zB)
zCzDzEzF = x4x5x6x7 XOR @s5[zA] XOR @s6[z9] XOR @s7[zB] XOR @s8[z8] XOR @s6[xB]
unpack_bytes(zCzDzEzF,zC,zD,zE,zF)
@k[16] = (@s5[z8] XOR @s6[z9] XOR @s7[z7] XOR @s8[z6] XOR @s5[z2]) AND &h1f
@k[17] = (@s5[zA] XOR @s6[zB] XOR @s7[z5] XOR @s8[z4] XOR @s6[z6]) AND &h1f
@k[18] = (@s5[zC] XOR @s6[zD] XOR @s7[z3] XOR @s8[z2] XOR @s7[z9]) AND &h1f
@k[19] = (@s5[zE] XOR @s6[zF] XOR @s7[z1] XOR @s8[z0] XOR @s8[zC]) AND &h1f 
x0x1x2x3 = z8z9zAzB XOR @s5[z5] XOR @s6[z7] XOR @s7[z4] XOR @s8[z6] XOR @s7[z0]
unpack_bytes(x0x1x2x3,x0,x1,x2,x3)
x4x5x6x7 = z0z1z2z3 XOR @s5[x0] XOR @s6[x2] XOR @s7[x1] XOR @s8[x3] XOR @s8[z2]
unpack_bytes(x4x5x6x7,x4,x5,x6,x7)
x8x9xAxB = z4z5z6z7 XOR @s5[x7] XOR @s6[x6] XOR @s7[x5] XOR @s8[x4] XOR @s5[z1]
unpack_bytes(x8x9xAxB,x8,x9,xA,xB)
xCxDxExF = zCzDzEzF XOR @s5[xA] XOR @s6[x9] XOR @s7[xB] XOR @s8[x8] XOR @s6[z3]
unpack_bytes(xCxDxExF,xC,xD,xE,xF)
@k[20] = (@s5[x3] XOR @s6[x2] XOR @s7[xC] XOR @s8[xD] XOR @s5[x8]) AND &h1f
@k[21] = (@s5[x1] XOR @s6[x0] XOR @s7[xE] XOR @s8[xF] XOR @s6[xD]) AND &h1f
@k[22] = (@s5[x7] XOR @s6[x6] XOR @s7[x8] XOR @s8[x9] XOR @s7[x3]) AND &h1f
@k[23] = (@s5[x5] XOR @s6[x4] XOR @s7[xA] XOR @s8[xB] XOR @s8[x7]) AND &h1f 
z0z1z2z3 = x0x1x2x3 XOR @s5[xD] XOR @s6[xF] XOR @s7[xC] XOR @s8[xE] XOR @s7[x8]
unpack_bytes(z0z1z2z3,z0,z1,z2,z3)
z4z5z6z7 = x8x9xAxB XOR @s5[z0] XOR @s6[z2] XOR @s7[z1] XOR @s8[z3] XOR @s8[xA]
unpack_bytes(z4z5z6z7,z4,z5,z6,z7)
z8z9zAzB = xCxDxExF XOR @s5[z7] XOR @s6[z6] XOR @s7[z5] XOR @s8[z4] XOR @s5[x9]
unpack_bytes(z8z9zAzB,z8,z9,zA,zB)
zCzDzEzF = x4x5x6x7 XOR @s5[zA] XOR @s6[z9] XOR @s7[zB] XOR @s8[z8] XOR @s6[xB]
unpack_bytes(zCzDzEzF,zC,zD,zE,zF)
@k[24] = (@s5[z3] XOR @s6[z2] XOR @s7[zC] XOR @s8[zD] XOR @s5[z9]) AND &h1f
@k[25] = (@s5[z1] XOR @s6[z0] XOR @s7[zE] XOR @s8[zF] XOR @s6[zC]) AND &h1f
@k[26] = (@s5[z7] XOR @s6[z6] XOR @s7[z8] XOR @s8[z9] XOR @s7[z2]) AND &h1f
@k[27] = (@s5[z5] XOR @s6[z4] XOR @s7[zA] XOR @s8[zB] XOR @s8[z6]) AND &h1f 
x0x1x2x3 = z8z9zAzB XOR @s5[z5] XOR @s6[z7] XOR @s7[z4] XOR @s8[z6] XOR @s7[z0]
unpack_bytes(x0x1x2x3,x0,x1,x2,x3)
x4x5x6x7 = z0z1z2z3 XOR @s5[x0] XOR @s6[x2] XOR @s7[x1] XOR @s8[x3] XOR @s8[z2]
unpack_bytes(x4x5x6x7,x4,x5,x6,x7)
x8x9xAxB = z4z5z6z7 XOR @s5[x7] XOR @s6[x6] XOR @s7[x5] XOR @s8[x4] XOR @s5[z1]
unpack_bytes(x8x9xAxB,x8,x9,xA,xB)
xCxDxExF = zCzDzEzF XOR @s5[xA] XOR @s6[x9] XOR @s7[xB] XOR @s8[x8] XOR @s6[z3]
unpack_bytes(xCxDxExF,xC,xD,xE,xF)
@k[28] = (@s5[x8] XOR @s6[x9] XOR @s7[x7] XOR @s8[x6] XOR @s5[x3]) AND &h1f
@k[29] = (@s5[xA] XOR @s6[xB] XOR @s7[x5] XOR @s8[x4] XOR @s6[x7]) AND &h1f
@k[30] = (@s5[xC] XOR @s6[xD] XOR @s7[x3] XOR @s8[x2] XOR @s7[x8]) AND &h1f
@k[31] = (@s5[xE] XOR @s6[xF] XOR @s7[x1] XOR @s8[x0] XOR @s8[xD]) AND &h1f 
'-- Burn the UserKey
poke$ Ctx.UserKey, zbs(Ctx.UserKeyLength)
function = -1  ' True on success
END FUNCTION 
'--------------------

MACRO f1(out_put,in_put,i)
t =       (@k[i] + in_put)
u =        @k[i+16]
! mov      ecx, u
! rol      t, cl
u =        @s_box[(0*256)+getbyte(t,3)]
u = (u XOR @s_box[(1*256)+getbyte(t,2)])
u = (u  -  @s_box[(2*256)+getbyte(t,1)])
u = (u  +  @s_box[(3*256)+getbyte(t,0)])
out_put = (out_put XOR u)
END MACRO 
'--------------------

MACRO f2(out_put,in_put,i)
t =       (@k[i] XOR in_put)
u =        @k[i+16]
! mov      ecx, u
! rol      t, cl
u =        @s_box[(0*256)+getbyte(t,3)]
u = (u  -  @s_box[(1*256)+getbyte(t,2)])
u = (u  +  @s_box[(2*256)+getbyte(t,1)])
u = (u XOR @s_box[(3*256)+getbyte(t,0)])
out_put = (out_put XOR u)
END MACRO 
'--------------------

MACRO f3(out_put,in_put,i)
t =       (@k[i] - in_put)
u =        @k[i+16]
! mov      ecx, u
! rol      t, cl
u =        @s_box[(0*256)+getbyte(t,3)]
u = (u  +  @s_box[(1*256)+getbyte(t,2)])
u = (u XOR @s_box[(2*256)+getbyte(t,1)])
u = (u  -  @s_box[(3*256)+getbyte(t,0)])
out_put = (out_put XOR u)
END MACRO 

'====================
FUNCTION EncryptBlock&(Ctx AS ENCRYPTION_CONTEXT)
LOCAL t&, u&, l&, r&, k AS LONG PTR, s_box AS LONG PTR
LOCAL retval&  ' for macro use
t = Ctx.@InBlock[0] : l = byte_reverse(t)
t = Ctx.@InBlock[1] : r = byte_reverse(t) 
'-- Local copies
k = Ctx.K : s_box = Ctx.S_Box 
f1(l,r,0)  : f2(r,l,1)  : f3(l,r,2)
f1(r,l,3)  : f2(l,r,4)  : f3(r,l,5)
f1(l,r,6)  : f2(r,l,7)  : f3(l,r,8)
f1(r,l,9)  : f2(l,r,10) : f3(r,l,11)
if Ctx.Rounds = %DEFAULT_ROUNDS then
   '-- Only if key length > 80 bits
   f1(l,r,12) : f2(r,l,13) : f3(l,r,14) : f1(r,l,15)
end if 
Ctx.@OutBlock[0] = byte_reverse(r)
Ctx.@OutBlock[1] = byte_reverse(l)
END FUNCTION 

'====================
FUNCTION DecryptBlock&(Ctx AS ENCRYPTION_CONTEXT)
LOCAL t&, u&, l&, r&, k AS LONG PTR, s_box AS LONG PTR
LOCAL retval&  ' for macro use 
t = Ctx.@InBlock[0] : l = byte_reverse(t)
t = Ctx.@InBlock[1] : r = byte_reverse(t) 
'-- Local copies
k = Ctx.K : s_box = Ctx.S_Box 
if Ctx.Rounds = %DEFAULT_ROUNDS then
   '-- Only if key length > 80 bits
   f1(l,r,15) : f3(r,l,14) : f2(l,r,13) : f1(r,l,12)
end if
f3(l,r,11) : f2(r,l,10) : f1(l,r,9)
f3(r,l,8)  : f2(l,r,7)  : f1(r,l,6)
f3(l,r,5)  : f2(r,l,4)  : f1(l,r,3)
f3(r,l,2)  : f2(l,r,1)  : f1(r,l,0) 
Ctx.@OutBlock[0] = byte_reverse(r)
Ctx.@OutBlock[1] = byte_reverse(l)
END FUNCTION 


'====================
SUB CAST128_Init(Ctx AS ENCRYPTION_CONTEXT)
Ctx.K_Buffer = zbs(%SUBKEY_SIZE*4)
Ctx.K        = varptr(Ctx.K_Buffer)
Ctx.S_Box    = codeptr(S_BOX1)
exit sub 
'-- CAST s-boxes
S_BOX1:
! DD  &h30FB40D4, &h9FA0FF0B, &h6BECCD2F, &h3F258C7A, &h1E213F2F, &h9C004DD3, &h6003E540, &hCF9FC949
! DD  &hBFD4AF27, &h88BBBDB5, &hE2034090, &h98D09675, &h6E63A0E0, &h15C361D2, &hC2E7661D, &h22D4FF8E
! DD  &h28683B6F, &hC07FD059, &hFF2379C8, &h775F50E2, &h43C340D3, &hDF2F8656, &h887CA41A, &hA2D2BD2D
! DD  &hA1C9E0D6, &h346C4819, &h61B76D87, &h22540F2F, &h2ABE32E1, &hAA54166B, &h22568E3A, &hA2D341D0
! DD  &h66DB40C8, &hA784392F, &h004DFF2F, &h2DB9D2DE, &h97943FAC, &h4A97C1D8, &h527644B7, &hB5F437A7
! DD  &hB82CBAEF, &hD751D159, &h6FF7F0ED, &h5A097A1F, &h827B68D0, &h90ECF52E, &h22B0C054, &hBC8E5935
! DD  &h4B6D2F7F, &h50BB64A2, &hD2664910, &hBEE5812D, &hB7332290, &hE93B159F, &hB48EE411, &h4BFF345D
! DD  &hFD45C240, &hAD31973F, &hC4F6D02E, &h55FC8165, &hD5B1CAAD, &hA1AC2DAE, &hA2D4B76D, &hC19B0C50
! DD  &h882240F2, &h0C6E4F38, &hA4E4BFD7, &h4F5BA272, &h564C1D2F, &hC59C5319, &hB949E354, &hB04669FE
! DD  &hB1B6AB8A, &hC71358DD, &h6385C545, &h110F935D, &h57538AD5, &h6A390493, &hE63D37E0, &h2A54F6B3
! DD  &h3A787D5F, &h6276A0B5, &h19A6FCDF, &h7A42206A, &h29F9D4D5, &hF61B1891, &hBB72275E, &hAA508167
! DD  &h38901091, &hC6B505EB, &h84C7CB8C, &h2AD75A0F, &h874A1427, &hA2D1936B, &h2AD286AF, &hAA56D291
! DD  &hD7894360, &h425C750D, &h93B39E26, &h187184C9, &h6C00B32D, &h73E2BB14, &hA0BEBC3C, &h54623779
! DD  &h64459EAB, &h3F328B82, &h7718CF82, &h59A2CEA6, &h04EE002E, &h89FE78E6, &h3FAB0950, &h325FF6C2
! DD  &h81383F05, &h6963C5C8, &h76CB5AD6, &hD49974C9, &hCA180DCF, &h380782D5, &hC7FA5CF6, &h8AC31511
! DD  &h35E79E13, &h47DA91D0, &hF40F9086, &hA7E2419E, &h31366241, &h051EF495, &hAA573B04, &h4A805D8D
! DD  &h548300D0, &h00322A3C, &hBF64CDDF, &hBA57A68E, &h75C6372B, &h50AFD341, &hA7C13275, &h915A0BF5
! DD  &h6B54BFAB, &h2B0B1426, &hAB4CC9D7, &h449CCD82, &hF7FBF265, &hAB85C5F3, &h1B55DB94, &hAAD4E324
! DD  &hCFA4BD3F, &h2DEAA3E2, &h9E204D02, &hC8BD25AC, &hEADF55B3, &hD5BD9E98, &hE31231B2, &h2AD5AD6C
! DD  &h954329DE, &hADBE4528, &hD8710F69, &hAA51C90F, &hAA786BF6, &h22513F1E, &hAA51A79B, &h2AD344CC
! DD  &h7B5A41F0, &hD37CFBAD, &h1B069505, &h41ECE491, &hB4C332E6, &h032268D4, &hC9600ACC, &hCE387E6D
! DD  &hBF6BB16C, &h6A70FB78, &h0D03D9C9, &hD4DF39DE, &hE01063DA, &h4736F464, &h5AD328D8, &hB347CC96
! DD  &h75BB0FC3, &h98511BFB, &h4FFBCC35, &hB58BCF6A, &hE11F0ABC, &hBFC5FE4A, &hA70AEC10, &hAC39570A
! DD  &h3F04442F, &h6188B153, &hE0397A2E, &h5727CB79, &h9CEB418F, &h1CACD68D, &h2AD37C96, &h0175CB9D
! DD  &hC69DFF09, &hC75B65F0, &hD9DB40D8, &hEC0E7779, &h4744EAD4, &hB11C3274, &hDD24CB9E, &h7E1C54BD
! DD  &hF01144F9, &hD2240EB1, &h9675B3FD, &hA3AC3755, &hD47C27AF, &h51C85F4D, &h56907596, &hA5BB15E6
! DD  &h580304F0, &hCA042CF1, &h011A37EA, &h8DBFAADB, &h35BA3E4A, &h3526FFA0, &hC37B4D09, &hBC306ED9
! DD  &h98A52666, &h5648F725, &hFF5E569D, &h0CED63D0, &h7C63B2CF, &h700B45E1, &hD5EA50F1, &h85A92872
! DD  &hAF1FBDA7, &hD4234870, &hA7870BF3, &h2D3B4D79, &h42E04198, &h0CD0EDE7, &h26470DB8, &hF881814C
! DD  &h474D6AD7, &h7C0C5E5C, &hD1231959, &h381B7298, &hF5D2F4DB, &hAB838653, &h6E2F1E23, &h83719C9E
! DD  &hBD91E046, &h9A56456E, &hDC39200C, &h20C8C571, &h962BDA1C, &hE1E696FF, &hB141AB08, &h7CCA89B9
! DD  &h1A69E783, &h02CC4843, &hA2F7C579, &h429EF47D, &h427B169C, &h5AC9F049, &hDD8F0F00, &h5C8165BF 
S_BOX2:
! DD  &h1F201094, &hEF0BA75B, &h69E3CF7E, &h393F4380, &hFE61CF7A, &hEEC5207A, &h55889C94, &h72FC0651
! DD  &hADA7EF79, &h4E1D7235, &hD55A63CE, &hDE0436BA, &h99C430EF, &h5F0C0794, &h18DCDB7D, &hA1D6EFF3
! DD  &hA0B52F7B, &h59E83605, &hEE15B094, &hE9FFD909, &hDC440086, &hEF944459, &hBA83CCB3, &hE0C3CDFB
! DD  &hD1DA4181, &h3B092AB1, &hF997F1C1, &hA5E6CF7B, &h01420DDB, &hE4E7EF5B, &h25A1FF41, &hE180F806
! DD  &h1FC41080, &h179BEE7A, &hD37AC6A9, &hFE5830A4, &h98DE8B7F, &h77E83F4E, &h79929269, &h24FA9F7B
! DD  &hE113C85B, &hACC40083, &hD7503525, &hF7EA615F, &h62143154, &h0D554B63, &h5D681121, &hC866C359
! DD  &h3D63CF73, &hCEE234C0, &hD4D87E87, &h5C672B21, &h071F6181, &h39F7627F, &h361E3084, &hE4EB573B
! DD  &h602F64A4, &hD63ACD9C, &h1BBC4635, &h9E81032D, &h2701F50C, &h99847AB4, &hA0E3DF79, &hBA6CF38C
! DD  &h10843094, &h2537A95E, &hF46F6FFE, &hA1FF3B1F, &h208CFB6A, &h8F458C74, &hD9E0A227, &h4EC73A34
! DD  &hFC884F69, &h3E4DE8DF, &hEF0E0088, &h3559648D, &h8A45388C, &h1D804366, &h721D9BFD, &hA58684BB
! DD  &hE8256333, &h844E8212, &h128D8098, &hFED33FB4, &hCE280AE1, &h27E19BA5, &hD5A6C252, &hE49754BD
! DD  &hC5D655DD, &hEB667064, &h77840B4D, &hA1B6A801, &h84DB26A9, &hE0B56714, &h21F043B7, &hE5D05860
! DD  &h54F03084, &h066FF472, &hA31AA153, &hDADC4755, &hB5625DBF, &h68561BE6, &h83CA6B94, &h2D6ED23B
! DD  &hECCF01DB, &hA6D3D0BA, &hB6803D5C, &hAF77A709, &h33B4A34C, &h397BC8D6, &h5EE22B95, &h5F0E5304
! DD  &h81ED6F61, &h20E74364, &hB45E1378, &hDE18639B, &h881CA122, &hB96726D1, &h8049A7E8, &h22B7DA7B
! DD  &h5E552D25, &h5272D237, &h79D2951C, &hC60D894C, &h488CB402, &h1BA4FE5B, &hA4B09F6B, &h1CA815CF
! DD  &hA20C3005, &h8871DF63, &hB9DE2FCB, &h0CC6C9E9, &h0BEEFF53, &hE3214517, &hB4542835, &h9F63293C
! DD  &hEE41E729, &h6E1D2D7C, &h50045286, &h1E6685F3, &hF33401C6, &h30A22C95, &h31A70850, &h60930F13
! DD  &h73F98417, &hA1269859, &hEC645C44, &h52C877A9, &hCDFF33A6, &hA02B1741, &h7CBAD9A2, &h2180036F
! DD  &h50D99C08, &hCB3F4861, &hC26BD765, &h64A3F6AB, &h80342676, &h25A75E7B, &hE4E6D1FC, &h20C710E6
! DD  &hCDF0B680, &h17844D3B, &h31EEF84D, &h7E0824E4, &h2CCB49EB, &h846A3BAE, &h8FF77888, &hEE5D60F6
! DD  &h7AF75673, &h2FDD5CDB, &hA11631C1, &h30F66F43, &hB3FAEC54, &h157FD7FA, &hEF8579CC, &hD152DE58
! DD  &hDB2FFD5E, &h8F32CE19, &h306AF97A, &h02F03EF8, &h99319AD5, &hC242FA0F, &hA7E3EBB0, &hC68E4906
! DD  &hB8DA230C, &h80823028, &hDCDEF3C8, &hD35FB171, &h088A1BC8, &hBEC0C560, &h61A3C9E8, &hBCA8F54D
! DD  &hC72FEFFA, &h22822E99, &h82C570B4, &hD8D94E89, &h8B1C34BC, &h301E16E6, &h273BE979, &hB0FFEAA6
! DD  &h61D9B8C6, &h00B24869, &hB7FFCE3F, &h08DC283B, &h43DAF65A, &hF7E19798, &h7619B72F, &h8F1C9BA4
! DD  &hDC8637A0, &h16A7D3B1, &h9FC393B7, &hA7136EEB, &hC6BCC63E, &h1A513742, &hEF6828BC, &h520365D6
! DD  &h2D6A77AB, &h3527ED4B, &h821FD216, &h095C6E2E, &hDB92F2FB, &h5EEA29CB, &h145892F5, &h91584F7F
! DD  &h5483697B, &h2667A8CC, &h85196048, &h8C4BACEA, &h833860D4, &h0D23E0F9, &h6C387E8A, &h0AE6D249
! DD  &hB284600C, &hD835731D, &hDCB1C647, &hAC4C56EA, &h3EBD81B3, &h230EABB0, &h6438BC87, &hF0B5B1FA
! DD  &h8F5EA2B3, &hFC184642, &h0A036B7A, &h4FB089BD, &h649DA589, &hA345415E, &h5C038323, &h3E5D3BB9
! DD  &h43D79572, &h7E6DD07C, &h06DFDF1E, &h6C6CC4EF, &h7160A539, &h73BFBE70, &h83877605, &h4523ECF1 
S_BOX3:
! DD  &h8DEFC240, &h25FA5D9F, &hEB903DBF, &hE810C907, &h47607FFF, &h369FE44B, &h8C1FC644, &hAECECA90
! DD  &hBEB1F9BF, &hEEFBCAEA, &hE8CF1950, &h51DF07AE, &h920E8806, &hF0AD0548, &hE13C8D83, &h927010D5
! DD  &h11107D9F, &h07647DB9, &hB2E3E4D4, &h3D4F285E, &hB9AFA820, &hFADE82E0, &hA067268B, &h8272792E
! DD  &h553FB2C0, &h489AE22B, &hD4EF9794, &h125E3FBC, &h21FFFCEE, &h825B1BFD, &h9255C5ED, &h1257A240
! DD  &h4E1A8302, &hBAE07FFF, &h528246E7, &h8E57140E, &h3373F7BF, &h8C9F8188, &hA6FC4EE8, &hC982B5A5
! DD  &hA8C01DB7, &h579FC264, &h67094F31, &hF2BD3F5F, &h40FFF7C1, &h1FB78DFC, &h8E6BD2C1, &h437BE59B
! DD  &h99B03DBF, &hB5DBC64B, &h638DC0E6, &h55819D99, &hA197C81C, &h4A012D6E, &hC5884A28, &hCCC36F71
! DD  &hB843C213, &h6C0743F1, &h8309893C, &h0FEDDD5F, &h2F7FE850, &hD7C07F7E, &h02507FBF, &h5AFB9A04
! DD  &hA747D2D0, &h1651192E, &hAF70BF3E, &h58C31380, &h5F98302E, &h727CC3C4, &h0A0FB402, &h0F7FEF82
! DD  &h8C96FDAD, &h5D2C2AAE, &h8EE99A49, &h50DA88B8, &h8427F4A0, &h1EAC5790, &h796FB449, &h8252DC15
! DD  &hEFBD7D9B, &hA672597D, &hADA840D8, &h45F54504, &hFA5D7403, &hE83EC305, &h4F91751A, &h925669C2
! DD  &h23EFE941, &hA903F12E, &h60270DF2, &h0276E4B6, &h94FD6574, &h927985B2, &h8276DBCB, &h02778176
! DD  &hF8AF918D, &h4E48F79E, &h8F616DDF, &hE29D840E, &h842F7D83, &h340CE5C8, &h96BBB682, &h93B4B148
! DD  &hEF303CAB, &h984FAF28, &h779FAF9B, &h92DC560D, &h224D1E20, &h8437AA88, &h7D29DC96, &h2756D3DC
! DD  &h8B907CEE, &hB51FD240, &hE7C07CE3, &hE566B4A1, &hC3E9615E, &h3CF8209D, &h6094D1E3, &hCD9CA341
! DD  &h5C76460E, &h00EA983B, &hD4D67881, &hFD47572C, &hF76CEDD9, &hBDA8229C, &h127DADAA, &h438A074E
! DD  &h1F97C090, &h081BDB8A, &h93A07EBE, &hB938CA15, &h97B03CFF, &h3DC2C0F8, &h8D1AB2EC, &h64380E51
! DD  &h68CC7BFB, &hD90F2788, &h12490181, &h5DE5FFD4, &hDD7EF86A, &h76A2E214, &hB9A40368, &h925D958F
! DD  &h4B39FFFA, &hBA39AEE9, &hA4FFD30B, &hFAF7933B, &h6D498623, &h193CBCFA, &h27627545, &h825CF47A
! DD  &h61BD8BA0, &hD11E42D1, &hCEAD04F4, &h127EA392, &h10428DB7, &h8272A972, &h9270C4A8, &h127DE50B
! DD  &h285BA1C8, &h3C62F44F, &h35C0EAA5, &hE805D231, &h428929FB, &hB4FCDF82, &h4FB66A53, &h0E7DC15B
! DD  &h1F081FAB, &h108618AE, &hFCFD086D, &hF9FF2889, &h694BCC11, &h236A5CAE, &h12DECA4D, &h2C3F8CC5
! DD  &hD2D02DFE, &hF8EF5896, &hE4CF52DA, &h95155B67, &h494A488C, &hB9B6A80C, &h5C8F82BC, &h89D36B45
! DD  &h3A609437, &hEC00C9A9, &h44715253, &h0A874B49, &hD773BC40, &h7C34671C, &h02717EF6, &h4FEB5536
! DD  &hA2D02FFF, &hD2BF60C4, &hD43F03C0, &h50B4EF6D, &h07478CD1, &h006E1888, &hA2E53F55, &hB9E6D4BC
! DD  &hA2048016, &h97573833, &hD7207D67, &hDE0F8F3D, &h72F87B33, &hABCC4F33, &h7688C55D, &h7B00A6B0
! DD  &h947B0001, &h570075D2, &hF9BB88F8, &h8942019E, &h4264A5FF, &h856302E0, &h72DBD92B, &hEE971B69
! DD  &h6EA22FDE, &h5F08AE2B, &hAF7A616D, &hE5C98767, &hCF1FEBD2, &h61EFC8C2, &hF1AC2571, &hCC8239C2
! DD  &h67214CB8, &hB1E583D1, &hB7DC3E62, &h7F10BDCE, &hF90A5C38, &h0FF0443D, &h606E6DC6, &h60543A49
! DD  &h5727C148, &h2BE98A1D, &h8AB41738, &h20E1BE24, &hAF96DA0F, &h68458425, &h99833BE5, &h600D457D
! DD  &h282F9350, &h8334B362, &hD91D1120, &h2B6D8DA0, &h642B1E31, &h9C305A00, &h52BCE688, &h1B03588A
! DD  &hF7BAEFD5, &h4142ED9C, &hA4315C11, &h83323EC5, &hDFEF4636, &hA133C501, &hE9D3531C, &hEE353783 
S_BOX4:
! DD  &h9DB30420, &h1FB6E9DE, &hA7BE7BEF, &hD273A298, &h4A4F7BDB, &h64AD8C57, &h85510443, &hFA020ED1
! DD  &h7E287AFF, &hE60FB663, &h095F35A1, &h79EBF120, &hFD059D43, &h6497B7B1, &hF3641F63, &h241E4ADF
! DD  &h28147F5F, &h4FA2B8CD, &hC9430040, &h0CC32220, &hFDD30B30, &hC0A5374F, &h1D2D00D9, &h24147B15
! DD  &hEE4D111A, &h0FCA5167, &h71FF904C, &h2D195FFE, &h1A05645F, &h0C13FEFE, &h081B08CA, &h05170121
! DD  &h80530100, &hE83E5EFE, &hAC9AF4F8, &h7FE72701, &hD2B8EE5F, &h06DF4261, &hBB9E9B8A, &h7293EA25
! DD  &hCE84FFDF, &hF5718801, &h3DD64B04, &hA26F263B, &h7ED48400, &h547EEBE6, &h446D4CA0, &h6CF3D6F5
! DD  &h2649ABDF, &hAEA0C7F5, &h36338CC1, &h503F7E93, &hD3772061, &h11B638E1, &h72500E03, &hF80EB2BB
! DD  &hABE0502E, &hEC8D77DE, &h57971E81, &hE14F6746, &hC9335400, &h6920318F, &h081DBB99, &hFFC304A5
! DD  &h4D351805, &h7F3D5CE3, &hA6C866C6, &h5D5BCCA9, &hDAEC6FEA, &h9F926F91, &h9F46222F, &h3991467D
! DD  &hA5BF6D8E, &h1143C44F, &h43958302, &hD0214EEB, &h022083B8, &h3FB6180C, &h18F8931E, &h281658E6
! DD  &h26486E3E, &h8BD78A70, &h7477E4C1, &hB506E07C, &hF32D0A25, &h79098B02, &hE4EABB81, &h28123B23
! DD  &h69DEAD38, &h1574CA16, &hDF871B62, &h211C40B7, &hA51A9EF9, &h0014377B, &h041E8AC8, &h09114003
! DD  &hBD59E4D2, &hE3D156D5, &h4FE876D5, &h2F91A340, &h557BE8DE, &h00EAE4A7, &h0CE5C2EC, &h4DB4BBA6
! DD  &hE756BDFF, &hDD3369AC, &hEC17B035, &h06572327, &h99AFC8B0, &h56C8C391, &h6B65811C, &h5E146119
! DD  &h6E85CB75, &hBE07C002, &hC2325577, &h893FF4EC, &h5BBFC92D, &hD0EC3B25, &hB7801AB7, &h8D6D3B24
! DD  &h20C763EF, &hC366A5FC, &h9C382880, &h0ACE3205, &hAAC9548A, &hECA1D7C7, &h041AFA32, &h1D16625A
! DD  &h6701902C, &h9B757A54, &h31D477F7, &h9126B031, &h36CC6FDB, &hC70B8B46, &hD9E66A48, &h56E55A79
! DD  &h026A4CEB, &h52437EFF, &h2F8F76B4, &h0DF980A5, &h8674CDE3, &hEDDA04EB, &h17A9BE04, &h2C18F4DF
! DD  &hB7747F9D, &hAB2AF7B4, &hEFC34D20, &h2E096B7C, &h1741A254, &hE5B6A035, &h213D42F6, &h2C1C7C26
! DD  &h61C2F50F, &h6552DAF9, &hD2C231F8, &h25130F69, &hD8167FA2, &h0418F2C8, &h001A96A6, &h0D1526AB
! DD  &h63315C21, &h5E0A72EC, &h49BAFEFD, &h187908D9, &h8D0DBD86, &h311170A7, &h3E9B640C, &hCC3E10D7
! DD  &hD5CAD3B6, &h0CAEC388, &hF73001E1, &h6C728AFF, &h71EAE2A1, &h1F9AF36E, &hCFCBD12F, &hC1DE8417
! DD  &hAC07BE6B, &hCB44A1D8, &h8B9B0F56, &h013988C3, &hB1C52FCA, &hB4BE31CD, &hD8782806, &h12A3A4E2
! DD  &h6F7DE532, &h58FD7EB6, &hD01EE900, &h24ADFFC2, &hF4990FC5, &h9711AAC5, &h001D7B95, &h82E5E7D2
! DD  &h109873F6, &h00613096, &hC32D9521, &hADA121FF, &h29908415, &h7FBB977F, &hAF9EB3DB, &h29C9ED2A
! DD  &h5CE2A465, &hA730F32C, &hD0AA3FE8, &h8A5CC091, &hD49E2CE7, &h0CE454A9, &hD60ACD86, &h015F1919
! DD  &h77079103, &hDEA03AF6, &h78A8565E, &hDEE356DF, &h21F05CBE, &h8B75E387, &hB3C50651, &hB8A5C3EF
! DD  &hD8EEB6D2, &hE523BE77, &hC2154529, &h2F69EFDF, &hAFE67AFB, &hF470C4B2, &hF3E0EB5B, &hD6CC9876
! DD  &h39E4460C, &h1FDA8538, &h1987832F, &hCA007367, &hA99144F8, &h296B299E, &h492FC295, &h9266BEAB
! DD  &hB5676E69, &h9BD3DDDA, &hDF7E052F, &hDB25701C, &h1B5E51EE, &hF65324E6, &h6AFCE36C, &h0316CC04
! DD  &h8644213E, &hB7DC59D0, &h7965291F, &hCCD6FD43, &h41823979, &h932BCDF6, &hB657C34D, &h4EDFD282
! DD  &h7AE5290C, &h3CB9536B, &h851E20FE, &h9833557E, &h13ECF0B0, &hD3FFB372, &h3F85C5C1, &h0AEF7ED2 
S_BOX5:
! DD  &h7ec90c04, &h2c6e74b9, &h9b0e66df, &ha6337911, &hb86a7fff, &h1dd358f5, &h44dd9d44, &h1731167f
! DD  &h08fbf1fa, &he7f511cc, &hd2051b00, &h735aba00, &h2ab722d8, &h386381cb, &hacf6243a, &h69befd7a
! DD  &he6a2e77f, &hf0c720cd, &hc4494816, &hccf5c180, &h38851640, &h15b0a848, &he68b18cb, &h4caadeff
! DD  &h5f480a01, &h0412b2aa, &h259814fc, &h41d0efe2, &h4e40b48d, &h248eb6fb, &h8dba1cfe, &h41a99b02
! DD  &h1a550a04, &hba8f65cb, &h7251f4e7, &h95a51725, &hc106ecd7, &h97a5980a, &hc539b9aa, &h4d79fe6a
! DD  &hf2f3f763, &h68af8040, &hed0c9e56, &h11b4958b, &he1eb5a88, &h8709e6b0, &hd7e07156, &h4e29fea7
! DD  &h6366e52d, &h02d1c000, &hc4ac8e05, &h9377f571, &h0c05372a, &h578535f2, &h2261be02, &hd642a0c9
! DD  &hdf13a280, &h74b55bd2, &h682199c0, &hd421e5ec, &h53fb3ce8, &hc8adedb3, &h28a87fc9, &h3d959981
! DD  &h5c1ff900, &hfe38d399, &h0c4eff0b, &h062407ea, &haa2f4fb1, &h4fb96976, &h90c79505, &hb0a8a774
! DD  &hef55a1ff, &he59ca2c2, &ha6b62d27, &he66a4263, &hdf65001f, &h0ec50966, &hdfdd55bc, &h29de0655
! DD  &h911e739a, &h17af8975, &h32c7911c, &h89f89468, &h0d01e980, &h524755f4, &h03b63cc9, &h0cc844b2
! DD  &hbcf3f0aa, &h87ac36e9, &he53a7426, &h01b3d82b, &h1a9e7449, &h64ee2d7e, &hcddbb1da, &h01c94910
! DD  &hb868bf80, &h0d26f3fd, &h9342ede7, &h04a5c284, &h636737b6, &h50f5b616, &hf24766e3, &h8eca36c1
! DD  &h136e05db, &hfef18391, &hfb887a37, &hd6e7f7d4, &hc7fb7dc9, &h3063fcdf, &hb6f589de, &hec2941da
! DD  &h26e46695, &hb7566419, &hf654efc5, &hd08d58b7, &h48925401, &hc1bacb7f, &he5ff550f, &hb6083049
! DD  &h5bb5d0e8, &h87d72e5a, &hab6a6ee1, &h223a66ce, &hc62bf3cd, &h9e0885f9, &h68cb3e47, &h086c010f
! DD  &ha21de820, &hd18b69de, &hf3f65777, &hfa02c3f6, &h407edac3, &hcbb3d550, &h1793084d, &hb0d70eba
! DD  &h0ab378d5, &hd951fb0c, &hded7da56, &h4124bbe4, &h94ca0b56, &h0f5755d1, &he0e1e56e, &h6184b5be
! DD  &h580a249f, &h94f74bc0, &he327888e, &h9f7b5561, &hc3dc0280, &h05687715, &h646c6bd7, &h44904db3
! DD  &h66b4f0a3, &hc0f1648a, &h697ed5af, &h49e92ff6, &h309e374f, &h2cb6356a, &h85808573, &h4991f840
! DD  &h76f0ae02, &h083be84d, &h28421c9a, &h44489406, &h736e4cb8, &hc1092910, &h8bc95fc6, &h7d869cf4
! DD  &h134f616f, &h2e77118d, &hb31b2be1, &haa90b472, &h3ca5d717, &h7d161bba, &h9cad9010, &haf462ba2
! DD  &h9fe459d2, &h45d34559, &hd9f2da13, &hdbc65487, &hf3e4f94e, &h176d486f, &h097c13ea, &h631da5c7
! DD  &h445f7382, &h175683f4, &hcdc66a97, &h70be0288, &hb3cdcf72, &h6e5dd2f3, &h20936079, &h459b80a5
! DD  &hbe60e2db, &ha9c23101, &heba5315c, &h224e42f2, &h1c5c1572, &hf6721b2c, &h1ad2fff3, &h8c25404e
! DD  &h324ed72f, &h4067b7fd, &h0523138e, &h5ca3bc78, &hdc0fd66e, &h75922283, &h784d6b17, &h58ebb16e
! DD  &h44094f85, &h3f481d87, &hfcfeae7b, &h77b5ff76, &h8c2302bf, &haaf47556, &h5f46b02a, &h2b092801
! DD  &h3d38f5f7, &h0ca81f36, &h52af4a8a, &h66d5e7c0, &hdf3b0874, &h95055110, &h1b5ad7a8, &hf61ed5ad
! DD  &h6cf6e479, &h20758184, &hd0cefa65, &h88f7be58, &h4a046826, &h0ff6f8f3, &ha09c7f70, &h5346aba0
! DD  &h5ce96c28, &he176eda3, &h6bac307f, &h376829d2, &h85360fa9, &h17e3fe2a, &h24b79767, &hf5a96b20
! DD  &hd6cd2595, &h68ff1ebf, &h7555442c, &hf19f06be, &hf9e0659a, &heeb9491d, &h34010718, &hbb30cab8
! DD  &he822fe15, &h88570983, &h750e6249, &hda627e55, &h5e76ffa8, &hb1534546, &h6d47de08, &hefe9e7d4 
S_BOX6:
! DD  &hf6fa8f9d, &h2cac6ce1, &h4ca34867, &he2337f7c, &h95db08e7, &h016843b4, &heced5cbc, &h325553ac
! DD  &hbf9f0960, &hdfa1e2ed, &h83f0579d, &h63ed86b9, &h1ab6a6b8, &hde5ebe39, &hf38ff732, &h8989b138
! DD  &h33f14961, &hc01937bd, &hf506c6da, &he4625e7e, &ha308ea99, &h4e23e33c, &h79cbd7cc, &h48a14367
! DD  &ha3149619, &hfec94bd5, &ha114174a, &heaa01866, &ha084db2d, &h09a8486f, &ha888614a, &h2900af98
! DD  &h01665991, &he1992863, &hc8f30c60, &h2e78ef3c, &hd0d51932, &hcf0fec14, &hf7ca07d2, &hd0a82072
! DD  &hfd41197e, &h9305a6b0, &he86be3da, &h74bed3cd, &h372da53c, &h4c7f4448, &hdab5d440, &h6dba0ec3
! DD  &h083919a7, &h9fbaeed9, &h49dbcfb0, &h4e670c53, &h5c3d9c01, &h64bdb941, &h2c0e636a, &hba7dd9cd
! DD  &hea6f7388, &he70bc762, &h35f29adb, &h5c4cdd8d, &hf0d48d8c, &hb88153e2, &h08a19866, &h1ae2eac8
! DD  &h284caf89, &haa928223, &h9334be53, &h3b3a21bf, &h16434be3, &h9aea3906, &hefe8c36e, &hf890cdd9
! DD  &h80226dae, &hc340a4a3, &hdf7e9c09, &ha694a807, &h5b7c5ecc, &h221db3a6, &h9a69a02f, &h68818a54
! DD  &hceb2296f, &h53c0843a, &hfe893655, &h25bfe68a, &hb4628abc, &hcf222ebf, &h25ac6f48, &ha9a99387
! DD  &h53bddb65, &he76ffbe7, &he967fd78, &h0ba93563, &h8e342bc1, &he8a11be9, &h4980740d, &hc8087dfc
! DD  &h8de4bf99, &ha11101a0, &h7fd37975, &hda5a26c0, &he81f994f, &h9528cd89, &hfd339fed, &hb87834bf
! DD  &h5f04456d, &h22258698, &hc9c4c83b, &h2dc156be, &h4f628daa, &h57f55ec5, &he2220abe, &hd2916ebf
! DD  &h4ec75b95, &h24f2c3c0, &h42d15d99, &hcd0d7fa0, &h7b6e27ff, &ha8dc8af0, &h7345c106, &hf41e232f
! DD  &h35162386, &he6ea8926, &h3333b094, &h157ec6f2, &h372b74af, &h692573e4, &he9a9d848, &hf3160289
! DD  &h3a62ef1d, &ha787e238, &hf3a5f676, &h74364853, &h20951063, &h4576698d, &hb6fad407, &h592af950
! DD  &h36f73523, &h4cfb6e87, &h7da4cec0, &h6c152daa, &hcb0396a8, &hc50dfe5d, &hfcd707ab, &h0921c42f
! DD  &h89dff0bb, &h5fe2be78, &h448f4f33, &h754613c9, &h2b05d08d, &h48b9d585, &hdc049441, &hc8098f9b
! DD  &h7dede786, &hc39a3373, &h42410005, &h6a091751, &h0ef3c8a6, &h890072d6, &h28207682, &ha9a9f7be
! DD  &hbf32679d, &hd45b5b75, &hb353fd00, &hcbb0e358, &h830f220a, &h1f8fb214, &hd372cf08, &hcc3c4a13
! DD  &h8cf63166, &h061c87be, &h88c98f88, &h6062e397, &h47cf8e7a, &hb6c85283, &h3cc2acfb, &h3fc06976
! DD  &h4e8f0252, &h64d8314d, &hda3870e3, &h1e665459, &hc10908f0, &h513021a5, &h6c5b68b7, &h822f8aa0
! DD  &h3007cd3e, &h74719eef, &hdc872681, &h073340d4, &h7e432fd9, &h0c5ec241, &h8809286c, &hf592d891
! DD  &h08a930f6, &h957ef305, &hb7fbffbd, &hc266e96f, &h6fe4ac98, &hb173ecc0, &hbc60b42a, &h953498da
! DD  &hfba1ae12, &h2d4bd736, &h0f25faab, &ha4f3fceb, &he2969123, &h257f0c3d, &h9348af49, &h361400bc
! DD  &he8816f4a, &h3814f200, &ha3f94043, &h9c7a54c2, &hbc704f57, &hda41e7f9, &hc25ad33a, &h54f4a084
! DD  &hb17f5505, &h59357cbe, &hedbd15c8, &h7f97c5ab, &hba5ac7b5, &hb6f6deaf, &h3a479c3a, &h5302da25
! DD  &h653d7e6a, &h54268d49, &h51a477ea, &h5017d55b, &hd7d25d88, &h44136c76, &h0404a8c8, &hb8e5a121
! DD  &hb81a928a, &h60ed5869, &h97c55b96, &heaec991b, &h29935913, &h01fdb7f1, &h088e8dfa, &h9ab6f6f5
! DD  &h3b4cbf9f, &h4a5de3ab, &he6051d35, &ha0e1d855, &hd36b4cf1, &hf544edeb, &hb0e93524, &hbebb8fbd
! DD  &ha2d762cf, &h49c92f54, &h38b5f331, &h7128a454, &h48392905, &ha65b1db8, &h851c97bd, &hd675cf2f 
S_BOX7:
! DD  &h85e04019, &h332bf567, &h662dbfff, &hcfc65693, &h2a8d7f6f, &hab9bc912, &hde6008a1, &h2028da1f
! DD  &h0227bce7, &h4d642916, &h18fac300, &h50f18b82, &h2cb2cb11, &hb232e75c, &h4b3695f2, &hb28707de
! DD  &ha05fbcf6, &hcd4181e9, &he150210c, &he24ef1bd, &hb168c381, &hfde4e789, &h5c79b0d8, &h1e8bfd43
! DD  &h4d495001, &h38be4341, &h913cee1d, &h92a79c3f, &h089766be, &hbaeeadf4, &h1286becf, &hb6eacb19
! DD  &h2660c200, &h7565bde4, &h64241f7a, &h8248dca9, &hc3b3ad66, &h28136086, &h0bd8dfa8, &h356d1cf2
! DD  &h107789be, &hb3b2e9ce, &h0502aa8f, &h0bc0351e, &h166bf52a, &heb12ff82, &he3486911, &hd34d7516
! DD  &h4e7b3aff, &h5f43671b, &h9cf6e037, &h4981ac83, &h334266ce, &h8c9341b7, &hd0d854c0, &hcb3a6c88
! DD  &h47bc2829, &h4725ba37, &ha66ad22b, &h7ad61f1e, &h0c5cbafa, &h4437f107, &hb6e79962, &h42d2d816
! DD  &h0a961288, &he1a5c06e, &h13749e67, &h72fc081a, &hb1d139f7, &hf9583745, &hcf19df58, &hbec3f756
! DD  &hc06eba30, &h07211b24, &h45c28829, &hc95e317f, &hbc8ec511, &h38bc46e9, &hc6e6fa14, &hbae8584a
! DD  &had4ebc46, &h468f508b, &h7829435f, &hf124183b, &h821dba9f, &haff60ff4, &hea2c4e6d, &h16e39264
! DD  &h92544a8b, &h009b4fc3, &haba68ced, &h9ac96f78, &h06a5b79a, &hb2856e6e, &h1aec3ca9, &hbe838688
! DD  &h0e0804e9, &h55f1be56, &he7e5363b, &hb3a1f25d, &hf7debb85, &h61fe033c, &h16746233, &h3c034c28
! DD  &hda6d0c74, &h79aac56c, &h3ce4e1ad, &h51f0c802, &h98f8f35a, &h1626a49f, &heed82b29, &h1d382fe3
! DD  &h0c4fb99a, &hbb325778, &h3ec6d97b, &h6e77a6a9, &hcb658b5c, &hd45230c7, &h2bd1408b, &h60c03eb7
! DD  &hb9068d78, &ha33754f4, &hf430c87d, &hc8a71302, &hb96d8c32, &hebd4e7be, &hbe8b9d2d, &h7979fb06
! DD  &he7225308, &h8b75cf77, &h11ef8da4, &he083c858, &h8d6b786f, &h5a6317a6, &hfa5cf7a0, &h5dda0033
! DD  &hf28ebfb0, &hf5b9c310, &ha0eac280, &h08b9767a, &ha3d9d2b0, &h79d34217, &h021a718d, &h9ac6336a
! DD  &h2711fd60, &h438050e3, &h069908a8, &h3d7fedc4, &h826d2bef, &h4eeb8476, &h488dcf25, &h36c9d566
! DD  &h28e74e41, &hc2610aca, &h3d49a9cf, &hbae3b9df, &hb65f8de6, &h92aeaf64, &h3ac7d5e6, &h9ea80509
! DD  &hf22b017d, &ha4173f70, &hdd1e16c3, &h15e0d7f9, &h50b1b887, &h2b9f4fd5, &h625aba82, &h6a017962
! DD  &h2ec01b9c, &h15488aa9, &hd716e740, &h40055a2c, &h93d29a22, &he32dbf9a, &h058745b9, &h3453dc1e
! DD  &hd699296e, &h496cff6f, &h1c9f4986, &hdfe2ed07, &hb87242d1, &h19de7eae, &h053e561a, &h15ad6f8c
! DD  &h66626c1c, &h7154c24c, &hea082b2a, &h93eb2939, &h17dcb0f0, &h58d4f2ae, &h9ea294fb, &h52cf564c
! DD  &h9883fe66, &h2ec40581, &h763953c3, &h01d6692e, &hd3a0c108, &ha1e7160e, &he4f2dfa6, &h693ed285
! DD  &h74904698, &h4c2b0edd, &h4f757656, &h5d393378, &ha132234f, &h3d321c5d, &hc3f5e194, &h4b269301
! DD  &hc79f022f, &h3c997e7e, &h5e4f9504, &h3ffafbbd, &h76f7ad0e, &h296693f4, &h3d1fce6f, &hc61e45be
! DD  &hd3b5ab34, &hf72bf9b7, &h1b0434c0, &h4e72b567, &h5592a33d, &hb5229301, &hcfd2a87f, &h60aeb767
! DD  &h1814386b, &h30bcc33d, &h38a0c07d, &hfd1606f2, &hc363519b, &h589dd390, &h5479f8e6, &h1cb8d647
! DD  &h97fd61a9, &hea7759f4, &h2d57539d, &h569a58cf, &he84e63ad, &h462e1b78, &h6580f87e, &hf3817914
! DD  &h91da55f4, &h40a230f3, &hd1988f35, &hb6e318d2, &h3ffa50bc, &h3d40f021, &hc3c0bdae, &h4958c24c
! DD  &h518f36b2, &h84b1d370, &h0fedce83, &h878ddada, &hf2a279c7, &h94e01be8, &h90716f4b, &h954b8aa3 
S_BOX8:
! DD  &he216300d, &hbbddfffc, &ha7ebdabd, &h35648095, &h7789f8b7, &he6c1121b, &h0e241600, &h052ce8b5
! DD  &h11a9cfb0, &he5952f11, &hece7990a, &h9386d174, &h2a42931c, &h76e38111, &hb12def3a, &h37ddddfc
! DD  &hde9adeb1, &h0a0cc32c, &hbe197029, &h84a00940, &hbb243a0f, &hb4d137cf, &hb44e79f0, &h049eedfd
! DD  &h0b15a15d, &h480d3168, &h8bbbde5a, &h669ded42, &hc7ece831, &h3f8f95e7, &h72df191b, &h7580330d
! DD  &h94074251, &h5c7dcdfa, &habbe6d63, &haa402164, &hb301d40a, &h02e7d1ca, &h53571dae, &h7a3182a2
! DD  &h12a8ddec, &hfdaa335d, &h176f43e8, &h71fb46d4, &h38129022, &hce949ad4, &hb84769ad, &h965bd862
! DD  &h82f3d055, &h66fb9767, &h15b80b4e, &h1d5b47a0, &h4cfde06f, &hc28ec4b8, &h57e8726e, &h647a78fc
! DD  &h99865d44, &h608bd593, &h6c200e03, &h39dc5ff6, &h5d0b00a3, &hae63aff2, &h7e8bd632, &h70108c0c
! DD  &hbbd35049, &h2998df04, &h980cf42a, &h9b6df491, &h9e7edd53, &h06918548, &h58cb7e07, &h3b74ef2e
! DD  &h522fffb1, &hd24708cc, &h1c7e27cd, &ha4eb215b, &h3cf1d2e2, &h19b47a38, &h424f7618, &h35856039
! DD  &h9d17dee7, &h27eb35e6, &hc9aff67b, &h36baf5b8, &h09c467cd, &hc18910b1, &he11dbf7b, &h06cd1af8
! DD  &h7170c608, &h2d5e3354, &hd4de495a, &h64c6d006, &hbcc0c62c, &h3dd00db3, &h708f8f34, &h77d51b42
! DD  &h264f620f, &h24b8d2bf, &h15c1b79e, &h46a52564, &hf8d7e54e, &h3e378160, &h7895cda5, &h859c15a5
! DD  &he6459788, &hc37bc75f, &hdb07ba0c, &h0676a3ab, &h7f229b1e, &h31842e7b, &h24259fd7, &hf8bef472
! DD  &h835ffcb8, &h6df4c1f2, &h96f5b195, &hfd0af0fc, &hb0fe134c, &he2506d3d, &h4f9b12ea, &hf215f225
! DD  &ha223736f, &h9fb4c428, &h25d04979, &h34c713f8, &hc4618187, &hea7a6e98, &h7cd16efc, &h1436876c
! DD  &hf1544107, &hbedeee14, &h56e9af27, &ha04aa441, &h3cf7c899, &h92ecbae6, &hdd67016d, &h151682eb
! DD  &ha842eedf, &hfdba60b4, &hf1907b75, &h20e3030f, &h24d8c29e, &he139673b, &hefa63fb8, &h71873054
! DD  &hb6f2cf3b, &h9f326442, &hcb15a4cc, &hb01a4504, &hf1e47d8d, &h844a1be5, &hbae7dfdc, &h42cbda70
! DD  &hcd7dae0a, &h57e85b7a, &hd53f5af6, &h20cf4d8c, &hcea4d428, &h79d130a4, &h3486ebfb, &h33d3cddc
! DD  &h77853b53, &h37effcb5, &hc5068778, &he580b3e6, &h4e68b8f4, &hc5c8b37e, &h0d809ea2, &h398feb7c
! DD  &h132a4f94, &h43b7950e, &h2fee7d1c, &h223613bd, &hdd06caa2, &h37df932b, &hc4248289, &hacf3ebc3
! DD  &h5715f6b7, &hef3478dd, &hf267616f, &hc148cbe4, &h9052815e, &h5e410fab, &hb48a2465, &h2eda7fa4
! DD  &he87b40e4, &he98ea084, &h5889e9e1, &hefd390fc, &hdd07d35b, &hdb485694, &h38d7e5b2, &h57720101
! DD  &h730edebc, &h5b643113, &h94917e4f, &h503c2fba, &h646f1282, &h7523d24a, &he0779695, &hf9c17a8f
! DD  &h7a5b2121, &hd187b896, &h29263a4d, &hba510cdf, &h81f47c9f, &had1163ed, &hea7b5965, &h1a00726e
! DD  &h11403092, &h00da6d77, &h4a0cdd61, &had1f4603, &h605bdfb0, &h9eedc364, &h22ebe6a8, &hcee7d28a
! DD  &ha0e736a0, &h5564a6b9, &h10853209, &hc7eb8f37, &h2de705ca, &h8951570f, &hdf09822b, &hbd691a6c
! DD  &haa12e4f2, &h87451c0f, &he0f6a27a, &h3ada4819, &h4cf1764f, &h0d771c2b, &h67cdb156, &h350d8384
! DD  &h5938fa0f, &h42399ef3, &h36997b07, &h0e84093d, &h4aa93e61, &h8360d87b, &h1fa98b0c, &h1149382c
! DD  &he97625a5, &h0614d1b7, &h0e25244b, &h0c768347, &h589e8d82, &h0d2059d1, &ha466bb1e, &hf8da0a82
! DD  &h04f19130, &hba6e4ec0, &h99265164, &h1ee7230d, &h50b2ad80, &heaee6801, &h8db2a283, &hea8bf59e
END SUB
'-- end CAST-128.BAS 




'=====================================================================
'                       CAST-128 Test Bed code
'               Compiles with either PBWIN 7.0+ or PBCC 3.0+
'=====================================================================
#COMPILE EXE
#REGISTER NONE
#DIM ALL
'============
DEFLNG A-Z
%NOGDI     = 1 ' no GDI (Graphics Device Interface) functions
%NOMMIDS   = 1 ' no Multimedia ID definitions
%NONEWWAVE = 1 ' no new waveform types except WAVEFORMATEX are defined
%NONEWRIFF = 1 ' no new RIFF formats are defined
%NOJPEGDIB = 1 ' no JPEG DIB definitions
%NONEWIC   = 1 ' no new Image Compressor types are defined
%NOBITMAP  = 1 ' no extended bitmap info header definition
#INCLUDE "WIN32API.INC" 
'--------------------
'-- Utility macros
'-------------------- 
#IF %def(%pb_win32)
   MACRO eol=$CR
   MACRO mbox(t)=msgbox t
#ELSEIF %def(%pb_cc32)
   MACRO eol=$CRLF
   MACRO mbox(t)=stdout t
#ENDIF 
'--------------------

MACRO EnterCC
#IF %def(%pb_cc32)
   LOCAL launched&
   if (cursory = 1) and (cursorx = 1) then launched = -1
#ENDIF
END MACRO 
'--------------------

MACRO ExitCC
#IF %def(%pb_cc32)
   if launched then
      input flush
      stdout "Press any key to end"
      waitkey$
   end if
#ENDIF
END MACRO 
''--------------------

'MACRO zbs(x)=string$(x,0) 

#INCLUDE "CAST-128.BAS" 

DECLARE FUNCTION Hex2Show$(Buffer$) 

'====================
FUNCTION PBMain&()
REGISTER i&
LOCAL key$, plain$, cipher$, shouldbe$, t$
LOCAL ctx AS ENCRYPTION_CONTEXT  ' defined in CAST-128.BAS
EnterCC 
CAST128_Init ctx 
'-- Standard CAST-128 test vectors:
'-- 128-bit key
key      = chr$(&h01,&h23,&h45,&h67,&h12,&h34,&h56,&h78,&h23,&h45,&h67,&h89,&h34,&h56,&h78,&h9A)
plain    = chr$(&h01,&h23,&h45,&h67,&h89,&hAB,&hCD,&hEF)
cipher   = zbs(len(plain$))
shouldbe = chr$(&h23,&h8B,&h4F,&hE5,&h84,&h7E,&h44,&hB2) 
t = "Key length (bits):" + str$(len(key)*8) + eol
t = t + "plain:    " + Hex2Show$(plain$) + eol
gosub DoEncrypt
t = t + "cipher:   " + Hex2Show$(cipher) + eol
t = t + "shouldbe: " + Hex2Show$(shouldbe) + eol
'-- Be sure to reload key$
key = chr$(&h01,&h23,&h45,&h67,&h12,&h34,&h56,&h78,&h23,&h45,&h67,&h89,&h34,&h56,&h78,&h9A)
gosub DoDecrypt
t = t + "plain:    " + Hex2Show$(plain) + eol + eol 
'-- 80-bit key
key      = chr$(&h01,&h23,&h45,&h67,&h12,&h34,&h56,&h78,&h23,&h45)
plain    = chr$(&h01,&h23,&h45,&h67,&h89,&hAB,&hCD,&hEF)
cipher   = zbs(len(plain))
shouldbe = chr$(&hEB,&h6A,&h71,&h1A,&h2C,&h02,&h27,&h1B) 
t = t + "Key length (bits):" + str$((len(key$)*8)) + eol
t = t + "plain:    " + Hex2Show$(plain) + eol
gosub DoEncrypt
t = t + "cipher:   " + Hex2Show$(cipher) + eol
t = t + "shouldbe: " + Hex2Show$(shouldbe) + eol 
key = chr$(&h01,&h23,&h45,&h67,&h12,&h34,&h56,&h78,&h23,&h45)
gosub DoDecrypt
t = t + "plain:    " + Hex2Show$(plain) + eol + eol 
'-- 40-bit key
key      = chr$(&h01,&h23,&h45,&h67,&h12)
plain    = chr$(&h01,&h23,&h45,&h67,&h89,&hAB,&hCD,&hEF)
cipher   = zbs(len(plain))
shouldbe = chr$(&h7A,&hC8,&h16,&hD1,&h6E,&h9B,&h30,&h2E) 
t = t + "Key length (bits):" + str$((len(key$)*8)) + eol
t = t + "plain:    " + Hex2Show$(plain) + eol
gosub DoEncrypt
t = t + "cipher:   " + Hex2Show$(cipher) + eol
t = t + "shouldbe: " + Hex2Show$(shouldbe) + eol 
key = chr$(&h01,&h23,&h45,&h67,&h12)
gosub DoDecrypt
t = t + "plain:    " + Hex2Show$(plain) + eol + eol 
mbox(t) 
ExitCC
exit function 
'============
DoEncrypt:
ctx.UserKey       = strptr(key$)
ctx.UserKeyLength = len(key$)
ctx.InBlock       = strptr(plain$)
ctx.OutBlock      = strptr(cipher$)
if Set_Key&(ctx) then 
   for i = 1 to (len(plain$)\%BLOCKSIZE)  '<-- Required: (len(plain$) mod 8) = 0
      EncryptBlock ctx
      ctx.InBlock  = ctx.InBlock  + %BLOCKSIZE
      ctx.OutBlock = ctx.OutBlock + %BLOCKSIZE
   next i&
else
   mbox("Key setup error")
end if
'-- Burn the subkey
poke$ Ctx.K, zbs(sizeof(Ctx.K_Buffer))
RETURN 
'============
DoDecrypt:
ctx.UserKey       = strptr(key$)
ctx.UserKeyLength = len(key$)
ctx.InBlock       = strptr(cipher$)
ctx.OutBlock      = strptr(plain$)
if Set_Key&(ctx) then 
   for i = 1 to (len(plain$)\%BLOCKSIZE)  '<-- Required: (len(plain$) mod 8) = 0
      DecryptBlock ctx
      ctx.InBlock  = ctx.InBlock  + %BLOCKSIZE
      ctx.OutBlock = ctx.OutBlock + %BLOCKSIZE
   next i
else
   mbox("Setup error")
end if
'-- Burn the subkey
poke$ Ctx.K, zbs(sizeof(Ctx.K_Buffer))
RETURN
END FUNCTION 
'====================

FUNCTION Hex2Show$(Buffer$)
LOCAL t$, i&, b AS BYTE PTR
b = strptr(Buffer$)
for i = 0 to len(Buffer$)-1
   t = t + hex$(@b[i],2) + " "
next i
function = t
END FUNCTION
'-- end TESTBED.BAS

Mirror provided by Knuth Konrad