/* wftp-ls.c
 *
 ****************************************************************
 * Copyright (C) 2001, 2002, 2003  Tom Lord
 * 
 * See the file "COPYING" for further information about
 * the copyright and warranty status of this work.
 */


#include "config-options.h"
#include "hackerlab/os/signal.h"
#include "hackerlab/cmd/main.h"
#include "hackerlab/vu-network/url-socket.h"
#include "ftp-utils/wftp/wftp-client.h"



static t_uchar * program_name = "wftp-ls";
static t_uchar * usage = "wftp-ls [options] [path]";
static t_uchar * version_string = (cfg__std__package " from regexps.com\n"
				   "\n"
				   "Copyright 2001, 2002, 2003 Tom Lord\n"
				   "\n"
				   "This is free software; see the source for copying conditions.\n"
				   "There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A\n"
				   "PARTICULAR PURPOSE.\n"
				   "\n"
				   "Report bugs to " cfg__with_ftp_bug_mail ".\n"
				   "\n");

#define OPTS(OP, OP2) \
  OP (opt_help_msg, "h", "help", 0, \
      "Display a help message and exit.") \
  OP (opt_long_help, "H", 0, 0, \
      "Display a verbose help message and exit.") \
  OP (opt_version, "V", "version", 0, \
      "Display a release identifier string") \
  OP2 (opt_version, 0, 0, 0, "and exit.") \
  OP (opt_verbose, "v", "verbose", 0, \
      "be verbose") \
  OP (opt_long, "l", "long", 0, \
      "print a long-format listing") \
  OP (opt_withftp, "W", "with-ftp", 1, \
      "Specify the with-ftp server to contact")

static t_uchar long_help[] = ("return a remote directory listing in a with-ftp session\n"
			      "List the contents of remote directory PATH in a with-ftp\n"
			      "session.  With \"-l\" or \"--long\", a long-format directory\n"
			      "listing is printed: but there are no guarantees about what\n"
			      "information is in a long listing, or how it is formatted.\n");

enum options
{
  OPTS (OPT_ENUM, OPT_IGN)  
};

struct opt_desc opts[] = 
{
  OPTS (OPT_DESC, OPT_DESC)
    {-1, 0, 0, 0, 0}
};



int
main (int argc, char * argv[])
{
  int use_passive_mode = 1;
  int o;
  struct opt_parsed * option;
  t_uchar * with_ftp;
  int verbose;
  t_uchar * cmd;

  {
    sigset_t interesting_signal_mask;

    sigfillset (&interesting_signal_mask);
    sigdelset (&interesting_signal_mask, SIGHUP);
    sigdelset (&interesting_signal_mask, SIGINT);
    sigdelset (&interesting_signal_mask, SIGTRAP);
    if (0 > sigprocmask (SIG_SETMASK, &interesting_signal_mask, 0))
      {
	panic ("sigprocmask(2)");
      }
  }

  cmd = "nlist";

  url_socket_push_client_handler (url_socket_unix, 0, 0);
  url_socket_push_client_handler (url_socket_inet, 0, 0);

  safe_buffer_fd (0, 0, O_RDONLY, 0);
  safe_buffer_fd (1, 0, O_WRONLY, 0);
  safe_buffer_fd (2, 0, O_WRONLY, 0);

  option = 0;
  with_ftp = 0;
  verbose = 0;

  while (1)
    {
      o = opt_standard (lim_use_must_malloc, &option, opts, &argc, argv, program_name, usage, version_string, long_help, opt_help_msg, opt_long_help, opt_version);
      if (o == opt_none)
	break;
      switch (o)
	{
	default:
	  safe_printfmt (2, "unhandled option `%s'\n", option->opt_string);
	  panic ("internal error parsing arguments");

	usage_error:
	  opt_usage (2, argv[0], program_name, usage, 1);
	  exit (1);

	/* bogus_arg: */
	  safe_printfmt (2, "ill-formed argument for `%s' (`%s')\n", option->opt_string, option->arg_string);
	  goto usage_error;

	case opt_verbose:
	  verbose = 1;
	  break;
	  
	case opt_long:
	  cmd = "list";
	  break;
	  
	case opt_withftp:
	  with_ftp = option->arg_string;
	  break;
	}
    }

  if ((argc < 1) || (argc > 2))
    goto usage_error;

  if (!with_ftp)
    {
      with_ftp = getenv ("WFTP");
      if (!with_ftp)
	{
	  safe_printfmt (2, "%s: -W (--with-ftp) not specified and $WFTP not set\n", program_name);
	  goto usage_error;
	}
    }

  {
    int errn;
    t_uchar * path;
    int wftp_in;
    int wftp_out;
    int cmd_ok;
    t_uchar * reply_message;
    long reply_message_len;

    path = ((argc == 2) ? argv[1] : "");

    if (str_chr_index (path, '\n') || str_chr_index (path, ' '))
      {
	safe_printfmt (2, "%s: illegal path (%s)\n", program_name, path);
	exit (1);
      }

    if (0 > wftp_client_init (&errn, &wftp_in, &wftp_out, with_ftp, use_passive_mode))
      {
	safe_printfmt (2, "\n%s: unable to connect to with-ftp server\n  error: %s\n  path: %s\n\n", program_name, errno_to_string (errn), path);
	exit (1);
      }

    if (0 > wftp_client_get_data_cmd (0, &errn, &cmd_ok, &reply_message, &reply_message_len, wftp_in, wftp_out, -1, 1, 1, cmd, "%s\n", path))
      {
	safe_printfmt (2, "\n%s: error interacting with with-ftp server\n  error: %s\n  path: %s\n\n", program_name, errno_to_string (errn), path);
	exit (1);
      }

    if (cmd_ok)
      {
	if (verbose)
	  {
	    safe_printfmt (1, "%s: operation succeeded\n%.*s\n", program_name, (int)reply_message_len, reply_message);
	    exit (0);
	  }
      }
    else
      {
	char * site;

	site = getenv ("WFTP_SITE");

	if (!site)
	  site = "WFTP_SITE not set in environment";

	safe_printfmt (2, "\n%s: %.*s  site: %s\n  path: %s\n\n", program_name, (int)reply_message_len, reply_message, site, path);
		       
	exit (1);
      }

  }

  return 0;
}

/* tag: Tom Lord Tue Dec  4 14:41:24 2001 (wftp-ls.c)
 */
