Back to index

im-sdk  12.3.91
Functions
i18nX.c File Reference
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include "FrameMgr.h"
#include "X11R6IMProtoData.h"
#include "Xi18n.h"
#include "Xi18nX.h"

Go to the source code of this file.

Functions

Xi18nClient_Xi18nFindClient (Xi18n, CARD16)
Xi18nClient_Xi18nNewClient (Xi18n)
void _Xi18nDeleteClient (Xi18n, CARD16)
static Bool WaitXConnectMessage (Display *, Window, XEvent *, XPointer)
static Bool WaitXIMProtocol (Display *, Window, XEvent *, XPointer)
static XClientNewXClient (Xi18n i18n_core, Window new_client)
static unsigned char * ReadXIMMessage (XIMS ims, XClientMessageEvent *ev, int *connect_id)
static void ReadXConnectMessage (XIMS ims, XClientMessageEvent *ev)
static Bool Xi18nXBegin (XIMS ims)
static Bool Xi18nXEnd (XIMS ims)
static char * MakeNewAtom (CARD16 connect_id, char *atomName)
static Bool Xi18nXSend (XIMS ims, CARD16 connect_id, unsigned char *reply, long length)
static Bool CheckCMEvent (Display *display, XEvent *event, XPointer xi18n_core)
static Bool Xi18nXWait (XIMS ims, CARD16 connect_id, CARD8 major_opcode, CARD8 minor_opcode)
static Bool Xi18nXDisconnect (XIMS ims, CARD16 connect_id)
Bool _Xi18nCheckXAddress (Xi18n i18n_core, TransportSW *transSW, char *address)

Function Documentation

Bool _Xi18nCheckXAddress ( Xi18n  i18n_core,
TransportSW transSW,
char *  address 
)

Definition at line 348 of file i18nX.c.

{
    XSpecRec *spec;

    if(!(spec = (XSpecRec *)malloc(sizeof(XSpecRec))))
      return False ;

    i18n_core->address.connect_addr = (XSpecRec *)spec;
    i18n_core->methods.begin = Xi18nXBegin;
    i18n_core->methods.end  = Xi18nXEnd;
    i18n_core->methods.send = Xi18nXSend;
    i18n_core->methods.wait = Xi18nXWait;
    i18n_core->methods.disconnect = Xi18nXDisconnect;
    return True;
}

Here is the call graph for this function:

void _Xi18nDeleteClient ( Xi18n  ,
CARD16   
)

Definition at line 83 of file i18nUtil.c.

{
    Xi18nClient *target = _Xi18nFindClient(i18n_core, connect_id);
    Xi18nClient *ccp, *ccp0;

    for (ccp = i18n_core->address.clients, ccp0 = NULL;
        ccp != NULL;
        ccp0 = ccp, ccp = ccp->next) {
       if (ccp == target) {
           if (ccp0 == NULL) {
              i18n_core->address.clients = ccp->next;
           } else {
              ccp0->next = ccp->next;
           }
           /* put it back to free list */
           target->next = i18n_core->address.free_clients;
           i18n_core->address.free_clients = target;
           return;
       }
    }
    return;
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 70 of file i18nUtil.c.

{
    Xi18nClient *client = i18n_core->address.clients;

    while (client != NULL) {
       if (client->connect_id == connect_id)
         return client;
       client = client->next;
    }
    return NULL;
}

Definition at line 46 of file i18nUtil.c.

{
    static CARD16 connect_id = 0;
    Xi18nClient *client;

    if (i18n_core->address.free_clients != NULL) {
       client = i18n_core->address.free_clients;
       i18n_core->address.free_clients = client->next;
    } else {
       client = (Xi18nClient *)malloc(sizeof(Xi18nClient));
    }
    memset(client, 0, sizeof(Xi18nClient));
    client->connect_id = ++connect_id;
    client->pending = (XIMPending *)NULL;
    client->sync = False;
    client->byte_order = '?';      /* initial value */
    memset(&client->pending, 0, sizeof(XIMPending *));
    client->next = i18n_core->address.clients;
    i18n_core->address.clients = client;

    return (Xi18nClient *)client;
}

Here is the caller graph for this function:

static Bool CheckCMEvent ( Display *  display,
XEvent *  event,
XPointer  xi18n_core 
) [static]

Definition at line 285 of file i18nX.c.

{
    Xi18n i18n_core = (Xi18n)((void *)xi18n_core);
    XSpecRec *spec = (XSpecRec *)i18n_core->address.connect_addr;

    if ((event->type == ClientMessage)
       && (event->xclient.message_type == spec->xim_request))
      return True;
    return False;

}

Here is the caller graph for this function:

static char* MakeNewAtom ( CARD16  connect_id,
char *  atomName 
) [static]

Definition at line 214 of file i18nX.c.

{
    static int sequence = 0;
    sprintf(atomName, "_server%d_%d", connect_id,
           (sequence > 20 ? (sequence = 0) : sequence++));
    return atomName;
}

Here is the caller graph for this function:

static XClient* NewXClient ( Xi18n  i18n_core,
Window  new_client 
) [static]

Definition at line 44 of file i18nX.c.

{
    Display *dpy = i18n_core->address.dpy;
    Xi18nClient *client = _Xi18nNewClient(i18n_core);
    XClient *x_client;

    x_client = (XClient *)malloc(sizeof(XClient));
    x_client->client_win = new_client;
    x_client->accept_win = XCreateSimpleWindow(dpy,
                                          DefaultRootWindow(dpy),
                                          0, 0, 1, 1, 1, 0, 0);
    client->trans_rec = x_client;
    return ((XClient *)x_client);
}

Here is the call graph for this function:

Here is the caller graph for this function:

static void ReadXConnectMessage ( XIMS  ims,
XClientMessageEvent *  ev 
) [static]

Definition at line 148 of file i18nX.c.

{
    Xi18n i18n_core = ims->protocol;
    XSpecRec *spec = (XSpecRec *)i18n_core->address.connect_addr;
    XEvent event;
    Display *dpy = i18n_core->address.dpy;
    Window new_client = ev->data.l[0];
    CARD32 major_version = ev->data.l[1];
    CARD32 minor_version = ev->data.l[2];
    XClient *x_client = NewXClient(i18n_core, new_client);

    if (ev->window != i18n_core->address.im_window)
      return;               /* incorrect connection request */

    if (major_version != 0 || minor_version != 0) {
       major_version = minor_version = 0;
       /* Only supporting only-CM & Property-with-CM method */
    }
    _XRegisterFilterByType(dpy, x_client->accept_win,
                        ClientMessage, ClientMessage,
                        WaitXIMProtocol, (XPointer)ims);
    event.xclient.type = ClientMessage;
    event.xclient.display = dpy;
    event.xclient.window = new_client;
    event.xclient.message_type = spec->connect_request;
    event.xclient.format       = 32;
    event.xclient.data.l[0]    = x_client->accept_win;
    event.xclient.data.l[1]    = major_version;
    event.xclient.data.l[2]    = minor_version;
    event.xclient.data.l[3]    = XCM_DATA_LIMIT;

    XSendEvent(dpy, new_client,
              False, NoEventMask, &event);
    XFlush(dpy);
}

Here is the call graph for this function:

Here is the caller graph for this function:

static unsigned char* ReadXIMMessage ( XIMS  ims,
XClientMessageEvent *  ev,
int *  connect_id 
) [static]

Definition at line 60 of file i18nX.c.

{
    Xi18n i18n_core = ims->protocol;
    Xi18nClient *client = i18n_core->address.clients;
    XClient *x_client = NULL;

    FrameMgr fm;
    extern XimFrameRec packet_header_fr[];
    register int total_size;
    unsigned char *p = NULL;
    unsigned char *p1;

    while (client != NULL) {
       x_client = (XClient *)client->trans_rec;
       if (x_client->accept_win == ev->window) {
           *connect_id = client->connect_id;
           break;
       }
       client = client->next;
    }

    if (ev->format == 8) {  /* ClientMessage only */
       XimProtoHdr *hdr = (XimProtoHdr *)ev->data.b;
       unsigned char *rec = (unsigned char *)(hdr + 1);
       CARD8 major_opcode, minor_opcode;
       CARD16 length;
       extern int _Xi18nNeedSwap(Xi18n, CARD16);

       if (client->byte_order == '?') {
           if (hdr->major_opcode == XIM_CONNECT)
             client->byte_order = (CARD8)rec[0];
           else
             return (unsigned char *)NULL;       /* can do nothing */
       }
       /* create FrameMgr */
       fm = FrameMgrInit(packet_header_fr, (char *)hdr,
                       _Xi18nNeedSwap(i18n_core, *connect_id));

       total_size = FrameMgrGetTotalSize(fm);
       /* get data */
       FrameMgrGetToken(fm, major_opcode);
       FrameMgrGetToken(fm, minor_opcode);
       FrameMgrGetToken(fm, length);

       /* free FrameMgr */
       FrameMgrFree(fm);

       if ((p = (unsigned char *)malloc(total_size + length * 4)) == NULL)
         return (unsigned char *)NULL;
       p1 = p;
       memmove(p1, &major_opcode, sizeof(CARD8)); p1 += sizeof(CARD8);
       memmove(p1, &minor_opcode, sizeof(CARD8)); p1 += sizeof(CARD8);
       memmove(p1, &length, sizeof(CARD16)); p1 += sizeof(CARD16);
       memmove(p1, rec, length * 4);
    } else if (ev->format == 32) { /* ClientMessage and WindowProperty */
       unsigned long length = (unsigned long)ev->data.l[0];
       Atom atom = (Atom)ev->data.l[1];
       int         return_code;
       Atom        actual_type_ret;
       int         actual_format_ret;
       unsigned long    bytes_after_ret;
       unsigned char    *prop;
       unsigned long    nitems;

       return_code = XGetWindowProperty(i18n_core->address.dpy,
                                    x_client->accept_win, atom,
                                    0L, length,
                                    True, AnyPropertyType,
                                    &actual_type_ret, &actual_format_ret,
                                    &nitems, &bytes_after_ret, &prop);
       if (return_code != Success
           || actual_format_ret == 0 || nitems == 0) {
           if (return_code == Success)
             XFree(prop);
           return (unsigned char *)NULL;
       }
       if (length != nitems) length = nitems;
                            /* if hit, it might be an error */
       if ((p = (unsigned char *)malloc(length)) == NULL)
         return (unsigned char *)NULL;
       memmove(p, prop, length);
       XFree(prop);
    }
    return (unsigned char *)p;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static Bool WaitXConnectMessage ( Display *  dpy,
Window  win,
XEvent *  ev,
XPointer  client_data 
) [static]

Definition at line 366 of file i18nX.c.

{
    XIMS ims = (XIMS)client_data;
    Xi18n i18n_core = ims->protocol;
    XSpecRec *spec = (XSpecRec *)i18n_core->address.connect_addr;

    if (((XClientMessageEvent *)ev)->message_type ==
       spec->connect_request) {
       ReadXConnectMessage(ims,
                         (XClientMessageEvent *)ev);
       return True;
    }
    return False;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static Bool WaitXIMProtocol ( Display *  dpy,
Window  win,
XEvent *  ev,
XPointer  client_data 
) [static]

Definition at line 383 of file i18nX.c.

{
    XIMS ims = (XIMS)client_data;
    Xi18n i18n_core = ims->protocol;
    XSpecRec *spec = (XSpecRec *)i18n_core->address.connect_addr;
    extern void _Xi18nMessageHandler(XIMS, CARD16,
                                 unsigned char*, Bool*);
    Bool delete = True;
    unsigned char *packet;
    int connect_id;

    if (((XClientMessageEvent *)ev)->message_type ==
       spec->xim_request) {
       if ((packet = ReadXIMMessage(ims,
                                 (XClientMessageEvent *)ev,
                                 &connect_id))
           == (unsigned char*)NULL) return False;

       _Xi18nMessageHandler(ims, connect_id, packet, &delete);
       if (delete == True)
           XFree(packet);
       return True;
    }
    return False;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static Bool Xi18nXBegin ( XIMS  ims) [static]

Definition at line 185 of file i18nX.c.

{
    Xi18n i18n_core = ims->protocol;
    Display *dpy = i18n_core->address.dpy;
    XSpecRec *spec = (XSpecRec *)i18n_core->address.connect_addr;

    spec->xim_request = XInternAtom(i18n_core->address.dpy,
                                _XIM_PROTOCOL, False);
    spec->connect_request = XInternAtom(i18n_core->address.dpy,
                                   _XIM_XCONNECT, False);

    _XRegisterFilterByType(dpy, i18n_core->address.im_window,
                        ClientMessage, ClientMessage,
                        WaitXConnectMessage, (XPointer)ims);
    return True;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static Bool Xi18nXDisconnect ( XIMS  ims,
CARD16  connect_id 
) [static]

Definition at line 332 of file i18nX.c.

{
    Xi18n i18n_core = ims->protocol;
    Display *dpy = i18n_core->address.dpy;
    Xi18nClient *client = _Xi18nFindClient(i18n_core, connect_id);
    XClient *x_client = (XClient *)client->trans_rec;

    XDestroyWindow(dpy, x_client->accept_win);
    _XUnregisterFilter(dpy, x_client->accept_win,
                     WaitXIMProtocol, (XPointer)ims);
    XFree(x_client);
    _Xi18nDeleteClient(i18n_core, connect_id);
    return True;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static Bool Xi18nXEnd ( XIMS  ims) [static]

Definition at line 203 of file i18nX.c.

{
    Xi18n i18n_core = ims->protocol;
    Display *dpy = i18n_core->address.dpy;

    _XUnregisterFilter(dpy, i18n_core->address.im_window,
                     WaitXConnectMessage, (XPointer)ims);
    return True;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static Bool Xi18nXSend ( XIMS  ims,
CARD16  connect_id,
unsigned char *  reply,
long  length 
) [static]

Definition at line 223 of file i18nX.c.

{
    Xi18n i18n_core = ims->protocol;
    Xi18nClient *client = _Xi18nFindClient(i18n_core, connect_id);
    XSpecRec *spec = (XSpecRec *)i18n_core->address.connect_addr;
    XClient *x_client = (XClient *)client->trans_rec;
    XEvent event;
    
    event.type = ClientMessage;
    event.xclient.window = x_client->client_win;
    event.xclient.message_type = spec->xim_request;

    if (length > XCM_DATA_LIMIT) {
       Atom atom;
       char atomName[16];
       Atom actual_type_ret;
       int actual_format_ret;
       int return_code;
       unsigned long nitems_ret;
       unsigned long bytes_after_ret;
       unsigned char *win_data;

       event.xclient.format = 32;
       atom = XInternAtom(i18n_core->address.dpy,
                        MakeNewAtom(connect_id, atomName), False);
       return_code = XGetWindowProperty(i18n_core->address.dpy,
                             x_client->client_win, atom, 0L, 10000L,
                             False, XA_STRING, &actual_type_ret,
                             &actual_format_ret, &nitems_ret,
                             &bytes_after_ret, &win_data);
       if (return_code != Success)
         return False;
       if (win_data)
         XFree((char *)win_data);
       XChangeProperty(i18n_core->address.dpy,
                     x_client->client_win, atom, XA_STRING, 8,
                     PropModeAppend, (unsigned char *)reply, length);
       event.xclient.data.l[0] = length;
       event.xclient.data.l[1] = atom;
    }
    else {
       unsigned char buffer[XCM_DATA_LIMIT];
       int i;

       event.xclient.format = 8;

       /* Clear unused field with NULL */
       memmove(buffer, reply, length);
       for (i = length; i < XCM_DATA_LIMIT; i++) {
           buffer[i] = (char)0;
       }
       length = XCM_DATA_LIMIT;
       memmove(event.xclient.data.b, buffer, length);
    }
    XSendEvent(i18n_core->address.dpy,
              x_client->client_win, False, NoEventMask, &event);
    XFlush(i18n_core->address.dpy);
    return True;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static Bool Xi18nXWait ( XIMS  ims,
CARD16  connect_id,
CARD8  major_opcode,
CARD8  minor_opcode 
) [static]

Definition at line 298 of file i18nX.c.

{
    Xi18n i18n_core = ims->protocol;
    XEvent event;
    Xi18nClient *client = _Xi18nFindClient(i18n_core, connect_id);
    XClient *x_client = (XClient *)client->trans_rec;

    for (;;) {
       unsigned char *packet;
       XimProtoHdr *hdr;
       int connect_id_ret;

       XIfEvent(i18n_core->address.dpy, &event,
               CheckCMEvent, (XPointer)i18n_core);
       if (event.xclient.window == x_client->accept_win) {

           if ((packet = ReadXIMMessage(ims,
                             (XClientMessageEvent *)&event,
                             &connect_id_ret))
              == (unsigned char*)NULL) return False;

           hdr = (XimProtoHdr *)packet;

           if ((hdr->major_opcode == major_opcode) &&
              (hdr->minor_opcode == minor_opcode))
             return True;
           else if (hdr->major_opcode == XIM_ERROR)
             return False;
       }
    }
}

Here is the call graph for this function:

Here is the caller graph for this function: