This example demonstrates the use of both the queuing and callback mechanisms in event handling. In the program, a message is sent to a GPIB device telling it to read some data. When the data collection is complete, the device asserts SRQ, informing the program that it can now read data. After reading the device's status byte, the handler begins to read asynchronously using a buffer of information that the main program passes to it.

C Example

#include "visa.h"
#include <stdlib.h>

#define MAX_CNT 1024

/* This function is to be called when an SRQ event occurs */
/* Here, an SRQ event indicates the device has data ready */
ViStatus _VI_FUNCH myCallback(ViSession vi, ViEventType etype, ViEvent eventContext, ViAddr userHandle)
{

   ViJobId    jobID;
   ViStatus   status;
   ViUInt16   stb; 

status = viReadSTB(vi, &stb);
status = viReadAsync(vi,(ViBuf)userHandle,MAX_CNT,&jobID);
return VI_SUCCESS;

}

int main(void)
{

   ViStatus     status;
   ViSession    defaultRM, gpibSesn;
   ViBuf        bufferHandle;
   ViUInt32     retCount;
   ViEventType  etype;
   ViEvent      eventContext; 

/* Begin by initializing the system */
status = viOpenDefaultRM(&defaultRM);
if (status < VI_SUCCESS) {

        /* Error initializing VISA...exiting */
        return -1;

    }
    /* Open communication with GPIB device at primary address 2 */
    status = viOpen(defaultRM, "GPIB0::2::INSTR", VI_NULL, VI_NULL, &gpibSesn);

    /* Allocate memory for buffer */
    /* In addition, allocate space for the ASCII NULL character */
    bufferHandle = (ViBuf)malloc(MAX_CNT+1);
    
    /* Tell the driver what function to call on an event */
    status = viInstallHandler(gpibSesn, VI_EVENT_SERVICE_REQ, myCallback, bufferHandle);

    /* Enable the driver to detect events */
    status = viEnableEvent(gpibSesn, VI_EVENT_SERVICE_REQ, VI_HNDLR, VI_NULL);
    status = viEnableEvent(gpibSesn, VI_EVENT_IO_COMPLETION, VI_QUEUE, VI_NULL);

    /* Tell the device to begin acquiring a waveform */
    status = viWrite(gpibSesn, "E0x51; W1", 9, &retCount);

    /* The device asserts SRQ when the waveform is ready */
    /* The callback begins reading the data */
    /* After the data is read, an I/O completion event occurs */

    status = viWaitOnEvent(gpibSesn, VI_EVENT_IO_COMPLETION, 20000, &etype, &eventContext);
    if (status < VI_SUCCESS) {

        /* Waveform not received...exiting */
        free(bufferHandle);
        viClose(defaultRM);
        return -1;
    }
    /* Your code should process the waveform data */

    /* Close the event context */
    viClose(eventContext);

    /* Stop listening for events */
    status = viDisableEvent(gpibSesn, VI_ALL_ENABLED_EVENTS, VI_ALL_MECH);
    status = viUninstallHandler(gpibSesn, VI_EVENT_SERVICE_REQ, myCallback,bufferHandle);

    /* Close down the system */
    free(bufferHandle);
    status = viClose(gpibSesn);
    status = viClose(defaultRM);
    return 0;

}

Visual Basic Example

Visual Basic does not support callback handlers, so currently the only way to handle events is through viWaitOnEvent(). Because Visual Basic does not support asynchronous operations either, this example uses the viRead() call instead of the viReadAsync() call.

Private Sub vbMain()

    Const MAX_CNT = 1024

   Dim stat              As ViStatus
   Dim dfltRM            As ViSession
   Dim sesn              As ViSession
   Dim bufferHandle      As String
   Dim retCount          As Long
   Dim etype             As ViEventType
   Dim event             As ViEvent
   Dim stb               As Integer

Rem Begin by initializing the system
Rem NOTE: For simplicity, we will not show error checking
stat = viOpenDefaultRM(dfltRM)
If (stat < VI_SUCCESS) Then

    Rem Error initializing VISA...exiting
    Exit Sub

   End If

   Rem Open communication with GPIB device at primary address 2
   stat = viOpen(dfltRM, "GPIB0::2::INSTR", VI_NULL, VI_NULL, sesn)

   Rem Allocate memory for buffer
   Rem In addition, allocate space for the ASCII NULL character
   bufferHandler = Space$(MAX_CNT + 1)

   Rem Enable the driver to detect events
   stat = viEnableEvent(sesn, VI_EVENT_SERVICE_REQ, VI_QUEUE, VI_NULL)

   Rem Tell the device to begin acquiring a waveform
   stat = viWrite(sesn, "E0x51; W1", 9, retCount)

   Rem The device asserts SRQ when the waveform is ready
   stat = viWaitOnEvent(sesn, VI_EVENT_SERVICE_REQ, 20000, etype, event)
   If (stat < VI_SUCCESS) Then

    Rem Waveform not received...exiting
    stat = viClose (dfltRM)
    Exit Sub

   End If
   stat = viReadSTB (sesn, stb)

   Rem Read the data
   stat = viRead(sesn, bufferHandle, MAX_CNT, retCount)
   Rem Your code should process the waveform data

   Rem Close the event context
   stat = viClose (event)
 
   Rem Stop listening for events
   stat = viDisableEvent(sesn, VI_ALL_ENABLED_EVENTS, VI_ALL_MECH)

   Rem Close down the system
   stat = viClose(sesn)
   stat = viClose(dfltRM)

End Sub