133a10a3c089b99ea16cf1232785147e0a5002ee
[ipc/ipcdev.git] / packages / ti / grcm / RcmClient.h
1 /*
2  * Copyright (c) 2011-2013, Texas Instruments Incorporated
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  *
9  * *  Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  *
12  * *  Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * *  Neither the name of Texas Instruments Incorporated nor the names of
17  *    its contributors may be used to endorse or promote products derived
18  *    from this software without specific prior written permission.
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
22  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
23  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
24  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
27  * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
28  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
29  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
30  * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  */
34 /*
35  *  ======== RcmClient.h ========
36  *
37  */
39 /*!
40  *  @file ti/grcm/RcmClient.h
41  *
42  *  @brief Remote Command Message Client Module. An RcmClient is used
43  *  for sending messages to an RcmServer for processing.
44  *
45  *  @sa RcmServer.h <br>
46  *  @ref ti_grcm "RCM Overview"
47  */
49 /*!
50  *  @defgroup ti_grcm_RcmClient RcmClient
51  *
52  *  @brief Remote Command Message Client Module. An RcmClient is used
53  *  for sending messages to an RcmServer for processing.
54  *
55  *  The RcmClient module is used to send messages to an RcmServer for
56  *  processing. An RcmClient instance must be created which will
57  *  communicate with a single RcmServer instance. An RcmServer instance
58  *  can receive messages from many RcmClient instances but an RcmClient
59  *  instance can send messages to only one RcmServer instance.
60  *
61  *  <a name="error_handling"></a><h2>Error Handling</h2>
62  *
63  *  Errors may be raised at various points in the execution flow of a
64  *  single message. These are the types of errors raised by RCM:
65  *  - RCM Errors
66  *  - User Errors
67  *  - Message Function Errors
68  *  - Library Function Errors
69  *
70  *  The following diagram illustrates the call flow and highlights the
71  *  points at which errors can be raised.
72  *
73  *  @image html ti/grcm/doc-files/ExecFlow.png "Diagram 1: Execution Flow"
74  *
75  *  RCM errors are raised by the RCM implementation. For example, when
76  *  calling RcmClient_exec(), it may raise an error if it
77  *  is unable to send the message. This will be reported immediately to
78  *  the caller, the server is never involved. This is highlighted in the
79  *  diagram at point [A].
80  *
81  *  RCM errors may also be raised by the RcmServer. Once RcmClient_exec()
82  *  sends a message, it waits for the return message. When the server
83  *  receives the message, it has to decode its type. If this fails, the
84  *  server records this error in the message and sends it back to the
85  *  client. This is highlighted at point [B] in the diagram. When
86  *  RcmClient_exec() receives the return message, it inspects the status
87  *  field and recognizes the error. It then raises an appropriate error
88  *  to the caller.
89  *
90  *  User errors are raised by RCM as a result of an invalid runtime
91  *  condition. They are typically detected and raised by the server and
92  *  then sent back to the client for processing. For example, when the
93  *  server receives a message, it will lookup the function index in it's
94  *  table and invoke the corresponding message function. If the index is
95  *  invalid, this is detected by the server and reported as an error.
96  *  The message function is never invoked. The message is returned to
97  *  the client and RcmClient_exec() will raise the appropriate error.
98  *  This error is raised at point [B] in the diagram.
99  *
100  *  Message function errors are raised by the message function itself.
101  *  This is highlighted at point [C] in the diagram. In the body of the
102  *  message function, an error is encountered either when calling a
103  *  framework function or when unmarshalling the arguments from the
104  *  message payload. In both cases, the message function will abort and
105  *  return an error value as its return value. The error value must be
106  *  less than zero (< 0). When control returns to the server, it inspects
107  *  the message function's return value. If the message was sent by
108  *  RcmClient_exec(), then the server simply stores the return value in
109  *  the message and returns it to the client. However, if the message was
110  *  send by RcmClient_execCmd(), the behavior is slightly
111  *  different. If the return value is < 0 (error condition), then the
112  *  server behaves the same as for the RcmClient_exec() case. However,
113  *  if there is no error, the server simply frees the message. The message
114  *  is never returned to the client.
115  *
116  *  Library functions errors are raised by the library functions invoked
117  *  by the message function, highlighted at point [D] in the diagram. It
118  *  is the responsibility of the message function to detect a library
119  *  function error and to marshal the appropriate error code into the
120  *  message payload. The message function must also return an error value
121  *  (< 0) so that server can do proper error handing as described
122  *  in the preceeding paragraph. It is the stub function's responsibility
123  *  to unmarshal the error value from the message payload and take the
124  *  appropriate action.
125  *
126  *  Understanding the types of errors raised by RCM and where they are
127  *  raised is important when writing the upper layer software. The following
128  *  code fragment illustrates how to check for the errors discussed above.
129  *  See <a href"#error_handling">Error Handling</a> above.
130  *
131  *  @code
132  *  RcmClient_Message *msg;
133  *
134  *  // send message
135  *  status = RcmClient_exec(h, msg, &msg);
136  *
137  *  // check for error
138  *  switch (status) {
139  *
140  *      case RcmClient_S_SUCCESS:
141  *          // no error, all is well
142  *          break;
143  *
144  *      case RcmClient_E_EXECFAILED:
145  *          // RCM error, unable to send message
146  *          :
147  *          break;
148  *
149  *      case RcmClient_E_INVALIDFXNIDX:
150  *          // user error, bad function index
151  *          :
152  *          break;
153  *
154  *      case RcmClient_E_MSGFXNERROR:
155  *          // decode message function error
156  *          msgFxnErr = msg->result;
157  *          :
158  *          // decode library function error
159  *          libFxnErr = msg->data[0];
160  *          :
161  *          break;
162  *  }
163  *
164  *  // free message if one was returned
165  *  if (msg != NULL) {
166  *      RcmClient_free(h, msg);
167  *      msg = NULL;
168  *  }
169  *  @endcode
170  *
171  *  The upper layer software begins by calling RcmClient_exec()
172  *  to send the message to the server. If RCM encounters a transport error
173  *  and is unable to send the message, an RcmClient_E_EXECFAILED error is
174  *  returned.
175  *
176  *  If the server encounters an error while decoding the message, say an
177  *  invalid function index, the server returns the message and an
178  *  RcmClient_E_INVALIDFXNIDX error is returned.
179  *
180  *  If the message function or the library function encounter an error,
181  *  the message is returned and an RcmClient_E_MSGFXNERROR error is
182  *  returned. The upper layer software must decode the results field to
183  *  see what error the message function returned. If the library function
184  *  returned an error, its error code must be unmarshalled from the payload.
185  *  This is illustrated by decoding the first word in the payload
186  *  (msg->data[0]). The actual marshal format is implementation specific.
187  *
188  *  The message function must return >=0 for success, <0 for error.
189  *  Here is a very simple message function which simply turns on an LED.
190  *
191  *  @code
192  *  Int32 Led_On(UInt32 size, UInt32 *data)
193  *  {
194  *      Ptr led = <addr>;
195  *
196  *      *led = 1;  // turn on LED
197  *      return(0); // success
198  *  }
199  *  @endcode
200  *
201  *  In this example, the message payload is not used. The message function
202  *  does all the work, it just sets a bit in the LED control register, and
203  *  returns success.
204  *
205  *  This next example illustrates a very simple RPC style skel function.
206  *  It unmarshalls two arguments and invokes the libraray function. If the
207  *  library function succeeds, the message function returns 0, otherwise it
208  *  returns -1 to indicate failure. In both cases, the library function's
209  *  return value is marshalled into the payload. The calling stub function
210  *  can umarshal the return value to get the library function's error code.
211  *
212  *  @code
213  *  Int32 MediaSkel_process(UInt32 size, UInt32 *data)
214  *  {
215  *      Int a, b, x;
216  *      Int32 status = 0;  // success
217  *
218  *      // unmarshal args
219  *      a = (Int)data[1];
220  *      b = (Int)data[2];
221  *
222  *      // invoke library function, returns >=0 on success
223  *      x = Media_process(a, b);
224  *
225  *      // marshal return value
226  *      data[0] = (Int32)x;
227  *
228  *      // return status
229  *      return(x >= 0 ? 0 : -1);
230  *  }
231  *  @endcode
232  *
233  *  @sa ti_grcm_RcmServer <br>
234  *  @ref ti_grcm "RCM Overview"
235  */
237 #ifndef ti_grcm_RcmClient__include
238 #define ti_grcm_RcmClient__include
240 #include <xdc/runtime/knl/GateThread.h>
243 /** @ingroup ti_grcm_RcmClient */
244 /*@{*/
246 #if defined (__cplusplus)
247 extern "C" {
248 #endif
251 // -------- status codes --------
253 /*!
254  *  @brief Success return code
255  */
256 #define RcmClient_S_SUCCESS (0)
258 /*!
259  *  @brief General failure return code
260  */
261 #define RcmClient_E_FAIL (-1)
263 /*!
264  *  @brief The client has not been configured for asynchronous notification
265  *
266  *  In order to use the RcmClient_execAsync() function, the RcmClient
267  *  must be configured with callbackNotification set to true in the
268  *  instance create parameters.
269  */
270 #define RcmClient_E_EXECASYNCNOTENABLED (-2)
272 /*!
273  *  @brief The client was unable to send the command message to the server
274  *
275  *  An IPC transport error occurred. The message was never sent to the server.
276  */
277 #define RcmClient_E_EXECFAILED (-3)
279 /*!
280  *  @brief A heap id must be provided in the create params
281  *
282  *  When an RcmClient instance is created, a heap id must be given
283  *  in the create params. This heap id must be registered with MessageQ
284  *  before calling RcmClient_create().
285  */
286 #define RcmClient_E_INVALIDHEAPID (-4)
288 /*!
289  *  @brief Invalid function index
290  *
291  *  An RcmClient_Message was sent to the server which contained a
292  *  function index value (in the fxnIdx field) that was not found
293  *  in the server's function table.
294  */
295 #define RcmClient_E_INVALIDFXNIDX (-5)
297 /*!
298  *  @brief Message function error
299  *
300  *  There was an error encountered in either the message function or
301  *  the library function invoked by the message function. The semantics
302  *  of the error code are implementation dependent.
303  */
304 #define RcmClient_E_MSGFXNERROR (-6)
306 /*!
307  *  @brief An unknown error has been detected from the IPC layer
308  *
309  *  Check the error log for additional information.
310  */
311 #define RcmClient_E_IPCERROR (-7)
313 /*!
314  *  @brief Failed to create the list object
315  */
316 #define RcmClient_E_LISTCREATEFAILED (-8)
318 /*!
319  *  @brief The expected reply message from the server was lost
320  *
321  *  A command message was sent to the RcmServer but the reply
322  *  message was not received. This is an internal error.
323  */
324 #define RcmClient_E_LOSTMSG (-9)
326 /*!
327  *  @brief Insufficient memory to allocate a message
328  *
329  *  The message heap cannot allocate a buffer of the requested size.
330  *  The reported size it the requested data size and the underlying
331  *  message header size.
332  */
333 #define RcmClient_E_MSGALLOCFAILED (-10)
335 /*!
336  *  @brief The client message queue could not be created
337  *
338  *  Each RcmClient instance must create its own message queue for
339  *  receiving return messages from the RcmServer. The creation of
340  *  this message queue failed, thus failing the RcmClient instance
341  *  creation.
342  */
343 #define RcmClient_E_MSGQCREATEFAILED (-11)
345 /*!
346  *  @brief The server message queue could not be opened
347  *
348  *  Each RcmClient instance must open the server's message queue.
349  *  This error is raised when an internal error occurred while trying
350  *  to open the server's message queue.
351  */
352 #define RcmClient_E_MSGQOPENFAILED (-12)
354 /*!
355  *  @brief The server returned an unknown error code
356  *
357  *  The server encountered an error with the given message but
358  *  the error code is not recognized by the client.
359  */
360 #define RcmClient_E_SERVERERROR (-13)
362 /*!
363  *  @brief The server specified in the create params was not found
364  *
365  *  When creating an RcmClient instance, the specified server could not
366  *  be found. This could occur if the server name is incorrect, or
367  *  if the RcmClient instance is created before the RcmServer. In such an
368  *  instance, the client can retry when the RcmServer is expected to
369  *  have been created.
370  */
371 #define RcmClient_E_SERVERNOTFOUND (-14)
373 /*!
374  *  @brief The given symbol was not found in the server symbol table
375  *
376  *  This error could occur if the symbol spelling is incorrect or
377  *  if the RcmServer is still loading its symbol table.
378  */
379 #define RcmClient_E_SYMBOLNOTFOUND (-15)
381 /*!
382  *  @brief There is insufficient memory left in the heap
383  */
384 #define RcmClient_E_NOMEMORY (-16)
386 /*!
387  *  @brief The given job id was not found on the server
388  *
389  *  When releasing a job id with a call to RcmClient_releaseJobId(),
390  *  this error return value indicates that the given job id was not
391  *  previously allocated with a call to RcmClient_acquireJobId().
392  */
393 #define RcmClient_E_JOBIDNOTFOUND (-17)
396 // -------- constants and types --------
398 /*!
399  *  @brief Invalid function index
400  */
401 #define RcmClient_INVALIDFXNIDX ((UInt32)(0xFFFFFFFF))
403 /*!
404  *  @brief Invalid heap id
405  */
406 #define RcmClient_INVALIDHEAPID ((UInt16)(0xFFFF))
408 /*!
409  *  @brief Invalid message id
410  */
411 #define RcmClient_INVALIDMSGID (0)
413 /*!
414  *  @brief Default worker pool id
415  *
416  *  The default worker pool is used to process all anonymous messages.
417  *  When a new message is allocated, the pool id property is
418  *  initialized to this value.
419  */
420 #define RcmClient_DEFAULTPOOLID ((UInt16)(0x8000))
422 /*!
423  *  @brief Invalid job stream id
424  *
425  *  All discrete messages must have their jobId property set to this value.
426  *  When a new message is allocated, the jobId property is initialized tothis value.
427  */
428 #define RcmClient_DISCRETEJOBID (0)
430 /*!
431  *  @brief RcmClient instance object handle
432  */
433 typedef struct RcmClient_Object_tag *RcmClient_Handle;
435 /*!
436  *  @brief Remote Command Message structure
437  *
438  *  An RcmClient needs to fill in this message before sending it
439  *  to the RcmServer for execution.
440  */
441 typedef struct {
442     /*!
443      *  @brief The worker pool id that will process this message.
444      *
445      *  The message will be processed by a worker thread from the worker
446      *  pool specified in this field. The default value is the default
447      *  pool id.
448      */
449     UInt16      poolId;
451     /*!
452      *  @brief The job id associated with this message.
453      *
454      *  All messages beloging to a job id must have this field set to
455      *  that id. Use the value RcmClient_DISCRETEJOBID if the message
456      *  does not belong to any job.
457      */
458     UInt16      jobId;
460     /*!
461      *  @brief The index of the remote function to execute.
462      */
463     UInt32      fxnIdx;
465     /*!
466      *  @brief The return value of the remote message function.
467      */
468     Int32       result;
470     /*!
471      *  @brief The size of the data buffer (in chars).
472      *
473      *  This field should be considered as read-only. It is set by
474      *  the call to the RcmClient_alloc() function.
475      */
476     UInt32      dataSize;
478     /*!
479      *  @brief The data buffer containing the message payload.
480      *
481      *  The size of this field is dataSize chars. The space is allocated
482      *  by the call to the RcmClient_alloc() function.
483      */
484     UInt32      data[1];
486 } RcmClient_Message;
488 /*!
489  *  @brief Callback function type
490  *
491  *  When using callback notification, the application must supply a
492  *  callback function of this type. The callback will be invoked with
493  *  the pointer to the RcmClient_Message returned from the server and
494  *  the application data pointer supplied in the call to RcmClient_execAsync().
495  */
496 typedef Void (*RcmClient_CallbackFxn)(RcmClient_Message *, Ptr);
498 /*!
499  *  @brief Instance create parameters
500  */
501 typedef struct {
502     /*!
503      *  @brief The heapId used by this instance for allocating messages
504      *
505      *  If sending messages to a remote server, the specified heap must
506      *  be compatible with the transport used for delivering messages
507      *  to the remote processor.
508      */
509     UInt16 heapId;
511     /*!
512      *  @brief Asynchronous callback notification support
513      *
514      *  When remote functions submitted with RcmClient_execAsync()
515      *  complete, the given callback function is invoked. The callback
516      *  function executes in the context of this RcmClient instance's
517      *  callback server thread.
518      *
519      *  This config param must be set to true when using RcmClient_execAsync()
520      *  to execute remote functions.
521      *
522      *  When set to false, the callback server thread is not created.
523      */
524     Bool callbackNotification;
526 } RcmClient_Params;
528 /*!
529  *  @brief Opaque client structure large enough to hold an instance object
530  *
531  *  Use this structure to define an embedded RcmClient object.
532  *
533  *  @sa RcmClient_construct
534  */
535 typedef struct {
536     xdc_runtime_knl_GateThread_Struct   _f1;
537     Ptr                 _f2;
538     Ptr                 _f3;
539     UInt16              _f4;
540     Ptr                 _f5;
541     UInt32              _f6;
542     Bool                _f7;
543     UInt16              _f8;
544     Ptr                 _f9;
545     Ptr                 _f10;
546     Ptr                 _f11;
547     Ptr                 _f12;
548 } RcmClient_Struct;
551 // -------- functions --------
553 /*
554  *  ======== RcmClient_acquireJobId ========
555  */
556 /*!
557  *  @brief Get a job id from the server
558  *
559  *  Acquire a unique job id from the server. The job id is used to associate
560  *  messages with a common job id. The server will process all messages for
561  *  a given job id in sequence.
562  */
563 Int RcmClient_acquireJobId(
564         RcmClient_Handle        handle,
565         UInt16 *                jobId
566     );
568 /*
569  *  ======== RcmClient_addSymbol ========
570  */
571 /*!
572  *  @brief Add a symbol and its address to the server table
573  *
574  *  This function is used by the client to dynamically load a new
575  *  function address into the server's function pointer table. The
576  *  given address must be in the server's address space. The function
577  *  must already be loaded into the server's memory.
578  *
579  *  This function is useful when dynamically loading code onto the
580  *  remote processor (as in the case of DLL's).
581  *
582  *  @param[in] handle Handle to an instance object
583  *
584  *  @param[in] name The function's name.
585  *
586  *  @param[in] addr The function's address as specified in the
587  *  remote processor's address space.
588  *
589  *  @param[out] index The function's index value to be used in the
590  *  RcmClient_Message.fxnIdx field.
591  *
592  *  @retval RcmClient_S_SUCCESS Success
593  *  @retval RcmClient_E_FAIL Failure
594  */
595 Int RcmClient_addSymbol(
596         RcmClient_Handle        handle,
597         String                  name,
598         Fxn                     addr,
599         UInt32 *                index
600     );
602 /*
603  *  ======== RcmClient_alloc ========
604  */
605 /*!
606  *  @brief Allocate a message from the heap configured for this instance
607  *
608  *  When a message is allocated, the RcmClient instance is the owner
609  *  of the message. All messages must be returned to the heap by
610  *  calling RcmClient_free().
611  *
612  *  During a call to all of the exec functions, the ownership of the
613  *  message is temporarily transfered to the server. If the exec
614  *  function returns an RcmClient_Message pointer, then ownership of
615  *  the message is returned to the instance. For the other exec
616  *  functions, the client acquires ownership of the return message
617  *  by calling RcmClient_waitUntilDone().
618  *
619  *  A message should not be accessed when ownership has been given
620  *  away. Once ownership has been reacquired, the message can be
621  *  either reused or returned to the heap.
622  *
623  *  @param[in] handle Handle to an instance object
624  *
625  *  @param[in] dataSize Specifies (in chars) how much space to allocate
626  *  for the RcmClient_Message.data array. The actual memory allocated
627  *  from the heap will be larger as it includes the size of the
628  *  internal message header.
629  *
630  *  @param[out] message A pointer to the allocated message or NULL on error.
631  */
632 Int RcmClient_alloc(
633         RcmClient_Handle        handle,
634         UInt32                  dataSize,
635         RcmClient_Message **    message
636     );
638 /*
639  *  ======== RcmClient_checkForError ========
640  */
641 /*!
642  *  @brief Check if an error message has been returned from the server
643  *
644  *  When using RcmClient_execCmd() to send messages to the server, the
645  *  message will be freed by the server unless an error occurs. In the
646  *  case of an error, the message is returned to the client. Use this
647  *  function to check for and to retrieve these error messages.
648  *
649  *  Note that the latency of the return message is dependent on many
650  *  system factors. In particular, the server's response time to processing
651  *  a message will be a significant factor. It is possible to call
652  *  RcmClient_execCmd() several times before any error message is returned.
653  *  There is no way to know when all the messages have been processed.
654  *
655  *  The return value of RcmClient_checkForError() is designed to mimic
656  *  the return value of RcmClient_exec(). When an error message is returned
657  *  to the caller, the return value of RcmClient_checkForError() will be
658  *  the appropriate error code as if the error had occured during a call
659  *  to RcmClient_exec(). For example, if a message is prepared with an
660  *  incorrect function index, the return value from RcmClient_exec() would
661  *  be RcmClient_E_INVALIDFXNIDX. However, the same message sent with
662  *  RcmClient_execCmd() will not return an error, because the function does
663  *  not wait for the return message. When the server receives the message
664  *  and detects the function index error, it will return the message to
665  *  the client on a special error queue. The subsequent call to
666  *  RcmClient_checkForError() will pickup this error message and return
667  *  with a status value of RcmClient_E_INVALIDFXNIDX, just as the call
668  *  to RcmClient_exec() would have done.
669  *
670  *  A return value of RcmClient_S_SUCCESS means there are no error messages.
671  *  This function will never return a message and a success status code at
672  *  the same time.
673  *
674  *  When this function returns an error message, the caller must return
675  *  the message to the heap by calling RcmClient_free().
676  *
677  *  It is possible that RcmClient_checkForError() will return with an error
678  *  but without an error message. This can happen when an internal error
679  *  occurs in RcmClient_checkForError() before it has checked the error
680  *  queue. In this case, an error is returned but the returnMsg argument
681  *  will be set to NULL.
682  *
683  *  @param[in] handle Handle to an instance object
684  *
685  *  @param[out] returnMsg A pointer to the error message or NULL if there
686  *  are no error messages in the queue.
687  *
688  *  @retval RcmClient_S_SUCCESS
689  *  @retval RcmClient_E_IPCERROR
690  *  @retval RcmClient_E_INVALIDFXNIDX
691  *  @retval RcmClient_E_MSGFXNERROR
692  *  @retval RcmClient_E_SERVERERROR
693  */
694 Int RcmClient_checkForError(
695         RcmClient_Handle        handle,
696         RcmClient_Message **    returnMsg
697     );
699 /*
700  *  ======== RcmClient_construct ========
701  */
702 /*!
703  *  @brief Initialize a new instance object inside the provided structure
704  *
705  *  This function is the same as RcmClient_create() except that it does not
706  *  allocate memory for the instance object. The instance object is
707  *  constructed inside the provided structure. Call RcmClient_destruct()
708  *  to finalize a constructed instance object.
709  *
710  *  @param[in] structPtr A pointer to an allocated structure.
711  *
712  *  @param[in] server The name of the server that messages will be sent to for
713  *  executing commands. The name must be a system-wide unique name.
714  *
715  *  @param[in] params The create params used to customize the instance object.
716  *
717  *  @sa RcmClient_create
718  */
719 Int RcmClient_construct(
720         RcmClient_Struct *      structPtr,
721         String                  server,
722         const RcmClient_Params *params
723     );
725 /*
726  *  ======== RcmClient_create ========
727  */
728 /*!
729  *  @brief Create an RcmClient instance
730  *
731  *  The RcmClient instance is used by the application to send messages to
732  *  an RcmServer for executing remote functions. A given
733  *  instance can send messages only to the server it was configured
734  *  for. If an application needs to send messages to multiple servers,
735  *  then create an RcmClient instance for each server.
736  *
737  *  The assigned server to this instance must already exist and be
738  *  running before creating RcmClient instances which send messages to it.
739  *
740  *  @param[in] server The name of the server that messages will be sent to for
741  *  executing commands. The name must be a system-wide unique name.
742  *
743  *  @param[in] params The create params used to customize the instance object.
744  *
745  *  @param[out] handle An opaque handle to the created instance object.
746  */
747 Int RcmClient_create(
748         String                  server,
749         const RcmClient_Params *params,
750         RcmClient_Handle *      handle
751     );
753 /*
754  *  ======== RcmClient_delete ========
755  */
756 /*!
757  *  @brief Delete an RcmClient instance
758  *
759  *  @param[in,out] handlePtr Handle to the instance object to delete.
760  */
761 Int RcmClient_delete(
762         RcmClient_Handle *      handlePtr
763     );
765 /*
766  *  ======== RcmClient_destruct ========
767  */
768 /*!
769  *  @brief Finalize the instance object inside the provided structure
770  *
771  *  @param[in] structPtr A pointer to the structure containing the
772  *  instance object to finalize.
773  */
774 Int RcmClient_destruct(
775         RcmClient_Struct *      structPtr
776     );
778 /*
779  *  ======== RcmClient_exec ========
780  */
781 /*!
782  *  @brief Execute a command message on the server
783  *
784  *  The message is sent to the server for processing. This call will
785  *  block until the remote function has completed. When this function
786  *  returns, the message will contain the return value of the remote
787  *  function as well as a possibly modified context.
788  *
789  *  After calling exec, the message can be either reused for another
790  *  call to exec or it can be freed.
791  *
792  *  @param[in] handle Handle to an instance object
793  *
794  *  @param[in] cmdMsg Pointer to an RcmClient_Message structure.
795  *
796  *  @param[out] returnMsg A pointer to the return message or NULL on
797  *  error. The client must free this message. The return value of the
798  *  message function is stored in the results field. The return value
799  *  of the library function is marshalled into the data field.
800  *
801  *  @retval RcmClient_S_SUCCESS
802  *  @retval RcmClient_E_EXECFAILED
803  *  @retval RcmClient_E_INVALIDFXNIDX
804  *  @retval RcmClient_E_LOSTMSG
805  *  @retval RcmClient_E_MSGFXNERROR
806  *  @retval RcmClient_E_SERVERERROR
807  */
808 Int RcmClient_exec(
809         RcmClient_Handle        handle,
810         RcmClient_Message *     cmdMsg,
811         RcmClient_Message **    returnMsg
812     );
814 /*
815  *  ======== RcmClient_execAsync ========
816  */
817 /*!
818  *  @brief Execute a command message and use a callback for notification
819  *
820  *  The message is sent to the server for execution, but this call does
821  *  not wait for the remote function to execute. This call returns
822  *  as soon as the message has been dispatched to the transport. Upon
823  *  returning from this function, the ownership of the message has been
824  *  lost; do not access the message at this time.
825  *
826  *  When the remote function completes, the given callback function is
827  *  invoked by this RcmClient instance's callback server thread. The
828  *  callback function is used to asynchronously notify the client that
829  *  the remote function has completed.
830  *
831  *  The RcmClient instance must be create with callbackNotification
832  *  set to true in order to use this function.
833  *
834  *  @param[in] handle Handle to an instance object
835  *
836  *  @param[in] cmdMsg Pointer to an RcmClient_Message structure.
837  *
838  *  @param[in] callback A callback function pointer supplied by the
839  *  application. It will be invoked by the callback server thread to
840  *  notify the application that the remote function has completed.
841  *
842  *  @param[in] appData A private data pointer supplied by the application.
843  *  This allows the application to provide its own context when
844  *  receiving the callback.
845  */
846 Int RcmClient_execAsync(
847         RcmClient_Handle        handle,
848         RcmClient_Message *     cmdMsg,
849         RcmClient_CallbackFxn   callback,
850         Ptr                     appData
851     );
853 /*
854  *  ======== RcmClient_execCmd ========
855  */
856 /*!
857  *  @brief Execute a one-way command message on the server
858  *
859  *  The message is sent to the server for processing but this function
860  *  does not wait for the return message. This function is non-blocking.
861  *  The server will processes the message and then free it, unless an
862  *  error occurs. The return value from the remote function is discarded.
863  *
864  *  If an error occurs on the server while processing the message, the server
865  *  will return the message to the client. Use RcmClient_checkForError()
866  *  to collect these return error messages.
867  *
868  *  When this function returns, ownership of the message has been transfered
869  *  to the server. Do not access the message after this function returns,
870  *  it could cause cache inconsistencies or a memory access violation.
871  *
872  *  @param[in] handle Handle to an instance object
873  *
874  *  @param[in] cmdMsg Pointer to an RcmClient_Message structure.
875  *
876  *  @retval RcmClient_S_SUCCESS
877  *  @retval RcmClient_E_IPCERROR
878  */
879 Int RcmClient_execCmd(
880         RcmClient_Handle        handle,
881         RcmClient_Message *     cmdMsg
882     );
884 /*
885  *  ======== RcmClient_execDpc ========
886  */
887 /*!
888  *  @brief Execute a deferred procedure call on the server
889  *
890  *  The return field of the message is not used.
891  *
892  *  @param[in] handle Handle to an instance object
893  *
894  *  @param[in] cmdMsg Pointer to an RcmClient_Message structure.
895  *
896  *  @param[out] returnMsg A pointer to the return message or NULL
897  *  on error. The client must free this message.
898  */
899 Int RcmClient_execDpc(
900         RcmClient_Handle        handle,
901         RcmClient_Message *     cmdMsg,
902         RcmClient_Message **    returnMsg
903     );
905 /*
906  *  ======== RcmClient_execNoWait ========
907  */
908 /*!
909  *  @brief Submit a command message to the server and return immediately
910  *
911  *  The message is sent to the server for execution but this call does
912  *  not wait for the remote function to execute. The call returns
913  *  as soon as the message has been dispatched to the transport. Upon
914  *  returning from this function, the ownership of the message has been
915  *  lost; do not access the message at this time.
916  *
917  *  Using this call to execute a remote message does not require a
918  *  callback server thread. The application must call
919  *  RcmClient_waitUntilDone() to get the return message from the remote
920  *  function.
921  *
922  *  @param[in] handle Handle to an instance object
923  *
924  *  @param[in] cmdMsg A pointer to an RcmClient_Message structure.
925  *
926  *  @param[out] msgId Pointer used for storing the message id. Use
927  *  the message id in a call to RcmClient_WaitUntilDone() to retrieve
928  *  the return value of the remote function.
929  */
930 Int RcmClient_execNoWait(
931         RcmClient_Handle        handle,
932         RcmClient_Message *     cmdMsg,
933         UInt16 *                msgId
934     );
936 /*
937  *  ======== RcmClient_exit ========
938  */
939 /*!
940  *  @brief Finalize the RcmClient module
941  *
942  *  This function is used to finalize the RcmClient module. Any resources
943  *  acquired by RcmClient_init() will be released. Do not call any RcmClient
944  *  functions after calling RcmClient_exit().
945  *
946  *  This function must be serialized by the caller.
947  */
948 Void RcmClient_exit(Void);
950 /*
951  *  ======== RcmClient_free ========
952  */
953 /*!
954  *  @brief Free the given message
955  *
956  *  @param[in] handle Handle to an instance object
957  *
958  *  @param msg Pointer to an RcmClient_Message structure.
959  */
960 Int RcmClient_free(
961         RcmClient_Handle        handle,
962         RcmClient_Message *     msg
963     );
965 /*
966  *  ======== RcmClient_getSymbolIndex ========
967  */
968 /*!
969  *  @brief Return the function index from the server
970  *
971  *  Query the server for the given function name and return its index.
972  *  Use the index in the fxnIdx field of the RcmClient_Message struct.
973  *
974  *  @param[in] handle Handle to an instance object
975  *
976  *  @param[in] name The function's name.
977  *
978  *  @param[out] index The function's index.
979  */
980 Int RcmClient_getSymbolIndex(
981         RcmClient_Handle        handle,
982         String                  name,
983         UInt32 *                index
984     );
986 /*
987  *  ======== RcmClient_init ========
988  */
989 /*!
990  *  @brief Initialize the RcmClient module
991  *
992  *  This function is used to initialize the RcmClient module. Call this
993  *  function before calling any other RcmClient function.
994  *
995  *  This function must be serialized by the caller
996  */
997 Void RcmClient_init(Void);
999 /*
1000  *  ======== RcmClient_Parmas_init ========
1001  */
1002 /*!
1003  *  @brief Initialize the instance create params structure
1004  */
1005 Void RcmClient_Params_init(
1006         RcmClient_Params *      params
1007     );
1009 /*
1010  *  ======== RcmClient_releaseJobId ========
1011  */
1012 /*!
1013  *  @brief Return a job id to the server and release all resources
1014  *
1015  *  @param[in] handle Handle to an instance object
1016  *
1017  *  @param[in] jobId The job id to be released
1018  */
1019 Int RcmClient_releaseJobId(
1020         RcmClient_Handle        handle,
1021         UInt16                  jobId
1022     );
1024 /*
1025  *  ======== RcmClient_removeSymbol ========
1026  */
1027 /*!
1028  *  @brief Remove a symbol and from the server function table
1029  *
1030  *  Useful when unloading a DLL from the server.
1031  *
1032  *  @param[in] handle Handle to an instance object
1033  *
1034  *  @param[in] name The function name.
1035  */
1036 Int RcmClient_removeSymbol(
1037         RcmClient_Handle        handle,
1038         String                  name
1039     );
1041 /*
1042  *  ======== RcmClient_waitUntilDone ========
1043  */
1044 /*!
1045  *  @brief Block until the specified message has been executed
1046  *
1047  *  This function will wait until the remote function invoked by the
1048  *  specified message has completed. Upon return from this call, the
1049  *  message will contain the return value and the return context of
1050  *  the remote function.
1051  *
1052  *  @param[in] handle Handle to an instance object
1053  *
1054  *  @param[in] msgId The message ID to wait for.
1055  *
1056  *  @param[out] returnMsg A pointer to the return message or NULL
1057  *  on error. The client must free this message.
1058  */
1059 Int RcmClient_waitUntilDone(
1060         RcmClient_Handle        handle,
1061         UInt16                  msgId,
1062         RcmClient_Message **    returnMsg
1063     );
1066 #if defined (__cplusplus)
1068 #endif /* defined (__cplusplus) */
1070 /*@}*/
1072 #endif /* ti_grcm_RcmClient__include */