/* editor.c:
 *
 ****************************************************************
 * Copyright (C) 2003 Colin Walters
 *
 * See the file "COPYING" for further information about
 * the copyright and warranty status of this work.
 */


#include "hackerlab/bugs/panic.h"
#include "hackerlab/os/stdarg.h"
#include "hackerlab/os/sys/types.h"
#include "hackerlab/os/unistd.h"
#include "hackerlab/os/sys/wait.h"
#include "hackerlab/os/signal.h"
#include "hackerlab/char/str.h"
#include "hackerlab/fs/file-names.h"
#include "hackerlab/arrays/ar.h"
#include "hackerlab/vu/safe.h"
#include "tla/libarch/editor.h"



int
arch_run_editor (t_uchar * name)
{
  int exit_status = 0;
#if 0
  t_uchar * editors[] =  {"/usr/bin/nano",  "/usr/bin/nano-tiny",
			  "/usr/bin/emacs", "/usr/bin/vi", 0};
#endif
  t_uchar * editor = 0;
  t_uchar ** argv = 0;
  int pid;
  int x;

  editor = getenv ("EDITOR");
#if 0
  if (!editor)
    {
      t_uchar ** editorp = 0;
      for (editorp = editors; *editorp != NULL; editorp++)
	if (!safe_access (*editorp, X_OK)) {
	  editor = *editorp;
	  break;
	}
    }
#endif
  if (!editor)
    {
      safe_printfmt (2, "arch_run_editor: please set $EDITOR\n");
      exit (2);
    }

  *(t_uchar **)ar_push ((void **)&argv, 0, sizeof (t_uchar *)) = str_save (0, editor);
  *(t_uchar **)ar_push ((void **)&argv, 0, sizeof (t_uchar *)) = str_save (0, name);
  *(t_uchar **)ar_push ((void **)&argv, 0, sizeof (t_uchar *)) = 0;

  pid = fork ();
  if (pid == -1)
    panic ("unable to fork for editor");

  if (pid)
    {
      int status;
      int wait_pid;

      wait_pid = waitpid (pid, &status, 0);
      if (wait_pid < 0)
	{
	  panic_msg ("error waiting for editor subprocess");
	  kill (0, SIGKILL);
	  panic ("error waiting for editor subprocess");
	}
      if (WIFSIGNALED (status))
	{
	  safe_printfmt (2, "\n");
	  safe_printfmt (2, "arch_run_editor: editor subprocess killed by signal %d\n", WTERMSIG (status));
	  safe_printfmt (2, "\n");
	  exit (2);
	  return -1;
	}
      else if (!WIFEXITED (status))
	{
	  panic_msg ("waitpid returned for a non-exited editor process");
	  kill (0, SIGKILL);
	  panic ("waitpid returned for a non-exited editor process and kill failed");
	  return -1;
	}
      else
	{
	  exit_status = WEXITSTATUS (status);
	}
    }
  else
    {
      execvp (editor, (char **)argv);
      panic ("arch_run_editor: execvp for editor script returned to caller");
      exit (2);
    }

  for (x = 0; x < ar_size ((void *)argv, 0, sizeof (t_uchar *)); ++x)
      lim_free (0, argv[x]);
  ar_free ((void **)&argv, 0);

  return exit_status;
}




/* tag: Colin Walters Wed, 19 Nov 2003 22:26:51 -0500 (editor.c)
 */
