Stuart McLachlan
stuart at lexacorp.com.pg
Tue Jan 6 22:12:04 CST 2004
On 6 Jan 2004 at 21:26, Robert Gracie wrote: > Hello All, > Instead of re-inventing the wheel here, does anyone have some code that > will allow me to pull the body of an e-mail (or a very large string even) > and encrypt it with out first writing it to a text file? I've tried three > different cipher routines, but they all want to break up the String. So I'm > left with only the first section in the string.... > How large is large? Here are some routines that use PC1 (see http://membres.lycos.fr/pc1/) Theorectically, it will handle any length of string up to 1/2 the maximum allowable string length for your development environment. (The encryted string is always exactly twice as large as the original.) This VBA versions works fairly well up to about 30 - 40K on my PC (1 -2 secs to encode, virtually instantaneous decode), but as the original string gets bigger, it takes *a lot* longer to encrypt. (70K = 12 secs, 80K = 22 secs, 90K = 38 secs etc but decrypt is still only about 3 secs at 90K). If you want to use larger strings, I can let you have a DLL version of this which I built in PowerBasic. It is *much* faster Option Compare Database Option Explicit '----------------------------------------------------------------------------------------------------- '(A little) More info on this algo can be found at [URL=http://www.multimania.com/cuisinons/pc1/index.html]http://www.multimania.com/cuisinons/pc1/index.html[/URL] 'Ported from VB to PB by Wayne Diamond. The PC1 cipher uses a 128-bit key. 'It's a stream cipher with a retroaction function. 'Ported from PB to Access VBA by Stuart McLachlan '----------------------------------------------------------------------------------------------------- Global x1aZero() As Long, cle() As Long '---------------------------------------------------------------------------------- Function code(x1aTwo As Long, EDsi As Long, EDi As Long) As Long Dim EDax As Long, EDbx As Long, EDcx As Long, EDdx As Long, EDtemp As Long On Error Resume Next EDdx = (x1aTwo + EDi) Mod 65536 EDax = x1aZero(EDi) EDcx = &H15A EDbx = &H4E35 EDtemp = EDax EDax = EDsi EDsi = EDtemp EDtemp = EDax EDax = EDdx EDdx = EDtemp If (EDax <> 0) Then EDax = (EDax * EDbx) Mod 65536 End If EDtemp = EDax EDax = EDcx EDcx = EDtemp If (EDax <> 0) Then EDax = (EDax * EDsi) Mod 65536 EDcx = (EDax + EDcx) Mod 65536 End If EDtemp = EDax EDax = EDsi EDsi = EDtemp EDax = (EDax * EDbx) Mod 65536 EDdx = (EDcx + EDdx) Mod 65536 EDax = EDax + 1 x1aTwo = EDdx x1aZero(EDi) = EDax code = EDax Xor EDdx EDi = EDi + 1 End Function '---------------------------------------------------------------------------------- Function Assemble(x1aTwo As Long, EDsi As Long, EDi As Long) As Long On Error Resume Next Dim inter As Long x1aZero(0) = ((cle(1) * 256) + cle(2)) Mod 65536 inter = code(x1aTwo, EDsi, EDi) x1aZero(1) = x1aZero(0) Xor ((cle(3) * 256) + cle(4)) inter = inter Xor code(x1aTwo, EDsi, EDi) x1aZero(2) = x1aZero(1) Xor ((cle(5) * 256) + cle(6)) inter = inter Xor code(x1aTwo, EDsi, EDi) x1aZero(3) = x1aZero(2) Xor ((cle(7) * 256) + cle(8)) inter = inter Xor code(x1aTwo, EDsi, EDi) x1aZero(4) = x1aZero(3) Xor ((cle(9) * 256) + cle(10)) inter = inter Xor code(x1aTwo, EDsi, EDi) x1aZero(5) = x1aZero(4) Xor ((cle(11) * 256) + cle(12)) inter = inter Xor code(x1aTwo, EDsi, EDi) x1aZero(6) = x1aZero(5) Xor ((cle(13) * 256) + cle(14)) inter = inter Xor code(x1aTwo, EDsi, EDi) x1aZero(7) = x1aZero(6) Xor ((cle(15) * 256) + cle(16)) Assemble = inter Xor code(x1aTwo, EDsi, EDi) EDi = 0 End Function '---------------------------------------------------------------------------------- Function PC1ENC(encPassword As String, encStringOut As String) As String On Error Resume Next Dim encStringIn As String, ChmpStr As String Dim j As Long, cfc As Long, cfd As Long, c As Long, D As Long, E As Long Dim Chmp As Long, compte As Long Dim x1aTwo As Long, EDsi As Long, EDi As Long, inter As Long ReDim x1aZero(9) As Long, cle(17) As Long encStringIn = "" EDsi = 0 x1aTwo = 0 EDi = 0 For j = 1 To 16 cle(j) = 0 Next j ChmpStr = encPassword Chmp = Len(ChmpStr) For j = 1 To Chmp cle(j) = Asc(Mid$(ChmpStr, j, 1)) Next j ChmpStr = encStringOut Chmp = Len(ChmpStr) For j = 1 To Chmp c = Asc(Mid$(ChmpStr, j, 1)) inter = Assemble(x1aTwo, EDsi, EDi) cfc = (((inter / 256) * 256) - (inter Mod 256)) / 256 cfd = inter Mod 256 For compte = 1 To 16 cle(compte) = cle(compte) Xor c Next compte c = c Xor (cfc Xor cfd) D = (((c / 16) * 16) - (c Mod 16)) / 16 E = c Mod 16 encStringIn = encStringIn + Chr$(&H61 + D) ' d+&h61 give one letter range from a to p for the 4 high bits of c encStringIn = encStringIn + Chr$(&H61 + E) ' e+&h61 give one letter range from a to p for the 4 low bits of c Next j PC1ENC = encStringIn End Function '---------------------------------------------------------------------------------- Function PC1DEC(encPassword As String, encStringIn As String) As String On Error Resume Next Dim encStringOut As String, ChmpStr As String Dim j As Long, cfc As Long, cfd As Long, c As Long, D As Long, E As Long Dim Chmp As Long, compte As Long Dim x1aTwo As Long, EDsi As Long, EDi As Long, inter As Long ReDim x1aZero(9) As Long, cle(17) As Long encStringOut = "" EDsi = 0 x1aTwo = 0 EDi = 0 For j = 1 To 16 cle(j) = 0 Next j ChmpStr = encPassword Chmp = Len(ChmpStr) For j = 1 To Chmp cle(j) = Asc(Mid$(ChmpStr, j, 1)) Next j ChmpStr = encStringIn Chmp = Len(ChmpStr) For j = 1 To Chmp D = Asc(Mid$(ChmpStr, j, 1)) If (D - &H61) >= 0 Then D = D - &H61 ' to transform the letter to the 4 high bits of c If (D >= 0) And (D <= 15) Then D = D * 16 End If End If If (j <> Chmp) Then j = j + 1 End If E = Asc(Mid$(ChmpStr, j, 1)) If (E - &H61) >= 0 Then E = E - &H61 ' to transform the letter to the 4 low bits of c If (E >= 0) And (E <= 15) Then c = D + E End If End If inter = Assemble(x1aTwo, EDsi, EDi) cfc = (((inter / 256) * 256) - (inter Mod 256)) / 256 cfd = inter Mod 256 c = c Xor (cfc Xor cfd) For compte = 1 To 16 cle(compte) = cle(compte) Xor c Next compte encStringOut = encStringOut + Chr$(c) Next j PC1DEC = encStringOut End Function '---------------------------------------------------------------------------------- Function test() As Long Dim strPassword As String Dim strOriginal As String Dim strEncode As String Dim strDecode As String strPassword = "12345678901" ' Max 11 Numbers it seems or ... strPassword = "abcdefghijklmno" ' around 16 letters is maximum strOriginal = String$(32000, "A") starttime = Timer strEncode = PC1ENC(strPassword, strOriginal) Debug.Print "Encoded in " & CInt(Timer - starttime) & " secs" Open "c:\test1.txt" For Output As #1 Print #1, strEncode Close #1 starttime = Timer strDecode = PC1DEC(strPassword, strEncode) Debug.Print "Decoded in " & CInt(Timer - starttime) & " secs" Open "c:\test2.txt" For Output As #1 Print #1, strDecode Close #1 End Function '---------------------------------------------------------------------------------- -- Lexacorp Ltd http://www.lexacorp.com.pg Information Technology Consultancy, Software Development,System Support.