Jump to content

[SOLVED] Unknown Race Condition on 32-bit OS Only


KongMD
 Share

Recommended Posts

Hi, everyone. In essence, all I'm trying to do with my script is click a button. The code below, compiled as a 32-bit executable, will press the button 100% of the time on a 64-bit OS. On a 32-bit OS, the script presses the button unpredictably: approximately 1-2% of the times I've ran the executable. I can't say for certain that this is based purely on the cpu architecture of the system the program is running on, but I've gotten the script to work on two computers with 64-bit Win 7, and have had it fail on 4+ computers running 32-bit Win 7.

I've tried variations of the script using ControlSend, ControlClick, setting focus, and even with just the raw Send function(window and button handles are correct, I checked). My goal is to find the race condition, with your help, and mitigate it. Here's the code in its entirety:

#include <constants.au3>
#include <GUIConstantsEx.au3>
#include <StaticConstants.au3>
#include <WinAPI.au3>
; UAC fix
#RequireAdmin
#AutoIt3Wrapper_Res_requestedExecutionLevel=requireAdministrator
Opt('WinWaitDelay',250)
Opt('WinDetectHiddenText',1)
Opt('MouseCoordMode',0)
Opt("WinTitleMatchMode", 2)
Global $kPath = ""
Global $utilsDir = @TempDir & "\Kaspersky Installation\Automation Utilities"

If @OSArch = "X86" Then
$scriptExe = "KasperskyAutomated x86.exe"
$kPath = @ProgramFilesDir & "\Kaspersky Lab\Kaspersky Anti-Virus 6.0 for Windows Workstations MP4\avp.exe"
ElseIf @OSArch = "X64" Then
$scriptExe = "KasperskyAutomated x64.exe"
$kPath =  EnvGet('ProgramFiles(x86)') & "\Kaspersky Lab\Kaspersky Anti-Virus 6.0 for Windows Workstations MP4\avp.exe"
EndIf

Dim $sProcess = $kPath
Dim $hProcess
Dim $tPI = DllStructCreate($tagPROCESS_INFORMATION), $pPI = DllStructGetPtr($tPI)
Dim $tSI = DllStructCreate($tagSTARTUPINFO), $pSI = DllStructGetPtr($tSI)
    DllStructSetData($tSI, 'Size', DllStructGetSize($tSI))
Dim $iSuccess = _WinAPI_CreateProcess('', $sProcess, 0, 0, False, 0, 0, 0, $pSI, $pPI)

If Not $iSuccess Then
    MsgBox(0x10, 'Error!', 'Could not create the process!!!')
Else
    _WinAPI_CloseHandle(DllStructGetData($tPI, 'hThread'))
    $hProcess = DllStructGetData($tPI, 'hProcess')
    _WinAPI_WaitForInputIdle($hProcess)
    ;MsgBox(0x40, 'Success!', 'process initialization has completed!!!')
If(ProcessExists("avp.exe")) Then
  ShellExecute($kPath, @SW_SHOW) ;bring program up from out of the tray
EndIf

_WinAPI_WaitForInputIdle($hProcess)
    MsgBox(0, 'Success!', 'process initialization has completed!!!')
$mainWin = WinGetHandle("Kaspersky Anti-Virus 6.0 for Windows Workstations")
$settingsBtn = ControlGetHandle($mainWin, "", "AVP.Button1")

;Sleep(3000)
ControlFocus ($mainWin, "", $settingsBtn)
;Sleep(3000)
MsgBox(0, "debug line " & @ScriptLineNumber, "@error = " & @error)
Send("{ENTER}")
MsgBox(0, "debug line " & @ScriptLineNumber, "@error = " & @error)
EndIf
Edited by KongMD
Link to comment
Share on other sites

Ok, brainstorm with me. It's not that the script is going too quickly, because I put in another WaitForInputIdle after giving the button the focus, but before clicking it (I also tried Sleep statements, just for kicks). It's not that the program has the wrong handles, because I can see the window actually come to the foreground with the button "highlighted", when the ControlFocus statement is called. I checked in Window Detective, and the button in question is a direct child of the main Kaspersky window, so it probably isn't anomalous parent/child behavior. I also commented out the MsgBoxes a couple times, to make sure they weren't stealing the focus.

So, the question is...why would clicking a button only work some of the time in 32-bit Windows, but work 100% of the time in 64-bit Windows? Could there be some kind of dependency that's not being fulfilled? Can I use any other method to press this button, other than MouseClick, ControlClick, ControlSend, and Send? I've spent the past two weeks or so trying to solve this one bug, and am not going to let this script defeat me this easily :)

Link to comment
Share on other sites

So, I tried using the Windows On-Screen Keyboard, but that doesn't work correctly with Kaspersky, either. I have the button highlighted, but am experiencing the same behavior as with the script, where clicking the spacebar or enter key does nothing in the program. The Windows On-Screen Keyboard works when sending input to the program on 64-bit Windows 7, however.

Where are these keystrokes going? Is there a program I can use to figure it what's intercepting my keystrokes?

Link to comment
Share on other sites

I've solved the problem! Kaspersky has a feature called "Self-Defense", in which it denies outside access to files and Registry keys owned by the application. This is what was blocking my script. You can go around this by doing one of two things:

1) Add your application to the "Trusted Zone", under the Protection part of Settings

2) Uncheck either of the two checkboxes in the Settings-->Options-->Self-Defense category

I'll have to lobby my system admin to set up a file mask to allow my script, which I can then delete after everything's configured and updated.

Link to comment
Share on other sites

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
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...