No announcement yet.

GPF (unless MsgBox)

  • Filter
  • Time
  • Show
Clear All
new posts

  • GPF (unless MsgBox)

    This code (in the main Exe), IF the MsgBox is present, works as
    expected. Without the MsgBox, it gives a GPF in User.Exe.

    The main Exe module creates a dialog with

    Local Style As Long
     Style = %WS_SYSMENU Or _
             %WS_MINIMIZEBOX Or _
     Dialog New 0, "peAc MAIN MENU", 0, 0, 534, 372, Style, %WS_EX_CONTROLPARENT To pDlg&
    The first time this main Exe calls the DLL it sends the handle of this primary dialog to the
    DLL which places it in a global variable "xDlg&", and then creates two further dialogs with the
    style ---

    Style& = %DS_SETFONT Or _
              %DS_3DLOOK Or _
              %DS_NOFAILCREATE Or _
    'Or _
     Dialog New xDlg&, "Quotation cost summary", 0, 24, 423, 300, Style& To cDlg&
     Control Add Frame, cDlg&, %QEmbxFrm, "Quotation cost summary", 6, 1, 412, 297
     Control Send cDlg&, %QEmbxFrm, %WM_SETFONT, qhFont&, 1
     Style&= %DS_SETFONT Or _
             %WS_BORDER Or _
             %DS_NOFAILCREATE Or _
             %DS_SETFOREGROUND Or _
             %WS_VSCROLL Or _
    'Or _
     Dialog New xDlg&, "", 13, 64, 396, 250, Style& To sDlg&
    The sub "ExitQuend" is in the DLL module and does nothing more alarming than cleaning up.
    The handles of both dialogs created in the DLL are passed back to the main Exe as soon as
    they have been created.

    Point of all this: I don't NEED the MsgBox, but it seems that Windows does!

    Anyone have any ideas?

    Sub ExitSubSystem                               'in main Exe module
     If ActiveSystem$="Creditors/purchases/stock" Then
      Call ExitCreditors
      If ScrnName$="Main finishing machines" Or _
         ScrnName$="Sundry finishing machines" Or _
         ScrnName$="Manual finishing" Then Call ExitFinishing
      If ScrnName$="TypeSetting"  Or _
         ScrnName$="Reproduction" Or _
         ScrnName$="PaperCostCalc" Or _
         ScrnName$="InkCostCalc"  Or _
         ScrnName$="PmcCostCalc" Then Call ExitTpsRpr
      If ScrnName$="Outwork" Then Dialog End DLLdlg&
      If ScrnName$="QuLetter" Or _
         ScrnName$="WkTicket" Then Call ExitLetWt
      If ScrnName$="Despatch" Or _
         ScrnName$="Qcosting" Or _
         ScrnName$="Worktickets menu" Or _
         ScrnName$="Time dockets capturing" Then
       Call ExitQuend
       If ScrnName$="Qcosting" Then
        Dialog End DLLdlg&                       'This and/or
        Dialog End DlxDlg&                       'this gives the GPF  
        End If
       End If
      If ScrnName$="Job cost analysis" Or _
         ScrnName$="Estimated/actual job costs" Or _
         ScrnName$="Job cost adjustments" Then Call ExitPrint
      If SysInit&=1 Then
       If ScrnName$="Printing department" Then Dialog End pmDlg&, 1
       Dialog End hDlg&
       End If
      End If
     If StjSetup&=1 Then Call ExitStdSetupBasics
     Call RemoveMainMenu
     If ActiveSystem$="ProdMenu" Then
      If ScrnName$="Account status for new quotes" Or _
         ScrnName$="Bleed defaults for bookwork" Or _
         ScrnName$="Bleed defaults for jobbing" Or _
         ScrnName$="Categories of outwork" Or _
         ScrnName$="Cost sub-allocations" Or _
         ScrnName$="Markup: labour" Or _
         ScrnName$="Markup: material" Or _
         ScrnName$="Markup: outwork" Or _
         ScrnName$="Markup: paper" Or _
         ScrnName$="Paper suppliers' setups" Or _
         ScrnName$="Paper trim defaults" Or _
         ScrnName$="Workticket options" Then Call ExitMiscCust
      End If
     If StjSetup&=1 Then Call ExitStdSetupBasics
     End Sub
    Sub ExitQuend Alias "ExitQuend" Export                 'in DLL module
     Call DestroyBrushes
     If fcn$="QuLetter" Or fcn$="WkTicket" Then Dialog End sDlg&, 1
     If fcn$="WkTicket" Or fcn$="Worktickets menu" Then WtMenuSort$=""
     If fcn$<>"Qcosting" Then  Dialog End hDlg&, 1
     End Sub


  • #2
    There is nothing that stands out as to the cause in your small snippet, so I suspect you'll have to post the entire code so we can see how the "cleanup" code is being called, how you are pumping messages and launching the child dialogs from the main dialog callback, etc.

    PowerBASIC Support
    mailto:[email protected][email protected]</A>
    mailto:[email protected]


    • #3
      Lance, thank you. However, I tried to compromise between what is
      relevant and massive size, and before I was through it was over
      500 lines, and quite a bit to go -- and anything omitted might just
      be the very trouble area. So, I tried, tried and tried again, and came
      up with the brilliant, logical and sublimely elegant solution below,
      which solves the problem. WHAT logic! I am leaving it so for the nonce,
      only because it works, though I have not the foggiest as to WHY.
      Perhaps time will heal the scars of what pride one has left and some
      of the cranial fur torn out.

      If ScrnName$="Qcosting" Then
          Style& = %WS_POPUP Or _             'add a dummy dialog
                   %DS_SETFONT Or _           'instead of a messagebox 
                   %DS_NOFAILCREATE Or _      'and remove it immediately
                   %DS_MODALFRAME Or _        '
                   %DS_3DLOOK Or _
          Dialog New pDlg&, "", 300, 300, 10, 10, Style& To oDlg&
          Dialog End DLLdlg&
          Dialog End DlxDlg&
          Dialog End oDlg&
          End If
         End If
      Aha, you say, if THAT fixes it, then the problem is obviously ,,,



      • #4
        > if THAT fixes it, then the problem is obviously ,,,

        ... still unidentified.

        It could well be that something in your program is corrupting memory, and by changing your program (by adding a message box or other code) you are moving the corruption to a location that Windows doesn't care about. The problem may return soon, or it may not pop up again for months or years.

        Does the GPF also go away if you use #DEBUG ERROR ON?

        IMO it's always best to identify the true source of a GPF before moving on...

        -- Eric

        Perfect Sync Development Tools
        Perfect Sync Web Site
        Contact Us: mailto:[email protected][email protected]</A>
        "Not my circus, not my monkeys."


        • #5
          Yes, problem still isn't fixed. What does a MSGBOX STR$(ERR) tell
          you at this point? You may have a "hanging error" from an earlier
          place in code to take care of.

          A few other things to test: Add a bunch of DIALOG DOEVENTS to allow
          Windows to catch up in the message que. Give the dialog you want to
          destroy focus, via "SetFocus DLLdlg&", etc. Make sure DLLdlg& and
          DlxDlg& really have a value, so you don't try to end the desktop..
          Add a value to the calls, like "Dialog End DlxDlg&, 1" and trap the
          result of the action in variable used in DIALOG SHOW.. TO, like:
          DIALOG SHOW MODAL DlxDlg&, CALL DlgProc TO lResult& 
          MSGBOX STR$(lResult&) '<- trap the result of unloading
          BTW, all those IF/THEN's will be gone through, but only one can be
          valid. Suggest you use ELSEIF between then instead, or SELECT CASE,
          for better efficiency..


          [This message has been edited by Borje Hagsten (edited March 22, 2001).]


          • #6
            Probably, I am wrong, but this problem can be linked with hinstance.
            Note, dialogs were created in DLL.
            What happends if to execute Dialog End for childs in WM_DESTROY of main dialog and to wait until IsWindow becomes 0 ?

            I remember that I did global hook and started DDT in DLL with hook.
            DDT worked fine up to the final moment only - termination.

            Just now under Win2000 I created child dialogs in DLL and nothing happened.

            [This message has been edited by Semen Matusovski (edited March 22, 2001).]


            • #7
              Thank you all for the feedback.

              Eric, #Debug Error on is there at all times (whilst testing), in all modules. The GPF
              occurs depite that. Of course, it is totally unsatifactory to have
              an error "solved" in such a way -- it is no solution unless it is
              proven to be so, and mine certainly does not look like one at this point, its only
              temporary merit being that one CAN get on for the time being.

              To test a theory of my own, I have moved the dummy code from the point
              of closing these dialogs to the point (in the main Exe) immediately
              after they have been created:

              CallBack Function Qcosting
               Call CloseDLLdialogs
               Call MainHeading
               Call RemoveMainMenu
               Call RemoveSubMenu
               Dialog End hDlg&, 1
               DLLdlg&=CostSummary (ByVal pDlg&)
              ' Style& = %WS_POPUP Or _                 'This (imo) makes pDlg& aware of the two new dialogs
              '          %DS_SETFONT Or _               'which have been created in the DLL -- of which, at
              '          %DS_NOFAILCREATE Or _          'pDlg& level, there is no knowledge until oDlg& is
              '          %DS_MODALFRAME Or _            'created within the pDlg& environment: this, I think,
              '          %DS_3DLOOK Or _                'forces a 'stock-taking', and, lo and behold, there
              '          %DS_SETFOREGROUND              'are the two stepchildren, now recognised, registered.
              '                                         'Or, on the other hand, maybe not.
              ' Dialog New pDlg&, "", 300, 300, 10, 10, Style& To oDlg&
              ' Dialog End oDlg&
               End Function
              It also removes the GPF, but my theory (noted on the side) remains just that - a theory.
              I had done this and tested before opening my e-mail this morning, to find all those responses.

              Borje, MsgBox Str$(Err) shows zero when inserted BEFORE the two Dialog End instructions, and
              also after the first and before the second. After the second, the GPF occurs and no MsgBox.
              DDLdlg& and DlxDlg& do have values -- I checked that, to safeguard the desktop from destruction.

              I also tried ---

              Dialog Show Modeless sDlg&, Call CostCallback To Lresult&
              --- but this gives Error 491 (invalid register variable)

              As to Dialog DoEvents, I have none at all. In the case of a modal dialog, Windows takes care
              of the message pump. I have not yet discovered WHERE in a modeless dialog -- and particularly in
              a DLL which is not the main module and has no WinMain -- a message pump belongs. Maybe that is
              at the root of many of my problems!

              The untidy If ... Then block I agree about. I've been intending to make it into a Select Case
              block, but then the GPF interfered. I shall do so, however!

              Semen, I take your point. However, it is not clear (my own theory above) whether the main dialog
              needs to be FORCED into awareness of the dialogs created in the DLL. They do have handles as
              passed back to the main dialog directly after they are created, and these are non-zero,
              but are they "registered" as being dialogs, seen from the main dialog? After all, they have
              been foisted on the main dialog in the DLL, and may just be numbers, until a MsgBox (or dummy
              dialog) WITHIN THE MAIN DIALOG causes a review/reassessment of its current structure, and the
              two dialogs created in the DLL are now recognised for what they are (???).

              Thanks again.



              • #8

                This is turning into a "guessing game" since we can't see what your complete code is doing.

                Please post the entire code, or (no promises on how fast we can help) but you could also email it to Tech Support if you are worried about disclosing it in the public domain).

                As to the register variable error... unless specified with #REGISTER NONE in that function (or at the top of the whole file) the compiler is automatically assigning one or more of your variables as a register variables. See Register Variables in the help file for more info on how #REGISTER DEFAULT (the default setting) assigns register variables.

                PowerBASIC Support
                mailto:[email protected][email protected]</A>
                mailto:[email protected]


                • #9
                  > As to Dialog DoEvents, I have none at all. In the case of a modal
                  > dialog, Windows takes care of the message pump.

                  Yes, for the dialog itself, but Windows can't do anything about
                  programmed loops, etc. Try a DO/INCR I/LOOP UNTIL I = 99999999999
                  with no DIALOG DOEVENTS in and your dialog will simply freeze while
                  the loop is using all processor time to reach given number.

                  Probably not the cause of this problem, but a good tip is to try
                  DIALOG DOEVENTS here and there in code, because it can often speed
                  up things like repainting a dialog after resize, etc. It also allows
                  other processes to finish up before you try to load/unload a dialog..

                  A good example is when you want to flash a progressbar and action
                  starts in WM_INITDIALOG. MODAL or MODELESS doesn't matter. Without
                  a series of DOEVENTS, maybe even 8-10 of them in a row, you often
                  find that action starts before the progressbar is visible, so the
                  initial dialog is empty and controls end up on screen, one by one,
                  when your dialog gets a slice of the processor time, enough long to
                  actually paint them on screen. In slow computers, this is a common
                  problem that makes many newer applications look real "amateurish",
                  compared to old days often more speedy code. DOEVENTS can often add
                  a professional touch and feeling to your apps..

                  As Lance said, it's a guessing game. What happens if you copy entire
                  project to another folder, strip out all working code from the dialogs
                  and then try again, using almost empty main dialog, DLL and childs?

                  Semen was onto something worth investigating. Maybe you can try to simply
                  set showstate hidden/show and destroy the DLL's dialogs in its WM_DESTROY,
                  so they destruct automatically when the DLL is unloaded at exit?



                  • #10
                    Lance, by "entire code" do you mean the main module and all DLL's in
                    "runnable" state? If so, PowerBASIC will first have to get a bigger building - they add up to 197,414 lines of text, which zips up to
                    934,112 bytes.

                    If you are referring only to the bits in any way related to the problem
                    area, it could still be in excess of 1,000 text lines, at a guess.
                    This, of course, won't be "runnable". I take it you mean this second
                    option, but please confirm!

                    I'll try the REGISTER NONE and see how I go, thanks.

                    Borje, I'll see what I can find out about how to use the Dialog DoEvents in Petzold Edition 5. What you say about it is very interesting, but
                    as I have no knowledge nor experience of it, I'll feel my way. Very
                    likely there are examples in Samples and/or the Petzold C-to-PB code.
                    The "professional feel" is of course important, and I do have one home-
                    made progress bar which takes a while to show up on a blank dialog.

                    In fact this whole story starts with an "unprofessional feel" problem:
                    the reason for making the main dialog a CONTROPARENT and all others
                    CHILD dialogs is that otherwise, when you move the main dialog, the
                    secondary ones stays put, and also, the new way permits one to
                    minimise the main dialog and all its progeny, whereas previously, if
                    the main dialog is minimised, the others remain on screen -- and,
                    without minimise boxes.



                    • #11
                      You'd really have to provide compilable code, but I don't have time to wade through 200K lines of code - sorry!

                      Maybe you could do as Borje suggested: duplicate the app directory and strip out everything that is irrelevent to the problem (ie, leaving just the GUI code).

                      PowerBASIC Support
                      mailto:[email protected][email protected]</A>
                      mailto:[email protected]


                      • #12
                        Dieny --
                        to destroy is much easy than to construct.
                        I debug big programs by very simple way.
                        I copy a program to another directory and step by step cut fragments.
                        When a code becomes to work correctly, I analyze last deleted fragment.

                        E-MAIL: [email protected]