Decoding Base64 image failed Topic is solved

Get help with using AutoHotkey and its commands and hotkeys
afe
Posts: 525
Joined: 06 Dec 2018, 04:36

Decoding Base64 image failed

13 Dec 2018, 05:01

Hello,
I tried to decode a Base64 encoding of an image, but it didn't work. Where is the mistake?

Thanks!


Code: Select all

Base64Char := "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"

Base64Index(c)
{
    Global Base64Char
    return InStr(Base64Char, c, CaseSensitive) - 1
}

Base64Decode(str, ByRef Bytes)
{
    Bytes := 0
    str := StrReplace(str, "=")

    Loop Parse, str
    {
        if Mod(A_Index, 4) = 1
            buffer := Base64Index(A_LoopField) << 18

        else If Mod(A_Index, 4) = 2
        {
            buffer += Base64Index(A_LoopField) << 12
            ++Bytes
        }
        else If Mod(A_Index, 4) = 3
        {
            buffer += Base64Index(A_LoopField) << 6
            ++Bytes
        }
         else
        {
            buffer += Base64Index(A_LoopField)
            r := r << 24 + buffer
            ++Bytes
        }
    }

    if Mod(StrLen(code),4) = 0
        return r
    if Mod(StrLen(code),4) = 2
        return r << 8 + buffer >> 16
    return r << 16 + buffer >> 8
}




Base64Str := "/9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAAgGBgcGBQgHBwcJCQgKDBQNDAsLDBkSEw8UHRofHh0aHBwgJC4nICIsIxwcKDcpLDAxNDQ0Hyc5PTgyPC4zNDL/2wBDAQkJCQwLDBgNDRgyIRwhMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjL/wgARCAACAAIDASIAAhEBAxEB/8QAFQABAQAAAAAAAAAAAAAAAAAAAAb/xAAUAQEAAAAAAAAAAAAAAAAAAAAA/9oADAMBAAIQAxAAAAG/B//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAQUCf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQMBAT8Bf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQIBAT8Bf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEABj8Cf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAT8hf//aAAwDAQACAAMAAAAQ8//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQMBAT8Qf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQIBAT8Qf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAT8Qf//Z"


Var := Base64Decode(Base64Str, Bytes)

File := FileOpen("test.jpg", "w")
File.RawWrite(Var, Bytes)
File.Close()
return
Last edited by afe on 13 Dec 2018, 06:46, edited 3 times in total.
John
Posts: 75
Joined: 10 Apr 2014, 08:59

Re: Decoding Base64 image failed

13 Dec 2018, 05:37

You base64 string doesn't decode into anything, https://codebeautify.org/base64-to-image-converter
The script didn't seem to work either, don't know why. If you justn eed to get it working and don't want/need to understand the unerlying issues then try this function instead https://autohotkey.com/board/topic/8570 ... r-decoder/ used it before and works fine.
swagfag
Posts: 2847
Joined: 11 Jan 2017, 17:59

13 Dec 2018, 05:44

no. its an image of a white square.
id say its the function, where did u get it? did u write this urself?
use this instead https://autohotkey.com/boards/viewtopic.php?t=35964
afe
Posts: 525
Joined: 06 Dec 2018, 04:36

Re: Decoding Base64 image failed

13 Dec 2018, 07:02

Yex, but there is a problem with thinking.

Base64 converts every 3 binary bytes of the image into 4 Base64 characters. In turn, decoding requires converting every 4 Base64 characters to 3 binary bytes.

But the problem arises, I mistakenly save these converted binary bytes into a variable "r". This may be the wrong place, or the idea is completely wrong. I'm confused.

What you can't figure out is if you combine these binary bytes into the same binary code as the original picture.

Yes, I have read some articles, but I still have not learned to use DllCall now, so I want to avoid it.


Or if the value of a variable is a string of binary code of an image, how can I save it as an image?
hd0202
Posts: 122
Joined: 04 Oct 2013, 03:07
Location: Germany near Cologne

Re: Decoding Base64 image failed  Topic is solved

14 Dec 2018, 06:48

here is my version (not tested if input is not multiple of 4):

Code: Select all

Base64Char := "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"

Base64Index(c)
{
    Global Base64Char
    return InStr(Base64Char, c, true) - 1
}

Base64Decode(str, ByRef var)
{
	Bytes := 1
	loop, % strlen(str) / 4
    {
		buffer := substr(str, (bytes - 1) * 4 + 1, 4)
		r := 0
		loop, 4
			r := (r << 6) + base64index(substr(buffer, a_index , 1))
		numput(x := r & 255, var, (bytes - 1) * 3 + 2, "uchar")
		numput(y := r >> 8 & 255, var, (bytes - 1) * 3 + 1, "uchar")
		numput(z := r >> 16 & 255, var, (bytes - 1) * 3, "uchar")
		bytes++
    }
;    if Mod(StrLen(code),4) = 0
;        return r
;    if Mod(StrLen(code),4) = 2
;        return r << 8 + buffer >> 16
;    return r << 16 + buffer >> 8
}

Base64Str := "/9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAAgGBgcGBQgHBwcJCQgKDBQNDAsLDBkSEw8UHRofHh0aHBwgJC4nICIsIxwcKDcpLDAxNDQ0Hyc5PTgyPC4zNDL/2wBDAQkJCQwLDBgNDRgyIRwhMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjL/wgARCAACAAIDASIAAhEBAxEB/8QAFQABAQAAAAAAAAAAAAAAAAAAAAb/xAAUAQEAAAAAAAAAAAAAAAAAAAAA/9oADAMBAAIQAxAAAAG/B//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAQUCf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQMBAT8Bf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQIBAT8Bf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEABj8Cf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAT8hf//aAAwDAQACAAMAAAAQ8//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQMBAT8Qf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQIBAT8Qf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAT8Qf//Z"

v := varsetcapacity(var, strlen(base64str) / 4 * 3)
Base64Decode(Base64Str, var)

File := FileOpen("test.jpg", "w")
File.RawWrite(Var, v)
File.Close()
return
Hubert
afe
Posts: 525
Joined: 06 Dec 2018, 04:36

Re: Decoding Base64 image failed

15 Dec 2018, 06:52

@hd0202 , thank you very much! Great, numput is exactly what I want. Thank you!
afe
Posts: 525
Joined: 06 Dec 2018, 04:36

Re: Decoding Base64 image failed

15 Dec 2018, 09:53

I modified it a bit and tried to use "RtlFillMemory" but it still failed. I don't know where it is wrong.

===========
It works now.

Code: Select all

Base64CharIndex(c)
{
    static Base64CharSet := "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
    return InStr(Base64CharSet, c, 1) - 1
}

WriteToMemory(ByRef bin, Fill)
{
    global pos

    DllCall("RtlFillMemory"
                            , "ptr",        &bin + pos
                            , "int",        1
                            , "uchar",    Fill)
    ++pos
    return
}

Base64Decode(Base64Code, ByRef bin)
{
    Base64CodeLength := StrLen(Base64Code) // 4 * 3

    if ( RegExMatch(Base64Code, "=$") )
    {
        if ( RegExMatch(Base64Code, "==$") )
            binSize := Base64CodeLength - 2
        else
            binSize := Base64CodeLength - 1
    }
    else
        binSize := Base64CodeLength

    VarSetCapacity(bin, binSize)

    Base64Code := StrReplace(Base64Code, "=")

    Loop, Parse, Base64Code
    {
        Base64CharIndexValue := Base64CharIndex(A_LoopField)
        n := A_Index & 3

        if ( n = 1 )
                buffer := Base64CharIndexValue << 18
        else If ( n = 2 )
                buffer += Base64CharIndexValue << 12
        else If ( n = 3 )
                 buffer += Base64CharIndexValue << 6
        else
        {
            buffer += Base64CharIndexValue

            WriteToMemory(bin, buffer >> 16 & 255)
            WriteToMemory(bin, buffer >> 8 & 255)
            WriteToMemory(bin, buffer & 255)
        }
    }

    sum := Base64CodeLength - binSize

    if ( sum = 2 )
        WriteToMemory(bin, buffer >> 16 & 255)
    else if ( sum = 1 )
    {
        WriteToMemory(bin, buffer >> 16 & 255)
        WriteToMemory(bin, buffer >> 8 & 255)
    }
    return binSize
}



Base64Code := "/9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAAgGBgcGBQgHBwcJCQgKDBQNDAsLDBkSEw8UHRofHh0aHBwgJC4nICIsIxwcKDcpLDAxNDQ0Hyc5PTgyPC4zNDL/2wBDAQkJCQwLDBgNDRgyIRwhMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjIyMjL/wgARCAACAAIDASIAAhEBAxEB/8QAFQABAQAAAAAAAAAAAAAAAAAAAAb/xAAUAQEAAAAAAAAAAAAAAAAAAAAA/9oADAMBAAIQAxAAAAG/B//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAQUCf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQMBAT8Bf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQIBAT8Bf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEABj8Cf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAT8hf//aAAwDAQACAAMAAAAQ8//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQMBAT8Qf//EABQRAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQIBAT8Qf//EABQQAQAAAAAAAAAAAAAAAAAAAAD/2gAIAQEAAT8Qf//Z"


pos := 0

Bytes := Base64Decode(Base64Code, bin)

File1 := FileOpen("test.jpg", "w")
File1.RawWrite(bin, Bytes)
File1.Close()
Last edited by afe on 23 Jan 2019, 02:35, edited 6 times in total.
hd0202
Posts: 122
Joined: 04 Oct 2013, 03:07
Location: Germany near Cologne

Re: Decoding Base64 image failed

15 Dec 2018, 12:41

after dllcall check errorlevel and have a look at the help -> dllcall

Hubert
afe
Posts: 525
Joined: 06 Dec 2018, 04:36

Re: Decoding Base64 image failed

19 Dec 2018, 09:47

@hd0202 , thank you very much!

I used my code to test the script startup time much slower than using DllCall ("Crypt32.dll\CryptStringToBinary" for 2 seconds. Is the code quality affecting the speed?



Using DllCall ("Crypt32.dll\CryptStringToBinary"

AutoHotkey.exe - 1 executions
0.2129
AutoHotkey.exe - 1 executions
0.1838
AutoHotkey.exe - 1 executions
0.2254
AutoHotkey.exe - 1 executions
0.1962
AutoHotkey.exe - 1 executions
0.1921



My code

AutoHotkey.exe - 1 executions
1.8072
AutoHotkey.exe - 1 executions
1.8963
AutoHotkey.exe - 1 executions
1.9433
AutoHotkey.exe - 1 executions
1.8579
AutoHotkey.exe - 1 executions
1.8075

Return to “Ask For Help”

Who is online

Users browsing this forum: aircooled, flyingDman, Frosti, ozz, rediffusion, RinkaDink, swagfag and 228 guests