Home | History | Annotate | Line # | Download | only in xlibi18n
      1 /*
      2  * Copyright 1992, 1993 by TOSHIBA Corp.
      3  *
      4  * Permission to use, copy, modify, and distribute this software and its
      5  * documentation for any purpose and without fee is hereby granted, provided
      6  * that the above copyright notice appear in all copies and that both that
      7  * copyright notice and this permission notice appear in supporting
      8  * documentation, and that the name of TOSHIBA not be used in advertising
      9  * or publicity pertaining to distribution of the software without specific,
     10  * written prior permission. TOSHIBA make no representations about the
     11  * suitability of this software for any purpose.  It is provided "as is"
     12  * without express or implied warranty.
     13  *
     14  * TOSHIBA DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
     15  * ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
     16  * TOSHIBA BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
     17  * ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
     18  * WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
     19  * ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
     20  * SOFTWARE.
     21  *
     22  * Author: Katsuhisa Yano	TOSHIBA Corp.
     23  *			   	mopi (at) osa.ilab.toshiba.co.jp
     24  */
     25 
     26 #ifdef HAVE_CONFIG_H
     27 #include <config.h>
     28 #endif
     29 #include <stdio.h>
     30 #include "Xlibint.h"
     31 #include "XlcPublic.h"
     32 #include "XlcPubI.h"
     33 
     34 /* The list of all known XlcCharSets. They are identified by their name. */
     35 
     36 typedef struct _XlcCharSetListRec {
     37     XlcCharSet charset;
     38     struct _XlcCharSetListRec *next;
     39 } XlcCharSetListRec, *XlcCharSetList;
     40 
     41 static XlcCharSetList charset_list = NULL;
     42 
     43 /* Returns the charset with the given name (including side suffix).
     44    Returns NULL if not found. */
     45 XlcCharSet
     46 _XlcGetCharSet(
     47     const char *name)
     48 {
     49     XlcCharSetList list;
     50     XrmQuark xrm_name;
     51 
     52     xrm_name = XrmStringToQuark(name);
     53 
     54     for (list = charset_list; list; list = list->next) {
     55 	if (xrm_name == list->charset->xrm_name)
     56 	    return (XlcCharSet) list->charset;
     57     }
     58 
     59     return (XlcCharSet) NULL;
     60 }
     61 
     62 /* Returns the charset with the given encoding (no side suffix) and
     63    responsible for at least the given side (XlcGL or XlcGR).
     64    Returns NULL if not found. */
     65 XlcCharSet
     66 _XlcGetCharSetWithSide(
     67     const char *encoding_name,
     68     XlcSide side)
     69 {
     70     XlcCharSetList list;
     71     XrmQuark xrm_encoding_name;
     72 
     73     xrm_encoding_name = XrmStringToQuark(encoding_name);
     74 
     75     for (list = charset_list; list; list = list->next) {
     76 	if (list->charset->xrm_encoding_name == xrm_encoding_name
     77 	    && (list->charset->side == XlcGLGR || list->charset->side == side))
     78 	    return (XlcCharSet) list->charset;
     79     }
     80 
     81     return (XlcCharSet) NULL;
     82 }
     83 
     84 /* Registers an XlcCharSet in the list of character sets.
     85    Returns True if successful. */
     86 Bool
     87 _XlcAddCharSet(
     88     XlcCharSet charset)
     89 {
     90     XlcCharSetList list;
     91 
     92     if (_XlcGetCharSet(charset->name))
     93 	return False;
     94 
     95     list = Xmalloc(sizeof(XlcCharSetListRec));
     96     if (list == NULL)
     97 	return False;
     98 
     99     list->charset = charset;
    100     list->next = charset_list;
    101     charset_list = list;
    102 
    103     return True;
    104 }
    105 
    106 /* List of resources for XlcCharSet. */
    107 static XlcResource resources[] = {
    108     { XlcNName, NULLQUARK, sizeof(char *),
    109       XOffsetOf(XlcCharSetRec, name), XlcGetMask },
    110     { XlcNEncodingName, NULLQUARK, sizeof(char *),
    111       XOffsetOf(XlcCharSetRec, encoding_name), XlcGetMask },
    112     { XlcNSide, NULLQUARK, sizeof(XlcSide),
    113       XOffsetOf(XlcCharSetRec, side), XlcGetMask },
    114     { XlcNCharSize, NULLQUARK, sizeof(int),
    115       XOffsetOf(XlcCharSetRec, char_size), XlcGetMask },
    116     { XlcNSetSize, NULLQUARK, sizeof(int),
    117       XOffsetOf(XlcCharSetRec, set_size), XlcGetMask },
    118     { XlcNControlSequence, NULLQUARK, sizeof(char *),
    119       XOffsetOf(XlcCharSetRec, ct_sequence), XlcGetMask }
    120 };
    121 
    122 /* Retrieves a number of attributes of an XlcCharSet.
    123    Return NULL if successful, otherwise the name of the first argument
    124    specifying a nonexistent attribute. */
    125 static char *
    126 get_values(
    127     XlcCharSet charset,
    128     XlcArgList args,
    129     int num_args)
    130 {
    131     if (resources[0].xrm_name == NULLQUARK)
    132 	_XlcCompileResourceList(resources, XlcNumber(resources));
    133 
    134     return _XlcGetValues((XPointer) charset, resources, XlcNumber(resources),
    135 			 args, num_args, XlcGetMask);
    136 }
    137 
    138 /* Retrieves a number of attributes of an XlcCharSet.
    139    Return NULL if successful, otherwise the name of the first argument
    140    specifying a nonexistent attribute. */
    141 char *
    142 _XlcGetCSValues(XlcCharSet charset, ...)
    143 {
    144     va_list var;
    145     XlcArgList args;
    146     char *ret;
    147     int num_args;
    148 
    149     va_start(var, charset);
    150     _XlcCountVaList(var, &num_args);
    151     va_end(var);
    152 
    153     va_start(var, charset);
    154     _XlcVaToArgList(var, num_args, &args);
    155     va_end(var);
    156 
    157     if (args == (XlcArgList) NULL)
    158 	return (char *) NULL;
    159 
    160     ret = get_values(charset, args, num_args);
    161 
    162     Xfree(args);
    163 
    164     return ret;
    165 }
    166 
    167 /* Creates a new XlcCharSet, given its name (including side suffix) and
    168    Compound Text ESC sequence (normally at most 4 bytes). */
    169 XlcCharSet
    170 _XlcCreateDefaultCharSet(
    171     const char *name,
    172     const char *ct_sequence)
    173 {
    174     XlcCharSet charset;
    175     size_t name_len, ct_sequence_len;
    176     const char *colon;
    177     char *tmp;
    178 
    179     charset = Xcalloc(1, sizeof(XlcCharSetRec));
    180     if (charset == NULL)
    181 	return (XlcCharSet) NULL;
    182 
    183     name_len = strlen(name);
    184     ct_sequence_len = strlen(ct_sequence);
    185 
    186     /* Fill in name and xrm_name.  */
    187     tmp = Xmalloc(name_len + 1 + ct_sequence_len + 1);
    188     if (tmp == NULL) {
    189 	Xfree(charset);
    190 	return (XlcCharSet) NULL;
    191     }
    192     memcpy(tmp, name, name_len+1);
    193     charset->name = tmp;
    194     charset->xrm_name = XrmStringToQuark(charset->name);
    195 
    196     /* Fill in encoding_name and xrm_encoding_name.  */
    197     if ((colon = strchr(charset->name, ':')) != NULL) {
    198         size_t length = (size_t)(colon - charset->name);
    199         char *encoding_tmp = Xmalloc(length + 1);
    200         if (encoding_tmp == NULL) {
    201             Xfree((char *) charset->name);
    202             Xfree(charset);
    203             return (XlcCharSet) NULL;
    204         }
    205         memcpy(encoding_tmp, charset->name, length);
    206         encoding_tmp[length] = '\0';
    207         charset->encoding_name = encoding_tmp;
    208         charset->xrm_encoding_name = XrmStringToQuark(charset->encoding_name);
    209     } else {
    210         charset->encoding_name = charset->name;
    211         charset->xrm_encoding_name = charset->xrm_name;
    212     }
    213 
    214     /* Fill in ct_sequence.  */
    215     tmp += name_len + 1;
    216     memcpy(tmp, ct_sequence, ct_sequence_len+1);
    217     charset->ct_sequence = tmp;
    218 
    219     /* Fill in side, char_size, set_size. */
    220     if (!_XlcParseCharSet(charset))
    221         /* If ct_sequence is not usable in Compound Text, remove it. */
    222         charset->ct_sequence = "";
    223 
    224     return (XlcCharSet) charset;
    225 }
    226