Using a callback mechanism with Globus

Abstract

This tip describes a callback mechanism to use in Grid applications using non-blocking calls and the globus Toolkit.

Contents

A callback is a C function provided as a parameter to an asynchronous Globus function that is invoked after the call of the function. The Globus call is non-blocking in that it does not wait for the operation to complete. Instead the Globus call returns immediately. The callback will be invoked after the call in a different thread. Consequently, a synchronization mechanism must be used between the callback thread and the program thread that called the asynchronous call so that the program knows when the callback has been made.

To ensure thread-safety for the application, a mutex coupled with a condition variable must be used for synchronization. The condition variable is used to send a signal from the callback function to the main program, and the mutex is used jointly with the condition variable to avoid deadlocks between the waiting thread and the active thread.

The thread in the main program that calls the asynchronous globus function must call the following globus_thread functions to wait for the completion of the operation:

globus_mutex_lock(&mutex);
while(done==GLOBUS_FALSE)
globus_cond_wait(&cond, &mutex);
globus_mutex_unlock(&mutex);

In this code, <done> is a boolean variable initialized to false or GLOBUS_FALSE. <done> indicates the state of the operation.

The callback function must call:

globus_mutex_lock(&mutex);
done = GLOBUS_TRUE;
globus_cond_signal(&cond);
globus_mutex_unlock(&mutex);

This mechanism is implemented here via the ITSO_CB class that embeds the <done> variable as an attribute. ITSO_CB provides the necessary methods:

Wait() waits for the completion of the operation.

setDone() sets the status of the operation to “done”. The done attribute is actually set to true.

IsDone() retrieves the state of the operation (done or not) and checks the value of the done attribute.

Continue() resets the value of the attribute done to false.

Sample callback code:


itso_cb.h

#ifndef ITSO_CB_H
#define ITSO_CB_H
#include <cstdio>
#include <iostream>
#include <globus_common.h>

class ITSO_CB {
globus_mutex_t mutex;
globus_cond_t cond;
globus_bool_t done;
public:
ITSO_CB() {
globus_mutex_init(&mutex, GLOBUS_NULL);
globus_cond_init(&cond, GLOBUS_NULL);
done = GLOBUS_FALSE ;
};
~ITSO_CB() {
globus_mutex_destroy(&mutex);
globus_cond_destroy(&cond);
};
globus_bool_t IsDone();
void setDone();
void Continue();
virtual void Wait();
};
#endif

itso_cb.C

#include "itso_cb.h"

globus_bool_t ITSO_CB::IsDone() { return done; };

void ITSO_CB::setDone() {
globus_mutex_lock(&mutex);
done = GLOBUS_TRUE;
globus_cond_signal(&cond);
globus_mutex_unlock(&mutex);
}

void ITSO_CB::Continue() {
globus_mutex_lock(&mutex);
done = GLOBUS_FALSE;
globus_mutex_unlock(&mutex);
}

void ITSO_CB::Wait() {
globus_mutex_lock(&mutex);
while(!IsDone())
globus_cond_wait(&cond, &mutex);
globus_mutex_unlock(&mutex);
};

Special Notices

This material has not been submitted to any formal IBM test and is published AS IS. It has not been the subject of rigorous review. IBM assumes no responsibility for its accuracy or completeness. The use of this information or the implementation of any of these techniques is a client responsibility and depends upon the client's ability to evaluate and integrate them into the client's operational environment.

Profile

Publish Date
22 May 2003


Rating: Not yet rated


Author(s)

IBM Form Number
TIPS0190