Jump to content

Recommended Posts

Posted (edited)

I tried the Binary() function for starters but since AU3 stores binary as hex I'm lost as to how to extract specific bits out of it.

Here's an example of what I'm trying to do:

1) Original Hex: 303425637013293133FDA4D5

2) Convert to Binary: 001100000011010000100101011000110111000000010011001010010011000100110011111111011010010011010101

3) Extract Bits 39 - 58 from binary: 00000100110010100100

4) Convert extracted bits to decimal: 19620

 

While I don't see that long binary string in step 2 I'll assume it's available internally in the script after Binary() so it's step 3 where I'm stuck.

I did try BinaryMid() but that just returned nothing with the parameters 39, 17 wrapped around the Binary() function.

And yes I did include 0x in front of my Hex number.

 

Any help is appreciated.

Thanks,

Kenny

Edited by ken82m

 "I believe that when we leave a place, part of it goes with us and part of us remains... Go anywhere, when it is quiet, and just listen.. After a while, you will hear the echoes of all our conversations, every thought and word we've exchanged.... Long after we are gone our voices will linger in these walls for as long as this place remains."

Posted

Hi, you can extract the necessary Bit functions from this post.

 

If you have the Autoit's Binary String, you can use the BinaryLen() and BinaryMid() functions to extract the needed characters. Use IsBinary to check if the string format is in the correct format.

Some of my script sourcecode

Posted

Maybe this helps you. I suspect that MSB for bits 39-58 are not correct by I stayed with your version. If the order of your most significant bit is reversed just reverse $BinNumber before extracting bits with StringMid().

 

$HexNumber = '303425637013293133FDA4D5'
$BinNumer = HexToBin($HexNumber)
$Bits39_58 = StringMid($BinNumer, 39, 20) ; 58 - 39 + 1 = 20
$Decimal = Bin2Dec($Bits39_58)
ConsoleWrite($Decimal & @CRLF)

Func HexToBin($dHex)
    If StringLeft($dHex, 2) = '0x' Then $dHex = StringTrimLeft($dHex, 2)
    Local $aSplit = StringSplit($dHex, '')
    Local $sBin, $aBits = StringSplit('0000|0001|0010|0011|0100|0101|0110|0111|1000|1001|1010|1011|1100|1101|1110|1111', '|', 2)
    For $Index = 1 To $aSplit[0]
        $sBin &= $aBits[Dec($aSplit[$Index])]
    Next
    Return $sBin
EndFunc

Func Bin2Dec($sBin)
    Local $iDecimal = 0
    For $Index = 1 To StringLen($sBin)
        $iDecimal += Number(StringMid($sBin, $Index , 1)) * (2 ^ (StringLen($sBin) - $Index))
    Next
    Return $iDecimal
EndFunc

 

Posted (edited)

Why on earth would you need to do this?  :)

#AutoIt3Wrapper_AU3Check_Parameters=-w 3 -w 4 -w 5 -w 6 -d

#include <Constants.au3>

example()

Func example()
    Const $BIN_VALUE   = Binary("0x303425637013293133FDA4D5")

    Local $sBase2Value = _BinaryBits($BIN_VALUE, False), _
          $sBits39to58 = StringMid($sBase2Value, 39, 20)

    Local $iInt32Value = _StringToInt32($sBits39to58, 2)

    ConsoleWrite("Base16 value:              " & $BIN_VALUE   & @CRLF)
    ConsoleWrite("Base2 value:               " & _BinaryBits($BIN_VALUE) & @CRLF)
    ConsoleWrite("Bits 39-58                 " & $sBits39to58 & @CRLF)
    ConsoleWrite("Int32 value of bits 39-58: " & $iInt32Value  & @CRLF)
EndFunc

; #FUNCTION# ====================================================================================================================
; Name ..........: _BinaryBits
; Description ...: Convert data to its base2 value (with or without a space between every 4 bits)
; Syntax ........: _BinaryBits($vData[, $bAddSeparator = True])
; Parameters ....: $vData           - a string or number value.
;                  $bAddSeparator   - [optional] a boolean value. Default is True.
; Return values .: A string representing the base2 value
; Author ........: TheXman
; ===============================================================================================================================
Func _BinaryBits($vData, $bAddSeparator = True)

    Local $sBits = ""

    Local $xBinaryData = Binary($vData), _
          $xByte       = Binary("")

    Local $iBinaryDataLength = BinaryLen($xBinaryData)


    ;Process binary data from left-most byte to right-most byte
    For $i = 1 To $iBinaryDataLength
        ;Get byte
        $xByte = BinaryMid($xBinaryData, $i, 1)

        ;Spin thru each bit of byte (msb to lsb)
        For $j = 7 To 0 Step -1
            ;If separator requested and this is 5th bit, then add a nibble separator
            If $bAddSeparator And $j = 3 Then $sBits &= " "

            ;If bit is set, then prepend 1 else prepend 0
            $sBits &= (BitAND($xByte, 2 ^ $j) ? "1" : "0")
        Next

        ;If this isn't the last byte to be processed, then add a byte separator
        If $i < $iBinaryDataLength And $bAddSeparator Then $sBits &= " "
    Next

    Return $sBits

EndFunc

; #FUNCTION# ====================================================================================================================
; Name ..........: _StringToInt32
; Description ...: Convert a string, in the specified number base, to an int32.
; Syntax ........: _StringToInt64($sString, $iBase)
; Parameters ....: $sString        A string representation of a integer value (in a base from 2 to 36).
;                  $iBase          An integer value from 2 to 36.
; Return values .: Success         An int32 value of the string.
;                  Failure         0 and sets @error to a non-zero value.
;                                  @error  1 = Invalid number base
;                                          2 = DllCall failed.  @extended = DllCall @error
; Author ........: TheXman
; ===============================================================================================================================
Func _StringToInt32($sString, $iBase)

    Local $aResult[0]

    If $iBase < 2 Or $iBase > 36 Then Return SetError(1, 0, "")
    $aResult = DllCall('msvcrt.dll', 'int64:cdecl', '_wcstoui64', _
                       'wstr'  , $sString, _
                       'wstr*' , Null, _
                       'int'   , $iBase)
    If @error Then Return SetError(2, @error, 0)

    Return Number($aResult[0], $NUMBER_32BIT)
EndFunc

Output:

Base16 value:              0x303425637013293133FDA4D5
Base2 value:               0011 0000 0011 0100 0010 0101 0110 0011 0111 0000 0001 0011 0010 1001 0011 0001 0011 0011 1111 1101 1010 0100 1101 0101
Bits 39-58                 00000100110010100100
Int32 value of bits 39-58: 19620

 

Edited by TheXman
Posted
4 minutes ago, TheXman said:

Why on earth would you need to do this?  :)

#AutoIt3Wrapper_AU3Check_Parameters=-w 3 -w 4 -w 5 -w 6 -d

#include <Constants.au3>

example()

Func example()
    Const $BIN_VALUE   = Binary("0x303425637013293133FDA4D5")

    Local $sBase2Value = _BinaryBits($BIN_VALUE, False), _
          $sBits39to58 = StringMid($sBase2Value, 39, 20)

    Local $iInt32Value = _StringToInt32($sBits39to58, 2)

    ConsoleWrite("Binary value:              " & $BIN_VALUE   & @CRLF)
    ConsoleWrite("Base2 value:               " & $sBase2Value & @CRLF)
    ConsoleWrite("Bits 39-58                 " & $sBits39to58 & @CRLF)
    ConsoleWrite("Int32 value of bits 39-58: " & $iInt32Value  & @CRLF)
EndFunc

; #FUNCTION# ====================================================================================================================
; Name ..........: _BinaryBits
; Description ...: Convert data to its base2 value (with or without a space between every 4 bits)
; Syntax ........: _BinaryBits($vData[, $bAddSeparator = True])
; Parameters ....: $vData           - a string or number value.
;                  $bAddSeparator   - [optional] a boolean value. Default is True.
; Return values .: A string representing the base2 value
; Author ........: TheXman
; ===============================================================================================================================
Func _BinaryBits($vData, $bAddSeparator = True)

    Local $sBits = ""

    Local $xBinaryData = Binary($vData), _
          $xByte       = Binary("")

    Local $iBinaryDataLength = BinaryLen($xBinaryData)


    ;Process binary data from left-most byte to right-most byte
    For $i = 1 To $iBinaryDataLength
        ;Get byte
        $xByte = BinaryMid($xBinaryData, $i, 1)

        ;Spin thru each bit of byte (msb to lsb)
        For $j = 7 To 0 Step -1
            ;If separator requested and this is 5th bit, then add a nibble separator
            If $bAddSeparator And $j = 3 Then $sBits &= " "

            ;If bit is set, then prepend 1 else prepend 0
            $sBits &= (BitAND($xByte, 2 ^ $j) ? "1" : "0")
        Next

        ;If this isn't the last byte to be processed, then add a byte separator
        If $i < $iBinaryDataLength And $bAddSeparator Then $sBits &= " "
    Next

    Return $sBits

EndFunc

; #FUNCTION# ====================================================================================================================
; Name ..........: _StringToInt32
; Description ...: Convert a string, in the specified number base, to an int32.
; Syntax ........: _StringToInt64($sString, $iBase)
; Parameters ....: $sString        A string representation of a integer value (in a base from 2 to 36).
;                  $iBase          An integer value from 2 to 36.
; Return values .: Success         An int32 value of the string.
;                  Failure         0 and sets @error to a non-zero value.
;                                  @error  1 = Invalid number base
;                                          2 = DllCall failed.  @extended = DllCall @error
; Author ........: TheXman
; ===============================================================================================================================
Func _StringToInt32($sString, $iBase)

    Local $aResult[0]

    If $iBase < 2 Or $iBase > 36 Then Return SetError(1, 0, "")
    $aResult = DllCall('msvcrt.dll', 'int64:cdecl', '_wcstoui64', _
                       'wstr'  , $sString, _
                       'wstr*' , Null, _
                       'int'   , $iBase)
    If @error Then Return SetError(2, @error, 0)

    Return Number($aResult[0], $NUMBER_32BIT)
EndFunc

Output:

Binary value:              0x303425637013293133FDA4D5
Base2 value:               001100000011010000100101011000110111000000010011001010010011000100110011111111011010010011010101
Bits 39-58                 00000100110010100100
Int32 value of bits 39-58: 19620

 

Uggg don't get me started. Some stupid vendor we're unfortunately willing to accommodate has this weird damn structure that's a combination of data that produces that hex number.

And when it gets transmitted back to them in volume it requires that piece of it converted back to decimal (which can vary) as part of the return data. It was a big enough pain putting this together with a piece of software. But then having to unravel this again which is a big enough pain to create to extract that specific section as part of the file that goes back to them. And of course I have to make all this junk work.

Alternatively I could write these to a database as we create them with that decimal value in another column which probably makes more sense. But honestly nobody here gives a damn about any of these values so I'd rather not have yet another database to administer. If I can just have a script these users can feed an input file to (which contains a lot of unnecessary fields) process that and produce the final output going back stand alone I can live with that.

I've though about a few other options but I can see users constantly screwing something up constantly lol.

 

Thank you all for your help. I've done plenty in AutoIT but I have never had to deal with actual binary directly in AU3.

 

 "I believe that when we leave a place, part of it goes with us and part of us remains... Go anywhere, when it is quiet, and just listen.. After a while, you will hear the echoes of all our conversations, every thought and word we've exchanged.... Long after we are gone our voices will linger in these walls for as long as this place remains."

Posted (edited)

A different approach:

#NoTrayIcon
#include ".\Eigen4AutoIt.au3"

_Eigen_StartUp("int")

$HexNumber = '303425637013293133FDA4D5'

$firstbit = 39  ; base-1 index
$lastbit = 58
$totalbits = 1+$lastbit-$firstbit
If $totalbits>32 Then Exit  ; value too large to fit into one int32

; store hex string as conseucutive int32s
$ints=Ceiling(StringLen($HexNumber)/8)
$vector=_Eigen_CreateVector(_Max(32,$ints)) ; ensure enough space for result
For $rc=0 To $ints-1
    _Eigen_WriteMatrixValue($vector,$rc,0,Number("0x" & StringMid($HexNumber,1+$rc*8,8)))
Next

; unpack all bits, store desired bits, and repack
$matA=_Eigen_Unpack($vector)
_Eigen_SetZero($vector) ; prezero results buffer
_Eigen_Copy_Ablock_ToBblock($matA,$vector,$firstbit-1,0,$totalbits,1,32-$totalbits,0)
_Eigen_Pack($vector,$matA)

ConsoleWrite("Selected Bits value = " & _Eigen_ReadMatrixValue($matA,0,0) & @CRLF)

_Eigen_CleanUp()

If the last int32 is can be incomplete, just pad it with extra zeroes before storing it in the vector:

#include <String.au3>
$HexNumber&=_StringRepeat("0",8-Mod(StringLen($HexNumber),8))

 

Edited by RTFC
  • 2 years later...
Posted (edited)
On 6/5/2023 at 11:07 PM, TheXman said:

Why on earth would you need to do this?  :)

#AutoIt3Wrapper_AU3Check_Parameters=-w 3 -w 4 -w 5 -w 6 -d

#include <Constants.au3>

example()

Func example()
    Const $BIN_VALUE   = Binary("0x303425637013293133FDA4D5")

    Local $sBase2Value = _BinaryBits($BIN_VALUE, False), _
          $sBits39to58 = StringMid($sBase2Value, 39, 20)

    Local $iInt32Value = _StringToInt32($sBits39to58, 2)

    ConsoleWrite("Base16 value:              " & $BIN_VALUE   & @CRLF)
    ConsoleWrite("Base2 value:               " & _BinaryBits($BIN_VALUE) & @CRLF)
    ConsoleWrite("Bits 39-58                 " & $sBits39to58 & @CRLF)
    ConsoleWrite("Int32 value of bits 39-58: " & $iInt32Value  & @CRLF)
EndFunc

; #FUNCTION# ====================================================================================================================
; Name ..........: _BinaryBits
; Description ...: Convert data to its base2 value (with or without a space between every 4 bits)
; Syntax ........: _BinaryBits($vData[, $bAddSeparator = True])
; Parameters ....: $vData           - a string or number value.
;                  $bAddSeparator   - [optional] a boolean value. Default is True.
; Return values .: A string representing the base2 value
; Author ........: TheXman
; ===============================================================================================================================
Func _BinaryBits($vData, $bAddSeparator = True)

    Local $sBits = ""

    Local $xBinaryData = Binary($vData), _
          $xByte       = Binary("")

    Local $iBinaryDataLength = BinaryLen($xBinaryData)


    ;Process binary data from left-most byte to right-most byte
    For $i = 1 To $iBinaryDataLength
        ;Get byte
        $xByte = BinaryMid($xBinaryData, $i, 1)

        ;Spin thru each bit of byte (msb to lsb)
        For $j = 7 To 0 Step -1
            ;If separator requested and this is 5th bit, then add a nibble separator
            If $bAddSeparator And $j = 3 Then $sBits &= " "

            ;If bit is set, then prepend 1 else prepend 0
            $sBits &= (BitAND($xByte, 2 ^ $j) ? "1" : "0")
        Next

        ;If this isn't the last byte to be processed, then add a byte separator
        If $i < $iBinaryDataLength And $bAddSeparator Then $sBits &= " "
    Next

    Return $sBits

EndFunc

; #FUNCTION# ====================================================================================================================
; Name ..........: _StringToInt32
; Description ...: Convert a string, in the specified number base, to an int32.
; Syntax ........: _StringToInt64($sString, $iBase)
; Parameters ....: $sString        A string representation of a integer value (in a base from 2 to 36).
;                  $iBase          An integer value from 2 to 36.
; Return values .: Success         An int32 value of the string.
;                  Failure         0 and sets @error to a non-zero value.
;                                  @error  1 = Invalid number base
;                                          2 = DllCall failed.  @extended = DllCall @error
; Author ........: TheXman
; ===============================================================================================================================
Func _StringToInt32($sString, $iBase)

    Local $aResult[0]

    If $iBase < 2 Or $iBase > 36 Then Return SetError(1, 0, "")
    $aResult = DllCall('msvcrt.dll', 'int64:cdecl', '_wcstoui64', _
                       'wstr'  , $sString, _
                       'wstr*' , Null, _
                       'int'   , $iBase)
    If @error Then Return SetError(2, @error, 0)

    Return Number($aResult[0], $NUMBER_32BIT)
EndFunc

Output:

Base16 value:              0x303425637013293133FDA4D5
Base2 value:               0011 0000 0011 0100 0010 0101 0110 0011 0111 0000 0001 0011 0010 1001 0011 0001 0011 0011 1111 1101 1010 0100 1101 0101
Bits 39-58                 00000100110010100100
Int32 value of bits 39-58: 19620

 

Thank you, I modified it a bit to work with integers :

#include-once
#include <Constants.au3>

Example()

; Current ====================================================================================================================
; _BinaryBits()      : Convert data to its base2 value (with or without a space between every 4 bits)
; _IntToString()     : Convert an integer to any base
; ============================================================================================================================
; _StringToInt32()   : Convert a string, in the specified number base, to an Int32.
; _StringToInt64()   : Convert a string, in the specified number base, to an Int64.
; ============================================================================================================================

Func Example()
    Local Const $dData = Binary("0x303425637013293133FDA4D5")
    Local $sBase2Value = _BinaryBits($dData, False)
    Local $sBits39to58 = StringMid($sBase2Value, 39, 20)
    Local $iInt64Value = _StringToInt64($sBits39to58, 2)
    Local $iInt32Value = _StringToInt32($sBits39to58, 2)
    ConsoleWrite("---- $dData ------------------------------------------------------------------------" &@CRLF)
    ConsoleWrite("Base16 value              : " & $dData                                                &@CRLF)
    ConsoleWrite("Base2 value               : " & _BinaryBits($dData)                                   &@CRLF)
    ConsoleWrite("Bits 39-58                : " & $sBits39to58                                          &@CRLF)
    ConsoleWrite("Int64 value of bits 39-58 : " & $iInt64Value                                          &@CRLF)
    ConsoleWrite("Int32 value of bits 39-58 : " & $iInt32Value                                          &@CRLF)
    ConsoleWrite("------------------------------------------------------------------------------------" &@CRLF)

    Local Const $iInt = 0xF0204060   ;-266321824
    ConsoleWrite("---- $iInt -------------------------------------------------------------------------" &@CRLF)
    ConsoleWrite(VarGetType($iInt)&"                       : " & $iInt                                  &@CRLF)
    ConsoleWrite("Binary                      : " & Binary($iInt)                                       &@CRLF)
    ConsoleWrite("Hex                         : " & "0x"&Hex($iInt)                                     &@CRLF)
    ConsoleWrite("Bits (raw)                  : " & _BinaryBits($iInt, True, False)                     &@CRLF)
    ConsoleWrite("Bits (reordered bytes)      : " & _BinaryBits($iInt, True, True)                      &@CRLF)
    ConsoleWrite("Int32 from bits (raw)       : " & _StringToInt32(_BinaryBits($iInt, False, False), 2) &@CRLF)
    ConsoleWrite("Int32 from bits (reordered) : " & _StringToInt32(_BinaryBits($iInt, False, True), 2)  &@CRLF)
    ConsoleWrite("Int64 from bits (reordered) : " & _StringToInt64(_BinaryBits($iInt, False, True), 2)  &@CRLF)
    ConsoleWrite("------------------------------------------------------------------------------------" &@CRLF)

    ConsoleWrite(_IntToString($iInt, 2, 0, False) &@CRLF)
EndFunc




; #FUNCTION# ====================================================================================================================
; Name ..........: _BinaryBits
; Description ...: Convert data to its base2 value (with or without a space between every 4 bits)
; Parameters ....: $vData            - The data. Strings starting with "0x" will be interpreted as hex data
;                  $bSpaces          - Put spaces between every 4 bits
;                  $bReorderIntBytes - Reverse integer bytes order on little endian CPUs. Should have no effect on big endian CPUs
; Return values .: A string representing the base2 value
; Author ........: TheXman + $bReorderIntBytes
; ===============================================================================================================================
Func _BinaryBits($vData, $bSpaces = True, $bReorderIntBytes = True)
    If $bReorderIntBytes And StringLeft(VarGetType($vData), 3) = "Int" Then $vData = "0x"&Hex($vData)
    Local $sBits, $dBin = Binary($vData), $iLen = BinaryLen($dBin), $xByte
    For $i = 1 To $iLen
        $xByte = BinaryMid($dBin, $i, 1)
        For $j = 7 To 0 Step -1
            If $bSpaces And $j = 3 Then $sBits &= " "
            $sBits &= (BitAND($xByte, 2 ^ $j) ? "1" : "0")
        Next
        If $i < $iLen And $bSpaces Then $sBits &= " "
    Next
    Return $sBits
EndFunc


; #FUNCTION# ====================================================================================================================
; Name ..........: _IntToString
; Description ...: Convert an integer to any base
; Parameters ....: $iInt           An integer to be converted to any base. Negative Int32 show as Int64
;                  $iBase          An integer value greater than 1 (seems infinite)
;                  $iWidth         Adds 0s to reach the specified width
;                  $bCheckInt32    Remove the Int64-related bits if $iBase = 2 and $iInt is a negative Int32
; Return values .: Success         A string representation of a integer value (in any base)
;                  Failure         0 and sets @error :
;                                  @error  1 = Invalid number base
;                                          2 = DllCall failed.  @extended = DllCall @error
; ===============================================================================================================================
Func _IntToString($iInt, $iBase, $iWidth = 0, $bCheckInt32 = False)
    If $iBase < 2 Then Return SetError(1, 0, "")
    Local $aRes = DllCall("msvcrt.dll", "str:cdecl", "_i64toa", "int64", $iInt, "str", "", "int", $iBase)
    If @error Then Return SetError(2, @error, "")
    Local $str = ($bCheckInt32 And $iBase = 2 And VarGetType($iInt) = "Int32" And $iInt < 0) ? StringRight($aRes[0], 32) : $aRes[0]
    Return $iWidth < 1 ? $str : StringFormat("%0" & $iWidth & "s", $str)
EndFunc




; #FUNCTION# ====================================================================================================================
; Name ..........: _StringToInt32
; Description ...: Convert a string, in the specified number base, to an Int32.
; Parameters ....: $sString        A string representation of a integer value (in a base from 2 to 36).
;                  $iBase          An integer value from 2 to 36.
; Return values .: Success         An int32 value of the string.
;                  Failure         0 and sets @error :
;                                  @error  1 = Invalid number base
;                                          2 = DllCall failed.  @extended = DllCall @error
; ===============================================================================================================================
Func _StringToInt32($sString, $iBase)
    If $iBase < 2 Or $iBase > 36 Then Return SetError(1, 0, 0x0)
    Local $aRes = DllCall("msvcrt.dll", "int64:cdecl", "_strtoi64", "str", $sString, "ptr*", 0, "int", $iBase)
    Return @error ? SetError(2, @error, 0x0) : Number($aRes[0], $NUMBER_32BIT)
EndFunc


; #FUNCTION# ====================================================================================================================
; Name ..........: _StringToInt64
; Description ...: Convert a string, in the specified number base, to an Int64. Must be converted to Int32 if the original was (otherwise negative numbers don't work)
; Parameters ....: $sString        A string representation of a integer value (in a base from 2 to 36).
;                  $iBase          An integer value from 2 to 36.
; Return values .: Success         An int64 value of the string.
;                  Failure         0 and sets @error :
;                                  @error  1 = Invalid number base
;                                          2 = DllCall failed.  @extended = DllCall @error
; ===============================================================================================================================
Func _StringToInt64($sString, $iBase)
    If $iBase < 2 Or $iBase > 36 Then Return SetError(1, 0, 0x0000000000000000)
    Local $aRes = DllCall("msvcrt.dll", "int64:cdecl", "_strtoi64", "str", $sString, "ptr*", 0, "int", $iBase)
    Return @error ? SetError(2, @error, 0x0000000000000000) : $aRes[0]
EndFunc

Output :

---- $dData ------------------------------------------------------------------------
Base16 value              : 0x303425637013293133FDA4D5
Base2 value               : 0011 0000 0011 0100 0010 0101 0110 0011 0111 0000 0001 0011 0010 1001 0011 0001 0011 0011 1111 1101 1010 0100 1101 0101
Bits 39-58                : 00000100110010100100
Int64 value of bits 39-58 : 19620
Int32 value of bits 39-58 : 19620
------------------------------------------------------------------------------------
---- $iInt -------------------------------------------------------------------------
Int32                       : -266321824
Binary                      : 0x604020F0
Hex                         : 0xF0204060
Bits (raw)                  : 0110 0000 0100 0000 0010 0000 1111 0000
Bits (reordered bytes)      : 1111 0000 0010 0000 0100 0000 0110 0000
Int32 from bits (raw)       : 1614815472
Int32 from bits (reordered) : -266321824
Int64 from bits (reordered) : 4028645472
------------------------------------------------------------------------------------
1111111111111111111111111111111111110000001000000100000001100000
Edited by Zehir
Posted (edited)

A little different :

; From Nine

Local $sHex = "303425637013293133FDA4D5"
Local $sBin
While $sHex
  $sBin &= _HexToBin(StringLeft($sHex, 16))
  $sHex = StringTrimLeft($sHex, 16)
WEnd

ConsoleWrite($sBin & @CRLF)
$sBin = StringMid($sBin, 39, 20)
ConsoleWrite($sBin & @CRLF)
ConsoleWrite(_StringToUint($sBin, 2) & @CRLF)

Func _HexToBin($_hex)
  Return StringFormat("%0" & 4 * StringLen($_hex) & "s", _UintToString(Dec($_hex), 2))
EndFunc   ;==>_HexToBin

Func _StringToUint($s, $base)
  Return DllCall("msvcrt.dll", "uint64:cdecl", "_strtoui64", "str", $s, "ptr*", 0, "int", $base)[0]
EndFunc   ;==>_StringToUint

Func _UintToString($i, $base)
  Return DllCall("msvcrt.dll", "str:cdecl", "_ui64toa", "uint64", $i, "str", "", "int", $base)[0]
EndFunc   ;==>_UintToString

 

Edited by Nine
Posted

Here my approach which is similar to Andreik's version.

;coded by UEZ build 2026-03-14
#Include <String.au3>

ConsoleWrite(ExtractBits("303425637013293133FDA4D5", 39, 58) & @CRLF)

Func Int2Bin($in)
    If IsFloat($in) Or IsString($in) Then Return SetError(1, 0, "")
    If $in = 0 Then Return 0
    Local $bin = "", $n = $in < 0
    If $n Then $in = -$in
    While $in
        $bin &= BitAND($in, 1)
        $in = BitShift($in, 1)
    WEnd
    Return ($n ? "-" : "") & StringReverse($bin)
EndFunc

Func ExtractBits($sHex, $bStart, $bEnd)
    Local $i, $sBin = "", $sExtractedBin, $iResult = 0, $n
    For $i = 1 To StringLen($sHex)
        $n = Dec(StringMid($sHex, $i, 1))
        If @error Then ContinueLoop
        $sBin &= StringFormat("%04s", Int2Bin($n))
    Next
    $sExtractedBin = StringReverse(StringMid($sBin, $bStart, $bEnd - $bStart + 1))
    For $i = 1 To StringLen($sExtractedBin)
        $n = StringMid($sExtractedBin, $i, 1)
        If Not $n Then ContinueLoop
        $iResult += $n * 2 ^ ($i - 1)
    Next
    Return $iResult
EndFunc

 

Please don't send me any personal message and ask for support! I will not reply!

Selection of finest graphical examples at Codepen.io

The own fart smells best!
Her 'sikim hıyar' diyene bir avuç tuz alıp koşma!
¯\_(ツ)_/¯  ٩(●̮̮̃•̃)۶ ٩(-̮̮̃-̃)۶ૐ

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...