/* modprobe.c - modprobe utility.
 *
 * Copyright 2012 Madhur Verma <mad.flexi@gmail.com>
 * Copyright 2013 Kyungwan Han <asura321@gmail.com>
 *
 * No Standard.

USE_MODPROBE(NEWTOY(modprobe, "alrqvsDbd*", TOYFLAG_SBIN))

config MODPROBE
  bool "modprobe"
  default n
  help
    usage: modprobe [-alrqvsDb] [-d DIR] MODULE [symbol=value][...]

    modprobe utility - inserts modules and dependencies.

    -a  Load multiple MODULEs
    -d  Load modules from DIR, option may be used multiple times
    -l  List (MODULE is a pattern)
    -r  Remove MODULE (stacks) or do autoclean
    -q  Quiet
    -v  Verbose
    -s  Log to syslog
    -D  Show dependencies
    -b  Apply blacklist to module names too
*/
#define FOR_modprobe
#include "toys.h"
#include <sys/syscall.h>

GLOBALS(
  struct arg_list *dirs;

  struct arg_list *probes;
  struct arg_list *dbase[256];
  char *cmdopts;
  int nudeps;
  uint8_t symreq;
)

/* Note: if "#define DBASE_SIZE" modified, 
 * Please update GLOBALS dbase[256] accordingly.
 */
#define DBASE_SIZE  256
#define MODNAME_LEN 256

// Modules flag definations
#define MOD_ALOADED   0x0001
#define MOD_BLACKLIST 0x0002
#define MOD_FNDDEPMOD 0x0004
#define MOD_NDDEPS    0x0008

// Current probing modules info
struct module_s {
  uint32_t flags;
  char *cmdname, *name, *depent, *opts;
  struct arg_list *rnames, *dep;
};

// Converts path name FILE to module name.
static char *path2mod(char *file, char *mod)
{
  int i;
  char *from;

  if (!file) return NULL;
  if (!mod) mod = xmalloc(MODNAME_LEN);

  from = getbasename(file);
  
  for (i = 0; i < (MODNAME_LEN-1) && from[i] && from[i] != '.'; i++)
    mod[i] = (from[i] == '-') ? '_' : from[i];
  mod[i] = '\0';
  return mod;
}

// Add options in opts from toadd.
static char *add_opts(char *opts, char *toadd)
{
  if (toadd) {
    int optlen = 0;

    if (opts) optlen = strlen(opts);
    opts = xrealloc(opts, optlen + strlen(toadd) + 2);
    sprintf(opts + optlen, " %s", toadd);
  }
  return opts;
}

// Remove first element from the list and return it.
static void *llist_popme(struct arg_list **head)
{
  char *data = NULL;
  struct arg_list *temp = *head;

  if (temp) {
    data = temp->arg;
    *head = temp->next;
    free(temp);
  }
  return data;
}

// Add new node at the beginning of the list.
static void llist_add(struct arg_list **old, void *data)
{
  struct arg_list *new = xmalloc(sizeof(struct arg_list));

  new->arg = (char*)data;
  new->next = *old;
  *old = new;
}

// Add new node at tail of list.
static void llist_add_tail(struct arg_list **head, void *data)
{
  while (*head) head = &(*head)->next;
  *head = xzalloc(sizeof(struct arg_list));
  (*head)->arg = (char*)data;
}

// Reverse list order.
static struct arg_list *llist_rev(struct arg_list *list)
{
  struct arg_list *rev = NULL;

  while (list) {
    struct arg_list *next = list->next;

    list->next = rev;
    rev = list;
    list = next;
  }
  return rev;
}

/*
 * Returns struct module_s from the data base if found, NULL otherwise.
 * if add - create module entry, add it to data base and return the same mod.
 */
static struct module_s *get_mod(char *mod, uint8_t add)
{
  char name[MODNAME_LEN];
  struct module_s *modentry;
  struct arg_list *temp;
  unsigned i, hash = 0;

  path2mod(mod, name);
  for (i = 0; name[i]; i++) hash = ((hash*31) + hash) + name[i];
  hash %= DBASE_SIZE;
  for (temp = TT.dbase[hash]; temp; temp = temp->next) {
    modentry = (struct module_s *) temp->arg;
    if (!strcmp(modentry->name, name)) return modentry;
  }
  if (!add) return NULL;
  modentry = xzalloc(sizeof(*modentry));
  modentry->name = xstrdup(name);
  llist_add(&TT.dbase[hash], modentry);
  return modentry;
}

/*
 * Read a line from file with \ continuation and escape commented line.
 * Return the line in allocated string (*li)
 */
static int read_line(FILE *fl, char **li)
{
  char *nxtline = NULL, *line;
  ssize_t len, nxtlen;
  size_t linelen, nxtlinelen;

  while (1) {
    line = NULL;
    linelen = nxtlinelen = 0;
    len = getline(&line, &linelen, fl);
    if (len <= 0) {
      free(line);
      return len;
    }
    // checking for commented lines.
    if (line[0] != '#') break;
    free(line);
  }
  for (;;) {
    if (line[len - 1] == '\n') len--;
    if (!len) { 
      free(line);
      return len;
    } else if (line[len - 1] != '\\') break;
    
    len--;
    nxtlen = getline(&nxtline, &nxtlinelen, fl);
    if (nxtlen <= 0) break;
    if (linelen < len + nxtlen + 1) {
      linelen = len + nxtlen + 1;
      line = xrealloc(line, linelen);
    }
    memcpy(&line[len], nxtline, nxtlen);
    len += nxtlen;
  }
  line[len] = '\0';
  *li = xstrdup(line);
  free(line);
  if (nxtline) free(nxtline);
  return len;
}

/*
 * Action to be taken on all config files in default directories
 * checks for aliases, options, install, remove and blacklist
 */
static int config_action(struct dirtree *node)
{
  FILE *fc;
  char *filename, *tokens[3], *line, *linecp;
  struct module_s *modent;
  int tcount = 0;

  if (!dirtree_notdotdot(node)) return 0;
  if (S_ISDIR(node->st.st_mode)) return DIRTREE_RECURSE;

  if (!S_ISREG(node->st.st_mode)) return 0; // process only regular file
  filename = dirtree_path(node, NULL);
  if (!(fc = fopen(filename, "r"))) {
    free(filename);
    return 0;
  }
  for (line = linecp = NULL; read_line(fc, &line) > 0; 
      free(line), free(linecp), line = linecp = NULL) {
    char *tk = NULL;

    if (!strlen(line)) continue; 
    linecp = xstrdup(line);
    for (tk = strtok(linecp, "# \t"), tcount = 0; tk;
        tk = strtok(NULL, "# \t"), tcount++) {
      tokens[tcount] = tk;
      if (tcount == 2) {
        tokens[2] = line + strlen(tokens[0]) + strlen(tokens[1]) + 2;
        break;
      }
    }
    if (!tk) continue; 
    // process the tokens[0] contains first word of config line.
    if (!strcmp(tokens[0], "alias")) {
      struct arg_list *temp;
      char aliase[MODNAME_LEN], *realname;

      if (!tokens[2]) continue;
      path2mod(tokens[1], aliase);
      for (temp = TT.probes; temp; temp = temp->next) {
        modent = (struct module_s *) temp->arg;
        if (fnmatch(aliase, modent->name, 0)) continue;
        realname = path2mod(tokens[2], NULL);
        llist_add(&modent->rnames, realname);
        if (modent->flags & MOD_NDDEPS) {
          modent->flags &= ~MOD_NDDEPS;
          TT.nudeps--;
        }
        modent = get_mod(realname, 1);
        if (!(modent->flags & MOD_NDDEPS)) {
          modent->flags |= MOD_NDDEPS;
          TT.nudeps++;
        }
      }
    } else if (!strcmp(tokens[0], "options")) {
      if (!tokens[2]) continue;
      modent = get_mod(tokens[1], 1);
      modent->opts = add_opts(modent->opts, tokens[2]);
    } else if (!strcmp(tokens[0], "include"))
      dirtree_read(tokens[1], config_action);
    else if (!strcmp(tokens[0], "blacklist"))
      get_mod(tokens[1], 1)->flags |= MOD_BLACKLIST;
    else if (!strcmp(tokens[0], "install")) continue;
    else if (!strcmp(tokens[0], "remove")) continue;
    else if (toys.optflags & FLAG_q)
      error_msg("Invalid option %s found in file %s", tokens[0], filename);
  }
  fclose(fc);
  free(filename);
  return 0;
}

// Show matched modules else return -1 on failure.
static int depmode_read_entry(char *cmdname)
{
  char *line;
  int ret = -1;
  FILE *fe = xfopen("modules.dep", "r");

  while (read_line(fe, &line) > 0) {
    char *tmp = strchr(line, ':');

    if (tmp) {
      *tmp = '\0';
     char *name = basename(line);

      tmp = strchr(name, '.');
      if (tmp) *tmp = '\0';
      if (!cmdname || !fnmatch(cmdname, name, 0)) {
        if (tmp) *tmp = '.';
        if (toys.optflags&FLAG_v) puts(line);
        ret = 0;
      }
    }
    free(line);
  }
  fclose(fe);
  return ret;
}

// Finds dependencies for modules from the modules.dep file.
static void find_dep(void)
{
  char *line = NULL;
  struct module_s *mod;
  FILE *fe = xfopen("modules.dep", "r");

  for (; read_line(fe, &line) > 0; free(line)) {
    char *tmp = strchr(line, ':');

    if (tmp) {
      *tmp = '\0';
      mod = get_mod(line, 0);
      if (!mod) continue;
      if ((mod->flags & MOD_ALOADED) &&
          !(toys.optflags & (FLAG_r | FLAG_D))) continue;
      
      mod->flags |= MOD_FNDDEPMOD;
      if ((mod->flags & MOD_NDDEPS) && (!mod->dep)) {
        TT.nudeps--;
        llist_add(&mod->dep, xstrdup(line));
        tmp++;
        if (*tmp) {
          char *tok;

          while ((tok = strsep(&tmp, " \t"))) {
            if (!*tok) continue;
            llist_add_tail(&mod->dep, xstrdup(tok));
          }
        }
      }
    }
  }
  fclose(fe);
}

// Remove a module from the Linux Kernel. if !modules does auto remove.
static int rm_mod(char *modules, uint32_t flags)
{
  if (modules) {
    int len = strlen(modules);

    if (len > 3 && !strcmp(modules+len-3, ".ko" )) modules[len-3] = 0;
  }

  errno = 0;
  syscall(__NR_delete_module, modules, flags ? flags : O_NONBLOCK|O_EXCL);

  return errno;
}

// Insert module same as insmod implementation.
static int ins_mod(char *modules, char *flags)
{
  char *buf = NULL;
  int len, res;
  int fd = xopenro(modules);

  while (flags && strlen(toybuf) + strlen(flags) + 2 < sizeof(toybuf)) {
    strcat(toybuf, flags);
    strcat(toybuf, " ");
  }

#ifdef __NR_finit_module
  res = syscall(__NR_finit_module, fd, toybuf, 0);
  if (!res || errno != ENOSYS) {
    xclose(fd);
    return res;
  }
#endif

  // TODO xreadfile()

  len = fdlength(fd);
  buf = xmalloc(len);
  xreadall(fd, buf, len);
  xclose(fd);

  res = syscall(__NR_init_module, buf, len, toybuf);
  if (CFG_TOYBOX_FREE && buf != toybuf) free(buf);
  return res;
}

// Add module in probes list, if not loaded.
static void add_mod(char *name)
{
  struct module_s *mod = get_mod(name, 1);

  if (!(toys.optflags & (FLAG_r | FLAG_D)) && (mod->flags & MOD_ALOADED)) {
    if (toys.optflags&FLAG_v) printf("skipping %s, already loaded\n", name);
    return;
  }
  if (toys.optflags&FLAG_v) printf("queuing %s\n", name);
  mod->cmdname = name;
  mod->flags |= MOD_NDDEPS;
  llist_add_tail(&TT.probes, mod);
  TT.nudeps++;
  if (!strncmp(mod->name, "symbol:", 7)) TT.symreq = 1;
}

// Parse cmdline options suplied for module.
static char *add_cmdopt(char **argv)
{
  char *opt = xzalloc(1);
  int lopt = 0;

  while (*++argv) {
    char *fmt, *var, *val;

    var = *argv;
    opt = xrealloc(opt, lopt + 2 + strlen(var) + 2);
    // check for key=val or key = val.
    fmt = "%.*s%s ";
    for (val = var; *val && *val != '='; val++);
    if (*val && strchr(++val, ' ')) fmt = "%.*s\"%s\" ";
    lopt += sprintf(opt + lopt, fmt, (int) (val - var), var, val);
  }
  return opt;
}

// Probes a single module and loads all its dependencies.
static int go_probe(struct module_s *m)
{
  int rc = 0, first = 1;

  if (!(m->flags & MOD_FNDDEPMOD)) {
    if (!(toys.optflags & FLAG_q))
      error_msg("module %s not found in modules.dep", m->name);
    return -ENOENT;
  }
  if (toys.optflags & FLAG_v) printf("go_prob'ing %s\n", m->name);
  if (!(toys.optflags & FLAG_r)) m->dep = llist_rev(m->dep);
  
  while (m->dep) {
    struct module_s *m2;
    char *fn, *options;

    rc = 0;
    fn = llist_popme(&m->dep);
    m2 = get_mod(fn, 1);
    // are we removing ?
    if (toys.optflags & FLAG_r) {
      if (m2->flags & MOD_ALOADED) {
        if ((rc = rm_mod(m2->name, O_EXCL))) {
          if (first) {
            perror_msg("can't unload module %s", m2->name);
            break;
          }
        } else m2->flags &= ~MOD_ALOADED;
      }
      first = 0;
      continue;
    }
    options = m2->opts;
    m2->opts = NULL;
    if (m == m2) options = add_opts(options, TT.cmdopts);

    // are we only checking dependencies ?
    if (toys.optflags & FLAG_D) {
      if (toys.optflags & FLAG_v)
        printf(options ? "insmod %s %s\n" : "insmod %s\n", fn, options);
      if (options) free(options);
      continue;
    }
    if (m2->flags & MOD_ALOADED) {
      if (toys.optflags&FLAG_v)
        printf("%s is already loaded, skipping\n", fn);
      if (options) free(options);
      continue;
    }
    // none of above is true insert the module.
    errno = 0;
    rc = ins_mod(fn, options);
    if (toys.optflags&FLAG_v)
      printf("loaded %s '%s': %s\n", fn, options, strerror(errno));
    if (errno == EEXIST) rc = 0;
    free(options);
    if (rc) {
      perror_msg("can't load module %s (%s)", m2->name, fn);
      break;
    }
    m2->flags |= MOD_ALOADED;
  }
  return rc;
}

void modprobe_main(void)
{
  struct utsname uts;
  char **argv = toys.optargs, *procline = NULL;
  FILE *fs;
  struct module_s *module;
  unsigned flags = toys.optflags;
  struct arg_list *dirs;

  if ((toys.optc < 1) && (((flags & FLAG_r) && (flags & FLAG_l))
        ||(!((flags & FLAG_r)||(flags & FLAG_l)))))
  {
    help_exit("bad syntax");
  }
  // Check for -r flag without arg if yes then do auto remove.
  if ((flags & FLAG_r) && !toys.optc) {
    if (rm_mod(NULL, O_NONBLOCK | O_EXCL)) perror_exit("rmmod");
    return;
  }

  if (!TT.dirs) {
    uname(&uts);
    TT.dirs = xzalloc(sizeof(struct arg_list));
    TT.dirs->arg = xmprintf("/lib/modules/%s", uts.release);
  }

  // modules.dep processing for dependency check.
  if (flags & FLAG_l) {
    for (dirs = TT.dirs; dirs; dirs = dirs->next) {
      xchdir(dirs->arg);
      if (!depmode_read_entry(toys.optargs[0])) return;
    }
    error_exit("no module found.");
  }

  // Read /proc/modules to get loaded modules.
  fs = xfopen("/proc/modules", "r");
  
  while (read_line(fs, &procline) > 0) {
    *(strchr(procline, ' ')) = '\0';
    get_mod(procline, 1)->flags = MOD_ALOADED;
    free(procline);
    procline = NULL;
  }
  fclose(fs);
  if ((flags & FLAG_a) || (flags & FLAG_r)) {
    do {
      add_mod(*argv++);
    } while (*argv);
  } else {
    add_mod(argv[0]);
    TT.cmdopts = add_cmdopt(argv);
  }
  if (!TT.probes) {
    if (toys.optflags&FLAG_v) puts("All modules loaded");
    return;
  }
  dirtree_flagread("/etc/modprobe.conf", DIRTREE_SHUTUP, config_action);
  dirtree_flagread("/etc/modprobe.d", DIRTREE_SHUTUP, config_action);

  for (dirs = TT.dirs; dirs; dirs = dirs->next) {
    xchdir(dirs->arg);
    if (TT.symreq) dirtree_read("modules.symbols", config_action);
    if (TT.nudeps) dirtree_read("modules.alias", config_action);
  }

  for (dirs = TT.dirs; dirs; dirs = dirs->next) {
    xchdir(dirs->arg);
    find_dep();
  }

  while ((module = llist_popme(&TT.probes))) {
    if (!module->rnames) {
      if (toys.optflags&FLAG_v) puts("probing by module name");
      /* This is not an alias. Literal names are blacklisted
       * only if '-b' is given.
       */
      if (!(flags & FLAG_b) || !(module->flags & MOD_BLACKLIST))
        go_probe(module);
      continue;
    }
    do { // Probe all real names for the alias.
      char *real = ((struct arg_list*)llist_pop(&module->rnames))->arg;
      struct module_s *m2 = get_mod(real, 0);
      
      if (toys.optflags&FLAG_v)
        printf("probing alias %s by realname %s\n", module->name, real);
      if (!m2) continue;
      if (!(m2->flags & MOD_BLACKLIST) 
          && (!(m2->flags & MOD_ALOADED) || (flags & (FLAG_r | FLAG_D))))
        go_probe(m2);
      free(real);
    } while (module->rnames);
  }
}
