pdirt/data/
pdirt/data/HELP/
pdirt/data/HELP/0/
pdirt/data/HELP/F/
pdirt/data/HELP/G/
pdirt/data/HELP/H/
pdirt/data/HELP/J/
pdirt/data/HELP/K/
pdirt/data/HELP/O/
pdirt/data/HELP/Q/
pdirt/data/HELP/R/
pdirt/data/HELP/U/
pdirt/data/HELP/V/
pdirt/data/HELP/Y/
pdirt/data/HELP/Z/
pdirt/data/MESSAGES/
pdirt/data/POWERINFO/
pdirt/data/WIZ_ZONES/
pdirt/drv/
pdirt/drv/bin/
pdirt/drv/compiler/converter/
pdirt/drv/compiler/libs/
pdirt/drv/compiler/scripts/
pdirt/drv/include/AberChat/
pdirt/drv/include/InterMud/
pdirt/drv/include/machine/
pdirt/drv/src/InterMud/
pdirt/drv/src/Players/
pdirt/drv/utils/UAFPort/
pdirt/drv/utils/dnsresolv/
pdirt/drv/utils/gdbm/
/***************************************************************************
 ** Reorganise ythe database files. Delete every users that hasnt been on for
 ** xx days and whom's level is between yy and zz. 
 ** Only downside is, that you cannot run this while the MUD is running. Thats
 ** because the program needs the write rights so it can delete players.
 **
 ** - Also checks their mailbox, and deletes it when it is found.
 ** - And their description.
 ***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <gdbm.h>
#include <time.h>
#include <sys/stat.h>
#include <unistd.h>
#include <ctype.h>
#include "kernel.h"
#include "mudtypes.h"

#define SECS_IN_A_DAY	(60 * 60 * 24)

int	min_level=0;		/* Min is LVL_GUEST */
int	max_level=99999;	/* Max is LVL_MAX */
int	days = 6*31;		/* About half a year */ 

char	file[124];		/* Buffer */
char    datadir[124];		/* string to datadir */

GDBM_FILE	fp;		

void clear_players(void);

int main(void)
{   char yn[80];

    printf("pDirt User Data Maintanance program. This program will delete some users\n"
           "from your database file, and delete their mailbox, if it exsists.\n\n"
           "Please give the file : ");
    scanf("%s",file);

    fp = gdbm_open(file, sizeof(PERSONA), GDBM_WRITER,S_IRUSR|S_IWUSR, NULL);
    if (fp == NULL)
    {   perror("Error opening file");
        return 1;
    }

    printf("Enter the datadirectory: ");
    scanf("%s",datadir);    

    if (access(datadir,X_OK) != 0)
    {   perror("Error finding data directory.");
        return 2;
    }

    printf("Please give lowest level: ");
    scanf("%d",&min_level);
    printf("Please give upper level: ");
    scanf("%d",&max_level);
    printf("Kick off players who have been ofline for more than (days): ");
    scanf("%d",&days);
    
    printf("\nSo you want to kick of players from level %d to level %d who havent been\n"
           "on for more than %d days.\nIs that correct [y/n]: ",min_level, max_level, days);
    fflush(stdin);
    scanf("%s",yn);
    
    if (yn[0] == 'y' || yn[0] == 'Y')
       clear_players();
    else
       printf("Then I'll quit.\n");

    gdbm_close(fp);
    printf("Command executed succesfully.\n");
       
    return 0;
}

void check_otherfiles(char *name)
{   char buff[120];

    *name = toupper(*name);

    sprintf(buff,"%s/MAIL/%s",datadir,name);

    if (access(buff,F_OK) == 0)
    {   fprintf(stderr,"                       Deleting Mailbox for user %s.\n",name);
        unlink(buff);
    }

    sprintf(buff,"%s/DESC/%s",datadir,name);
    if (access(buff,F_OK) == 0)
    {   fprintf(stderr,"                       Deleting Player Description for %s.\n",name);
        unlink(buff);
    }
}

void clear_players(void)
{  time_t last = time(0) - days * SECS_IN_A_DAY;
   int total=0, deleted = 0;
   datum key;
   datum in;
   datum nextkey;
   char *l;
 
   PERSONA p;
   
   key = gdbm_firstkey(fp);
   
   while (key.dptr != NULL)
   {   in = gdbm_fetch(fp,key);
       bcopy(in.dptr,&p, sizeof(PERSONA));
       nextkey = gdbm_nextkey(fp,key);
       
       if (p.p_name != '\0')
          total++;
          
       if (p.p_last_on < last && p.p_level > min_level && p.p_level < max_level &&
           *p.p_name != '\0')
       {   l = ctime(&p.p_last_on);
           *(l+11) = '\0';

           fprintf(stderr,"Deleting %-12s  Level: %5d  Score: %6d   Last login: %s\n",
                   p.p_name,p.p_level,p.p_score, l);
           key.dsize = strlen(key.dptr) + 1;
           (void)gdbm_delete(fp,key);
           check_otherfiles(p.p_name);
           deleted++;
       }
       else
       {  l = ctime(&p.p_last_on);
          *(l+11) = '\0';
          fprintf(stderr,"Keeping player %s. Last on : %s\n",p.p_name,l);
       }

       if (key.dptr != NULL) 
       	  free(key.dptr);
       if (in.dptr != NULL)
          free(in.dptr);
       key = nextkey;
   }
   printf("\nDone. Processed %d users, deleted %d.\nReorganising Database\n",total,deleted);
   gdbm_reorganize(fp);
}