select.c 8.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341
  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: select.c /main/6 1996/11/21 12:17:43 cde-hp $ */
  24. #include "xims.h"
  25. static int fill_ims_ent(/* list, top, last */);
  26. static int setup_local_selection(/* sel, list, conf_all */);
  27. static int setup_remote_selection(/* sel */);
  28. static int setup_user_selection(/* sel, list, idx */);
  29. void ximsSelect(void)
  30. {
  31. int ret;
  32. bool use_win;
  33. char *def_ims;
  34. ImsList *list = (ImsList *) 0;
  35. FileSel *fsel = (FileSel *) 0;
  36. UserSelection *sel = &userSel;
  37. OpState = State_Select;
  38. /* clear_UserSelection(sel); */
  39. sel->iconic = -1;
  40. if (!localList) {
  41. if ((ret = get_ims_list(&list, NULL, False)) != NoError) {
  42. OpState = State_Select_Err;
  43. OpErrCode = ret;
  44. return;
  45. }
  46. localList = list;
  47. } else
  48. list = localList;
  49. use_win = True;
  50. def_ims = NULL;
  51. if (Opt.SelectMode == SEL_MODE_GIVEN) {
  52. sel->name = NEWSTR(Opt.ImsName);
  53. use_win = False;
  54. } else {
  55. if (read_user_selection(&sel->fsel, NULL) == NoError) {
  56. fsel = sel->fsel;
  57. #ifdef DEBUG
  58. if (DebugLvl > 1) pr_FileSel(sel->fsel);
  59. #endif
  60. }
  61. if (list->default_idx >= 0)
  62. def_ims = list->elist[list->default_idx]->name;
  63. if ((OpFlag & FLAG_NOSAVE) || Opt.SelectMode == SEL_MODE_NOAUTO) {
  64. use_win = True;
  65. } else if (Opt.SelectMode == SEL_MODE_AUTO) {
  66. use_win = False;
  67. #ifdef SelectMode_ONCE
  68. } else if (Opt.SelectMode == SEL_MODE_ONCE) {
  69. if (fsel->name)
  70. use_win = False;
  71. #endif /* SelectMode_ONCE */
  72. #ifdef AutoSelectionForSoleIMS
  73. } else if (list->num_ent == 1) {
  74. DPR(("ximsSelect(): only one entry in locale_conf\n"));
  75. sel->name = NEWSTR(list->elist[0]->name);
  76. use_win = False;
  77. #endif /* AutoSelectionForSoleIMS */
  78. } else if (fsel) {
  79. if (fsel->select_mode != SEL_MODE_NOAUTO
  80. && ((fsel->select_mode == SEL_MODE_AUTO ||
  81. list->def_selmode == SEL_MODE_AUTO)
  82. && (def_ims || fsel->name))
  83. #ifdef SelectMode_ONCE
  84. || ((fsel->select_mode == SEL_MODE_ONCE
  85. || list->def_selmode == SEL_MODE_ONCE)
  86. && fsel->name)
  87. #endif /* SelectMode_ONCE */
  88. )
  89. use_win = False;
  90. } else if (list->def_selmode == SEL_MODE_AUTO && def_ims) {
  91. DPR(("ximsSelect(): def_selmode==AUTO in locale_conf\n"));
  92. use_win = False;
  93. }
  94. }
  95. if (sel->iconic == -1) {
  96. sel->iconic = fsel ? fsel->iconic : 0;
  97. } else if (sel->iconic != fsel->iconic) { /* this should never happen ! */
  98. sel->flag |= F_SELECT_CHANGED;
  99. }
  100. if (fsel && fsel->select_mode == SEL_MODE_NONE) {
  101. if (list->def_selmode != SEL_MODE_NONE) {
  102. fsel->select_mode = list->def_selmode;
  103. sel->flag |= F_SELECT_CHANGED;
  104. }
  105. }
  106. if (!sel->name && fsel && fsel->name)
  107. sel->name = NEWSTR(fsel->name);
  108. else if (def_ims)
  109. sel->name = NEWSTR(def_ims);
  110. if (Opt.HostName)
  111. sel->hostname = NEWSTR(Opt.HostName);
  112. else if (fsel && fsel->hostname)
  113. sel->hostname = NEWSTR(fsel->hostname);
  114. if (sel->hostname)
  115. sel->host_type = check_hostname(sel->hostname);
  116. else
  117. sel->host_type = HOST_LOCAL;
  118. if (use_win == True) {
  119. ret = setup_local_selection(sel, list, True);
  120. ret = start_selection_window();
  121. } else {
  122. switch (sel->host_type) {
  123. case HOST_REMOTE:
  124. ret = setup_remote_selection(sel);
  125. if (ret != NoError) {
  126. put_xims_errmsg(ret, 0, 0, 0);
  127. }
  128. break;
  129. case HOST_LOCAL:
  130. ret = setup_local_selection(sel, list, False);
  131. break;
  132. case HOST_UNKNOWN:
  133. ret = ErrUnknownHost;
  134. /* put_xims_errmsg(ret, sel->hostname, 0, 0); */
  135. break;
  136. }
  137. }
  138. OpErrCode = ret;
  139. OpState = ret == NoError ? State_Select_Done : State_Select_Err;
  140. return;
  141. }
  142. static int fill_ims_ent(ImsList *list, int top, int last)
  143. {
  144. int ret;
  145. int i;
  146. ImsConf *ims;
  147. ImsEnt *ent;
  148. /* if (top < 0 || last < 0) return 0; */
  149. ims = (ImsConf *) 0;
  150. for (i = top; i <= last; i++) { /* read IMS conf */
  151. ret = NoError;
  152. ent = list->elist[i];
  153. if (!ent->ims) {
  154. if (!ims) ims = ALLOC(1, ImsConf);
  155. ret = read_imsconf(ims, ent->name, ent->fname);
  156. if (ret == NoError) {
  157. ent->ims = ims;
  158. ims = (ImsConf *) 0;
  159. }
  160. }
  161. if (ret == NoError)
  162. set_ims_status(ent);
  163. else
  164. ent->status = ret;
  165. }
  166. if (ims) FREE(ims);
  167. return last - top + 1;
  168. }
  169. static int setup_local_selection(UserSelection *sel, ImsList *list, int conf_all)
  170. {
  171. int ret;
  172. int idx, top, last;
  173. idx = get_ims_idx(list, sel->name);
  174. top = last = 0;
  175. if (conf_all) last = list->num_ent - 1;
  176. else if (idx >= 0) top = last = idx;
  177. fill_ims_ent(list, top, last);
  178. ret = setup_user_selection(sel, list, idx);
  179. return ret;
  180. }
  181. static int setup_remote_selection(UserSelection *sel)
  182. {
  183. int ret;
  184. int idx;
  185. ImsList *new_list;
  186. ret = get_remote_conf(&new_list, sel->hostname, NULL, sel->name);
  187. if (ret == NoError) {
  188. idx = get_ims_idx(new_list, sel->name);
  189. ret = setup_user_selection(sel, new_list, idx);
  190. }
  191. return ret;
  192. }
  193. static int setup_user_selection(UserSelection *sel, ImsList *list, int idx)
  194. {
  195. if (sel->name) {
  196. if (idx >= 0) {
  197. sel->ent = list->elist[idx];
  198. sel->status = sel->ent->status;
  199. } else {
  200. /* this ims isn't registered in locale_conf */
  201. sel->status = ErrNotRegistered;
  202. }
  203. } else
  204. sel->status = ErrNoSelection;
  205. sel->ims_idx = idx;
  206. sel->list = list;
  207. return sel->status;
  208. }
  209. int update_user_selection(UserSelection *sel, ImsList *list, int idx, char *host, int host_type)
  210. {
  211. ImsEnt *ent;
  212. if (idx < 0 || idx >= list->num_ent) return False;
  213. ent = list->elist[idx];
  214. if (ent->status != NoError) return False;
  215. if (strcmp(sel->name, ent->name)) {
  216. RENEWSTR(sel->name, ent->name);
  217. }
  218. if ((host) && (!(sel->hostname) || strcmp(sel->hostname, host))) {
  219. RENEWSTR(sel->hostname, host);
  220. }
  221. sel->host_type = host_type;
  222. if (sel->list && sel->list != localList && sel->list != list) {
  223. clear_ImsList(sel->list);
  224. FREE(sel->list);
  225. }
  226. sel->list = list;
  227. sel->ent = ent;
  228. sel->status = ent->status;
  229. sel->ims_idx = idx;
  230. sel->flag |= F_SELECT_CHANGED;
  231. return True;
  232. }
  233. int get_ims_idx(ImsList *list, char *name)
  234. {
  235. int idx;
  236. if (name) {
  237. for (idx = 0; idx < list->num_ent; idx++)
  238. if (strcmp(name, list->elist[idx]->name) == 0)
  239. return idx;
  240. }
  241. return -1;
  242. }
  243. int set_ims_status(ImsEnt *ent)
  244. {
  245. int ret = NoError;
  246. ImsConf *ims = ent->ims;
  247. if (ent->name && strcmp(ent->name, NAME_NONE) == 0) {
  248. ret = NoError;
  249. } else if (!ims) {
  250. ret = ErrNoImsConf;
  251. } else if (ims->cmd_path && !(ims->flags & F_BUILTIN)
  252. && !is_executable(ims->cmd_path)) {
  253. DPR(("set_ims_status(%s): executable '%s' not exist\n",
  254. ent->name, ims->cmd_path));
  255. ret = ErrNoExecutable;
  256. }
  257. ent->status = ret;
  258. return ret;
  259. }
  260. int get_ims_list(ImsList **listp, char *locale, int fill_ent)
  261. {
  262. int ret = NoError;
  263. ImsList *list;
  264. list = ALLOC(1, ImsList);
  265. if ((ret = read_localeconf(list, locale)) != NoError) {
  266. ret = ErrNoLocaleConf;
  267. } else if (list->num_ent == 0) {
  268. DPR(("get_ims_list(%s): no IMS in locale conf\n", locale));
  269. ret = ErrNoImsEntry;
  270. } else if (fill_ent) {
  271. fill_ims_ent(list, 0, list->num_ent - 1);
  272. }
  273. if (ret == NoError) {
  274. list->status = ret;
  275. } else {
  276. clear_ImsList(list);
  277. FREE(list);
  278. list = (ImsList *) 0;
  279. }
  280. *listp = list;
  281. return ret;
  282. }