2
0

main.c 35 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332
  1. /*
  2. * CDE - Common Desktop Environment
  3. *
  4. * Copyright (c) 1993-2012, The Open Group. All rights reserved.
  5. *
  6. * These libraries and programs are free software; you can
  7. * redistribute them and/or modify them under the terms of the GNU
  8. * Lesser General Public License as published by the Free Software
  9. * Foundation; either version 2 of the License, or (at your option)
  10. * any later version.
  11. *
  12. * These libraries and programs are distributed in the hope that
  13. * they will be useful, but WITHOUT ANY WARRANTY; without even the
  14. * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
  15. * PURPOSE. See the GNU Lesser General Public License for more
  16. * details.
  17. *
  18. * You should have received a copy of the GNU Lesser General Public
  19. * License along with these libraries and programs; if not, write
  20. * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
  21. * Floor, Boston, MA 02110-1301 USA
  22. */
  23. /* $XConsortium: main.c /main/10 1996/10/28 12:41:03 cde-hp $ */
  24. /*
  25. * (c) Copyright 1996 Digital Equipment Corporation.
  26. * (c) Copyright 1996 Hewlett-Packard Company.
  27. * (c) Copyright 1996 International Business Machines Corp.
  28. * (c) Copyright 1996 Sun Microsystems, Inc.
  29. * (c) Copyright 1996 Novell, Inc.
  30. * (c) Copyright 1996 FUJITSU LIMITED.
  31. * (c) Copyright 1996 Hitachi.
  32. */
  33. char *ProgramRevision = "dtimsstart $Revision: /main/10 $";
  34. #define _EXTERN_DEFINE_
  35. #include "xims.h"
  36. #undef _EXTERN_DEFINE_
  37. #include <signal.h>
  38. #include <locale.h>
  39. #include <Dt/MsgCatP.h>
  40. #define NL_SETN 1 /* set number */
  41. static nl_catd catd = (nl_catd) -1;
  42. extern char *find_system_locale_name(char *);
  43. /* local functions */
  44. static int IsNoError(/* error */);
  45. static int EnvNeeded(/* error */);
  46. static int ErrMsgDisabled(/* error */);
  47. static int ximsShowImsList(/* */);
  48. static int ximsShowCurrentIms(/* */);
  49. static int prepare_remote(/* win_st */);
  50. static int ximsRemoteConf(/* */);
  51. static int ximsSetMode(/* */);
  52. static void show_select_mode(/* mode */);
  53. static int set_locale_env(/* locale */);
  54. static void init_command(/* progname */);
  55. static bool optname_match(/* name, str, minlen */);
  56. static int parse_options(/* argc, argv */);
  57. static void usage(/* force */);
  58. static int exitSignalNumber = 0;
  59. static bool do_usage = False;
  60. int main (int argc, char **argv)
  61. {
  62. int ret = NoError;
  63. int ret2;
  64. init_command(argv[0]);
  65. ret = parse_options(argc, argv);
  66. ret2 = set_locale_env(Opt.LocaleName); /* set LANG, LC_ALL, msg cat */
  67. /* get_user_environ() does check ErrNoLocale */
  68. if (do_usage) { /* '-help' option */
  69. usage(True);
  70. Exit(NoError);
  71. }
  72. if (ret != NoError)
  73. Exit(ret);
  74. if (OpMode == MODE_START && getenv(ENV_NO_DTIMSSTART))
  75. Exit(ErrDisabled);
  76. if ((ret = set_cmd_env()) != NoError) {
  77. /* get_user_environ()) & read_cmd_conf()) */
  78. Exit(ret);
  79. }
  80. #ifdef DEBUG
  81. if (DebugLvl > 2) { pr_CmdConf(); }
  82. if (DebugLvl > 1) { pr_CmdOpt(), pr_OpModeFlag(); pr_UserEnv(); }
  83. #endif
  84. /* set signal handler */
  85. if (signal(SIGINT, SIG_IGN) != SIG_IGN) signal(SIGINT, sigExit);
  86. signal(SIGTERM, sigExit);
  87. signal(SIGHUP, sigExit);
  88. signal(SIGQUIT, sigExit);
  89. /* create $HOME/.xims if needed */
  90. if (OpMode == MODE_START
  91. || (OpMode == MODE_MODE && Opt.SelectMode != SEL_MODE_QUERY)) {
  92. if ((ret = create_xims_dir()) != NoError) {
  93. OpErrCode = ret;
  94. OpState = State_Init_Err;
  95. ximsMain(); /* abort with error msg */
  96. }
  97. }
  98. OpState = State_Init_Done;
  99. switch (OpMode) {
  100. case MODE_LISTNAME:
  101. case MODE_LIST: ret = ximsShowImsList(); break;
  102. case MODE_CURRENT: ret = ximsShowCurrentIms(); break;
  103. case MODE_MODE: ret = ximsSetMode(); break;
  104. case MODE_REMCONF: ret = ximsRemoteConf(); break;
  105. case MODE_START:
  106. #ifndef DEBUG2
  107. # if defined(CSRG_BASED)
  108. setsid();
  109. # else
  110. setpgrp();
  111. # endif
  112. #endif
  113. ximsMain(); /* never returns */
  114. }
  115. Exit(ret);
  116. }
  117. void sigExit(int sig)
  118. {
  119. DPR(("sigExit: %s (%d)\n", sig_name(sig), sig));
  120. signal(sig, SIG_IGN);
  121. exitSignalNumber = sig;
  122. Exit(ErrSignaled);
  123. }
  124. void Exit(int err_code)
  125. {
  126. int exit_code = IsNoError(err_code) ? 0 : 1;
  127. DPR(("Exit(%s[%d]): exit(%d)\n",
  128. error_name(err_code), err_code, exit_code));
  129. if (Verbose > 0 && err_code != LastErrMsg) {
  130. if (exit_code != 0 && !ErrMsgDisabled(err_code)) {
  131. UseMsgWindow = False; /* disable msg window */
  132. put_xims_errmsg(err_code, 0, 0, 0);
  133. }
  134. }
  135. if (OpFlag & FLAG_NOTIFY)
  136. NotifyErrCode(exit_code == 0 ? NoError : err_code);
  137. /*
  138. * if the reason we're exiting is because of a syntax
  139. * error, set the exit code to 2.
  140. */
  141. if (ErrSyntax == err_code)
  142. exit_code = 2;
  143. exit(exit_code);
  144. }
  145. int NotifyErrCode(int err_code)
  146. {
  147. char buf[BUFSIZ], *bp, val[20];
  148. static bool notify_done = False;
  149. if (/* !(OpFlag & FLAG_NOTIFY) || */ notify_done)
  150. return False;
  151. notify_done = True;
  152. buf[0] = 0; bp = buf;
  153. bp = strcpyx(bp, STR_ERRORCODE);
  154. *bp++ = '=';
  155. sprintf(val, "%ld", (long)err_code);
  156. bp = strcpyx(bp, val);
  157. *bp++ = '\n'; *bp = 0;
  158. if (ErrFilePathNeeded(err_code)) {
  159. bp = strcpyx(bp, STR_ERRORPATH);
  160. *bp++ = '=';
  161. if (err_code == ErrImsAborted)
  162. bp = strcpyx(bp, Opt.LogPath);
  163. else
  164. bp = strcpyx(bp, errFilePath);
  165. *bp++ = '\n'; *bp = 0;
  166. }
  167. if (OpMode == MODE_REMCONF) {
  168. send_dtims_msg(WIN_ST_REMOTE_CONF, err_code);
  169. } else if (OpMode == MODE_START && (OpFlag & FLAG_REMOTERUN)) {
  170. send_dtims_msg(WIN_ST_REMOTE_RUN, err_code);
  171. } else {
  172. fflush(stdout); fflush(stderr);
  173. (void) fwrite((void *)buf, (size_t)(bp - buf), (size_t)1, stdout);
  174. fflush(stdout);
  175. }
  176. return True;
  177. }
  178. static int IsNoError(ximsError error)
  179. {
  180. switch (error) {
  181. case NoError: case ErrIsNone: case ErrNotRun:
  182. case ErrImsWaiting: case ErrImsWaitDone:
  183. case ErrImsConnecting: case ErrImsConnectDone:
  184. case ErrNoImsEntry: case ErrNoLocaleConf:
  185. case ErrNoSelectionFile: case ErrNoSelection: case ErrSaveSelection:
  186. case ErrDisabled:
  187. return True;
  188. }
  189. return False;
  190. }
  191. static int EnvNeeded(ximsError error)
  192. {
  193. switch (error) {
  194. case NoError: case ErrIsNone: case ErrNotRun:
  195. case ErrImsWaiting: case ErrImsWaitDone:
  196. case ErrImsRunning: case ErrImsTimeout:
  197. /* case ErrImsExecution: case ErrImsAborted: */
  198. case ErrOpenResource: /* case ErrSignaled: */
  199. return True;
  200. }
  201. return False;
  202. }
  203. static int ErrMsgDisabled(ximsError error)
  204. {
  205. switch (error) {
  206. case NoError: case ErrIsNone: case ErrNotRun:
  207. case ErrImsWaiting: case ErrImsWaitDone:
  208. case ErrImsConnecting: case ErrImsConnectDone:
  209. return True;
  210. case ErrSignaled:
  211. return (Verbose <= 2);
  212. case ErrInvState: case ErrInternal:
  213. return (Verbose <= 3);
  214. }
  215. return False;
  216. }
  217. int ErrFilePathNeeded(ximsError error)
  218. {
  219. switch (error) {
  220. case ErrFileOpen: case ErrFileCreate: case ErrDirCreate:
  221. case ErrMissEntry: case ErrNoExecutable: case ErrImsAborted:
  222. case ErrOpenResource:
  223. return True;
  224. }
  225. return False;
  226. }
  227. int InWaitingState(void)
  228. {
  229. switch (OpState) {
  230. case State_Init_Err:
  231. case State_Finish_Defered:
  232. case State_Mode_Done:
  233. return True;
  234. }
  235. return False;
  236. }
  237. void ximsMain(void)
  238. {
  239. static int call_cnt = 0;
  240. call_cnt++;
  241. DPR(("\nximsMain(call_cnt=%d): OpState=%s OpErrCode=%s[%d]\n",
  242. call_cnt, StateName(), error_name(OpErrCode), OpErrCode));
  243. #ifdef DEBUG
  244. pr_brk("ximsMain");
  245. #endif
  246. if (OpFlag & FLAG_REMOTERUN) {
  247. int ret;
  248. if ((ret = prepare_remote(WIN_ST_REMOTE_RUN)) != NoError) {
  249. Exit(ret);
  250. }
  251. }
  252. switch (OpState) {
  253. case State_Init_Done: if (Verbose > 1)
  254. put_xims_log("Started.", 0, 0, 0);
  255. ximsSelect();
  256. case State_Select_Done:
  257. case State_Select_Canceled: ximsStart();
  258. case State_Start_Done: ximsWait();
  259. case State_Init_Err:
  260. case State_Select_Err:
  261. case State_Start_Err:
  262. case State_Wait_Err:
  263. if (!WaitingDialogReply && !IsNoError(OpErrCode)) {
  264. LastErrMsg = OpErrCode;
  265. put_xims_errmsg(OpErrCode, 0, 0, 0);
  266. }
  267. case State_Wait_Done:
  268. ximsFinish();
  269. case State_Finish:
  270. if (WaitingDialogReply) {
  271. DPR(("ximsMain(): enter xevent_loop()\n"));
  272. xevent_loop(); /* never returns */
  273. WaitingDialogReply = False; /* if failed */
  274. }
  275. case State_Finish_Defered:
  276. if (OpState == State_Finish_Defered) {
  277. WaitingDialogReply = False;
  278. ximsFinish();
  279. }
  280. case State_Finish_Done: break;
  281. case State_Finish_Err: break;
  282. case State_Mode_Done:
  283. case State_Mode_Canceled: break;
  284. default:
  285. OpErrCode = ErrInvState; break;
  286. }
  287. Exit(OpErrCode);
  288. }
  289. void ximsFinish(void)
  290. {
  291. OpStateVal oldOpState = OpState;
  292. DPR(("ximsFinish(): OpState=%s OpErrCode=%s[%d]\n",
  293. StateName(), error_name(OpErrCode), OpErrCode));
  294. OpState = State_Finish;
  295. if (oldOpState != State_Finish_Defered) {
  296. if (!(OpFlag & FLAG_NORESOURCE) && isXsession())
  297. restore_resources();
  298. if (WaitingDialogReply) {
  299. DPR2(("ximsFinish(): OpState => State_Finish_Defered\n"));;
  300. OpState = State_Finish_Defered;
  301. return;
  302. }
  303. }
  304. if (OpMode == MODE_START && (OpFlag & FLAG_ENV)) {
  305. if (userSel.name && EnvNeeded(OpErrCode)) {
  306. OutEnv outEnv;
  307. CLR(&outEnv, OutEnv);
  308. if (make_new_environ(&outEnv, &userSel) == NoError) {
  309. put_new_environ(&outEnv);
  310. clear_OutEnv(&outEnv);
  311. }
  312. } else {
  313. DPR(("ximsFinish(): Not put env (pri->status=%s[%d])\n",
  314. error_name(userSel.renv->status), userSel.renv->status));
  315. }
  316. }
  317. /* if (IsNoError(OpErrCode)) OpErrCode = NoError; */
  318. OpState = State_Finish_Done;
  319. return;
  320. }
  321. static int ximsShowImsList(void)
  322. {
  323. int ret = NoError;
  324. int i;
  325. int host_type = HOST_LOCAL;
  326. char *hostname;
  327. ImsList *list = (ImsList *) 0;
  328. DPR(("ximsShowImsList()\n"));
  329. hostname = Opt.HostName;
  330. if (hostname) {
  331. host_type = check_hostname(hostname);
  332. userSel.hostname = NEWSTR(hostname); /* for error msg */
  333. }
  334. switch (host_type) {
  335. case HOST_UNKNOWN:
  336. ret = ErrUnknownHost;
  337. break;
  338. case HOST_REMOTE:
  339. ret = get_remote_conf(&list, hostname, NULL, NULL);
  340. break;
  341. case HOST_LOCAL:
  342. ret = get_ims_list(&list, NULL, True);
  343. break;
  344. }
  345. if (ret != NoError) {
  346. DPR2(("ximsShowImsList: ret=%s[%d]\n", error_name(ret), ret));
  347. /* return ret; */
  348. } else if (Verbose < 1) {
  349. for (i = 0; i < list->num_ent; i++)
  350. puts(list->elist[i]->name);
  351. } else {
  352. int err, len;
  353. for (i = 0; i < list->num_ent; i++) {
  354. /* If invoked from dtstyle with -listname put the "#" if this is
  355. the default one. */
  356. if (Opt.Listname == 1)
  357. if (i == list->default_idx)
  358. putchar('#');
  359. err = list->elist[i]->status;
  360. if (err) putchar('(');
  361. fputs(list->elist[i]->name, stdout);
  362. if (err) putchar(')');
  363. /* If invoked from dtstyle with -listname put the label */
  364. if (Opt.Listname == 1) {
  365. putchar(' ');
  366. fputs(list->elist[i]->label, stdout);
  367. }
  368. if (Verbose > 1) {
  369. char *msg = "cannot execute";
  370. switch (err) {
  371. case NoError:
  372. msg = "ok"; break;
  373. case ErrNoExecutable:
  374. msg = "no executable file"; break;
  375. case ErrNoImsConf:
  376. msg = "no configuration file"; break;
  377. case ErrMissEntry:
  378. msg = "invalid configuration file"; break;
  379. }
  380. len = strlen(list->elist[i]->name) + (err ? 2 : 0);
  381. for ( ; len < 16; len++) putchar(' ');
  382. putchar(' '); putchar('['); fputs(msg, stdout); putchar(']');
  383. }
  384. putchar('\n');
  385. }
  386. }
  387. fflush(stdout);
  388. if (list) {
  389. clear_ImsList(list); FREE(list);
  390. }
  391. return NoError;
  392. }
  393. static int ximsShowCurrentIms(void)
  394. {
  395. int ret = NoError;
  396. FileSel *fsel;
  397. DPR(("ximsShowCurrentIms()\n"));
  398. if (read_user_selection(&fsel, NULL) != NoError) {
  399. DPR2(("No selection file.\n"));
  400. return ErrNoSelectionFile;
  401. }
  402. if (fsel->name) {
  403. if (fsel->hostname)
  404. printf("%s\t[on %s]\n", fsel->name, fsel->hostname);
  405. else
  406. puts(fsel->name);
  407. fflush(stdout);
  408. } else {
  409. DPR2(("No IMS selected.\n"));
  410. ret = ErrNoSelection;
  411. }
  412. clear_FileSel(fsel); FREE(fsel);
  413. return ret;
  414. }
  415. static int prepare_remote(int win_st)
  416. {
  417. int ret;
  418. char **av = NULL;
  419. int ac = 0;
  420. int cur_st;
  421. DPR(("prepare_remote()\n"));
  422. #ifndef DEBUG
  423. Verbose = DebugLvl = 0; /* disable error messages */
  424. #endif
  425. UseMsgWindow = False;
  426. if ((ret = init_window_env()) != NoError)
  427. return ret;
  428. if (winEnv.atom_owner == None)
  429. return ErrRemoteData;
  430. cur_st = get_window_status();
  431. if (cur_st != win_st) {
  432. DPR(("prepare_remote(): invalid status '%d', should be '%d'\n",
  433. cur_st, win_st));
  434. return ErrRemoteData;
  435. }
  436. ret = get_window_data(&ac, &av); /* additional options */
  437. if (ret != NoError) {
  438. DPR(("prepare_remote(): get_window_data (%s[%d])\n",
  439. error_name(ret), ret));
  440. }
  441. if (ret == NoError) {
  442. ret = parse_options(ac, av);
  443. if (ret != NoError) {
  444. DPR(("secondary parse_options(): failed (%s[%d])\n",
  445. error_name(ret), ret));
  446. }
  447. }
  448. return NoError;
  449. }
  450. static int ximsRemoteConf(void)
  451. {
  452. int ret;
  453. char *locale;
  454. DPR(("ximsRemoteConf()\n"));
  455. if ((ret = prepare_remote(WIN_ST_REMOTE_CONF)) != NoError)
  456. return ret;
  457. locale = userEnv.real_locale ? userEnv.real_locale : userEnv.locale;
  458. ret = put_remote_conf(locale, Opt.ImsName);
  459. return ret;
  460. }
  461. static int ximsSetMode(void)
  462. {
  463. int ret = NoError;
  464. int cur_mode = SEL_MODE_NONE;
  465. ImsList imsList;
  466. DPR(("ximsSetMode(op=%d)\n", Opt.SelectMode));
  467. OpState = State_Mode;
  468. if ((ret = read_localeconf(&imsList, NULL)) != NoError) {
  469. DPR(("ximsSetMode(%s) locale '%s' isn't supported\n", userEnv.locale));
  470. /* return ErrNoLocaleConf; */
  471. }
  472. cur_mode = get_select_mode();
  473. if (cur_mode != SEL_MODE_AUTO && cur_mode != SEL_MODE_NOAUTO)
  474. cur_mode = imsList.def_selmode;
  475. switch (Opt.SelectMode) {
  476. case SEL_MODE_NONE:
  477. case SEL_MODE_QUERY: show_select_mode(cur_mode);
  478. break;
  479. case SEL_MODE_WIN: start_mode_window(cur_mode);
  480. /* never returned */
  481. break;
  482. #ifdef SelectMode_ONCE
  483. case SEL_MODE_ONCE:
  484. #endif /* SelectMode_ONCE */
  485. case SEL_MODE_AUTO:
  486. case SEL_MODE_NOAUTO: ret = set_select_mode(cur_mode, Opt.SelectMode);
  487. break;
  488. }
  489. OpErrCode = ret;
  490. OpState = State_Mode_Done;
  491. return ret;
  492. }
  493. static void show_select_mode(int mode)
  494. {
  495. char *valp;
  496. printf("%s: \t", (CATGETS(catd,NL_SETN,20, "SelectMode")));
  497. switch (mode) {
  498. default:
  499. #ifdef DEBUG
  500. case SEL_MODE_NONE: valp = "<NOT DEFINED>"; /* break; */
  501. #endif
  502. case SEL_MODE_NOAUTO:
  503. valp = (CATGETS(catd,NL_SETN,21, "ask_at_login"));
  504. break;
  505. case SEL_MODE_AUTO:
  506. valp = (CATGETS(catd,NL_SETN,22, "resume_current_input_method"));
  507. break;
  508. #ifdef SelectMode_ONCE
  509. case SEL_MODE_ONCE:
  510. valp = "auto-selection if once selected";
  511. break;
  512. #endif /* SelectMode_ONCE */
  513. }
  514. puts(valp); fflush(stdout);
  515. return;
  516. }
  517. static int set_locale_env(char *locale)
  518. {
  519. char *env_name, *env_value, *bp, *vp, buf[BUFSIZ], buf2[BUFSIZ];
  520. static char *last_lang_env[2] = { NULL, NULL };
  521. buf[0] = buf2[0] = 0;
  522. env_name = "LANG";
  523. env_value = getenv(env_name);
  524. if (env_value)
  525. snprintf(buf, sizeof(buf), "%s", env_value);
  526. if (locale && *locale) {
  527. if (!*buf || strcmp(locale, buf)) {
  528. bp = strcpyx(buf, env_name); *bp++ = '=';
  529. strcpyx(bp, locale);
  530. putenv(bp = NEWSTR(buf));
  531. FREE(last_lang_env[0]);
  532. last_lang_env[0] = bp;
  533. }
  534. } else if (*buf)
  535. locale = buf;
  536. else
  537. return ErrNoLocale;
  538. env_name = "LC_ALL";
  539. env_value = getenv(env_name);
  540. if (env_value)
  541. snprintf(buf2, sizeof(buf2), "%s", env_value);
  542. if (!*buf2 || strcmp(locale, buf2)) {
  543. bp = strcpyx(buf2, env_name); *bp++ = '=';
  544. strcpyx(bp, locale);
  545. putenv(bp = NEWSTR(buf2));
  546. FREE(last_lang_env[1]);
  547. last_lang_env[1] = bp;
  548. }
  549. setlocale(LC_ALL, locale);
  550. /* set XFILESEARCHPATH */
  551. vp = getenv(ENV_XFILESEARCHPATH);
  552. bp = strcpyx(buf, ENV_XFILESEARCHPATH);
  553. bp = strcpyx(bp, "=");
  554. if (vp) {
  555. bp = strcpyx(bp, vp);
  556. bp = strcpyx(bp, ":");
  557. }
  558. bp = strcpyx(bp, ENV_XFILESEARCHPATH_STRING);
  559. if(*buf) {
  560. putenv(XtNewString(buf));
  561. }
  562. /* set NLSPATH */
  563. vp = getenv(ENV_NLSPATH);
  564. bp = strcpyx(buf, ENV_NLSPATH);
  565. bp = strcpyx(bp, "=");
  566. if (vp) {
  567. bp = strcpyx(bp, vp);
  568. bp = strcpyx(bp, ":");
  569. }
  570. bp = strcpyx(bp, ENV_NLSPATH_STRING);
  571. /* BUG should this be putenv(bp) ? */
  572. if(*buf) {
  573. putenv(XtNewString(buf));
  574. }
  575. (void)CATCLOSE(catd);
  576. if (Verbose > 0) {
  577. catd = CATOPEN(DTIMS_PROGNAME, 0);
  578. }
  579. return NoError;
  580. }
  581. static void init_command(char *progname)
  582. {
  583. /* globals */
  584. ProgramName = progname;
  585. if (progname = strrchr(progname, '/'))
  586. ProgramName = progname + 1;
  587. #ifdef unused
  588. if (strstr(ProgramName, "mode")) ProgramType = MODE_MODE;
  589. else if (strstr(ProgramName, "list")) ProgramType = MODE_LIST;
  590. else if (strstr(ProgramName, "current")) ProgramType = MODE_CURRENT;
  591. else if (strstr(ProgramName, "conf")) ProgramType = MODE_REMCONF;
  592. else
  593. #endif
  594. ProgramType = MODE_START;
  595. OpState = State_None;
  596. OpMode = ProgramType;
  597. OpFlag = FLAG_DEFAULT;
  598. OpErrCode = NoError;
  599. LogFp = stderr;
  600. Wargc = 0;
  601. Wargv = NULL;
  602. WaitingDialogReply = False;
  603. WaitingActionDone = False;
  604. UseMsgWindow = True;
  605. IsRemote = False;
  606. LastErrMsg = NoError;
  607. Verbose = 1;
  608. DebugLvl = 0;
  609. ximsErrArgs[0] = ximsErrArgs[1] = ximsErrArgs[2] = (void *) 0;
  610. errFilePath[0] = 0;
  611. errFuncName = NULL;
  612. CLR(&Conf, CmdConf);
  613. CLR(&Opt, CmdOpt);
  614. CLR(&winEnv, WinEnv);
  615. CLR(&userEnv, UserEnv);
  616. CLR(&userSel, UserSelection);
  617. localList = (ImsList *) 0;
  618. return;
  619. }
  620. static bool optname_match(char *name, char *str, int minlen)
  621. {
  622. int nlen, slen;
  623. if (strcmp(name, str) == 0) return True;
  624. nlen = strlen(name);
  625. slen = strlen(str);
  626. if (slen >= nlen || slen < minlen) return False;
  627. if (strncmp(name, str, slen) == 0) return True;
  628. return False;
  629. }
  630. static int parse_options(int argc, char **argv)
  631. {
  632. char *opt;
  633. int i, n;
  634. int wac = 1;
  635. char *wav[80];
  636. int orgMode = MODE_START;
  637. static bool first_time = True;
  638. #define SET_FLAG(f) OpFlag |= (f)
  639. #define CLR_FLAG(f) OpFlag &= ~(f)
  640. #define CHK_FLAG(f) (OpFlag & (f))
  641. if (first_time) {
  642. argc--; argv++;
  643. /* preset */
  644. Opt.Listname = 0;
  645. orgMode = OpMode;
  646. if (orgMode == MODE_START) SET_FLAG(FLAG_WINDOW);
  647. Opt.SelectMode = SEL_MODE_NONE;
  648. }
  649. for (i = 0; i < argc; i++) {
  650. opt = argv[i];
  651. if (*opt++ != '-') goto _inv_opt;
  652. /* option for MODE */
  653. if (optname_match("mode", opt, 2)) {
  654. if (orgMode != MODE_START && orgMode != MODE_MODE)
  655. goto _inv_opt;
  656. OpMode = MODE_MODE;
  657. #if 0 /* not implemented yet */
  658. } else if (optname_match("style", opt, 3)) {
  659. if (orgMode != MODE_START && orgMode != MODE_MODE)
  660. goto _inv_opt;
  661. OpMode = MODE_STYLE;
  662. #endif
  663. } else if (optname_match("listname", opt, 5)) {
  664. if (orgMode != MODE_START && orgMode != MODE_LISTNAME)
  665. goto _inv_opt;
  666. OpMode = MODE_LISTNAME;
  667. Opt.Listname = 1;
  668. } else if (optname_match("list", opt, 2)) {
  669. if (orgMode != MODE_START && orgMode != MODE_LIST)
  670. goto _inv_opt;
  671. OpMode = MODE_LIST;
  672. } else if (optname_match("current", opt, 2)) {
  673. if (orgMode != MODE_START && orgMode != MODE_CURRENT)
  674. goto _inv_opt;
  675. OpMode = MODE_CURRENT;
  676. } else if (optname_match("remoteconf", opt, 7)) {
  677. if (orgMode != MODE_START && orgMode != MODE_REMCONF)
  678. goto _inv_opt;
  679. OpMode = MODE_REMCONF;
  680. SET_FLAG(FLAG_NOTIFY);
  681. /* option for FLAG */
  682. } else if (optname_match("nosave", opt, 4)) {
  683. SET_FLAG(FLAG_NOSAVE);
  684. } else if (optname_match("nostart", opt, 4)) {
  685. SET_FLAG(FLAG_NOSTART);
  686. } else if (optname_match("noenv", opt, 4)) {
  687. CLR_FLAG(FLAG_ENV);
  688. } else if (optname_match("envonly", opt, 4)) {
  689. SET_FLAG(FLAG_NOSTART|FLAG_ENV);
  690. } else if (optname_match("env", opt, 2)) {
  691. SET_FLAG(FLAG_ENV);
  692. } else if (optname_match("nowait", opt, 4)) {
  693. SET_FLAG(FLAG_NOWAIT);
  694. } else if (optname_match("notimeout", opt, 5)) {
  695. SET_FLAG(FLAG_NOTIMEOUT);
  696. } else if (optname_match("noresource", opt, 5)) {
  697. SET_FLAG(FLAG_NORESOURCE);
  698. } else if (optname_match("noremote", opt, 5)) {
  699. SET_FLAG(FLAG_NOREMOTE);
  700. } else if (optname_match("notify", opt, 5)) {
  701. SET_FLAG(FLAG_NOTIFY);
  702. } else if (optname_match("connect", opt, 4)) {
  703. SET_FLAG(FLAG_CONNECT);
  704. } else if (optname_match("dt", opt, 2)) {
  705. SET_FLAG(FLAG_DT);
  706. } else if (optname_match("window", opt, 2)) {
  707. SET_FLAG(FLAG_WINDOW);
  708. } else if (optname_match("nowindow", opt, 4)) {
  709. CLR_FLAG(FLAG_WINDOW);
  710. } else if (optname_match("remoterun", opt, 7)) {
  711. SET_FLAG(FLAG_REMOTERUN);
  712. SET_FLAG(FLAG_NOTIFY);
  713. } else if (optname_match("auto", opt, 2)) {
  714. Opt.SelectMode = SEL_MODE_AUTO;
  715. } else if (optname_match("noauto", opt, 3)) {
  716. Opt.SelectMode = SEL_MODE_NOAUTO;
  717. #ifdef SelectMode_ONCE
  718. } else if (optname_match("once", opt, 3)) {
  719. Opt.SelectMode = SEL_MODE_ONCE;
  720. #endif /* SelectMode_ONCE */
  721. /* help, verbose & debug options */
  722. } else if (optname_match("help", opt, 1)) {
  723. if (first_time)
  724. do_usage = True;
  725. } else if (optname_match("quiet", opt, 1)) {
  726. Verbose = DebugLvl = 0;
  727. } else if (optname_match("verbose", opt, 1)) {
  728. Verbose++;
  729. } else if (optname_match("debug", opt, 2)) {
  730. Verbose++; DebugLvl++;
  731. } else if (i >= argc - 1 || !*(argv[i+1])) {
  732. goto _inv_opt; /* the rest options need an argument */
  733. /* options with an argument */
  734. } else if (optname_match("imsoption", opt, 4)) {
  735. i++;
  736. Opt.ImsOption = argv[i];
  737. } else if (optname_match("ims", opt, 2)) {
  738. i++;
  739. Opt.ImsName = argv[i];
  740. } else if (optname_match("display", opt, 2)) {
  741. i++;
  742. Opt.DisplayName = argv[i];
  743. wav[wac++] = argv[i - 1]; wav[wac++] = argv[i]; /* ??? */
  744. } else if (optname_match("locale", opt, 2)) {
  745. i++;
  746. Opt.LocaleName = argv[i];
  747. } else if (optname_match("CDE_locale", opt, 2)) {
  748. i++;
  749. Opt.LocaleName = find_system_locale_name(argv[i]);
  750. } else if (optname_match("hostname", opt, 2)) {
  751. i++;
  752. Opt.HostName = argv[i];
  753. } else if (optname_match("config", opt, 2)) {
  754. i++;
  755. Opt.ConfPath = argv[i];
  756. } else if (optname_match("file", opt, 2)) {
  757. i++;
  758. Opt.UserPath = argv[i];
  759. } else if (optname_match("log", opt, 2)) {
  760. i++;
  761. Opt.LogPath = argv[i];
  762. } else if (optname_match("resource", opt, 3)) {
  763. i++;
  764. Opt.ResourceFile = argv[i];
  765. } else if (optname_match("shell", opt, 2)) {
  766. i++;
  767. Opt.ShellName = argv[i];
  768. } else if (optname_match("timeout", opt, 3)) {
  769. i++;
  770. if (str_to_int(argv[i], &n) && n >= 0)
  771. Opt.Timeout = n;
  772. } else if (optname_match("interval", opt, 3)) {
  773. i++;
  774. if (str_to_int(argv[i], &n) && n >= 0)
  775. Opt.Interval = n;
  776. /* Xt options */
  777. } else if (optname_match("font", opt, 2)
  778. || optname_match("fn", opt, 2)
  779. || optname_match("fg", opt, 2)
  780. || optname_match("bg", opt, 2)
  781. || optname_match("bd", opt, 2)
  782. || optname_match("foreground", opt, 4)
  783. || optname_match("backgroundg", opt, 4)
  784. || optname_match("bordercolor", opt, 4)
  785. || optname_match("geometry", opt, 2)
  786. || optname_match("title", opt, 2)
  787. || optname_match("xnlLanguage", opt, 3)
  788. /* || optname_match("iconic", opt, 4) */
  789. || optname_match("xrm", opt, 2)) {
  790. i++;
  791. wav[wac++] = argv[i - 1]; wav[wac++] = argv[i];
  792. } else
  793. goto _inv_opt;
  794. }
  795. first_time = False;
  796. if (do_usage) return NoError;
  797. switch (OpMode) { /* adjust OpFlag */
  798. #if 0 /* noy implemented yet */
  799. case MODE_STYLE:
  800. SET_FLAG(FLAG_DT | FLAG_WINDOW);
  801. CLR_FLAG(FLAG_VUE);
  802. break;
  803. #endif
  804. case MODE_START:
  805. if (Opt.ImsName) {
  806. SET_FLAG(FLAG_NOSAVE);
  807. /* CLR_FLAG(USE_WINDOW_MASK); */
  808. Opt.SelectMode = SEL_MODE_GIVEN;
  809. }
  810. if (Opt.LogPath) { /* open log file */
  811. if (set_errorlog(Opt.LogPath) != NoError)
  812. Opt.LogPath = NULL;
  813. }
  814. if (CHK_FLAG(FLAG_REMOTERUN)) {
  815. SET_FLAG(FLAG_NOTIFY);
  816. SET_FLAG(FLAG_NOSAVE);
  817. CLR_FLAG(USE_WINDOW_MASK);
  818. }
  819. break;
  820. case MODE_MODE:
  821. if (CHK_FLAG(FLAG_WINDOW)) {
  822. Opt.SelectMode = SEL_MODE_WIN;
  823. } else if (Opt.SelectMode == SEL_MODE_NONE) {
  824. Opt.SelectMode = SEL_MODE_QUERY;
  825. CLR_FLAG(USE_WINDOW_MASK);
  826. }
  827. break;
  828. case MODE_LISTNAME:
  829. SET_FLAG(FLAG_WINDOW);
  830. break;
  831. default:
  832. CLR_FLAG(USE_WINDOW_MASK);
  833. break;
  834. }
  835. if (CHK_FLAG(USE_WINDOW_MASK)) {
  836. /* create argc & argv for window */
  837. Wargv = ALLOC(wac + 1 + 4, char *); /* spare for '-xnlLanguage' */
  838. memcpy(Wargv, wav, sizeof(char *) * wac);
  839. Wargv[0] = ProgramName;
  840. Wargv[wac] = NULL;
  841. Wargc = wac;
  842. } else {
  843. UseMsgWindow = False; /* disable msg window */
  844. }
  845. #undef CLR_FLAG
  846. #undef SET_FLAG
  847. #undef CHK_FLAG
  848. return NoError;
  849. _inv_opt:
  850. DPR(("%s: invalid option '%s'\n", ProgramName, argv[i]));
  851. setErrArg1(argv[i]);
  852. return ErrSyntax;
  853. }
  854. /* ******** usage ******** */
  855. #ifdef DEBUG
  856. typedef struct {
  857. char *name;
  858. char *desc;
  859. } OptDesc;
  860. #if 0
  861. static OptDesc opts_start[] = {
  862. { "-env", "print modified environment variables" },
  863. { "-shell <name>", "override $SHELL" },
  864. { "-ims <name>", "specifies input method name" },
  865. { "-imsopt <string>", "specifies command options for input method server" },
  866. { "-host <name>", "specifies host where input method server should be run" },
  867. { "-mode", "change input method selection mode" },
  868. { "-list", "show registered input method" },
  869. { "-help", "show this message" },
  870. { NULL, NULL }
  871. };
  872. static OptDesc opts_mode[] = {
  873. { "-auto", "enable auto-selection mode" },
  874. { "-noauto", "disable auto-selection mode" },
  875. { NULL, NULL }
  876. };
  877. #endif
  878. static OptDesc opts_internal[] = {
  879. { "-display <dpy>", "override $DISPLAY" },
  880. { "-current", "show selected input method" },
  881. { "-listname", "show registered input method for dtstyle" },
  882. { "-remoteconf", "print IMS configuration data for remote execution" },
  883. { "-remoterun", "start IMS as remote execution" },
  884. { "-nosave", "not save the selection" },
  885. { "-select", "force select" },
  886. { "-noenv", "disable printing environment variables" },
  887. { "-envonly", "-noenv & -nostart" },
  888. { "-nostart", "not start IMS" },
  889. { "-noresouce", "not load session resource files" },
  890. { "-nowait", "immediately exits after IMS invocation" },
  891. { "-notimeout", "do not timeout" },
  892. { "-noremote", "disable remote execution" },
  893. { "-notify", "print error code to stderr" },
  894. #ifdef SelectMode_ONCE
  895. { "-once", "auto-selection once selected" },
  896. #endif /* SelectMode_ONCE */
  897. { "-dt" , "in CDE environment" },
  898. { "-window", "use window environment" },
  899. { "-nowindow", "do not use window environment" },
  900. { "-timeout <num>", "specifies timeout period (sec.)" },
  901. { "-interval <num>", "specifies check interval (msec.)" },
  902. { "-locale <locale>", "override $LANG" },
  903. { "-CDE_locale <CDE_locale>", "CDE generic locale name" },
  904. { "-resource <file>", "specifies resource file" },
  905. { "-config <file>", "specifies configuration file" },
  906. { "-file <file>", "specifies user selection file" },
  907. { "-log <file>", "specifies log file" },
  908. { "-fn <fontlist>", "specifies font" },
  909. { "-quiet", "print no messages" },
  910. { "-verbose", "print verbose messages" },
  911. { "-debug", "print debug messages" },
  912. { "<Xt options>", "standard X toolkit options" },
  913. { NULL, NULL }
  914. };
  915. #endif /* DEBUG */
  916. static void usage(int force)
  917. {
  918. char *fmt = "\t%-20s%s\n";
  919. if (!force && Verbose <= 0) return;
  920. fprintf(LogFp, (CATGETS(catd,NL_SETN,1, "usage: %s [options ..]")),
  921. ProgramName);
  922. putc('\n', LogFp);
  923. if (OpMode != MODE_MODE) {
  924. fprintf(LogFp, fmt,
  925. "-env", (CATGETS(catd,NL_SETN,2, "print modified environment variables")));
  926. fprintf(LogFp, fmt,
  927. "-shell <name>", (CATGETS(catd,NL_SETN,3, "override $SHELL")));
  928. fprintf(LogFp, fmt,
  929. "-ims <name>", (CATGETS(catd,NL_SETN,4, "specifies input method name")));
  930. fprintf(LogFp, fmt,
  931. "-imsopt <string>", (CATGETS(catd,NL_SETN,5, "specifies command options for input method server")));
  932. fprintf(LogFp, fmt,
  933. "-host <name>", (CATGETS(catd,NL_SETN,6, "specifies host where input method server should be run")));
  934. fprintf(LogFp, fmt,
  935. "-mode", (CATGETS(catd,NL_SETN,7, "change input method selection mode")));
  936. fprintf(LogFp, fmt,
  937. "-list", (CATGETS(catd,NL_SETN,8, "print registered input method")));
  938. fprintf(LogFp, fmt,
  939. "-help", (CATGETS(catd,NL_SETN,9, "show this message")));
  940. } else {
  941. fprintf(LogFp, fmt,
  942. "-auto", (CATGETS(catd,NL_SETN,23, "force 'resume_current_input_method' mode")));
  943. fprintf(LogFp, fmt,
  944. "-noauto", (CATGETS(catd,NL_SETN,24, "force 'ask_at_login' mode")));
  945. }
  946. #ifdef DEBUG
  947. if (Verbose > 1) {
  948. OptDesc *opts;
  949. fprintf(LogFp, "\n <internal options>\n");
  950. for (opts = opts_internal; opts->name; opts++)
  951. fprintf(LogFp, fmt, opts->name, opts->desc);
  952. }
  953. #endif
  954. }
  955. /* ******** error messages ******** */
  956. char *xims_errmsg(int err_num, void *arg1, void *arg2, void *arg3)
  957. {
  958. char *fmt = NULL, *bp;
  959. int len;
  960. static char msgbuf[BUFSIZ];
  961. switch (err_num) {
  962. case NoError:
  963. break;
  964. case ErrSyntax: /* arg1: option string */
  965. fmt = (CATGETS(catd,NL_SETN,31, "invalid option '%s'"));
  966. break;
  967. case ErrNoHome:
  968. fmt = (CATGETS(catd,NL_SETN,32, "environment variable 'HOME' not defined"));
  969. break;
  970. case ErrNoLocale:
  971. fmt = (CATGETS(catd,NL_SETN,33, "environment variable 'LANG' not defined"));
  972. break;
  973. case ErrNoCDELocale:
  974. fmt = (CATGETS(catd,NL_SETN,34, "this locale is not supported by the desktop."));
  975. break;
  976. case ErrNoDisplay:
  977. fmt = (CATGETS(catd,NL_SETN,35, "environment variable 'DISPLAY' not defined"));
  978. break;
  979. case ErrFileOpen: /* arg1: file name */
  980. fmt = (CATGETS(catd,NL_SETN,36, "cannot open file\n [%s]"));
  981. setErrArg1(errFilePath);
  982. break;
  983. case ErrFileCreate: /* arg1: file name */
  984. fmt = (CATGETS(catd,NL_SETN,37, "cannot create file\n [%s]"));
  985. setErrArg1(errFilePath);
  986. break;
  987. case ErrDirCreate: /* arg1: dir name */
  988. fmt = (CATGETS(catd,NL_SETN,38, "cannot create directory\n [%s]"));
  989. setErrArg1(errFilePath);
  990. break;
  991. case ErrMissEntry: /* arg1: entry name, arg2: file name */
  992. fmt = (CATGETS(catd,NL_SETN,39, "missing '%s' entry in configuration file\n [%s]"));
  993. setErrArg2(errFilePath);
  994. break;
  995. case ErrAnotherProg:
  996. fmt = (CATGETS(catd,NL_SETN,40, "another '%s' is already running"));
  997. setErrArg1(ProgramName);
  998. break;
  999. case ErrNoSelectionFile: /* arg1: locale name */
  1000. fmt = (CATGETS(catd,NL_SETN,41, "no selection file for '%s'"));
  1001. setErrArg1(userEnv.locale);
  1002. break;
  1003. case ErrSaveSelection: /* arg1: file name */
  1004. fmt = (CATGETS(catd,NL_SETN,42, "cannot create selection file\n [%s]"));
  1005. setErrArg1(errFilePath);
  1006. break;
  1007. case ErrNoSelection: /* arg1: locale name */
  1008. fmt = (CATGETS(catd,NL_SETN,43, "no ims selected for '%s'"));
  1009. setErrArg1(userEnv.locale);
  1010. break;
  1011. case ErrNoLocaleConf: /* arg1: file name */
  1012. fmt = (CATGETS(catd,NL_SETN,44, "no locale configuration file for '%s'"));
  1013. setErrArg1(userEnv.locale);
  1014. break;
  1015. case ErrNoImsEntry: /* arg1: locale name */
  1016. fmt = (CATGETS(catd,NL_SETN,45, "no ims configured for '%s'"));
  1017. setErrArg1(userEnv.locale);
  1018. break;
  1019. case ErrNoImsConf: /* arg1: ims name */
  1020. fmt = (CATGETS(catd,NL_SETN,46, "no ims configuration file for '%s'"));
  1021. setErrArg1(userSel.name);
  1022. break;
  1023. case ErrNotRegistered: /* arg1: ims name */
  1024. fmt = (CATGETS(catd,NL_SETN,47, "ims '%s' not registered"));
  1025. setErrArg1(userSel.name);
  1026. break;
  1027. case ErrNoExecutable: /* arg1: ims name, arg2: file name */
  1028. fmt = (CATGETS(catd,NL_SETN,48, "no executable file for '%s'\n [%s]"));
  1029. setErrArg1(userSel.name);
  1030. setErrArg2(userSel.ent->ims->cmd_path);
  1031. break;
  1032. case ErrImsRunning: /* arg1: ims name */
  1033. fmt = (CATGETS(catd,NL_SETN,49, "ims '%s' is already running"));
  1034. setErrArg1(userSel.name);
  1035. break;
  1036. case ErrImsExecution: /* arg1: ims name */
  1037. fmt = (CATGETS(catd,NL_SETN,50, "cannot execute ims '%s'"));
  1038. setErrArg1(userSel.name);
  1039. break;
  1040. case ErrImsAborted: /* arg1: ims name, arg2: log file */
  1041. fmt = (CATGETS(catd,NL_SETN,51, "ims '%s' aborted. See log file.\n [%s]"));
  1042. setErrArg1(userSel.name);
  1043. if (userSel.host_type == HOST_REMOTE)
  1044. setErrArg2(errFilePath);
  1045. else
  1046. setErrArg2(Opt.LogPath);
  1047. break;
  1048. case ErrImsTimeout: /* arg1: file name */
  1049. fmt = (CATGETS(catd,NL_SETN,52, "ims '%s' is not available yet"));
  1050. setErrArg1(userSel.name);
  1051. break;
  1052. case ErrUnknownHost: /* arg1: host name */
  1053. fmt = (CATGETS(catd,NL_SETN,53, "unknown host '%s'"));
  1054. setErrArg1(userSel.hostname);
  1055. break;
  1056. case ErrRemoteAction: /* arg1: action name */
  1057. fmt = (CATGETS(catd,NL_SETN,54, "action '%s' failed"));
  1058. setErrArg1(errFuncName);
  1059. break;
  1060. case ErrRemoteData: /* arg1: host name */
  1061. fmt = (CATGETS(catd,NL_SETN,55, "remote execution failed on '%s'"));
  1062. setErrArg1(userSel.hostname);
  1063. break;
  1064. case ErrNoImsstart: /* arg1: host name */
  1065. fmt = (CATGETS(catd,NL_SETN,56, "remote functionality is not available on '%s'"));
  1066. setErrArg1(userSel.hostname);
  1067. break;
  1068. case ErrRemoteNoIms: /* arg1: host name */
  1069. fmt = (CATGETS(catd,NL_SETN,57, "no ims registered on '%s'"));
  1070. setErrArg1(userSel.hostname);
  1071. break;
  1072. case ErrRemoteMissIms: /* arg1: ims name, arg2: host name */
  1073. fmt = (CATGETS(catd,NL_SETN,58, "ims '%1$s' not registered on '%2$s'"));
  1074. setErrArg1(userSel.name);
  1075. setErrArg2(userSel.hostname);
  1076. break;
  1077. case ErrOpenDpy: /* arg1: display name */
  1078. fmt = (CATGETS(catd,NL_SETN,59, "cannot open display '%s'"));
  1079. setErrArg1(userEnv.displayname);
  1080. break;
  1081. #ifdef DEBUG
  1082. case ErrSignaled: /* arg1: signal number */
  1083. fmt = "terminated by signal (signal=%d)";
  1084. setErrArg1(exitSignalNumber);
  1085. break;
  1086. case ErrDisabled: /* arg1: program name, arg2: env name */
  1087. fmt = "ximsstart is disabled ('%s' is set)";
  1088. setErrArg1(ENV_NO_DTIMSSTART);
  1089. break;
  1090. case ErrRemoteIms: /* arg1: ims name, arg2: host name */
  1091. fmt = "cannot execute ims '%s' on '%s'";
  1092. setErrArg1(userSel.name);
  1093. setErrArg2(userSel.hostname);
  1094. break;
  1095. case ErrOpenResource: /* arg1: file name */
  1096. fmt = "cannot open resource file\n [%s]";
  1097. setErrArg1(Opt.ResourceFile);
  1098. break;
  1099. case ErrMemory: /* arg1: function name */
  1100. fmt = "cannot allocate memory in %s()";
  1101. setErrArg1(errFuncName);
  1102. break;
  1103. case ErrIsNone: /* arg1: ims name */
  1104. fmt = "the selected ims is '%s'";
  1105. setErrArg1(userSel.name);
  1106. break;
  1107. case ErrNotRun: /* arg1: ims name */
  1108. fmt = "the selected ims '%s' need not to run";
  1109. setErrArg1(userSel.name);
  1110. break;
  1111. case ErrImsWaiting: /* arg1: ims name */
  1112. fmt = "internal error [ImsWaiting] (ims='%s')";
  1113. setErrArg1(userSel.name);
  1114. break;
  1115. case ErrImsWaitDone: /* arg1: ims name */
  1116. fmt = "internal error [ImsWaitDone] (ims='%s')";
  1117. setErrArg1(userSel.name);
  1118. break;
  1119. case ErrImsConnecting: /* arg1: ims name */
  1120. fmt = "internal error [ImsConnecting] (ims='%s')";
  1121. setErrArg1(userSel.name);
  1122. break;
  1123. case ErrImsConnectDone: /* arg1: ims name */
  1124. fmt = "internal error [ImsConnectDone] (ims='%s')";
  1125. setErrArg1(userSel.name);
  1126. break;
  1127. case ErrInvState: /* arg1: OpStateVal */
  1128. fmt = "internal error [invalid state: '%d']";
  1129. setErrArg1(OpState);
  1130. break;
  1131. case ErrInternal: /* arg1: function name */
  1132. fmt = "internal error in %s()";
  1133. setErrArg1(errFuncName);
  1134. break;
  1135. #endif /* DEBUG */
  1136. }
  1137. if (!fmt) return NULL;
  1138. bp = strcpyx(msgbuf, ProgramName); *bp++ = ':'; *bp++ = ' ';
  1139. if (!arg1) arg1 = ximsErrArgs[0];
  1140. if (!arg2) arg2 = ximsErrArgs[1];
  1141. if (!arg3) arg3 = ximsErrArgs[2];
  1142. sprintf(bp, fmt, arg1, arg2, arg3);
  1143. len = strlen(bp);
  1144. bp[len++] = '\n'; bp[len] = '\0';
  1145. return msgbuf;
  1146. }