On Fri, 26 Jan 2001 08:43:23 -0800, Bruce Knoth <bknoth@erg.sri.com> wrote:
Any idea on when global message passing will be supported? Should I be looking
at a different technique?
No idea when global message passing will be ready, but in the meantime you can use the
/proc/mount folder to get all you need to connect to a remote server process.
Here are the significant parts of the code (I hope nothing really important is missing):
/**
- the server should do something like this…
*/
pNameAttach = name_attach (NULL, ATTACH_POINT, NAME_FLAG_ATTACH_GLOBAL);
if (pNameAttach != NULL ) {
bReceiveError = FALSE;
while (bReceiveError == FALSE) {
nRxPid = MsgReceive (pNameAttach->chid, pBenchMsg, nBufSize, &MsgInfo);
if (nRxPid == 0) {
// handle pulses, messages, whatever
// …
// …
/**
- this is how a client looks like
*/
mhConnectionID = ConnectToServer ();
if (mhConnectionID != INVALID_ID) {
nRet = MsgSend (hConnectionID, m_pBenchMsg, m_nMessageSize, NULL, 0);
// …
//
/**
- The client locates the NID/PID/CHID by peeking into /proc/mount
- folder on the remote machine, i.e. if the server machine is my_server
- and the global name is my_name, then a shell command like
- ls -la /net/my_server/proc/mount/dev/name/global/my_name
- will give us enough info to connect to the server process
-
- Here is the code to do this:
*/
/**
- Locate the server process on local or remote node
- Return connection ID handle. Otherwise,
- Return error code if server not available
/
static int ConnectToServer (void)
{
int hFile;
int hConnectionID;
int nBytesRead;
char szPidInfo [256];
char szRemotePath [256];
DIR dirp;
struct dirent* direntp;
if (strlen (mOptions.szHostName) > 0) {
// hostname assumed valid → locate server process on remote node
hConnectionID = name_open (ATTACH_POINT, NAME_FLAG_ATTACH_GLOBAL);
if (hConnectionID == INVALID_ID) {
// KLUDGE: overcame global names not implemented in Neutrino
strcpy (szRemotePath, “/net/”);
strcat (szRemotePath, mOptions.szHostName);
strcat (szRemotePath, “/proc/mount/dev/name/global/”);
strcat (szRemotePath, ATTACH_POINT);
dirp = opendir (szRemotePath);
if (dirp != NULL) {
direntp = readdir (dirp);
if (direntp != NULL) {
// extract NIP/PID/CHID from d_name
LocateProcessCoordinates (direntp->d_name);
hConnectionID = ConnectAttach (mOptions.nNodeID, mOptions.nProcessID, mOptions.nChannelID, 0, 0);
}
closedir (dirp);
}
else {
printf (“Error opening directory %s\n”, szRemotePath);
}
}
}
else {
// hostname missing → locate server process on local node
hConnectionID = name_open (ATTACH_POINT, NAME_FLAG_ATTACH_GLOBAL);
if (hConnectionID == INVALID_ID) {
printf (“local name open failed\n”);
perror (“errno”);
}
}
return hConnectionID;
}
/**
- LocateProcessCoordinates
- parse the input string to extract the NID/PID/CHID
- input string has these values separated by commas, e.g.
- szInfo = 0,12345,1,2,12 means:
- nodeId = 0, pid=12345, chid=1, handle=2, ftype=12 (_FTYPE_NAME)
- set also the remote node ID as seen from the local node
*/
static void LocateProcessCoordinates (char *pszInfo)
{
int ndx;
int nValue [3];
char *pszThis;
char *pszNext;
char szValue [32];
char szFullHostName [50];
ndx = 0;
memset (&nValue [0], 0, sizeof (nValue));
pszThis = pszInfo;
pszNext = strpbrk (pszThis, “,”);
while (ndx < 3 && pszNext != NULL) {
memset (szValue, 0, sizeof (szValue));
strncpy (szValue, pszThis, pszNext - pszThis);
nValue [ndx] = atoi (szValue);
pszThis = pszNext + 1;
pszNext = strpbrk (pszThis, “,”);
++ndx;
}
mOptions.nProcessID = nValue [1];
mOptions.nChannelID = nValue [2];
strcpy (szFullHostName, “/net/”);
strcat (szFullHostName, mOptions.szHostName);
mOptions.nNodeID = netmgr_strtond (szFullHostName, NULL);
/* here is the info needed to do a ConnectAttach */
printf (“NID/PID/CHID = %d/%d/%d\n”, mOptions.nNodeID, mOptions.nProcessID, mOptions.nChannelID);
}