diff options
Diffstat (limited to 'libXt/src/Initialize.c')
-rw-r--r-- | libXt/src/Initialize.c | 1054 |
1 files changed, 1054 insertions, 0 deletions
diff --git a/libXt/src/Initialize.c b/libXt/src/Initialize.c new file mode 100644 index 000000000..9b2928d12 --- /dev/null +++ b/libXt/src/Initialize.c @@ -0,0 +1,1054 @@ +/* $Xorg: Initialize.c,v 1.8 2001/02/09 02:03:55 xorgcvs Exp $ */ + +/*********************************************************** +Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts +Copyright 1993 by Sun Microsystems, Inc. Mountain View, CA. + + All Rights Reserved + +Permission to use, copy, modify, and distribute this software and its +documentation for any purpose and without fee is hereby granted, +provided that the above copyright notice appear in all copies and that +both that copyright notice and this permission notice appear in +supporting documentation, and that the names of Digital or Sun not be +used in advertising or publicity pertaining to distribution of the +software without specific, written prior permission. + +DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING +ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL +DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR +ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, +WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, +ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS +SOFTWARE. + +SUN DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, +INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FIT- +NESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SUN BE LI- +ABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR +ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR +PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR +OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH +THE USE OR PERFORMANCE OF THIS SOFTWARE. + +******************************************************************/ +/* $XFree86: xc/lib/Xt/Initialize.c,v 3.21 2003/04/21 16:34:27 herrb Exp $ */ + +/* + +Copyright 1987, 1988, 1994, 1998 The Open Group + +Permission to use, copy, modify, distribute, and sell this software and its +documentation for any purpose is hereby granted without fee, provided that +the above copyright notice appear in all copies and that both that +copyright notice and this permission notice appear in supporting +documentation. + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN +AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +Except as contained in this notice, the name of The Open Group shall not be +used in advertising or otherwise to promote the sale, use or other dealings +in this Software without prior written authorization from The Open Group. + +*/ + +/* Make sure all wm properties can make it out of the resource manager */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif +#include "IntrinsicI.h" +#include "StringDefs.h" +#include "CoreP.h" +#include "ShellP.h" +#include <stdio.h> +#include <X11/Xlocale.h> +#ifdef XTHREADS +#include <X11/Xthreads.h> +#endif +#ifndef WIN32 +#define X_INCLUDE_PWD_H +#define XOS_USE_XT_LOCKING +#include <X11/Xos_r.h> +#endif + +#include <stdlib.h> + +#if (defined(SUNSHLIB) || defined(AIXSHLIB)) && defined(SHAREDCODE) +/* + * If used as a shared library, generate code under a different name so that + * the stub routines in sharedlib.c get loaded into the application binary. + */ +#define XtToolkitInitialize _XtToolkitInitialize +#define XtOpenApplication _XtOpenApplication +#define XtAppInitialize _XtAppInitialize +#define XtInitialize _XtInitialize +#endif /* (SUNSHLIB || AIXSHLIB) && SHAREDCODE */ + +/* + * hpux + * Hand-patched versions of HP-UX prior to version 7.0 can usefully add + * -DUSE_UNAME in the appropriate config file to get long hostnames. + */ + +#ifdef USG +#define USE_UNAME +#endif + +#ifdef USE_UNAME +#include <sys/utsname.h> +#endif + +/* some unspecified magic number of expected search levels for Xrm */ +#define SEARCH_LIST_SIZE 1000 + +/* + This is a set of default records describing the command line arguments that + Xlib will parse and set into the resource data base. + + This list is applied before the users list to enforce these defaults. This is + policy, which the toolkit avoids but I hate differing programs at this level. +*/ + +static XrmOptionDescRec const opTable[] = { +{"+rv", "*reverseVideo", XrmoptionNoArg, (XtPointer) "off"}, +{"+synchronous","*synchronous", XrmoptionNoArg, (XtPointer) "off"}, +{"-background", "*background", XrmoptionSepArg, (XtPointer) NULL}, +{"-bd", "*borderColor", XrmoptionSepArg, (XtPointer) NULL}, +{"-bg", "*background", XrmoptionSepArg, (XtPointer) NULL}, +{"-bordercolor","*borderColor", XrmoptionSepArg, (XtPointer) NULL}, +{"-borderwidth",".borderWidth", XrmoptionSepArg, (XtPointer) NULL}, +{"-bw", ".borderWidth", XrmoptionSepArg, (XtPointer) NULL}, +{"-display", ".display", XrmoptionSepArg, (XtPointer) NULL}, +{"-fg", "*foreground", XrmoptionSepArg, (XtPointer) NULL}, +{"-fn", "*font", XrmoptionSepArg, (XtPointer) NULL}, +{"-font", "*font", XrmoptionSepArg, (XtPointer) NULL}, +{"-foreground", "*foreground", XrmoptionSepArg, (XtPointer) NULL}, +{"-geometry", ".geometry", XrmoptionSepArg, (XtPointer) NULL}, +{"-iconic", ".iconic", XrmoptionNoArg, (XtPointer) "on"}, +{"-name", ".name", XrmoptionSepArg, (XtPointer) NULL}, +{"-reverse", "*reverseVideo", XrmoptionNoArg, (XtPointer) "on"}, +{"-rv", "*reverseVideo", XrmoptionNoArg, (XtPointer) "on"}, +{"-selectionTimeout", + ".selectionTimeout", XrmoptionSepArg, (XtPointer) NULL}, +{"-synchronous","*synchronous", XrmoptionNoArg, (XtPointer) "on"}, +{"-title", ".title", XrmoptionSepArg, (XtPointer) NULL}, +{"-xnllanguage",".xnlLanguage", XrmoptionSepArg, (XtPointer) NULL}, +{"-xrm", NULL, XrmoptionResArg, (XtPointer) NULL}, +{"-xtsessionID",".sessionID", XrmoptionSepArg, (XtPointer) NULL}, +}; + + +/* + * GetHostname - emulates gethostname() on non-bsd systems. + */ + +static void GetHostname ( + char *buf, + int maxlen) +{ +#ifdef USE_UNAME + int len; + struct utsname name; + + if (maxlen <= 0 || buf == NULL) + return; + + uname (&name); + len = strlen (name.nodename); + if (len >= maxlen) len = maxlen; + (void) strncpy (buf, name.nodename, len-1); + buf[len-1] = '\0'; +#else + if (maxlen <= 0 || buf == NULL) + return; + + buf[0] = '\0'; + (void) gethostname (buf, maxlen); + buf [maxlen - 1] = '\0'; +#endif +} + + +#ifdef SUNSHLIB +void _XtInherit(void) +{ + extern void __XtInherit(); + __XtInherit(); +} +#define _XtInherit __XtInherit +#endif + + +#if (defined (WIN32) || defined(__CYGWIN__)) && !defined(_MSC_VER) +/* + * The Symbol _XtInherit is used in two different manners. + * First it could be used as a generic function and second + * as an absolute address reference, which will be used to + * check the initialisation process of several other libraries. + * Because of this the symbol must be accessable by all + * client dll's and applications. In unix environments + * this is no problem, because the used shared libraries + * format (elf) supports this immediatly. Under Windows + * this isn't true, because a functions address in a dll + * is different from the same function in another dll or + * applications, because the used Portable Executable + * File adds a code stub to each client to provide the + * exported symbol name. This stub uses an indirect + * pointer to get the original symbol address, which is + * then jumped to, like in this example: + * + * --- client --- --- dll ---- + * ... + * call foo + * + * foo: jmp (*_imp_foo) ----> foo: .... + * nop + * nop + * + * _imp_foo: .long <index of foo in dll export table, is + * set to the real address by the runtime linker> + * + * Now it is clear why the clients symbol foo isn't the same + * as in the dll and we can think about how to deal which + * this two above mentioned requirements, to export this + * symbol to all clients and to allow calling this symbol + * as a function. The solution I've used exports the + * symbol _XtInherit as data symbol, because global data + * symbols are exported to all clients. But how to deal + * with the second requirement, that this symbol should + * be used as function. The Trick is to build a little + * code stub in the data section in the exact manner as + * above explained. This is done with the assembler code + * below. + * + * Ralf Habacker + * + * References: + * msdn http://msdn.microsoft.com/msdnmag/issues/02/02/PE/PE.asp + * cygwin-xfree: http://www.cygwin.com/ml/cygwin-xfree/2003-10/msg00000.html + */ + +asm (".data\n\ + .globl __XtInherit \n\ + __XtInherit: jmp *_y \n\ + _y: .long ___XtInherit \n\ + .text \n"); + +#define _XtInherit __XtInherit +#endif + + +void _XtInherit(void) +{ + XtErrorMsg("invalidProcedure","inheritanceProc",XtCXtToolkitError, + "Unresolved inheritance operation", + (String *)NULL, (Cardinal *)NULL); +} + + +void XtToolkitInitialize(void) +{ + static Boolean initialized = False; + + LOCK_PROCESS; + if (initialized) { + UNLOCK_PROCESS; + return; + } + initialized = True; + UNLOCK_PROCESS; + /* Resource management initialization */ + XrmInitialize(); + _XtResourceListInitialize(); + + /* Other intrinsic intialization */ + _XtConvertInitialize(); + _XtEventInitialize(); + _XtTranslateInitialize(); + + /* Some apps rely on old (broken) XtAppPeekEvent behavior */ + if(getenv("XTAPPPEEKEVENT_SKIPTIMER")) + XtAppPeekEvent_SkipTimer = True; + else + XtAppPeekEvent_SkipTimer = False; +} + + +String _XtGetUserName( + String dest, + int len) +{ +#ifdef WIN32 + String ptr = NULL; + + if ((ptr = getenv("USERNAME"))) { + (void) strncpy (dest, ptr, len-1); + dest[len-1] = '\0'; + } else + *dest = '\0'; +#else +#ifdef X_NEEDS_PWPARAMS + _Xgetpwparams pwparams; +#endif + struct passwd *pw; + char* ptr; + + if ((ptr = getenv("USER"))) { + (void) strncpy (dest, ptr, len-1); + dest[len-1] = '\0'; + } else { + if ((pw = _XGetpwuid(getuid(),pwparams)) != NULL) { + (void) strncpy (dest, pw->pw_name, len-1); + dest[len-1] = '\0'; + } else + *dest = '\0'; + } +#endif + return dest; +} + + +static String GetRootDirName( + String dest, + int len) +{ +#ifdef WIN32 + register char *ptr1; + register char *ptr2 = NULL; + int len1 = 0, len2 = 0; + + if (ptr1 = getenv("HOME")) { /* old, deprecated */ + len1 = strlen (ptr1); + } else if ((ptr1 = getenv("HOMEDRIVE")) && (ptr2 = getenv("HOMEDIR"))) { + len1 = strlen (ptr1); + len2 = strlen (ptr2); + } else if (ptr2 = getenv("USERNAME")) { + len1 = strlen (ptr1 = "/users/"); + len2 = strlen (ptr2); + } + if ((len1 + len2 + 1) < len) + sprintf (dest, "%s%s", ptr1, (ptr2) ? ptr2 : ""); + else + *dest = '\0'; +#else +#ifdef X_NEEDS_PWPARAMS + _Xgetpwparams pwparams; +#endif + struct passwd *pw; + static char *ptr; + + if (len <= 0 || dest == NULL) + return NULL; + + if ((ptr = getenv("HOME"))) { + (void) strncpy (dest, ptr, len-1); + dest[len-1] = '\0'; + } else { + if ((ptr = getenv("USER"))) + pw = _XGetpwnam(ptr,pwparams); + else + pw = _XGetpwuid(getuid(),pwparams); + if (pw != NULL) { + (void) strncpy (dest, pw->pw_dir, len-1); + dest[len-1] = '\0'; + } else + *dest = '\0'; + } +#endif + return dest; +} + +static void CombineAppUserDefaults( + Display *dpy, + XrmDatabase *pdb) +{ + char* filename; + char* path; + Boolean deallocate = False; + + if (!(path = getenv("XUSERFILESEARCHPATH"))) { +#if !defined(WIN32) || !defined(__MINGW32__) + char *old_path; + char homedir[PATH_MAX]; + GetRootDirName(homedir, PATH_MAX); + if (!(old_path = getenv("XAPPLRESDIR"))) { + char *path_default = "%s/%%L/%%N%%C:%s/%%l/%%N%%C:%s/%%N%%C:%s/%%L/%%N:%s/%%l/%%N:%s/%%N"; + if (!(path = + ALLOCATE_LOCAL(6*strlen(homedir) + strlen(path_default)))) + _XtAllocError(NULL); + sprintf( path, path_default, + homedir, homedir, homedir, homedir, homedir, homedir ); + } else { + char *path_default = "%s/%%L/%%N%%C:%s/%%l/%%N%%C:%s/%%N%%C:%s/%%N%%C:%s/%%L/%%N:%s/%%l/%%N:%s/%%N:%s/%%N"; + if (!(path = + ALLOCATE_LOCAL( 6*strlen(old_path) + 2*strlen(homedir) + + strlen(path_default)))) + _XtAllocError(NULL); + sprintf(path, path_default, old_path, old_path, old_path, homedir, + old_path, old_path, old_path, homedir ); + } + deallocate = True; +#endif + } + + filename = XtResolvePathname(dpy, NULL, NULL, NULL, path, NULL, 0, NULL); + if (filename) { + (void)XrmCombineFileDatabase(filename, pdb, False); + XtFree(filename); + } + + if (deallocate) DEALLOCATE_LOCAL(path); +} + +static void CombineUserDefaults( + Display *dpy, + XrmDatabase *pdb) +{ +#ifdef __MINGW32__ + char *slashDotXdefaults = "/Xdefaults"; +#else + char *slashDotXdefaults = "/.Xdefaults"; +#endif + char *dpy_defaults = XResourceManagerString(dpy); + + if (dpy_defaults) { + XrmCombineDatabase(XrmGetStringDatabase(dpy_defaults), pdb, False); + } else { + char filename[PATH_MAX]; + (void) GetRootDirName(filename, + PATH_MAX - strlen (slashDotXdefaults) - 1); + (void) strcat(filename, slashDotXdefaults); + (void)XrmCombineFileDatabase(filename, pdb, False); + } +} + +/*ARGSUSED*/ +static Bool StoreDBEntry( + XrmDatabase *db, + XrmBindingList bindings, + XrmQuarkList quarks, + XrmRepresentation *type, + XrmValuePtr value, + XPointer data) +{ + XrmQPutResource((XrmDatabase *)data, bindings, quarks, *type, value); + return False; +} + +static XrmDatabase CopyDB(XrmDatabase db) +{ + XrmDatabase copy = NULL; + XrmQuark empty = NULLQUARK; + + XrmEnumerateDatabase(db, &empty, &empty, XrmEnumAllLevels, + StoreDBEntry, (XPointer)©); + return copy; +} + +/*ARGSUSED*/ +static String _XtDefaultLanguageProc( + Display *dpy, /* unused */ + String xnl, + XtPointer closure) /* unused */ +{ + if (! setlocale(LC_ALL, xnl)) + XtWarning("locale not supported by C library, locale unchanged"); + + if (! XSupportsLocale()) { + XtWarning("locale not supported by Xlib, locale set to C"); + setlocale(LC_ALL, "C"); + } + if (! XSetLocaleModifiers("")) + XtWarning("X locale modifiers not supported, using default"); + + return setlocale(LC_ALL, NULL); /* re-query in case overwritten */ +} + +XtLanguageProc XtSetLanguageProc( + XtAppContext app, + XtLanguageProc proc, + XtPointer closure) +{ + XtLanguageProc old; + + if (!proc) { + proc = _XtDefaultLanguageProc; + closure = NULL; + } + + if (app) { + LOCK_APP(app); + LOCK_PROCESS; + /* set langProcRec only for this application context */ + old = app->langProcRec.proc; + app->langProcRec.proc = proc; + app->langProcRec.closure = closure; + UNLOCK_PROCESS; + UNLOCK_APP(app); + } else { + /* set langProcRec for all application contexts */ + ProcessContext process; + + LOCK_PROCESS; + process = _XtGetProcessContext(); + old = process->globalLangProcRec.proc; + process->globalLangProcRec.proc = proc; + process->globalLangProcRec.closure = closure; + app = process->appContextList; + while (app) { + app->langProcRec.proc = proc; + app->langProcRec.closure = closure; + app = app->next; + } + UNLOCK_PROCESS; + } + return (old ? old : _XtDefaultLanguageProc); +} + +XrmDatabase XtScreenDatabase( + Screen *screen) +{ + int scrno; + Bool doing_def; + XrmDatabase db, olddb; + XtPerDisplay pd; + Status do_fallback; + char *scr_resources; + Display *dpy = DisplayOfScreen(screen); + DPY_TO_APPCON(dpy); + + LOCK_APP(app); + LOCK_PROCESS; + if (screen == DefaultScreenOfDisplay(dpy)) { + scrno = DefaultScreen(dpy); + doing_def = True; + } else { + scrno = XScreenNumberOfScreen(screen); + doing_def = False; + } + pd = _XtGetPerDisplay(dpy); + if ((db = pd->per_screen_db[scrno])) { + UNLOCK_PROCESS; + UNLOCK_APP(app); + return (doing_def ? XrmGetDatabase(dpy) : db); + } + scr_resources = XScreenResourceString(screen); + + if (ScreenCount(dpy) == 1) { + db = pd->cmd_db; + pd->cmd_db = NULL; + } else { + db = CopyDB(pd->cmd_db); + } + { /* Environment defaults */ + char filenamebuf[PATH_MAX]; + char *filename; + + if (!(filename = getenv("XENVIRONMENT"))) { + int len; +#ifdef __MINGW32__ + char *slashDotXdefaultsDash = "/Xdefaults-"; +#else + char *slashDotXdefaultsDash = "/.Xdefaults-"; +#endif + + (void) GetRootDirName(filename = filenamebuf, + PATH_MAX - strlen (slashDotXdefaultsDash) - 1); + (void) strcat(filename, slashDotXdefaultsDash); + len = strlen(filename); + GetHostname (filename+len, PATH_MAX-len); + } + (void)XrmCombineFileDatabase(filename, &db, False); + } + if (scr_resources) + { /* Screen defaults */ + XrmCombineDatabase(XrmGetStringDatabase(scr_resources), &db, False); + XFree(scr_resources); + } + /* Server or host defaults */ + if (!pd->server_db) + CombineUserDefaults(dpy, &db); + else { + (void) XrmCombineDatabase(pd->server_db, &db, False); + pd->server_db = NULL; + } + + if (!db) + db = XrmGetStringDatabase(""); + pd->per_screen_db[scrno] = db; + olddb = XrmGetDatabase(dpy); + /* set database now, for XtResolvePathname to use */ + XrmSetDatabase(dpy, db); + CombineAppUserDefaults(dpy, &db); + do_fallback = 1; + { /* System app-defaults */ + char *filename; + + if ((filename = XtResolvePathname(dpy, "app-defaults", + NULL, NULL, NULL, NULL, 0, NULL))) { + do_fallback = !XrmCombineFileDatabase(filename, &db, False); + XtFree(filename); + } + } + /* now restore old database, if need be */ + if (!doing_def) + XrmSetDatabase(dpy, olddb); + if (do_fallback && pd->appContext->fallback_resources) + { /* Fallback defaults */ + XrmDatabase fdb = NULL; + String *res; + + for (res = pd->appContext->fallback_resources; *res; res++) + XrmPutLineResource(&fdb, *res); + (void)XrmCombineDatabase(fdb, &db, False); + } + UNLOCK_PROCESS; + UNLOCK_APP(app); + return db; +} + +/* + * Merge two option tables, allowing the second to over-ride the first, + * so that ambiguous abbreviations can be noticed. The merge attempts + * to make the resulting table lexicographically sorted, but succeeds + * only if the first source table is sorted. Though it _is_ recommended + * (for optimizations later in XrmParseCommand), it is not required + * that either source table be sorted. + * + * Caller is responsible for freeing the returned option table. + */ + +static void _MergeOptionTables( + const XrmOptionDescRec *src1, + Cardinal num_src1, + const XrmOptionDescRec *src2, + Cardinal num_src2, + XrmOptionDescRec **dst, + Cardinal *num_dst) +{ + XrmOptionDescRec *table, *endP; + register XrmOptionDescRec *opt1, *whereP, *dstP; + register const XrmOptionDescRec *opt2; + int i1; + Cardinal i2; + int dst_len, order; + Boolean found; + enum {Check, NotSorted, IsSorted} sort_order = Check; + + *dst = table = (XrmOptionDescRec*) + __XtMalloc( sizeof(XrmOptionDescRec) * (num_src1 + num_src2) ); + + (void) memmove(table, src1, sizeof(XrmOptionDescRec) * num_src1 ); + if (num_src2 == 0) { + *num_dst = num_src1; + return; + } + endP = &table[dst_len = num_src1]; + for (opt2 = src2, i2= 0; i2 < num_src2; opt2++, i2++) { + found = False; + whereP = endP-1; /* assume new option goes at the end */ + for (opt1 = table, i1 = 0; i1 < dst_len; opt1++, i1++) { + /* have to walk the entire new table so new list is ordered + (if src1 was ordered) */ + if (sort_order == Check && i1 > 0 + && strcmp(opt1->option, (opt1-1)->option) < 0) + sort_order = NotSorted; + if ((order = strcmp(opt1->option, opt2->option)) == 0) { + /* same option names; just overwrite opt1 with opt2 */ + *opt1 = *opt2; + found = True; + break; + } + /* else */ + if (sort_order == IsSorted && order > 0) { + /* insert before opt1 to preserve order */ + /* shift rest of table forward to make room for new entry */ + for (dstP = endP++; dstP > opt1; dstP--) + *dstP = *(dstP-1); + *opt1 = *opt2; + dst_len++; + found = True; + break; + } + /* else */ + if (order < 0) + /* opt2 sorts after opt1, so remember this position */ + whereP = opt1; + } + if (sort_order == Check && i1 == dst_len) + sort_order = IsSorted; + if (!found) { + /* when we get here, whereP points to the last entry in the + destination that sorts before "opt2". Shift rest of table + forward and insert "opt2" after whereP. */ + whereP++; + for (dstP = endP++; dstP > whereP; dstP--) + *dstP = *(dstP-1); + *whereP = *opt2; + dst_len++; + } + } + *num_dst = dst_len; +} + + +/* NOTE: name, class, and type must be permanent strings */ +static Boolean _GetResource( + Display *dpy, + XrmSearchList list, + String name, + String class, + String type, + XrmValue* value) +{ + XrmRepresentation db_type; + XrmValue db_value; + XrmName Qname = XrmPermStringToQuark(name); + XrmClass Qclass = XrmPermStringToQuark(class); + XrmRepresentation Qtype = XrmPermStringToQuark(type); + + if (XrmQGetSearchResource(list, Qname, Qclass, &db_type, &db_value)) { + if (db_type == Qtype) { + if (Qtype == _XtQString) + *(String*)value->addr = db_value.addr; + else + (void) memmove(value->addr, db_value.addr, value->size ); + return True; + } else { + WidgetRec widget; /* hack, hack */ + bzero( &widget, sizeof(widget) ); + widget.core.self = &widget; + widget.core.widget_class = coreWidgetClass; + widget.core.screen = (Screen*)DefaultScreenOfDisplay(dpy); + XtInitializeWidgetClass(coreWidgetClass); + if (_XtConvert(&widget,db_type,&db_value,Qtype,value,NULL)) { + return True; + } + } + } + return False; +} + +XrmDatabase _XtPreparseCommandLine( + XrmOptionDescRec *urlist, + Cardinal num_urs, + int argc, + String *argv, + /* return */ + String *applName, + String *displayName, + String *language) +{ + XrmDatabase db = NULL; + XrmOptionDescRec *options; + Cardinal num_options; + XrmName name_list[3]; + XrmName class_list[3]; + XrmRepresentation type; + XrmValue val; + String *targv; + int targc = argc; + + targv = (String *) __XtMalloc(sizeof(char *) * argc); + (void) memmove(targv, argv, sizeof(char *) * argc); + _MergeOptionTables(opTable, XtNumber(opTable), urlist, num_urs, + &options, &num_options); + name_list[0] = class_list[0] = XrmPermStringToQuark("."); + name_list[2] = class_list[2] = NULLQUARK; + XrmParseCommand(&db, options, num_options, ".", &targc, targv); + if (applName) { + name_list[1] = XrmPermStringToQuark("name"); + if (XrmQGetResource(db, name_list, name_list, &type, &val) && + type == _XtQString) + *applName = val.addr; + } + if (displayName) { + name_list[1] = XrmPermStringToQuark("display"); + if (XrmQGetResource(db, name_list, name_list, &type, &val) && + type == _XtQString) + *displayName = val.addr; + } + if (language) { + name_list[1] = XrmPermStringToQuark("xnlLanguage"); + class_list[1] = XrmPermStringToQuark("XnlLanguage"); + if (XrmQGetResource(db, name_list, class_list, &type, &val) && + type == _XtQString) + *language = val.addr; + } + + XtFree((char *)targv); + XtFree((char *)options); + return db; +} + + +static void GetLanguage( + Display *dpy, + XtPerDisplay pd) +{ + XrmRepresentation type; + XrmValue value; + XrmName name_list[3]; + XrmName class_list[3]; + + LOCK_PROCESS; + if (! pd->language) { + name_list[0] = pd->name; + name_list[1] = XrmPermStringToQuark("xnlLanguage"); + class_list[0] = pd->class; + class_list[1] = XrmPermStringToQuark("XnlLanguage"); + name_list[2] = class_list[2] = NULLQUARK; + if (!pd->server_db) + CombineUserDefaults(dpy, &pd->server_db); + if (pd->server_db && + XrmQGetResource(pd->server_db,name_list,class_list, &type, &value) + && type == _XtQString) + pd->language = (char *) value.addr; + } + + if (pd->appContext->langProcRec.proc) { + if (! pd->language) pd->language = ""; + pd->language = (*pd->appContext->langProcRec.proc) + (dpy, pd->language, pd->appContext->langProcRec.closure); + } + else if (! pd->language || pd->language[0] == '\0') /* R4 compatibility */ + pd->language = getenv("LANG"); + + if (pd->language) pd->language = XtNewString(pd->language); + UNLOCK_PROCESS; +} + +static void ProcessInternalConnection ( + XtPointer client_data, + int* fd, + XtInputId* id) +{ + XProcessInternalConnection ((Display *) client_data, *fd); +} + +static void ConnectionWatch ( + Display* dpy, + XPointer client_data, + int fd, + Bool opening, + XPointer* watch_data) +{ + XtInputId* iptr; + XtAppContext app = XtDisplayToApplicationContext(dpy); + + if (opening) { + iptr = (XtInputId *) __XtMalloc(sizeof(XtInputId)); + *iptr = XtAppAddInput(app, fd, (XtPointer) XtInputReadMask, + ProcessInternalConnection, client_data); + *watch_data = (XPointer) iptr; + } else { + iptr = (XtInputId *) *watch_data; + XtRemoveInput(*iptr); + (void) XtFree(*watch_data); + } +} + +void _XtDisplayInitialize( + Display *dpy, + XtPerDisplay pd, + _Xconst char* name, + XrmOptionDescRec *urlist, + Cardinal num_urs, + int *argc, + char **argv) +{ + Boolean tmp_bool; + XrmValue value; + XrmOptionDescRec *options; + Cardinal num_options; + XrmDatabase db; + XrmName name_list[2]; + XrmClass class_list[2]; + XrmHashTable* search_list; + int search_list_size = SEARCH_LIST_SIZE; + + GetLanguage(dpy, pd); + + /* Parse the command line and remove Xt arguments from argv */ + _MergeOptionTables( opTable, XtNumber(opTable), urlist, num_urs, + &options, &num_options ); + XrmParseCommand(&pd->cmd_db, options, num_options, name, argc, argv); + + db = XtScreenDatabase(DefaultScreenOfDisplay(dpy)); + + if (!(search_list = (XrmHashTable*) + ALLOCATE_LOCAL( SEARCH_LIST_SIZE*sizeof(XrmHashTable)))) + _XtAllocError(NULL); + name_list[0] = pd->name; + class_list[0] = pd->class; + name_list[1] = NULLQUARK; + class_list[1] = NULLQUARK; + + while (!XrmQGetSearchList(db, name_list, class_list, + search_list, search_list_size)) { + XrmHashTable* old = search_list; + Cardinal size = (search_list_size*=2)*sizeof(XrmHashTable); + if (!(search_list = (XrmHashTable*)ALLOCATE_LOCAL(size))) + _XtAllocError(NULL); + (void) memmove((char*)search_list, (char*)old, (size>>1) ); + DEALLOCATE_LOCAL(old); + } + + value.size = sizeof(tmp_bool); + value.addr = (XtPointer)&tmp_bool; + if (_GetResource(dpy, search_list, "synchronous", "Synchronous", + XtRBoolean, &value)) { + int i; + Display **dpyP = pd->appContext->list; + pd->appContext->sync = tmp_bool; + for (i = pd->appContext->count; i; dpyP++, i--) { + (void) XSynchronize(*dpyP, (Bool)tmp_bool); + } + } else { + (void) XSynchronize(dpy, (Bool)pd->appContext->sync); + } + + if (_GetResource(dpy, search_list, "reverseVideo", "ReverseVideo", + XtRBoolean, &value) + && tmp_bool) { + pd->rv = True; + } + + value.size = sizeof(pd->multi_click_time); + value.addr = (XtPointer)&pd->multi_click_time; + if (!_GetResource(dpy, search_list, + "multiClickTime", "MultiClickTime", + XtRInt, &value)) { + pd->multi_click_time = 200; + } + + value.size = sizeof(pd->appContext->selectionTimeout); + value.addr = (XtPointer)&pd->appContext->selectionTimeout; + (void)_GetResource(dpy, search_list, + "selectionTimeout", "SelectionTimeout", + XtRInt, &value); + +#ifndef NO_IDENTIFY_WINDOWS + value.size = sizeof(pd->appContext->identify_windows); + value.addr = (XtPointer)&pd->appContext->identify_windows; + (void)_GetResource(dpy, search_list, + "xtIdentifyWindows", "XtDebug", + XtRBoolean, &value); +#endif + + XAddConnectionWatch(dpy, ConnectionWatch, (XPointer) dpy); + + XtFree( (XtPointer)options ); + DEALLOCATE_LOCAL( search_list ); +} + +/* Function Name: XtAppSetFallbackResources + * Description: Sets the fallback resource list that will be loaded + * at display initialization time. + * Arguments: app_context - the app context. + * specification_list - the resource specification list. + * Returns: none. + */ + +void +XtAppSetFallbackResources( + XtAppContext app_context, + String *specification_list) +{ + LOCK_APP(app_context); + app_context->fallback_resources = specification_list; + UNLOCK_APP(app_context); +} + + +Widget XtOpenApplication(XtAppContext *app_context_return, + _Xconst char *application_class, + XrmOptionDescRec *options, Cardinal num_options, + int *argc_in_out, String *argv_in_out, + String *fallback_resources, WidgetClass widget_class, + ArgList args_in, Cardinal num_args_in) +{ + XtAppContext app_con; + Display * dpy; + register int saved_argc = *argc_in_out; + Widget root; + Arg args[3], *merged_args; + Cardinal num = 0; + + XtToolkitInitialize(); /* cannot be moved into _XtAppInit */ + + dpy = _XtAppInit(&app_con, (String)application_class, options, num_options, + argc_in_out, &argv_in_out, fallback_resources); + + LOCK_APP(app_con); + XtSetArg(args[num], XtNscreen, DefaultScreenOfDisplay(dpy)); num++; + XtSetArg(args[num], XtNargc, saved_argc); num++; + XtSetArg(args[num], XtNargv, argv_in_out); num++; + + merged_args = XtMergeArgLists(args_in, num_args_in, args, num); + num += num_args_in; + + root = XtAppCreateShell(NULL, application_class, widget_class, dpy, + merged_args, num); + + if (app_context_return) + *app_context_return = app_con; + + XtFree((XtPointer)merged_args); + XtFree((XtPointer)argv_in_out); + UNLOCK_APP(app_con); + return root; +} + + +Widget +XtAppInitialize( + XtAppContext * app_context_return, + _Xconst char* application_class, + XrmOptionDescRec *options, + Cardinal num_options, + int *argc_in_out, + String *argv_in_out, + String *fallback_resources, + ArgList args_in, + Cardinal num_args_in) +{ + return XtOpenApplication(app_context_return, application_class, + options, num_options, + argc_in_out, argv_in_out, fallback_resources, + applicationShellWidgetClass, + args_in, num_args_in); +} + + +/*ARGSUSED*/ +Widget +XtInitialize( + _Xconst char* name, + _Xconst char* classname, + XrmOptionDescRec *options, + Cardinal num_options, + int *argc, + String *argv) +{ + Widget root; + XtAppContext app_con; + register ProcessContext process = _XtGetProcessContext(); + + root = XtAppInitialize(&app_con, classname, options, num_options, + argc, argv, NULL, NULL, (Cardinal) 0); + + LOCK_PROCESS; + process->defaultAppContext = app_con; + UNLOCK_PROCESS; + return root; +} |