Main Page   Class Hierarchy   Alphabetical List   Data Structures   File List   Data Fields   Globals  

nmlqr.cc

Go to the documentation of this file.
00001 
00002 #include "cms.hh"               // class CMS
00003 #include "timer.hh"             // esleep()
00004 #include "nmlqr.hh"
00005 #include "dbg_mem.h"            // DEBUG_MALLOC, DEBUG_FREE
00006 
00007 #ifdef EXTERN_C_STD_HEADERS
00008 extern "C"
00009 {
00010 #endif
00011 
00012 #include <stdlib.h>             /* malloc(), free() */
00013 #include <stddef.h>             /* size_t */
00014 #include <string.h>             /* strcpy(), strlen(),memcpy() */
00015 #include <stdio.h>              // sprintf
00016 
00017 
00018 #ifdef EXTERN_C_STD_HEADERS
00019 }
00020 #endif
00021 
00022 #define ID_REQUEST_TYPE 9991
00023 #define ID_REPLY_TYPE 9992
00024 #define ID_DELETE_TYPE 9993
00025 
00026 class ID_REQUEST:public NML_QUERY_MSG
00027 {
00028 public:
00029   ID_REQUEST ():NML_QUERY_MSG (ID_REQUEST_TYPE, sizeof (ID_REQUEST))
00030   {
00031   };
00032   void update (CMS *);
00033 };
00034 
00035 void
00036 ID_REQUEST::update (CMS * cms)
00037 {
00038 }
00039 
00040 
00041 class ID_REPLY:public NML_QUERY_MSG
00042 {
00043 public:
00044   ID_REPLY ():NML_QUERY_MSG (ID_REPLY_TYPE, sizeof (ID_REPLY))
00045   {
00046   };
00047   void update (CMS *);
00048   int subdiv;
00049 };
00050 
00051 void
00052 ID_REPLY::update (CMS * cms)
00053 {
00054   cms->update (subdiv);
00055 }
00056 
00057 
00058 class ID_DELETE:public NML_QUERY_MSG
00059 {
00060 public:
00061   ID_DELETE ():NML_QUERY_MSG (ID_DELETE_TYPE, sizeof (ID_DELETE))
00062   {
00063   };
00064   void update (CMS *);
00065   int subdiv;
00066 };
00067 
00068 void
00069 ID_DELETE::update (CMS * cms)
00070 {
00071   cms->update (subdiv);
00072 }
00073 
00074 void
00075 NML_QUERY_MSG::update (CMS * cms)
00076 {
00077   cms->update (subdiv_for_reply);
00078 }
00079 
00080 int
00081 queryFormat (NMLTYPE type, void *buf, CMS * cms)
00082 {
00083   ((NML_QUERY_MSG *) buf)->update (cms);
00084   return 0;
00085 }
00086 
00087 
00088 int
00089 idFormat (NMLTYPE type, void *buf, CMS * cms)
00090 {
00091   queryFormat (type, buf, cms);
00092   switch (type)
00093     {
00094     case ID_REQUEST_TYPE:
00095       ((ID_REQUEST *) buf)->update (cms);
00096       break;
00097 
00098     case ID_REPLY_TYPE:
00099       ((ID_REPLY *) buf)->update (cms);
00100       break;
00101 
00102     case ID_DELETE_TYPE:
00103       ((ID_DELETE *) buf)->update (cms);
00104       break;
00105 
00106     default:
00107       return 0;
00108     }
00109   return 1;
00110 }
00111 
00112 
00113 NML_QR_SERVER::NML_QR_SERVER (NML_FORMAT_PTR f_ptr,
00114                               char *qr_name, char *process_name,
00115                               char *config_file)
00116 {
00117 
00118   queryChannel = NULL;
00119   replyChannel = NULL;
00120   idChannel = NULL;
00121   reply_subdiv = -1;
00122   subdiv_allocation_table = NULL;
00123 
00124   char repbufname[40];
00125   sprintf (repbufname, "%sReply", qr_name);
00126   char querybufname[40];
00127   sprintf (querybufname, "%sQuery", qr_name);
00128   char idbufname[40];
00129   sprintf (idbufname, "%sID", qr_name);
00130   idChannel =
00131     new NML_ID_CHANNEL (f_ptr, idbufname, process_name, config_file);
00132   queryChannel =
00133     new NML_QUERY_CHANNEL (f_ptr, querybufname, process_name, config_file);
00134   replyChannel = new NML (f_ptr, repbufname, process_name, config_file);
00135 
00136   if (replyChannel->get_total_subdivisions () > 1)
00137     {
00138       subdiv_allocation_table =
00139         (char *) DEBUG_MALLOC (replyChannel->get_total_subdivisions ());
00140     }
00141   memset (subdiv_allocation_table, 0,
00142           replyChannel->get_total_subdivisions ());
00143 }
00144 
00145 
00146 NML_QR_SERVER::~NML_QR_SERVER ()
00147 {
00148   if (NULL != queryChannel)
00149     {
00150       delete queryChannel;
00151       queryChannel = NULL;
00152     }
00153   if (NULL != idChannel)
00154     {
00155       delete idChannel;
00156       idChannel = NULL;
00157     }
00158   if (NULL != replyChannel)
00159     {
00160       delete replyChannel;
00161       replyChannel = NULL;
00162     }
00163   if (NULL != subdiv_allocation_table)
00164     {
00165       DEBUG_FREE (subdiv_allocation_table);
00166       subdiv_allocation_table = NULL;
00167     }
00168 }
00169 
00170 NMLTYPE
00171 NML_QR_SERVER::readQuery ()
00172 {
00173   while (1)
00174     {
00175       NMLTYPE query_read_type;
00176       switch (query_read_type = queryChannel->read ())
00177         {
00178         case ID_REQUEST_TYPE:
00179           {
00180             int subdiv_found = 0;
00181             for (int i = 0; i < replyChannel->get_total_subdivisions (); i++)
00182               {
00183                 if (subdiv_allocation_table[i] == 0)
00184                   {
00185                     subdiv_allocation_table[i] = 1;
00186                     ID_REPLY idMsg;
00187                     idMsg.subdiv = i;
00188                     idChannel->write (idMsg);
00189                     subdiv_found = 1;
00190                     break;
00191                   }
00192               }
00193             if (!subdiv_found)
00194               {
00195                 // Send the message we are full.
00196                 ID_REPLY idMsg;
00197                 idMsg.subdiv = -1;
00198                 idChannel->write (idMsg);
00199               }
00200           }
00201           break;
00202 
00203         case ID_REPLY_TYPE:
00204           return -1;            // Very weird a reply message in the query buffer.
00205           break;
00206 
00207         case ID_DELETE_TYPE:
00208           {
00209             ID_DELETE *idDeleteMsg =
00210               (ID_DELETE *) queryChannel->get_address ();
00211             if (idDeleteMsg->subdiv >= 0
00212                 && idDeleteMsg->subdiv <
00213                 replyChannel->get_total_subdivisions ())
00214               {
00215                 subdiv_allocation_table[idDeleteMsg->subdiv] = 0;
00216               }
00217           }
00218           break;
00219 
00220         default:
00221           NML_QUERY_MSG * qMsg =
00222             (NML_QUERY_MSG *) queryChannel->get_address ();
00223           reply_subdiv = qMsg->subdiv_for_reply;
00224           return query_read_type;
00225         }
00226     }
00227 }
00228 
00229 NMLTYPE
00230 NML_QR_SERVER::waitForQuery (double timeout)
00231 {
00232   while (1)
00233     {
00234       NMLTYPE query_read_type;
00235       switch (query_read_type = queryChannel->blocking_read (timeout))
00236         {
00237         case ID_REQUEST_TYPE:
00238           {
00239             int subdiv_found = 0;
00240             for (int i = 0; i < replyChannel->get_total_subdivisions (); i++)
00241               {
00242                 if (subdiv_allocation_table[i] == 0)
00243                   {
00244                     subdiv_allocation_table[i] = 1;
00245                     ID_REPLY idMsg;
00246                     idMsg.subdiv = i;
00247                     idChannel->write (idMsg);
00248                     subdiv_found = 1;
00249                     break;
00250                   }
00251               }
00252             if (!subdiv_found)
00253               {
00254                 // Send the message we are full.
00255                 ID_REPLY idMsg;
00256                 idMsg.subdiv = -1;
00257                 idChannel->write (idMsg);
00258               }
00259           }
00260           break;
00261 
00262         case ID_REPLY_TYPE:
00263           return -1;            // Very weird a reply message in the query buffer.
00264           break;
00265 
00266         case ID_DELETE_TYPE:
00267           {
00268             ID_DELETE *idDeleteMsg =
00269               (ID_DELETE *) queryChannel->get_address ();
00270             if (idDeleteMsg->subdiv >= 0
00271                 && idDeleteMsg->subdiv <
00272                 replyChannel->get_total_subdivisions ())
00273               {
00274                 subdiv_allocation_table[idDeleteMsg->subdiv] = 0;
00275               }
00276           }
00277           break;
00278 
00279         default:
00280           NML_QUERY_MSG * qMsg =
00281             (NML_QUERY_MSG *) queryChannel->get_address ();
00282           reply_subdiv = qMsg->subdiv_for_reply;
00283           return query_read_type;
00284         }
00285     }
00286 }
00287 
00288 NMLmsg *
00289 NML_QR_SERVER::getQueryAddress ()
00290 {
00291   if (NULL == queryChannel)
00292     {
00293       return NULL;
00294     }
00295   return queryChannel->get_address ();
00296 }
00297 
00298 
00299 int
00300 NML_QR_SERVER::replyToLastQuery (NMLmsg * message_to_send)
00301 {
00302   if (NULL == replyChannel)
00303     {
00304       return -1;
00305     }
00306   if (reply_subdiv < 0
00307       || reply_subdiv > replyChannel->get_total_subdivisions ())
00308     {
00309       return -1;
00310     }
00311   return replyChannel->write_subdivision (reply_subdiv, message_to_send);
00312 }
00313 
00314 
00315 int
00316 NML_QR_SERVER::valid ()
00317 {
00318   if (!idChannel->valid ())
00319     {
00320       return 0;
00321     }
00322   if (!queryChannel->valid ())
00323     {
00324       return 0;
00325     }
00326   if (!replyChannel->valid ())
00327     {
00328       return 0;
00329     }
00330   return 1;
00331 }
00332 
00333 int
00334 NML_QR_SERVER::reset ()
00335 {
00336   if (!idChannel->valid ())
00337     {
00338       idChannel->reset ();
00339     }
00340   if (!queryChannel->valid ())
00341     {
00342       queryChannel->reset ();
00343     }
00344   if (!replyChannel->valid ())
00345     {
00346       replyChannel->reset ();
00347     }
00348   return valid ();
00349 }
00350 
00351 
00352 
00353 NML_QR_CLIENT::NML_QR_CLIENT (NML_FORMAT_PTR f_ptr, char *qr_name,
00354                               char *process_name, char *config_file)
00355 {
00356   queryChannel = NULL;
00357   replyChannel = NULL;
00358   idChannel = NULL;
00359   reply_subdiv = -1;
00360 
00361   char repbufname[40];
00362   sprintf (repbufname, "%sReply", qr_name);
00363   char querybufname[40];
00364   sprintf (querybufname, "%sQuery", qr_name);
00365   char idbufname[40];
00366   sprintf (idbufname, "%sID", qr_name);
00367   idChannel =
00368     new NML_ID_CHANNEL (f_ptr, idbufname, process_name, config_file);
00369   queryChannel =
00370     new NML_QUERY_CHANNEL (f_ptr, querybufname, process_name, config_file);
00371   replyChannel = new NML (f_ptr, repbufname, process_name, config_file);
00372 
00373   if (idChannel->valid () && queryChannel->valid ())
00374     {
00375       ID_REQUEST reqMsg;
00376       queryChannel->write (reqMsg);
00377       esleep (0.05);
00378       while (!idChannel->read ())
00379         {
00380           esleep (0.05);
00381         }
00382       ID_REPLY *idReply = (ID_REPLY *) idChannel->get_address ();
00383       if (idReply->type == ID_REPLY_TYPE)
00384         {
00385           reply_subdiv = idReply->subdiv;
00386         }
00387     }
00388 }
00389 
00390 NML_QR_CLIENT::~NML_QR_CLIENT ()
00391 {
00392   if (NULL != queryChannel)
00393     {
00394       if (reply_subdiv >= 0)
00395         {
00396           ID_DELETE idDeleteMsg;
00397           idDeleteMsg.subdiv_for_reply = reply_subdiv;
00398           idDeleteMsg.subdiv = reply_subdiv;
00399           queryChannel->write (&idDeleteMsg);
00400           esleep (0.05);
00401         }
00402       delete queryChannel;
00403       queryChannel = NULL;
00404     }
00405   if (NULL != idChannel)
00406     {
00407       delete idChannel;
00408       idChannel = NULL;
00409     }
00410   if (NULL != replyChannel)
00411     {
00412       delete replyChannel;
00413       replyChannel = NULL;
00414     }
00415 }
00416 
00417 int
00418 NML_QR_CLIENT::sendQuery (NML_QUERY_MSG * qMsg)
00419 {
00420   if (NULL == queryChannel)
00421     {
00422       return -1;
00423     }
00424   qMsg->subdiv_for_reply = reply_subdiv;
00425   return queryChannel->write (qMsg);
00426 }
00427 
00428 
00429 NMLTYPE
00430 NML_QR_CLIENT::readReply ()
00431 {
00432   if (NULL == replyChannel || reply_subdiv < 0)
00433     {
00434       return -1;
00435     }
00436   return replyChannel->read_subdivision (reply_subdiv);
00437 }
00438 
00439 
00440 NMLTYPE
00441 NML_QR_CLIENT::waitForReply (double timeout)
00442 {
00443   if (NULL == replyChannel || reply_subdiv < 0)
00444     {
00445       return -1;
00446     }
00447   return replyChannel->blocking_read_subdivision (reply_subdiv, timeout);
00448 }
00449 
00450 NMLmsg *
00451 NML_QR_CLIENT::getReplyAddress ()
00452 {
00453   if (NULL == replyChannel || reply_subdiv < 0)
00454     {
00455       return NULL;
00456     }
00457   return replyChannel->get_address_subdivision (reply_subdiv);
00458 }
00459 
00460 
00461 int
00462 NML_QR_CLIENT::valid ()
00463 {
00464   if (!idChannel->valid ())
00465     {
00466       return 0;
00467     }
00468   if (!queryChannel->valid ())
00469     {
00470       return 0;
00471     }
00472   if (!replyChannel->valid ())
00473     {
00474       return 0;
00475     }
00476   if (reply_subdiv < 0)
00477     {
00478       return 0;
00479     }
00480   return 1;
00481 }
00482 
00483 int
00484 NML_QR_CLIENT::reset ()
00485 {
00486   if (!idChannel->valid ())
00487     {
00488       idChannel->reset ();
00489     }
00490   if (!queryChannel->valid ())
00491     {
00492       queryChannel->reset ();
00493     }
00494   if (!replyChannel->valid ())
00495     {
00496       replyChannel->reset ();
00497     }
00498   if (idChannel->valid () && queryChannel->valid () && reply_subdiv < 0)
00499     {
00500       ID_REQUEST reqMsg;
00501       queryChannel->write (reqMsg);
00502       esleep (0.05);
00503       while (!idChannel->read ())
00504         {
00505           esleep (0.05);
00506         }
00507       ID_REPLY *idReply = (ID_REPLY *) idChannel->get_address ();
00508       if (idReply->type == ID_REPLY_TYPE)
00509         {
00510           reply_subdiv = idReply->subdiv;
00511         }
00512     }
00513   return valid ();
00514 }
00515 
00516 
00517 NML_QUERY_CHANNEL::NML_QUERY_CHANNEL (NML_FORMAT_PTR f_ptr, char *name,
00518                                       char *process, char *file,
00519 int set_to_server):
00520 NML (name, process, file, set_to_server)
00521 {
00522   format_chain = new RCS_LINKED_LIST;
00523   prefix_format_chain (f_ptr);
00524   prefix_format_chain (idFormat);
00525   channel_type = NML_QUERY_CHANNEL_TYPE;
00526   sizeof_message_header = sizeof (NML_QUERY_MSG);
00527 
00528   if (NULL != cms)
00529     {
00530       cms->sizeof_message_header = sizeof_message_header;
00531     }
00532 
00533   register_with_server ();
00534 
00535 }
00536 
00537 NML_QUERY_CHANNEL::~NML_QUERY_CHANNEL ()
00538 {
00539   // Something funny happens to gdb without this being explicitly defined.
00540 }
00541 
00542 
00543 NML_ID_CHANNEL::NML_ID_CHANNEL (NML_FORMAT_PTR f_ptr, char *name,
00544                                 char *process, char *file, int set_to_server):
00545 NML (name, process, file, set_to_server)
00546 {
00547   format_chain = new RCS_LINKED_LIST;
00548   prefix_format_chain (idFormat);
00549   channel_type = NML_ID_CHANNEL_TYPE;
00550   sizeof_message_header = sizeof (NML_QUERY_MSG);
00551 
00552   if (NULL != cms)
00553     {
00554       cms->sizeof_message_header = sizeof_message_header;
00555     }
00556 
00557   register_with_server ();
00558 
00559 }
00560 
00561 NML_ID_CHANNEL::~NML_ID_CHANNEL ()
00562 {
00563   // Something funny happens to gdb without this being explicitly defined.
00564 }

Generated on Sun Dec 2 15:56:50 2001 for rcslib by doxygen1.2.11.1 written by Dimitri van Heesch, © 1997-2001