/*static char *SCCSID = "@(#)rxnlsinf.c 6.1 91/09/20";*/
/*******************************************************************/
/*								   */
/* Module Name:	       RXNLSINF					   */
/*								   */
/* Description:	       Provide limited NLS support for REXX.	   */
/*								   */
/* Function:	       Returns country dependent information for   */
/*		       use in formatting currency amounts.	   */
/*								   */
/* Entry point:	       RxNLSInfo()				   */
/*								   */
/* Notes:							   */
/*								   */
/*   The entry point obeys the calling conventions for REXX	   */
/*   external functions.					   */
/*								   */
/*******************************************************************/

/*******************************************************************/
/*								   */
/* Include files.  We use the following:			   */
/*								   */
/*    REXXSAA.H		REXX specific type definitions and	   */
/*			function prototypes.			   */
/*								   */
/*    OS2.H		OS/2 specific type definitions and	   */
/*			function prototypes.			   */
/*								   */
/*    stdlib.h		Standard C library function prototypes.	   */
/*								   */
/*    string.h		Standard C library string function	   */
/*			prototypes.				   */
/*								   */
/*******************************************************************/

#define	    INCL_DOSNLS
#include    <os2.h>
#define INCL_RXFUNC		  /* include external function	info */
#include    <rexxsaa.h>
#include    <stdlib.h>
#include    <string.h>

/*******************************************************************/
/*								   */
/* Function prototype follows.					   */
/*								   */
/*******************************************************************/
RexxFunctionHandler RxNLSInfo;

/*******************************************************************/
/*								   */
/* Function:		RxNLSInfo()				   */
/*								   */
/* Description:		Return country dependent information.	   */
/*			Please see notes for details.		   */
/*								   */
/* Input:		Name of desired information.		   */
/*								   */
/* Output:		Desired information.  Please see notes.	   */
/*			Returns 0 if the function executed OK,	   */
/*			-1 otherwise.  The interpreter will	   */
/*			raise an error condition if this function  */
/*			returns a non-zero result.		   */
/*								   */
/* Effects:		None.					   */
/*								   */
/* External References: DosQueryCtryInfo()			   */
/*								   */
/* Internal References: none					   */
/*								   */
/* Notes:							   */
/*								   */
/*   This routine takes one parameter.	The form of the call is:   */
/*								   */
/*   NLS_Information = RxNLSInfo( request )			   */
/*								   */
/*   The value of the request parameter determines the information */
/*   returned.	Valid values are:				   */
/*								   */
/*   request		value returned				   */
/*   -------		--------------				   */
/*								   */
/*   prefix		Currency prefix string.	 It is followed by */
/*			a space if a space should separate the	   */
/*			currency symbol from the value.		   */
/*			If the currency string follows the amount, */
/*			this request returns an empty string.	   */
/*								   */
/*   suffix		Currency suffix string.	 If the currency   */
/*			string preceeds the amount, this request   */
/*			returns an empty string.		   */
/*								   */
/*   infix		Currency infix string.	This is the	   */
/*			decimal point unless the currency string   */
/*			goes between the integer and fractional	   */
/*			part of the amount.  In this case, it	   */
/*			is the currency string.			   */
/*								   */
/*   thousand		Thousands separator.			   */
/*								   */
/*   decimal		Decimal separator.			   */
/*								   */
/*   The routine ignores the case of the request parameter.  If	   */
/*   the parameter is invalid or the argument count is not one,	   */
/*   the function returns an empty string.			   */
/*								   */
/* Error handling:  If this function is called with the wrong	   */
/*   number of arguments, or an argument that is not on the	   */
/*   list above, then we return with a value of -1, which will	   */
/*   raise REXX error 40, "Invalid call to routine", in the	   */
/*   REXX program.						   */
/*   This function also raises that error if the call to	   */
/*   DosQueryCtryInfo produces any non-zero return code.	   */
/*								   */
/*******************************************************************/

ULONG RxNLSInfo(
   PUCHAR    func,
   ULONG     argc,
   PRXSTRING argv,
   PSZ	     que,
   PRXSTRING ret)
{
   COUNTRYINFO	   country_data ;      /* Structure to receive	    */
				       /* country-dependent data.   */
   static
      COUNTRYCODE  country_code =      /* Country and code page	    */
		   {		       /* desired.		    */
		      0,	       /* Default country code.	    */
		      0		       /* Default code page.	    */
		    } ;

   PSZ		    infix ;	       /* Currency infix pointer.   */

   ULONG	    bytes_returned ;   /* Number of bytes returned  */
				       /* by DosQueryCtryInfo().    */

   LONG		    rc = -1 ;	       /* Function return value.    */

   /*****************************************************************/
   /* If the call to DosGetCntryInfo() fails or the arguments are   */
   /* invalid, we want to return an empty RXSTRING.		    */
   /* So we set the return strlength to 0.			    */
   /*								    */
   /* Please note that the REXX interpreter allocates 255 bytes in  */
   /* the return string.  This will suffice for us.		    */
   /*****************************************************************/

   ret -> strlength = 0 ;

   /*****************************************************************/
   /* If the argument count is valid (i.e.  1) and the argument is  */
   /* not too long, try to get the country dependent information.   */
   /* If the call succeeds, return the information that the caller  */
   /* wants.							    */
   /*****************************************************************/

   if( ( argc == 1 ) &&		       /* Arg count valid?	    */
       ( ! DosQueryCtryInfo(	       /* Have country info?	    */
		sizeof( country_data ),
		& country_code,
		& country_data,
		& bytes_returned ) ) )
   {

      /**************************************************************/
      /* We have the country dependent data in the data structure.  */
      /* Extract the data the caller requested and return it in the */
      /* return buffer.						    */
      /**************************************************************/

      if( ! stricmp( argv->strptr, "PREFIX" ) )
      {
	 rc = 0 ;		       /* Function call is OK.	   */

	 /**********************************************************/
	 /* Caller has requested currency prefix.  If the currency */
	 /* string preceeds the amount, return it.  If a space	   */
	 /* should follow the currency string, insert a space	   */
	 /* after the currency string.				   */
	 /**********************************************************/

	 if( ! ( country_data . fsCurrencyFmt & 5 ) )
	 {
	    ( void ) strcpy( ret -> strptr,
			     country_data . szCurrency ) ;

	    ret -> strlength =
			strlen( country_data . szCurrency ) ;

	    /********************************************************/
	    /* If a space should follow the currency string,	    */
	    /* append one.					    */
	    /********************************************************/

	    if( ( country_data . fsCurrencyFmt & 1 ) )
	    {
	       ( void ) strcat( ret -> strptr,
				" " ) ;
	       ++ ( ret -> strlength ) ;
	    }			       /* If a space follows ...    */
	 }			       /* If symbol preceeds ...    */
      }				       /* If caller wants prefix ...*/
      else if( ! stricmp( argv->strptr, "SUFFIX" ) )
      {
	 rc = 0 ;		       /* Function call is OK.	    */

	 /***********************************************************/
	 /* Caller has requested the currency suffix.  If the	    */
	 /* currency string follows the amount, return the string.  */
	 /* Otherwise, leave the returned string empty.		    */
	 /***********************************************************/

	 if( ( country_data . fsCurrencyFmt & 5 ) == 1 )
	 {
	    if( ( country_data . fsCurrencyFmt & 1 ) == 1 )
	    {
	       ( void ) strcpy( ret -> strptr, " " ) ;
	       ret -> strlength = 1 ;
	    }

	    ( void ) strcat( ret -> strptr,
			     country_data . szCurrency ) ;

	    ret -> strlength +=
			strlen( country_data . szCurrency ) ;
	 }			       /* If string follows amount. */
      }				       /* If Caller wants prefix ...*/
      else if( ! stricmp( argv->strptr, "INFIX" ) )
      {
	 rc = 0 ;		       /* Function call is OK ...   */

	 /***********************************************************/
	 /* Caller has requested the currency infix.  If the	    */
	 /* currency symbol separates the integral and fractional   */
	 /* portions of the amount, return the currency string.	    */
	 /* Otherwise, return the decimal separator.		    */
	 /***********************************************************/

	 infix = (		       /* Select the string to	    */
	    country_data .	       /* return...		    */
	       fsCurrencyFmt & 4 ) ?
		  country_data . szCurrency :
		  country_data . szDecimal ;

	    ( void ) strcpy( ret -> strptr,
			     infix ) ;

	    ret -> strlength =
			strlen( infix ) ;

      }				       /* If caller wants infix ... */
      else if( ! stricmp( argv->strptr, "THOUSAND" ) )
      {
	 rc = 0 ;		       /* Function call is OK.	    */

	 /***********************************************************/
	 /* Caller has requested thousands separator.  Return same. */
	 /***********************************************************/

	 ( void ) strcpy( ret -> strptr,
			  country_data . szThousandsSeparator ) ;

	    ret -> strlength =
			strlen( country_data . szThousandsSeparator ) ;
      }				       /* If thousand separator ..  */
      else if( ! stricmp( argv->strptr, "DECIMAL" ) )
      {
	 rc = 0 ;		       /* Call is OK.		    */

	 /***********************************************************/
	 /* Caller has requested the decimal point.  Return same.   */
	 /***********************************************************/

	 ( void ) strcpy( ret -> strptr,
			  country_data . szDecimal ) ;

	    ret -> strlength =
			strlen( country_data . szDecimal ) ;
      }				       /* If caller wants decimal.  */
   }				       /* If args & call OK ...	    */
   return( rc ) ;
}				       /* End of function.	    */

