/* mount.cc

This file is part of Cygwin.

This software is a copyrighted work licensed under the terms of the
Cygwin license.  Please consult the file "CYGWIN_LICENSE" for
details. */

#include <stdio.h>
#include <sys/mount.h>
#include <sys/stat.h>
#include <mntent.h>
#include <windows.h>
#include <sys/cygwin.h>
#include <cygwin/version.h>
#include <stdlib.h>
#include <unistd.h>
#include <getopt.h>
#include <dirent.h>
#include "path.h"

#include <errno.h>

#define NT_MAX_PATH 32768

#define EXEC_FLAGS (MOUNT_EXEC | MOUNT_NOTEXEC | MOUNT_CYGWIN_EXEC)

static void mount_entries (void);
static void show_mounts (void);
static void show_cygdrive_info (void);
static void change_cygdrive_prefix (const char *new_prefix, int flags);
static int mount_already_exists (const char *posix_path, int flags);

// static short create_missing_dirs = FALSE;
static bool force = false;

static const char *progname;

static void
error (const char *path)
{
  fprintf (stderr, "%s: %s: %s\n", progname, path,
	   (errno == EMFILE) ? "Too many mount entries" : strerror (errno));
  exit (1);
}

/* FIXME: do_mount should also print a warning message if the dev arg
   is a non-existent Win32 path. */

static void
do_mount (const char *dev, const char *where, int flags)
{
  struct stat statbuf;
  int statres;

  statres = stat (where, &statbuf);

#if 0
  if (statres == -1)
    {
      /* FIXME: this'll fail if mount dir is missing any parent dirs */
      if (create_missing_dirs == TRUE)
	{
	  if (mkdir (where, 0755) == -1)
	    fprintf (stderr, "Warning: unable to create %s!\n", where);
	  else
	    statres = 0; /* Pretend stat succeeded if we could mkdir. */
	}
    }
#endif

  if (statres == -1)
    {
      if (!force)
	fprintf (stderr, "%s: warning - %s does not exist.\n", progname, where);
    }
  else if (!(statbuf.st_mode & S_IFDIR))
    {
      if (!force)
	fprintf (stderr, "%s: warning: %s is not a directory.\n",
		 progname, where);
    }

  if (!force && !(flags & (EXEC_FLAGS | MOUNT_BIND)) && strlen (dev))
    {
      char devtmp[1 + 2 * strlen (dev)];
      strcpy (devtmp, dev);
      char c = strchr (devtmp, '\0')[-1];
      if (c == '/' || c == '\\')
	strcat (devtmp, ".");
      /* Use a curious property of Windows which allows the use of \.. even
	 on non-directory paths. */
      for (const char *p = dev; (p = strpbrk (p, "/\\")); p++)
	strcat (devtmp, "\\..");
      strcat (devtmp, "\\");
      if (GetDriveType (devtmp) == DRIVE_REMOTE)
	{
	  fprintf (stderr,
      "%s: defaulting to 'notexec' mount option for speed since native path\n"
      "%*creferences a remote share.  Use '-f' option to override.\n",
		   progname, (int) strlen(progname) + 2, ' ');
	  flags |= MOUNT_NOTEXEC;
	}
    }

  if (mount (dev, where, flags))
    error (where);
}

static void
from_fstab (bool user)
{
  char path[PATH_MAX];
  char buf[65536];
  mnt_t *m = mount_table + max_mount_entry;

  strcpy (path, "/etc/fstab");
  if (user)
    {
      strcat (path, ".d/");
      strcat (path, getlogin ());
    }
  FILE *fh = fopen (path, "rt");
  if (!fh)
    return;
  while (fgets (buf, 65536, fh))
    {
      char *c = strrchr (buf, '\n');
      if (c)
      	*c = '\0';
      if (from_fstab_line (m, buf, user))
	++m;
    }
  max_mount_entry = m - mount_table;
  fclose (fh);
}

static void
do_mount_from_fstab (const char *where)
{
  force = true;
  /* Read fstab entries. */
  from_fstab (false);
  from_fstab (true);
  /* Loop through fstab entries and see if it matches `where'.  If `where'
     is NULL, all entries match. */
  bool exists = false;
  for (mnt_t *m = mount_table; m - mount_table < max_mount_entry; ++m)
    if (!where || !strcmp (where, m->posix))
      {
	if (m->flags & MOUNT_CYGDRIVE)
	  {
	    /* Get the cygdrive info */
	    char user[MAX_PATH];
	    char system[MAX_PATH];
	    char user_flags[MAX_PATH];
	    char system_flags[MAX_PATH];

	    exists = true;
	    cygwin_internal (CW_GET_CYGDRIVE_INFO, user, system, user_flags,
			     system_flags);
	    if ((*user && strcmp (user, m->posix) != 0)
		|| (*system && strcmp (system, m->posix) != 0))
	      if (mount (NULL, m->posix, m->flags))
		error (m->posix);
	  }
	else
	  {
	    exists = true;
	    /* Compare with existing mount table.  If the entry doesn't exist,
	       mount it. */
	    FILE *mt = setmntent ("/-not-used-", "r");
	    struct mntent *p;

	    while ((p = getmntent (mt)) != NULL)
	      if (!strcmp (m->posix, p->mnt_dir))
		break;
	    if (!p)
	      do_mount (m->native, m->posix, m->flags);
	    endmntent (mt);
	    if (where)
	      break;
	  }
      }
  if (!exists && where)
    fprintf (stderr,
	     "%s: can't find %s in /etc/fstab or in /etc/fstab.d/$USER\n",
	     progname, where);
}

static struct option longopts[] =
{
  {"all", no_argument, NULL, 'a'},
  {"change-cygdrive-prefix", no_argument, NULL, 'c'},
  {"force", no_argument, NULL, 'f'},
  {"help", no_argument, NULL, 'h' },
  {"mount-entries", no_argument, NULL, 'm'},
  {"options", required_argument, NULL, 'o'},
  {"show-cygdrive-prefix", no_argument, NULL, 'p'},
  {"version", no_argument, NULL, 'V'},
  {NULL, 0, NULL, 0}
};

static char opts[] = "acfhmpVo:";

static void
usage (FILE *where = stderr)
{
  char *options;

  fprintf (where, "Usage: %1$s [OPTION] [<win32path> <posixpath>]\n\
       %1$s -a\n\
       %1$s <posixpath>\n\
\n\
Display information about mounted filesystems, or mount a filesystem\n\
\n\
  -a, --all                     mount all filesystems mentioned in fstab\n\
  -c, --change-cygdrive-prefix  change the cygdrive path prefix to <posixpath>\n\
  -f, --force                   force mount, don't warn about missing mount\n\
				point directories\n\
  -h, --help                    output usage information and exit\n\
  -m, --mount-entries           write fstab entries to replicate mount points\n\
				and cygdrive prefixes\n\
  -o, --options X[,X...]	specify mount options\n\
  -p, --show-cygdrive-prefix    show user and/or system cygdrive path prefix\n\
  -V, --version                 output version information and exit\n\n",
  progname);
  if (!cygwin_internal (CW_LST_MNT_OPTS, &options))
    fprintf (where, "Valid options are: %s\n\n", options);
  exit (where == stderr ? 1 : 0);
}

static void
print_version ()
{
  printf ("mount (cygwin) %d.%d.%d\n"
	  "Mount filesystem utility\n"
	  "Copyright (C) 1996 - %s Cygwin Authors\n"
	  "This is free software; see the source for copying conditions.  There is NO\n"
	  "warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n",
	  CYGWIN_VERSION_DLL_MAJOR / 1000,
	  CYGWIN_VERSION_DLL_MAJOR % 1000,
	  CYGWIN_VERSION_DLL_MINOR,
	  strrchr (__DATE__, ' ') + 1);
}

static char *
concat3 (char *a, const char *b, const char *c)
{
  size_t totlen = strlen (a) + strlen (b) + strlen (c) + 1;
  a = (char *) realloc (a, totlen);
  return strcat (strcat (a, b), c);
}

int
main (int argc, char **argv)
{
  int i;
  int flags = MOUNT_BINARY;
  char *options = strdup ("");
  enum do_what
  {
    nada,
    saw_change_cygdrive_prefix,
    saw_show_cygdrive_prefix,
    saw_mount_commands,
    saw_mount_all,
  } do_what = nada;

  progname = program_invocation_short_name;

  if (argc == 1)
    {
      show_mounts ();
      exit (0);
    }

  while ((i = getopt_long (argc, argv, opts, longopts, NULL)) != EOF)
    switch (i)
      {
      case 'a':
	if (do_what == nada)
	  do_what = saw_mount_all;
	else
	  usage ();
	break;
      case 'c':
	if (do_what == nada)
	  do_what = saw_change_cygdrive_prefix;
	else
	  usage ();
	break;
      case 'f':
	force = true;
	break;
      case 'h':
	usage (stdout);
	break;
      case 'm':
	if (do_what == nada)
	  do_what = saw_mount_commands;
	else
	  usage ();
	break;
      case 'o':
	if (do_what == saw_mount_all)
	  usage ();
	else if (*options)
	  options = concat3 (options, ",", optarg);
	else
	  options = strdup (optarg);
	break;
      case 'p':
	if (do_what == nada)
	  do_what = saw_show_cygdrive_prefix;
	else
	  usage ();
	break;
      case 'V':
	print_version ();
	return 0;
	break;
      default:
	fprintf (stderr, "Try `%s --help' for more information.\n", progname);
	return 1;
      }

  if (cygwin_internal (CW_CVT_MNT_OPTS, &options, &flags))
    {
      fprintf (stderr, "%s: invalid option - '%s'\n", progname, options);
      exit (1);
    }

  if (flags & MOUNT_NOTEXEC && flags & (MOUNT_EXEC | MOUNT_CYGWIN_EXEC))
    {
      fprintf (stderr, "%s: invalid combination of executable options\n",
	       progname);
      exit (1);
    }

  cygwin_internal (CW_SET_DOS_FILE_WARNING, false);

  argc--;
  switch (do_what)
    {
    case saw_change_cygdrive_prefix:
      if (optind != argc)
	usage ();
      change_cygdrive_prefix (argv[optind], flags);
      break;
    case saw_show_cygdrive_prefix:
      if (optind <= argc)
	usage ();
      show_cygdrive_info ();
      break;
    case saw_mount_commands:
      if (optind <= argc)
	usage ();
      mount_entries ();
      break;
    case saw_mount_all:
      if (optind <= argc)
	usage ();
      do_mount_from_fstab (NULL);
      break;
    default:
      if (optind == argc)
	do_mount_from_fstab (argv[optind]);
      else if (optind != (argc - 1))
	{
	  fprintf (stderr, "%s: too many arguments\n", progname);
	  usage ();
	}
      else if (force || !mount_already_exists (argv[optind + 1], flags))
	do_mount (argv[optind], argv[optind + 1], flags);
      else
	{
	  errno = EBUSY;
	  error (argv[optind + 1]);
	}
    }

  /* NOTREACHED */
  return 0;
}

static char *
convert_spaces (char *tgt, const char *src)
{
  char *tp, *spacep;
  const char *sp;

  tp = tgt;
  for (sp = src; (spacep = strchr (sp, ' ')); sp = spacep + 1)
    {
      tp = stpncpy (tp, sp, spacep - sp);
      tp = stpcpy (tp, "\\040");
    }
  stpcpy (tp, sp);
  return tgt;
}

static void
mount_entries (void)
{
  FILE *m = setmntent ("/-not-used-", "r");
  struct mntent *p;
  const char *format_mnt = "%s %s %s %s 0 0\n";
  const char *format_cyg = "none %s cygdrive %s 0 0\n";

  // write fstab entries for normal mount points
  while ((p = getmntent (m)) != NULL)
    // Only list non-cygdrives and non-automounts
    if (!strstr (p->mnt_opts, ",noumount") && !strstr (p->mnt_opts, ",auto"))
      {
	char fsname[NT_MAX_PATH], dirname[NT_MAX_PATH];
	/* Drop the "bind" option since it can't be reverted. */
	char *c = strstr (p->mnt_opts, ",bind");
	if (c)
	  memmove (c, c + 5, strlen (c + 5) + 1);
	printf (format_mnt, convert_spaces (fsname, p->mnt_fsname),
			    convert_spaces (dirname, p->mnt_dir),
			    p->mnt_type, p->mnt_opts);
      }
  endmntent (m);

  // write fstab entry for cygdrive prefix
  m = setmntent ("/-not-used-", "r");
  while ((p = getmntent (m)) != NULL)
    {
      char *noumount;
      if ((noumount = strstr (p->mnt_opts, ",noumount")))
	{
	  char dirname[NT_MAX_PATH];
	  char opts[strlen (p->mnt_opts) + 1];

	  convert_spaces (dirname, p->mnt_dir);
	  // remove trailing slash
	  char *ls = strrchr (dirname, '/');
	  if (ls)
	    {
	      // last slash == leading slash?  cygdrive prefix == "/"
	      if (ls == dirname)
		++ls;
	      *ls = '\0';
	    }
	  *stpncpy (opts, p->mnt_opts, noumount - p->mnt_opts) = '\0';
	  printf (format_cyg, dirname, opts);
	  break;
	}
    }
  endmntent (m);

  exit(0);
}

static void
show_mounts (void)
{
  FILE *m = setmntent ("/-not-used-", "r");
  struct mntent *p;
  const char *format = "%s on %s type %s (%s)\n";

  // printf (format, "Device", "Directory", "Type", "Flags");
  while ((p = getmntent (m)) != NULL)
    printf (format, p->mnt_fsname, p->mnt_dir, p->mnt_type, p->mnt_opts);
  endmntent (m);
}

/* Return 1 if mountpoint from the same registry area is already in
   mount table.  Otherwise return 0. */
static int
mount_already_exists (const char *posix_path, int flags)
{
  int found_matching = 0;

  FILE *m = setmntent ("/-not-used-", "r");
  struct mntent *p;

  while ((p = getmntent (m)) != NULL)
    {
      /* if the paths match, and they're both the same type of mount. */
      if (strcmp (p->mnt_dir, posix_path) == 0)
	{
	  if (p->mnt_type[0] == 'u')
	    {
	      if (!(flags & MOUNT_SYSTEM)) /* both current_user */
		found_matching = 1;
	      else
		fprintf (stderr,
			 "%s: warning: system mount point of '%s' "
			 "will always be masked by user mount.\n",
			 progname, posix_path);
	      break;
	    }
	  else if (p->mnt_type[0] == 's')
	    {
	      if (flags & MOUNT_SYSTEM) /* both system */
		found_matching = 1;
	      else
		fprintf (stderr,
			 "%s: warning: user mount point of '%s' "
			 "masks system mount.\n", progname, posix_path);
	      break;
	    }
	  else
	    {
	      fprintf (stderr, "%s: warning: couldn't determine mount type.\n",
		       progname);
	      break;
	    }
	}
    }
  endmntent (m);

  return found_matching;
}

/* change_cygdrive_prefix: Change the cygdrive prefix */
static void
change_cygdrive_prefix (const char *new_prefix, int flags)
{
  flags |= MOUNT_CYGDRIVE;

  if (mount (NULL, new_prefix, flags))
    error (new_prefix);

  exit (0);
}

/* show_cygdrive_info: Show the user and/or cygdrive info, i.e., prefix and
   flags.*/
static void
show_cygdrive_info ()
{
  /* Get the cygdrive info */
  char user[MAX_PATH];
  char system[MAX_PATH];
  char user_flags[MAX_PATH];
  char system_flags[MAX_PATH];
  cygwin_internal (CW_GET_CYGDRIVE_INFO, user, system, user_flags,
		   system_flags);

  /* Display the user and system cygdrive path prefix, if necessary
     (ie, not empty) */
  const char *format = "%-18s  %-11s  %s\n";
  printf (format, "Prefix", "Type", "Flags");
  if (strlen (user) > 0)
    printf (format, user, "user", user_flags);
  if (strlen (system) > 0)
    printf (format, system, "nouser", system_flags);

  exit (0);
}
