 /*
  * Khoros: $Id: exit.c,v 1.4 1992/03/20 22:43:00 dkhoros Exp $
  */

#if !defined(lint) && !defined(SABER)
static char rcsid[] = "Khoros: $Id: exit.c,v 1.4 1992/03/20 22:43:00 dkhoros Exp $";
#endif

 /*
  * $Log: exit.c,v $
 * Revision 1.4  1992/03/20  22:43:00  dkhoros
 * VirtualPatch5
 *
  */ 

/*
 *----------------------------------------------------------------------
 *
 * Copyright 1990, University of New Mexico.  All rights reserved.
 *
 * Permission to copy and modify this software and its documen-
 * tation only for internal use in your organization is hereby
 * granted, provided that this notice is retained thereon and
 * on all copies.  UNM makes no representations as too the sui-
 * tability and operability of this software for any purpose.
 * It is provided "as is" without express or implied warranty.
 * 
 * UNM DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FIT-
 * NESS.  IN NO EVENT SHALL UNM BE LIABLE FOR ANY SPECIAL,
 * INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY OTHER DAMAGES WHAT-
 * SOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER
 * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
 * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PER-
 * FORMANCE OF THIS SOFTWARE.
 * 
 * No other rights, including for example, the right to redis-
 * tribute this software and its documentation or the right to
 * prepare derivative works, are granted unless specifically
 * provided in a separate license agreement.
 *---------------------------------------------------------------------
 */

#include "unmcopyright.h"	 /* Copyright 1990 by UNM */
#include "cantata.h"
#include <X11/Xproto.h>

static void quick_exit();

/* >>>>>>>>>>>>>>>>>>>>>>>>>>>>> <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
   >>>>                                                       <<<<
   >>>>	    file name:  error.c                               <<<<
   >>>>                                                       <<<<
   >>>>   description:                                        <<<<
   >>>>                                                       <<<<
   >>>>      routines:  xvl_exit_program()		      <<<<
   >>>>                 xvl_quick_exit()		      <<<<
   >>>>                                                       <<<<
   >>>> modifications:					      <<<<
   >>>>                                                       <<<<
   >>>>>>>>>>>>>>>>>>>>>>>>>>>>> <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< */



/************************************************************
*
* Routine Name:  xvl_exit_program
*
*      Purpose:  This routine is used to exit cantata when an
*		 an error occurs or if we need to abnormally exit
*		 cantata.
*
*        Input:  None
*
*
*   Written By: Mark Young
*
*************************************************************/


xvl_exit_program()
{
	FILE	 *file;
	int	 status;
	static   int exiting = False;
	char	 ans[MaxLength], command[MaxLength], *username, *getenv();


	if (main_workspace == NULL)
	   exit(1);

	if (exiting == True)
	   xvl_quick_exit();
	else
	   exiting = True;

	/*
	 *  If the workspace is not empty then we are going to want to
	 *  give the user the option of saving their workspace before
	 *  exiting.
	 */
	if (main_workspace->glyphs != NULL)
	{
	   do
	   {
	      (void) fprintf(stderr,"Do you wish to save the current workspace \
before exiting? (y/n)... ");

	      if (gets(ans) == NULL)
	      {
		 ans[0] = 'A';
		 break;
	      }

	      if (isupper(ans[0]))
	         ans[0] = tolower(ans[0]);

	   } while (ans[0] != 'y' && ans[0] != 'n');

	   if (ans[0] == 'y')
	   {
	      if (xvl_save_workspace(main_workspace, main_workspace->glyphs,
			"saved.workspace", True))
	      {
	         (void) fprintf(stderr,"\n\nSaving cantata workspace in 'saved.\
workspace.Z' .  To recover restart cantata by:\n\t%% cantata -restore \
saved.workspace.Z\n\n");
	      }
	      else
	      {
	         (void) fprintf(stderr, "\n\nSorry! Unable to save cantata \
workspace. Goodbye...  :-(\n\n");
	      }
	   }
	   else if (ans[0] == 'A')
	   {
	      status = xvl_save_workspace(main_workspace,main_workspace->glyphs,
			"saved.workspace", True);

              if (!(username = getenv("USER")))
		 file = stderr;
	      else
	      {
		sprintf(command,"/bin/mail %s", username);
		if ((file = popen(command, "w")) == NULL)
		   file = stderr;
	      }

	      if (status == True)
	      {
		 (void) fprintf(file,"Subject: cantata killed...\n");
	         (void) fprintf(file,"\n\nSaved cantata workspace in 'saved.\
workspace'.\nTo recover restart cantata by:\n\t%% cantata -restore \
saved.workspace\n\n");
	      }
	      else
	      {
		 (void) fprintf(file,"Subject: cantata killed...\n");
	         (void) fprintf(file, "\n\nSorry! Unable to save cantata \
workspace. Goodbye...  :-(\n\n");
	      }
	      if (file != stderr) pclose(file);
	   }
	}

	/*
	 * xvl_destroy_workspace(main_workspace) will delete all
	 * associated workspaces and glyph's.  We then exit the program.
	 */
	if (display != NULL)
	{
	   xvl_destroy_workspace(main_workspace);
	   xvl_stop_phantomd();
	   xvl_stop_negotiator();
	}
	exit(1);
}



/************************************************************
*
* Routine Name:  xvl_quick_exit
*
*      Purpose:  This routine is used quickly exit cantata.
*		 xvl_quick_exit() sole responsibilty is to
*		 remove any temporary files.
*
*        Input:  None
*
*
*   Written By: Mark Young
*
*************************************************************/


xvl_quick_exit()
{
	static int  exiting = False;


	if (exiting == True)
	   exit(1);
	else
	   exiting = True;

	quick_exit(main_workspace);
	quick_exit(clipboard);
	xvl_stop_phantomd();
	xvl_stop_negotiator();
	exit(1);
}

static void quick_exit(workspace)

Workspace *workspace;
{
	Glyph	  *glyph;
	Node	  *node;

	GlyphList *glyphlist;
	NodeList  *nodelist;


	if (workspace->var_file != stderr && workspace->var_file != NULL)
	{
	   fclose(workspace->var_file);
	   unlink(workspace->var_name);
	}

	glyphlist = workspace->glyphs;
	while (glyphlist != NULL)
	{
	   glyph = glyphlist->glyph;

	   nodelist = glyph->output_list;
	   while (nodelist != NULL)
	   {
	      node = nodelist->node;
	      if (node->filename != NULL)
	      {
		 if (node->temp_file)
		    xvl_unlink_tempfile(node);
	      }
	      nodelist = nodelist->next;
	   }

	   if (glyph->type == PROCEDURE)
	      quick_exit(glyph->val.macro);

	   glyphlist = glyphlist->next;
	}
}
