1. Dan Cooperstock
  2. PowerBuilder
  3. Friday, 01 March 2019

This is in PB 2017 R3. I'm having a weird problem where some code I'm using to try to determine whether an instance of my app is already running is somewhat randomly crashing the compiled program (or PB if I run from there or use the debugger).

I have an external function declaration as follows:

FUNCTION long GetWindowText(ulong handle, ref string wintext, long length) Library "user32.dll" alias for "GetWindowTextW"

The I call it as follows (having determined the ULong handle value ulHwnd somehow):

String lsTitle, lsTitleStart = "text to search for"
lsTitle = String(200)
if gnv_environment.GetWindowText(ulHwnd, REF lsTitle, 200) > 0 then
    if Pos(lsTitle, lsTitleStart) = 0 then
        ....

I have seen in the debugger where the GetWindowText succeeds (I see a value for lsTitle) but then PB crashes on the next line, looking for lsTitleStart in lsTitle. Other times it crashes other places in the larger function containing this (or sometimes doesn't crash if I put enough debugging messageboxes into the code at various places).

So my intuition is that the GetWindowText is somehow screwing things up in PB's internal memory. But I don't know how. And oddly enough, another function that calls GetWindowText seems to always work. But I'm pretty sure it's what is causing the problem in this function, because if I eliminate that call, it never crashes (so far!).

Any thoughts, or other similar experience? Thanks.

Who is viewing this page
Accepted Answer
Roland Smith Accepted Answer Pending Moderation
0
Votes
Undo

You need:

lsTitle = Space(200)

Instead of:

lsTitle = String(200)

 

Comment
Oh my. That is almost certainly the right answer. Feeling really dumb. :(
  1. Dan Cooperstock
  2. Saturday, 2 March 2019
There are no comments made yet.
  1. Friday, 1 March 2019
  2. PowerBuilder
  3. # Permalink
Roland Smith Accepted Answer Pending Moderation
0
Votes
Undo

Maybe instead you should use a Mutex to prevent multiple copies. It isn't dependent on the window title which could change.

http://www.topwizprogramming.com/freecode_mutex.html

 

Comment
I was also using the mutex - I was only showing the part of the code with the problem. But then I have to find the previous instance app to try to activate it, or in some cases send a message to it.
  1. Dan Cooperstock
  2. Saturday, 2 March 2019
That is how PBSearch does it, a GetWindow loop that calls GetWindowText.
  1. Roland Smith
  2. Saturday, 2 March 2019
There are no comments made yet.
  1. Friday, 1 March 2019
  2. PowerBuilder
  3. # 1
Olan Knight Accepted Answer Pending Moderation
0
Votes
Undo


We make the same check on a process that we kick off using this:

string          ls_exe_title
uint            val

ls_exe_title =
val             = FindWindowW(0, ls_exe_title)

IF (val = 0) THEN
   ...the exe is not currently running
END IF

 

In another utility, we also use this trick:

// In the OPEN event of the application
// ---------------------------------------------------
IF Handle( This, TRUE ) <> 0 THEN
    MessageBox( "Application Error", this.DisplayName + " is already running.", StopSign! )
    Return
END IF

 

Maybe one of those will accomplish what you need.


Good Luck,

Olan

Comment
We can't do such a simple FindWindow because the title bar varies depending on the user's data.



And the current docs says if the 2nd arg to Handle is TRUE, it always returns 0.



So I'm not sure either of these suggestions would work for me.
  1. Dan Cooperstock
  2. Friday, 1 March 2019
There are no comments made yet.
  1. Friday, 1 March 2019
  2. PowerBuilder
  3. # 2
  • Page :
  • 1


There are no replies made for this question yet.
However, you are not allowed to reply to this question.