Intel® Fortran Compiler
Build applications that can scale for the future with optimized code designed for Intel® Xeon® and compatible processors.
Announcements
FPGA community forums and blogs on community.intel.com are migrating to the new Altera Community and are read-only. For urgent support needs during this transition, please visit the FPGA Design Resources page or contact an Altera Authorized Distributor.

SetConsoleCrtlHandler

reneeculver
Beginner
4,766 Views
Ian has been a remarkable help to me and I want to thank him.

Rather than have a special source for exiting, in that it was an example of a real program as opposed to the real thing, I have moved the code back to the sources. In doing that, I now have an accvio.

I guess I better explain what this does. First there's a handler that's setup. When a number event occurs the handler is called. Parsing for the argument occurs. The code "does the right thing" based on an argument on what event is occurring.

Part of the reason why I am having trouble debugging is that I'm used to a debbuger that uses addresses which MS doesn't. The handler does generate an address but it's not the correct one and because addresses are not used I can't tell how far off I am.

The code is:

SUBROUTINE SetupExit

USE KERNEL32, ONLY: SetConsoleCtrlHandler, BOOL, TRUE

INTEGER(BOOL) :: ff

ff = SetConsoleCtrlHandler(LOC(CloseWindow), TRUE)

END SUBROUTINE SetupExit

FUNCTION CloseWindow(number)

USE KERNEL32, ONLY: BOOL, DWORD, TRUE, FALSE

INTEGER(DWORD), INTENT(IN) :: number

INTEGER(BOOL) :: CloseWindow

!DEC$ ATTRIBUTES STDCALL :: CloseWindow

SELECT CASE (number)

CASE (0) ! Ctrl c

PRINT "('Oi!! Stop pressing Ctrl-C!')"

CloseWindow = TRUE

CASE (1) ! Ctrl break

PRINT "('Ouch!! That Ctrl-Break hurt!')"

CloseWindow = TRUE

CASE (2) ! Console Window close

PRINT "('Wait a tick - I don''t want to go away!')"

CloseWindow = TRUE

CASE DEFAULT ! 5 for log off, 6 for shutdown -

PRINT "('Bye bye!!')"

CloseWindow = FALSE

END SELECT

END FUNCTION CloseWindow

I haven't altered the code yet. It's still Ians.

The first accvio I get is:

Unhandled exception at 0x002ab537 in Adventure.exe: 0xC0000005: Access violation writing location 0x0000000000000000. It occurs when I try to close the window with the X that occurs at the top right of all windows.

Renee

0 Kudos
1 Solution
IDZ_A_Intel
Employee
4,755 Views
Hello reneeculver,

I tested your code with a test program and it seems fine. My code is:

[fortran]module my_setconsole

contains

    SUBROUTINE SetupExit

        USE KERNEL32, ONLY: SetConsoleCtrlHandler, BOOL, TRUE
        INTEGER(BOOL) :: ff
        ff = SetConsoleCtrlHandler(loc(CloseWindow), TRUE)
        continue
    END SUBROUTINE SetupExit

    INTEGER(BOOL) FUNCTION CloseWindow(number)
    !DEC$ ATTRIBUTES STDCALL :: CloseWindow

        USE KERNEL32, ONLY: BOOL, DWORD, TRUE, FALSE

        INTEGER(DWORD) :: number

        SELECT CASE (number)
            CASE (0) ! Ctrl c
                PRINT "('Oi!! Stop pressing Ctrl-C!')"
                CloseWindow = TRUE
            CASE (1) ! Ctrl break
                PRINT "('Ouch!! That Ctrl-Break hurt!')"
                CloseWindow = TRUE
            CASE (2) ! Console Window close
                PRINT "('Wait a tick - I don''t want to go away!')"
                CloseWindow = TRUE
            CASE DEFAULT ! 5 for log off, 6 for shutdown -
                PRINT "('Bye bye!!')"
                CloseWindow = FALSE
        END SELECT
    END FUNCTION CloseWindow 
end module my_setconsole

program close_handle
    USE IFCORE
    USE my_setconsole
    implicit none

    ! Variables
    logical :: pressed=.false.
    ! Body of close_handle
    Call SetupExit
    print *, 'Hello World'
    DO WHILE (.NOT. pressed)   
        pressed = PEEKCHARQQ ( )
        CALL SLEEPQQ (200) 
    END DO

end program close_handle[/fortran]

I've just inserted the subroutines inside a module and I've created a test program. Please try it and tell me if it works for you.

Pedro

View solution in original post

0 Kudos
41 Replies
reneeculver
Beginner
2,088 Views
Sorry, I was using the syntaxhighlighter as you requested.

The closing was a wild guess. That file drives Adventure and is open the whole time Adventure is open.

I will be happy to send you the project. That file is the first thing opened after the commons in the source.

Renee
0 Kudos
IDZ_A_Intel
Employee
2,088 Views
Please attach the project and sources to a post here. If you have doubts please see "Attaching or including files in a post" in one of Steve Lionel posts.

Pedro
0 Kudos
reneeculver
Beginner
2,088 Views
Well, I can see why "Attaching or including files in a post" only got two stars. It's not usable!

How do you use it? I have adventure.zip right here and I can't ship it because that stupid system does not work as far as I can tell......or should I read the release notes? :)

Renee
0 Kudos
IDZ_A_Intel
Employee
2,088 Views
Renee,

Using the instructions I managed to attach a file. No problem. I think Steve Lionel explanation is concise and clear. I will rate as 5 stars.

Pedro
0 Kudos
IDZ_A_Intel
Employee
2,088 Views
Renee,

It was "just" the STOP statement when handling the program close event. I also put the subroutines inside a module. There is another problem with the ctrl+c event. It is related to the fact that the program waits for keyboard user inputs. So it is trapped inside a read statement. I've corrected this in the first question (when it asks if the "gamer" wants help). The function I changed is named "yes". Take a look. If you only want to handle the window close event just forget this.

Pedro
0 Kudos
reneeculver
Beginner
2,088 Views
Thank you Pedro.

Allow me to tell you a couple of things about me. I was a high ranking engineer for the company that produced the compiler. Steve worked in the same building. We were the second largest computer company in the world. One of the things that made us so good, is that we wouldn't not have settled to such a message to customers. We were meticulous.

This really doesn't bother me. But it's the principle of the the thing. It's sloppy and DEC wouldn't have settled for it. That's why I am as meticulous as I am.

I deeply appreciate what you have done for me.

Renee
0 Kudos
IDZ_A_Intel
Employee
2,088 Views
Renee,

No problem. We are here to help each other.

Pedro
0 Kudos
Les_Neilson
Valued Contributor II
2,088 Views
I think this program should come with a health warning. :-)
Many years ago Igot into a lot of trouble for being (very) late to pick up my daughter because I was engrossed in playing the game and lost track of time.

Mother and daughter have forgiven me, for the moment.

Les
0 Kudos
reneeculver
Beginner
2,088 Views
Les,

I think I know what you mean.

Once again, I'd like to thank Pedro.

Renee
0 Kudos
reneeculver
Beginner
2,088 Views
I've been playing with this some more. Basically, I am confused because there are ways to leave the program without getting that message.

CNTRL-C will generate no message at all as the windows leaves which is the behavior I am looking for. I know Pedro has worked on CNTRL-Y. Currently without Pedro's fix, CNTRL-Y just shows up on the screen.

What does CNTRL-C do that the others dont do? There has to be a call to get the same behavior that CNTRL-C gets......

Renee
0 Kudos
IDZ_A_Intel
Employee
2,088 Views
Renee,
CNTRL-Y? Was that a typo? The problem here is that the program is trapped inside a read statement (waiting for the user to interact). What I've done was to replace the read(*,*). Take a look at function yes at the end of file "ASUBS.FOR". If you use the original yes function and press the ctrl+c you will get:
forrtl: severe (24): end-of-file during read, unit -4, file CONIN$
Which basically means that the program was closed, when it is expecting to read data from stdin.
Pedro
0 Kudos
Steven_L_Intel1
Employee
2,088 Views
Cntrl-Y is a VMS thing. As far as I know it doesn't have a meaning on Windows.
0 Kudos
reneeculver
Beginner
2,088 Views
Youre right steve and thank you Pedro.

Right now, what I need is a clean exit (without an error message) like what CNTRL-C gets from a console task like Adventure. Right now even a STOP in the SetConsoleCrtlHandler produces a Window Error. What I need is a call like Call Exit(1) that does will not have a error in Fortran. You know...a clean Exit.

Renee
0 Kudos
IDZ_A_Intel
Employee
2,088 Views
Renee,
The version I provided gives you a clean exit with ctrl+c and with the exit button.
Pedro
0 Kudos
reneeculver
Beginner
2,088 Views
With the red button at the top right of the frame??

Renee
0 Kudos
reneeculver
Beginner
2,088 Views
Pedro,

You were right!!! The STOP was the problem which I never would have guessed.

Thank you so much!!!

Renee
0 Kudos
IDZ_A_Intel
Employee
2,088 Views
Renee,
I thought you have already realized that. The project I attached in a previous post had all this issues corrected.
Pedro
0 Kudos
reneeculver
Beginner
2,088 Views
Had you said, "just remove the stops from CloseWidow that would have done iy.

I still don't know why no stop goes in there? By the way, I did not return to the module. Although there is a debugger breakpoint where ever I place, I still can't single step through it.

[bash] INTEGER(BOOL) FUNCTION CloseWindow(number)
!DEC$ ATTRIBUTES STDCALL :: CloseWindow
      USE KERNEL32, ONLY: BOOL, DWORD, TRUE, FALSE
      implicit none
      INTEGER(DWORD) :: number
      CloseWindow = TRUE
      SELECT CASE (number)
        CASE (0) ! Ctrl c
        CASE (1) ! Ctrl break
        CASE (2) ! Console Window close
        CASE DEFAULT ! 5 for log off, 6 for shutdown -
            CloseWindow = FALSE
      END SELECT
      END FUNCTION CloseWindow [/bash]
The code now looks like the above:

Renee
0 Kudos
IDZ_A_Intel
Employee
2,088 Views
Renee,
Use the project I posted. Place a breakpointinside CloseWindow (in the select case for example), run the program and press ctrl+c. You will hit the breakpoint.
Pedro
0 Kudos
reneeculver
Beginner
2,089 Views
Pedro.

Hitting the breakpoint is not an issue. Single stepping through CloseWindow after I hit the breakpoint is an issue. I still dont understand why it was the stop but the error message was basically about a stack imbalance. I wonder if the the STOP cause that stack imbalance to be reported?

Once again. thank you so much!!!

Renee
0 Kudos
IDZ_A_Intel
Employee
2,089 Views
Renee,
The STOP statment is a problem only when the close button is pressed (case 2). Because of this, I think that two close events are being generated: one with the STOP statment and another by windows manager.
Pedro
0 Kudos
Reply