Use same SIGCHLD handling for OpenBSD as for OSF.
[oweals/cde.git] / cde / programs / dtfile / Main.c
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 librararies 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 /* $TOG: Main.c /main/29 1999/09/17 13:35:04 mgreess $ */
24 /************************************<+>*************************************
25  ****************************************************************************
26  *
27  *   FILE:           Main.c
28  *
29  *   COMPONENT_NAME: Desktop File Manager (dtfile)
30  *
31  *   Description:    This file contains the main program for dtfile.
32  *                   It also contains functions for session management and
33  *                   directory view control.
34  *
35  *   FUNCTIONS: BlackPixelOfScreen
36  *              BuildAndShowIconName
37  *              CheckForOpenDirectory
38  *              CheckOpenDir
39  *              CleanUp
40  *              CloseView
41  *              DirectoryChanged
42  *              DisplayHeight
43  *              DisplayWidth
44  *              DtfileCvtStringToDTIcon
45  *              DtfileCvtStringToDirection
46  *              DtfileCvtStringToGrid
47  *              DtfileCvtStringToObjPlace
48  *              DtfileCvtStringToOpenDir
49  *              DtfileCvtStringToOrder
50  *              DtfileCvtStringToTree
51  *              DtfileCvtStringToTreeFiles
52  *              DtfileCvtStringToView
53  *              DtfileStringToDirection
54  *              DtfileStringToGrid
55  *              DtfileStringToOrder
56  *              DtfileStringToTree
57  *              DtfileStringToTreeFiles
58  *              DtfileStringToView
59  *              ErrorHandler
60  *              ExitApp
61  *              ExitHandler
62  *              ForceMyIconClosed
63  *              ForceMyIconOpen
64  *              GetNewView
65  *              GetPWD
66  *              GetRestrictedDirectory
67  *              HandleTtRequest
68  *              LoadViews
69  *              MarqueeSelect
70  *              MoveDefaultSettings
71  *              ObserveTtNotice
72  *              OpenDirectories
73  *              ReloadDatabases
74  *              RemoveTextFields
75  *              RestoreSession
76  *              RestoreSettingsFile
77  *              RestrictModeUsage
78  *              ReturnDesktopPtr
79  *              RootWindowOfScreen
80  *              SaveDefaultCancelCB
81  *              SaveDefaultOkCB
82  *              SaveSession
83  *              SaveSessionCallback
84  *              SaveSettingsCB
85  *              SetupSendRequestArgs
86  *              Stop
87  *              ToolkitErrorHandler
88  *              Usage
89  *              ViewAccept
90  *              ViewDirectoryHandler
91  *              ViewDirectoryProc
92  *              ViewHomeDirectoryHandler
93  *              ViewSessionHandler
94  *              ViewToolsDirectoryHandler
95  *              WaitForResponseAndExit
96  *              WhitePixelOfScreen
97  *              XtMalloc
98  *              _DtNextToken
99  *              _DtWsmAddMarqueeSelectionCallback
100  *              if
101  *              main
102  *              strcmp
103  *              strlen
104  *
105  *   (c) Copyright 1993, 1994, 1995 Hewlett-Packard Company
106  *   (c) Copyright 1993, 1994, 1995 International Business Machines Corp.
107  *   (c) Copyright 1993, 1994, 1995 Sun Microsystems, Inc.
108  *   (c) Copyright 1993, 1994, 1995 Novell, Inc.
109  *
110  ****************************************************************************
111  ************************************<+>*************************************/
112
113 #include <sys/types.h>
114 #include <stdio.h>
115 #include <stdlib.h>
116 #include <sys/stat.h>
117 #include <signal.h>
118
119 #if defined(__osf__) || defined(__OpenBSD__)
120 #include <sys/wait.h>
121 #endif /* __osf__ */
122
123 #include <errno.h>
124 #include <pwd.h>
125 #include <stdlib.h>
126 #include <ctype.h>
127
128 #ifndef sun /* don't need the nl_types.h file */
129 #include <nl_types.h>
130 #endif /* !sun */
131
132 #include <locale.h>
133
134 #include <Xm/XmP.h>
135 #include <Xm/DrawingA.h>
136 #include <Xm/DrawingAP.h>
137 #include <Xm/MessageB.h>
138 #include <Xm/RowColumn.h>
139 #include <Xm/MwmUtil.h>
140
141 #include <Xm/IconFileP.h>
142 #include <Dt/Icon.h>
143 #include <Dt/IconP.h>
144 #include <Dt/IconFile.h>
145
146 #include <Dt/HelpDialog.h>
147
148 #ifdef SHAPE
149 #include <X11/extensions/shape.h>
150 #endif
151
152 #include <X11/Shell.h>
153 #include <X11/Xatom.h>
154 #include <Xm/Protocols.h>
155 #ifdef HAVE_EDITRES
156 #include <X11/Xmu/Editres.h>
157 #endif
158 #include <Dt/Session.h>
159 #include <Dt/Dt.h>
160 #include <Dt/DtP.h>
161 #include <Dt/Connect.h>
162 #include <Dt/FileM.h>
163 #include <Dt/Indicator.h>
164 #include <Dt/Lock.h>
165 #include <Dt/UserMsg.h>
166 #include <Dt/Wsm.h>
167 #include <Dt/WsmP.h>
168 #include <Dt/DtNlUtils.h>
169 #include <Dt/CommandM.h>
170 #include <Dt/EnvControlP.h>
171 #include <Dt/Dts.h>
172 #include <Dt/SharedProcs.h>
173
174 #include "Encaps.h"
175 #include "SharedProcs.h"
176
177 #include <Tt/tttk.h>
178
179 #include "Help.h"
180 #include "FileMgr.h"
181 #include "Desktop.h"
182 #include "Main.h"
183 #include "ChangeDir.h"
184 #include "Prefs.h"
185 #include "Common.h"
186 #include "Filter.h"
187 #include "Find.h"
188 #include "ModAttr.h"
189
190 /* From Command.c */
191 extern void MoveCopyLinkHandler(Tt_message ttMsg, int opType);
192
193 /* From Desktop.c */
194 extern void PutOnWorkspaceHandler(Tt_message ttMsg);
195
196 /* From Filter.c */
197 extern void UpdateFilterAfterDBReread (DialogData * dialog_data);
198
199 /* From ToolTalk.c */
200 extern int InitializeToolTalkSession( Widget topLevel, int ttFd );
201 extern Tt_status InitializeToolTalkProcid( int *ttFd, Widget topLevel, Boolean sendStarted );
202 extern void FinalizeToolTalkSession();
203 /* From Trash.c */
204 void CloseTrash(Widget w, XtPointer client_data, XtPointer call_data) ;
205
206
207
208 /* When openDir resource is set to NEW
209    File Manager will use this prefix to find for a different icon
210    to display.
211 */
212 #define ICON_OPEN_PREFIX "OPEN_"
213
214 /* THESE ARE ONLY STRINGS WHICH DO NOT NEED TO BE LOCALIZED */
215 /* Don't use '#define' since you end up with multiple copies */
216 char DTFILE_CLASS_NAME[] = "Dtfile";
217 char DTFILE_HELP_NAME[] = "Filemgr";
218 char DESKTOP_DIR[] = ".dt/Desktop";
219
220 static char WS_RES_HEADER[] = ".Workspace.";
221 static char SEC_HELP_RES_HEADER[] = ".secondaryHelpDialogCount: ";
222 static char WS_LOAD_RES_HEADER[] = "Workspace";
223 static char SEC_LOAD_HELP_RES_HEADER[] = "secondaryHelpDialogCount";
224 static char RESTRICTED_HEADER[] = "-restricted";
225 static char VIEW_HEADER[] = "-view";
226
227
228 /*  Structure, resource definitions, for View's optional parameters.  */
229
230 typedef struct
231 {
232    char * no_view;
233    char * session;
234    char * directories;
235    int tree_view;
236    int tree_files;
237    int view;
238    int order;
239    int direction;
240    int grid;
241    int instanceIconWidth;
242    int instanceIconHeight;
243    XmFontList user_font;
244    Dimension tool_width;
245    Dimension tool_height;
246    Dimension dir_width;
247    Dimension dir_height;
248    Boolean prompt_user;
249    char * root_title;
250    char * title;
251    char * help_volume;
252    char * restricted;
253    int dragThreshold;
254    int rereadTime;
255    int checkBrokenLink;
256    int maxDirectoryProcesses;
257    int maxRereadProcesses;
258    int maxRereadProcsPerTick;
259    int trashWait;
260    int desktopIconType;
261    Boolean showFilesystem;
262    Boolean showDropZone;
263    Boolean showEmptySet;
264    Boolean showEmptyMsg;
265    int openDirType;
266    Boolean restrictMode;
267    int desktopPlacement;
268    Boolean freezeOnConfig;
269 #if defined(__hpux) || defined(sun)
270    Boolean follow_links;
271 #endif
272    char * fileMgrIcon;
273    char * appMgrIcon;
274    char * trashIcon;
275    int retryLoadDesktop;
276    int smallIconWidth;
277    int smallIconHeight;
278    int largeIconWidth;
279    int largeIconHeight;
280    Boolean emptyTrashOnExit;
281 } ApplicationArgs, *ApplicationArgsPtr;
282
283 static ApplicationArgs application_args;
284
285 /********    Static Function Declarations    ********/
286
287 static void ErrorHandler(
288                         Display *disp,
289                         XErrorEvent *event) ;
290 static void ToolkitErrorHandler(
291                         char *message) ;
292 static void Usage(
293                         char **argv) ;
294 static void RestrictModeUsage(
295                         char **argv) ;
296 static void Stop( void ) ;
297 static void RestoreSettingsFile( void ) ;
298 static void MoveDefaultSettings(
299                         int mode) ;
300 static void SaveDefaultCancelCB(
301                         Widget w,
302                         XtPointer client_data,
303                         XtPointer call_data) ;
304 static void SaveDefaultOkCB(
305                         Widget w,
306                         XtPointer client_data,
307                         XtPointer call_data) ;
308 static void SaveSession(
309                         char *path) ;
310 static int RestoreSession(
311                         char *path,
312                         int type_of_restore,
313                         char *directory) ;
314 static void GetPWD(
315                         char current_directory[]) ;
316 static void OpenDirectories(
317                         char *directory_set,
318                         char *type) ;
319 static Tt_callback_action ObserveTtNotice(
320                         Tt_message msg,
321                         Tt_pattern pat) ;
322 static void ViewSessionHandler(
323                         Tt_message msg);
324 static void ViewDirectoryHandler(
325                         Tt_message msg);
326 static void ViewHomeDirectoryHandler(
327                         Tt_message msg);
328 static void ViewToolsDirectoryHandler(
329                         Tt_message msg);
330 static void ExitHandler(
331                         Tt_message msg,
332                         XtPointer clientData,
333                         String * messageFields,
334                         int numFields);
335 static void ReloadDatabases( void );
336 static void ViewAccept(
337                         View *view,
338                         Tt_message msg);
339 static void LoadViews (
340                         int num_views,
341                         XrmDatabase db,
342                         char *host_name,
343                         char *directory_name,
344                         char *type,
345                         Tt_message msg);
346 static void RemoveTextFields (
347                         XtPointer client_data,
348                         DialogData * old_dialog_data,
349                         DialogData * new_dialog_data) ;
350 static void DtfileCvtStringToObjPlace (
351                         XrmValue *args,
352                         Cardinal numArgs,
353                         XrmValue *fromVal,
354                         XrmValue *toVal) ;
355 static unsigned char *_DtNextToken (
356                         unsigned char *pchIn,
357                         int *pLen,
358                         unsigned char **ppchNext) ;
359 static void DtfileCvtStringToOpenDir (
360                         XrmValue *args,
361                         Cardinal numArgs,
362                         XrmValue *fromVal,
363                         XrmValue *toVal) ;
364 static void DtfileCvtStringToDTIcon (
365                         XrmValue *args,
366                         Cardinal numArgs,
367                         XrmValue *fromVal,
368                         XrmValue *toVal) ;
369 static void DtfileCvtStringToTree (
370                         XrmValue *args,
371                         Cardinal numArgs,
372                         XrmValue *fromVal,
373                         XrmValue *toVal) ;
374 static void DtfileCvtStringToTreeFiles (
375                         XrmValue *args,
376                         Cardinal numArgs,
377                         XrmValue *fromVal,
378                         XrmValue *toVal) ;
379 static void DtfileCvtStringToView (
380                         XrmValue *args,
381                         Cardinal numArgs,
382                         XrmValue *fromVal,
383                         XrmValue *toVal) ;
384 static void DtfileCvtStringToOrder (
385                         XrmValue *args,
386                         Cardinal numArgs,
387                         XrmValue *fromVal,
388                         XrmValue *toVal) ;
389 static void DtfileCvtStringToDirection (
390                         XrmValue *args,
391                         Cardinal numArgs,
392                         XrmValue *fromVal,
393                         XrmValue *toVal) ;
394 static void DtfileCvtStringToGrid (
395                         XrmValue *args,
396                         Cardinal numArgs,
397                         XrmValue *fromVal,
398                         XrmValue *toVal) ;
399 static void DtfileStringToTree(
400                         char *str,
401                         int *type) ;
402 static void DtfileStringToTreeFiles(
403                         char *str,
404                         int *type) ;
405 static void DtfileStringToView(
406                         char *str,
407                         int *type) ;
408 static void DtfileStringToOrder(
409                         char *str,
410                         int *type) ;
411 static void DtfileStringToDirection(
412                         char *str,
413                         int *type) ;
414 static void DtfileStringToGrid(
415                         char *str,
416                         int *type) ;
417 static void SetupSendRequestArgs(
418                         ApplicationArgs application_args,
419                         Tt_message msg) ;
420 static void BuildAndShowIconName(
421                         char *file_type_name,
422                         unsigned char view,
423                         unsigned char show_type,
424                         Widget widget) ;
425 static void MarqueeSelect (
426                         Widget w,
427                         int type,
428                         Position x,
429                         Position y,
430                         Dimension width,
431                         Dimension height,
432                         XtPointer client_data);
433 static void WaitForResponseAndExit( void ) ;
434 static void ExitApp(
435                         XtPointer clientData,
436                         String *words,
437                         int num_fields) ;
438 static Widget post_dialog(
439                         Widget parent,
440                         char *title,
441                         char *msg,
442                         void (*callback)());
443 static void DtErrExitCB(
444                         Widget widget,
445                         XtPointer client_data,
446                         XtPointer call_data);
447
448 /********    End Static Function Declarations    ********/
449
450 /*  debugging flag  */
451 #ifdef DEBUG
452 int debug = 0;
453 #endif
454
455 /*  performance flag  */
456 #ifdef DT_PERFORMANCE
457 int perform = 0;
458 #endif
459
460 /*  The id's of the dialogs registered by main  */
461
462 int file_mgr_dialog;
463 int change_dir_dialog;
464 int preferences_dialog;
465 int filter_dialog;
466 int find_dialog;
467 int mod_attr_dialog;
468 int help_dialog;
469
470 /* The shared menu button and pane Id's */
471
472 Widget * create_dataBtn;
473 Widget * renameBtn;
474 Widget * moveBtn;
475 Widget * duplicateBtn;
476 Widget * linkBtn;
477 Widget * findBtn;
478 Widget * create_directoryBtn;
479 Widget * change_directoryBtn;
480 Widget * showHiddenMenu;
481 Widget * preferencesBtn;
482 Widget * filterBtn;
483 Widget * defaultEnvBtn;
484 Widget * homeBarBtn;
485 Widget * upBarBtn;
486 Widget * newViewBtn;
487 Widget * cleanUpBtn;
488 Widget * separator1;
489 Widget * separator2;
490 Widget * terminalBtn;
491 Widget * usingHelp = NULL;
492 Widget * fileManagerHelp = NULL;
493 Widget * applicationManagerHelp = NULL;
494 Widget * usingHelpTrash = NULL;
495
496
497 /* Bitmask used to indicate the current sensitivity state of shared menu btns */
498
499 unsigned int currentMenuStates = ( RENAME | MOVE | DUPLICATE | LINK | TRASH |
500                                  MODIFY | CHANGEDIR | PREFERENCES | FILTER |
501                                  FIND | CREATE_DIR | CREATE_FILE |
502                                  PUT_ON_DESKTOP | PUTBACK |
503                                  CLEAN_UP | MOVE_UP |
504                                  HOME | CHANGE_DIR | TERMINAL);
505
506 /* Drag manager globals */
507 Boolean b1Drag;
508 Boolean dragActive = False;
509
510 /* Desktop Globals */
511 int numColumns;
512 int numRows;
513
514 /*  Globally referenced application name.  Set to argv[0] in main  */
515
516 char * application_name = NULL;
517
518
519 /*  uid for root user; used when we are checking access permissions  */
520
521 long root_user = -1;
522
523
524 /*  Home host name  */
525
526 char home_host_name[MAX_PATH];
527 char users_home_dir[MAX_PATH];
528
529
530 /*  Toolbox directory  */
531
532 char * desktop_dir = NULL;
533 char * trash_dir = NULL;
534 char * remote_sys_dir = NULL;
535
536 /* Restor type */
537
538 int restoreType = NORMAL_RESTORE;
539
540
541 /*  Black and White pixels  */
542
543 Pixel black_pixel;
544 Pixel white_pixel;
545
546
547 /*  File manager view set before a new view is created and   */
548 /*  used to propagate visual attributes from the initiating  */
549 /*  view to the new view.                                    */
550
551 XtPointer initiating_view = NULL;
552 Boolean special_view = False;
553 Boolean TrashView = False;
554
555
556 /*  system wide user font  */
557
558 XmFontList user_font;
559
560
561 /* Global localizable strings */
562
563 String openInPlace;
564 String openNewView;
565
566
567 /* Global dialog button labels, as XmStrings */
568
569 XmString okXmString;
570 XmString cancelXmString;
571 XmString helpXmString;
572 XmString applyXmString;
573 XmString closeXmString;
574
575
576 /* Global top level widget  */
577
578 Widget toplevel;
579
580 /* Global Application resources */
581 Boolean showFilesystem;
582 Boolean showDropZone;
583 Boolean showEmptySet;
584 Boolean showEmptyMsg;
585 Boolean restrictMode;
586 int openDirType;
587 char *root_title;
588 char *fileMgrTitle;
589 char *fileMgrHelpVol;
590 int desktopIconType;
591 int rereadTime;
592 int checkBrokenLink;
593 int trashWait;
594 int desktopPlacement;
595 Boolean freezeOnConfig;
596 #if defined(__hpux) || defined(sun)
597 Boolean follow_links;
598 #endif
599 int treeType;
600 int treeFiles;
601 int viewType;
602 int orderType;
603 int directionType;
604 int randomType;
605 int instanceWidth;
606 int instanceHeight;
607 unsigned char keybdFocusPolicy;
608 int special_treeType;
609 int special_treeFiles;
610 int special_viewType;
611 int special_orderType;
612 int special_directionType;
613 int special_randomType;
614 char *special_restricted;
615 char *special_title;
616 char *special_helpVol;
617 char *fileMgrIcon;
618 char *appMgrIcon;
619 char *trashIcon;
620 int retryLoadDesktopInfo;
621
622 int smallIconWidth;
623 int smallIconHeight;
624 int largeIconWidth;
625 int largeIconHeight;
626
627 Boolean emptyTrashOnExit;
628
629 #ifdef SHAPE
630 Boolean shapeExtension;
631 #endif
632
633 /* Drag state variables */
634 Boolean B1DragPossible = False;
635 Boolean B2DragPossible = False;
636 Boolean ProcessBtnUp = False;
637 Boolean ProcessBtnUpCD = True;
638 int initialDragX;
639 int initialDragY;
640 int dragThreshold;
641 int xErrorDetected = False;
642
643 /* BMenu button binding */
644 int bMenuButton;
645
646 View ** view_set = NULL;
647 int view_count = 0;
648 int view_set_size = 0;
649
650 /*  Globals used within this file.  */
651
652 static Display * display;
653 char * dt_path = NULL;
654 static Boolean message_display_enabled = True;
655
656
657 static Atom save_yourself_atom;
658 static Atom command_atom;
659 static Atom wm_state_atom;
660 static Atom save_mode;
661
662 /*  Structure used on a save session to see if a dt is iconic  */
663
664 typedef struct
665 {
666    int state;
667    Window icon;
668 } WM_STATE;
669
670
671 /*  Application resource list definition  */
672
673 static XrmOptionDescRec option_list[] =
674 {
675    {  "-noview",            "noView",          XrmoptionIsArg,   NULL  },
676    {  "-session",           "session",         XrmoptionSepArg,  NULL  },
677    {  "-dir",               "folder",          XrmoptionSepArg,  NULL  },
678    {  "-folder",            "folder",          XrmoptionSepArg,  NULL  },
679    {  "-tree",              "treeView",        XrmoptionSepArg,  NULL  },
680    {  "-tree_files",        "treeFiles",       XrmoptionSepArg,  NULL  },
681    {  VIEW_HEADER,          "view",            XrmoptionSepArg,  NULL  },
682    {  "-order",             "order",           XrmoptionSepArg,  NULL  },
683    {  "-direction",         "direction",       XrmoptionSepArg,  NULL  },
684    {  "-grid",              "grid",            XrmoptionSepArg,  NULL  },
685    {  RESTRICTED_HEADER,    "restricted",      XrmoptionIsArg,   NULL  },
686    {  "-title",             "title",           XrmoptionSepArg,  NULL  },
687    {  "-help_volume",       "help_volume",     XrmoptionSepArg,  NULL  },
688    {  "-noprompt",          "promptUser",      XrmoptionNoArg,  "False"  },
689    {  "-small_icon_width",  "smallIconWidth",  XrmoptionSepArg,  NULL  },
690    {  "-small_icon_height", "smallIconHeight", XrmoptionSepArg,  NULL  },
691    {  "-large_icon_width",  "largeIconWidth",  XrmoptionSepArg,  NULL  },
692    {  "-large_icon_height", "largeIconHeight", XrmoptionSepArg,  NULL  },
693 };
694
695
696 static XtResource resources[] =
697 {
698    {
699      "noView", "NoView", XmRString, sizeof (char *),
700      XtOffset (ApplicationArgsPtr, no_view), XmRImmediate, (XtPointer) NULL,
701    },
702
703    {
704      "session", "Session", XmRString, sizeof (char *),
705      XtOffset (ApplicationArgsPtr, session), XmRImmediate, (XtPointer) NULL,
706    },
707
708    {
709      "folder", "Folder", XmRString, sizeof (char *),
710      XtOffset (ApplicationArgsPtr, directories), XmRImmediate, (XtPointer) NULL,
711    },
712
713    {
714      "treeView", "TreeView", "Tree", sizeof (int),
715      XtOffset (ApplicationArgsPtr, tree_view), XmRImmediate,
716      (XtPointer) UNSET_VALUE,
717    },
718
719    {
720      "treeFiles", "TreeFiles", "TreeFiles", sizeof (int),
721      XtOffset (ApplicationArgsPtr, tree_files), XmRImmediate,
722      (XtPointer) UNSET_VALUE,
723    },
724
725    {
726      "view", "View", "View", sizeof (int),
727      XtOffset (ApplicationArgsPtr, view), XmRImmediate, (XtPointer) UNSET_VALUE,
728    },
729
730    {
731      "order", "Order", "Order", sizeof (int),
732      XtOffset (ApplicationArgsPtr, order), XmRImmediate, (XtPointer) UNSET_VALUE,
733    },
734
735    {
736      "direction", "Direction", "Direction", sizeof (int),
737      XtOffset (ApplicationArgsPtr, direction), XmRImmediate,
738      (XtPointer) UNSET_VALUE,
739    },
740
741    {
742      "grid", "Grid", "Grid", sizeof (int),
743      XtOffset (ApplicationArgsPtr, grid), XmRImmediate, (XtPointer) UNSET_VALUE,
744    },
745
746    {
747      "instanceIconWidth", "InstanceIconWidth", XmRInt, sizeof (int),
748      XtOffset (ApplicationArgsPtr, instanceIconWidth), XmRImmediate,
749      (XtPointer) 256,
750    },
751
752    {
753      "instanceIconHeight", "InstanceIconHeight", XmRInt, sizeof (int),
754      XtOffset (ApplicationArgsPtr, instanceIconHeight), XmRImmediate,
755      (XtPointer) 256,
756    },
757
758    {
759      "restricted", "Restricted", XmRString, sizeof (char *),
760      XtOffset (ApplicationArgsPtr, restricted), XmRImmediate, (XtPointer) NULL,
761    },
762
763    {
764      "title", "Title", XmRString, sizeof (char *),
765      XtOffset (ApplicationArgsPtr, title), XmRImmediate, (XtPointer)NULL,
766    },
767
768    {
769      "help_volume", "Help_volume", XmRString, sizeof (char *),
770      XtOffset (ApplicationArgsPtr, help_volume), XmRImmediate, (XtPointer)NULL,
771    },
772
773    {
774      "userFont", "XmCFontList", XmRFontList, sizeof (XmFontList),
775      XtOffset (ApplicationArgsPtr, user_font), XmRString, (XtPointer) "Fixed",
776    },
777
778    {
779      "toolWidth", "ToolWidth", XmRHorizontalDimension, sizeof (Dimension),
780      XtOffset (ApplicationArgsPtr, tool_width), XmRImmediate, (XtPointer) 700,
781    },
782
783    {
784      "toolHeight", "ToolHeight", XmRVerticalDimension, sizeof (Dimension),
785      XtOffset (ApplicationArgsPtr, tool_height), XmRImmediate, (XtPointer) 250,
786    },
787
788    {
789      "dirWidth", "DirWidth", XmRHorizontalDimension, sizeof (Dimension),
790      XtOffset (ApplicationArgsPtr, dir_width), XmRImmediate, (XtPointer) 555,
791    },
792
793    {
794      "dirHeight", "DirHeight", XmRVerticalDimension, sizeof (Dimension),
795      XtOffset (ApplicationArgsPtr, dir_height), XmRImmediate, (XtPointer) 400,
796    },
797
798    {
799      "promptUser", "PromptUser", XmRBoolean, sizeof (Boolean),
800      XtOffset (ApplicationArgsPtr, prompt_user), XmRImmediate, (XtPointer) True,
801    },
802
803    {
804      "rootTitle", "RootTitle", XmRString, sizeof (char *),
805      XtOffset (ApplicationArgsPtr, root_title), XmRImmediate, (XtPointer)"ROOT",
806    },
807
808    {
809      "moveThreshold", "MoveThreshold", XmRInt, sizeof (int),
810      XtOffset (ApplicationArgsPtr, dragThreshold), XmRImmediate, (XtPointer) 4,
811    },
812
813    {
814      "rereadTime", "RereadTime", XmRInt, sizeof (int),
815      XtOffset (ApplicationArgsPtr, rereadTime), XmRImmediate, (XtPointer) 3,
816    },
817
818    {
819      "checkBrokenLink", "CheckBrokenLink", XmRInt, sizeof (int),
820      XtOffset (ApplicationArgsPtr, checkBrokenLink), XmRImmediate,
821      (XtPointer) 180,
822    },
823
824    {
825      "maxDirectoryProcesses", "MaxDirectoryProcesses", XmRInt, sizeof (int),
826      XtOffset (ApplicationArgsPtr, maxDirectoryProcesses), XmRImmediate,
827      (XtPointer) 10,
828    },
829
830    {
831      "maxRereadProcesses", "MaxRereadProcesses", XmRInt, sizeof (int),
832      XtOffset (ApplicationArgsPtr, maxRereadProcesses), XmRImmediate,
833      (XtPointer) 5,
834    },
835
836    {
837      "maxRereadProcsPerTick", "MaxRereadProcsPerTick", XmRInt, sizeof (int),
838      XtOffset (ApplicationArgsPtr, maxRereadProcsPerTick), XmRImmediate,
839      (XtPointer) 1,
840    },
841
842    {
843      "trashWait", "TrashWait", XmRInt, sizeof (int),
844      XtOffset (ApplicationArgsPtr, trashWait), XmRImmediate, (XtPointer) 1,
845    },
846
847    {
848      "desktopIcon", "DesktopIcon", "DesktopIcon", sizeof (int),
849      XtOffset (ApplicationArgsPtr, desktopIconType), XmRImmediate,
850      (XtPointer)LARGE,
851    },
852
853    {
854      "showFilesystem", "ShowFilesystem", XmRBoolean, sizeof (Boolean),
855      XtOffset (ApplicationArgsPtr, showFilesystem), XmRImmediate,
856      (XtPointer)True,
857    },
858
859    {
860      "showDropZone", "ShowDropZone", XmRBoolean, sizeof (Boolean),
861      XtOffset (ApplicationArgsPtr, showDropZone), XmRImmediate,
862      (XtPointer)False,
863    },
864
865    {
866      "showEmptySet", "ShowEmptySet", XmRBoolean, sizeof (Boolean),
867      XtOffset (ApplicationArgsPtr, showEmptySet), XmRImmediate,
868      (XtPointer)False,
869    },
870
871    {
872      "showEmptyMsg", "ShowEmptyMsg", XmRBoolean, sizeof (Boolean),
873      XtOffset (ApplicationArgsPtr, showEmptyMsg), XmRImmediate,
874      (XtPointer)False,
875    },
876
877    {
878      "openFolder", "OpenFolder", "OpenFolder", sizeof (int),
879      XtOffset (ApplicationArgsPtr, openDirType), XmRImmediate,
880      (XtPointer)CURRENT,
881    },
882
883    {
884      "restrictMode", "RestrictMode", XmRBoolean, sizeof (Boolean),
885      XtOffset (ApplicationArgsPtr, restrictMode), XmRImmediate,
886      (XtPointer)False,
887    },
888
889    {
890      "objectPlacement", "ObjectPlacement", "ObjectPlacement", sizeof (int),
891      XtOffset (ApplicationArgsPtr, desktopPlacement), XmRImmediate,
892      (XtPointer)(OBJ_PLACE_TOP_PRIMARY | OBJ_PLACE_RIGHT_SECONDARY),
893    },
894
895    {
896      "freezeOnConfig", "FreezeOnConfig", XmRBoolean, sizeof (Boolean),
897      XtOffset (ApplicationArgsPtr, freezeOnConfig), XmRImmediate,
898      (XtPointer)True,
899    },
900
901    {
902      "fileManagerIcon", "FileManagerIcon", XmRString, sizeof (char *),
903      XtOffset (ApplicationArgsPtr, fileMgrIcon), XmRImmediate,
904      (XtPointer) HOME_ICON_NAME,
905    },
906
907    {
908      "appManagerIcon", "AppManagerIcon", XmRString, sizeof (char *),
909      XtOffset (ApplicationArgsPtr, appMgrIcon), XmRImmediate,
910      (XtPointer) TOOL_ICON_NAME,
911    },
912
913    {
914      "trashIcon", "TrashIcon", XmRString, sizeof (char *),
915      XtOffset (ApplicationArgsPtr, trashIcon), XmRImmediate,
916      (XtPointer) TRASH_ICON_NAME,
917    },
918
919    {
920      "retryLoadDesktop", "RetryLoadDesktop", XmRInt, sizeof (int),
921      XtOffset (ApplicationArgsPtr, retryLoadDesktop), XmRImmediate,
922      (XtPointer) 10,
923    },
924
925    {
926      "smallIconWidth", "SmallIconWidth", XmRInt, sizeof (int),
927      XtOffset (ApplicationArgsPtr, smallIconWidth), XmRImmediate,
928      (XtPointer) 24,
929    },
930
931    {
932      "smallIconHeight", "SmallIconHeight", XmRInt, sizeof (int),
933      XtOffset (ApplicationArgsPtr, smallIconHeight), XmRImmediate,
934      (XtPointer) 24,
935    },
936
937    {
938      "largeIconWidth", "LargeIconWidth", XmRInt, sizeof (int),
939      XtOffset (ApplicationArgsPtr, largeIconWidth), XmRImmediate,
940      (XtPointer) 38,
941    },
942
943    {
944      "largeIconHeight", "LargeIconHeight", XmRInt, sizeof (int),
945      XtOffset (ApplicationArgsPtr, largeIconHeight), XmRImmediate,
946      (XtPointer) 38,
947    },
948
949    {
950      "emptyTrashOnExit", "EmptyTrashOnExit", XmRBoolean, sizeof (Boolean),
951      XtOffset (ApplicationArgsPtr, emptyTrashOnExit), XmRImmediate,
952      (XtPointer)False,
953    },
954
955 #if defined(__hpux) || defined(sun)
956    { "followLinks", "FollowLinks", XmRBoolean, sizeof(Boolean),
957      XtOffset(ApplicationArgsPtr, follow_links), XmRImmediate,
958      (XtPointer) False,
959    },
960 #endif
961
962 };
963
964 XtActionsRec actionTable[] = {
965    {"Space", (XtActionProc)VFTextChangeSpace},
966    {"EscapeFM", (XtActionProc)CancelOut},
967 };
968
969 /************************************************************************
970  *
971  *  DT File
972  *      The main program for the file manager.
973  *
974  ************************************************************************/
975
976 extern XtInputId ProcessToolTalkInputId;
977
978 #if defined(__osf__) || defined(__OpenBSD__)
979 extern void sigchld_handler(int);
980 #endif /* __osf__ */
981
982 int
983 main(
984         int argc,
985         char **argv )
986 {
987 #ifdef DT_PERFORMANCE
988    struct timeval update_time_s;
989    struct timeval update_time_f;
990    struct timeval update_time_ss;
991    struct timeval update_time_fs;
992 #endif
993    struct passwd * pw;
994    char current_directory[MAX_PATH];
995    struct passwd * pwInfo;
996    char * homeDir;
997    XEvent event;
998    XtInputMask pending;
999    Boolean eventDebugging;
1000    int offset;
1001    int displayHeight;
1002    int displayWidth;
1003    Arg args[10];
1004    int n;
1005    char * tmpStr;
1006    XSetWindowAttributes sAttributes;
1007    Window root;
1008 #ifdef SHAPE
1009    int base1, base2;
1010 #endif
1011    XrmValue resource_value;
1012    XrmDatabase db;
1013    char *rep_type;
1014    char *string, *str;
1015    int i;
1016    int ttFd;    /* ToolTalk file descriptor */
1017    char *sessId;
1018    Tt_pattern events2Watch;
1019    Tt_pattern requests2Handle;
1020    Tt_message msg;
1021    Tt_status status;
1022 #if defined(__osf__) || defined(__OpenBSD__)
1023    struct sigaction sa, osa;
1024 #endif /* __osf__ */
1025    int session_flag = 0;
1026
1027 #ifdef DT_PERFORMANCE
1028    printf("  Start\n");
1029    gettimeofday(&update_time_ss, NULL);
1030 #endif
1031    (void) signal (SIGINT, (void (*)())Stop);
1032
1033    /* We don't want any zombie children, do we? */
1034 #if defined(__osf__) || defined(__OpenBSD__)
1035     sa.sa_handler = sigchld_handler;
1036     sigemptyset(&sa.sa_mask);
1037     sa.sa_flags   =  0;
1038
1039     if (sigaction(SIGCHLD, &sa, &osa) < 0)
1040     /* error handling follows, none for now */
1041         ;
1042 #else
1043    (void) signal (SIGCHLD, SIG_IGN);
1044 #endif /* __osf__ */
1045    XtSetLanguageProc( NULL, NULL, NULL );
1046
1047 #ifdef DT_PERFORMANCE
1048 { /* Initialize the checkpoint protocol  - Aloke Gupta */
1049 Display *display;
1050 display = XOpenDisplay("");
1051 _DtPerfChkpntInit(display, RootWindow(display, DefaultScreen(display)),
1052                     argv[0], True);
1053 }
1054 #endif
1055
1056
1057    _DtEnvControl(DT_ENV_SET);
1058
1059 #ifdef DT_PERFORMANCE
1060    printf("  XtInitalize\n");
1061    gettimeofday(&update_time_s, NULL);
1062
1063    /* Added by Aloke Gupta */
1064 _DtPerfChkpntMsgSend("Begin XtInitialize");
1065 #endif
1066
1067    /*  Initialize the toolkit and open the display  */
1068    toplevel = XtInitialize (argv[0], DTFILE_CLASS_NAME,
1069                             option_list, XtNumber(option_list),
1070                             (int *)&argc, argv);
1071
1072 /* MERGE START: May not need
1073 #ifdef __osf__
1074    _XmColorObjCreate ( toplevel, NULL, NULL );
1075 #endif
1076 */
1077
1078 #ifdef DT_PERFORMANCE
1079    gettimeofday(&update_time_f, NULL);
1080    if (update_time_s.tv_usec > update_time_f.tv_usec) {
1081       update_time_f.tv_usec += 1000000;
1082       update_time_f.tv_sec--;
1083    }
1084    printf("    done XtInitialize, time: %ld.%ld\n\n", update_time_f.tv_sec - update_time_s.tv_sec, update_time_f.tv_usec - update_time_s .tv_usec);
1085
1086    /* Added by Aloke Gupta */
1087    _DtPerfChkpntMsgSend("Done  XtInitialize");
1088 #endif
1089
1090    /* Initialize the function ptr for alphabetic sorting */
1091    FMStrcoll = GetStrcollProc();
1092
1093    /* Open the message catalog - DO NOT PERFORM until after XtInitialize! */
1094    {
1095       char * foo = ((char *)GETMESSAGE(18, 1, ""));
1096    }
1097
1098    /* set application name for later */
1099    str = strrchr(argv[0], '/');
1100    if(str != NULL)
1101       application_name = XtNewString (str + 1);
1102    else
1103       application_name = XtNewString (argv[0]);
1104
1105    n = 0;
1106    XtSetArg(args[n], XmNallowShellResize, True); n++;
1107    XtSetArg(args[n], XmNmappedWhenManaged, False); n++;
1108    XtSetArg(args[n], XmNheight, 1); n++;
1109    XtSetArg(args[n], XmNwidth, 1); n++;
1110    XtSetValues(toplevel, args, n);
1111    XtRealizeWidget(toplevel);
1112    display = XtDisplay (toplevel);
1113 #ifdef HAVE_EDITRES
1114     XtAddEventHandler(toplevel, 0, True,
1115                       (XtEventHandler) _XEditResCheckMessages,
1116                       (XtPointer) NULL);
1117 #endif
1118
1119    /* Initialize BMenu button binding */
1120    {
1121         int numMouseButtons = XGetPointerMapping(display,
1122                                         (unsigned char *)NULL, 0);
1123         bMenuButton = (numMouseButtons < 3) ? Button2 : Button3;
1124    }
1125
1126    /* initialize debugging flag */
1127 #ifdef DEBUG
1128    if ((tmpStr = getenv("DTFILE_DEBUG")) != NULL)
1129    {
1130       debug = atoi(tmpStr);
1131       if (debug <= 0)
1132          debug = 1;
1133    }
1134    if (getenv("DTFILE_XSYNC") != NULL)
1135    {
1136       XSynchronize(display, True);
1137    }
1138 #endif
1139
1140    /* initialize performance flag */
1141 #ifdef DT_PERFORMANCE
1142    if ((tmpStr = getenv("DTFILE_PERFORM")) != NULL)
1143    {
1144       perform = atoi(tmpStr);
1145       if (perform <= 0)
1146          perform = 1;
1147    }
1148    if (getenv("DTFILE_XSYNC") != NULL)
1149    {
1150       XSynchronize(display, True);
1151    }
1152 #endif
1153
1154    /*  Create the atom set used by save and restore session  */
1155    save_yourself_atom = XmInternAtom (display, "WM_SAVE_YOURSELF", False);
1156    wm_state_atom = XmInternAtom (display, "WM_STATE", False);
1157    command_atom = XA_WM_COMMAND;
1158    save_mode = XmInternAtom (display, _XA_DT_RESTORE_MODE, False);
1159
1160    root = RootWindowOfScreen(XtScreen(toplevel));
1161
1162    /* Set session property on the top level window */
1163    XmAddWMProtocols(toplevel, &save_yourself_atom, 1);
1164    XmAddWMProtocolCallback(toplevel, save_yourself_atom, SaveSessionCallback,
1165                            NULL);
1166
1167    XSetErrorHandler ((int (*)())ErrorHandler);
1168    XtAppSetErrorHandler (XtWidgetToApplicationContext(toplevel),
1169                          ToolkitErrorHandler);
1170
1171    /* get the keyboard focus policy so we know how we want to set up the */
1172    /*  Icon gadgets */
1173    XtSetArg(args[0], XmNkeyboardFocusPolicy, &keybdFocusPolicy);
1174    XtGetValues(toplevel, args, 1);
1175
1176    /*  If all of the command line parameters were not processed  */
1177    /*  out, print out a usage message set and exit.              */
1178
1179    if (argc != 1) Usage (argv);
1180
1181    displayWidth = DisplayWidth(display, DefaultScreen(display));
1182    displayHeight = DisplayHeight(display, DefaultScreen(display));
1183
1184    /*  Get Dt initialized  */
1185
1186    if (DtInitialize (display, toplevel, argv[0], FILE_MANAGER_TOOL_CLASS) == False)
1187    {
1188       /* Fatal Error: could not connect to the messaging system. */
1189       /* DtInitialize() has already logged an appropriate error msg */
1190       exit(-1);
1191    }
1192
1193 #ifdef DT_PERFORMANCE
1194    printf("  Setup Converters and get resources\n");
1195    gettimeofday(&update_time_s, NULL);
1196
1197    /* Added by Aloke Gupta */
1198    _DtPerfChkpntMsgSend("Begin Setup Converters");
1199
1200 #endif
1201
1202    /* First lets add the resource converters needed */
1203    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1204                        XtRString, "ObjectPlacement",
1205                        (XtConverter)DtfileCvtStringToObjPlace, NULL, 0);
1206    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1207                        XtRString, "OpenFolder",
1208                        (XtConverter)DtfileCvtStringToOpenDir, NULL, 0);
1209    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1210                        XtRString, "DesktopIcon",
1211                        (XtConverter)DtfileCvtStringToDTIcon, NULL, 0);
1212    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1213                        XtRString, "Tree",
1214                        (XtConverter)DtfileCvtStringToTree, NULL, 0);
1215    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1216                        XtRString, "TreeFiles",
1217                        (XtConverter)DtfileCvtStringToTreeFiles, NULL, 0);
1218    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1219                        XtRString, "View",
1220                        (XtConverter)DtfileCvtStringToView, NULL, 0);
1221    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1222                        XtRString, "Order",
1223                        (XtConverter)DtfileCvtStringToOrder, NULL, 0);
1224    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1225                        XtRString, "Direction",
1226                        (XtConverter)DtfileCvtStringToDirection, NULL, 0);
1227    XtAppAddConverter (XtWidgetToApplicationContext (toplevel),
1228                        XtRString, "Grid",
1229                        (XtConverter)DtfileCvtStringToGrid, NULL, 0);
1230
1231    /*  Get the application defined resources of session and  */
1232    /*  directory, and get the processes host.                */
1233
1234    XtGetApplicationResources(toplevel, &application_args,
1235                              resources, XtNumber(resources), NULL,0);
1236
1237 #ifdef DT_PERFORMANCE
1238    gettimeofday(&update_time_f, NULL);
1239    if (update_time_s.tv_usec > update_time_f.tv_usec) {
1240       update_time_f.tv_usec += 1000000;
1241       update_time_f.tv_sec--;
1242    }
1243    printf("    done Setting up Converters and got resources, time: %ld.%ld\n\n", update_time_f.tv_sec - update_time_s.tv_sec, update_time_f.tv_usec - update_time_s .tv_usec);
1244
1245    /* Added by Aloke Gupta */
1246    _DtPerfChkpntMsgSend("Done  Setup Converters");
1247 #endif
1248
1249 #ifdef DT_PERFORMANCE
1250    printf("  DtDbLoad\n");
1251    gettimeofday(&update_time_s, NULL);
1252    /* Added by Aloke Gupta */
1253    _DtPerfChkpntMsgSend("Begin DtDbLoad");
1254
1255 #endif
1256
1257    /*  Set up the messaging and file types  */
1258
1259    DtDbLoad();
1260 #ifdef DT_PERFORMANCE
1261    gettimeofday(&update_time_f, NULL);
1262    if (update_time_s.tv_usec > update_time_f.tv_usec) {
1263       update_time_f.tv_usec += 1000000;
1264       update_time_f.tv_sec--;
1265    }
1266    printf("    done DtDbLoad, time: %ld.%ld\n\n", update_time_f.tv_sec - update_time_s.tv_sec, update_time_f.tv_usec - update_time_s .tv_usec);
1267
1268    /* Added by Aloke Gupta */
1269    _DtPerfChkpntMsgSend("Done  DtDbLoad");
1270
1271 #endif
1272
1273
1274    /* Create some global strings */
1275    db = XtDatabase(display);
1276    if (XrmGetResource (db, "dttypes.defaultActions",
1277                        "Dttypes.DefaultActions", &rep_type,
1278                        &resource_value))
1279    {
1280      string = XtNewString(resource_value.addr);
1281      for(str = DtStrtok(string, ",") ,i = 0; str != NULL && i < 2 ;
1282      str = DtStrtok(NULL, ","), i++) {
1283        if(i == 0)
1284          openInPlace = XtNewString(str);
1285        else
1286          openNewView = XtNewString(str);
1287      }
1288      XtFree(string);
1289    }
1290    if(openInPlace == NULL || strlen(openInPlace) == 0)
1291        openInPlace = XtNewString("OpenInPlace");
1292    if(openNewView == NULL || strlen(openNewView) == 0)
1293        openNewView = XtNewString("OpenNewView");
1294
1295    DtGetShortHostname (home_host_name, MAX_PATH);
1296
1297    /*  Get the lock established to ensure only one dtfile process  */
1298    /*  is running.                                                  */
1299    if (_DtGetLock (display, DTFILE_CLASS_NAME) == 0)
1300    {
1301       status = InitializeToolTalkProcid( &ttFd, toplevel, False );
1302       if (TT_OK != status)
1303       {
1304           char *errfmt, *errmsg, *title, *statmsg;
1305           title = GETMESSAGE(21,38,"File Manager Error");
1306           errfmt = GETMESSAGE(18, 40,
1307                    "Could not connect to ToolTalk:\n%s\nExiting ...");
1308           statmsg = tt_status_message(status);
1309
1310           errmsg = XtMalloc(strlen(errfmt) + strlen(statmsg) + 2);
1311           fprintf(stderr, errfmt, statmsg);
1312           sprintf(errmsg, errfmt, statmsg);
1313
1314           /* put up error dialog and loop,
1315            * application will exit in dialog callback
1316            */
1317           post_dialog(toplevel, title, errmsg, DtErrExitCB); 
1318       }
1319
1320       if (application_args.session != NULL)
1321       {
1322          msg = tttk_message_create( 0, TT_REQUEST, TT_SESSION, 0,
1323                                     "DtFileSession_Run",
1324                                     (Tt_message_callback)ExitApp );
1325          tt_message_file_set( msg, application_args.session );
1326          tt_message_send( msg );
1327       }
1328       else if (application_args.directories != NULL)
1329       {
1330          msg = tttk_message_create( 0, TT_REQUEST, TT_SESSION, 0,
1331                                     "DtFolder_Show",
1332                                     (Tt_message_callback)ExitApp );
1333          tt_message_file_set( msg, application_args.directories );
1334          SetupSendRequestArgs( application_args, msg );
1335          tt_message_send( msg );
1336       }
1337       else
1338       {
1339          /* Default action: Open up pwd or home dir */
1340          GetPWD(current_directory);
1341
1342          if (current_directory[0] != '\0')
1343          {
1344             msg = tttk_message_create( 0, TT_REQUEST, TT_SESSION, 0,
1345                                        "DtFolder_Show",
1346                                        (Tt_message_callback)ExitApp );
1347             tt_message_file_set( msg, current_directory );
1348          }
1349          else
1350          {
1351             msg = tttk_message_create( 0, TT_REQUEST, TT_SESSION, 0,
1352                                        "DtHome_Show",
1353                                        (Tt_message_callback)ExitApp );
1354          }
1355          SetupSendRequestArgs( application_args, msg );
1356          tt_message_send( msg );
1357       }
1358       WaitForResponseAndExit();
1359    }
1360
1361    /*  Initialize the encapsulation mechanism and install the dialogs  */
1362    /*  used by the file manager.                                       */
1363
1364    _DtInitializeEncapsulation (display, argv[0], DTFILE_CLASS_NAME);
1365    topPositionOffset = -8;
1366
1367    status = InitializeToolTalkProcid( &ttFd, toplevel, True );
1368    if (TT_OK != status)
1369    {
1370        char *errfmt, *errmsg, *title, *statmsg;
1371        title = GETMESSAGE(21,38,"File Manager Error");
1372        errfmt = GETMESSAGE(18, 40,
1373                 "Could not connect to ToolTalk:\n%s\nExiting ...");
1374        statmsg = tt_status_message(status);
1375
1376        errmsg = XtMalloc(strlen(errfmt) + strlen(statmsg) + 2);
1377        fprintf(stderr, errfmt, statmsg);
1378        sprintf(errmsg, errfmt, statmsg);
1379
1380        /* put up error dialog and loop,
1381         * application will exit in dialog callback
1382         */
1383        post_dialog(toplevel, title, errmsg, DtErrExitCB); 
1384    }
1385
1386
1387 #ifdef DT_PERFORMANCE
1388    printf("  Setup Callbacks (messaging)\n");
1389    gettimeofday(&update_time_s, NULL);
1390
1391    /* Added by Aloke Gupta */
1392    _DtPerfChkpntMsgSend("Begin Setup Callbacks");
1393
1394 #endif
1395    events2Watch = tt_pattern_create();
1396    tt_pattern_category_set( events2Watch, TT_OBSERVE );
1397    tt_pattern_class_add( events2Watch, TT_NOTICE );
1398    tt_pattern_scope_add( events2Watch, TT_SESSION );
1399    sessId = tt_default_session();
1400    tt_pattern_session_add( events2Watch, sessId );
1401    tt_free( sessId );
1402    tt_pattern_op_add( events2Watch, "DtTypes_Reloaded" );
1403    tt_pattern_op_add( events2Watch, "XSession_Ending" );
1404    tt_pattern_callback_add( events2Watch, ObserveTtNotice );
1405    tt_pattern_register( events2Watch );
1406
1407    requests2Handle = tt_pattern_create();
1408    tt_pattern_category_set( requests2Handle, TT_HANDLE );
1409    tt_pattern_class_add( requests2Handle, TT_REQUEST );
1410    tt_pattern_scope_add( requests2Handle, TT_SESSION );
1411    sessId = tt_default_session();
1412    tt_pattern_session_add( requests2Handle, sessId );
1413    tt_free( sessId );
1414    tt_pattern_op_add( requests2Handle, "DtFileSession_Run" );
1415    tt_pattern_op_add( requests2Handle, "DtFolder_Show" );
1416    tt_pattern_op_add( requests2Handle, "DtHome_Show" );
1417    tt_pattern_op_add( requests2Handle, "DtTools_Show" );
1418    tt_pattern_op_add( requests2Handle, "DtTrash_Show" );
1419    tt_pattern_op_add( requests2Handle, "DtTrash_Remove" );
1420    tt_pattern_op_add( requests2Handle, "DtTrash_Empty" );
1421    tt_pattern_op_add( requests2Handle, "DtTrash_File" );
1422    tt_pattern_op_add( requests2Handle, "DtTrash_Restore" );
1423    tt_pattern_op_add( requests2Handle, "DtFile_PutOnWorkspace" );
1424    tt_pattern_op_add( requests2Handle, "DtFile_Move" );
1425    tt_pattern_op_add( requests2Handle, "DtFile_Copy" );
1426    tt_pattern_op_add( requests2Handle, "DtFile_Link" );
1427    tt_pattern_callback_add( requests2Handle, HandleTtRequest );
1428    tt_pattern_register( requests2Handle );
1429
1430    /* Setup the settings file if any to setup */
1431
1432    _DtWsmAddMarqueeSelectionCallback(toplevel,
1433                                      (DtWsmMarqueeSelectionProc) MarqueeSelect,
1434                                      NULL);
1435
1436 #ifdef DT_PERFORMANCE
1437    gettimeofday(&update_time_f, NULL);
1438    if (update_time_s.tv_usec > update_time_f.tv_usec) {
1439       update_time_f.tv_usec += 1000000;
1440       update_time_f.tv_sec--;
1441    }
1442    printf("    done Setting Callbacks (messaging), time: %ld.%ld\n\n", update_time_f.tv_sec - update_time_s.tv_sec, update_time_f.tv_usec - update_time_s .tv_usec);
1443
1444     /* Added by Aloke Gupta */
1445    _DtPerfChkpntMsgSend("Done  Setup Callbacks");
1446
1447 #endif
1448
1449    smallIconWidth = application_args.smallIconWidth;
1450    smallIconHeight = application_args.smallIconHeight;
1451    largeIconWidth = application_args.largeIconWidth;
1452    largeIconHeight = application_args.largeIconHeight;
1453    user_font = application_args.user_font;
1454    dragThreshold = application_args.dragThreshold;
1455    rereadTime = application_args.rereadTime;
1456    checkBrokenLink = application_args.checkBrokenLink;
1457    maxDirectoryProcesses = application_args.maxDirectoryProcesses;
1458    maxRereadProcesses = application_args.maxRereadProcesses;
1459    maxRereadProcsPerTick = application_args.maxRereadProcsPerTick;
1460    trashWait = application_args.trashWait;
1461    showFilesystem = application_args.showFilesystem;
1462    showDropZone = application_args.showDropZone;
1463    showEmptySet = application_args.showEmptySet;
1464    showEmptyMsg = application_args.showEmptyMsg;
1465    restrictMode = application_args.restrictMode;
1466    openDirType = application_args.openDirType;
1467    desktopIconType = application_args.desktopIconType;
1468    desktopPlacement = application_args.desktopPlacement;
1469    freezeOnConfig = application_args.freezeOnConfig;
1470    emptyTrashOnExit = application_args.emptyTrashOnExit;
1471 #if defined(__hpux) || defined(sun)
1472    follow_links = application_args.follow_links;
1473 #endif
1474    instanceWidth = application_args.instanceIconWidth;
1475    instanceHeight = application_args.instanceIconHeight;
1476    fileMgrIcon = application_args.fileMgrIcon;
1477    appMgrIcon = application_args.appMgrIcon;
1478    trashIcon = application_args.trashIcon;
1479    retryLoadDesktopInfo = application_args.retryLoadDesktop;
1480    if( application_args.directories != NULL
1481        || (strcmp (application_args.restricted, RESTRICTED_HEADER) == 0)
1482        || restrictMode )
1483    {
1484       special_view = True;
1485       if(strcmp (application_args.restricted, RESTRICTED_HEADER) == 0)
1486       {
1487          if(application_args.directories != NULL)
1488             special_restricted = XtNewString(application_args.directories);
1489          else
1490          {
1491             /* Get users pwd so we can set the restricted dir to it */
1492             GetPWD(current_directory);
1493
1494             if (current_directory[0] != '\0')
1495                special_restricted = XtNewString(current_directory);
1496             else
1497                special_restricted = XtNewString("~");
1498          }
1499       }
1500       else if( restrictMode )
1501          special_restricted = XtNewString("~");
1502       else
1503          special_restricted = NULL;
1504       special_treeType = treeType = application_args.tree_view;
1505       special_treeFiles = treeFiles = application_args.tree_files;
1506       special_viewType = viewType = application_args.view;
1507       special_orderType = orderType = application_args.order;
1508       special_directionType = directionType = application_args.direction;
1509       special_randomType = randomType = application_args.grid;
1510       special_title = XtNewString(application_args.title);
1511       if(application_args.help_volume == NULL)
1512       {
1513          special_helpVol = XtNewString(DTFILE_HELP_NAME);
1514          fileMgrHelpVol = XtNewString(DTFILE_HELP_NAME);
1515       }
1516       else
1517       {
1518          special_helpVol = XtNewString(application_args.help_volume);
1519          fileMgrHelpVol = XtNewString(application_args.help_volume);
1520       }
1521       fileMgrTitle = application_args.title;
1522    }
1523    else
1524    {
1525       special_view = False;
1526       treeType = application_args.tree_view;
1527       treeFiles = application_args.tree_files;
1528       viewType = application_args.view;
1529       orderType = application_args.order;
1530       directionType = application_args.direction;
1531       randomType = application_args.grid;
1532       fileMgrTitle = application_args.title;
1533       if(application_args.help_volume == NULL)
1534          fileMgrHelpVol = XtNewString(DTFILE_HELP_NAME);
1535       else
1536          fileMgrHelpVol = XtNewString(application_args.help_volume);
1537    }
1538
1539
1540    if(desktopIconType == LARGE)
1541    {
1542       numRows = displayHeight / PIXELS_PER_ROW_LARGE;
1543       numColumns = displayWidth / PIXELS_PER_COLUMN_LARGE;
1544    }
1545    else /* small */
1546    {
1547       numRows = displayHeight / PIXELS_PER_ROW_SMALL;
1548       numColumns = displayWidth / PIXELS_PER_COLUMN_SMALL;
1549    }
1550
1551 #ifdef SHAPE
1552    /* determine whether the Server has the shape extension */
1553    if(XShapeQueryExtension(display, &base1, &base2) == True)
1554       shapeExtension = True;
1555    else
1556       shapeExtension = False;
1557 #endif
1558
1559    /* get the name for the root directory */
1560    root_title = (char *)XtMalloc(strlen(application_args.root_title) + 1);
1561    strcpy(root_title, application_args.root_title);
1562
1563    if ((homeDir = getenv("HOME")) == NULL || strlen (homeDir) == 0)
1564    {
1565       pwInfo = getpwuid (getuid());
1566       homeDir = pwInfo->pw_dir;
1567    }
1568    strncpy(users_home_dir, homeDir, MAX_PATH - 1);
1569    if(restrictMode)
1570    {
1571       if(application_args.directories != NULL &&
1572                            strncmp(application_args.directories, "~", 1) != 0 )
1573       {
1574          if(strncmp(application_args.directories, users_home_dir,
1575                                                   strlen(users_home_dir)) != 0)
1576             RestrictModeUsage (argv);
1577       }
1578       else if (application_args.directories == NULL)
1579           application_args.directories = XtNewString("~");
1580    }
1581    if (strcmp(users_home_dir, "/") != 0)
1582       strcat(users_home_dir, "/");
1583
1584    XtAppAddActions(XtWidgetToApplicationContext (toplevel), actionTable, 2);
1585
1586    /* Create some global Xm strings for our dialog buttons */
1587
1588    okXmString = XmStringCreateLocalized((char*)_DtOkString);
1589    cancelXmString = XmStringCreateLocalized((char*)_DtCancelString);
1590    helpXmString = XmStringCreateLocalized((char*)_DtHelpString);
1591    applyXmString = XmStringCreateLocalized((char*)_DtApplyString);
1592    closeXmString = XmStringCreateLocalized((char*)_DtCloseString);
1593
1594    /*  Get the dt path created and initialized  */
1595
1596    dt_path = _DtCreateDtDirs (display);
1597
1598    if (dt_path == NULL)
1599    {
1600       Widget dialog;
1601       char *msg, *title;
1602       title = XtNewString((GETMESSAGE(21,38,"File Manager Error")));
1603       tmpStr = GETMESSAGE(18, 2, "Could not create the ~/.dt folder or sub folders.");
1604       msg = XtNewString(tmpStr);
1605
1606       /* put up error dialog and loop, application will exit in 
1607          dialog callback */
1608
1609       dialog = post_dialog(toplevel, title, msg, DtErrExitCB); 
1610       XtFree(msg);
1611       XtFree(title);
1612
1613       while (TRUE)
1614       {
1615         XtAppProcessEvent(XtWidgetToApplicationContext(dialog), XtIMAll );
1616       }
1617     }
1618
1619    /*  Set the black and white pixel globals.  */
1620
1621    black_pixel = BlackPixelOfScreen (XtScreen (toplevel));
1622    white_pixel = WhitePixelOfScreen (XtScreen (toplevel));
1623
1624    /*
1625     * Take over the drawing area's redisplay functions, so that we can get
1626     * the dtfile views to redraw according to stacking order, using our own
1627     * redraw function.
1628     */
1629    xmDrawingAreaWidgetClass->core_class.expose = DrawingAreaRedisplay;
1630
1631
1632    /* Get the root user id */
1633
1634    if ((pw = getpwnam("root")) == NULL)
1635       root_user = 0;          /* Assume root is uid 0 */
1636    else
1637       root_user = pw->pw_uid;
1638
1639
1640    file_mgr_dialog = _DtInstallDialog (fileMgrClass, True, True);
1641    change_dir_dialog = _DtInstallDialog (changeDirClass, True, True);
1642    preferences_dialog = _DtInstallDialog (preferencesClass, True, True);
1643    filter_dialog = _DtInstallDialog (filterClass, True, True);
1644    find_dialog = _DtInstallDialog (findClass, True, True);
1645    mod_attr_dialog = _DtInstallDialog (modAttrClass, True, True);
1646    help_dialog = _DtInstallDialog (helpClass, False, False);
1647
1648    if(special_view == True && special_restricted != NULL) {
1649       if(strncmp(special_restricted, "~", 1) == 0)
1650       {
1651          char *ptr, *ptr1;
1652
1653          special_restricted = _DtChangeTildeToHome(special_restricted);
1654          ptr = strrchr(special_restricted, '/');
1655          ptr1 = ptr + 1;
1656          if(ptr1[0] == '\0')
1657             *ptr = '\0';
1658       }
1659    }
1660
1661    /* Setup the settings file if any to setup */
1662    RestoreSettingsFile();
1663
1664 #ifdef DT_PERFORMANCE
1665    printf("  TrashCreateDialog\n");
1666    gettimeofday(&update_time_s, NULL);
1667
1668    /* Added by Aloke Gupta */
1669    _DtPerfChkpntMsgSend("Begin TrashCreateDialog");
1670
1671 #endif
1672    if( InitializeTrash( application_args.prompt_user ) )
1673
1674 #ifdef DEFER_TRASH_CREATION
1675 ;
1676 #else
1677      TrashCreateDialog (display);
1678 #endif
1679
1680 #ifdef DT_PERFORMANCE
1681    gettimeofday(&update_time_f, NULL);
1682    if (update_time_s.tv_usec > update_time_f.tv_usec) {
1683       update_time_f.tv_usec += 1000000;
1684       update_time_f.tv_sec--;
1685    }
1686    printf("    done TrashCreateDialog, time: %ld.%ld\n\n", update_time_f.tv_sec - update_time_s.tv_sec, update_time_f.tv_usec - update_time_s .tv_usec);
1687
1688    /* Added by Aloke Gupta */
1689    _DtPerfChkpntMsgSend("Done  TrashCreateDialog");
1690 #endif
1691
1692    /* lets go empty the trash if there is any */
1693 /*
1694    TrashEmpty();
1695 */
1696
1697 #ifdef DT_PERFORMANCE
1698    printf("  Setup Desktop\n");
1699    gettimeofday(&update_time_s, NULL);
1700    /* Added by Aloke Gupta */
1701    _DtPerfChkpntMsgSend("Begin Setup Desktop");
1702
1703 #endif
1704    /* go build 10 desktop windows */
1705    desktop_data = NULL;
1706    InitializeDesktopWindows(10, display);
1707    InitializeDesktopGrid();
1708
1709    LoadDesktopInfo(application_args.session);
1710
1711    /* Install WorkSpaceRemoved handler.
1712       This handler will be called when a workspace is being removed
1713       so File Manager can go through its desktop icons and clean up.
1714    */
1715    DtWsmAddWorkspaceModifiedCallback( toplevel, WorkSpaceRemoved, NULL );
1716
1717 #ifdef DT_PERFORMANCE
1718    gettimeofday(&update_time_f, NULL);
1719    if (update_time_s.tv_usec > update_time_f.tv_usec) {
1720       update_time_f.tv_usec += 1000000;
1721       update_time_f.tv_sec--;
1722    }
1723    printf("    done Setting up Desktop, time: %ld.%ld\n\n", update_time_f.tv_sec - update_time_s.tv_sec, update_time_f.tv_usec - update_time_s .tv_usec);
1724
1725    /* Added by Aloke Gupta */
1726    _DtPerfChkpntMsgSend("Done  Setup Desktop");
1727 #endif
1728
1729
1730    /*  Process the application resources to restore a session, dt  */
1731    /*  a directory set or display the users home directory.         */
1732
1733 #ifdef DT_PERFORMANCE
1734    printf("  Bring up View\n");
1735    gettimeofday(&update_time_s, NULL);
1736
1737    /* Added by Aloke Gupta */
1738    _DtPerfChkpntMsgSend("Begin Bring up View");
1739
1740 #endif
1741
1742    if (strcmp (application_args.no_view, "-noview") != 0)
1743    {
1744      if (application_args.session != NULL)
1745         session_flag =
1746           RestoreSession (application_args.session, NORMAL_RESTORE, NULL);
1747      else if (application_args.directories != NULL)
1748      {
1749         restoreType = CURRENT_DIR_RESTORE;
1750         OpenDirectories (application_args.directories, NULL);
1751      }
1752    }
1753
1754 #ifdef DT_PERFORMANCE
1755    gettimeofday(&update_time_f, NULL);
1756    if (update_time_s.tv_usec > update_time_f.tv_usec) {
1757       update_time_f.tv_usec += 1000000;
1758       update_time_f.tv_sec--;
1759    }
1760    printf("    done Bringing up view, time: %ld.%ld\n\n", update_time_f.tv_sec - update_time_s.tv_sec, update_time_f.tv_usec - update_time_s .tv_usec);  fflush(stdout);
1761
1762    /* Added by Aloke Gupta */
1763     _DtPerfChkpntMsgSend("Done  Bring up View");
1764 #endif
1765
1766
1767    /*  If no views were opened upon invocation, display the  */
1768    /*  current directory.                                    */
1769
1770    if ( (strcmp (application_args.no_view, "-noview") != 0) &&
1771         ((application_args.session == NULL) ||
1772          (session_flag != 0)) )
1773    {
1774       if (view_count == 0)
1775       {
1776          /* Get users pwd so we can create a fileviewer window of it */
1777          GetPWD(current_directory);
1778
1779          if (current_directory[0] != '\0')
1780          {
1781            if (!GetNewView (home_host_name, current_directory, NULL, NULL, 0))
1782               ViewHomeDirectoryHandler (0);
1783          }
1784          else
1785          {
1786            ViewHomeDirectoryHandler (0);
1787          }
1788       }
1789    }
1790
1791
1792    /*  Set up the timer based directory reading.      */
1793    InitializeDirectoryRead (toplevel);
1794
1795    /* Process and dispatch incoming events */
1796    eventDebugging = getenv("EVENT_DEBUGGING") != NULL;
1797
1798 #ifdef DT_PERFORMANCE
1799    printf("  InitializeToolTalkSession\n");
1800    gettimeofday(&update_time_s, NULL);
1801 #endif
1802    (void) InitializeToolTalkSession( toplevel, ttFd );
1803 #ifdef DT_PERFORMANCE
1804    gettimeofday(&update_time_f, NULL);
1805    if (update_time_s.tv_usec > update_time_f.tv_usec) {
1806       update_time_f.tv_usec += 1000000;
1807       update_time_f.tv_sec--;
1808    }
1809    printf("    done InitializeToolTalkSession, time: %ld.%ld\n\n", update_time_f.tv_sec - update_time_s.tv_sec, update_time_f.tv_usec - update_time_s .tv_usec);
1810 #endif
1811
1812  #ifdef DT_PERFORMANCE
1813    gettimeofday(&update_time_fs, NULL);
1814    if (update_time_ss.tv_usec > update_time_fs.tv_usec) {
1815       update_time_fs.tv_usec += 1000000;
1816       update_time_fs.tv_sec--;
1817    }
1818    printf("    Finish, time: %ld.%ld\n\n", update_time_fs.tv_sec - update_time_ss.tv_sec, update_time_fs.tv_usec - update_time_ss .tv_usec);
1819 #endif
1820
1821    while (1)
1822    {
1823       XtNextEvent(&event);
1824
1825       if (event.type != 0)
1826          XtDispatchEvent(&event);
1827    }
1828
1829    return EXIT_SUCCESS;
1830 }
1831
1832
1833
1834 /************************************************************************
1835  *
1836  *  ErrorHandler
1837  *
1838  ************************************************************************/
1839
1840 static void
1841 ErrorHandler(
1842         Display *disp,
1843         XErrorEvent *event )
1844 {
1845   #define _DTFILE_BUFSIZE 1024
1846   char errmsg[_DTFILE_BUFSIZE];
1847
1848   _DtPrintDefaultErrorSafe (disp, event, errmsg, _DTFILE_BUFSIZE);
1849   _DtSimpleError(application_name, DtWarning, NULL, errmsg, NULL);
1850   xErrorDetected = True;
1851
1852   /* We do not want to exit here lets try to continue... */
1853
1854 }
1855
1856 static void
1857 ToolkitErrorHandler(
1858         char *message )
1859 {
1860     char * msg;
1861     char * tmpStr;
1862
1863     tmpStr = GETMESSAGE(18, 6, "An X Toolkit error occurred... Exiting.\n");
1864     msg = (char *)malloc(strlen(tmpStr) + strlen(message) + 3);
1865     strcpy(msg, message);
1866     strcat(msg, "\n");
1867     strcat(msg, tmpStr);
1868     _DtSimpleError (application_name, DtError, NULL, msg);
1869     printf ("%s",msg);
1870     XtFree(msg);
1871     FinalizeToolTalkSession( );
1872     exit (1);
1873 }
1874
1875
1876
1877
1878 /************************************************************************
1879  *
1880  *  Usage
1881  *      When incorrect parameters have been specified on the command
1882  *      line, print out a set of messages detailing the correct use
1883  *      and exit.
1884  *
1885  ************************************************************************/
1886
1887 static void
1888 Usage(
1889         char **argv )
1890 {
1891    char * template;
1892    char * message_string1 = "\nUsage: %s...\n\n"
1893                          "   -noview\n\n\t"
1894                          "Dtfile runs in server mode.\n\n"
1895                          "   -session SessionFile\n\n\t"
1896                          "Dtfile runs with the session file specified in the SessionFile\n\t"
1897                          "parameter.\n\n"
1898                          "   -folder Folder[,Folder,Folder]\n"
1899                          "   -dir Folder[,Folder,Folder]\n\n\t"
1900                          "Dtfile displays a window for each folder specified in the\n\t"
1901                          "Folder parameter.  The Folder parameter may contain many\n\t"
1902                          "folders separated by commas.  Folders may be in the form\n\t"
1903                          "'path'.\n\n"
1904                          "   -title Title\n\n\t"
1905                          "Dtfile uses the string specified in the Title parameter as the\n\t"
1906                          "title for its windows.\n\n"
1907                          "   -help_volume HelpVolume\n\n\t"
1908                          "Dtfile uses the help volume specified in the HelpVolume parameter.\n\n"
1909                          "   -restricted\n\n\t"
1910                          "Dtfile will not display folders above the restricted folder.\n\t"
1911                          "If the -dir option is used, the folder specified in that option\n\t"
1912                          "is the restricted folder.  If the -dir option is not used, the\n\t"
1913                          "user's current folder is the restricted folder.\n\n"
1914                          "   -grid on/off\n\n\t"
1915                          "on     = Files are displayed in a grid pattern.\n\t"
1916                          "off    = Files are displayed as placed.\n\n"
1917                          "   -tree on/off\n\n\t"
1918                          "on     = Files are displayed in single folder mode.\n";
1919
1920    char * message_string2 = "\toff    = Files are displayed in folder tree mode.\n\n"
1921                          "   -tree_files never/always/choose\n\n\t"
1922                          "never  = Tree mode has two states: partially expanded or collapsed.\n\t"
1923                          "always = Tree mode has two states: fully expanded or collapsed.\n\t"
1924                          "choose = Tree mode has three states: partially expanded, fully\n\t"
1925                          "         expanded, or collapsed.\n\n"
1926                          "   -order alphabetical/file_type/date/size\n\n\t"
1927                          "Files are displayed in the specified order: alphabetical, by file\n\t"
1928                          "type, by date, or by size.\n\n"
1929                          "   -view no_icon/large_icon/small_icon/attributes\n\n\t"
1930                          "Files are displayed in the specified format: text only, text and\n\t"
1931                          "large icons, text and small icons, with attributes.\n\n"
1932                          "   -direction ascending/descending\n\n\t"
1933                          "Files are displayed in the specified direction: ascending or\n\t"
1934                          "descending.\n\n"
1935                          "   -large_icon_width  <size>\n\n"
1936                          "   -large_icon_height <size>\n\n"
1937                          "   -small_icon_width  <size>\n\n"
1938                          "   -small_icon_height <size>\n\n"
1939                          "        The display area size for the icon images in File Manager\n"
1940                          "        Icon images larger than this size will be clipped to this size\n"
1941                          "        The default display area size for large is 38 and small is 24\n\n"
1942                          "\n"
1943 ;
1944
1945    template = (GETMESSAGE(18,23, message_string1));
1946    fprintf (stderr, template, argv[0]);
1947    template = (GETMESSAGE(18,24, message_string2));
1948    fprintf (stderr, "%s", template);
1949
1950    exit (0);
1951 }
1952
1953 static void
1954 RestrictModeUsage(
1955         char **argv )
1956 {
1957    char * template;
1958    char * message_string = "\nRestricted Mode Usage: %s...\n\n"
1959                          "   -folder Folder[,Folder,Folder]\n"
1960                          "   -dir Folder[,Folder,Folder]\n\n\t"
1961                          "Where Folder is a Folder below and/or including\n\t"
1962                          "the user's Home Folder.\n\n";
1963
1964    template = (GETMESSAGE(18,26, message_string));
1965
1966    fprintf (stderr, template, argv[0]);
1967
1968    FinalizeToolTalkSession( );
1969    exit (0);
1970 }
1971
1972
1973
1974
1975 /************************************************************************
1976  *
1977  *  Stop
1978  *      Catches Ctrl C's and exits.
1979  *
1980  ************************************************************************/
1981
1982 static void
1983 Stop( void )
1984 {
1985   FinalizeToolTalkSession( );
1986   exit(0);
1987 }
1988
1989
1990
1991
1992
1993
1994
1995 /***********************************************************************
1996  *
1997  * RestoreSettingsFile
1998  *         Used to restore the save settings files from
1999  *         either $HOME/.dt/$DISPLAY/current or $HOME/.dt/$DISPLAY/home.
2000  *
2001  ***********************************************************************/
2002 static void
2003 RestoreSettingsFile( void )
2004 {
2005    int             status, fd;
2006    char            *dtPath=NULL;
2007    char            *homeSavePath=NULL;
2008    char            *homeHomePath=NULL;
2009    char            *toolSavePath=NULL;
2010    char            *toolHomePath=NULL;
2011    char            *dirName=NULL;
2012    Atom            actualType;
2013    int             actualFormat;
2014    unsigned long   nitems;
2015    unsigned long   leftover;
2016    unsigned char   *data = NULL;
2017
2018
2019   /* go get the dt path */
2020   /* _DtCreateDtDirs returs a path of MaxPath Length */
2021    dtPath = (char *)_DtCreateDtDirs(display);
2022
2023   /* Determin which type of session we are running HOME or CURRENT */
2024
2025   /* get the root window property of SaveMode */
2026   XGetWindowProperty(display, RootWindow(display,0),
2027                          save_mode, 0L, (long)BUFSIZ,False,
2028                          XA_STRING, &actualType,
2029                          &actualFormat,&nitems,&leftover,
2030                          &data);
2031
2032   if(strcmp((char *)data, "home") == 0)
2033     dirName = XtNewString("home");
2034   else if(strcmp((char *)data, "current") == 0)
2035     dirName = XtNewString("current");
2036   else
2037   {
2038     XtFree(dtPath);
2039     return;  /* we are comming up in a system mode (e.g. default) */
2040   }
2041
2042
2043   /* Build the paths to read the files from */
2044
2045   toolSavePath = (char *)XtMalloc(strlen(dtPath) +
2046                   strlen(TOOL_SETTINGS_FILENAME) +
2047                   strlen(dirName) + 4);
2048
2049   homeSavePath = (char *)XtMalloc(strlen(dtPath) +
2050                   strlen(HOME_SETTINGS_FILENAME) +
2051                   strlen(dirName) + 4);
2052
2053   sprintf( homeSavePath, "%s/%s/%s", dtPath, dirName, HOME_SETTINGS_FILENAME );
2054   sprintf( toolSavePath, "%s/%s/%s", dtPath, dirName, TOOL_SETTINGS_FILENAME );
2055
2056   /* open the home settings file to see if its there */
2057   if((fd = open(homeSavePath, O_RDONLY)) != -1)
2058   {
2059       close(fd);
2060      /* create where the saved file is going to go */
2061
2062       homeHomePath = (char *)XtMalloc(strlen(dtPath) +
2063                      strlen(HOME_SETTINGS_FILENAME) + 2);
2064
2065       sprintf( homeHomePath, "%s/%s", dtPath, HOME_SETTINGS_FILENAME );
2066
2067      /* remove any existing dtfile.home (e.g. HOME_SETTINGS_FILENAME) */
2068       unlink(homeHomePath);
2069
2070      /* copy the saved one into $HOME/.dt/$DISPLAY ... this is the one that
2071       * will be used by the dtfile
2072       */
2073       status = link(homeSavePath, homeHomePath);
2074       if(status != 0)
2075       {
2076         char *tmpStr, *msg;
2077
2078         tmpStr = GETMESSAGE(18,27, "Unable to recover the saved default home settings file, will use default.\n");
2079         msg = XtNewString(tmpStr);
2080         _DtSimpleErrnoError(application_name, DtWarning, NULL, msg, NULL);
2081         XtFree(msg);
2082       }
2083
2084    }
2085
2086  /* open the tool settings file to see if its there */
2087   if((fd = open(toolSavePath, O_RDONLY)) != -1)
2088   {
2089       close(fd);
2090      /* create where the saved file is going to go */
2091       toolHomePath = (char *)XtMalloc(strlen(dtPath) +
2092                      strlen(TOOL_SETTINGS_FILENAME) + 2);
2093
2094       sprintf( toolHomePath, "%s/%s", dtPath, TOOL_SETTINGS_FILENAME );
2095
2096      /* remove any existing dtfile.tool (e.g. TOOL_SETTINGS_FILENAME) */
2097       unlink(toolHomePath);
2098
2099      /* copy the saved one into $HOME/.dt/$DISPLAY ... this is the one that
2100       * will be used by the dtfile
2101       */
2102       status = link(toolSavePath, toolHomePath);
2103       if(status != 0)
2104       {
2105         char *tmpStr, *msg;
2106
2107         tmpStr = GETMESSAGE(18,28, "Unable to recover the saved default tool settings file, will use default.\n");
2108         msg = XtNewString(tmpStr);
2109         _DtSimpleErrnoError(application_name, DtWarning, NULL, msg, NULL);
2110         XtFree(msg);
2111       }
2112    }
2113
2114
2115   /* free up space */
2116    XFree(data);
2117    XtFree(dtPath);
2118    XtFree(dirName);
2119    XtFree(homeSavePath);
2120    XtFree(toolSavePath);
2121    XtFree(toolHomePath);
2122    XtFree(homeHomePath);
2123
2124
2125 }
2126
2127
2128
2129
2130
2131 /***********************************************************************
2132  *
2133  * MoveDefaultSettings
2134  *         Used to save the dtfile.tool and dtfile.home settings files to
2135  *         either $HOME/.dt/$DISPLAY/current or $HOME/.dt/$DISPLAY/home.
2136  *         The parameter mode determines whether it is home or
2137  *         current.
2138  *
2139  ***********************************************************************/
2140 static void
2141 MoveDefaultSettings(
2142         int mode )
2143 {
2144    int status;
2145    char *toolSavePath=NULL;
2146    char *homeSavePath=NULL;
2147    char *dirName=NULL;
2148    char *toolMovePath=NULL;
2149    char *homeMovePath=NULL;
2150    char *dtPath;
2151
2152    /* determine whether home or current */
2153    if(mode == HOME_DIR_RESTORE)
2154      dirName = XtNewString("home");
2155    else
2156      dirName = XtNewString("current");
2157
2158   /* go get the dt path */
2159   /* _DtCreateDtDirs returs a path of MaxPath Length */
2160   dtPath = (char *)_DtCreateDtDirs(display);
2161
2162
2163   /* Build the paths to save the files to */
2164
2165   toolSavePath = (char *)XtMalloc(strlen(dtPath) +
2166                   strlen(TOOL_SETTINGS_FILENAME) +
2167                   strlen(dirName) + 4);
2168
2169   homeSavePath = (char *)XtMalloc(strlen(dtPath) +
2170                   strlen(HOME_SETTINGS_FILENAME) +
2171                   strlen(dirName) + 4);
2172
2173
2174    /* create the directory and filename of where its going to be saved */
2175   sprintf( homeSavePath, "%s/%s/%s", dtPath, dirName, HOME_SETTINGS_FILENAME );
2176   sprintf( toolSavePath, "%s/%s/%s", dtPath, dirName, TOOL_SETTINGS_FILENAME );
2177
2178    /* Setup the paths used to GET the old files */
2179
2180    toolMovePath= (char *)XtMalloc(strlen(dtPath) +
2181                    strlen(TOOL_SETTINGS_FILENAME) + 3);
2182
2183    homeMovePath= (char *)XtMalloc(strlen(dtPath) +
2184                    strlen(HOME_SETTINGS_FILENAME) + 3);
2185
2186    /* create the filename of where its going to be saved from */
2187
2188    /* Tool File location */
2189    sprintf( toolMovePath, "%s/%s", dtPath, TOOL_SETTINGS_FILENAME );
2190
2191    /* Home File location */
2192    sprintf( homeMovePath, "%s/%s", dtPath, HOME_SETTINGS_FILENAME );
2193
2194
2195   /* get rid of the tool settings file that is already in home or current */
2196    status = unlink(toolSavePath);
2197
2198   /* get rid of the home settings file that is already in home or current */
2199    status = unlink(homeSavePath);
2200
2201
2202   /* now save tool settings file in home or current determined by savePath */
2203    status = link(toolMovePath, toolSavePath);
2204
2205   /* now save home settings file in home or current determined by savePath */
2206    status = link(homeMovePath, homeSavePath);
2207
2208    /* free up space */
2209    XtFree(homeMovePath);
2210    XtFree(toolMovePath);
2211    XtFree(homeSavePath);
2212    XtFree(toolSavePath);
2213    XtFree(dirName);
2214    XtFree(dtPath);
2215 }
2216
2217
2218 /************************************************************************
2219  *
2220  *  SaveSettingsCB
2221  *      Callback for the Save Settings menupick.
2222  *
2223  ************************************************************************/
2224 void
2225 SaveSettingsCB(
2226         Widget w,
2227         XtPointer client_data,
2228         XtPointer call_data )
2229 {
2230    Widget dlog;
2231    Widget mbar;
2232    Arg args[1];
2233    char * message;
2234    char * title;
2235    FileMgrRec * file_mgr_rec;
2236    DialogData * dialog_data;
2237    FileMgrData * file_mgr_data;
2238    char * tmpStr;
2239
2240    /* Strip the file_mgr_rec from the current widget
2241    * and attach it to the ok callback button
2242    */
2243
2244
2245    /* Get the file_mgr_rec hanging off the menubar */
2246    mbar = XmGetPostedFromWidget(XtParent(w));
2247    XmUpdateDisplay (w);
2248    XtSetArg(args[0], XmNuserData, &file_mgr_rec);
2249    XtGetValues(mbar, args, 1);
2250
2251
2252    /* Ignore accelerators when we're insensitive */
2253    if ((file_mgr_rec->menuStates & SETTINGS) == 0)
2254    {
2255      XSetInputFocus(XtDisplay(w),
2256                     XtWindow(file_mgr_rec->defaultEnvBtn_child),
2257                     RevertToParent, CurrentTime);
2258      return;
2259    }
2260
2261    /* Desensatize the save settings menu pick here */
2262    file_mgr_rec->menuStates &= ~SETTINGS;
2263
2264
2265    /* Get the file_mgr_rec dialog data info */
2266    if ((dialog_data = _DtGetInstanceData ((XtPointer)file_mgr_rec)) == NULL)
2267      return;
2268    file_mgr_data = (FileMgrData *) dialog_data->data;
2269
2270
2271    /* Based on the path we must determine if we are saving a Tools or
2272     * HomeDir dtfile view.
2273     */
2274    if (file_mgr_data->restricted_directory != NULL && file_mgr_data->toolbox)
2275      file_mgr_data->restoreKind = TOOL_RESTORE;
2276    else
2277      file_mgr_data->restoreKind = HOME_RESTORE;
2278
2279
2280    /* Setup and call the _DtMessageDialog procedure to post the dialog */
2281
2282    if (file_mgr_data->restoreKind == HOME_RESTORE)
2283    {
2284      tmpStr = (GETMESSAGE(18,29, "Save the current File Manager View window size,\npreferences, and filter settings?\n\nThey will be used for any new File Manager View windows\nstarted from the Front Panel."));
2285    }
2286    else
2287    {
2288      tmpStr = (GETMESSAGE(18,35, "Save the current Application Manager\nView window size, preferences, and filter settings?\n\nThey will be used for any new Application Manager\nwindows started from the Front Panel."));
2289    }
2290    message = XtNewString(tmpStr);
2291
2292    if(file_mgr_data->title != NULL &&
2293                strcmp(file_mgr_data->helpVol, DTFILE_HELP_NAME) != 0)
2294    {
2295       tmpStr = GETMESSAGE(18, 16, "Save As Default Options");
2296       title = (char *)XtMalloc(strlen(tmpStr) +
2297                                  strlen(file_mgr_data->title) + 5);
2298       sprintf(title, "%s - %s", file_mgr_data->title, tmpStr);
2299    }
2300    else
2301    {
2302       tmpStr = GETMESSAGE(18, 32, "File Manager - Save As Default Options");
2303       title = XtNewString(tmpStr);
2304    }
2305    dlog = (Widget)_DtMessageDialog(mbar, title, message, NULL, TRUE,
2306                                    SaveDefaultCancelCB, SaveDefaultOkCB, NULL,
2307                                    HelpRequestCB, False, QUESTION_DIALOG);
2308    file_mgr_rec->defaultEnvBtn_child=dlog;
2309    XtFree (message);
2310    XtFree (title);
2311
2312
2313    /* Add array as userdata on the dialog. */
2314
2315    XtSetArg(args[0], XmNuserData, file_mgr_rec);
2316    XtSetValues(dlog, args, 1);
2317
2318 }
2319
2320 /************************************************************************
2321  *
2322  *  SaveDefaultCancelCB
2323  *      Cleanup and unmanage the save settings dialog.
2324  *
2325  ************************************************************************/
2326 static void
2327 SaveDefaultCancelCB(
2328         Widget w,
2329         XtPointer client_data,
2330         XtPointer call_data )
2331 {
2332   FileMgrRec * file_mgr_rec;
2333   Arg args[1];
2334
2335     /* Update the display, and un-post the dialog */
2336     XtUnmanageChild((Widget)client_data);
2337     XmUpdateDisplay((Widget)client_data);
2338     XtSetArg(args[0], XmNuserData, &file_mgr_rec);
2339     XtGetValues((Widget)client_data, args, 1);
2340
2341
2342     /* Re-sensatize the save settings menu pick */
2343     file_mgr_rec->menuStates |= SETTINGS;
2344
2345
2346     XtDestroyWidget((Widget)client_data);
2347
2348 }
2349
2350
2351 /************************************************************************
2352  *
2353  *  SaveDefaultOkCB
2354  *      Save the current dtfile view as the default environment for
2355  *      new dtfiles created.
2356  *
2357  ************************************************************************/
2358 static void
2359 SaveDefaultOkCB(
2360         Widget w,
2361         XtPointer client_data,
2362         XtPointer call_data )
2363 {
2364
2365    FileMgrRec * file_mgr_rec;
2366    static char * name_list[] = { DTFILE_CLASS_NAME, NULL, NULL };
2367    char view_number[5];
2368    int fd;
2369    Arg args[1];
2370
2371    DialogData * dialog_data;
2372    FileMgrData * file_mgr_data;
2373    char * msg;
2374    char * tmp_path;
2375    char full_path[MAX_PATH + 1];
2376    char * tmpStr;
2377    char * save_host;
2378    char * save_directory;
2379    char ** save_branch_list;
2380    FileViewData ** save_selection_list;
2381    int save_selected_file_count;
2382
2383
2384    /* Get the file_mgr_rec hanging off the dialog */
2385    XtUnmanageChild((Widget)client_data);
2386    XmUpdateDisplay ((Widget)client_data);
2387    XtSetArg(args[0], XmNuserData, &file_mgr_rec);
2388    XtGetValues((Widget)client_data, args, 1);
2389
2390
2391    /* Re-sensatize the save settings menu pick */
2392    file_mgr_rec->menuStates |= SETTINGS;
2393
2394
2395    /* Get the file_mgr_rec dialog data info */
2396
2397    dialog_data = _DtGetInstanceData ((XtPointer)file_mgr_rec);
2398    file_mgr_data = (FileMgrData *) dialog_data->data;
2399
2400
2401    /* Build the path for our env file */
2402
2403    tmp_path = _DtCreateDtDirs(display);
2404    if (tmp_path == NULL)
2405      {
2406        XtDestroyWidget(client_data);
2407        return;
2408      }
2409
2410
2411    /* Look and see what type of restore we are doing */
2412    if (file_mgr_data->restoreKind == TOOL_RESTORE)
2413    {
2414       sprintf(full_path, "%s/%s", tmp_path, TOOL_SETTINGS_FILENAME);
2415       application_args.tool_width = file_mgr_data->width;
2416       application_args.tool_height = file_mgr_data->height;
2417    }
2418    else
2419    {
2420       sprintf(full_path, "%s/%s", tmp_path, HOME_SETTINGS_FILENAME);
2421       application_args.dir_width = file_mgr_data->width;
2422       application_args.dir_height = file_mgr_data->height;
2423    }
2424
2425    XtFree(tmp_path);
2426
2427
2428    /*  Create the Environment session file  */
2429
2430    if ((fd = creat(full_path, S_IRUSR | S_IRGRP | S_IWUSR | S_IWGRP)) == -1)
2431    {
2432       char *title;
2433       tmpStr = GETMESSAGE(18, 17, "Unable to create a file to store the default options.");
2434       title = XtNewString((GETMESSAGE(21,38,"Object Create Error")));
2435       msg = XtNewString(tmpStr);
2436       _DtMessage (toplevel, title, msg, NULL, HelpRequestCB);
2437       XtFree(msg);
2438       XtFree(title);
2439       return;
2440    }
2441
2442
2443    /*  Write out the general information  */
2444
2445    (void) write (fd, "*", strlen ("*"));
2446    (void) write (fd, DTFILE_CLASS_NAME,strlen (DTFILE_CLASS_NAME));
2447    (void) write (fd, "*view_count:      ", strlen ("*view_count:      "));
2448
2449    (void) sprintf (view_number, "%d", 1);
2450    (void) write (fd, view_number, strlen (view_number));
2451    (void) write (fd, "\n#\n", strlen ("\n#\n"));
2452
2453    name_list[1] = view_number;
2454
2455    /* Temporarily remove data that we don't need or want saved */
2456
2457    save_host = file_mgr_data->host;
2458    save_directory = file_mgr_data->current_directory;
2459    save_branch_list = file_mgr_data->branch_list;
2460    save_selection_list = file_mgr_data->selection_list;
2461    save_selected_file_count = file_mgr_data->selected_file_count;
2462    file_mgr_data->host = NULL;
2463    file_mgr_data->current_directory = NULL;
2464    file_mgr_data->branch_list = NULL;
2465    file_mgr_data->selection_list = NULL;
2466    file_mgr_data->selected_file_count = 0;
2467
2468    /*  Call the encapsulation mechanism to write each dialog  */
2469
2470    (void) sprintf (view_number, "%d", 0);
2471    _DtWriteDialogData (dialog_data, fd, name_list);
2472    (void) write (fd, "#\n", strlen ("#\n"));
2473
2474    /* Restore the data that was temporarily removed */
2475
2476    file_mgr_data->host = save_host;
2477    file_mgr_data->current_directory = save_directory;
2478    file_mgr_data->branch_list = save_branch_list;
2479    file_mgr_data->selection_list = save_selection_list;
2480    file_mgr_data->selected_file_count = save_selected_file_count;
2481
2482    (void) close (fd);
2483
2484    XtDestroyWidget(client_data);
2485
2486 }
2487
2488
2489
2490 /************************************************************************
2491  *
2492  *  SaveSessionCallback
2493  *      Get the session name and call the function to save the session.
2494  *
2495  ************************************************************************/
2496
2497 void
2498 SaveSessionCallback(
2499         Widget w,
2500         XtPointer client_data,
2501         XtPointer call_data )
2502 {
2503    char * full_path=NULL;
2504    char * file_name=NULL;
2505    char * strPtr;
2506    int restore=NORMAL_RESTORE;
2507    Boolean status=FALSE;
2508    char * sessionFileName;
2509    char ** argv;
2510
2511    if(view_count == 0 && desktop_data->numIconsUsed == 0)
2512    {
2513       XChangeProperty (display, XtWindow (toplevel), command_atom,
2514                     XA_STRING, 8, PropModeReplace, (unsigned char *)NULL, 0);
2515       XSync(display, False);
2516       FinalizeToolTalkSession( );
2517       exit(0);
2518    }
2519
2520    status = DtSessionSavePath(w, &full_path, &file_name);
2521
2522    if (status)
2523      sessionFileName = file_name;
2524    else
2525    {
2526      XtFree( (char *)full_path);
2527      full_path = (char *) XtMalloc (sizeof (char) * MAX_PATH);
2528      sprintf( full_path, "%s/%s", dt_path, DTFILE_CLASS_NAME );
2529      sessionFileName = full_path;
2530    }
2531    SaveSession( full_path );
2532
2533    /* skip to the /.dt/ portion of the sessionFileName */
2534    strPtr = strstr(full_path, "/.dt/");
2535    (void)strcpy(full_path, strPtr);
2536
2537    /* Save off the settings files for both tool and home views */
2538    do {
2539         strPtr = DtStrrchr(full_path, '/');
2540         if ( !strPtr )
2541            continue;
2542         if ((strncmp(strPtr, "/home", 5) == 0))
2543            restore = HOME_DIR_RESTORE;
2544         else if ((strncmp(strPtr, "/current", 8) == 0))
2545            restore = CURRENT_DIR_RESTORE;
2546
2547         if (strPtr != NULL)
2548           *strPtr = '\0';
2549    } while ((strPtr != NULL) && (restore == NORMAL_RESTORE));
2550
2551    SaveDesktopInfo(restore);
2552
2553    /* Cop the settings files to the proper dir */
2554    MoveDefaultSettings(restore);
2555
2556    /*  Generate the reinvoking command and add it as the property value */
2557    argv = (char **) XtMalloc(3 * sizeof(char *));
2558    argv[0] = XtNewString(application_name);
2559    argv[1] = XtNewString("-session");
2560    argv[2] = XtNewString(sessionFileName);
2561    XSetCommand(XtDisplay(toplevel), XtWindow(toplevel), argv, 3);
2562
2563    XtFree ((char *) argv[0]);
2564    XtFree ((char *) argv[1]);
2565    XtFree ((char *) argv[2]);
2566    XtFree ((char *) argv);
2567
2568    XtFree ((char *) full_path);
2569    XtFree ((char *) file_name);
2570 }
2571
2572 /************************************************************************
2573  *
2574  *  SaveSession
2575  *      Save the current File Manager session as a set of resources
2576  *      within the file denoted by path.
2577  *
2578  ************************************************************************/
2579
2580 static void
2581 SaveSession(
2582         char *path
2583         )
2584 {
2585    static char * name_list[] = { DTFILE_CLASS_NAME, NULL, NULL, NULL,
2586                                  NULL, NULL};
2587    char view_number[5];
2588    char number[5];
2589    char workspaceNumber[5];
2590    int fd;
2591    Atom * ws_presence = NULL;
2592    char * workspace_name=NULL;
2593    unsigned long num_workspaces = 0;
2594
2595    Atom actual_type;
2596    int  actual_format;
2597    unsigned long nitems;
2598    unsigned long leftover;
2599    WM_STATE * wm_state;
2600
2601    DialogData * dialog_data;
2602    FileMgrData * file_mgr_data;
2603    FileMgrRec  * file_mgr_rec;
2604    int i;
2605    int j;
2606    char * msg;
2607    int view_index;
2608    WorkspaceRec * workspaceInfo;
2609    char * tmpStr;
2610    Boolean saveTitle;
2611    char *actualSavedTitle;
2612
2613    /* This needs to be done because name_list is static and the values
2614       can be changed during the routine.  This means that they need to be
2615       NULL'd out each pass */
2616    name_list[1] = NULL;
2617    name_list[2] = NULL;
2618    name_list[3] = NULL;
2619    name_list[4] = NULL;
2620    name_list[5] = NULL;
2621
2622    /*  Disable any message box display during save session  */
2623
2624    message_display_enabled = False;
2625
2626
2627    /*  Create the session file  */
2628
2629    if ((fd = creat (path, S_IRUSR | S_IRGRP | S_IWUSR | S_IWGRP)) == -1)
2630    {
2631       tmpStr = GETMESSAGE(18, 18, "Could not open the session file.");
2632       msg = XtNewString(tmpStr);
2633       _DtSimpleError (application_name, DtError, NULL, msg);
2634       XtFree(msg);
2635       message_display_enabled = True;
2636
2637       return;
2638    }
2639
2640
2641    /*  Write out the general information  */
2642
2643    /* Number of dtfile views */
2644    (void) write (fd, "*", strlen ("*"));
2645    (void) write (fd, DTFILE_CLASS_NAME, strlen (DTFILE_CLASS_NAME));
2646    (void) write (fd, "*view_count:      ", strlen ("*view_count:        "));
2647
2648    if (trashFileMgrData)
2649    {
2650       if (trashFileMgrData->file_mgr_rec)
2651          (void) sprintf (view_number, "%d", view_count + 1);
2652       else
2653          (void) sprintf (view_number, "%d", view_count);
2654    }
2655    else
2656    {
2657       (void) sprintf (view_number, "%d", view_count);
2658    }
2659    (void) write (fd, view_number, strlen (view_number));
2660    (void) write (fd, "\n#\n", strlen ("\n#\n"));
2661
2662    (void) write (fd, "*", strlen ("*"));
2663    (void) write (fd, DTFILE_CLASS_NAME, strlen (DTFILE_CLASS_NAME));
2664    (void) write (fd, "*showFilesystem:  ", strlen ("*showFilesystem:    "));
2665
2666    if(showFilesystem)
2667       (void) write (fd, "True", strlen ("True"));
2668    else
2669       (void) write (fd, "False", strlen ("False"));
2670    (void) write (fd, "\n#\n", strlen ("\n#\n"));
2671
2672    (void) write (fd, "*", strlen ("*"));
2673    (void) write (fd, DTFILE_CLASS_NAME, strlen (DTFILE_CLASS_NAME));
2674    (void) write (fd, "*restrictMode:    ", strlen ("*restrictMode:      "));
2675
2676    if(restrictMode)
2677       (void) write (fd, "True", strlen ("True"));
2678    else
2679       (void) write (fd, "False", strlen ("False"));
2680    (void) write (fd, "\n#\n", strlen ("\n#\n"));
2681
2682    (void) write (fd, "*", strlen ("*"));
2683    (void) write (fd, DTFILE_CLASS_NAME, strlen (DTFILE_CLASS_NAME));
2684    (void) write (fd, "*openFolder:      ", strlen ("*openFolder:        "));
2685
2686    if(openDirType == NEW)
2687       (void) write (fd, "NEW", strlen ("NEW"));
2688    else
2689       (void) write (fd, "CURRENT", strlen ("CURRENT"));
2690    (void) write (fd, "\n#\n", strlen ("\n#\n"));
2691
2692    view_index = 0;
2693    name_list[1] = view_number;
2694    saveTitle = False;
2695
2696
2697    /*  Write out each of the view's resources  */
2698    /*  start with -1 so we can include the trash dialog */
2699    for (i = -1; i < view_count; i++)
2700    {
2701       if(i == -1)
2702       {
2703          if(trashDialogData)
2704             dialog_data = (DialogData *) trashDialogData;
2705          else
2706             continue;
2707       }
2708       else
2709       {
2710          dialog_data = (DialogData *) view_set[i]->dialog_data;
2711       }
2712
2713       file_mgr_data = (FileMgrData *) dialog_data->data;
2714       if(i == -1 && trashDialogData)
2715           file_mgr_data->IsTrashCan = True;
2716       file_mgr_rec = (FileMgrRec *) file_mgr_data->file_mgr_rec;
2717       if(file_mgr_rec == NULL)
2718          continue;
2719
2720       /* This is a bug fix ... We don't want to save the title if the
2721          View is the Trash Can of if it is an Application Manager.  This
2722          is because if the user saves a session in one Locale, then logs
2723          in in another, the Title will be in the locale that the session was
2724          saved in rather then the new local.  So let's save the Title,
2725          Null it out, Save the session info, and finally restore the Title.
2726       */
2727       if(i == -1 || file_mgr_data->toolbox)
2728       {
2729          /* the Trash Can or toolbox (i.e. Application Manager) */
2730          actualSavedTitle = file_mgr_data->title;
2731          file_mgr_data->title = NULL;
2732          saveTitle = True;
2733       }
2734
2735       /*  Getting the WM_STATE property to see if iconified or not */
2736       XGetWindowProperty (display, XtWindow (file_mgr_rec->shell),
2737                              wm_state_atom, 0L, (long) BUFSIZ, False,
2738                              wm_state_atom, &actual_type, &actual_format,
2739                              &nitems, &leftover, (unsigned char **) &wm_state);
2740
2741       /* Write out if iconified our not */
2742
2743       write (fd, "*", strlen ("*"));
2744       write (fd, DTFILE_CLASS_NAME, strlen (DTFILE_CLASS_NAME));
2745       sprintf (view_number, "%d", view_index);
2746       write (fd, ".", strlen ("."));
2747       write (fd, view_number, strlen (view_number));
2748
2749       (void) write (fd, ".iconify:      ", strlen (".iconify:   "));
2750
2751       if (wm_state->state == IconicState)
2752         write (fd, "True\n", strlen ("True\n"));
2753       else
2754         write (fd, "False\n", strlen ("False\n"));
2755
2756
2757       /*  Get the workspaces for this dt by accessing the property.  */
2758
2759       if (DtWsmGetWorkspacesOccupied (display, XtWindow (file_mgr_rec->shell),
2760                                   &ws_presence, &num_workspaces) == Success)
2761       {
2762          write (fd, "*", strlen ("*"));
2763          write (fd, DTFILE_CLASS_NAME, strlen (DTFILE_CLASS_NAME));
2764          (void) write (fd, ".", strlen ("."));
2765          (void) write (fd, view_number, strlen (view_number));
2766          (void) write (fd, ".workspace: ", strlen (".workspace: "));
2767
2768
2769          for (j = 0; j < num_workspaces; j++)
2770          {
2771             if (j != 0) (void) write (fd, "*", strlen ("*"));
2772             workspace_name = XGetAtomName (display, ws_presence[j]);
2773             (void) write (fd, workspace_name, strlen (workspace_name));
2774             XtFree ((char *) workspace_name);
2775          }
2776
2777
2778          (void) write (fd, "\n", strlen ("\n"));
2779          XFree((char *)ws_presence);
2780       }
2781
2782
2783       /*  Call the encapsulation mechanism to write each dialog  */
2784
2785       if(i == -1)
2786          _DtWriteDialogData (trashDialogData, fd, name_list);
2787       else
2788          _DtWriteDialogData ((DialogData *)view_set[i]->dialog_data,
2789                              fd, name_list);
2790       (void) write (fd, "#\n", strlen ("#\n"));
2791
2792       view_index++;
2793       if(saveTitle)
2794       {
2795          file_mgr_data->title = actualSavedTitle;
2796          saveTitle = False;
2797       }
2798    }
2799
2800    /*
2801     * Save off help dialog information for each workspace.
2802     * These are the help dialogs used for the desktop objects.
2803     */
2804    name_list[1] = WS_LOAD_RES_HEADER;
2805    name_list[2] = workspaceNumber;
2806    name_list[3] = number;
2807
2808    for (i = 0; i < desktop_data->numWorkspaces; i++)
2809    {
2810       workspaceInfo = desktop_data->workspaceData[i];
2811
2812       /*
2813        * Save number of secondary help dialogs in format:
2814        *     *Dtfile.Workspace.<WS#>.secondaryHelpDialogCount:  <#>
2815        */
2816       write(fd, "*", strlen("*"));
2817       write(fd, DTFILE_CLASS_NAME, strlen(DTFILE_CLASS_NAME));
2818       write(fd, WS_RES_HEADER, strlen(WS_RES_HEADER));
2819       sprintf(workspaceNumber, "%d", i);
2820       write(fd, workspaceNumber, strlen(workspaceNumber));
2821       write(fd, SEC_HELP_RES_HEADER, strlen(SEC_HELP_RES_HEADER));
2822       sprintf(view_number, "%d", workspaceInfo->secondaryHelpDialogCount);
2823       write(fd, view_number, strlen(view_number));
2824       write (fd, "\n#\n", strlen ("\n#\n"));
2825
2826       /* Save each of the secondary help dialogs */
2827       for (j = 0; j < workspaceInfo->secondaryHelpDialogCount; j++)
2828       {
2829          sprintf(number, "%d", j + 1);
2830          _DtWriteDialogData(workspaceInfo->secondaryHelpDialogList[j],
2831                            fd, name_list);
2832       }
2833
2834       /* Save the primary help dialog window */
2835       if (workspaceInfo->primaryHelpDialog)
2836       {
2837          sprintf(number, "%d", 0);
2838          _DtWriteDialogData(workspaceInfo->primaryHelpDialog,
2839                            fd, name_list);
2840       }
2841       write (fd, "#\n", strlen ("#\n"));
2842    }
2843    (void) close (fd);
2844
2845    /*  Re-able message box display flag after save session  */
2846    message_display_enabled = True;
2847
2848
2849 }
2850
2851
2852
2853 /*
2854  * Given a directory name, this function will see if a view of the parent
2855  * directory is open; if so, then it will update the icon representing
2856  * this icon, in the parent view, so that it is drawn as 'open'.  This
2857  * function must only be called if openDirType == NEW.
2858  */
2859
2860 void
2861 ForceMyIconOpen (
2862    char * host_name,
2863    char * directory_name)
2864 {
2865    FileViewData * file_view_data = NULL;
2866    DesktopRec *desktopWindow;
2867    DialogData * dd;
2868    FileMgrData * fmd;
2869    char * parent;
2870    char * fname;
2871    char * ptr;
2872    char * full_path;
2873    int i, j, k;
2874    char *icon_name, *new_file_type_name, *file_type_name;
2875    Arg args[5];
2876
2877    /* if directory_name is passed in a NULL, we want to go through all
2878       existing open directories and check to see if there are any open
2879       directories in each of them. This is used at the end of OpenNewView
2880       and the end of ShowNewDirectory */
2881    if (directory_name == NULL)
2882    {
2883       for (i = 0; i < view_count; i++)
2884       {
2885          dd = (DialogData *) view_set[i]->dialog_data;
2886          fmd = (FileMgrData *) dd->data;
2887
2888          for(j = 0; j < fmd->directory_count; j++)
2889          {
2890             ForceMyIconOpen(view_set[i]->host_name,
2891                             fmd->directory_set[j]->name);
2892          }
2893       }
2894       return;
2895    }
2896
2897    parent = _DtPName(directory_name);
2898    fname =  DName(directory_name);
2899
2900    /* first lets check to see if the directory is open in one of the
2901       open file manager views */
2902    for (i = 0; i < view_count; i++)
2903    {
2904       dd = (DialogData *) view_set[i]->dialog_data;
2905       fmd = (FileMgrData *) dd->data;
2906
2907       /* loop through until we find the file_view_data structure for the
2908          directory to force open */
2909       if (strcmp(host_name, view_set[i]->host_name) == 0)
2910       {
2911          for(j = 0; j < fmd->directory_count; j++)
2912          {
2913             if (strcmp(parent, fmd->directory_set[j]->name) == 0)
2914             {
2915                for (k = 0; k < fmd->directory_set[j]->file_count; k++)
2916                {
2917                   file_view_data = fmd->directory_set[j]->file_view_data[k];
2918                   if (strcmp(file_view_data->file_data->file_name, fname) == 0)
2919                      break;
2920                   file_view_data = NULL;
2921                }
2922                break;
2923             }
2924          }
2925       }
2926
2927       if (file_view_data)
2928       {
2929          fmd = (FileMgrData *)(((DirectorySet *)file_view_data->directory_set)->
2930                            file_mgr_data);
2931
2932          file_type_name = file_view_data->file_data->logical_type;
2933
2934          if(fmd->view != BY_NAME)
2935             BuildAndShowIconName(file_type_name, fmd->view,
2936                                  fmd->show_type, file_view_data->widget);
2937       }
2938    }
2939
2940    /* now we need to check to see if the directory being opened has a
2941       representation on the Desktop */
2942    for(i = 0; i < desktop_data->numIconsUsed; i++)
2943    {
2944       char buf[MAX_PATH];
2945
2946       desktopWindow = desktop_data->desktopWindows[i];
2947       file_view_data = desktopWindow->file_view_data;
2948
2949       sprintf(buf, "%s/%s", desktopWindow->dir_linked_to,
2950                             desktopWindow->file_name);
2951       DtEliminateDots (buf);
2952
2953       if (strcmp(buf, directory_name) == 0 &&
2954                                     strcmp(desktopWindow->host, host_name) == 0)
2955       {
2956          file_type_name = file_view_data->file_data->logical_type;
2957          if(desktopIconType == LARGE)
2958              BuildAndShowIconName(file_type_name, BY_NAME_AND_ICON,
2959                                  SINGLE_DIRECTORY, desktopWindow->iconGadget);
2960          else /* SMALL */
2961              BuildAndShowIconName(file_type_name, BY_NAME_AND_SMALL_ICON,
2962                                  SINGLE_DIRECTORY, desktopWindow->iconGadget);
2963       }
2964    }
2965 }
2966
2967
2968
2969
2970 /************************************************************************
2971  *
2972  *  RestoreSession
2973  *      Open the file as a resource data base, and use the data to
2974  *      create a set of File Manager views.
2975  *
2976  ************************************************************************/
2977
2978 static int
2979 RestoreSession(
2980         char *path,
2981         int type_of_restore,
2982         char *directory)
2983 {
2984    static char * name_list[] = { DTFILE_CLASS_NAME, NULL, NULL, NULL,
2985                                  NULL, NULL };
2986    XrmDatabase db;
2987    XrmName xrm_name[10];
2988    XrmRepresentation rep_type;
2989    XrmValue value;
2990    int num_views = 0;
2991    char * full_path = NULL;
2992    Boolean status=False;
2993    char * temp = NULL;
2994    char wsNum[5];
2995    char dialogNum[5];
2996    int num_sec_help_dialogs;
2997    int i;
2998    int j;
2999    DialogData * dialogData;
3000    struct stat stat_buf;
3001
3002
3003    /* Build the session path if we need to.
3004     * (e.g. When using the -session option)
3005     */
3006     if (type_of_restore == NORMAL_RESTORE)
3007     {
3008       status = DtSessionRestorePath(toplevel, &full_path, path);
3009
3010       if (!status)
3011          return(-1);
3012
3013       if (stat(full_path, &stat_buf) != 0)
3014       {
3015         char *tmpStr, *msg, *title;
3016
3017         tmpStr = GETMESSAGE(18, 18, "Could not open the session file.");
3018         msg = XtNewString(tmpStr);
3019         title = XtNewString((GETMESSAGE(21,39,"File Open Error")));
3020         _DtMessage (toplevel, title, msg, NULL, HelpRequestCB);
3021         XtFree(msg);
3022         XtFree(title);
3023         XtFree(full_path);
3024         full_path = NULL;
3025         return(-1);
3026       }
3027
3028       path = XtNewString(full_path);
3029     }
3030
3031    /* This prevents the encapsulator from placing the dialogs */
3032    disableDialogAutoPlacement = True;
3033
3034    /*  Open the file as a resource database and query it to  */
3035    /*  get the previously saved view count.                  */
3036
3037    db = XrmGetFileDatabase (path);
3038
3039    if (type_of_restore == NORMAL_RESTORE)
3040    {
3041       /* first find out if it should show the file system */
3042       xrm_name [0] = XrmStringToQuark (DTFILE_CLASS_NAME);
3043       xrm_name [1] = XrmStringToQuark ("showFilesystem");
3044       xrm_name [2] = 0;
3045       if (XrmQGetResource (db, xrm_name, xrm_name, &rep_type, &value))
3046       {
3047          if ((temp = (char *) value.addr) != NULL &&
3048                  strcmp (temp, "True") == 0)
3049          {
3050             showFilesystem = True;
3051          }
3052          else
3053             showFilesystem = False;
3054       }
3055       else
3056          showFilesystem = True;
3057
3058       /* find out if it should be in restricted mode */
3059       xrm_name [0] = XrmStringToQuark (DTFILE_CLASS_NAME);
3060       xrm_name [1] = XrmStringToQuark ("restrictMode");
3061       xrm_name [2] = 0;
3062       if (XrmQGetResource (db, xrm_name, xrm_name, &rep_type, &value))
3063       {
3064          if ((temp = (char *) value.addr) != NULL &&
3065                  strcmp (temp, "True") == 0)
3066          {
3067             restrictMode = True;
3068          }
3069          else
3070             restrictMode = False;
3071       }
3072       else
3073          restrictMode = False;
3074
3075       /* find out openFolder mode */
3076       xrm_name [0] = XrmStringToQuark (DTFILE_CLASS_NAME);
3077       xrm_name [1] = XrmStringToQuark ("openFolder");
3078       xrm_name [2] = 0;
3079       if (XrmQGetResource (db, xrm_name, xrm_name, &rep_type, &value))
3080       {
3081          if ((temp = (char *) value.addr) != NULL &&
3082                  strcmp (temp, "NEW") == 0)
3083          {
3084             openDirType = NEW;
3085          }
3086          else
3087             openDirType = CURRENT;
3088       }
3089       else
3090          openDirType = CURRENT;
3091    }
3092
3093    xrm_name [0] = XrmStringToQuark (DTFILE_CLASS_NAME);
3094    xrm_name [1] = XrmStringToQuark ("view_count");
3095    xrm_name [2] = 0;
3096
3097    /* Load standard dtfile views */
3098    if (XrmQGetResource (db, xrm_name, xrm_name, &rep_type, &value))
3099    {
3100       num_views = atoi (value.addr);
3101       if (num_views > 0)
3102          LoadViews(num_views, db, NULL, directory, special_restricted, 0);
3103    }
3104
3105    /* Restore any desktop help dialogs */
3106    if (type_of_restore == NORMAL_RESTORE)
3107    {
3108       for (i = 0; i < desktop_data->numWorkspaces; i++)
3109       {
3110          sprintf(wsNum, "%d", i);
3111          xrm_name [0] = XrmStringToQuark (DTFILE_CLASS_NAME);
3112          xrm_name [1] = XrmStringToQuark (WS_LOAD_RES_HEADER);
3113          xrm_name [2] = XrmStringToQuark (wsNum);
3114          xrm_name [3] = XrmStringToQuark (SEC_LOAD_HELP_RES_HEADER);
3115          xrm_name [4] = 0;
3116
3117          /* Load standard dtfile views */
3118          if (XrmQGetResource (db, xrm_name, xrm_name, &rep_type, &value))
3119          {
3120             num_sec_help_dialogs = atoi (value.addr);
3121             if (num_sec_help_dialogs > 0)
3122             {
3123                desktop_data->workspaceData[i]->secondaryHelpDialogCount =
3124                   num_sec_help_dialogs;
3125                desktop_data->workspaceData[i]->secondaryHelpDialogList =
3126                 (DialogData **) XtMalloc(sizeof(DialogData *) *
3127                    num_sec_help_dialogs);
3128
3129                for (j = 0; j < num_sec_help_dialogs; j++)
3130                {
3131                   name_list[0] = DTFILE_CLASS_NAME;
3132                   name_list[1] = WS_LOAD_RES_HEADER;
3133                   name_list[2] = wsNum;
3134                   name_list[3] = dialogNum;
3135                   name_list[4] = NULL;
3136                   sprintf(dialogNum, "%d", j + 1);
3137                   dialogData =
3138                        _DtGetResourceDialogData(help_dialog, db, name_list);
3139                   desktop_data->workspaceData[i]->secondaryHelpDialogList[j]=
3140                      dialogData;
3141                   ShowDTHelpDialog(NULL, i, HYPER_HELP_DIALOG,
3142                                    dialogData, NULL, NULL, NULL, NULL,
3143                                    DtHELP_TYPE_TOPIC);
3144                }
3145             }
3146          }
3147
3148          /* Load the primary help dialog */
3149          name_list[0] = DTFILE_CLASS_NAME;
3150          name_list[1] = WS_LOAD_RES_HEADER;
3151          name_list[2] = wsNum;
3152          name_list[3] = dialogNum;
3153          name_list[4] = NULL;
3154          sprintf(dialogNum, "%d", 0);
3155          dialogData = _DtGetResourceDialogData(help_dialog, db, name_list);
3156
3157          /* Keep only if currently posted */
3158          if (!(((HelpData *)dialogData->data)->displayed))
3159          {
3160             /* Not currently displayed */
3161             _DtFreeDialogData(dialogData);
3162             dialogData = NULL;
3163          }
3164          desktop_data->workspaceData[i]->primaryHelpDialog = dialogData;
3165          if (dialogData)
3166          {
3167             ShowDTHelpDialog(NULL, i, MAIN_HELP_DIALOG,
3168                              dialogData, NULL, DTFILE_HELP_NAME,
3169                              NULL, NULL, 0);
3170          }
3171       }
3172    }
3173
3174    XtFree(full_path);
3175    full_path = NULL;
3176
3177    /* Free the Xrm Database */
3178    XrmDestroyDatabase(db);
3179    disableDialogAutoPlacement = False;
3180
3181    return(0);
3182 }
3183
3184
3185 static void
3186 ViewAccept(
3187    View *view,
3188    Tt_message msg)
3189 {
3190    extern Tt_message FileCallback();
3191    extern Tt_message SessionCallback();
3192
3193    if ((msg == 0) || tt_is_err( tt_ptr_error( msg ))) {
3194       return;
3195    }
3196    view->msg = msg;
3197    /*
3198     * Register for notifications on the directory viewed.
3199     * This is done so that requesting apps can notify the
3200     * view if the directory name is changed.
3201     */
3202    view->pats = ttdt_file_join( view->directory_name, TT_SESSION, 0,
3203                                 FileCallback, view );
3204    if (tt_is_err( tt_ptr_error( view->pats ))) {
3205       view->pats = 0;
3206    }
3207
3208    /* Returned patterns automatically get destroyed when msg is destroyed */
3209    ttdt_message_accept( msg, SessionCallback,
3210                         _DtGetDialogShell( (DialogData *)view->dialog_data ),
3211                         view, 1, 1 );
3212 }
3213
3214
3215 static void
3216 LoadViews (
3217    int num_views,
3218    XrmDatabase db,
3219    char *host_name,
3220    char *directory_name,
3221    char *type,
3222    Tt_message msg)
3223
3224 {
3225    XrmName xrm_name[5];
3226    XrmRepresentation rep_type;
3227    XrmValue value;
3228    static char * name_list[] = { DTFILE_CLASS_NAME, NULL, NULL };
3229    char view_number[5];
3230    DialogData * dialog_data;
3231    FileMgrData * file_mgr_data;
3232    char * workspaces;
3233    XClassHint classHints;
3234    char * iconify = NULL;
3235    Boolean iconify_window;
3236    int i;
3237    char *title, *tmpTitle;
3238
3239    name_list[1] = view_number;
3240    xrm_name [0] = XrmStringToQuark (DTFILE_CLASS_NAME);
3241
3242
3243    /*  Get and display view_count views.  */
3244
3245    for (i = 0; i < num_views; i++)
3246    {
3247       struct stat stat_buf;
3248
3249       (void) sprintf (view_number, "%d", i);
3250       xrm_name [1] = XrmStringToQuark (view_number);
3251
3252       /* Get the main dialog data and set up the view  */
3253
3254       dialog_data = _DtGetResourceDialogData (file_mgr_dialog, db, name_list);
3255       file_mgr_data = (FileMgrData *) dialog_data->data;
3256
3257       if(file_mgr_data->toolbox && file_mgr_data->title == NULL)
3258          file_mgr_data->title = DtActionLabel("Dtappmgr");
3259
3260       if (stat(file_mgr_data->current_directory, &stat_buf) != 0)
3261       {
3262          _DtFreeDialogData(dialog_data);
3263          continue;
3264       }
3265
3266       if (trashFileMgrData
3267           && (file_mgr_data->IsTrashCan == True)
3268           && strcmp(file_mgr_data->current_directory, trash_dir) == 0)
3269       {
3270          trashFileMgrData->view = file_mgr_data->view;
3271          trashFileMgrData->order = file_mgr_data->order;
3272          trashFileMgrData->direction = file_mgr_data->direction;
3273          trashFileMgrData->positionEnabled = file_mgr_data->positionEnabled;
3274          trashFileMgrData->preferences = file_mgr_data->preferences;
3275          file_mgr_data->preferences = NULL;
3276          _DtFreeDialogData(dialog_data);
3277          continue;
3278       }
3279
3280       /* Increment the view list size if necessary and add directory to list */
3281
3282       if (view_count == view_set_size)
3283       {
3284          view_set_size += 10;
3285          view_set =
3286             (View **) XtRealloc ((char *)view_set,
3287                                      sizeof (View **) * view_set_size);
3288       }
3289       view_set[view_count] = (View *) XtMalloc (sizeof (View));
3290       view_set[view_count]->dialog_data = (XtPointer) dialog_data;
3291       view_set[view_count]->msg = 0;
3292       view_set[view_count]->pats = 0;
3293
3294       if(restoreType == TOOL_RESTORE)
3295          file_mgr_data->toolbox = True;
3296
3297       if(directory_name == NULL)
3298       {
3299          view_set[view_count]->host_name = XtNewString (file_mgr_data->host);
3300          view_set[view_count]->directory_name =
3301             XtNewString (file_mgr_data->current_directory);
3302       }
3303       else
3304       {
3305          XtFree(file_mgr_data->current_directory);
3306          file_mgr_data->current_directory = NULL;
3307          XtFree(file_mgr_data->restricted_directory);
3308          file_mgr_data->restricted_directory = NULL;
3309
3310          view_set[view_count]->directory_name = XtNewString(directory_name);
3311          XtFree((char *)file_mgr_data->selection_list);
3312          file_mgr_data->selection_list = NULL;
3313          if(host_name == NULL)
3314          {
3315             view_set[view_count]->host_name = XtNewString (file_mgr_data->host);
3316             file_mgr_data->current_directory = XtNewString(directory_name);
3317             if(type == NULL)
3318               file_mgr_data->restricted_directory =
3319                                               XtNewString(directory_name);
3320             else
3321               file_mgr_data->restricted_directory =
3322                                               XtNewString(type);
3323          }
3324          else
3325          {
3326             view_set[view_count]->host_name = XtNewString (host_name);
3327             XtFree(file_mgr_data->host);
3328             file_mgr_data->host = XtNewString(host_name);
3329             file_mgr_data->current_directory = XtNewString(directory_name);
3330             if(special_view && special_restricted != NULL)
3331                file_mgr_data->restricted_directory =
3332                                      XtNewString(special_restricted);
3333             else
3334                file_mgr_data->restricted_directory = NULL;
3335          }
3336          FileMgrBuildDirectories (file_mgr_data,
3337                           view_set[view_count]->host_name, directory_name);
3338       }
3339
3340       /*  Get the workspace set the view is contained in  */
3341       /*  and set the property for the view just created  */
3342
3343       xrm_name [2] = XrmStringToQuark ("workspace");
3344       xrm_name [3] = 0;
3345
3346       if (XrmQGetResource (db, xrm_name, xrm_name, &rep_type, &value))
3347       {
3348          /*  Make sure we have some valid workspaces names to work with */
3349
3350          /* value.addr should = NULL if no workspace names */
3351          workspaces = (char *) value.addr;
3352       }
3353       else
3354         /* we have no workspace resource so use default */
3355         workspaces = NULL;
3356
3357       /*  Get and set whether the view is iconic  */
3358
3359       xrm_name [2] = XrmStringToQuark ("iconify");
3360       xrm_name [3] = 0;
3361
3362       if (XrmQGetResource (db, xrm_name, xrm_name, &rep_type, &value))
3363       {
3364          /*  If there is an iconify resource and its value is True,  */
3365          /*  then mark the window as iconified.                      */
3366
3367          if ((iconify = (char *) value.addr) != NULL &&
3368               strcmp (iconify, "True") == 0)
3369          {
3370            iconify_window = True;
3371
3372          }
3373          else
3374           iconify_window = False;
3375       }
3376       else
3377          iconify_window = False;
3378
3379      if(file_mgr_data->positionEnabled == RANDOM_ON &&
3380                         (file_mgr_data->object_positions == NULL))
3381         LoadPositionInfo(file_mgr_data);
3382
3383       /* Call _DtShowDialog to create and manage the new window */
3384
3385      tmpTitle = file_mgr_data->title;
3386      title = file_mgr_data->title = _DtBuildFMTitle(file_mgr_data);
3387      if (special_title)
3388         XtFree(special_title);
3389      special_title = XtNewString(title);
3390
3391      classHints.res_name = title;
3392      classHints.res_class = DTFILE_CLASS_NAME;
3393
3394      _DtShowDialog (NULL, NULL, NULL, dialog_data, NULL, NULL,
3395                     RemoveTextFields, NULL, workspaces, iconify_window,
3396                     special_view, title, &classHints);
3397
3398      XtFree(title);
3399      file_mgr_data->title = tmpTitle;
3400
3401      if (msg != 0) {
3402         ViewAccept( view_set[view_count], msg );
3403         msg = 0;
3404      }
3405
3406      view_count++;
3407    }
3408
3409    if (openDirType == NEW)
3410       ForceMyIconOpen(file_mgr_data->host, NULL);
3411 }
3412
3413
3414 /************************************************************************
3415  *
3416  *  GetPWD
3417  *
3418  ************************************************************************/
3419 static void
3420 GetPWD(
3421         char current_directory[] )
3422 {
3423    FILE * pwd_file;
3424    register int i;
3425
3426     /*  Open a pwd process and read the current working directory  */
3427     /*  from it.  If the open fails or a read fails, then display  */
3428     /*  the users home directory.                                  */
3429
3430       pwd_file = popen ("pwd", "r");
3431       i = 0;
3432
3433       if (pwd_file != NULL)
3434       {
3435          while (1)
3436          {
3437             errno = 0;
3438             if (fread (&current_directory[i], sizeof(char), 1, pwd_file) != 1)
3439             {
3440                if (errno == EINTR)
3441                   continue;
3442                else
3443                   break;
3444             }
3445
3446             if (current_directory[i] == '\n')
3447                break;
3448
3449             i++;
3450          }
3451       }
3452     (void) pclose (pwd_file);
3453     current_directory[i] = '\0';
3454
3455 }
3456
3457 /************************************************************************
3458  *
3459  *  OpenDirectories
3460  *      Given a string that contains a single or set of host:path
3461  *      specifications, parse out each host:path, validate it as
3462  *      a accessible directory, and call a function to create a
3463  *      file manager view of the directory.
3464  *
3465  ************************************************************************/
3466
3467 static void
3468 OpenDirectories(
3469         char *directory_set,
3470         char *type)
3471 {
3472    char * separator;
3473    char * host;
3474    char * path;
3475
3476    /*  Loop the the directory set string until all of  */
3477    /*  the path specifications have be parsed.    */
3478
3479    while (1)
3480    {
3481       separator = DtStrchr (directory_set, ',');
3482       if (separator != NULL)
3483          *separator = '\0';
3484
3485       _DtPathFromInput(directory_set, NULL, &host, &path);
3486
3487       if (path)
3488       {
3489          GetNewView (host, path, type, NULL, 0);
3490       }
3491       else
3492       {
3493          char *tmpStr, *errTitle, *errMsg, *dmsg;
3494
3495          tmpStr = GETMESSAGE(32, 2, "File Manager Open Directory Error");
3496          errTitle = XtNewString(tmpStr);
3497          tmpStr = GETMESSAGE(18, 38, "Invalid folder specification, %s");
3498          errMsg = XtNewString(tmpStr);
3499          dmsg = XtMalloc(strlen(errMsg)+strlen(directory_set)+1);
3500          sprintf(dmsg, errMsg, directory_set);
3501          _DtMessage(toplevel, errTitle, dmsg, NULL, HelpRequestCB);
3502
3503          XtFree(errTitle);
3504          XtFree(errMsg);
3505          XtFree(dmsg);
3506       }
3507
3508       /*  Free up the unique host and directory names  */
3509       /*  that were allocated.                         */
3510
3511       XtFree ((char *) host);
3512       XtFree ((char *) path);
3513
3514       /*  Set the starting position of the next host:path  */
3515
3516       if (separator != NULL)
3517          directory_set = separator + 1;
3518       else
3519          break;
3520    }
3521 }
3522
3523
3524
3525
3526 /************************************************************************
3527  *
3528  *  GetNewView
3529  *      Given a directory name, generate a new view for the directory.
3530  *
3531  ************************************************************************/
3532 DialogData *
3533 GetNewView(
3534         char *host_name,
3535         char *directory_name,
3536         char *type,
3537         WindowPosition *position,
3538         Tt_message msg)
3539 {
3540    DialogData * dialog_data;
3541    DialogInstanceData * instance_data;
3542    FileMgrData * file_mgr_data;
3543    FileMgrData * fmd;
3544    FileMgrRec * file_mgr_rec;
3545    char * real_directory_name;
3546    int i;
3547    XClassHint classHints;
3548    char *title, *tmpTitle;
3549    struct stat stat_buf;
3550    char *tmpStr;
3551    char *errMsg = NULL;
3552
3553    DtEliminateDots( directory_name );
3554
3555    if (stat(directory_name, &stat_buf) == 0)
3556    {
3557       if ((stat_buf.st_mode & S_IFMT) != S_IFDIR)
3558       {
3559          tmpStr = GETMESSAGE(18, 19,
3560                   "The folder specification,\n%s\nis not a folder.");
3561          errMsg = XtNewString(tmpStr);
3562       }
3563    }
3564    else
3565    {
3566       tmpStr = GETMESSAGE(18, 20,
3567                "The folder specification,\n%s\ndoes not exist.");
3568       errMsg = XtNewString(tmpStr);
3569    }
3570
3571    if (errMsg)
3572    {
3573       char *title, *dmsg;
3574
3575       tmpStr = GETMESSAGE(32, 2, "File Manager Open Directory Error");
3576       title = XtNewString(tmpStr);
3577       dmsg = XtMalloc(strlen(errMsg) +
3578                       strlen(directory_name) + 1);
3579       sprintf(dmsg, errMsg, directory_name);
3580       _DtMessage(toplevel, title, dmsg, NULL, HelpRequestCB);
3581
3582       XtFree(errMsg);
3583       XtFree(title);
3584       XtFree(dmsg);
3585       return(NULL);
3586    }
3587
3588    /*
3589     * Special case: When opening any of the special desktop directory
3590     * icons (Home, Remote Systems, etc), we want to display the correct
3591     * path (i.e. $HOME instead of $HOME/.dt/Desktop/Home).  So ... we'll
3592     * do the remap here.
3593     */
3594    real_directory_name = directory_name;
3595
3596    if(openDirType == NEW || (strcmp(real_directory_name, desktop_dir) == 0))
3597    {
3598       for(i = 0; i < view_count; i++)
3599       {
3600          if((strcmp(real_directory_name, view_set[i]->directory_name) == 0 &&
3601             (strcmp(host_name, view_set[i]->host_name) == 0))
3602                                   )
3603          {
3604              Window   rootWindow;
3605              Atom     pCurrent;
3606              Screen   *currentScreen;
3607              int      screen;
3608
3609              dialog_data = (DialogData *) view_set[i]->dialog_data;
3610              file_mgr_data = (FileMgrData *) dialog_data->data;
3611              file_mgr_rec = (FileMgrRec *) file_mgr_data->file_mgr_rec;
3612
3613              screen = XDefaultScreen(display);
3614              currentScreen = XScreenOfDisplay(display, screen);
3615              rootWindow = RootWindowOfScreen(currentScreen);
3616
3617              /* Get the current Workspace */
3618              if (DtWsmGetCurrentWorkspace(display, rootWindow, &pCurrent)
3619                                                                    == Success)
3620              {
3621                 Atom * ws_presence = NULL;
3622                 unsigned long num_workspaces = 0;
3623                 int k;
3624
3625                 if (DtWsmGetWorkspacesOccupied(display,
3626                      XtWindow(file_mgr_rec->shell), &ws_presence,
3627                      &num_workspaces) == Success)
3628                 {
3629                    /* Already in this workspace? */
3630                    for (k = 0; k < num_workspaces; k++)
3631                    {
3632                       if (ws_presence[k] == pCurrent)
3633                          break;
3634                    }
3635
3636                    if (k >= num_workspaces)
3637                    {
3638                       /* Add to the workspace */
3639                       ws_presence = (Atom *) XtRealloc((char *)ws_presence,
3640                            sizeof (Atom) * (num_workspaces + 1));
3641
3642                       ws_presence[num_workspaces] = pCurrent;
3643                       DtWsmSetWorkspacesOccupied(display,
3644                                           XtWindow(file_mgr_rec->shell),
3645                                           ws_presence, num_workspaces + 1);
3646                    }
3647                    XFree((char *)ws_presence);
3648                 }
3649                 else
3650                 {
3651                    /* Change the hints to reflect the current workspace */
3652                    DtWsmSetWorkspacesOccupied(display,
3653                                            XtWindow(file_mgr_rec->shell),
3654                                            &pCurrent, 1);
3655                 }
3656              }
3657
3658              /* must map the window to catch iconified windows */
3659              /* a XtPopup will not catch it */
3660              XtMapWidget(file_mgr_rec->shell);
3661              XRaiseWindow(display, XtWindow(file_mgr_rec->shell));
3662
3663              /* announce activity */
3664              {
3665                 Tt_message msg;
3666                 msg = tt_pnotice_create(TT_SESSION, "DtActivity_Began");
3667                 tt_message_send(msg);
3668                 tttk_message_destroy(msg);
3669              }
3670
3671              return(NULL);
3672          }
3673       }
3674    }
3675
3676    /* If in novice mode, force the icon for this dir to the 'Open' state */
3677    if (openDirType == NEW)
3678       ForceMyIconOpen(host_name, directory_name);
3679
3680    /*  Increment the list size if necessary.  */
3681
3682    if (view_count == view_set_size)
3683    {
3684       view_set_size += 10;
3685       view_set =
3686          (View **) XtRealloc ((char *)view_set,
3687                                     sizeof (View **) * view_set_size);
3688    }
3689
3690    view_set[view_count] = (View *) XtMalloc (sizeof (View));
3691    view_set[view_count]->msg = 0;
3692    view_set[view_count]->pats = 0;
3693
3694    if (initiating_view != NULL)
3695       dialog_data = _DtGetDefaultDialogData (file_mgr_dialog);
3696    else
3697    {
3698       char * tmp_path;
3699       char full_path[MAX_PATH + 1];
3700       XrmDatabase db;
3701
3702       tmp_path = _DtCreateDtDirs(display);
3703       if(type != NULL)
3704          sprintf(full_path, "%s/%s", tmp_path, TOOL_SETTINGS_FILENAME);
3705       else
3706          sprintf(full_path, "%s/%s", tmp_path, HOME_SETTINGS_FILENAME);
3707       XtFree(tmp_path);
3708       db = XrmGetFileDatabase (full_path);
3709       if(db != NULL)
3710       {
3711          if(type != NULL)
3712          {
3713             restoreType = TOOL_RESTORE;
3714             LoadViews(1, db, NULL, directory_name, type, msg);
3715          }
3716          else
3717          {
3718             restoreType = HOME_RESTORE;
3719             LoadViews(1, db, host_name, directory_name, NULL, msg);
3720          }
3721
3722          /*
3723           * Free the Xrm Database
3724           */
3725          XrmDestroyDatabase(db);
3726          dialog_data = (DialogData *)view_set[view_count - 1]->dialog_data;
3727          file_mgr_data = (FileMgrData *) dialog_data->data;
3728          if(type != NULL)
3729          {
3730             application_args.tool_width = file_mgr_data->width;
3731             application_args.tool_height = file_mgr_data->height;
3732          }
3733          else
3734          {
3735             application_args.dir_width = file_mgr_data->width;
3736             application_args.dir_height = file_mgr_data->height;
3737          }
3738          if(file_mgr_data->find != NULL &&
3739                                 file_mgr_data->current_directory != NULL)
3740          {
3741             DialogData * dialog_data;
3742             FindData * find_data;
3743
3744             dialog_data = (DialogData *)file_mgr_data->find;
3745             find_data = (FindData *)dialog_data->data;
3746
3747             XtFree(find_data->directories);
3748             if(file_mgr_data->restricted_directory == NULL)
3749             {
3750                if(restrictMode)
3751                   find_data->directories = XtNewString(users_home_dir);
3752                else
3753                   find_data->directories =
3754                             XtNewString(file_mgr_data->current_directory);
3755             }
3756             else
3757             {
3758                if(strcmp(file_mgr_data->current_directory,
3759                          file_mgr_data->restricted_directory) == 0)
3760                   find_data->directories = XtNewString("/");
3761                else
3762                   find_data->directories =
3763                         XtNewString(file_mgr_data->current_directory +
3764                         strlen(file_mgr_data->restricted_directory));
3765             }
3766          }
3767
3768          /* If in novice mode, force the icon for all the dir's to the
3769             'Open' state */
3770          if (openDirType == NEW)
3771             ForceMyIconOpen(host_name, NULL);
3772
3773          return((DialogData *)view_set[view_count - 1]->dialog_data);
3774       }
3775       else
3776          dialog_data = _DtGetDefaultDialogData (file_mgr_dialog);
3777    }
3778    view_set[view_count]->dialog_data = (XtPointer) dialog_data;
3779    file_mgr_data = (FileMgrData *) dialog_data->data;
3780
3781    /*  Adjust the view settings if this new view was created  */
3782    /*  because of an action on a previous view.               */
3783
3784    if (initiating_view != NULL)
3785    {
3786       FileMgrPropagateSettings ((FileMgrData *)initiating_view, file_mgr_data);
3787       /* force new window to come up in flat mode */
3788       file_mgr_data->show_type =
3789         ((PreferencesData *)file_mgr_data->preferences->data)->show_type =
3790                                                               SINGLE_DIRECTORY;
3791       file_mgr_data->view = file_mgr_data->view_single;
3792    }
3793
3794       /*  Call the FileMgr dialog to build up its directory set for  */
3795       /*  the directory name.                                        */
3796    FileMgrBuildDirectories (file_mgr_data, host_name, real_directory_name);
3797
3798    if(type != NULL)
3799    {
3800       PreferencesData *preferences_data;
3801
3802       file_mgr_data->toolbox = True;
3803       file_mgr_data->width = application_args.tool_width;
3804       file_mgr_data->height = application_args.tool_height;
3805
3806       /* we want to default for the toolboxes (i.e. Application Manager) to
3807        * look different from a normal File Manager view.  Let's turn off
3808        * the iconic_path, current_directory, and status_line.
3809        */
3810       file_mgr_data->show_iconic_path = False;
3811       file_mgr_data->show_current_dir = False;
3812 /*
3813       file_mgr_data->show_status_line = True;
3814 */
3815
3816       preferences_data = (PreferencesData *)file_mgr_data->preferences->data;
3817       preferences_data->show_iconic_path = file_mgr_data->show_iconic_path;
3818       preferences_data->show_current_dir = file_mgr_data->show_current_dir;
3819       preferences_data->show_status_line = file_mgr_data->show_status_line;
3820    }
3821    else
3822    {
3823       file_mgr_data->toolbox = False;
3824       file_mgr_data->width = application_args.dir_width;
3825       file_mgr_data->height = application_args.dir_height;
3826    }
3827
3828
3829    if(file_mgr_data->find != NULL && file_mgr_data->current_directory != NULL)
3830    {
3831       DialogData * dialog_data;
3832       FindData * find_data;
3833
3834       dialog_data = (DialogData *)file_mgr_data->find;
3835       find_data = (FindData *)dialog_data->data;
3836
3837       XtFree(find_data->directories);
3838       if(file_mgr_data->restricted_directory == NULL)
3839       {
3840          if(restrictMode)
3841             find_data->directories = XtNewString(users_home_dir);
3842          else
3843             find_data->directories =
3844                             XtNewString(file_mgr_data->current_directory);
3845       }
3846       else
3847       {
3848          if(strcmp(file_mgr_data->current_directory,
3849                    file_mgr_data->restricted_directory) == 0)
3850             find_data->directories = XtNewString("/");
3851          else
3852             find_data->directories =
3853                    XtNewString(file_mgr_data->current_directory +
3854                    strlen(file_mgr_data->restricted_directory));
3855       }
3856    }
3857
3858    view_set[view_count]->host_name = XtNewString (file_mgr_data->host);
3859    view_set[view_count]->directory_name =
3860          XtNewString (file_mgr_data->current_directory);
3861
3862    /* Load default position info, or inherit, if appropriate */
3863    if ((fmd = (FileMgrData *)initiating_view) &&
3864        (strcmp(fmd->host, host_name) == 0) &&
3865        (strcmp(fmd->current_directory, real_directory_name) == 0))
3866    {
3867       InheritPositionInfo(fmd, file_mgr_data);
3868    }
3869    else
3870       LoadPositionInfo(file_mgr_data);
3871
3872
3873    /*  Get the dialog displayed.  */
3874    if (position)
3875    {
3876       instance_data = (DialogInstanceData *) dialog_data->data;
3877       instance_data->x = position->x;
3878       instance_data->y = position->y;
3879       instance_data->displayed = True;  /* @@@ Hack! without this,
3880                                           _DtShowDialog will ignore
3881                                            our position info */
3882    }
3883
3884    tmpTitle = file_mgr_data->title;
3885    title = file_mgr_data->title = _DtBuildFMTitle(file_mgr_data);
3886    if (special_title)
3887       XtFree(special_title);
3888    special_title = XtNewString(title);
3889
3890    classHints.res_name = title;
3891    classHints.res_class = DTFILE_CLASS_NAME;
3892    initiating_view = NULL;
3893
3894    _DtShowDialog (NULL, NULL, NULL, dialog_data, NULL, NULL, RemoveTextFields,
3895                NULL, NULL, False, special_view, title, &classHints);
3896
3897    XtFree(title);
3898    file_mgr_data->title = tmpTitle;
3899
3900    if (msg != 0) {
3901       ViewAccept( view_set[view_count], msg );
3902       msg = 0;
3903    }
3904
3905    view_count++;
3906
3907    /* If in novice mode, force the icon for all the dir's to the 'Open' state */
3908    if (openDirType == NEW)
3909       ForceMyIconOpen(host_name, NULL);
3910
3911    return(dialog_data);
3912 }
3913
3914
3915
3916
3917 /************************************************************************
3918  *
3919  *  CloseView
3920  *      Update the view set array when a view is closed.
3921  *
3922  ************************************************************************/
3923
3924 void
3925 CloseView(
3926         DialogData *dialog_data )
3927 {
3928    register int i;
3929    register int j;
3930    FileMgrData * file_mgr_data;
3931    DialogData * tmpDialog_data;
3932    FileMgrRec * file_mgr_rec;
3933    XmManagerWidget file_window;
3934    char *directory_name = NULL;
3935    char *host_name = NULL;
3936
3937    if(dialog_data == trashDialogData)
3938    {
3939       CloseTrash(NULL, NULL, NULL);
3940       return;
3941    }
3942
3943    for (i = 0; i < view_count; i++)
3944    {
3945       if (dialog_data == (DialogData *) (view_set[i]->dialog_data))
3946       {
3947          tmpDialog_data = (DialogData *) (view_set[i]->dialog_data);
3948          file_mgr_data = (FileMgrData *)tmpDialog_data->data;
3949
3950          directory_name = (char *)XtMalloc( strlen(view_set[i]->directory_name) + 1);
3951          strcpy(directory_name, view_set[i]->directory_name);
3952          host_name = (char *)XtMalloc( strlen(view_set[i]->host_name) + 1);
3953          strcpy(host_name, view_set[i]->host_name);
3954
3955          if (view_set[i]->msg != 0) {
3956             if (view_set[i]->pats != 0) {
3957                ttdt_file_quit( view_set[i]->pats, 0 );
3958                view_set[i]->pats = 0;
3959             }
3960             tt_message_reply( view_set[i]->msg );
3961             tttk_message_destroy( view_set[i]->msg );
3962             view_set[i]->msg = 0;
3963          }
3964
3965          XtFree ((char *) view_set[i]->directory_name);
3966          XtFree ((char *) view_set[i]->host_name);
3967          XtFree ((char *) view_set[i]);
3968          view_set[i] = NULL;
3969
3970          for (j = i; j < view_count - 1; j++)
3971             view_set[j] = view_set[j + 1];
3972
3973          view_count--;
3974
3975          _DtHideDialog (dialog_data, True);
3976
3977          file_mgr_rec = (FileMgrRec *)file_mgr_data->file_mgr_rec;
3978          file_window = (XmManagerWidget)file_mgr_rec->file_window;
3979          /* For next time, unmanage all the icons */
3980          XtUnmanageChildren(file_window->composite.children,
3981                             file_window->composite.num_children);
3982
3983          if(PositionFlagSet(file_mgr_data))
3984             SavePositionInfo(file_mgr_data);
3985
3986          /* If it is an Application Manager view, then no point in
3987           caching this dialog, so free it */
3988
3989          if(file_mgr_data->toolbox)
3990             _DtFreeDialog(dialog_data);
3991
3992          _DtFreeDialogData (dialog_data);
3993
3994          break;
3995       }
3996    }
3997
3998
3999    /*  Update the directory cache list to remove unneeded directories.  */
4000
4001    UpdateCachedDirectories (view_set, view_count);
4002
4003    if (openDirType == NEW)
4004       ForceMyIconClosed(host_name, directory_name);
4005
4006    XtFree(directory_name);
4007    XtFree(host_name);
4008 }
4009
4010
4011
4012
4013 /************************************************************************
4014  *
4015  *  DirectoryChanged
4016  *      This function is called when a view may be changing its
4017  *      current directory.  It updates the view_set list to the
4018  *      new host and directory.
4019  *
4020  ************************************************************************/
4021
4022 void
4023 DirectoryChanged(
4024         XtPointer file_mgr_data,
4025         char *old_host_name,
4026         char *new_host_name,
4027         char *old_directory_name,
4028         char *new_directory_name )
4029 {
4030    int i;
4031
4032
4033    /*  See if the directory is one being viewed  */
4034
4035    for (i = 0; i < view_count; i++)
4036    {
4037       if (((DialogData *) (view_set[i]->dialog_data))->data == file_mgr_data)
4038       {
4039          if (strcmp (old_host_name, view_set[i]->host_name) == 0              &&
4040              strcmp (old_directory_name, view_set[i]->directory_name) == 0)
4041          {
4042             XtFree ((char *) view_set[i]->host_name);
4043             view_set[i]->host_name = XtNewString (new_host_name);
4044
4045             XtFree ((char *) view_set[i]->directory_name);
4046             view_set[i]->directory_name = XtNewString (new_directory_name);
4047          }
4048       }
4049    }
4050
4051
4052    /*  Update the directory cache list to remove unneeded directories.  */
4053
4054    UpdateCachedDirectories (view_set, view_count);
4055 }
4056
4057
4058
4059 /************************************************************************
4060  *
4061  *  ObserveTtNotice
4062  *      Dispatch ToolTalk events to internal handlers.
4063  *
4064  ************************************************************************/
4065
4066 static Tt_callback_action
4067 ObserveTtNotice(
4068         Tt_message msg,
4069         Tt_pattern pat
4070 )
4071 {
4072    char *op;
4073    Tt_status status;
4074
4075    op = tt_message_op( msg );
4076    status = tt_ptr_error( op );
4077    if ((status != TT_OK) || (op == 0)) {
4078       /* Let tttk_Xt_input_handler() Do The Right Thing */
4079       return TT_CALLBACK_CONTINUE;
4080    }
4081    if (strcmp( op, "DtTypes_Reloaded" ) == 0) {
4082       ReloadDatabases();
4083    } else if (strcmp( op, "XSession_Ending" ) == 0) {
4084       if( emptyTrashOnExit )
4085          TrashEmpty();
4086    } else {
4087       tt_free( op );
4088       return TT_CALLBACK_CONTINUE;
4089    }
4090    tt_free( op );
4091    tttk_message_destroy( msg );
4092    return TT_CALLBACK_PROCESSED;
4093 }
4094
4095 /************************************************************************
4096  *
4097  *  HandleTtRequest
4098  *      Dispatch ToolTalk requests to internal handlers.
4099  *
4100  ************************************************************************/
4101
4102 Tt_callback_action
4103 HandleTtRequest(
4104         Tt_message msg,
4105         Tt_pattern pat
4106 )
4107 {
4108         char *op;
4109         Tt_status status;
4110
4111         op = tt_message_op( msg );
4112         status = tt_ptr_error( op );
4113         if ((status != TT_OK) || (op == 0)) {
4114                 /* Let tttk_Xt_input_handler() Do The Right Thing */
4115                 return TT_CALLBACK_CONTINUE;
4116         }
4117         if (strcmp( op, "DtFileSession_Run" ) == 0) {
4118                 ViewSessionHandler( msg );
4119         } else if (strcmp( op, "DtFolder_Show" ) == 0) {
4120                 ViewDirectoryHandler( msg );
4121         } else if (strcmp( op, "DtHome_Show" ) == 0) {
4122                 ViewHomeDirectoryHandler( msg );
4123         } else if (strcmp( op, "DtTools_Show" ) == 0) {
4124                 ViewToolsDirectoryHandler( msg );
4125         } else if (strcmp( op, "DtTrash_Show" ) == 0) {
4126                 TrashDisplayHandler( msg );
4127         } else if (strcmp( op, "DtTrash_Remove" ) == 0) {
4128                 TrashRemoveHandler( msg );
4129         } else if (strcmp( op, "DtTrash_Empty" ) == 0) {
4130                 TrashEmptyHandler( msg );
4131         } else if (strcmp( op, "DtTrash_File" ) == 0) {
4132                 TrashRemoveNoConfirmHandler( msg );
4133     } else if (strcmp( op, "DtTrash_Restore" ) == 0) {
4134          TrashRestoreHandler( msg );
4135     } else if (strcmp( op, "DtFile_PutOnWorkspace" ) == 0) {
4136          PutOnWorkspaceHandler( msg );
4137     } else if (strcmp( op, "DtFile_Move" ) == 0) {
4138          MoveCopyLinkHandler( msg, MOVE_FILE );
4139     } else if (strcmp( op, "DtFile_Copy" ) == 0) {
4140          MoveCopyLinkHandler( msg, COPY_FILE );
4141     } else if (strcmp( op, "DtFile_Link" ) == 0) {
4142          MoveCopyLinkHandler( msg, LINK_FILE );
4143     } else {
4144          tt_free( op );
4145          return TT_CALLBACK_CONTINUE;
4146     }
4147     tt_free( op );
4148     return TT_CALLBACK_PROCESSED;
4149 }
4150
4151
4152
4153
4154 /************************************************************************
4155  *
4156  *  ViewSessionHandler
4157  *      This function is called upon the dt session  message
4158  *      being received.  The name of the session file is extracted
4159  *      out of the message and a function is called to create
4160  *      a view or set of views described by the file.
4161  *
4162  ************************************************************************/
4163
4164 static void
4165 ViewSessionHandler(
4166    Tt_message msg)
4167 {
4168    char *file = tt_message_file( msg );
4169    tt_message_reply( msg );
4170    tttk_message_destroy( msg );
4171
4172    if (! tt_is_err( tt_ptr_error( file )))
4173    {
4174       if (view_count == 0 && desktop_data->numIconsUsed == 0)
4175       {
4176            int session_flag = 0;
4177            char *session_name;
4178
4179            session_name = strrchr(file, '/');
4180            session_name++;
4181            LoadDesktopInfo(session_name);
4182            session_flag = RestoreSession (session_name, NORMAL_RESTORE, NULL);
4183            if ((session_flag != 0) && (view_count == 0))
4184            {
4185               char current_directory[MAX_PATH];
4186
4187               GetPWD(current_directory);
4188               if (current_directory[0] != '\0')
4189               {
4190                  if (!GetNewView
4191                       (home_host_name, current_directory, NULL, NULL, 0))
4192                     ViewHomeDirectoryHandler (0);
4193               }
4194               else
4195               {
4196                  ViewHomeDirectoryHandler (0);
4197               }
4198            }
4199       }
4200       else
4201       {
4202            char *tmpStr, *msg, *title;
4203
4204            tmpStr = GETMESSAGE(18, 39, "Cannot start a second File Manager session because a File Manager\nsession is already open on the desktop.  If you want to start a new File\nManager session, you must first close all current File Manager windows\nand remove all File Manager objects from the workspaces.");
4205            msg = XtNewString(tmpStr);
4206            title = XtNewString((GETMESSAGE(18,40,"Session Error")));
4207            _DtMessage (toplevel, title, msg, NULL, HelpRequestCB);
4208            XtFree(msg);
4209            XtFree(title);
4210       }
4211    }
4212    tt_free( file );
4213 }
4214
4215
4216
4217
4218 /************************************************************************
4219  *
4220  *  ViewDirectoryHandler
4221  *      This function is called upon the dt directory message
4222  *      being received.  The name of the directory is extracted
4223  *      out of the message and a function is called to create
4224  *      a view of the directory.
4225  *
4226  ************************************************************************/
4227
4228 static void
4229 ViewDirectoryHandler(
4230    Tt_message msg)
4231 {
4232    int i, j, k;
4233    char *msgFile;
4234    int numArgs;
4235
4236    initiating_view = NULL;
4237    msgFile = tt_message_file( msg );
4238    if (tt_is_err( tt_ptr_error( msgFile ))) msgFile = 0;
4239
4240    if(restrictMode)
4241    {
4242       if(msgFile && strncmp(msgFile, "~", 1) != 0 )
4243       {
4244          if((strcmp(users_home_dir, "/") != 0) &&
4245             (strncmp(msgFile, users_home_dir, strlen(users_home_dir)-1) != 0))
4246          {
4247             char *tmpStr, *errTitle, *errMsg, *dmsg;
4248
4249             tmpStr = GETMESSAGE(32, 2, "File Manager Open Directory Error");
4250             errTitle = XtNewString(tmpStr);
4251             tmpStr = GETMESSAGE(2,20,"You cannot switch to folder:\n\n%s\n\nYou are not allowed to view this folder\nbecause it is a restricted folder.");
4252             errMsg = XtNewString(tmpStr);
4253             dmsg = XtMalloc(strlen(errMsg)+strlen(msgFile)+1);
4254             sprintf(dmsg, errMsg, msgFile);
4255             _DtMessage(toplevel, errTitle, dmsg, NULL, HelpRequestCB);
4256
4257             XtFree(errTitle);
4258             XtFree(errMsg);
4259             XtFree(dmsg);
4260
4261             tt_free( msgFile );
4262             tt_message_reply( msg );
4263             tttk_message_destroy( msg );
4264             return;
4265          }
4266       }
4267    }
4268
4269    numArgs = tt_message_args_count( msg );
4270    if (tt_is_err( tt_int_error( numArgs ))) numArgs = 0;
4271    if (numArgs > 0)
4272    {
4273       special_view = True;
4274       special_treeType = UNSET_VALUE;
4275       special_treeFiles = UNSET_VALUE;
4276       special_viewType = UNSET_VALUE;
4277       special_orderType = UNSET_VALUE;
4278       special_directionType = UNSET_VALUE;
4279       special_randomType = UNSET_VALUE;
4280       special_restricted = NULL;
4281       special_title = NULL;
4282       special_helpVol = XtNewString(DTFILE_HELP_NAME);
4283       for(i = 0; i < numArgs; i++)
4284       {
4285          char *vtype;
4286          char *val;
4287          vtype = tt_message_arg_type( msg, i );
4288          if ((vtype == 0) || (tt_is_err( tt_ptr_error( vtype )))) {
4289             continue;
4290          }
4291          val = tt_message_arg_val( msg, i );
4292          if(strcmp(vtype, "-title") == 0)
4293          {
4294             special_title = XtNewString(val);
4295          }
4296          else if(strcmp(vtype, "-help_volume") == 0)
4297          {
4298             special_helpVol = XtNewString(val);
4299          }
4300          if(strcmp(vtype, "-tree") == 0)
4301          {
4302             DtfileStringToTree(val, &special_treeType);
4303          }
4304          else if(strcmp(vtype, "-tree_files") == 0)
4305          {
4306             DtfileStringToTreeFiles(val, &special_treeFiles);
4307          }
4308          else if(strcmp(vtype, VIEW_HEADER) == 0)
4309          {
4310             DtfileStringToView(val, &special_viewType);
4311          }
4312          else if(strcmp(vtype, "-order") == 0)
4313          {
4314             DtfileStringToOrder(val, &special_orderType);
4315          }
4316          else if(strcmp(vtype, "-direction") == 0)
4317          {
4318             DtfileStringToDirection(val, &special_directionType);
4319          }
4320          else if(strcmp(vtype, "-grid") == 0)
4321          {
4322             DtfileStringToGrid(val, &special_randomType);
4323          }
4324          else if(strcmp(vtype, RESTRICTED_HEADER) == 0)
4325          {
4326             special_restricted = XtNewString(msgFile);
4327          }
4328          tt_free( val );
4329          tt_free( vtype );
4330
4331          if ((restrictMode) && (!special_restricted))
4332          {
4333             char *ptr;
4334
4335             ptr = strrchr(users_home_dir, '/');
4336             *ptr = '\0';
4337             special_restricted = XtNewString(users_home_dir);
4338             *ptr = '/';
4339          }
4340       }
4341    }
4342    else if (restrictMode)
4343    {
4344      char *ptr;
4345
4346      special_view = True;
4347      special_treeType = treeType;
4348      special_treeFiles = treeFiles;
4349      special_viewType = viewType;
4350      special_orderType = orderType;
4351      special_directionType = directionType;
4352      special_randomType = randomType;
4353
4354      ptr = strrchr(users_home_dir, '/');
4355      *ptr = '\0';
4356      special_restricted = XtNewString(users_home_dir);
4357      *ptr = '/';
4358
4359      special_title = NULL;
4360      special_helpVol = XtNewString(DTFILE_HELP_NAME);
4361
4362    }
4363    else
4364       special_view = False;
4365
4366    OpenDirectories (msgFile, NULL);
4367
4368    tt_free( msgFile );
4369    tt_message_reply( msg );
4370    tttk_message_destroy( msg );
4371 }
4372
4373
4374
4375
4376 /************************************************************************
4377  *
4378  *  ViewDirectoryProc
4379  *      This function is called upon the dt directory message
4380  *      being received.  The name of the directory is extracted
4381  *      out of the message and a function is called to create
4382  *      a view of the directory.  This function is passed directly
4383  *      to DtActionInvoke to be used as a callback.
4384  *
4385  ************************************************************************/
4386
4387 DialogData *
4388 ViewDirectoryProc(
4389    char* root_dir,
4390    int restricted,
4391    Tt_message msg
4392 )
4393 {
4394    DialogData *return_data;
4395
4396    if(restrictMode)
4397    {
4398       if(root_dir && strncmp(root_dir, "~", 1) != 0 )
4399       {
4400          if((strcmp(users_home_dir, "/") != 0) &&
4401             (strncmp(root_dir, users_home_dir, strlen(users_home_dir)-1) != 0))
4402          {
4403             char *tmpStr, *errTitle, *errMsg, *dmsg;
4404
4405             tmpStr = GETMESSAGE(32, 2, "File Manager Open Directory Error");
4406             errTitle = XtNewString(tmpStr);
4407             tmpStr = GETMESSAGE(2,20,"You cannot switch to folder:\n\n%s\n\nYou are not allowed to view this folder\nbecause it is a restricted folder.");
4408             errMsg = XtNewString(tmpStr);
4409             dmsg = XtMalloc(strlen(errMsg)+strlen(root_dir)+1);
4410             sprintf(dmsg, errMsg, root_dir);
4411             _DtMessage(toplevel, errTitle, dmsg, NULL, HelpRequestCB);
4412
4413             XtFree(errTitle);
4414             XtFree(errMsg);
4415             XtFree(dmsg);
4416             return NULL;
4417          }
4418       }
4419    }
4420
4421    initiating_view = NULL;
4422    special_view = True;
4423    special_treeType = treeType;
4424    special_treeFiles = treeFiles;
4425    special_viewType = viewType;
4426    special_orderType = orderType;
4427    special_directionType = directionType;
4428    special_randomType = randomType;
4429
4430    if (restricted) {
4431      special_restricted = XtNewString(root_dir);
4432    }
4433    else {
4434      special_restricted = NULL;
4435    }
4436
4437    if ((restrictMode) && (!special_restricted))
4438    {
4439       char *ptr;
4440
4441       ptr = strrchr(users_home_dir, '/');
4442       *ptr = '\0';
4443       special_restricted = XtNewString(users_home_dir);
4444       *ptr = '/';
4445    }
4446
4447    special_title = NULL;
4448    special_helpVol = XtNewString(DTFILE_HELP_NAME);
4449
4450    return_data = GetNewView (home_host_name, root_dir, NULL, NULL, msg);
4451
4452    if ((!return_data) && msg)
4453    {
4454       tt_message_reply(msg);
4455       tttk_message_destroy( msg );
4456    }
4457
4458    return(return_data);
4459 }
4460
4461
4462
4463 /************************************************************************
4464  *
4465  *  ViewHomeDirectoryHandler
4466  *      This function is called upon the dt home directory message
4467  *      being received.  The home directory is extracted from the
4468  *      users uid and used to open the directory.
4469  *
4470  ************************************************************************/
4471
4472
4473 static void
4474 ViewHomeDirectoryHandler(
4475    Tt_message msg)
4476 {
4477    register int i, j, k;
4478    struct passwd * pwInfo;
4479    char * homeDir;
4480    char * tmp_path;
4481    char full_path[MAX_PATH + 1];
4482    struct stat stat_buf;
4483    int numArgs;
4484
4485    /* We have a new view so set initiating_view to null */
4486    initiating_view = NULL;
4487
4488    if ((homeDir = getenv("HOME")) == NULL || strlen (homeDir) == 0)
4489    {
4490       pwInfo = getpwuid (getuid());
4491       homeDir = pwInfo->pw_dir;
4492    }
4493
4494    /* Look and see if we have a default environment file present */
4495    tmp_path = _DtCreateDtDirs(display);
4496
4497    numArgs = 0;
4498    if (msg) numArgs = tt_message_args_count(msg);
4499    if (tt_is_err(tt_int_error(numArgs))) numArgs = 0;
4500    if (numArgs > 0)
4501    {
4502       special_view = True;
4503       special_treeType = UNSET_VALUE;
4504       special_treeFiles = UNSET_VALUE;
4505       special_viewType = UNSET_VALUE;
4506       special_orderType = UNSET_VALUE;
4507       special_directionType = UNSET_VALUE;
4508       special_randomType = UNSET_VALUE;
4509       special_restricted = NULL;
4510       special_title = NULL;
4511       special_helpVol = XtNewString(DTFILE_HELP_NAME);
4512       for(i = 0; i < numArgs; i++)
4513       {
4514          char *vtype;
4515          char *val;
4516          vtype = tt_message_arg_type( msg, i );
4517          if ((vtype == 0) || (tt_is_err( tt_ptr_error( vtype )))) {
4518             continue;
4519          }
4520          val = tt_message_arg_val(msg, i);
4521          if(strcmp(vtype, "-title") == 0)
4522          {
4523             special_title = XtNewString(val);
4524          }
4525          else if(strcmp(vtype, "-help_volume") == 0)
4526          {
4527             special_helpVol = XtNewString(val);
4528          }
4529          if(strcmp(vtype, "-tree") == 0)
4530          {
4531             DtfileStringToTree(val, &special_treeType);
4532          }
4533          else if(strcmp(vtype, "-tree_files") == 0)
4534          {
4535             DtfileStringToTreeFiles(val, &special_treeFiles);
4536          }
4537          else if(strcmp(vtype, VIEW_HEADER) == 0)
4538          {
4539             DtfileStringToView(val, &special_viewType);
4540          }
4541          else if(strcmp(vtype, "-order") == 0)
4542          {
4543             DtfileStringToOrder(val, &special_orderType);
4544          }
4545          else if(strcmp(vtype, "-direction") == 0)
4546          {
4547             DtfileStringToDirection(val, &special_directionType);
4548          }
4549          else if(strcmp(vtype, "-grid") == 0)
4550          {
4551             DtfileStringToGrid(val, &special_randomType);
4552          }
4553          else if(strcmp(vtype, RESTRICTED_HEADER) == 0)
4554          {
4555             special_restricted = XtNewString(val);
4556          }
4557          tt_free( val );
4558          tt_free( vtype );
4559       }
4560    }
4561    else if (restrictMode)
4562    {
4563      char *ptr;
4564
4565      special_view = True;
4566      special_treeType = treeType;
4567      special_treeFiles = treeFiles;
4568      special_viewType = viewType;
4569      special_orderType = orderType;
4570      special_directionType = directionType;
4571      special_randomType = randomType;
4572
4573      ptr = strrchr(users_home_dir, '/');
4574      *ptr = '\0';
4575      special_restricted = XtNewString(users_home_dir);
4576      *ptr = '/';
4577
4578      special_title = NULL;
4579      special_helpVol = XtNewString(DTFILE_HELP_NAME);
4580    }
4581    else
4582       special_view = False;
4583
4584    if (tmp_path == NULL)
4585       OpenDirectories (homeDir, NULL);
4586    else
4587    {
4588      sprintf(full_path, "%s/%s", tmp_path, HOME_SETTINGS_FILENAME);
4589      XtFree(tmp_path);
4590
4591      /* Stat the file and make sure its there */
4592      if(numArgs > 0)
4593      {
4594         if (stat (full_path, &stat_buf) == 0 && numArgs < 1)
4595         {
4596            restoreType = HOME_RESTORE;
4597            RestoreSession(full_path, HOME_RESTORE, NULL);
4598            restoreType = NORMAL_RESTORE;
4599         }
4600         else
4601         {
4602            char *ptr;
4603
4604            ptr = strrchr(users_home_dir, '/');
4605            *ptr = '\0';
4606            strcpy(full_path, users_home_dir);
4607            *ptr = '/';
4608            OpenDirectories (full_path, NULL);
4609         }
4610      }
4611      else if (numArgs < 1 && stat (full_path, &stat_buf) == 0)
4612      {
4613         restoreType = HOME_RESTORE;
4614         RestoreSession(full_path, HOME_RESTORE, NULL);
4615         restoreType = NORMAL_RESTORE;
4616      }
4617      else
4618      {
4619        char *ptr;
4620
4621        ptr = strrchr(users_home_dir, '/');
4622
4623        if( ptr != users_home_dir )
4624          *ptr = '\0';
4625
4626        strcpy(full_path, users_home_dir);
4627        *ptr = '/';
4628
4629        OpenDirectories (full_path, NULL);
4630      }
4631    }
4632
4633    if(msg)
4634    {
4635      tt_message_reply(msg);
4636      tttk_message_destroy(msg);
4637    }
4638 }
4639
4640 /************************************************************************
4641  *
4642  *  ViewToolsDirectroyHandler
4643  *      This function is called upon the dt tools message
4644  *      being received.  The names of the tools directories are
4645  *      retrieved from libXue, a view is created and the change
4646  *      directory dialog for the view is displayed with the
4647  *      set of directories contained in the list.
4648  *
4649  ************************************************************************/
4650
4651 static void
4652 ViewToolsDirectoryHandler(
4653    Tt_message msg)
4654 {
4655    register int i;
4656    char * tmp_path = NULL;
4657    char * tool_dir = NULL;
4658    char * msgFile = NULL;
4659    int numArgs = 0;
4660
4661    /* We have a new view so set initiating_view to null */
4662    initiating_view = NULL;
4663
4664    /* Look and see if we have a default environment file present */
4665    tmp_path = _DtCreateDtDirs(display);
4666
4667    if (msg) msgFile = tt_message_file(msg);
4668    if (tt_is_err(tt_ptr_error(msgFile))) msgFile = 0;
4669
4670    if (msg) numArgs = tt_message_args_count(msg);
4671    if (tt_is_err(tt_int_error( numArgs ))) numArgs = 0;
4672
4673    if(msgFile != NULL)
4674    {
4675       if(numArgs > 0)
4676       {
4677          char *link_point = NULL;
4678          char *root_toolbox = NULL;
4679          char *user_install_point = NULL;
4680
4681          special_view = True;
4682          special_treeType = treeType;
4683          special_treeFiles = treeFiles;
4684          special_viewType = viewType;
4685          special_orderType = orderType;
4686          special_directionType = directionType;
4687          special_randomType = randomType;
4688          special_restricted = XtNewString(msgFile);
4689          special_title = NULL;
4690          special_helpVol = XtNewString(DTFILE_HELP_NAME);
4691          for(i = 0; i < numArgs; i++)
4692          {
4693             char *vtype;
4694             char *val;
4695             vtype = tt_message_arg_type( msg, i );
4696             if ((vtype == 0) || (tt_is_err( tt_ptr_error( vtype )))) {
4697                continue;
4698             }
4699             val = tt_message_arg_val( msg, i );
4700             if(strcmp(vtype, "-title") == 0)
4701             {
4702                special_title = XtNewString(val);
4703             }
4704             else if(strcmp(vtype, "-help_volume") == 0)
4705             {
4706                special_helpVol = XtNewString(val);
4707             }
4708             else if(strcmp(vtype, "-root") == 0)
4709             {
4710                root_toolbox = XtNewString(val);
4711             }
4712             else if(strcmp(vtype, "-common_link_point") == 0)
4713             {
4714                link_point = XtNewString(val);
4715             }
4716             else if(strcmp(vtype, "-user_install_point") == 0)
4717             {
4718                user_install_point = XtNewString(val);
4719             }
4720             if(strcmp(vtype, "-tree") == 0)
4721             {
4722                DtfileStringToTree(val, &special_treeType);
4723             }
4724             else if(strcmp(vtype, "-tree_files") == 0)
4725             {
4726                DtfileStringToTreeFiles(val, &special_treeFiles);
4727             }
4728             else if(strcmp(vtype, VIEW_HEADER) == 0)
4729             {
4730                DtfileStringToView(val, &special_viewType);
4731             }
4732             else if(strcmp(vtype, "-order") == 0)
4733             {
4734                DtfileStringToOrder(val, &special_orderType);
4735             }
4736             else if(strcmp(vtype, "-direction") == 0)
4737             {
4738                DtfileStringToDirection(val, &special_directionType);
4739             }
4740             else if(strcmp(vtype, "-grid") == 0)
4741             {
4742                DtfileStringToGrid(val, &special_randomType);
4743             }
4744             else if(strcmp(vtype, RESTRICTED_HEADER) == 0)
4745             {
4746                ;
4747             }
4748             tt_free( val );
4749             tt_free( vtype );
4750          }
4751          /* Due to the use of tooltalk messaging, app manager objects
4752             that are dragged either to the desktop or to the front
4753             panel are identified by their fully resolved names (ie.
4754             /usr/dt/appconfig/appmanager/$LANG/.... as opposed to
4755             /var/dt/appconfig/appmanager/$DTUSERSESSION/....).  In order
4756             for the File Manager to treat these objects as links existing
4757             in the /var/.... directory, we use the following ugly code:
4758
4759               1. Search the incoming path for $LANG (if you can't find
4760                  $LANG, try C since this is the default).
4761               2. Concatenate the path following $LANG to the path for the
4762                  root toolbox (this comes in with the tooltalk message
4763                  so that we don't have to hardcode it).
4764               3. Call OpenDirectories with the new path that you have
4765                  created and with the root toolbox path as the restricted
4766                  directory.
4767
4768             This problem is further complicated by:
4769               1. Users traversing into APPGROUPs.
4770               2. Users opening the parent folders for workspace APPGROUPs.
4771
4772             For situation 1, File Manager kicks the user into the App Manager
4773             if he/she traverses into an APPGROUP.  BUT we don't want to
4774             make modifications to the path as we do above.
4775             So, if there is nothing following $LANG or if we can't find
4776             $LANG in the path,
4777             (ie. /var/dt/appconfig/appmanager/$DTUSERSESSION), call
4778             OpenDirectories with no parameter changes.
4779
4780             For situation 2, File Manager is unable to distinguish between
4781             workspace objects dragged from /usr/.... or /var/...., so
4782             the parent folder for all workspace APPGROUPS is considered to
4783             be in the /var path.  In addition to the OpenAppGroup action,
4784             there is an OpenParentAppGroup action which also triggers
4785             ViewToolsDirectoryHandler but sends in an additional
4786             parameter (user_install_point).
4787             If we know that this msg was generated by the OpenParentAppGroup
4788             action
4789             AND nothing follows $LANG.
4790               Modify the parameters as above.
4791             OR we can't find $LANG but we can find the user_install_point
4792               (user's personal appgroup path).
4793               Concatenate the path following .dt/appmanager to the path for the
4794               root toolbox. Call OpenDirectories with the new path and the
4795               root toolbox as the restricted directory.
4796          */
4797          if( root_toolbox )
4798          {
4799             if( link_point )
4800             {
4801                char *ptr;
4802
4803                if ((user_install_point) &&
4804                    (ptr = strstr(msgFile, user_install_point)))
4805                {
4806                   ptr += strlen(user_install_point);
4807                   tool_dir = XtMalloc(strlen(root_toolbox) + strlen(ptr) + 1);
4808                   sprintf(tool_dir, "%s%s", root_toolbox, ptr);
4809                   XtFree(special_restricted);
4810                   special_restricted = XtNewString(root_toolbox);
4811                }
4812                else
4813                {
4814                   ptr = strstr(msgFile, link_point);
4815
4816                   if (!ptr)
4817                   {
4818                      XtFree(link_point);
4819                      link_point = XtNewString("C");
4820                      ptr = strstr(msgFile, link_point);
4821                   }
4822
4823                   if (ptr)
4824                   {
4825                      ptr += strlen(link_point);
4826                      if (strcmp(ptr, "") != 0)
4827                      {
4828                         tool_dir = XtMalloc(strlen(root_toolbox) +
4829                                             strlen(ptr) + 1);
4830                         sprintf(tool_dir, "%s%s", root_toolbox, ptr);
4831                         XtFree(special_restricted);
4832                         special_restricted = XtNewString(root_toolbox);
4833                      }
4834                      else if (user_install_point)
4835                      {
4836                         tool_dir = XtNewString(root_toolbox);
4837                         XtFree(special_restricted);
4838                         special_restricted = XtNewString(root_toolbox);
4839                      }
4840                   }
4841                }
4842             }
4843          }
4844          XtFree(link_point);
4845          XtFree(root_toolbox);
4846          XtFree(user_install_point);
4847       }
4848       else if (restrictMode)
4849       {
4850          char *ptr;
4851
4852          special_view = True;
4853          ptr = strrchr(users_home_dir, '/');
4854          *ptr = '\0';
4855          special_restricted = XtNewString(users_home_dir);
4856          *ptr = '/';
4857       }
4858       else
4859          special_view = False;
4860    }
4861
4862    if (tmp_path == NULL)
4863    {
4864       if (tool_dir)
4865          OpenDirectories (tool_dir, special_restricted);
4866       else if (msgFile != NULL)
4867          OpenDirectories (msgFile, special_restricted);
4868    }
4869    else
4870    {
4871       char full_path[MAX_PATH + 1];
4872       struct stat stat_buf;
4873
4874       sprintf(full_path, "%s/%s", tmp_path, TOOL_SETTINGS_FILENAME);
4875       XtFree(tmp_path);
4876
4877       /* Stat the file and make sure its there */
4878       if (stat (full_path, &stat_buf) == 0 && numArgs > 0)
4879       {
4880          DialogData * dialog_data;
4881          FileMgrData * file_mgr_data;
4882
4883          restoreType = TOOL_RESTORE;
4884          if (tool_dir)
4885             RestoreSession(full_path, TOOL_RESTORE, tool_dir);
4886          else
4887             RestoreSession(full_path, TOOL_RESTORE, msgFile);
4888          dialog_data = (DialogData *)view_set[view_count - 1]->dialog_data;
4889          file_mgr_data = (FileMgrData *) dialog_data->data;
4890          application_args.tool_width = file_mgr_data->width;
4891          application_args.tool_height = file_mgr_data->height;
4892          restoreType = NORMAL_RESTORE;
4893       }
4894       else
4895       {
4896          if (tool_dir)
4897             OpenDirectories (tool_dir, special_restricted);
4898          else if (msgFile != NULL)
4899             OpenDirectories (msgFile, special_restricted);
4900       }
4901    }
4902
4903    if( msgFile )
4904      tt_free( msgFile );
4905
4906    if( msg )
4907    {
4908      tt_message_reply( msg );
4909      tttk_message_destroy( msg );
4910    }
4911
4912    if (tool_dir)
4913       XtFree(tool_dir);
4914 }
4915
4916
4917 /************************************************************************
4918  *
4919  *  ExitHandler
4920  *      This function is called upon the DtSTOP message.
4921  *
4922  ************************************************************************/
4923
4924 static void
4925 ExitHandler(
4926    Tt_message msg,
4927    XtPointer clientData,
4928    String * messageFields,
4929    int numFields)
4930 {
4931    tt_message_reply( msg );
4932    tttk_message_destroy( msg );
4933    FinalizeToolTalkSession( );
4934    exit(0);
4935 }
4936
4937
4938 /*
4939  * This is the message handling function responsible for reloading
4940  * the filetype and action databases, and then updating our collection
4941  * of action menu items, and updating all open views.
4942  */
4943
4944 static void
4945 ReloadDatabases(void)
4946 {
4947    int i;
4948    DialogData * dialog_data;
4949    FileMgrData * file_mgr_data;
4950    FileMgrRec  * file_mgr_rec;
4951    FileViewData *file_view_data;
4952    DesktopRec *desktopWindow;
4953
4954    DtDbLoad();
4955
4956    XmeFlushIconFileCache ( NULL );
4957
4958    /* Update each directory_set view, both mapped and not */
4959    UpdateDirectorySet();
4960
4961    /* Force action menus to update the next time they're posted */
4962    XtFree(fileMgrPopup.action_pane_file_type);
4963    fileMgrPopup.action_pane_file_type = NULL;
4964    XtFree(desktop_data->popupMenu->action_pane_file_type);
4965    desktop_data->popupMenu->action_pane_file_type = NULL;
4966
4967    /* Update each view */
4968    for (i = 0; i < view_count; i++)
4969    {
4970       dialog_data = (DialogData *)view_set[i]->dialog_data;
4971       file_mgr_data = (FileMgrData *) dialog_data->data;
4972       file_mgr_rec = (FileMgrRec *) file_mgr_data->file_mgr_rec;
4973       XtFree(file_mgr_rec->action_pane_file_type);
4974       file_mgr_rec->action_pane_file_type = NULL;
4975       UpdateFilterAfterDBReread(file_mgr_data->filter_active);
4976       UpdateFilterAfterDBReread(file_mgr_data->filter_edit);
4977       FileMgrRedisplayFiles(file_mgr_rec, file_mgr_data, False);
4978    }
4979
4980    /* go through the desktop objects to make sure the icons change
4981     * Do this by setting the logical_type to -l, CheckDesktop will
4982     * then update the logical type and the icon
4983     */
4984    for(i = 0; i < desktop_data->numIconsUsed; i++)
4985    {
4986       desktopWindow = desktop_data->desktopWindows[i];
4987       file_view_data = desktopWindow->file_view_data;
4988
4989       file_view_data->file_data->logical_type = NULL;
4990    }
4991    CheckDesktop();
4992 }
4993
4994
4995 /*
4996  * Whenever a directory view or drawer view is closed, we need to remove
4997  * any of its text field children, so that they will not magically reappear
4998  * should this view be reused from the cache to view the same directory later.
4999  */
5000
5001 static void
5002 RemoveTextFields (
5003    XtPointer client_data,
5004    DialogData * old_dialog_data,
5005    DialogData * new_dialog_data)
5006 {
5007    FileMgrRec * file_mgr_rec;
5008    XmManagerWidget file_window;
5009    int i;
5010    int num_children;
5011
5012    file_mgr_rec = (FileMgrRec *) _DtGetDialogInstance(old_dialog_data);
5013    file_window = (XmManagerWidget) file_mgr_rec->file_window;
5014    num_children = file_window->composite.num_children;
5015
5016    for (i = 0; i < num_children; i++)
5017    {
5018       if (XmIsTextField(file_window->composite.children[i]))
5019          XtDestroyWidget(file_window->composite.children[i]);
5020    }
5021
5022    _DtFreeDialogData (new_dialog_data);
5023 }
5024
5025
5026 /*
5027  * This function searches the view list, and returns the file_mgr_data
5028  * associated with the passed-in widget.
5029  */
5030
5031 FileMgrData *
5032 ReturnDesktopPtr (
5033    Widget w)
5034 {
5035    int i;
5036    DialogData * dialog_data;
5037    FileMgrData * file_mgr_data;
5038
5039    for (i = 0; i < view_count; i++)
5040    {
5041       dialog_data = (DialogData *) view_set[i]->dialog_data;
5042       file_mgr_data = (FileMgrData *) dialog_data->data;
5043
5044       if (w == ((FileMgrRec *)file_mgr_data->file_mgr_rec)->file_window ||
5045           w == ((FileMgrRec *)file_mgr_data->file_mgr_rec)->shell)
5046          return(file_mgr_data);
5047    }
5048
5049    return(NULL);
5050 }
5051
5052
5053 PixmapData *
5054 CheckForOpenDirectory(
5055      FileViewData *order_list,
5056      DirectorySet *directory_set,
5057      FileMgrData *file_mgr_data,
5058      char * logical_type)
5059 {
5060    int i;
5061    char *ptr;
5062    char *file_type_name, *new_file_type_name;
5063    char directory_name[MAX_PATH];
5064    char * real_dir_name;
5065    FileMgrRec *file_mgr_rec;
5066    int icon_size;
5067    PixmapData *pixmapData = NULL;
5068
5069    if (file_mgr_data->view == BY_NAME_AND_ICON)
5070      icon_size = LARGE;
5071    else
5072      icon_size = SMALL;
5073
5074    file_mgr_rec = (FileMgrRec *)file_mgr_data->file_mgr_rec;
5075
5076    if (strcmp (directory_set->name, "/") != 0)
5077      sprintf( directory_name, "%s/%s", directory_set->name, order_list->file_data->file_name);
5078    else
5079      sprintf( directory_name, "%s%s", directory_set->name, order_list->file_data->file_name );
5080
5081    (void) DtEliminateDots (directory_name);
5082
5083    real_dir_name = XtNewString(directory_name);
5084
5085    for(i = 0; i < view_count; i++)
5086    {
5087       if(strcmp(real_dir_name, view_set[i]->directory_name) == 0)
5088       {
5089          file_type_name = order_list->file_data->logical_type;
5090          new_file_type_name = (char *)XtMalloc(strlen(file_type_name)
5091                                                + strlen(ICON_OPEN_PREFIX) + 1);
5092          sprintf(new_file_type_name, "%s%s", ICON_OPEN_PREFIX, file_type_name);
5093          pixmapData = _DtRetrievePixmapData(new_file_type_name,
5094                                             NULL,
5095                                             NULL,
5096                                             file_mgr_rec->file_window,
5097                                             icon_size);
5098          XtFree(new_file_type_name);
5099          break;
5100       }
5101    }
5102    XtFree(real_dir_name);
5103
5104    if(pixmapData == NULL || pixmapData->iconFileName == NULL)
5105    {
5106      if( pixmapData != NULL )
5107      {
5108        DtDtsFreeAttributeValue(pixmapData->hostPrefix);
5109        DtDtsFreeAttributeValue(pixmapData->instanceIconName);
5110        DtDtsFreeAttributeValue(pixmapData->iconName);
5111        XtFree((char *)pixmapData);
5112      }
5113
5114        pixmapData = _DtRetrievePixmapData(logical_type,
5115                                           NULL,
5116                                           NULL,
5117                                           file_mgr_rec->file_window,
5118                                           icon_size);
5119    }
5120
5121    return(pixmapData);
5122 }
5123
5124
5125 /*
5126  * The is the menu callback function for cleaning up a view.
5127  */
5128
5129 void
5130 CleanUp (
5131    Widget w,
5132    XtPointer client_data,
5133    XtPointer call_data)
5134 {
5135    Widget mbar;
5136    Arg args[2];
5137    FileMgrRec * file_mgr_rec;
5138    DialogData * dialog_data;
5139    FileMgrData * file_mgr_data;
5140    int i, j;
5141    XmManagerWidget file_window;
5142    char * name;
5143    FileViewData * file_view_data;
5144    XRectangle textExtent;
5145    Position x, y;
5146
5147    if ((int)(XtArgVal) client_data == FM_POPUP)
5148      mbar = XtParent(w);
5149    else
5150      mbar = XmGetPostedFromWidget(XtParent(w));
5151
5152    XmUpdateDisplay(w);
5153    XtSetArg(args[0], XmNuserData, &file_mgr_rec);
5154    XtGetValues(mbar, args, 1);
5155
5156    /* Ignore accelerators when we're insensitive */
5157    if ((file_mgr_rec->menuStates & CLEAN_UP) == 0)
5158       return;
5159
5160    /* Ignore accelerators received after we're unposted */
5161    if ((dialog_data = _DtGetInstanceData((XtPointer)file_mgr_rec)) == NULL)
5162       return;
5163
5164    file_mgr_data = (FileMgrData *)dialog_data->data;
5165
5166    /* Reset the grid size, so it will be recalculated later. */
5167    file_mgr_data->grid_height = 0;
5168    file_mgr_data->grid_width = 0;
5169
5170    if(file_mgr_data->object_positions)
5171       FreePositionInfo(file_mgr_data);
5172
5173    /* CLEAN_UP_OP is not really a menu state.
5174       It's a flag to let GetFileData in FileMgr.c (call when the directory
5175       is being reread) not to reload icon positions from the .!dt<userid> file.
5176    */
5177    file_mgr_rec->menuStates |= CLEAN_UP_OP;
5178
5179    /* Re-layout the view */
5180    FileMgrRedisplayFiles(file_mgr_rec, file_mgr_data, False);
5181
5182    if ((file_mgr_data->show_type == SINGLE_DIRECTORY) &&
5183         (file_mgr_data->view != BY_ATTRIBUTES) &&
5184         (file_mgr_data->positionEnabled == RANDOM_ON))
5185    {
5186       ((PreferencesData *)(file_mgr_data->preferences->data))->positionEnabled =
5187           RANDOM_ON;
5188    }
5189    else
5190    {
5191       /* Update the preferences dialog */
5192       ((PreferencesData *)(file_mgr_data->preferences->data))->positionEnabled =
5193           RANDOM_OFF;
5194    }
5195
5196    /* Move any text widget, to keep them in sync with their icons */
5197    file_window = (XmManagerWidget)file_mgr_rec->file_window;
5198
5199    for (j = 0; j < file_window->composite.num_children; j++)
5200    {
5201       if (XmIsTextField(file_window->composite.children[j]) &&
5202           !file_window->composite.children[j]->core.being_destroyed)
5203       {
5204          XtSetArg(args[0], XmNuserData, &name);
5205          XtGetValues(file_window->composite.children[j], args, 1);
5206
5207          /* Find the associated icon data */
5208          /* @@@ this won't work for tree mode! */
5209          for (i = 0; i < file_mgr_data->directory_set[0]->file_count; i++)
5210          {
5211             file_view_data = file_mgr_data->directory_set[0]->file_view_data[i];
5212             if (strcmp(name, file_view_data->file_data->file_name) == 0)
5213             {
5214                _DtIconGetTextExtent_r(file_view_data->widget, &textExtent);
5215                x = textExtent.x;
5216                y = textExtent.y -
5217                    (Dimension)(file_window->composite.children[j]->core.height -
5218                     textExtent.height)/(Dimension)2;
5219                XtSetArg (args[0], XmNx, x);
5220                XtSetArg (args[1], XmNy, y);
5221                XtSetValues (file_window->composite.children[j], args, 2);
5222                break;
5223             }
5224          }
5225       }
5226    }
5227
5228    if ((file_mgr_rec->menuStates & CLEAN_UP_OP))
5229      file_mgr_rec->menuStates  &= ~CLEAN_UP_OP;
5230 }
5231
5232 /*************************************<->*************************************
5233  *
5234  *  DtfileCvtStringToObjPlace (args, numArgs, fromVal, toVal)
5235  *
5236  *
5237  *  Description:
5238  *  -----------
5239  *  This function converts a string to an desktop placement scheme description.
5240  *
5241  *
5242  *  Inputs:
5243  *  ------
5244  *  args = NULL (don't care)
5245  *
5246  *  numArgs = 0 (don't care)
5247  *
5248  *  fromVal = resource value to convert
5249  *
5250  *
5251  *  Outputs:
5252  *  -------
5253  *  toVal = descriptor to use to return converted value
5254  *
5255  *************************************<->***********************************/
5256
5257 static void
5258 DtfileCvtStringToObjPlace (
5259           XrmValue *args,
5260           Cardinal numArgs,
5261           XrmValue *fromVal,
5262           XrmValue *toVal)
5263 {
5264     unsigned char       *pch = (unsigned char *) (fromVal->addr);
5265     unsigned char       *pchNext;
5266     int         len;
5267     static long cval;
5268     char tmp[2];
5269     Boolean     fPrimarySet = False;
5270     Boolean     fSecondarySet = False;
5271
5272 /*
5273  * Icon placement layout values:
5274  */
5275
5276 #define OBJ_PLACE_BOTTOM_STR           (unsigned char *)"bottom"
5277 #define OBJ_PLACE_LEFT_STR             (unsigned char *)"left"
5278 #define OBJ_PLACE_RIGHT_STR            (unsigned char *)"right"
5279 #define OBJ_PLACE_TOP_STR              (unsigned char *)"top"
5280
5281
5282     /*
5283      * Convert the icon placement resource value:
5284      */
5285
5286     cval = 0;
5287
5288     while (*pch && _DtNextToken (pch, &len, &pchNext))
5289     {
5290         tmp[0] = pch[len];
5291         pch[len] = '\0';
5292         switch( *pch )
5293         {
5294             case 'B':
5295             case 'b':
5296                 if (_DtStringsAreEquivalent((char *)pch, (char *)OBJ_PLACE_BOTTOM_STR))
5297                 {
5298                   if (!fPrimarySet)
5299                   {
5300                     cval |= OBJ_PLACE_BOTTOM_PRIMARY;
5301                     fPrimarySet = True;
5302                   }
5303                   else if (!fSecondarySet)
5304                   {
5305                     if (!(cval &
5306                           (OBJ_PLACE_BOTTOM_PRIMARY | OBJ_PLACE_TOP_PRIMARY)))
5307                     {
5308                       cval |= OBJ_PLACE_BOTTOM_SECONDARY;
5309                       fSecondarySet = True;
5310                     }
5311                   }
5312                 }
5313                 break;
5314
5315
5316             case 'L':
5317             case 'l':
5318                 if (_DtStringsAreEquivalent ((char *)pch, (char *)OBJ_PLACE_LEFT_STR))
5319                 {
5320                   if (!fPrimarySet)
5321                   {
5322                     cval |= OBJ_PLACE_LEFT_PRIMARY;
5323                     fPrimarySet = True;
5324                   }
5325                   else if (!fSecondarySet)
5326                   {
5327                     if (!(cval &
5328                           (OBJ_PLACE_LEFT_PRIMARY | OBJ_PLACE_RIGHT_PRIMARY)))
5329                     {
5330                       cval |= OBJ_PLACE_LEFT_SECONDARY;
5331                       fSecondarySet = True;
5332                     }
5333                   }
5334                 }
5335                 break;
5336
5337             case 'R':
5338             case 'r':
5339                 if (_DtStringsAreEquivalent ((char *)pch, (char *)OBJ_PLACE_RIGHT_STR))
5340                 {
5341                   if (!fPrimarySet)
5342                   {
5343                     cval |= OBJ_PLACE_RIGHT_PRIMARY;
5344                     fPrimarySet = True;
5345                   }
5346                   else if (!fSecondarySet)
5347                   {
5348                     if (!(cval &
5349                           (OBJ_PLACE_RIGHT_PRIMARY | OBJ_PLACE_LEFT_PRIMARY)))
5350                     {
5351                       cval |= OBJ_PLACE_RIGHT_SECONDARY;
5352                       fSecondarySet = True;
5353                     }
5354                   }
5355                 }
5356                 break;
5357
5358             case 'T':
5359             case 't':
5360                 if (_DtStringsAreEquivalent ((char *)pch, (char *)OBJ_PLACE_TOP_STR))
5361                 {
5362                   if (!fPrimarySet)
5363                   {
5364                     cval |= OBJ_PLACE_TOP_PRIMARY;
5365                     fPrimarySet = True;
5366                   }
5367                   else if (!fSecondarySet)
5368                   {
5369                     if (!(cval &
5370                           (OBJ_PLACE_TOP_PRIMARY | OBJ_PLACE_BOTTOM_PRIMARY)))
5371                     {
5372                       cval |= OBJ_PLACE_TOP_SECONDARY;
5373                       fSecondarySet = True;
5374                     }
5375                   }
5376                 }
5377
5378                 break;
5379         }
5380         pch[len] = tmp[0];
5381         pch = pchNext;
5382     }
5383
5384     if (!fPrimarySet)
5385     {
5386         cval =  OBJ_PLACE_TOP_PRIMARY;
5387     }
5388     if (!fSecondarySet)
5389     {
5390         if (cval & (OBJ_PLACE_LEFT_PRIMARY | OBJ_PLACE_RIGHT_PRIMARY))
5391         {
5392             cval |= OBJ_PLACE_TOP_SECONDARY;
5393         }
5394         else        {
5395             cval |= OBJ_PLACE_RIGHT_SECONDARY;
5396         }
5397     }
5398
5399
5400     (*toVal).size = sizeof (long);
5401     (*toVal).addr = (XtPointer) &cval;
5402
5403 } /* END OF FUNCTION DtfileCvtStringToObjPlace */
5404
5405 /*************************************<->*************************************
5406  *
5407  *  _DtNextToken (pchIn, pLen, ppchNext)
5408  *
5409  *
5410  *  Description:
5411  *  -----------
5412  *  XXDescription ...
5413  *
5414  *
5415  *  Inputs:
5416  *  ------
5417  *  pchIn = pointer to start of next token
5418  *
5419  *
5420  *  Outputs:
5421  *  -------
5422  *  pLen  =    pointer to integer containing number of characters in next token
5423  *  ppchNext = address of pointer to following token
5424  *
5425  *  Return =   next token or NULL
5426  *
5427  *
5428  *  Comments:
5429  *  --------
5430  *  None.
5431  *
5432  *************************************<->***********************************/
5433
5434 static unsigned char
5435 *_DtNextToken (
5436         unsigned char *pchIn,
5437         int *pLen,
5438         unsigned char **ppchNext)
5439 {
5440     unsigned char *pchR = pchIn;
5441     register int   i;
5442 #ifdef MULTIBYTE
5443     register int   chlen;
5444
5445     for (i = 0; ((chlen = mblen ((char *)pchIn, MB_CUR_MAX)) > 0); i++)
5446     /* find end of word: requires singlebyte whitespace terminator */
5447     {
5448         if ((chlen == 1) && isspace (*pchIn))
5449         {
5450             break;
5451         }
5452         pchIn += chlen;
5453     }
5454
5455 #else
5456     for (i = 0; *pchIn && !isspace (*pchIn); i++, pchIn++)
5457     /* find end of word */
5458     {
5459     }
5460 #endif
5461
5462     /* skip to next word */
5463 #ifdef MULTIBYTE
5464     while (pchIn && (mblen ((char *)pchIn, MB_CUR_MAX) == 1) && isspace (*pchIn))
5465 #else
5466     while (pchIn && isspace (*pchIn))
5467 #endif
5468     {
5469         *pchIn++;
5470     }
5471
5472     *ppchNext = pchIn;
5473     *pLen = i;
5474     if (i)
5475     {
5476         return(pchR);
5477     }
5478     else
5479     {
5480        return(NULL);
5481     }
5482
5483 } /* END OF FUNCTION _DtNextToken */
5484
5485 /*************************************<->*************************************
5486  *
5487  *  DtfileCvtStringToOpenDir (args, numArgs, fromVal, toVal)
5488  *
5489  *
5490  *  Description:
5491  *  -----------
5492  *  This function converts a string to an desktop placement scheme description.
5493  *
5494  *
5495  *  Inputs:
5496  *  ------
5497  *  args = NULL (don't care)
5498  *
5499  *  numArgs = 0 (don't care)
5500  *
5501  *  fromVal = resource value to convert
5502  *
5503  *
5504  *  Outputs:
5505  *  -------
5506  *  toVal = descriptor to use to return converted value
5507  *
5508  *************************************<->***********************************/
5509
5510 static void
5511 DtfileCvtStringToOpenDir (
5512           XrmValue *args,
5513           Cardinal numArgs,
5514           XrmValue *fromVal,
5515           XrmValue *toVal)
5516 {
5517    char * in_str = (char *) (fromVal->addr);
5518    static int i;
5519
5520    toVal->size = sizeof (int);
5521    toVal->addr = (XtPointer) &i;
5522
5523    if (_DtStringsAreEquivalent (in_str, "current"))
5524       i = CURRENT;
5525    else if (_DtStringsAreEquivalent (in_str, "new"))
5526       i = NEW;
5527    else
5528       i = CURRENT;
5529 /*
5530    else
5531    {
5532       toVal->size = 0;
5533       toVal->addr = NULL;
5534       XtStringConversionWarning ((char *)fromVal->addr, "OpenDir");
5535    }
5536 */
5537 }
5538
5539 /*************************************<->*************************************
5540  *
5541  *  DtfileCvtStringToDTIcon (args, numArgs, fromVal, toVal)
5542  *
5543  *
5544  *  Description:
5545  *  -----------
5546  *  This function converts a string to an desktop placement scheme description.
5547  *
5548  *
5549  *  Inputs:
5550  *  ------
5551  *  args = NULL (don't care)
5552  *
5553  *  numArgs = 0 (don't care)
5554  *
5555  *  fromVal = resource value to convert
5556  *
5557  *
5558  *  Outputs:
5559  *  -------
5560  *  toVal = descriptor to use to return converted value
5561  *
5562  *************************************<->***********************************/
5563
5564 static void
5565 DtfileCvtStringToDTIcon (
5566           XrmValue *args,
5567           Cardinal numArgs,
5568           XrmValue *fromVal,
5569           XrmValue *toVal)
5570 {
5571    char * in_str = (char *) (fromVal->addr);
5572    static int i;
5573
5574    toVal->size = sizeof (int);
5575    toVal->addr = (XtPointer) &i;
5576
5577    if (_DtStringsAreEquivalent (in_str, "large"))
5578       i = LARGE;
5579    else if (_DtStringsAreEquivalent (in_str, "small"))
5580       i = SMALL;
5581    else if (_DtStringsAreEquivalent (in_str, "default"))
5582       i = LARGE;  /* for now, eventually want to look at screen width/height*/
5583    else
5584       i = LARGE;
5585 /*
5586    else
5587    {
5588       toVal->size = 0;
5589       toVal->addr = NULL;
5590       XtStringConversionWarning ((char *)fromVal->addr, "DesktopIcon");
5591    }
5592 */
5593 }
5594
5595 static void
5596 DtfileCvtStringToTree (
5597           XrmValue *args,
5598           Cardinal numArgs,
5599           XrmValue *fromVal,
5600           XrmValue *toVal)
5601 {
5602    char * in_str = (char *) (fromVal->addr);
5603    static int i;
5604
5605    toVal->size = sizeof (int);
5606    toVal->addr = (XtPointer) &i;
5607
5608    DtfileStringToTree(in_str, &i);
5609 }
5610
5611 static void
5612 DtfileCvtStringToTreeFiles (
5613           XrmValue *args,
5614           Cardinal numArgs,
5615           XrmValue *fromVal,
5616           XrmValue *toVal)
5617 {
5618    char * in_str = (char *) (fromVal->addr);
5619    static int i;
5620
5621    toVal->size = sizeof (int);
5622    toVal->addr = (XtPointer) &i;
5623
5624    DtfileStringToTreeFiles(in_str, &i);
5625 }
5626
5627 static void
5628 DtfileCvtStringToView (
5629           XrmValue *args,
5630           Cardinal numArgs,
5631           XrmValue *fromVal,
5632           XrmValue *toVal)
5633 {
5634    char * in_str = (char *) (fromVal->addr);
5635    static int i;
5636
5637    toVal->size = sizeof (int);
5638    toVal->addr = (XtPointer) &i;
5639
5640    DtfileStringToView(in_str, &i);
5641 }
5642
5643 static void
5644 DtfileCvtStringToOrder (
5645           XrmValue *args,
5646           Cardinal numArgs,
5647           XrmValue *fromVal,
5648           XrmValue *toVal)
5649 {
5650    char * in_str = (char *) (fromVal->addr);
5651    static int i;
5652
5653    toVal->size = sizeof (int);
5654    toVal->addr = (XtPointer) &i;
5655
5656    DtfileStringToOrder(in_str, &i);
5657 }
5658
5659 static void
5660 DtfileCvtStringToDirection (
5661           XrmValue *args,
5662           Cardinal numArgs,
5663           XrmValue *fromVal,
5664           XrmValue *toVal)
5665 {
5666    char * in_str = (char *) (fromVal->addr);
5667    static int i;
5668
5669    toVal->size = sizeof (int);
5670    toVal->addr = (XtPointer) &i;
5671
5672    DtfileStringToDirection(in_str, &i);
5673 }
5674
5675 static void
5676 DtfileCvtStringToGrid (
5677           XrmValue *args,
5678           Cardinal numArgs,
5679           XrmValue *fromVal,
5680           XrmValue *toVal)
5681 {
5682    char * in_str = (char *) (fromVal->addr);
5683    static int i;
5684
5685    toVal->size = sizeof (int);
5686    toVal->addr = (XtPointer) &i;
5687
5688    DtfileStringToGrid(in_str, &i);
5689 }
5690
5691 FileMgrData *
5692 CheckOpenDir (
5693           char * directory,
5694           char * host)
5695 {
5696    int i;
5697    FileMgrData *file_mgr_data;
5698    DialogData *dialog_data;
5699
5700    for(i = 0; i < view_count; i++)
5701    {
5702       if(strcmp(directory, view_set[i]->directory_name) == 0 &&
5703                             strcmp(host, view_set[i]->host_name) == 0)
5704       {
5705          dialog_data = (DialogData *) view_set[i]->dialog_data;
5706          file_mgr_data = (FileMgrData *) dialog_data->data;
5707          return(file_mgr_data);
5708       }
5709    }
5710    return(NULL);
5711 }
5712
5713 char *
5714 GetRestrictedDirectory (
5715           Widget widget)
5716 {
5717    int i;
5718    FileMgrData *file_mgr_data;
5719    FileMgrRec *file_mgr_rec;
5720    DialogData *dialog_data;
5721
5722    for(i = 0; i < view_count; i++)
5723    {
5724       dialog_data = (DialogData *) view_set[i]->dialog_data;
5725       file_mgr_data = (FileMgrData *) dialog_data->data;
5726       file_mgr_rec = (FileMgrRec *)file_mgr_data->file_mgr_rec;
5727       if(file_mgr_rec->current_directory_text == widget &&
5728                                           file_mgr_data->fast_cd_enabled)
5729       {
5730          return(file_mgr_data->restricted_directory);
5731       }
5732    }
5733    return((char *)NULL);
5734 }
5735
5736 static void
5737 DtfileStringToTree(
5738    char *str,
5739    int *type)
5740 {
5741    if (_DtStringsAreEquivalent (str, "on"))
5742       *type = MULTIPLE_DIRECTORY;
5743    else if (_DtStringsAreEquivalent (str, "off"))
5744       *type = SINGLE_DIRECTORY;
5745    else
5746       *type = UNSET_VALUE;
5747 }
5748
5749 static void
5750 DtfileStringToTreeFiles(
5751    char *str,
5752    int *type)
5753 {
5754    if (_DtStringsAreEquivalent (str, "never"))
5755       *type = TREE_FILES_NEVER;
5756    else if (_DtStringsAreEquivalent (str, "choose"))
5757       *type = TREE_FILES_CHOOSE;
5758    else if (_DtStringsAreEquivalent (str, "always"))
5759       *type = TREE_FILES_ALWAYS;
5760    else
5761       *type = UNSET_VALUE;
5762 }
5763
5764 static void
5765 DtfileStringToView(
5766    char *str,
5767    int *type)
5768 {
5769    if (_DtStringsAreEquivalent (str, "no_icon") ||
5770                             _DtStringsAreEquivalent (str, "no_icons"))
5771       *type = BY_NAME;
5772    else if (_DtStringsAreEquivalent (str, "large_icon") ||
5773                             _DtStringsAreEquivalent (str, "large_icons"))
5774       *type = BY_NAME_AND_ICON;
5775    else if (_DtStringsAreEquivalent (str, "small_icon") ||
5776                             _DtStringsAreEquivalent (str, "small_icons"))
5777       *type = BY_NAME_AND_SMALL_ICON;
5778    else if (_DtStringsAreEquivalent (str, "attributes"))
5779       *type = BY_ATTRIBUTES;
5780    else
5781       *type = UNSET_VALUE;
5782 }
5783
5784 static void
5785 DtfileStringToOrder(
5786    char *str,
5787    int *type)
5788 {
5789    if (_DtStringsAreEquivalent (str, "file_type"))
5790       *type = ORDER_BY_FILE_TYPE;
5791    else if (_DtStringsAreEquivalent (str, "alphabetical"))
5792       *type = ORDER_BY_ALPHABETICAL;
5793    else if (_DtStringsAreEquivalent (str, "date"))
5794       *type = ORDER_BY_DATE;
5795    else if (_DtStringsAreEquivalent (str, "size"))
5796       *type = ORDER_BY_SIZE;
5797    else
5798       *type = UNSET_VALUE;
5799 }
5800
5801
5802 static void
5803 DtfileStringToDirection(
5804    char *str,
5805    int *type)
5806 {
5807    if (_DtStringsAreEquivalent (str, "ascending"))
5808       *type = DIRECTION_ASCENDING;
5809    else if (_DtStringsAreEquivalent (str, "descending"))
5810       *type = DIRECTION_DESCENDING;
5811    else
5812       *type = UNSET_VALUE;
5813 }
5814
5815 static void
5816 DtfileStringToGrid(
5817    char *str,
5818    int *type)
5819 {
5820    if (_DtStringsAreEquivalent (str, "on"))
5821       *type = RANDOM_OFF;
5822    else if (_DtStringsAreEquivalent (str, "off"))
5823       *type = RANDOM_ON;
5824    else
5825       *type = UNSET_VALUE;
5826 }
5827
5828 static void
5829 SetupSendRequestArgs(
5830    ApplicationArgs application_args,
5831    Tt_message msg)
5832 {
5833    char *vtype;
5834    if(application_args.title != NULL)
5835    {
5836       tt_message_arg_add( msg, TT_IN, "-title", application_args.title );
5837    }
5838    if(application_args.restricted != NULL)
5839    {
5840       tt_message_arg_add( msg, TT_IN, RESTRICTED_HEADER, 0 );
5841    }
5842    vtype = VIEW_HEADER;
5843    switch( application_args.view )
5844    {
5845        case BY_NAME:
5846            tt_message_arg_add( msg, TT_IN, vtype, "no_icon" );
5847            break;
5848        case BY_NAME_AND_ICON:
5849            tt_message_arg_add( msg, TT_IN, vtype, "large_icon" );
5850            break;
5851        case BY_NAME_AND_SMALL_ICON:
5852            tt_message_arg_add( msg, TT_IN, vtype, "small_icon" );
5853            break;
5854        case BY_ATTRIBUTES:
5855            tt_message_arg_add( msg, TT_IN, vtype, "attributes" );
5856            break;
5857        default:
5858            tt_message_arg_add( msg, TT_IN, vtype, "none" );
5859            break;
5860    }
5861
5862    vtype = "-order";
5863    switch( application_args.order )
5864    {
5865        case ORDER_BY_FILE_TYPE:
5866            tt_message_arg_add( msg, TT_IN, vtype, "file_type" );
5867            break;
5868        case ORDER_BY_ALPHABETICAL:
5869            tt_message_arg_add( msg, TT_IN, vtype, "alphabetical" );
5870            break;
5871        case ORDER_BY_DATE:
5872            tt_message_arg_add( msg, TT_IN, vtype, "date" );
5873            break;
5874        case ORDER_BY_SIZE:
5875            tt_message_arg_add( msg, TT_IN, vtype, "size" );
5876            break;
5877        default:
5878            tt_message_arg_add( msg, TT_IN, vtype, "none" );
5879            break;
5880    }
5881
5882    vtype = "-direction";
5883    switch( application_args.direction )
5884    {
5885        case DIRECTION_ASCENDING:
5886            tt_message_arg_add( msg, TT_IN, vtype, "ascending" );
5887            break;
5888        case DIRECTION_DESCENDING:
5889            tt_message_arg_add( msg, TT_IN, vtype, "descending" );
5890            break;
5891        default:
5892            tt_message_arg_add( msg, TT_IN, vtype, "none" );
5893            break;
5894    }
5895
5896    vtype = "-grid";
5897    switch( application_args.grid )
5898    {
5899        case RANDOM_OFF:
5900            tt_message_arg_add( msg, TT_IN, vtype, "on" );
5901            break;
5902        case RANDOM_ON:
5903            tt_message_arg_add( msg, TT_IN, vtype, "off" );
5904            break;
5905        default:
5906            tt_message_arg_add( msg, TT_IN, vtype, "none" );
5907            break;
5908    }
5909    vtype = "-tree";
5910    switch( application_args.tree_view )
5911    {
5912        case MULTIPLE_DIRECTORY:
5913            tt_message_arg_add( msg, TT_IN, vtype, "on" );
5914            break;
5915        case SINGLE_DIRECTORY:
5916            tt_message_arg_add( msg, TT_IN, vtype, "off" );
5917            break;
5918        default:
5919            tt_message_arg_add( msg, TT_IN, vtype, "none" );
5920            break;
5921    }
5922
5923    vtype = "-tree_files";
5924    switch( application_args.tree_files )
5925    {
5926        case TREE_FILES_NEVER:
5927            tt_message_arg_add( msg, TT_IN, vtype, "never" );
5928            break;
5929        case TREE_FILES_CHOOSE:
5930            tt_message_arg_add( msg, TT_IN, vtype, "choose" );
5931            break;
5932        case TREE_FILES_ALWAYS:
5933            tt_message_arg_add( msg, TT_IN, vtype, "always" );
5934            break;
5935        default:
5936            tt_message_arg_add( msg, TT_IN, vtype, "none" );
5937            break;
5938    }
5939
5940    if(application_args.help_volume != NULL)
5941    {
5942       tt_message_arg_add( msg, TT_IN, "-help_volume",
5943                           application_args.help_volume );
5944    }
5945 }
5946
5947 /*
5948  * This routine is used by ForceMyIconOpen to get the "Open" filetype and
5949  * find out what the new icon is.  It then places that icon in the
5950  * correct icon gadget.
5951  */
5952 static void
5953 BuildAndShowIconName(
5954    char *file_type_name,
5955    unsigned char view,
5956    unsigned char show_type,
5957    Widget widget)
5958 {
5959    char *new_file_type_name;
5960    char *ptr;
5961    Arg args[1];
5962    PixmapData *pixmapData;
5963
5964    new_file_type_name = (char *)XtMalloc(strlen(file_type_name) +
5965                                          strlen(ICON_OPEN_PREFIX) + 1);
5966    sprintf(new_file_type_name, "%s%s", ICON_OPEN_PREFIX, file_type_name);
5967
5968    if (view == BY_NAME_AND_ICON && show_type != MULTIPLE_DIRECTORY)
5969      pixmapData = _DtRetrievePixmapData(new_file_type_name,
5970                                         NULL,
5971                                         NULL,
5972                                         widget,
5973                                         LARGE);
5974    else
5975      pixmapData = _DtRetrievePixmapData(new_file_type_name,
5976                                         NULL,
5977                                         NULL,
5978                                         widget,
5979                                         SMALL);
5980
5981    if(pixmapData && pixmapData->iconFileName)
5982    {
5983      XtSetArg (args[0], XmNimageName, pixmapData->iconFileName);
5984      XtSetValues(widget, args, 1);
5985    }
5986 /*
5987    else
5988    {
5989      XtSetArg (args[0], XmNimageName, NULL);
5990      XtSetValues(widget, args, 1);
5991    }
5992 */
5993
5994    _DtCheckAndFreePixmapData(new_file_type_name,
5995                              widget,
5996                              (DtIconGadget) widget,
5997                              pixmapData);
5998
5999    XtFree(new_file_type_name);
6000 }
6001
6002
6003 /*
6004  * Given a directory name, this function will see if a view of the parent
6005  * directory is open; if so, then it will update the icon representing
6006  * this icon, in the parent view, so that it is drawn as 'closed'.  This
6007  * function must only be called if openDirType == NEW.
6008  */
6009
6010 void
6011 ForceMyIconClosed (
6012    char * host_name,
6013    char * directory_name)
6014 {
6015    register int i;
6016    register int j;
6017    register int k;
6018    Arg args[1];
6019    FileViewData * file_view_data = NULL;
6020    DialogData *dialog_data;
6021    FileMgrData *file_mgr_data;
6022    DesktopRec *desktopWindow;
6023    char * parent;
6024    char * fname;
6025    PixmapData *pixmapData;
6026
6027    /* find the parent directory of the one just removed */
6028    parent = _DtPName(directory_name);
6029    fname =  DName(directory_name);
6030
6031    /* first check to see if any File Manager views have this directory */
6032    for (i = 0; i < view_count; i++)
6033    {
6034       dialog_data = (DialogData *) view_set[i]->dialog_data;
6035       file_mgr_data = (FileMgrData *) dialog_data->data;
6036
6037       /* loop through until we find the file_view_data structure for
6038        * the directory to force open */
6039
6040       for(j = 0; j < file_mgr_data->directory_count; j++)
6041       {
6042          if (strcmp(parent, file_mgr_data->directory_set[j]->name) == 0)
6043          {
6044             for (k = 0; k < file_mgr_data->directory_set[j]->file_count; k++)
6045             {
6046                file_view_data =
6047                        file_mgr_data->directory_set[j]->file_view_data[k];
6048                if (strcmp(file_view_data->file_data->file_name, fname) == 0)
6049                   goto search_done;
6050             }
6051             break;
6052          }
6053       }
6054    }
6055
6056    search_done:
6057
6058    if( (file_view_data) && (file_mgr_data->view != BY_NAME) )
6059    {
6060       if (file_mgr_data->view == BY_NAME_AND_ICON  &&
6061                        file_mgr_data->show_type != MULTIPLE_DIRECTORY)
6062          pixmapData = _DtRetrievePixmapData(
6063                                  file_view_data->file_data->logical_type,
6064                                  fname,
6065                                  parent,
6066                                  file_view_data->widget,
6067                                  LARGE);
6068       else
6069          pixmapData = _DtRetrievePixmapData(
6070                                  file_view_data->file_data->logical_type,
6071                                  fname,
6072                                  parent,
6073                                  file_view_data->widget,
6074                                  SMALL);
6075
6076       if (pixmapData)
6077         XtSetArg (args[0], XmNimageName, pixmapData->iconFileName);
6078       else
6079         XtSetArg (args[0], XmNimageName, NULL);
6080       XtSetValues (file_view_data->widget, args, 1);
6081
6082       _DtCheckAndFreePixmapData(file_view_data->file_data->logical_type,
6083                                 file_view_data->widget,
6084                                 (DtIconGadget) file_view_data->widget,
6085                                 pixmapData);
6086    }
6087
6088    /* now check to see if any desktop objects are this directory */
6089    for(j = 0; j < desktop_data->numIconsUsed; j++)
6090    {
6091       char buf[MAX_PATH];
6092
6093       desktopWindow = desktop_data->desktopWindows[j];
6094       file_view_data = desktopWindow->file_view_data;
6095
6096       sprintf(buf, "%s/%s", desktopWindow->dir_linked_to,
6097                             desktopWindow->file_name);
6098       DtEliminateDots (buf);
6099
6100       if( (strcmp(buf, directory_name) == 0) &&
6101           (strcmp(desktopWindow->host, host_name) == 0) )
6102       {
6103          pixmapData = _DtRetrievePixmapData(
6104               file_view_data->file_data->logical_type,
6105               fname,
6106               NULL,
6107               desktopWindow->shell,
6108               desktopIconType);
6109
6110          if(pixmapData)
6111            XtSetArg (args[0], XmNimageName, pixmapData->iconFileName);
6112          else
6113            XtSetArg (args[0], XmNimageName, NULL);
6114          XtSetValues (desktopWindow->iconGadget, args, 1);
6115
6116          _DtCheckAndFreePixmapData(
6117                  desktopWindow->file_view_data->file_data->logical_type,
6118                  desktopWindow->shell,
6119                  (DtIconGadget) desktopWindow->iconGadget,
6120                  pixmapData);
6121       }
6122    }
6123 }
6124
6125
6126 /*************************************************************************
6127  *
6128  * MarqueeSelect - this is the callback which gets called when there is
6129  *    a marquee event happening on the root window.
6130  *
6131  ************************************************************************/
6132 static void
6133 MarqueeSelect (
6134       Widget w,
6135       int type,
6136       Position x,
6137       Position y,
6138       Dimension width,
6139       Dimension height,
6140       XtPointer client_data)
6141 {
6142    int i;
6143    Window   rootWindow;
6144    Atom     pCurrent;
6145    Screen   *currentScreen;
6146    int      screen;
6147    char     *workspace_name=NULL;
6148    Display *display;
6149
6150
6151    switch (type)
6152    {
6153        case DT_WSM_MARQUEE_SELECTION_TYPE_BEGIN:
6154             display = XtDisplay(desktop_data->desktopWindows[0]->shell);
6155             screen = XDefaultScreen(display);
6156             currentScreen = XScreenOfDisplay(display, screen);
6157             rootWindow = RootWindowOfScreen(currentScreen);
6158
6159             if(DtWsmGetCurrentWorkspace(display, rootWindow, &pCurrent)
6160                                                             == Success)
6161             {
6162                workspace_name = XGetAtomName (display, pCurrent);
6163                CleanUpWSName(workspace_name);
6164             }
6165             else
6166                workspace_name =
6167                   XtNewString(desktop_data->workspaceData[0]->name);
6168
6169             for(i = 0; i < desktop_data->numWorkspaces; i++)
6170             {
6171                if(strcmp(workspace_name,
6172                            desktop_data->workspaceData[i]->name) == 0)
6173                {
6174                   DeselectAllDTFiles(desktop_data->workspaceData[i]);
6175                   break;
6176                }
6177             }
6178             XtFree(workspace_name);
6179             break;
6180
6181        case DT_WSM_MARQUEE_SELECTION_TYPE_END:
6182             CheckDesktopMarquee(x, y, width, height);
6183             break;
6184
6185        case DT_WSM_MARQUEE_SELECTION_TYPE_CANCEL:
6186             break;
6187
6188        case DT_WSM_MARQUEE_SELECTION_TYPE_CONTINUE:
6189             CheckDesktopMarquee(x, y, width, height);
6190             break;
6191
6192        default:
6193             break;
6194    }
6195 }
6196
6197
6198 /*
6199  * We must wait for the message response, before exiting
6200  */
6201
6202 static void
6203 WaitForResponseAndExit( void )
6204
6205 {
6206    XtMainLoop();
6207 }
6208
6209 static void
6210 ExitApp(
6211         XtPointer clientData,
6212         DtString words[],
6213         int num_fields )
6214
6215 {
6216   FinalizeToolTalkSession( );
6217   exit(0);
6218 }
6219
6220
6221 /*
6222  * Puts up an Error dialog with Cancel and Help unmapped in the
6223  * center of the screen. The last argument is the OK callback
6224  */
6225
6226 static Widget
6227 post_dialog(Widget parent, char *title, char *msg, void (*DtErrExitCB)())
6228 {
6229    Widget dialog, dialogShell;
6230    XmString message_text, ok;
6231    Arg args[10];
6232    Dimension dialogWd, dialogHt;
6233    int n = 0;
6234
6235    ok = XmStringCreateLocalized ((char*)_DtOkString);
6236    message_text = XmStringCreateLocalized (msg);
6237
6238    XtSetArg(args[n], XmNautoUnmanage, False); n++;
6239    XtSetArg(args[n], XmNokLabelString, ok); n++;
6240    XtSetArg(args[n], XmNtitle, title); n++;
6241    XtSetArg(args[n], XmNmessageString, message_text); n++;
6242    XtSetArg(args[n], XmNdialogStyle, XmDIALOG_FULL_APPLICATION_MODAL); n++;
6243    XtSetArg (args[n], XmNdefaultPosition, False); n++;
6244    XtSetArg(args[n], XmNuseAsyncGeometry, True); n++;
6245
6246    dialog = XmCreateErrorDialog (parent, title, args, n);
6247    XtAddCallback (dialog, XmNokCallback, DtErrExitCB, NULL);
6248    XtUnmanageChild (XmMessageBoxGetChild (dialog, XmDIALOG_CANCEL_BUTTON));
6249    XtUnmanageChild (XmMessageBoxGetChild (dialog, XmDIALOG_HELP_BUTTON));
6250
6251    /* Disable the frame menu from dialog since we don't want the user
6252       to be able to close dialogs with the frame menu */
6253
6254    dialogShell = XtParent(dialog);
6255    XtSetArg(args[0], XmNmappedWhenManaged, False);
6256    XtSetArg(args[1], XmNmwmDecorations, MWM_DECOR_ALL | MWM_DECOR_MENU);
6257    XtSetValues(dialogShell, args, 2);
6258    XtManageChild (dialog);
6259    XtRealizeWidget (dialogShell);
6260
6261    /* Center the dialog */
6262
6263    XtSetArg(args[0], XmNwidth, &dialogWd);
6264    XtSetArg(args[1], XmNheight, &dialogHt);
6265    XtGetValues(dialog, args, 2);
6266    XtSetArg (args[0], XmNx,
6267                 (WidthOfScreen(XtScreen(dialog)) - dialogWd) / 2);
6268    XtSetArg (args[1], XmNy,
6269                 (HeightOfScreen(XtScreen(dialog)) - dialogHt) / 2);
6270    XtSetArg (args[2], XmNmappedWhenManaged, True); 
6271    XtSetValues (dialog, args, 3);
6272
6273    XtSetArg(args[0], XmNmappedWhenManaged, True);
6274    XtSetValues(dialogShell, args, 1);
6275
6276    XtManageChild (dialog);
6277    XmStringFree(message_text);
6278
6279    return (dialog);
6280 }
6281
6282 /*  
6283  * This is the Callback when an error occurs while trying to create 
6284  * the .dt folder or sub-folders. Application exits.
6285  */
6286
6287 static void 
6288 DtErrExitCB (Widget dialog, XtPointer client_data, XtPointer call_data)
6289 {
6290 XtPopdown (XtParent (dialog));
6291 FinalizeToolTalkSession();
6292 exit (1);
6293 }
6294
6295 #if defined(__osf__) || defined(__OpenBSD__)
6296 extern void
6297 sigchld_handler(int signo)      /* Do not use the arg signo at the moment */
6298 {
6299     pid_t   pid;
6300     int     stat_loc;
6301
6302     /*
6303       On DUX, the process remains in the ZOMBIE
6304       state untill parent invokes wait or waitpid.
6305     */
6306
6307     pid = waitpid(-1, &stat_loc, WNOHANG);
6308     /* Child exit handling code follows, if any */
6309 }
6310 #endif /* __osf__ */