#3968 assigned Bug

global struct gets corrupted after GUISetState() — at Version 6

Reported by: argumentum Owned by:
Milestone: Component: AutoIt
Version: 3.3.16.1 Severity: None
Keywords: Struct Cc:

Description (last modified by mLipok)

#include <WinAPISys.au3> ; for $tagLOGFONT ;
Global $___gt__HiDpi_WinFont, $sFont
_SystemParametersInfo_GetSystemFont()
$hGUI = GUICreate('Test', 400, 400)

GUISetState(@SW_SHOW, $hGUI) ; try the code with this and without it

ConsoleWrite("Font : Attributes: " & $___gt__HiDpi_WinFont.Attributes & @CRLF)
ConsoleWrite("Font :     Weight: " & DllStructGetData($___gt__HiDpi_WinFont, 'Weight') & @CRLF)
ConsoleWrite("Font :    Quality: " & DllStructGetData($___gt__HiDpi_WinFont, 'Quality') & @CRLF)
ConsoleWrite("Font :   FaceName: " & DllStructGetData($___gt__HiDpi_WinFont, 'FaceName') & @CRLF)
ConsoleWrite("Font :   FaceName: " & $sFont & @CRLF) ; this never changes

Func _SystemParametersInfo_GetSystemFont()
        Local $dMenuFont = Binary(RegRead('HKEY_CURRENT_USER\Control Panel\Desktop\WindowMetrics', 'MenuFont'))
        ConsoleWrite($dMenuFont & @CRLF)
        Local $tLOGFONT = DllStructCreate('byte[' & BinaryLen($dMenuFont) & ']')
        DllStructSetData($tLOGFONT, 1, $dMenuFont)
        $___gt__HiDpi_WinFont = DllStructCreate($tagLOGFONT, DllStructGetPtr($tLOGFONT))
        $sFont = DllStructGetData($___gt__HiDpi_WinFont, 'FaceName')
EndFunc

While troubleshooting we discovered a bug.
The thread is at https://www.autoitscript.com/forum/topic/210637-systemparametersinfo-getsystemfont-i-made-an-ugly-bug/?do=findComment&comment=1522165

Change History (6)

comment:1 by argumentum, on Aug 3, 2023 at 1:37:51 AM

so, the bug was in the coder.
This works as advertised:

#include <WinAPISys.au3>
#include <WinAPIsysinfoConstants.au3>

Global $___gt__HiDpi_WinFont = _SystemParametersInfo_GetSystemFont()

$hGUI = GUICreate('Test', 400, 400)
GUISetState(@SW_SHOW, $hGUI)

ConsoleWrite("Font : Attributes: " & $___gt__HiDpi_WinFont.Attributes & @CRLF)
ConsoleWrite("Font :     Weight: " & $___gt__HiDpi_WinFont.Weight & @CRLF)
ConsoleWrite("Font :    Quality: " & $___gt__HiDpi_WinFont.Quality & @CRLF)
ConsoleWrite("Font :   FaceName: " & $___gt__HiDpi_WinFont.FaceName & @CRLF)


Func _SystemParametersInfo_GetSystemFont()
    Local $tLOGFONT = DllStructCreate(StringReplace($tagLOGFONT, 'OutPrecision', 'Attributes'))
    Local $iSize = DllStructGetSize($tLOGFONT)
    Local $tNONCLIENTMETRICS = DllStructCreate("STRUCT;uint cbsize;int iBorderWidth;int iScrollWidth;int iScrollHeight;int iCaptionWidth;" & _
    "int iCaptionHeight;byte lfCaptionFont[" & $iSize & "];int iSmCaptionWidth;int iSmCaptionHeight;byte lfSmCaptionFont[" & $iSize & "];int iMenuWidth;" & _
    "int iMenuHeight;byte lfMenuFont[" & $iSize & "];byte lfStatusFont[" & $iSize & "];byte lfMessageFont[" & $iSize & "];int iPaddedBorderWidth;ENDSTRUCT")
    $tNONCLIENTMETRICS.cbsize = DllStructGetSize($tNONCLIENTMETRICS)
    If Not _WinAPI_SystemParametersInfo($SPI_GETNONCLIENTMETRICS, $tNONCLIENTMETRICS.cbsize, $tNONCLIENTMETRICS) Then Return SetError(@error, @extended, 0)
    Local $tTemp = DllStructCreate($tagLOGFONT, DllStructGetPtr($tNONCLIENTMETRICS, "lfCaptionFont"))
    With $tLOGFONT
        .Weight = $tTemp.Weight
        .FaceName = $tTemp.FaceName
        .Quality = $tTemp.Quality
        .Attributes = BitOR(($tTemp.Italic ? 2 : 0),($tTemp.Underline ? 4 : 0),($tTemp.Strikeout ? 8 : 0))
    EndWith
    Return $tLOGFONT
EndFunc

Do pardon my lack of experience if you would.

Last edited on Aug 22, 2023 at 2:55:46 PM by mLipok (previous) (diff)

comment:2 by Jos, on Aug 3, 2023 at 9:31:03 AM

Resolution: No Bug
Status: newclosed

comment:3 by Jpm, on Aug 3, 2023 at 12:51:57 PM

In case it help the error was coming from the fact thatthe global variable was assign to a local variable
the correction is

#include <WinAPISys.au3> ; For $tagLOGFONT ;
Global $g_sFont
Global $___gt__HiDpi_WinFont= _SystemParametersInfo_GetSystemFont()

Local $hGUI = GUICreate('Test', 400, 400)

GUISetState(@SW_SHOW, $hGUI) ; try the code with this and without it

ConsoleWrite("Font : Attributes: " & $___gt__HiDpi_WinFont.Attributes & @CRLF)
ConsoleWrite("Font :     Weight: " & DllStructGetData($___gt__HiDpi_WinFont, 'Weight') & @CRLF)
ConsoleWrite("Font :    Quality: " & DllStructGetData($___gt__HiDpi_WinFont, 'Quality') & @CRLF)
ConsoleWrite("Font :   FaceName: " & DllStructGetData($___gt__HiDpi_WinFont, 'FaceName') & @CRLF)
ConsoleWrite("Font :   FaceName: " & $g_sFont & @CRLF) ; this never changes

Func _SystemParametersInfo_GetSystemFont()
        Local $dMenuFont = Binary(RegRead('HKEY_CURRENT_USER\Control Panel\Desktop\WindowMetrics', 'MenuFont'))
        ConsoleWrite($dMenuFont & @CRLF)
        Local $tLOGFONT = DllStructCreate('byte[' & BinaryLen($dMenuFont) & ']')
        DllStructSetData($tLOGFONT, 1, $dMenuFont)
        Local $tTemp = DllStructCreate($tagLOGFONT, DllStructGetPtr($tLOGFONT))
        $g_sFont = DllStructGetData($___gt__HiDpi_WinFont, 'FaceName')
        Return $tTemp
EndFunc   ;==>_SystemParametersInfo_GetSystemFont

Cheers

Last edited on Aug 22, 2023 at 2:56:07 PM by mLipok (previous) (diff)

comment:4 by argumentum, on Aug 5, 2023 at 6:59:06 PM

hmm, I've run the correction you posted here but it does not correct the original code that is observable while running over and over again while testing.

comment:5 by Jpm, on Aug 12, 2023 at 2:40:19 PM

Resolution: No Bug
Status: closedreopened

Hi
I understand that the return is erratic even If I fix the

$g_sFont = DllStructGetData($_gtHiDpi_WinFont, 'FaceName')
to
$g_sFont = DllStructGetData($tTemp, 'FaceName')
I don't understand the influence of the position of
Global $_gtHiDpi_WinFont= _SystemParametersInfo_GetSystemFont()
which is ok after the
GUISetState(@SW_SHOW, $hGUI) ; try the code with this and without it
here is the code which is erratic

#include <WinAPISys.au3> ; For $tagLOGFONT ;
Global $g_sFont
Local $___gt__HiDpi_WinFont= _SystemParametersInfo_GetSystemFont()

Local $hGUI = GUICreate('Test', 400, 400)

GUISetState(@SW_SHOW, $hGUI) ; try the code with this and without it

ConsoleWrite("Font : Attributes: " & $___gt__HiDpi_WinFont.Attributes & @CRLF)
ConsoleWrite("Font :     Weight: " & DllStructGetData($___gt__HiDpi_WinFont, 'Weight') & @CRLF)
ConsoleWrite("Font :    Quality: " & DllStructGetData($___gt__HiDpi_WinFont, 'Quality') & @CRLF)
ConsoleWrite("Font :   FaceName: " & DllStructGetData($___gt__HiDpi_WinFont, 'FaceName') & @CRLF)
ConsoleWrite("Font :   FaceName: " & $g_sFont & @CRLF) ; this never changes

Func _SystemParametersInfo_GetSystemFont()
        Local $dMenuFont = Binary(RegRead('HKEY_CURRENT_USER\Control Panel\Desktop\WindowMetrics', 'MenuFont'))
        ConsoleWrite(BinaryLen($dMenuFont) & @CRLF)
        ConsoleWrite($dMenuFont & @CRLF)
        Local $tLOGFONT = DllStructCreate('byte[' & BinaryLen($dMenuFont) & ']')
        DllStructSetData($tLOGFONT, 1, $dMenuFont)
        Local $tTemp = DllStructCreate($tagLOGFONT, DllStructGetPtr($tLOGFONT))
        $g_sFont = DllStructGetData($tTemp, 'FaceName')
        Return $tTemp
EndFunc   ;==>_SystemParametersInfo_GetSystemFont

Last edited on Aug 22, 2023 at 2:56:30 PM by mLipok (previous) (diff)

comment:6 by mLipok, on Aug 22, 2023 at 2:55:20 PM

Description: modified (diff)
Note: See TracTickets for help on using tickets.