TOC PREV NEXT INDEX


Procedure for Calling a Generated C Encode Function


The encode function generated for an XSD global element definition is the normal entry point for encoding an XML document. The general procedure for calling a global element encode function is as follows:
1. Prepare a context variable for encoding
2. Initialize an encode message buffer or stream to receive the encoded XML data
3. Populate the data variable with data to be encoded
4. Call the appropriate compiler-generated encode function to encode the message
5. If a message buffer was used, get the start pointer and length of the encoded message
Before a C XML encode function can be called; the user must initialize a context variable. This is a variable of type OSCTXT. This variable holds all of the working data used during the encoding of a message. The context variable is declared as a normal automatic variable within the top-level calling function. It must be initialized before use. This can be accomplished by using the rtXmlInitContext function:

	OSCTXT ctxt;	/* context variable */ 
 

 
	if (rtXmlInitContext (&ctxt) != 0) {
 
           /* initialization failed, could be a license problem */
 
           printf ("context initialization failed (check license)\n");
 
           return -1;
 
        }
 

The next step is to specify an encode buffer or stream into which the message will be encoded. This is accomplished by calling the rtXmlSetEncBufPtr run-time function (for a message buffer) or one of the rtxStream functions to create an output stream. If a message buffer is to be used, the user has the option to either pass the address of a buffer and size allocated in his or her program (referred to as a static buffer), or set these parameters to zero and let the encode function manage the buffer memory allocation (referred to as a dynamic buffer). Better performance can normally be attained by using a static buffer because this eliminates the high-overhead operation of allocating and reallocating memory.
After initializing the context and populating a variable of the structure to be encoded, an encode function can be called to encode the message. If the return status indicates success, the run-time library function rtXmlGetEncBufPtr can be called to obtain the start address of the encoded message. In the static case, this is simply the start address of the static buffer. In the dynamic case, this function will return the pointer to the allocated memory buffer. The memory allocated for a dynamic buffer will be freed when either the context is freed (rtxFreeContext) or all memory associated with the context is released (rtxMemFree) or the buffer memory is explicity released (rtxMemFreePtr).
In the stream case, the pointer to the encoded message generally cannot be obtained since the message has already been written to the stream. The only thing necessary to do in this case is to close the stream after encoding is complete. Use the rtxStreamClose function which should be called before the rtxFreeContext function.
A program fragment that could be used to encode an employee record is as follows:

#include "employee.h"
 

 
#define MAXMSGLEN 1024
 

 
int main (int argc, char** argv)
 
{
 
   PersonnelRecord employee;
 
   OSCTXT	  ctxt;
 
   OSOCTET	 msgbuf[MAXMSGLEN];
 
   int	    i, stat;
 
   const char* filename = "message.xml";
 

 
   /* Init context */
 

 
   stat = rtXmlInitContext (&ctxt);
 
   if (0 != stat) {
 
      printf ("Context initialization failed.\n");
 
      rtxErrPrint (&ctxt);
 
      return stat;
 
   }
 

 
   /* Populate structure of generated type */
 

 
   Init_PersonnelRecord (&ctxt, &employee);
 

 
   ... logic to populate structure here ...
 

 
   /* Encode */
 

 
   stat = rtXmlSetEncBufPtr (&ctxt, msgbuf, sizeof(msgbuf));
 

 
   if (0 == stat)
 
      stat = XmlE_personnelRecord (&ctxt, &employee);
 

 
   if (0 == stat) {
 
      printf ("encoded XML message:\n");
 
      printf (msgbuf);
 
      printf ("\n");
 
   }
 
   else {
 
      printf ("Encoding failed\n");
 
      rtxErrPrint (&ctxt);
 
      return stat;
 
   }
 

 
	... logic to process encoded message (write to file, etc.) ...
 

 
   rtxFreeContext (&ctxt);
 

 
  
 
This example used a static message buffer. The encoded XML text will reside in the msgbuf message buffer when the procedure complete.
A program fragment that could be used to encode an employee record to a file stream is as follows:

#include "rtxsrc/rtxStreamFile.h"
 
#include "employee.h"
 

 
int main (int argc, char** argv)
 
{
 
   PersonnelRecord employee;
 
   OSCTXT  ctxt;
 
   int     stat;
 
   const char* filename = "message.xml";
 

 
   /* Init context */
 

 
   stat = rtXmlInitContext (&ctxt);
 
   if (0 != stat) {
 
      printf ("Context initialization failed.\n");
 
      rtxErrPrint (&ctxt);
 
      return stat;
 
   }
 

 
   /* Populate structure of generated type */
 

 
   Init_PersonnelRecord (&ctxt, &employee);
 

 
   ... logic to populate structure here ...
 

 
   /* Encode directly to output stream */
 

 
   stat = rtxStreamFileCreateWriter (&ctxt, filename);
 
   if (0 != stat) {
 
      printf ("Stream initialization failed.\n");
 
      rtxErrPrint (&ctxt);
 
      return stat;
 
   }
 

 
   stat = XmlE_personnelRecord (&ctxt, &employee);
 

 
   if (0 != stat) {
 
      printf ("Encoding failed\n");
 
      rtxErrPrint (&ctxt);
 
      return stat;
 
   }
 
   rtxStreamClose (&ctxt);
 
   rtxFreeContext (&ctxt);
 
   return 0;
 
}
 

 

Copyright © Objective Systems 2002-2008
This document may be distributed in any form, electronic or otherwise, provided that it is distributed in its entirety and that the copyright and this notice are included.

Objective Systems, Inc.

55 Dowlin Forge Road
Exton, Pennsylvania 19341
http://www.obj-sys.com
Phone: (484) 875-9841
Toll-free: (877) 307-6855 (US only)
Fax: (484) 875-9830
info@obj-sys.com

TOC PREV NEXT INDEX