Software Archive
Read-only legacy content

Multitasking

Intel_C_Intel
Employee
1,086 Views
Trying to improve the cooperation between legacy code recast as CVF DLLs and the Visual Basic wrapper programs that use them. Some of the DLLs run a very long time and thus keep Windows from servicing the message queue. On older PCs (like my P133 dino), this locks up the PC for the duration of the run and makes updating status dialogs (in VB) difficult.

Wondered if any of the forum users have any suggestions for preempting the DLL periodically, allowing the VB layer to update its status screens, and then resuming the DLL where it left off.

Thanks
0 Kudos
6 Replies
Steven_L_Intel1
Employee
1,086 Views
Usually, the way this is done is to periodically call back into VB, to a routine whose address you pass in, allowing VB to update the window, then return to the Fortran code.

Steve
0 Kudos
Intel_C_Intel
Employee
1,086 Views
Steve

Thanks - I thought that was the way, but I'm still struggling with the mechanics. Can you point me to a reasonably concise example of how CVF implements a callback - My approaches all seem to crash. I looked at the MS BB Help files and they jumped right off to the deep end - way more complicated than anything I need.

P..

Every time I try to reply to your posting, the forum software asks me to log in again and makes it look like I'm replying to my original posting. I'll look later to see what's up there - probably I'm just not familiar with the new forum operation.

Thanks
0 Kudos
Jugoslav_Dujic
Valued Contributor II
1,086 Views
Hi,

There's another approach, which I deem purer: let the fortran code run
in a thread, and pass a few synchronization objects through its arg-list so
that it could change their state from time to time; in this way, the caller
remains running. However, you have to ensure that nothing harmful happens in the VB caller in the meantime, i.e. you have to disable GUI options which may affect the calculation (e.g. you probably wouldn't like
the user to run the same calculation again while one's already running).

A simple but nice solution is to create a modal dialog box in VB caller with a progress bar (and, optionally, a "Cancel" button); that would enable the user _only_ to watch (or, possibly, cancel) the current operation, while VB window would remain normally painted. I mean something like this:

 
SUBROUTINE ProgressDialog_OnInitialize() 
 
!User-defined object for passing data 
TYPE T_SyncObj 
   INTEGER hProgressBar     !Handle of PB control 
   INTEGER hEvent               !Event used for cancelling 
END TYPE 
 
TYPE(T_SyncObj) SyncObj 
 
!TODO declare FortranCalc routine as appropriate; SyncObj 
!should be ByRef 
SyncObj%hProgressBar=GetDlgItem(hDialog, ID_PROGRESSBAR) 
SyncObj%hEvent=CreateEvent(NULL,.TRUE.,.FALSE.,NULL) 
hThread=CreateThread(NULL, 0, LOC(FortranCalc), LOC(SyncObj), 0, LOC(idThread)) 
 
END SUBROUTINE 
!============================= 
SUBROUTINE ProgressDialog_OnCancel() 
 
RaiseEvent(SyncObj%hEvent) 
EndDialog(hDialog) 
 
END SUBROUTINE 
!============================= 
INTEGER FUNCTION FortranCalc(SyncObj) 
!DEC$ATTRIBUTES STDCALL:: FortranCalc 
!DEC$ATTRIBUTES REFERENCE:: SyncObj 
 
TYPE(T_SyncObj)::   SyncObj 
 
DO i=1,many_iterations 
... 
     !Update progress bar 
     SendMessage(SyncObj%hProgressBar,PBM_STEPIT,0,0) 
     !Check if the user cancelled the operation 
     IF (WaitForSingleObject(SyncObj%hEvent,0).EQ.WAIT_OBJECT_0) THEN 
          FortranCalc=0 
          ResetEvent(SyncObj%hEvent) 
     END IF 
END DO 
FortranCalc=1 
 
END FUNCTION 


The code above is rather pseudo -- I'm not familiar with VB, but I hope you'll get the idea); of course, take care about the scope of type declarations. You can also put in T_SyncObj all parameters needed in arg-list. Take care that T_SyncObj is declared identical in VB and Fortran. Don't forget to CloseHandle(SyncObj%hEvent) after the dialog ends (I'm not sure if it's allowed to CloseHandle in FortranCalc).

HTH

Jugoslav
0 Kudos
Jugoslav_Dujic
Valued Contributor II
1,086 Views
...just to add, I forgot the obvious RETURN in the IF (WaitForSingleObject) block.
0 Kudos
Steven_L_Intel1
Employee
1,086 Views
The forum will ask you to log in again if you haven't done anything in the last 15 minutes. Annoying, I know.

When you reply, it shows you the initial topic, but you can see all of the replies if you scroll up. This message board is not threaded, so there is no concept of a "reply to a reply".

Steve
0 Kudos
Intel_C_Intel
Employee
1,086 Views
Since the original posting, I've belatedly found the sample "Callback" in SamplesB. I plan to investigate that approach so the the BB front end can do the heavy lifting and I can keep Fort ran "engine" from becoming too Windows-specific.

We are also planning to port our legacy code to NIX and Linux platforms, so whatever approach allows me to encapsulate the platform-specific stuff in an abstraction layer will probably be used. The sample code from Samples and that from I_hunter and Yugoslav Dujic will be evaluated in that light. When we settle on an approach, I'll try to remember to report it here.

One question about the two approaches cited - Are they compatible with a DELL (required to interface with VB) or do they require building the project as a QWIN or Windows project? I'll be able to answer this myself when I get back to the office - Don't have all of the tools here at home.

Thanks again.

Thanks to
0 Kudos
Reply