
#include <stdio.h>
#include <syslog.h>
#include <sys/ioctl.h>
#include "server.h"
#include <signal.h>
#include <sys/types.h>
#include <sys/time.h>

int debug_mode = 0;
int disable_afs_admin_commands = 0;
int have_afs_admin_tokens = 0;
int do_timer_stuff_flag = 0;

main (argc, argv)
     int argc;
     char **argv;
{
/*  char *config_file = "/site/server/etc/freeload.conf"; */
  char *config_file = "/afs/sipb/project/freeload/src/server/freeload.conf"; 
  int init_database = 0;

  while (++argv, --argc) {
    if (**argv == '-')
      switch (argv[0][1]) {
      case 'c':
	if (!--argc) usage();
	config_file = *(++argv);
	break;
      case 'd':
	debug_mode++;
	break;
      case 'i':
	init_database++;
	break;
      case 'n':
	disable_afs_admin_commands++;
	break;
      case 'h':
	have_afs_admin_tokens++;
	break;
      }
    else
      usage();
  }
  if (!debug_mode)
    fork_me();
  signal (SIGPIPE, SIG_IGN);
#ifdef ultrix
  openlog ("freeloadd", 0);
#else  
  openlog ("freeloadd", 0, SERVER_FACILITY);
#endif
  load_configuration(config_file);
  open_database(init_database);

  hes_init();
  sfrp_init();
  uc_init();
  timer_init();
  main_loop();
}

usage()
{
  fprintf(stderr, "usage: freeloadd [-i] [-c config-file] [-d] [-n] [-h]\n");
  exit(1);
}

fork_me ()
{
  int pid;
  
  switch (pid = fork()) {
  case -1:
    perror ("fork");
    break;
  case 0:
    break;
  default:
    exit(0);
  }
  ioctl (0, TIOCNOTTY, 0);
  ioctl (1, TIOCNOTTY, 0);
  ioctl (2, TIOCNOTTY, 0);
  close (0);
  close (1);
  close (2);
}


main_loop()
{
  while(1)
    sfrp_handle();
}

void should_do_timer_stuff()
{
  do_timer_stuff_flag = 1;
}

void do_timer_stuff()
{
  Server* server;
  Freeload *f;
  int dl;

  syslog (LOG_DEBUG, "Getting new tokens");
  get_afs_tokens();
  syslog (LOG_DEBUG, "Checking downed servers");
  for(server = (Server*)first_server_down(); server; server = (Server*)next_server_down()) {
    if(!do_attach(server)) {
      /* server is up... attach succeeded */
      syslog(LOG_INFO, "server partition %s:%s is up again", server->hostname, server->partition);
      delete_server_down(server);
    } else {
      syslog(LOG_DEBUG, "server partition %s:%s is still down", server->hostname, server->partition);
    }
  }

  syslog (LOG_DEBUG, "Checking for expired freeloaders");
  for(f = (Freeload *) first_freeload(); f; f = (Freeload *) next_freeload())
    if ((dl = DAYSLEFT(f->issued)) < 0) {
      syslog(LOG_INFO, "%s's volume %s expired... nuking", f->username, f->volname);
      delete_volume(f->partition, f->volname, f->mountpoint);
      remove_freeload(f);
    } else
      syslog(LOG_DEBUG, "%s's volume %s has %d days to go", f->username, f->volname, dl);

  do_timer_stuff_flag = 0;
}

    
timer_init()
{
  struct itimerval value;
  value.it_interval.tv_sec = recheck_time;
  value.it_interval.tv_usec = 0;
  value.it_value.tv_sec = recheck_time;
  value.it_value.tv_usec = 0;
  
  signal(SIGALRM, should_do_timer_stuff);
  setitimer(ITIMER_REAL, &value, 0);
  do_timer_stuff();
}


