home *** CD-ROM | disk | FTP | other *** search
- From: shaw@stortek.stortek.com (Greg Shaw)
- Newsgroups: comp.sources.misc
- Subject: v44i004: rocat - Roman Catacombs BBS System v.0.75, Part04/09
- Date: 1 Aug 1994 12:08:47 -0500
- Organization: Sterling Software
- Sender: kent@sparky.sterling.com
- Approved: kent@sparky.sterling.com
- Message-ID: <31ja6v$b0f@sparky.sterling.com>
- X-Md4-Signature: ac4c2527a9c1d7a7030efcb176f071e2
-
- Submitted-by: shaw@stortek.stortek.com (Greg Shaw)
- Posting-number: Volume 44, Issue 4
- Archive-name: rocat/part04
- Environment: Linux, GNU C++/libg++
-
- #! /bin/sh
- # This is a shell archive. Remove anything before this line, then feed it
- # into a shell via "sh file" or similar. To overwrite existing files,
- # type "sh file -c".
- # Contents: rocat-0.75/src/files.C rocat-0.75/src/user.C
- # Wrapped by kent@sparky on Mon Jul 11 22:22:51 1994
- PATH=/bin:/usr/bin:/usr/ucb:/usr/local/bin:/usr/lbin:$PATH ; export PATH
- echo If this archive is complete, you will see the following message:
- echo ' "shar: End of archive 4 (of 9)."'
- if test -f 'rocat-0.75/src/files.C' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'rocat-0.75/src/files.C'\"
- else
- echo shar: Extracting \"'rocat-0.75/src/files.C'\" \(47604 characters\)
- sed "s/^X//" >'rocat-0.75/src/files.C' <<'END_OF_FILE'
- X// Filename: files.C
- X// Contents: the files object methods
- X// Author: Greg Shaw
- X// Created: 8/1/93
- X
- X/*
- XThis file is free software; you can redistribute it and/or modify it
- Xunder the terms of the GNU General Public License as published by the
- XFree Software Foundation; either version 2, or (at your option) any
- Xlater version.
- X
- XIn addition to the permissions in the GNU General Public License, the
- XFree Software Foundation gives you unlimited permission to link the
- Xcompiled version of this file with other programs, and to distribute
- Xthose programs without any restriction coming from the use of this
- Xfile. (The General Public License restrictions do apply in other
- Xrespects; for example, they cover modification of the file, and
- Xdistribution when not linked into another program.)
- X
- XThis file is distributed in the hope that it will be useful, but
- XWITHOUT ANY WARRANTY; without even the implied warranty of
- XMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- XGeneral Public License for more details.
- X
- XYou should have received a copy of the GNU General Public License
- Xalong with this program; see the file COPYING. If not, write to
- Xthe Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
- X
- X#ifndef _FILES_C_
- X#define _FILES_C_
- X
- X#include "bbshdr.h"
- X
- X// Function: constructor
- X// Purpose: initialize the files object to a known state
- X// Input: user - the card to use for the user using the BBS currently
- X// Output: none
- X// Author: Greg Shaw
- X// Created: 8/1/93
- X
- Xfiles::files()
- X{
- X acl = 0;
- X num_files = 0;
- X name[0] = 0;
- X age = 0;
- X long_desc[0] = 0;
- X sysop[0] = 0;
- X numsel = 0;
- X ksel = 0;
- X};
- X
- X// Function: edit_file
- X// Purpose: edit the information for a file
- X// Input: item - the information for a particular file
- X// Output: The file may be deleted or edited. In either case, the
- X// file information is updated.
- X// Author: Greg Shaw
- X// Created: 4/27/94
- X
- Xint files::edit_file(FInfo *item)
- X{
- X int edited; // edited anything?
- X int linenum; // line counter for description
- X int off; // char offset into line
- X char *editor; // name of their 'favorite' editor
- X char tmpstr[255]; // temp str
- X char oldname[MAX_FILENAMELENGTH]; // name prior to change
- X char filename[255]; // new name of file
- X char machreq[255]; // machine requirements
- X char c;
- X char ldesc[3][100]; // long description
- X FILE *infile, *outfile; // files
- X
- X clear();
- X strcpy(oldname,item->name); // save old name so we can find it later
- X machreq[0] = 0;
- X ldesc[0][0] = 0;
- X sprintf(tmpstr,"Filename: %s",item->name);
- X sstrcr(tmpstr);
- X cr();
- X sstr("Edit, Delete or Quit? " );
- X while (c = tolower(gch(1)), c != 'e' && c != 'd' && c != 'q');
- X cr();
- X if (c == 'q')
- X return(0);
- X else if (c == 'd') // delete
- X return(update_information(item, NULL, ldesc, machreq, 1));
- X else if (c == 'e') // edit
- X {
- X edited = 0;
- X while (1) // return will get out
- X {
- X sstrcr("Current file information:");
- X cr();
- X info(item,ldesc, machreq);
- X cr();
- X sstrcr("1. Name");
- X sstrcr("2. Short Description");
- X sstrcr("3. Uploader");
- X sstrcr("4. Number of Downloads");
- X sstrcr("5. Machine Requirements");
- X sstrcr("6. Long Description");
- X sstrcr("q. Done editing, quit");
- X cr();
- X sstr("Edit which? ");
- X while (c = tolower(gch(1)), c != 'q' && (c < '0' || c > '6') );
- X cr();
- X cr();
- X switch(c)
- X {
- X case 'q':
- X if (edited)
- X return(update_information(item,oldname,ldesc,machreq,0));
- X return(0);
- X case '1': // name
- X edited++;
- X sstr("New name? ");
- X gstr(item->name,MAX_FILENAMELENGTH);
- X break;
- X case '2': // short description
- X edited++;
- X sstr("New short description? ");
- X gstr(item->sdesc,60);
- X break;
- X case '3': // uploader
- X edited++;
- X sstr("New uploader? ");
- X gstr(item->uploader,40);
- X break;
- X case '4': // number of downloads
- X edited++;
- X sstr("New number of downloads? ");
- X gstr(tmpstr,5);
- X sscanf(tmpstr,"%d",&item->numdls);
- X break;
- X case '5': // machine requirements
- X edited++;
- X sstr("New machine requirements? ");
- X gstr(machreq,40);
- X break;
- X case '6': // long description
- X edited++;
- X // now get the long description
- X // create temp file
- X strcpy(tmpstr,"bbsXXXXXX");
- X mktemp(tmpstr);
- X if (tmpstr[0] == 0)
- X {
- X ap_log("Unable to create temp file for long description editing.");
- X return(0);
- X }
- X // got temp file. pass to system.
- X cr();
- X cr();
- X sstrcr("The long description will be placed in a file..");
- X sstrcr("Note: Anything more than 3 lines will be ignored.");
- X
- X waitcr();
- X strcpy(filename,tmpstr);
- X strcpy(tmpstr,editor);
- X if (editor = getenv("EDITOR"), editor == NULL)
- X {
- X sstrcr("I am unable to find your EDITOR environment variable.");
- X sstrcr("In the future, setting the EDITOR environment variable will");
- X sstrcr("allow use of your editor of preference");
- X cr();
- X sstrcr("Defaulting to the 'vi' editor.");
- X waitcr();
- X strcpy(tmpstr,"vi");
- X }
- X else
- X strcpy(tmpstr,editor);
- X strcat(tmpstr," /tmp/");
- X strcat(tmpstr,filename);
- X sysint(tmpstr);
- X strcpy(tmpstr,"/tmp/");
- X strcat(tmpstr,filename); // now open file
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X fprintf(outfile,"[D ]\n");
- X fprintf(outfile,"[E ]\n");
- X fprintf(outfile,"[F ]\n");
- X continue;
- X }
- X // now digest file
- X linenum = 0;
- X off = 0;
- X ldesc[linenum][0] = 0;
- X while (!feof(infile))
- X {
- X while (c = fgetc(infile), c != '\r' && c != '\n' && !feof(infile))
- X tmpstr[off++] = c;
- X tmpstr[off] = 0;
- X strcpy(ldesc[linenum],tmpstr);
- X linenum++;
- X off = 0;
- X }
- X bclose(infile);
- X sprintf(tmpstr,"/tmp/%s",filename);
- X if (unlink(tmpstr)) // remove temp file
- X {
- X ap_log("file edit: unable to remove temp file.");
- X // not fatal
- X }
- X }
- X }
- X }
- X else // unknown
- X {
- X ap_log("Unknown quantity found in edit_file.");
- X return(0);
- X }
- X return(0);
- X};
- X
- X// Function: create
- X// Purpose: create a files section. read all file information from
- X// directory and insert into files header file.
- X// Input: open must be called prior to this one. the name of the
- X// files section must be in the object.
- X// Output: a new files section header file is created in the
- X// $(BBS)/fileshdr directory.
- X// Author: Greg Shaw
- X// Created: 8/4/93
- X// Notes: *THIS IS VERY DANGEROUS* It should only be done on BBS
- X// files area initialization. It will overwrite the 'old'
- X// files header, losing any information that was there.
- X
- Xint files::create(void)
- X{
- X FILE *outfile; // output file
- X DIR *fdir; // directory file descriptor
- X struct dirent *dentry; // directory entry
- X struct stat fistat; // file status record
- X time_t now; // date of file added (today)
- X char bbsdir[255]; // bbs directory
- X char tmpstr[255]; // tmpstr
- X
- X time(&now);
- X strcpy(bbsdir,getenv("BBSDIR")); // not checking error
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/filehdr/"); // tack on files header
- X strcat(tmpstr,name);
- X if (outfile = bopen(tmpstr,"w"), outfile == NULL)
- X {
- X printf("Unable to open files section header %s",name);
- X }
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/files/");
- X strcat(tmpstr,dn_path);
- X if (fdir = opendir(tmpstr), fdir == NULL)
- X {
- X printf("Unable to open directory %s for reading.\n",tmpstr);
- X bclose(outfile);
- X exit(0);
- X }
- X // ok. output file is open. directory is open. doit.
- X while (dentry = readdir(fdir), dentry != NULL)
- X {
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/files/");
- X strcat(tmpstr,dn_path);
- X strcat(tmpstr,"/");
- X strcat(tmpstr,dentry->d_name); // for stat
- X if (stat(tmpstr,&fistat) == 0 && S_ISREG(fistat.st_mode))
- X {
- X fprintf(outfile,"[A sysop 0 %s ]\n",dentry->d_name);
- X fprintf(outfile,"[B ]\n");
- X fprintf(outfile,"[C ]\n");
- X fprintf(outfile,"[D ]\n");
- X fprintf(outfile,"[E ]\n");
- X fprintf(outfile,"[F ]\n");
- X }
- X }
- X closedir(fdir);
- X bclose(outfile);
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/filehdr/"); // tack on files header
- X strcat(tmpstr,name);
- X chmod(tmpstr,0775);
- X chown(tmpstr,bbs_uid(),bbs_gid()); // change owner to bbs
- X return(0);
- X};
- X// Function: download
- X// Purpose: download file(s) from the BBS
- X// Input: list - an array of FInfo pointers (file records)
- X// num - the number of records (files)
- X// Output: if everything works well, and the karma of the universe aligns with the
- X// BBSs, it will download files.
- X// Author: Greg Shaw
- X// Created: 8/4/93
- X
- Xint files::download(FInfo *list[], int num, int increment)
- X{
- X FILE *infile; // protocols file
- X time_t now; // loop (5sec) counter
- X time_t then; // loop (5sec) counter
- X int off; // offset into line
- X int x;
- X int numprot; // number of 'real' protocols
- X int protsel; // index of selected protocol
- X int done; // loop boolean
- X char c; // one char from file
- X char tmpstr[255]; // temp str
- X char comm[MAX_DL_COMMANDS][50]; // 15 commands max
- X char key[MAX_DL_COMMANDS]; // key for selecting command
- X char text[MAX_DL_COMMANDS][50]; // text describing command
- X char line[255];
- X
- X if (!(num > 0))
- X return(0);
- X // Ok. Change current working directory to files download area
- X strcpy(tmpstr,getenv("BBSDIR"));
- X strcat(tmpstr,"/files/");
- X strcat(tmpstr,dn_path);
- X chdir(tmpstr); // change to files download directory (so local naming works)
- X strcpy(tmpstr,getenv("BBSDIR"));
- X strcat(tmpstr,"/config/protocols");
- X // read protocols file. digest. display options to user.
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X ap_log("Unable to open config/protocols file.");
- X return(0);
- X }
- X // now read protocols file.
- X numprot = 0;
- X while (!feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\n' && c != '\r' && !feof(infile))
- X line[off++] = c;
- X // now digest line
- X line[off] = 0; // add null (for posterity) (and possibly anterity)
- X if (off < 5 || feof(infile)) // line can't be less than 5 chars long
- X continue;
- X if (line[0] == 'D') // we care about download only
- X {
- X // get command
- X // note: this is pretty nasty. Beer (good) and programming
- X // are not necessarily mutually exclusive.
- X // although beer and excellent programming may be.
- X off = 2;
- X while (line[off] != '|' && line[off] != 0)
- X {
- X comm[numprot][off-2] = line[off++];
- X }
- X comm[numprot][off-2] = 0; // add null
- X off++; // skip |
- X key[numprot] = line[off++]; // get hot key
- X off++; // skip |
- X x = off; // give an offset
- X while (line[off] != 0)
- X text[numprot][off - x] = line[off++];
- X text[numprot++][off-x] = 0;
- X }
- X }
- X bclose(infile);
- X // now show the bastich the protocols and let him choose...
- X cr();
- X sstrcr("Select Download Protocol: (or q to quit)");
- X cr();
- X for (x=0; x<numprot; x++)
- X sstrcr(text[x]);
- X cr();
- X sstr("Your choice? ");
- X done = 0;
- X while (!done)
- X {
- X c = gch(1);
- X if (c == 'q')
- X return(0);
- X for (x=0; x<numprot; x++)
- X if (key[x] == c)
- X {
- X done++;
- X protsel = x;
- X }
- X }
- X // Ok. Got protocol. Now do the download.
- X cr();
- X cr();
- X sstrcr("Ready to start download.");
- X cr();
- X strcpy(tmpstr,comm[protsel]);
- X for (x=0; x<num; x++)
- X {
- X strcat(tmpstr," ");
- X strcat(tmpstr,list[x]->name);
- X }
- X strcat(tmpstr," > /dev/null"); // pipe all stdout to /dev/null
- X // ok. pass to system
- X waitcr();
- X sysint(tmpstr);
- X for (x=0; x<num; x++)
- X {
- X sprintf(tmpstr,"%s downloaded %s",username(),list[x]->name);
- X ap_log(tmpstr);
- X }
- X increment_dls(list,num);
- X time(&then);
- X while (time(&now), now - then < 5)
- X fflush(stdin); // trash any additional garbage left on line
- X return(num);
- X};
- X
- X// Function: increment_dls
- X// Purpose: increment the number of downloads for the files downloaded
- X// Input: list - the information for the files
- X// Output: none
- X// Author: Greg Shaw
- X// Created: 8/10/93
- X
- Xint files::increment_dls(FInfo *list[], int num)
- X{
- X FILE *infile;
- X FILE *outfile;
- X int x;
- X int off;
- X int numdls;
- X char uploader[10];
- X char numdone[20]; // max 20 files can be downloaded
- X char line[150];
- X char tmpstr[255];
- X char fname[MAX_FILENAMELENGTH+1];
- X char fname2[MAX_FILENAMELENGTH+1];
- X char fname3[MAX_FILENAMELENGTH+1];
- X char c;
- X
- X for (x=0; x< 20; x++)
- X numdone[x] = 0;
- X sprintf(tmpstr,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X sprintf(tmpstr,"Unable to open %s for read.",name);
- X ap_log(tmpstr);
- X return(0);
- X }
- X sprintf(tmpstr,"%s/filehdr/%s.new",getenv("BBSDIR"),name);
- X if (outfile = bopen(tmpstr,"w"), outfile == NULL)
- X {
- X sprintf(tmpstr,"Unable to open %s.new for write.",name);
- X ap_log(tmpstr);
- X return(0);
- X }
- X while (!feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\r' && c != '\n' && !feof(infile))
- X line[off++] = c;
- X line[off] = 0;
- X if (line[0] == '[' && line[1] == 'A') // first line?
- X {
- X fname2[0] = 0;
- X fname3[0] = 0;
- X sscanf(&line[2],"%s %d %s", uploader, &numdls, fname, fname2, fname3);
- X if (strlen(fname2) > 0 && fname2[0] != ']')
- X {
- X sprintf(tmpstr,"%s %s",fname,fname2);
- X strcpy(fname,tmpstr);
- X }
- X if (strlen(fname3) > 0 && fname3[0] != ']')
- X {
- X sprintf(tmpstr,"%s %s",fname,fname3);
- X strcpy(fname,tmpstr);
- X }
- X for (x=0; x< num; x++)
- X if (!numdone[x] && strcmp(fname,list[x]->name) == 0 )
- X {
- X numdone[x] = 1;
- X numdls++;
- X }
- X fprintf(outfile,"[A %s %d %s ]\n",uploader, numdls, fname);
- X }
- X else if (strcmp(line,"") != 0)
- X fprintf(outfile,"%s\n",line);
- X }
- X bclose(infile);
- X bclose(outfile);
- X sprintf(tmpstr,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X sprintf(line,"%s/filehdr/%s.old",getenv("BBSDIR"),name);
- X rename(tmpstr,line); // rename file
- X sprintf(tmpstr,"%s/filehdr/%s.new",getenv("BBSDIR"),name);
- X sprintf(line,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X rename(tmpstr,line); // rename file
- X sprintf(tmpstr,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X chmod(tmpstr,0775);
- X chown(tmpstr,bbs_uid(),bbs_gid()); // change owner to bbs
- X return(0);
- X};
- X
- X// Function: info
- X// Purpose: get info on a file and display to user
- X// Input: fptr - a FInfo pointer (NULL to prompt user for filename)
- X// Output: the long information is shown to user
- X// Author: Greg Shaw
- X// Created: 8/10/93
- X
- Xint files::info(FInfo *fptr, char ldesc[3][100], char *machreq)
- X{
- X char tmpstr[255];
- X char filename[MAX_FILENAMELENGTH+1]; // name of file (if fptr NULL)
- X char line[255]; // one line of description
- X char datestr[12]; // date of file upload
- X char c;
- X int x;
- X int lp; // number of lines of description printed
- X int off; // offset into line
- X int state; // which line are we working on?
- X int numlines=0; // number of lines used for info
- X FILE *infile;
- X FInfo *rec;
- X struct tm *tmrec; // date representation
- X
- X if (fptr == NULL)
- X {
- X // get file from user
- X sstr("Get info on which file? (q to quit) ");
- X gstr(filename,MAX_FILENAMELENGTH);
- X if (strcmp(filename,"q")==0)
- X return(0);
- X list_obj.top();
- X rec = list_obj.next();
- X while (strcmp(rec->name,filename) != 0 && rec != NULL)
- X rec = list_obj.next();
- X if (rec == NULL)
- X {
- X sprintf(tmpstr,"Unable to find a file named %s.",filename);
- X sstrcr(tmpstr);
- X waitcr();
- X return(0);
- X }
- X }
- X else
- X rec = fptr;
- X sprintf(tmpstr,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X if (ldesc != NULL && strlen(ldesc[0]) != 0)// if we have description already, don't bother looking for it
- X {
- X tmrec = localtime(&rec->date);
- X strftime(datestr,11,"%x",tmrec);
- X sprintf(tmpstr,"Name: %-14.14s Size: %8d Uploaded on: %s by: %s ",
- X rec->name,rec->size,datestr,rec->uploader);
- X sstrcr(tmpstr);
- X sprintf(tmpstr," Downloads: %2d Short Description: %s",rec->numdls,rec->sdesc);
- X sstrcr(tmpstr);
- X sprintf(tmpstr," Avail? %c Machine Requirements: %s",rec->avail,machreq);
- X sstrcr(tmpstr);
- X for (x=0; x<3; x++)
- X {
- X sstr(" ");
- X sstrcr(ldesc[x]);
- X }
- X return(0);
- X }
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X sprintf(tmpstr,"Unable to open files section %s.",name);
- X ap_log(tmpstr);
- X sstrcr("No files found.");
- X waitcr();
- X return(0);
- X }
- X if (fseek(infile,rec->filepos,0) != 0)
- X {
- X sprintf(tmpstr,"Unable to set position in %s to %ld.",name,rec->filepos);
- X ap_log(tmpstr);
- X return(0);
- X }
- X // Ok. right place. now let's read the beastie
- X tmrec = localtime(&rec->date);
- X strftime(datestr,11,"%x",tmrec);
- X sprintf(tmpstr,"Name: %-14.14s Size: %8d Uploaded on: %s by: %s ",
- X rec->name,rec->size,datestr,rec->uploader);
- X sstrcr(tmpstr);
- X sprintf(tmpstr," Downloads: %2d Short Description: %s",rec->numdls,rec->sdesc);
- X sstrcr(tmpstr);
- X numlines += 2;
- X state = 0;
- X lp = 0;
- X while (state < 4 && !feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != ']' && !feof(infile))
- X line[off++] = c;
- X line[off] = 0;
- X if (feof(infile))
- X continue;
- X if (c == ']') // if got right bracket skip rest of line
- X while (c = fgetc(infile), c != '\r' && c != '\n' && !feof(infile));
- X state++;
- X switch(state)
- X {
- X case 1: // machine requirements line
- X sprintf(tmpstr," Avail? %c Machine Requirements: %s",rec->avail,&line[2]);
- X sstrcr(tmpstr);
- X if (machreq != NULL)
- X strcpy(machreq,&line[2]);
- X numlines++;
- X lp++;
- X break;
- X case 2: // first long description line
- X if (strcmp(&line[2]," ")!=0)
- X {
- X sstr(" ");
- X sstrcr(&line[2]);
- X numlines++;
- X lp++;
- X }
- X if (ldesc != NULL) // save long desc for return
- X strcpy(ldesc[0],&line[2]);
- X break;
- X case 3: // second long description line
- X if (strcmp(&line[2]," ")!=0)
- X {
- X sstr(" ");
- X sstrcr(&line[2]);
- X numlines++;
- X lp++;
- X }
- X if (ldesc != NULL) // save long desc for return
- X strcpy(ldesc[1],&line[2]);
- X break;
- X case 4: // third long description line
- X if (strcmp(&line[2]," ")!=0)
- X {
- X sstr(" ");
- X sstrcr(&line[2]);
- X numlines++;
- X lp++;
- X }
- X if (ldesc != NULL) // save long desc for return
- X strcpy(ldesc[2],&line[2]);
- X }
- X }
- X if (lp == 0)
- X {
- X sstrcr(" No description given.");
- X numlines++;
- X }
- X return(numlines);
- X};
- X
- X
- X// Function: list
- X// Purpose: list the files found in the section
- X// Input: can_download - true if give user option to download
- X// kused - the amount of K used by the user today
- X// Output: a files listing
- X// Author: Greg Shaw
- X// Created: 8/1/93
- X
- Xint files::list(int can_download, CardRec *user, int *kused, time_t since_time, float uratio)
- X{
- X FILE *infile;
- X FInfo *flist[20]; // five files on screen at once
- X FInfo *mlist[20]; // the file info for files he has marked
- X FInfo *rec; // temporary rec
- X struct tm *tmrec;
- X time_t now; // time conversion
- X time_t then; // used for idle timeout
- X time_t fromdate; // date to show the user 'from'
- X char tmpstr[255];
- X char fname[255];
- X char datestr[11];
- X char *bbsdir;
- X char c;
- X int day,mon,year; // for 'from' date selection
- X int display_dir; // direction of display
- X int t;
- X int off;
- X int x; // counter
- X int done; // main loop counter
- X int numlines; // number of descriptions on screen
- X int numfiles; // number of files marked
- X int ksel; // amount of 'k' selected for download
- X int oneline; // one line or multiple lines?
- X int numdownls; // number of files user downloaded
- X int inactivity; // inactivity timeout
- X
- X numdownls = 0;
- X bbsdir = getenv("BBSDIR");
- X strcpy(tmpstr,bbsdir); // not checking because he shouldn't
- X // get here if bbsdir not set
- X strcat(tmpstr,"/filehdr/"); // tack on files header
- X strcat(tmpstr,name); // add name
- X strcpy(fname,tmpstr);
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X sprintf(tmpstr,"Unable to open %s files section.",name);
- X ap_log(tmpstr);
- X sstrcr("No files found.");
- X waitcr();
- X return(0);
- X }
- X // got the file. let's ask him what he wants
- X clear();
- X sstrcr("List files as:");
- X cr();
- X sstrcr("1. One line descriptions. (one line per file)");
- X sstrcr("2. Full file descriptions. (4 lines per file)");
- X cr();
- X sstr("Choice? ");
- X while (c = gch(1), c != '1' && c != '2');
- X if (c == '1')
- X oneline = 1;
- X else
- X oneline = 0;
- X cr();
- X cr();
- X if (!since_time)
- X {
- X sstrcr("List files in what order? ");
- X cr();
- X sstrcr("1. Forward chronologically (old-->new)");
- X sstrcr("2. Backward chronologically (new-->old)");
- X sstrcr("3. Alphabetically ");
- X sstrcr("4. Forward chronologically from some date");
- X cr();
- X sstr("Choice? ");
- X c = 0;
- X while (c != '1' && c != '2' && c != '3' && c != '4')
- X c = gch(1);
- X cr();
- X cr();
- X switch(c)
- X {
- X case '1': // forward chrono
- X list_obj.sort(1);
- X display_dir = 0;
- X break;
- X case '2': // reverse chrono
- X list_obj.sort(1);
- X display_dir = 1;
- X break;
- X case '3': // alphabetically
- X list_obj.sort(2);
- X display_dir = 0;
- X break;
- X case '4': // forward from user entered date
- X list_obj.sort(1);
- X display_dir = 0;
- X // get date from user
- X done = 0;
- X while (!done)
- X {
- X cr();
- X sstr("Forward from what date? (mm/dd/yy) ");
- X gstr(tmpstr,9);
- X if (sscanf(tmpstr,"%d/%d/%d",&mon,&day,&year) == 3)
- X {
- X done++;
- X time(&now);
- X tmrec = localtime(&now);
- X tmrec->tm_mday = day;
- X tmrec->tm_mon = mon-1;
- X tmrec->tm_year = year;
- X tmrec->tm_sec = 1;
- X tmrec->tm_min = 0;
- X tmrec->tm_hour = 0;
- X fromdate = mktime(tmrec);
- X since_time = fromdate;
- X list_obj.top();
- X rec = list_obj.next();
- X while (rec->date < fromdate && rec != NULL)
- X rec = list_obj.next();
- X if (rec == NULL)
- X {
- X waitcr();
- X return(0);
- X }
- X rec = list_obj.previous(); // move back one (for forward)
- X }
- X }
- X }
- X }
- X else // 'new' files only
- X {
- X list_obj.sort(1);
- X display_dir = 0;
- X list_obj.top();
- X rec = list_obj.next();
- X done = 0;
- X while (!done)
- X {
- X if (rec == NULL)
- X {
- X done++;
- X continue;
- X }
- X if (rec->date < since_time)
- X rec = list_obj.next();
- X else
- X done++;
- X }
- X if (rec == NULL)
- X {
- X sstrcr("No new files found.");
- X waitcr();
- X return(0);
- X }
- X rec = list_obj.previous(); // move back one (for forward)
- X }
- X // Ok. got everything we need. Now show him the files.
- X done = 0;
- X if (!since_time)
- X if (display_dir == 1)
- X list_obj.bottom();
- X else
- X list_obj.top();
- X numfiles = 0;
- X ksel = 0; // nothing selected (yet)
- X while (!done)
- X {
- X x = 0;
- X clear();
- X numlines=0;
- X sprintf(tmpstr,"Files section %s: (%d files)",long_desc,list_obj.numrecs());
- X sstrcr(tmpstr);
- X if (oneline)
- X sstrcr(" # Filename Size Date Dl A Short Description");
- X while (x<20&&numlines<20)
- X {
- X if (display_dir == 1)
- X rec = list_obj.previous();
- X else
- X rec = list_obj.next();
- X flist[x] = rec;
- X if (rec == NULL)
- X {
- X x = 20;
- X continue;
- X }
- X if (oneline)
- X {
- X tmrec = localtime(&rec->date);
- X strftime(datestr,11,"%x",tmrec);
- X sprintf(tmpstr,"%2d. %-14.14s %6d %s %2d %c %-39.39s",x+1,
- X rec->name,rec->size,datestr,rec->numdls,rec->avail,rec->sdesc);
- X sstrcr(tmpstr);
- X } else
- X {
- X sprintf(tmpstr,"%2d. ",x+1);
- X sstr(tmpstr);
- X numlines += info(rec,NULL,NULL);
- X }
- X x++;
- X }
- X // now give him a prompt
- X cr();
- X if (strcmp(user->colr,"black")==0 || strcmp(username(),sysop)==0) // sysop
- X sstr("E>dit ");
- X if (can_download)
- X sstr("M>ark U>nmark D>ownload ");
- X sstr("I>nfo Q>uit F>orward B>ack Command? ");
- X time(&then);
- X inactivity = inactivity_timeout();
- X while (c = tolower(gch(2)), c != 'd' && c != 'm' && c != 'i' && c !=
- X 'u' && c != 'q' && c != 'f' && c != 'b' && c != 'e')
- X {
- X time(&now);
- X if ((now - then)/60 > inactivity)
- X {
- X return(numdownls);
- X }
- X }
- X cr();
- X switch(c)
- X {
- X case 'e':
- X if (strcmp(user->colr,"black")==0 || strcmp(username(),sysop)==0) // sysop
- X {
- X sprintf(tmpstr,"Edit which file? (1-%d) ",x);
- X sstr(tmpstr);
- X gstr(tmpstr,3);
- X if (sscanf(tmpstr,"%d",&off) == 1 && off > 0 && off < 21)
- X {
- X
- X edit_file(flist[off-1]);
- X }
- X }
- X break;
- X case 'd':
- X if (can_download)
- X {
- X if (numfiles <= 0)
- X { // do one file
- X sprintf(tmpstr,"Download which file? (1-%d) ",x);
- X sstr(tmpstr);
- X gstr(tmpstr,3);
- X if (sscanf(tmpstr,"%d",&off) == 1 && off > 0 && off <= x)
- X {
- X if (flist[off-1]->avail != 'Y')
- X {
- X sprintf(tmpstr,"File %s is not available for download.",flist[off-1]->name);
- X sstrcr(tmpstr);
- X waitcr();
- X }
- X else
- X {
- X numdownls += download(&flist[off-1],1,1);// one file
- X *kused += flist[off-1]->size/1024;
- X return(numdownls);
- X }
- X }
- X }
- X else
- X {
- X numdownls += download(mlist,numfiles,1);// many files
- X for (x=0; x<numfiles; x++)
- X *kused += mlist[x]->size/1024;
- X numfiles = 0;
- X ksel = 0;
- X return(numdownls);
- X }
- X }
- X else
- X {
- X sstrcr("You do not have download privileges for this files area.");
- X waitcr();
- X }
- X break;
- X case 'q': // exit
- X if (numfiles > 0)
- X {
- X clear();
- X sstrcr("You have marked files for download.");
- X sstr("Do you want to exit without downloading? ");
- X if (yesno())
- X return(0);
- X }
- X else
- X return(0);
- X case 'm': // mark a file
- X if (numfiles < 19&&can_download)
- X {
- X if (uratio > fabs(ratio()))
- X {
- X sstrcr("You have not kept your download to upload ratio");
- X sprintf(tmpstr,"within %2.1f to 1. (%2.1f downloads are allowed for every upload)",ratio());
- X sstrcr(tmpstr);
- X sstrcr("Please upload to fix the problem.");
- X waitcr();
- X return(0);
- X }
- X if (uratio <= 0 && ratio() < 0)
- X {
- X sstrcr("You must upload to the BBS before you are given");
- X sstrcr("download priviledges.");
- X sstrcr("Please upload and you will have download access.");
- X waitcr();
- X return(0);
- X }
- X sprintf(tmpstr,"Mark which file? (1-%d) ",x);
- X sstr(tmpstr);
- X gstr(tmpstr,3);
- X if (sscanf(tmpstr,"%d",&off) == 1 && off > 0 && off < 21)
- X {
- X if (flist[off-1] != NULL)
- X {
- X if (*kused + ((flist[off-1]->size/1024)+ksel) > thisuser->kbytes && thisuser->kbytes > 0)
- X {
- X cr();
- X cr();
- X sstrcr("You do not have enough download space to download this file.");
- X sprintf(tmpstr,"You have %d K-bytes of download space every %d hours.",thisuser->kbytes,waittime());
- X sstrcr(tmpstr);
- X waitcr();
- X }
- X else if (ksel + (flist[off-1]->size/1024) > maxk())
- X {
- X cr();
- X cr();
- X sprintf(tmpstr,"The BBS allows %d Kbytes of downloads for any one batch.",maxk());
- X sstrcr(tmpstr);
- X sstrcr("Your batch size must remain below this amount.");
- X waitcr();
- X }
- X else
- X {
- X if (flist[off-1]->avail != 'Y')
- X {
- X sprintf(tmpstr,"File %s is not available for download.",flist[off-1]->name);
- X sstrcr(tmpstr);
- X waitcr();
- X }
- X else
- X {
- X ksel += flist[off-1]->size/1024;
- X cr();
- X cr();
- X sprintf(tmpstr,"Marked %s for download.",flist[off-1]->name);
- X sstrcr(tmpstr);
- X waitcr();
- X mlist[numfiles++] = flist[off-1];
- X }
- X }
- X }
- X }
- X }
- X else
- X {
- X if (numfiles >= 19)
- X sstrcr("Only 20 files may be marked for download at one time.");
- X else
- X sstrcr("You do not have download privileges for this files area.");
- X waitcr();
- X }
- X break;
- X case 'i': // info on a file
- X sprintf(tmpstr,"Info on which file? (1-%d) ",x);
- X sstr(tmpstr);
- X gstr(tmpstr,3);
- X if (sscanf(tmpstr,"%d",&off) == 1 && off > 0 && off < 21)
- X {
- X if (flist[off-1] != NULL)
- X {
- X info(flist[off-1],NULL,NULL);
- X waitcr();
- X }
- X }
- X break;
- X case 'f': // move to next screen
- X continue;
- X break;
- X case 'b': // move back one screen
- X x = 0;
- X while (x<40 && rec != NULL )
- X {
- X if (display_dir == 1)
- X rec = list_obj.next();
- X else
- X rec = list_obj.previous();
- X x++;
- X }
- X continue;
- X break;
- X case 'u': // unmark a file
- X if (numfiles > 0)
- X {
- X cr();
- X sstrcr("Files marked for download:");
- X for (x=0; x<numfiles; x++)
- X {
- X sprintf(tmpstr,"%d. %s",x+1,mlist[x]);
- X sstrcr(tmpstr);
- X }
- X cr();
- X sstr("Unmark which file? ");
- X gstr(tmpstr,3);
- X if (sscanf(tmpstr,"%d",&off) == 1 && off > 0 && off < numfiles+1)
- X {
- X sprintf(tmpstr,"File %d unmarked.",mlist[off-1]);
- X sstrcr(tmpstr);
- X // umark the file. compact list
- X t = 0;
- X for (x=0; x<numfiles; x++)
- X if (x != off-1)
- X flist[x] = mlist[t++];
- X else
- X t++;
- X // now copy back w/o file
- X for (x=0; x<numfiles-1; x++)
- X mlist[x] = flist[x];
- X numfiles--;
- X waitcr();
- X }
- X }
- X }
- X // go back so that 'next' batch is right
- X while (x>-1 && rec != NULL)
- X {
- X if (display_dir != 1)
- X rec = list_obj.previous();
- X else
- X rec = list_obj.next();
- X x--;
- X }
- X }
- X return(numdownls);
- X};
- X// Function: one_download
- X// Purpose: get a filename from the user and download that file
- X// Input: none
- X// Output: if the file name is found, the file will be downloaded
- X// Author: Greg Shaw
- X// Created: 8/10/93
- X
- Xint files::one_download(int *kused, float uratio, char *filename, int counts)
- X{
- X char str[50];
- X char tmpstr[20];
- X FInfo *rec,tmprec;
- X
- X // get filename
- X clear();
- X if (filename != NULL)
- X {
- X // create a dummy record for this download
- X strcpy(tmprec.name,filename);
- X tmprec.avail = 'Y';
- X tmprec.numdls = 0;
- X tmprec.size = 0;
- X rec = &tmprec;
- X }
- X else
- X {
- X sstrcr("Note: case matters");
- X cr();
- X sstr("Download which file? (q to quit) ");
- X gstr(tmpstr,MAX_FILENAMELENGTH);
- X if (strcmp(tmpstr,"q") == 0)
- X return(0);
- X cr();
- X // now find the file in the list
- X list_obj.top();
- X rec = list_obj.next();
- X while (strcmp(rec->name,tmpstr) != 0 && rec != NULL)
- X rec = list_obj.next();
- X if (rec == NULL)
- X {
- X sprintf(str,"Unable to find a file named %s.",tmpstr);
- X sstrcr(str);
- X waitcr();
- X return(0);
- X }
- X if (rec->avail == 'N')
- X {
- X sprintf(str,"File %s is not available for download.",rec->name);
- X sstrcr(str);
- X waitcr();
- X return(0);
- X }
- X }
- X // download the beastie!
- X if (counts) // does this count to upload/download ratios?
- X {
- X if (*kused + ((rec->size/1024)+ksel) > thisuser->kbytes && thisuser->kbytes > 0)
- X {
- X cr();
- X cr();
- X sstrcr("You do not have enough download space to download this file.");
- X sprintf(tmpstr,"You have %d K-bytes of download space every %d hours.",thisuser->kbytes,waittime());
- X sstrcr(tmpstr);
- X waitcr();
- X return(0);
- X }
- X if (uratio > fabs(ratio()))
- X {
- X sstrcr("You have not kept your download to upload ratio");
- X sprintf(tmpstr,"within %2.1f to 1. (%2.1f downloads are allowed for every upload)",ratio());
- X sstrcr(tmpstr);
- X sstrcr("Please upload to fix the problem.");
- X waitcr();
- X return(0);
- X }
- X if (uratio <= 0 && ratio() < 0)
- X {
- X sstrcr("You must upload to the BBS before you are given");
- X sstrcr("download priviledges.");
- X sstrcr("Please upload and you will have download access.");
- X waitcr();
- X return(0);
- X }
- X }
- X download(&rec,1,counts);
- X return(1);
- X};
- X
- X// Function: open
- X// Purpose: open the files section.
- X// Input: path - the name of the bbs section to read
- X// Output: none. setup function only.
- X// Author: Greg Shaw
- X// Created: 8/1/93
- X
- Xint files::open(char *sname, CardRec *user)
- X{
- X FILE *infile;
- X struct stat fistat; // file status record
- X FInfo newrec; // record for insert into list
- X char word[50];
- X char tmpstr[255];
- X char tmpstr2[255];
- X char tmpstr3[255];
- X int off;
- X int line;
- X int found;
- X char *u; // used for erasing right bracket
- X char *bbsdir;// used for bbsdir environment var
- X char c;
- X
- X thisuser = user;
- X bbsdir = getenv("BBSDIR"); // not checking because he shouldn't
- X if (strcmp(sname,name) != 0) // don't open if already open
- X {
- X list_obj.clear_list(); // nuke old values
- X strcpy(tmpstr,getenv("BBSDIR")); // not checking because he shouldn't
- X // get here if bbsdir not set
- X strcat(tmpstr,"/filehdr/bbs_files_hdr"); // tack on files header
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X sprintf(tmpstr,"Unable to open main files section header (bbs_files_hdr)",name);
- X ap_log(tmpstr);
- X return(-1);
- X }
- X // ok. got file. let's find the line we're looking for
- X found = 0;
- X while (!found && !feof(infile))
- X {
- X // look for left bracket
- X while (c = fgetc(infile), c != '[' && !feof(infile));
- X // now get the rest of the line
- X if (fscanf(infile,"%s %s %d %s %s %d%50s",name,sysop,&acl,dn_path,
- X up_path, &age, long_desc) != 7)
- X {
- X sprintf(tmpstr,"Unable to find %s in bbs main files header.",sname);
- X ap_log(tmpstr);
- X return(-1);
- X }
- X while (fscanf(infile,"%s",word) == 1 && strchr(word,']') == NULL)
- X {
- X strcat(long_desc," ");
- X strcat(long_desc,word);
- X }
- X if (u = strchr(long_desc,']'), u != NULL)
- X u[0] = 0; // turn into null
- X if (strcmp(name,sname) == 0)
- X found++; // gotcha
- X }
- X bclose(infile);
- X strcpy(tmpstr,getenv("BBSDIR"));// not checking because he shouldn't make it this far
- X strcat(tmpstr,"/filehdr/"); // get name of file area
- X strcat(tmpstr,name);
- X if (infile = bopen(tmpstr,"r"),infile == NULL)
- X {
- X // empty files section
- X return(0);
- X }
- X // ok. now read everything into dllist object
- X line = 0;
- X while (!feof(infile))
- X {
- X while (c=fgetc(infile), c != '[' && !feof(infile));
- X if (feof(infile))
- X continue;
- X switch(line)
- X {
- X case 0: // line 1
- X if (c = fgetc(infile), c == 'A')
- X {
- X tmpstr2[0] = 0;
- X tmpstr3[0] = 0;
- X fscanf(infile,"%s %d %s",newrec.uploader,
- X &newrec.numdls,newrec.name,tmpstr2,tmpstr3);
- X if (strlen(tmpstr2) > 0 && tmpstr2[0] != ']')
- X {
- X sprintf(tmpstr,"%s %s",newrec.name,tmpstr2);
- X strcpy(newrec.name,tmpstr);
- X }
- X if (strlen(tmpstr3) > 0 && tmpstr3[0] != ']')
- X {
- X sprintf(tmpstr,"%s %s",newrec.name,tmpstr3);
- X strcpy(newrec.name,tmpstr);
- X }
- X
- X sprintf(tmpstr,"%s/files/%s/%s",bbsdir,dn_path,newrec.name);
- X if (stat(tmpstr,&fistat) == 0 && S_ISREG(fistat.st_mode))
- X {
- X newrec.size = fistat.st_size;
- X newrec.date = fistat.st_ctime;
- X newrec.avail = 'Y';
- X }
- X else
- X {
- X newrec.size = 0;
- X newrec.date = 0;
- X newrec.avail = 'N';
- X }
- X line++;
- X }
- X break;
- X case 1: // line 2
- X if (c = fgetc(infile), c == 'B')
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\r' && c != '\n' && !feof(infile))
- X tmpstr[off++] = c;
- X tmpstr[off] = 0;
- X strcpy(newrec.sdesc,tmpstr);
- X if (u = strchr(newrec.sdesc,']'), u != NULL)
- X u[0] = 0; // turn into null
- X if (strcmp(newrec.sdesc," ") == 0)
- X strcpy(newrec.sdesc,"none");
- X line++;
- X }
- X break;
- X case 2: // line 3
- X if (c = fgetc(infile), c == 'C')
- X {
- X newrec.filepos = ftell(infile);
- X list_obj.add(&newrec);
- X fscanf(infile,"%s",tmpstr);
- X line++;
- X }
- X break;
- X case 3: // line 4
- X if (c = fgetc(infile), c == 'D')
- X {
- X fscanf(infile,"%s",tmpstr);
- X line++;
- X }
- X break;
- X case 4: // line 5
- X if (c = fgetc(infile), c == 'E')
- X {
- X fscanf(infile,"%s",tmpstr);
- X line++;
- X }
- X break;
- X case 5: // line 6
- X if (c = fgetc(infile), c == 'F')
- X {
- X fscanf(infile,"%s",tmpstr);
- X line = 0;
- X }
- X break;
- X }
- X }
- X bclose(infile);
- X }
- X return(0);
- X};
- X
- X// Function: update_information
- X// Purpose: update the file information in the header file
- X// Input: list - the information for the file
- X// Output: none
- X// Author: Greg Shaw
- X// Created: 8/10/93
- X
- Xint files::update_information(FInfo *item, char *origname, char desc[3][100], char *machreq, int del)
- X{
- X FILE *infile;
- X FILE *outfile;
- X int off;
- X char line[150];
- X char tmpstr[255];
- X char fname[MAX_FILENAMELENGTH+1];
- X char c;
- X
- X printf("opening files...\n");
- X fflush(stdout);
- X sprintf(tmpstr,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X sprintf(tmpstr,"Unable to open %s for read.",name);
- X ap_log(tmpstr);
- X return(0);
- X }
- X sprintf(tmpstr,"%s/filehdr/%s.new",getenv("BBSDIR"),name);
- X if (outfile = bopen(tmpstr,"w"), outfile == NULL)
- X {
- X sprintf(tmpstr,"Unable to open %s.new for write.",name);
- X ap_log(tmpstr);
- X return(0);
- X }
- X printf("start of loop...\n");
- X fflush(stdout);
- X while (!feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\r' && c != '\n' && !feof(infile))
- X line[off++] = c;
- X line[off] = 0;
- X if (line[0] == '[' && line[1] == 'A') // first line?
- X {
- X if (!sscanf(&line[2],"%s %*ld %*ld %*d %*s", fname))
- X {
- X sprintf(tmpstr,"Error found in files listing %s for file %s",name,fname);
- X ap_log(tmpstr);
- X }
- X if (strcmp(fname,origname) == 0 )
- X {
- X printf("found target...\n");
- X fflush(stdout);
- X if (del)
- X {
- X sprintf(tmpstr,"%s/files/%s/%s",getenv("BBSDIR"),
- X dn_path, item->name);
- X if (unlink(tmpstr))
- X {
- X sprintf(tmpstr,"Unable to delete file %s",item->name);
- X ap_log(tmpstr);
- X }
- X // skip next 5 lines
- X off=0;
- X while (off < 5)
- X {
- X if (c = fgetc(infile), c == '\r' || c == '\n')
- X off++;
- X }
- X }
- X fprintf(outfile,"[A %s %d %s ]\n",item->uploader, item->numdls, item->name);
- X fprintf(outfile,"[B %s ]\n",item->sdesc);
- X fprintf(outfile,"[C %s ]\n",machreq);
- X fprintf(outfile,"[D %s ]\n",desc[0]);
- X fprintf(outfile,"[E %s ]\n",desc[1]);
- X fprintf(outfile,"[F %s ]\n",desc[2]);
- X // skip next 5 lines
- X off=0;
- X while (off < 5)
- X {
- X if (c = fgetc(infile), c == '\r' || c == '\n')
- X off++;
- X }
- X while (!feof(infile))
- X if (c = fgetc(infile), c != EOF)
- X fputc(c,outfile);
- X }
- X else
- X fprintf(outfile,"%s\n",line);
- X }
- X else if (strcmp(line,"") != 0)
- X fprintf(outfile,"%s\n",line);
- X }
- X printf("exit loop...\n");
- X fflush(stdout);
- X bclose(infile);
- X bclose(outfile);
- X sprintf(tmpstr,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X sprintf(line,"%s/filehdr/%s.old",getenv("BBSDIR"),name);
- X rename(tmpstr,line); // rename file
- X sprintf(tmpstr,"%s/filehdr/%s.new",getenv("BBSDIR"),name);
- X sprintf(line,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X rename(tmpstr,line); // rename file
- X sprintf(tmpstr,"%s/filehdr/%s",getenv("BBSDIR"),name);
- X chmod(tmpstr,0775);
- X chown(tmpstr,bbs_uid(),bbs_gid()); // change owner to bbs
- X return(0);
- X};
- X
- X
- X// Function: search
- X// Purpose: search for a file in the files section
- X// Input: can_download - can the user download the file if he wants
- X// Output: if the search is successfull, the file will be displayed to the user
- X// bbs directory upload directory (or wherever the uploaddir is)
- X// Author: Greg Shaw
- X// Created: 8/9/93
- X
- Xint files::search(int can_download)
- X{
- X char fname[MAX_FILENAMELENGTH+1]; // filename to search for
- X FInfo *rec;
- X
- X clear();
- X sstrcr("Enter any substring to search for.");
- X cr();
- X sstr("Search for what string? ");
- X gstr(fname,MAX_FILENAMELENGTH);
- X if (fname[0] == 0)
- X return(0);
- X list_obj.top();
- X while (rec = list_obj.next(), rec != NULL)
- X {
- X if (strstr(rec->name,fname) != NULL)
- X {
- X info(rec,NULL,NULL);
- X waitcr();
- X if (can_download)
- X {
- X cr();
- X sstr("Download this file? ");
- X if (yesno())
- X download(&rec,1,1);
- X }
- X sstr("Continue with search? ");
- X if (!yesno())
- X break;
- X }
- X }
- X cr();
- X sstrcr("No more files found.");
- X waitcr();
- X return(0);
- X};
- X
- X// Function: upload
- X// Purpose: upload file(s) to the BBS
- X// Input: name - name of user (for temp directory name)
- X// Output: if the file upload is successful, it will be moved to the
- X// bbs directory upload directory (or wherever the uploaddir is)
- X// Author: Greg Shaw
- X// Created: 8/9/93
- X
- Xint files::upload(char *uname, char *editor, int *credminutes)
- X{
- X DIR *fdir; // directory file descriptor
- X struct dirent *dentry; // directory entry
- X struct stat fistat; // file status record
- X time_t now; // upload date
- X time_t start; // start of upload time
- X time_t end; // end of upload time
- X FILE *outfile; // protocols file
- X FILE *infile; // protocols file
- X int off; // offset into line
- X int x;
- X int numuploads; // number of files uploaded
- X int numprot; // number of 'real' protocols
- X int protsel; // index of selected protocol
- X int done; // loop boolean
- X int linenum; // line number
- X char c; // one char from file
- X char tmpstr[255]; // temp str
- X char tmpstr2[255]; // temp str
- X char bbsdir[255]; // temp str
- X char comm[MAX_DL_COMMANDS][50]; // 15 commands max
- X char key[MAX_DL_COMMANDS]; // key for selecting command
- X char needs_filename[MAX_DL_COMMANDS];// key for selecting command
- X char filename[MAX_FILENAMELENGTH]; // filename
- X char text[MAX_DL_COMMANDS][50]; // text describing command
- X char line[255];
- X
- X time(&start);
- X numuploads = 0;
- X strcpy(bbsdir,getenv("BBSDIR")); // not checking error
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/config/protocols");
- X // read protocols file. digest. display options to user.
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X ap_log("Unable to open config/protocols file.");
- X return(0);
- X }
- X // now read protocols file.
- X numprot = 0;
- X while (!feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\n' && c != '\r' && !feof(infile))
- X line[off++] = c;
- X // now digest line
- X line[off] = 0; // add null (for posterity) (and possibly anterity)
- X if (off < 5 || feof(infile)) // line can't be less than 5 chars long
- X continue;
- X if (line[0] == 'U') // we care about upload only
- X {
- X // get command
- X // note: this is pretty nasty. Beer (good) and programming
- X // are not necessarily mutually exclusive.
- X // although beer and excellent programming may be.
- X off = 2;
- X while (line[off] != '|' && line[off] != 0)
- X {
- X comm[numprot][off-2] = line[off++];
- X }
- X comm[numprot][off-2] = 0; // add null
- X off++; // skip |
- X needs_filename[numprot] = line[off++]; // get 'needs filename' information
- X off++; // skip |
- X key[numprot] = line[off++]; // get hot key
- X off++; // skip |
- X x = off; // give an offset
- X while (line[off] != 0)
- X text[numprot][off - x] = line[off++];
- X text[numprot++][off-x] = 0;
- X }
- X }
- X bclose(infile);
- X // now show the bastich the protcols and let him choose...
- X cr();
- X sstrcr("Select Upload Protocol: (or q to quit) ");
- X cr();
- X for (x=0; x<numprot; x++)
- X sstrcr(text[x]);
- X cr();
- X sstr("Your choice? ");
- X done = 0;
- X while (!done)
- X {
- X c = gch(1);
- X if (c == 'q')
- X return(0);
- X for (x=0; x<numprot; x++)
- X if (key[x] == c)
- X {
- X done++;
- X protsel = x;
- X }
- X }
- X // Got protocol. Now create temp directory.
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/tmp/"); // bbsdir/tmp
- X strcat(tmpstr,uname); // bbsdir/tmp/username
- X if (mkdir(tmpstr,(S_IRUSR | S_IWUSR | S_IXUSR)) != 0 && errno != EEXIST)
- X {
- X sprintf(tmpstr,"Unable to create %s/tmp/%s",bbsdir,uname);
- X ap_log(tmpstr);
- X return(-1);
- X }
- X // Ok. Change current working directory to new directory
- X chdir(tmpstr); // change to new directory
- X if (needs_filename[protsel] == 'y')
- X {
- X cr();
- X cr();
- X sstrcr("Enter 'q' to exit.");
- X sstr("Please enter the filename: ");
- X gstr(filename,MAX_FILENAMELENGTH);
- X fflush(stdout);
- X if (strcmp(filename,"q") == 0)
- X {
- X sstrcr("Upload aborted.");
- X waitcr();
- X return(0);
- X }
- X }
- X cr();
- X cr();
- X sstrcr("Ready to start upload.");
- X cr();
- X strcpy(tmpstr,comm[protsel]);
- X if (needs_filename[protsel] == 'y')
- X {
- X strcat(tmpstr," ");
- X strcat(tmpstr,filename);
- X }
- X // ok. pass to system
- X waitcr();
- X sysint(tmpstr);
- X clear();
- X cr();
- X cr();
- X sstr("Was the upload successful? ");
- X if (!yesno())
- X {
- X sstr("Would you like to save your transfer to resume later? ");
- X if (!yesno())
- X {
- X sprintf(tmpstr,"rm -rf %s/tmp/%s",bbsdir,uname);
- X sysint(tmpstr);
- X }
- X return(0);
- X }
- X // now look at directory and get filename(s) that were uploaded
- X time(&now);
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/filehdr/"); // tack on files header
- X strcat(tmpstr,name);
- X if (outfile = bopen(tmpstr,"a"), outfile == NULL)
- X {
- X sprintf(tmpstr,"Unable to open files section header %s",name);
- X ap_log(tmpstr);
- X return(0);
- X }
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/tmp/");
- X strcat(tmpstr,uname);
- X if (fdir = opendir(tmpstr), fdir == NULL)
- X {
- X sprintf(line,"Unable to open directory %s for reading.\n",tmpstr);
- X bclose(outfile);
- X ap_log(line);
- X return(0);
- X }
- X // ok. now loop for every file found, getting file information
- X while (dentry = readdir(fdir), dentry != NULL)
- X {
- X strcpy(tmpstr,bbsdir);
- X strcat(tmpstr,"/tmp/");
- X strcat(tmpstr,uname);
- X strcat(tmpstr,"/");
- X strcat(tmpstr,dentry->d_name); // for stat
- X if (stat(tmpstr,&fistat) == 0 && S_ISREG(fistat.st_mode))
- X {
- X sprintf(tmpstr,"Was file %s uploaded correctly? ",dentry->d_name);
- X sstr(tmpstr);
- X if (!yesno())
- X continue; // skip bad file upload
- X fprintf(outfile,"[A %s 0 %s ]\n",uname, dentry->d_name);
- X sprintf(tmpstr,"Entering information for file %s.",dentry->d_name);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Please enter a short (less than 40 characters) description for the file. ");
- X sstr(": ");
- X gstr(tmpstr,40);
- X fprintf(outfile,"[B %s ]\n",tmpstr);
- X // get machine requirements
- X cr();
- X sstrcr("Please enter the software/hardware requirements ");
- X sprintf(tmpstr,"for file %s: ",dentry->d_name);
- X sstr(tmpstr);
- X gstr(tmpstr,40);
- X fprintf(outfile,"[C %s ]\n",tmpstr);
- X // now get the long description
- X // create temp file
- X strcpy(tmpstr,"bbsXXXXXX");
- X mktemp(tmpstr);
- X if (tmpstr[0] == 0)
- X {
- X ap_log("Unable to create temp file for upload long description entry.");
- X fprintf(outfile,"[D ]\n");
- X fprintf(outfile,"[E ]\n");
- X fprintf(outfile,"[F ]\n");
- X continue;
- X }
- X // got temp file. pass to system.
- X cr();
- X cr();
- X sstrcr("Now enter the long description for the file.");
- X sstrcr("I will pass you to your editor. Please enter up to 3 ");
- X sstrcr("lines of text (80 columns per line).");
- X sstrcr("Note: Anything more than 3 lines will be ignored.");
- X
- X waitcr();
- X strcpy(filename,tmpstr);
- X strcpy(tmpstr,editor);
- X strcat(tmpstr," /tmp/");
- X strcat(tmpstr,filename);
- X sysint(tmpstr);
- X strcpy(tmpstr,"/tmp/");
- X strcat(tmpstr,filename); // now open file
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X fprintf(outfile,"[D ]\n");
- X fprintf(outfile,"[E ]\n");
- X fprintf(outfile,"[F ]\n");
- X continue;
- X }
- X // now digest file
- X linenum = 0;
- X off = 0;
- X line[0] = 0;
- X while (!feof(infile))
- X {
- X while (c = fgetc(infile), c != '\r' && c != '\n' && !feof(infile))
- X line[off++] = c;
- X line[off] = 0;
- X linenum++;
- X switch(linenum)
- X {
- X case 1:
- X fprintf(outfile,"[D %s ]\n",line);
- X off = 0;
- X break;
- X case 2:
- X fprintf(outfile,"[E %s ]\n",line);
- X off = 0;
- X break;
- X case 3:
- X fprintf(outfile,"[F %s ]\n",line);
- X off = 0;
- X }
- X }
- X if (linenum < 3) // got all 3 lines?
- X {
- X if (linenum == 0) // no lines
- X {
- X fprintf(outfile,"[D %s ]\n",line);
- X fprintf(outfile,"[E ]\n");
- X fprintf(outfile,"[F ]\n");
- X }
- X else if (linenum == 1) // one line
- X {
- X fprintf(outfile,"[E %s ]\n",line);
- X fprintf(outfile,"[F ]\n");
- X }
- X else if (linenum == 2) // two lines
- X fprintf(outfile,"[F %s ]\n",line);
- X }
- X bclose(infile);
- X // now move file to uploads area
- X sprintf(tmpstr,"%s/tmp/%s/%s",bbsdir,uname,dentry->d_name);
- X sprintf(line,"%s/%s/%s",bbsdir,up_path,dentry->d_name);
- X if (rename(tmpstr,line))
- X {
- X sprintf(tmpstr2,"Unable to move %s to %s",tmpstr,line);
- X ap_log(tmpstr2);
- X }
- X sprintf(tmpstr,"/tmp/%s",filename);
- X unlink(tmpstr); // remove temp file
- X numuploads++;
- X sprintf(tmpstr,"%s uploaded %s to %s",uname,dentry->d_name,name);
- X ap_log(tmpstr);
- X }
- X }
- X bclose(outfile);
- X closedir(fdir);
- X sprintf(tmpstr,"%s",bbsdir);
- X chdir(tmpstr); // change to bbs root directory
- X sprintf(tmpstr,"%s/filehdr/%s",bbsdir,name);
- X chmod(tmpstr,0775); // chmod 775
- X chown(tmpstr,bbs_uid(),bbs_gid()); // change owner to bbs
- X sprintf(tmpstr,"%s/tmp/%s",bbsdir,uname);
- X chmod(tmpstr,0775); // chmod 775
- X chown(tmpstr,bbs_uid(),bbs_gid()); // change owner to bbs
- X sprintf(tmpstr,"%s/tmp/%s/* 2> /dev/null",bbsdir,uname);
- X unlink(tmpstr); // remove any leftover files
- X sprintf(tmpstr,"%s/tmp/%s 2> /dev/null",bbsdir,uname);
- X rmdir(tmpstr); // remove upload directory
- X cr();
- X sstrcr("End of upload.");
- X cr();
- X sstrcr("The file(s) have been moved to the upload directory.");
- X sstrcr("After being reviewed, they will be available for download.");
- X waitcr();
- X time(&end);
- X *credminutes = (end - start)/60;
- X return(numuploads);
- X};
- X
- X
- X
- X#endif // _FILES_C_
- END_OF_FILE
- if test 47604 -ne `wc -c <'rocat-0.75/src/files.C'`; then
- echo shar: \"'rocat-0.75/src/files.C'\" unpacked with wrong size!
- fi
- chmod +x 'rocat-0.75/src/files.C'
- # end of 'rocat-0.75/src/files.C'
- fi
- if test -f 'rocat-0.75/src/user.C' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'rocat-0.75/src/user.C'\"
- else
- echo shar: Extracting \"'rocat-0.75/src/user.C'\" \(45033 characters\)
- sed "s/^X//" >'rocat-0.75/src/user.C' <<'END_OF_FILE'
- X// Filename: User.c
- X// Contents: the methods for the User object
- X// Author: Greg Shaw
- X// Created: 6/1/93
- X
- X/*
- XThis file is free software; you can redistribute it and/or modify it
- Xunder the terms of the GNU General Public License as published by the
- XFree Software Foundation; either version 2, or (at your option) any
- Xlater version.
- X
- XIn addition to the permissions in the GNU General Public License, the
- XFree Software Foundation gives you unlimited permission to link the
- Xcompiled version of this file with other programs, and to distribute
- Xthose programs without any restriction coming from the use of this
- Xfile. (The General Public License restrictions do apply in other
- Xrespects; for example, they cover modification of the file, and
- Xdistribution when not linked into another program.)
- X
- XThis file is distributed in the hope that it will be useful, but
- XWITHOUT ANY WARRANTY; without even the implied warranty of
- XMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- XGeneral Public License for more details.
- X
- XYou should have received a copy of the GNU General Public License
- Xalong with this program; see the file COPYING. If not, write to
- Xthe Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
- X
- X#ifndef _USER_C_
- X#define _USER_C_
- X
- X#include "bbshdr.h"
- X
- X// Function: append
- X// Purpose: append a new user record to the user file
- X// Input: object attributes
- X// Output: (file is written)
- X// Author: Greg Shaw
- X// Created: 7/20/93
- X
- Xint User::append(void)
- X{
- X FILE *ofile;
- X char finame[255]; // filename
- X char line[255]; // one line in file (255 max)
- X char bbspath[225]; // bbs path
- X
- X if (strcpy(bbspath,getenv("BBSDIR")), bbspath == NULL)
- X {
- X sprintf(finame,"user.save: BBSDIR env var not set for %s",login_name);
- X ap_log(finame);
- X return(-1);
- X }
- X strcpy(line,bbspath);
- X strcat(line,"/admin/userlog");
- X if (ofile = bopen(line,"a"), ofile == NULL)
- X {
- X sprintf(line,"user.save: Unable to open userlog file ");
- X ap_log(line);
- X return(-1);
- X }
- X //[A login_name firstname lastname state city]
- X fprintf(ofile,"[A %s %s %s %s %s %s ]\n", login_name, fname, lname, alias, state, city);
- X //[B terminal_type last_logon #_logins downloads uploads card_color]
- X fprintf(ofile,"[B %s %ld %d %d %d %s ]\n", uterm,
- X last_login, logins, downloads, uploads, card->colr);
- X //[C private_msgs public_msgs credited_time has_color editor lines cols]
- X fprintf(ofile,"[C %d %d %d %d %s %d %d ]\n",priv_msgs,pub_msgs,
- X credited, has_color, editor, lines, cols);
- X //[D flags access_level timelimit timeused_last_call anniversary kused ]
- X fprintf(ofile,"[D %lx %d %d %d %ld %d ]\n",flags, acl, timelimit, timeused, anniversary, kused);
- X bclose(ofile);
- X return(0);
- X};
- X
- X// Function: change_acl
- X// Purpose: change the user's access level (possibly permanently)
- X// Input: acl - the timlit to change to
- X// perm - permanent or not
- X// Output: none
- X// Author: Greg Shaw
- X// Created: 6/8/93
- X
- Xint User::change_acl(int acl, char perm)
- X{
- X if (perm)
- X acl = acl;
- X else
- X tmpacl = acl;
- X return(0);
- X}
- X
- X// Function: change_flags
- X// Purpose: change the user's timelimit (possibly permanently)
- X// Input: flags - the flags to change to
- X// perm - permanent or not
- X// or - or into user flags or and into user flags
- X// Output: none
- X// Author: Greg Shaw
- X// Created: 6/9/93
- X
- Xint User::change_flags(unsigned long fl, char perm, char or)
- X{
- X if (perm)
- X if (or)
- X flags |= fl;
- X else
- X flags &= fl;
- X else
- X if (or)
- X tmpflags |= fl;
- X else
- X tmpflags &= fl;
- X return(0);
- X}
- X
- X// Function: change_tl
- X// Purpose: change the user's timelimit (possibly permanently)
- X// Input: tl - the timlit to change to
- X// perm - permanent or not
- X// Output: none
- X// Author: Greg Shaw
- X// Created: 6/8/93
- X
- Xint User::change_tl(int tl, char perm)
- X{
- X if (perm)
- X timelimit = tl;
- X else
- X tmptl = tl;
- X return(0);
- X}
- X
- X// Function: check_card
- X// Purpose: check the user's access information vs. the card color he has
- X// Input: none
- X// Output: (user may be changed)
- X// Author: Greg Shaw
- X
- Xint User::check_card(void)
- X{
- X if (card = cardinfo(card_color), card == NULL)
- X return(-1);
- X if (acl < card->acl) // only update info if card better
- X acl = card->acl;
- X if (timelimit < card->tl)
- X timelimit = card->tl;
- X flags |= card->flags;
- X return(0);
- X};
- X
- X// Function: delete_user
- X// Purpose: delete a user from the BBS
- X// Input: name - the login name of the user to delete
- X// Output: none
- X// Author: Greg Shaw
- X// Created: 4/11/94
- X
- Xint User::delete_user(char *name)
- X{
- X};
- X
- X// Function: display_info
- X// Purpose: display the user's information
- X// Input: logon - has the user just logged on? (it gives 'welcome' message
- X// Output: user information is formatted and printed.
- X// Author: Greg Shaw
- X// Created: 7/2793
- X
- Xint User::display_info(int logon)
- X{
- X char tmpstr[255]; // string
- X char *str2; // used for time
- X
- X clear();
- X if (logon)
- X sprintf(tmpstr,"Welcome back %s %s from %s, %s!",fname,lname,city,state);
- X else
- X sprintf(tmpstr,"You are %s %s from %s, %s,",fname,lname,city,state);
- X sstrcr(tmpstr);
- X str2 = ctime(&login_time);
- X str2[strlen(str2)-1] = 0; // chop \n
- X sprintf(tmpstr,"You have been on since %s",str2);
- X sstrcr(tmpstr);
- X str2 = ctime(&last_login);
- X str2[strlen(str2)-1] = 0; // chop \n
- X sprintf(tmpstr,"You have logged in %d times. Your last logon was %s",logins,str2);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"Your alias is %s, your editor %s and your terminal is %s",alias,editor,uterm);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"which has %d lines and %d columns.",lines,cols);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"Your membership card color is %s, which entitles you to ",card->colr);
- X sstrcr(tmpstr);
- X if (card->kbytes > 0)
- X sprintf(tmpstr,"to %d minutes on-line and %d k-bytes of downloads every %d hours",timelimit,card->kbytes,waittime());
- X else
- X sprintf(tmpstr,"to %d minutes on-line and unlimited downloads every %d hours",timelimit,card->kbytes,waittime());
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"You have %d credited minutes, have downloaded %d files",credited,downloads);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"and uploaded %d files.",uploads);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"Last call you used %d minutes and downloaded %d kbytes.",timeused,kused);
- X sstrcr(tmpstr);
- X waitcr();
- X return(0);
- X};
- X
- X// Function: export
- X// Purpose: export the user's environment variables
- X// Input: none
- X// Output: (environment vars are exported)
- X// Author: Greg Shaw
- X// Created: 7/2793
- X
- Xint User::export(void)
- X{
- X char tmpmsg[100];
- X char *outmsg;
- X
- X sprintf(tmpmsg,"EDITOR=%s",editor);
- X if (outmsg = (char *) malloc(strlen(tmpmsg)+1), outmsg == NULL)
- X {
- X ap_log("Unable to malloc more environment space.");
- X }
- X strcpy(outmsg,tmpmsg);
- X if (putenv(outmsg) != 0)
- X ap_log("Unable to export variable.");
- X sprintf(tmpmsg,"VISUAL=%s",editor);
- X if (outmsg = (char *) malloc(strlen(tmpmsg)+1), outmsg == NULL)
- X {
- X ap_log("Unable to malloc more environment space.");
- X }
- X strcpy(outmsg,tmpmsg);
- X if (putenv(outmsg) != 0)
- X ap_log("Unable to export variable.");
- X sprintf(tmpmsg,"TERM=%s",uterm);
- X if (outmsg = (char *) malloc(strlen(tmpmsg)+1), outmsg == NULL)
- X {
- X ap_log("Unable to malloc more environment space.");
- X }
- X strcpy(outmsg,tmpmsg);
- X if (putenv(outmsg) != 0)
- X ap_log("Unable to export variable.");
- X sprintf(tmpmsg,"LINES=%s",lines);
- X if (outmsg = (char *) malloc(strlen(tmpmsg)+1), outmsg == NULL)
- X {
- X ap_log("Unable to malloc more environment space.");
- X }
- X strcpy(outmsg,tmpmsg);
- X if (putenv(outmsg) != 0)
- X ap_log("Unable to export variable.");
- X sprintf(tmpmsg,"COLUMNS=%s",cols);
- X if (outmsg = (char *) malloc(strlen(tmpmsg)+1), outmsg == NULL)
- X {
- X ap_log("Unable to malloc more environment space.");
- X }
- X strcpy(outmsg,tmpmsg);
- X if (putenv(outmsg) != 0)
- X ap_log("Unable to export variable.");
- X return(0);
- X};
- X
- X
- X// Function: get
- X// Purpose: get the user's info from the user list
- X// Input: none
- X// Output: object is loaded or an error is returned
- X// Author: Greg Shaw
- X// Created: 7/13/93
- X// Notes: the user file is a plain text file (to allow editing).
- X// its format is such:
- X// [A login_name firstname lastname]
- X// [B terminal_type last_logon #_logins downloads uploads card color]
- X// [C private_msgs public_msgs credited_time has_color editor lines cols]
- X// [D flags access_level timelimit timeused_last_call]
- X// the above format includes the brackets and lines (for reference)
- X
- Xint User::get(char *name)
- X{
- X FILE *ufile;
- X char *u;
- X char finame[255]; // filename
- X char line[255]; // one line in file (255 max)
- X char logname[10]; // user login name
- X char found; // user found?
- X char linenum; // used to look for appropriate line
- X char c; // input char
- X unsigned char of; // offset into line
- X int x;
- X struct passwd *userent; // user entry in password file
- X
- X if (name == NULL)
- X strcpy(logname,username()); // get user's login information
- X else
- X strcpy(logname,name);
- X if (strcpy(finame,getenv("BBSDIR")), fname == NULL)
- X {
- X sprintf(finame,"user.get: BBSDIR environment variable not set for %s",logname);
- X ap_log(finame);
- X return(-1);
- X }
- X strcat(finame,"/admin/userlog");
- X linenum = 0; // look for first line first
- X if (ufile = bopen(finame,"r"), ufile != NULL)
- X {
- X found = 0;
- X while (!found && !feof(ufile))
- X {
- X of = 0;
- X while (c = fgetc(ufile), c != '\r' && c != '\n' && !feof(ufile))
- X if (c != ']') // skip trailing left bracket
- X line[of++] = c;
- X line[of] = 0; // add null
- X switch(linenum)
- X {
- X case 0: // first line
- X if (line[0] == '[' && line[1] == 'A') // got line 1?
- X {
- X x = sscanf(&line[2],"%s %s %s %s %s %s",login_name,
- X fname, lname, alias, state, city);
- X if (u = strchr(city,']'), u != NULL)
- X { // convert any left brackets to null
- X u++;
- X u[0] = 0;
- X }
- X if (strcmp(login_name,logname) == 0)
- X {
- X linenum++; // get next line
- X }
- X }
- X break;
- X case 1: // second line
- X if (line[0] == '[' && line[1] == 'B') // got line 2?
- X {
- X if (sscanf(&line[2],"%s %ld %d %d %d %s",uterm,
- X &last_login, &logins, &downloads, &uploads,
- X card->colr) != 6)
- X {
- X ap_log("user.get: bad read from user file. Corrupted?");
- X sprintf(finame,"user.get: bad user record was %s, line B",login_name);
- X ap_log(finame);
- X return(-1);
- X }
- X linenum++; // get next line
- X if (!strcmp(card->colr,"red"))
- X card_color = 0;
- X if (!strcmp(card->colr,"blue"))
- X card_color = 1;
- X if (!strcmp(card->colr,"green"))
- X card_color = 2;
- X if (!strcmp(card->colr,"white"))
- X card_color = 3;
- X if (!strcmp(card->colr,"grey"))
- X card_color = 4;
- X if (!strcmp(card->colr,"pink"))
- X card_color = 5;
- X if (!strcmp(card->colr,"yellow"))
- X card_color = 6;
- X if (!strcmp(card->colr,"black"))
- X card_color = 7;
- X }
- X break;
- X case 2: // third line
- X if (line[0] == '[' && line[1] == 'C') // got line 3?
- X {
- X if (sscanf(&line[2],"%d %d %d %d %s %d %d",&priv_msgs,&pub_msgs,
- X &credited, &has_color, editor, &lines, &cols) != 7)
- X {
- X ap_log("user.get: bad read from user file. Corrupted?");
- X sprintf(finame,"user.get: bad user record was %s, line C",login_name);
- X ap_log(finame);
- X return(-1);
- X }
- X linenum++; // get next line
- X }
- X break;
- X case 3: // fourth line
- X if (line[0] == '[' && line[1] == 'D') // got line 4?
- X {
- X if (sscanf(&line[2],"%lx %d %d %d %ld %d",&flags,
- X &acl, &timelimit, &timeused, &anniversary,&kused) != 6)
- X {
- X ap_log("user.get: bad read from user file. Corrupted?");
- X sprintf(finame,"user.get: bad user record was %s, line D",login_name);
- X ap_log(finame);
- X return(-1);
- X }
- X linenum++; // get next line
- X }
- X break;
- X }
- X if (linenum == 4) // got him.
- X {
- X found++;
- X bclose(ufile);
- X logins++;
- X if (name != NULL && (login_time - last_login)/60 < waittime())
- X {
- X if ((timelimit - timeused) < 5)
- X {
- X clear();
- X sstrcr("You do not have enough unused time on the BBS to logon.");
- X sprintf(finame,"In the future, please wait at least %d hours before logging on again.",waittime());
- X sstrcr(finame);
- X cr();
- X cr();
- X waitcr();
- X sstrcr("Thanks for Calling!");
- X exit(0);
- X }
- X }
- X else
- X {
- X kused = 0; // start all counters over
- X timeused = 0;
- X credited = 0;
- X }
- X tmpflags = flags;
- X tmpacl = acl;
- X tmptl = timelimit;
- X if (name == NULL)
- X {
- X sprintf(line,"Logon for %s %s",fname,lname);
- X ap_log(line);
- X export(); // export his environment variables
- X check_card(); // check his access level vs. card
- X }
- X return(1); // return 1 for new user only
- X }
- X }
- X }
- X bclose(ufile); // close just in case
- X // didn't find him in user file. Need to get his information
- X if (name != NULL) // error - unable to find user in userlog
- X {
- X sprintf(line,"Unable to find %s in userlog.",name);
- X ap_log(line);
- X return(0);
- X }
- X strcpy(login_name,logname); // get login name
- X sstrcr("I am unable to find you in the user list of the bbs.");
- X sstr("Would you like to register for the bbs? ");
- X if (!yesno())
- X {
- X fflush(stdout);
- X sprintf(finame,"user.get: %s decided not to register for bbs.",logname);
- X ap_log(finame);
- X return(-1);
- X }
- X cr();
- X if (userent = getpwnam((char *)username()), userent == NULL)
- X {
- X sprintf(finame,"user.get: Unable to get user %s's password entry!",logname);
- X ap_log(finame);
- X return(-1);
- X }
- X sscanf(userent->pw_gecos,"%s %s",fname,lname); // get user name
- X getinfo(1); // get user information
- X export(); // export his environment variables
- X check_card(); // check his access level vs. card
- X append();
- X sprintf(line,"Logon for %s %s",fname,lname);
- X ap_log(line);
- X return(0);
- X}
- X
- X// Function: getinfo
- X// Purpose: prompt the user for information to setup the user object
- X// Input: firsttime - is this the first logon by user?
- X// Output: (user questions)
- X// Author: Greg Shaw
- X// Created: 7/25/93
- X
- Xint User::getinfo(char firsttime)
- X{
- X char loop; // loop counter
- X char done; // loop counter
- X char entered; // entered anything?
- X char tmpstr[255];
- X char anotherstr[50]; // another string
- X char finame[255]; // filename
- X char logname[10]; // user login name
- X
- X loop = 1;
- X entered = 0;
- X while (loop)
- X {
- X clear(); // clear screen
- X if (!firsttime || entered)
- X {
- X cr();
- X cr();
- X cr();
- X sstrcr("You have entered the following:");
- X cr();
- X sprintf(finame,"Login: %s",login_name);
- X sstrcr(finame);
- X sprintf(finame,"Real Name: %s %s",fname,lname);
- X sstrcr(finame);
- X sprintf(finame,"Alias: %s",alias);
- X sstrcr(finame);
- X sprintf(finame,"Calling from: %s, %s",city,state);
- X sstrcr(finame);
- X sprintf(finame,"Terminal type: %s",uterm);
- X sstrcr(finame);
- X sprintf(finame,"Terminal supports color: %s",has_color?"Yes":"No");
- X sstrcr(finame);
- X sprintf(finame,"Editor: %s",editor);
- X sstrcr(finame);
- X sprintf(finame,"Lines: %d Columns: %d",lines,cols);
- X sstrcr(finame);
- X cr();
- X sstr("Is this correct? ");
- X if (yesno())
- X loop = 0;
- X }
- X if (loop) // still looping?
- X {
- X if (!firsttime)
- X sstrcr("Enter 'x' to keep your old entry in any field.");
- X strcpy(logname,username()); // get user's login information
- X done = 0;
- X while (!done)
- X {
- X sstrcr("If your city is two words, please enter the city as a word separated by a dash.");
- X sstrcr("Example: Fort Collins would be Fort-Collins.");
- X sstr("To begin, please enter the city you are calling from: ");
- X if (gstr(tmpstr,20), strcmp(tmpstr,"") == 0)
- X continue;
- X if (!strcmp(tmpstr,"x"))
- X {
- X if (firsttime) // no empty entries for first time
- X continue;
- X }
- X else
- X strcpy(city,tmpstr);
- X done++;
- X }
- X cr();
- X done = 0;
- X while (!done)
- X {
- X sstrcr("Please enter the state where you are calling from.");
- X sstr("Only two letters, please. (example: CO for Colorado) ");
- X if (gstr(tmpstr,2), strcmp(tmpstr,"") == 0)
- X continue;
- X if (!strcmp(tmpstr, "x"))
- X {
- X if (firsttime) // no empty entries for first time
- X continue;
- X }
- X else
- X strcpy(state,tmpstr);
- X done++;
- X }
- X cr();
- X done = 0;
- X while (!done)
- X {
- X sstrcr("Now comes a tough question. On Unix (which is what this");
- X sstrcr("BBS runs under), it is *VERY* important that you get ");
- X sstrcr("your terminal type (the type of terminal emulation supported");
- X sstrcr("by your software) entered correctly.");
- X cr();
- X sstrcr("If entered incorrectly, it can cause problems in");
- X sstrcr("programs external to the BBS, such as mail programs.");
- X sstrcr("Also, if your terminal type is entered");
- X sstrcr("correctly, it will enable the bbs to use some of the more");
- X sstrcr("advanced features of your program.");
- X cr();
- X sstrcr("If you're calling in from a PC-ANSI emulating terminal, I'd");
- X sstrcr("recommend the 'ansi' terminal type.");
- X sstrcr("'vt100' is another popular terminal type.");
- X sstrcr("Unless you *KNOW* what terminal type you've got (like a wyse60 terminal),");
- X sstrcr("enter 'vt100' or 'ansi'");
- X cr();
- X sstrcr("Note: You must enter the terminal type in lower case.");
- X sstr("What terminal type would you like to use? ");
- X if (gstr(tmpstr,20), strcmp(tmpstr,"") == 0)
- X continue;
- X if (!strcmp(tmpstr,"x"))
- X {
- X if (firsttime) // no empty entries for first time
- X continue;
- X }
- X else
- X strcpy(uterm,tmpstr);
- X done++;
- X }
- X cr();
- X cr();
- X sstr("Does your terminal program support color? ");
- X if (yesno())
- X has_color = 1;
- X else
- X has_color = 0;
- X cr();
- X cr();
- X if (strcpy(finame,getenv("BBSDIR")), finame == NULL)
- X {
- X sprintf(finame,"user.get: BBSDIR env var not set for %s",logname);
- X ap_log(finame);
- X return(-1);
- X }
- X strcat(finame,"/text/editors");
- X sprintf(tmpstr,"Viewing %s",finame);
- X sysopstrcr(tmpstr);
- X display_file(finame,1); // display file with paging
- X cr();
- X cr();
- X done = 0;
- X while (!done)
- X {
- X sstrcr("Note: the editor name must be lower case");
- X sstr("Which editor would you like to use? ");
- X if (gstr(tmpstr,14), strcmp(tmpstr,"") == 0)
- X continue;
- X if (!strcmp(tmpstr,"x"))
- X {
- X if (firsttime) // no empty entries for first time
- X continue;
- X }
- X else
- X strcpy(editor,tmpstr);
- X done++;
- X }
- X cr();
- X cr();
- X sstrcr("You may also enter an alias, or, you may use your logon");
- X sstrcr("name as your alias. Would you like to user your logon as");
- X sstr("your alias? (y/n) ");
- X if (yesno())
- X strcpy(alias,logname);
- X else
- X {
- X done = 0;
- X while (!done)
- X {
- X sstrcr("Your alias must be only one word.");
- X sstr("Please enter your alias: ");
- X if (gstr(tmpstr,20), strcmp(tmpstr,"") == 0)
- X continue;
- X if (!strcmp(tmpstr,"x"))
- X {
- X if (firsttime) // no empty entries for first time
- X continue;
- X }
- X else
- X if (sscanf(tmpstr,"%s%s",alias,anotherstr) != 1)
- X continue;
- X done++;
- X }
- X }
- X cr();
- X cr();
- X done = 0;
- X while (!done)
- X {
- X sstrcr("I need to know how many lines are on your screen.");
- X sstrcr("Enter 'x' for the default 24 lines per screen.");
- X sstr("How many lines does your terminal support? ");
- X if (gstr(tmpstr,5), strcmp(tmpstr,"") == 0)
- X continue;
- X if (tmpstr[0] == 'x')
- X {
- X lines = 24;
- X }
- X else
- X sscanf(tmpstr,"%d",&lines);
- X done++;
- X }
- X cr();
- X cr();
- X done = 0;
- X while (!done)
- X {
- X sstrcr("I need to know how many columns are on your screen.");
- X sstrcr("Enter 'x' for the default 80 columns per screen.");
- X sstr("How many columns does your terminal support? ");
- X if (gstr(tmpstr,5), strcmp(tmpstr,"") == 0)
- X continue;
- X if (tmpstr[0] == 'x')
- X {
- X cols = 80;
- X }
- X else
- X sscanf(tmpstr,"%d",&cols);
- X done++;
- X }
- X entered++;
- X }
- X }
- X export();
- X return(0);
- X};
- X
- X// Function: inactive_list
- X// Purpose: list the inactive (people who haven't called lately) users
- X// Input: none
- X// Output: A list of users who haven't called in a specified time
- X// Author: Greg Shaw
- X// Created: 4/3/94
- X
- Xint User::inactive_list(void)
- X{
- X char tmpstr[255];
- X char line[150];
- X char c;
- X char key[MAX_FILENAMELENGTH+1];
- X char uname[10];
- X char fullname[50];
- X char fname[15];
- X char lname[15];
- X char tmp[2][15];
- X char state[50];
- X char city[50];
- X char llogon[10];
- X char from[50];
- X char *sptr;
- X int logins;
- X int uls,dls;
- X time_t laston;
- X time_t today;
- X struct tm *tmdata;
- X int off;
- X int found;
- X int days;
- X FILE *infile;
- X
- X
- X clear();
- X time(&today);
- X // get number of days inactive to search for
- X sstrcr("I need to know how many days to search back to list");
- X sstrcr("the inactive users. For example, 30 would mean that");
- X sstrcr("the user hasn't called in the last 30 days minimum.");
- X cr();
- X sstr("How many days ago since last call should I list? ");
- X gstr(key,MAX_FILENAMELENGTH);
- X if (key[0] == 0 || sscanf(key,"%d",&days) != 1)
- X return(0);
- X sprintf(tmpstr,"%s/admin/userlog",getenv("BBSDIR"));
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X ap_log("Unable to open userlog for read.");
- X return(0);
- X }
- X found = 0;
- X sstrcr("Username From Last Logon Uls Dls");
- X while (!feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\n' && c != '\r' && !feof(infile))
- X line[off++] = c;
- X line[off] = 0;
- X if (line[0] == '[')
- X {
- X if (line[1] == 'A')
- X {
- X sscanf(&line[2],"%s %s %s %s %s %s %s %s", uname, fname, lname, alias, state, city,tmp[0], tmp[1]);
- X strcat(city,tmp[0]);
- X strcat(city,tmp[1]);
- X if (sptr = strchr(city,']'), sptr != NULL)
- X sptr[0] = 0;
- X } else if (line[1] == 'B')
- X {
- X sscanf(&line[2],"%*s %ld %d %d %d %*s",&laston, &logins,&uls,&dls);
- X sprintf(fullname,"%s %s",fname,lname);
- X sprintf(from,"%s, %s",city,state);
- X tmdata = localtime(&laston);
- X strftime(llogon, 12, "%b %d,%Y", tmdata);
- X if ((today - laston)/86400 >= days)
- X {
- X sprintf(tmpstr,"%-15s %-15s %s %d %d",fullname,from,llogon,uls,dls);
- X sstrcr(tmpstr);
- X found++;
- X }
- X if (found == 17)
- X {
- X found = 0;
- X waitcr();
- X sstr("Continue listing? ");
- X if (!yesno())
- X {
- X bclose(infile);
- X return(0);
- X }
- X }
- X }
- X }
- X }
- X cr();
- X sstrcr("No more found.");
- X bclose(infile);
- X waitcr();
- X return(0);
- X};
- X
- X// Function: inactive_delete
- X// Purpose: delete inactive users on the BBS
- X// Input: none
- X// Output: A list of users who haven't called in a specified time
- X// Author: Greg Shaw
- X// Created: 4/21/94
- X
- Xint User::inactive_delete(void)
- X{
- X char tmpstr[255];
- X char line[150];
- X char c,b;
- X char key[MAX_FILENAMELENGTH+1];
- X char uname[10];
- X char fullname[50];
- X char fname[15];
- X char lname[15];
- X char tmp[2][15];
- X char state[50];
- X char city[50];
- X char llogon[10];
- X char from[50];
- X char *sptr;
- X int x;
- X int logins;
- X int uls,dls;
- X time_t laston;
- X time_t today;
- X struct tm *tmdata;
- X int off;
- X int found;
- X int days;
- X FILE *infile;
- X FILE *outfile;
- X
- X
- X clear();
- X time(&today);
- X // get number of days inactive to search for
- X sstrcr("I need to know how many days to search back to delete");
- X sstrcr("the inactive users. For example, 30 would mean that");
- X sstrcr("the user hasn't called in at least 30 days.");
- X cr();
- X sstr("How many days ago since last call should I delete users? ");
- X gstr(key,MAX_FILENAMELENGTH);
- X if (key[0] == 0 || sscanf(key,"%d",&days) != 1)
- X return(0);
- X sprintf(tmpstr,"Will delete users %d days.",days);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Would you like me to delete Automatically (no prompting)");
- X sstr("or Interactively (prompted) ? (A/I) ");
- X while (b = tolower(gch(1)), b != 'a' && b != 'i');
- X cr();
- X if (b == 'i') // interactively
- X {
- X sstrcr("Prompting enabled...");
- X waitcr();
- X }
- X sprintf(tmpstr,"%s/admin/userlog",getenv("BBSDIR"));
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X ap_log("Unable to open userlog for read.");
- X sstrcr("Unable to open userlog for read.");
- X waitcr();
- X return(0);
- X }
- X strcat(tmpstr,".new"); // get 'new' filename
- X if (outfile = bopen(tmpstr,"w"), outfile == NULL)
- X {
- X ap_log("Unable to open userlog.new for write.");
- X sstrcr("Unable to open userlog.new for write.");
- X waitcr();
- X return(0);
- X }
- X found = 0;
- X while (!feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\n' && c != '\r' && !feof(infile))
- X line[off++] = c;
- X line[off] = 0;
- X if (line[0] == '[')
- X {
- X if (line[1] == 'A')
- X {
- X sscanf(&line[2],"%s %s %s %s %s %s %s %s", uname, fname, lname, alias, state, city,tmp[0], tmp[1]);
- X strcat(city,tmp[0]);
- X strcat(city,tmp[1]);
- X if (sptr = strchr(city,']'), sptr != NULL)
- X sptr[0] = 0;
- X } else if (line[1] == 'B')
- X {
- X if (sscanf(&line[2],"%s %ld %d %d %d %s",uterm, &laston, &logins,&uls,&dls,card->colr) != 6)
- X {
- X sprintf(tmpstr,"Error found in line B userlog in entry %s %s",fname,lname);
- X ap_log(tmpstr);
- X sstrcr("Error found in userlog. Clean aborted.");
- X waitcr();
- X return(0);
- X }
- X sprintf(fullname,"%s %s",fname,lname);
- X sprintf(from,"%s, %s",city,state);
- X tmdata = localtime(&laston);
- X strftime(llogon, 12, "%b %d,%Y", tmdata);
- X if ((today - laston)/86400 >= days)
- X {
- X sprintf(tmpstr,"%-15s %-15s %s %d %d",fullname,from,llogon,uls,dls);
- X sstrcr(tmpstr);
- X if (b == 'i') // interactive?
- X {
- X sstr("Delete this user? ");
- X if (yesno())
- X continue;
- X }
- X else
- X continue;
- X }
- X for (x=0; x<2; x++)
- X if (strlen(tmp[x]) < 2)
- X tmp[x][0] = 0;
- X // save info and next two lines
- X fprintf(outfile,"[A %s %s %s %s %s %s %s %s ]\n", uname, fname, lname, alias, state, city, tmp[0], tmp[1]);
- X fprintf(outfile,"%s\n",line);
- X x = 0;
- X while (x < 2)
- X {
- X if (c = fgetc(infile), c == '\n' || c == '\r')
- X x++;
- X fputc(c,outfile);
- X }
- X }
- X }
- X }
- X cr();
- X bclose(outfile);
- X sprintf(tmpstr,"%s/admin/userlog",getenv("BBSDIR"));
- X sprintf(line,"%s/admin/userlog.old",getenv("BBSDIR"));
- X rename(tmpstr,line);
- X sprintf(tmpstr,"%s/admin/userlog.new",getenv("BBSDIR"));
- X sprintf(line,"%s/admin/userlog",getenv("BBSDIR"));
- X rename(tmpstr,line);
- X waitcr();
- X return(0);
- X};
- X
- X// Function: list
- X// Purpose: return a user record
- X// Input: path - the path to the user file
- X// Output: a list of users on the bbs -
- X// Author: Greg Shaw
- X// Created: 6/8/93
- X
- Xint User::list(int search, int sysop)
- X{
- X char tmpstr[255];
- X char line[150];
- X char c;
- X char key[MAX_FILENAMELENGTH+1];
- X char uname[10];
- X char alias[25];
- X char fname[15];
- X char lname[15];
- X char tmp[2][15];
- X char state[50];
- X char city[50];
- X char *sptr;
- X int logins;
- X time_t laston;
- X int off;
- X int found;
- X FILE *infile;
- X
- X
- X clear();
- X sprintf(tmpstr,"%s/admin/userlog",getenv("BBSDIR"));
- X if (infile = bopen(tmpstr,"r"), infile == NULL)
- X {
- X ap_log("Unable to open userlog for read.");
- X return(0);
- X }
- X if (search)
- X {
- X sstrcr("You may enter any number of characters to search for.");
- X cr();
- X sstr("Search for what characters? ");
- X gstr(key,MAX_FILENAMELENGTH);
- X if (key[0] == 0)
- X return(0);
- X // search for characters in userlog
- X found = 0;
- X while (!feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\n' && c != '\r' && !feof(infile))
- X line[off++] = c;
- X line[off] = 0;
- X if (line[0] == '[')
- X {
- X if (line[1] == 'A')
- X {
- X sscanf(&line[2],"%s %s %s %s %s %s %s %s", uname, fname, lname, alias, state, city,tmp[0], tmp[1]);
- X strcat(city,tmp[0]);
- X strcat(city,tmp[1]);
- X if (sptr = strchr(city,']'), sptr != NULL)
- X sptr[0] = 0;
- X if (strstr(line,key) != NULL)
- X {
- X sprintf(tmpstr,"Name: %s %s from %s, %s",fname,lname,city,state);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"Logon: %s Alias: %s ",uname,alias);
- X sstrcr(tmpstr);
- X found++;
- X }
- X } else if (found && line[1] == 'B')
- X {
- X sscanf(&line[2],"%*s %ld %d %*d %*d %*s",&laston, &logins);
- X sptr = ctime(&laston);
- X sptr[strlen(sptr)-1] = 0; // chop \n
- X sprintf(tmpstr,"Number of logons: %d Last Logon: %s ",logins,sptr);
- X sstrcr(tmpstr);
- X waitcr();
- X if (sysop)
- X {
- X sstr("Continue, Edit or Delete? ");
- X while (c = toupper(gch(1)), c != 'D' && c != 'C' && c != 'E');
- X if (c == 'D')
- X {
- X bclose(infile);
- X delete_user(uname);
- X return(0);
- X }
- X else if (c == 'E')
- X {
- X bclose(infile);
- X if (get(uname))
- X {
- X check_card();
- X sysop_edit();
- X }
- X else
- X {
- X sprintf(tmpstr,"Unable to get %s for sysop edit.",uname);
- X ap_log(tmpstr);
- X }
- X return(0);
- X }
- X }
- X else
- X {
- X sstr("Continue search? ");
- X if (!yesno())
- X {
- X bclose(infile);
- X return(0);
- X }
- X }
- X found = 0;
- X }
- X }
- X }
- X bclose(infile);
- X }
- X else
- X {
- X found = 0;
- X while (!feof(infile))
- X {
- X off = 0;
- X while (c = fgetc(infile), c != '\n' && c != '\r' && !feof(infile))
- X line[off++] = c;
- X if (line[0] == '[')
- X {
- X if (line[1] == 'A')
- X {
- X sscanf(&line[2],"%s %s %s %s %s %s %s %s", uname, fname, lname, alias, state, city,tmp[0], tmp[1]);
- X strcat(city,tmp[0]);
- X strcat(city,tmp[1]);
- X if (sptr = strchr(city,']'), sptr != NULL)
- X sptr[0] = 0;
- X sprintf(tmpstr,"%s %s from %s, %s",fname,lname,city,state);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"Logon: %s Alias: %s ",uname,alias);
- X sstrcr(tmpstr);
- X } else if (line[1] == 'B')
- X {
- X sscanf(&line[2],"%*s %ld %d %*d %*d %*s",&laston, &logins);
- X sptr = ctime(&laston);
- X sptr[strlen(sptr)-1] = 0; // chop \n
- X sprintf(tmpstr,"Number of logons: %d Last Logon: %s ",logins,sptr);
- X sstrcr(tmpstr);
- X cr();
- X if (found == 6)
- X {
- X found = 0;
- X waitcr();
- X sstr("Continue listing? ");
- X if (!yesno())
- X {
- X bclose(infile);
- X return(0);
- X }
- X }
- X found++;
- X }
- X }
- X }
- X cr();
- X }
- X cr();
- X sstrcr("No more found.");
- X waitcr();
- X return(0);
- X}
- X
- X// Function: mailavail
- X// Purpose: return true if mail for the user is available
- X// Input: none
- X// Output: 1 for mail. 0 for no mail
- X// Author: Greg Shaw
- X// Created: 8/10/93
- X
- Xint User::mailavail(void)
- X{
- X struct stat fistat; // file status record
- X char tmpstr[255]; // tmpstr
- X time_t now = 0L; // current time
- X static time_t then = 0L; // previous check time
- X
- X time(&now);
- X if (abs(now - then) > mailchecktime()) // seconds elapsed?
- X {
- X sprintf(tmpstr,"%s/%s",mailspool(),login_name);
- X if (stat(tmpstr,&fistat) == 0 && S_ISREG(fistat.st_mode))
- X {
- X if (mail_check == 0) // just check size the first time
- X {
- X mail_check = fistat.st_mtime;// save modification time
- X if (mail_size = fistat.st_size, mail_size > 0)
- X return(1);
- X }
- X else // check date of last mail update
- X {
- X if (fistat.st_mtime != mail_check &&
- X fistat.st_size > mail_size) // new mail (mailbox bigger)
- X {
- X return(1);
- X }
- X mail_check = fistat.st_mtime;
- X mail_size = fistat.st_size;
- X }
- X }
- X }
- X return(0);
- X};
- X
- X// Function: save
- X// Purpose: save the current User to the User file
- X// Input: path - the path to the User file
- X// Output: returns non-zero on failure
- X// Author: Greg Shaw
- X// Created: 6/5/93
- X
- Xint User::save(char *name)
- X{
- X FILE *ufile;
- X FILE *ofile;
- X char finame[255]; // filename
- X char line[255]; // one line in file (255 max)
- X char bbspath[225]; // bbs path
- X char logname[10]; // user login name
- X char found; // user found?
- X char linenum; // used to look for appropriate line
- X char c; // input character
- X char *u;
- X unsigned char of; // offset into line
- X int x;
- X time_t now;
- X
- X last_login = login_time; // set to new login time
- X time(&now);
- X timeused += (now - login_time)/60; // update time used field.
- X if (name == NULL)
- X strcpy(logname,username()); // get user's log information
- X else
- X strcpy(logname,name);
- X if (strcpy(bbspath,getenv("BBSDIR")), bbspath == NULL)
- X {
- X sprintf(finame,"user.save: BBSDIR env var not set for %s",logname);
- X ap_log(finame);
- X return(-1);
- X }
- X strcpy(line,bbspath);
- X strcat(line,"/admin/nuserlog");
- X if (ofile = bopen(line,"w"), ofile == NULL)
- X {
- X sprintf(line,"user.save: Unable to open new userlog file: %s",logname);
- X ap_log(line);
- X return(-1);
- X }
- X chmod(line,S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH); // change permissions
- X strcpy(finame,bbspath);
- X strcat(finame,"/admin/userlog");
- X linenum = 0; // look for first line first
- X if (ufile = bopen(finame,"r"), ufile == NULL)
- X {
- X // create the bugger so that you can continue
- X ufile = bopen(finame,"w");
- X bclose(ufile);
- X if (ufile = bopen(finame,"r"), ufile == NULL)
- X { // still can't open the file! AARGH!
- X sprintf(line,"user.save: Unable to open userlog file.",logname);
- X ap_log(line);
- X return(-1);
- X }
- X }
- X else
- X {
- X found = 0;
- X while (!found && !feof(ufile))
- X {
- X // get first line
- X of = 0;
- X while (c = fgetc(ufile), c != '\r' && c != '\n' && !feof(ufile))
- X if (c != ']') // skip trailing left bracket
- X line[of++] = c;
- X line[of] = 0; // add null
- X if (!feof(ufile) && of > 1) // end of file, skip.
- X {
- X switch(linenum)
- X {
- X case 0: // first line
- X if (line[0] == '[' && line[1] == 'A') // got line 1?
- X {
- X x = sscanf(&line[2],"%s %s %s %s %s %s",login_name,
- X fname, lname, alias, state, city);
- X if (u = strchr(city,']'), u != NULL)
- X { // convert any left brackets to null
- X u++;
- X u[0] = 0;
- X }
- X if (strcmp(login_name,logname) == 0)
- X {
- X linenum++; // get next line
- X fprintf(ofile,"[A %s %s %s %s %s %s ]\n", login_name, fname, lname, alias, state, city);
- X }
- X else
- X fprintf(ofile,"%s]\n",line);
- X // [A login_name firstname lastname state city]
- X }
- X else
- X fprintf(ofile,"%s]\n",line);
- X break;
- X case 1: // second line
- X if (line[0] == '[' && line[1] == 'B') // got line 2?
- X {
- X fprintf(ofile,"[B %s %ld %d %d %d %s ]\n", uterm,
- X last_login, logins, downloads, uploads, card->colr);
- X // [B terminal_type last_logon #_logins downloads uploads]
- X linenum++; // get next line
- X }
- X else
- X fprintf(ofile,"%s]\n",line);
- X break;
- X case 2: // third line
- X if (line[0] == '[' && line[1] == 'C') // got line 3?
- X {
- X fprintf(ofile,"[C %d %d %d %d %s %d %d]\n",priv_msgs,
- X pub_msgs, credited, has_color, editor, lines, cols);
- X linenum++; // save next line
- X // [C private_msgs public_msgs credited_time has_color editor lines cols]
- X }
- X else
- X fprintf(ofile,"%s]\n",line);
- X break;
- X case 3: // fourth line
- X if (line[0] == '[' && line[1] == 'D') // got line 4?
- X {
- X fprintf(ofile,"[D %lx %d %d %d %ld %d ]\n",
- X flags, acl, timelimit, timeused,anniversary,kused);
- X // [D flags access_level timelimit timeused_last_call anniversary kused ]
- X linenum++; // save next line
- X }
- X else
- X fprintf(ofile,"%s]\n",line);
- X break;
- X }
- X if (linenum == 4) // got him.
- X {
- X found++;
- X }
- X }
- X }
- X // Ok, got the guy. copy the rest of the file
- X while (!feof(ufile))
- X {
- X c = fgetc(ufile);
- X if (!feof(ufile))
- X fputc(c,ofile);
- X }
- X }
- X // now rename the userfile to old userfile
- X bclose(ufile);
- X bclose(ofile);
- X strcpy(line,bbspath);
- X strcat(line,"/admin/userlog.old");
- X if (rename(finame, line) != 0)
- X {
- X sprintf(finame,"user.save: unable to rename userlog to userlog.old");
- X ap_log(finame);
- X return(-1);
- X }
- X strcpy(line,bbspath);
- X strcat(line,"/admin/nuserlog");
- X strcpy(finame,bbspath);
- X strcat(finame,"/admin/userlog");
- X if (rename(line, finame) != 0)
- X {
- X sprintf(finame,"user.save: unable to rename new userlog to userlog",logname);
- X ap_log(finame);
- X return(-1);
- X }
- X chmod(finame,S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH); // change permissions
- X return(0);
- X}
- X
- X// Function: sysop_edit
- X// Purpose: allow the sysop to edit a user
- X// Input: firsttime - is this the first logon by user?
- X// Output: (user questions)
- X// Author: Greg Shaw
- X// Created: 4/11/94
- X
- Xint User::sysop_edit(void)
- X{
- X char c;
- X char loop; // loop counter
- X char changed; // changed anything?
- X char tmpstr[255];
- X char str1[50], str2[50];
- X int selected; // which selected?
- X int tmp;
- X int x;
- X struct tm *tmdata; // time stuff
- X
- X loop = 1;
- X changed = 0;
- X while (loop)
- X {
- X clear(); // clear screen
- X cr();
- X cr();
- X cr();
- X sstrcr("Current User Statistics:");
- X cr();
- X sprintf(tmpstr,"Login: %s Full Name: %s %s from %s, %s",login_name,fname,lname,city,state);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"Alias: %s Downloads: %d Uploads %d Number of Logons: %d ",alias, downloads, uploads, logins);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"ACL: %d Flags(hex): 0x%8.8lx Timelimit: %d minutes",acl, flags, timelimit);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"Terminal Type: %s Card Color: %s Lines: %d Columns %d",uterm,card->colr,lines,cols);
- X sstrcr(tmpstr);
- X tmdata = localtime(&anniversary);
- X strftime(str1,49,"%c",tmdata);
- X tmdata = localtime(&last_login);
- X strftime(str2,49,"%c",tmdata);
- X sprintf(tmpstr,"First Logon: %s",str1);
- X sstrcr(tmpstr);
- X sprintf(tmpstr,"Last Logon: %s for %d minutes",str2,timeused);
- X sstrcr(tmpstr);
- X sstr("Is this correct? ");
- X if (yesno())
- X {
- X if (changed)
- X {
- X sstrcr("Saving user information...");
- X save(login_name);
- X }
- X return(0);
- X }
- X clear();
- X sstrcr("You may edit the following: ");
- X sstrcr("1. Login Name 2. First Name");
- X sstrcr("3. Last Name 4. City");
- X sstrcr("5. State 6. Alias");
- X sstrcr("7. Downloads 8. Uploads");
- X sstrcr("9. Access Level 10. Flags");
- X sstrcr("11. Timelimit 12. Terminal Type");
- X sstrcr("13. Card Color 14. Lines");
- X sstrcr("15. Columns");
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Edit which? ");
- X gstr(str1,3);
- X selected = 0;
- X if (sscanf(str1,"%d",&selected) != 1 || (selected < 1 || selected > 15))
- X continue;
- X switch(selected)
- X {
- X case 1: // get login name
- X sstrcr("Login name change hasn't been done yet.");
- X sstrcr("It would require /etc/passwd modifications.");
- X sstrcr("Which would be a security hole.");
- X waitcr();
- X break; // not done at this time (requires
- X // modification of passwd file)
- X case 2: // get first name
- X sprintf(tmpstr,"Current first name: %s",fname);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change first name to? ");
- X gstr(str1,20);
- X if (sscanf(str1,"%s",str2) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X strcpy(fname,str2);
- X changed++;
- X break;
- X case 3: // get last name
- X sprintf(tmpstr,"Current last name: %s",lname);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change last name to? ");
- X gstr(str1,20);
- X if (sscanf(str1,"%s",str2) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X strcpy(lname,str2);
- X changed++;
- X break;
- X case 4: // get city
- X sprintf(tmpstr,"Current city: %s",city);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change city to? ");
- X gstr(str1,20);
- X if (sscanf(str1,"%s",str2) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X strcpy(city,str2);
- X changed++;
- X break;
- X case 5: // get state
- X sprintf(tmpstr,"Current state: %s",state);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change state to? ");
- X gstr(str1,14);
- X if (sscanf(str1,"%s",str2) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X strcpy(state,str2);
- X changed++;
- X break;
- X case 6: // get alias
- X sprintf(tmpstr,"Current alias: %s",alias);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change alias to? ");
- X gstr(str1,20);
- X if (sscanf(str1,"%s",str2) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X strcpy(alias,str2);
- X changed++;
- X break;
- X case 7: // get downloads
- X sprintf(tmpstr,"Current downloads: %d",downloads);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change downloads to? ");
- X gstr(str1,4);
- X if (sscanf(str1,"%d",&tmp) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X downloads = tmp;
- X changed++;
- X break;
- X case 8: // get uploads
- X sprintf(tmpstr,"Current downloads: %d",downloads);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change downloads to? ");
- X gstr(str1,4);
- X if (sscanf(str1,"%d",&tmp) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X downloads = tmp;
- X changed++;
- X break;
- X case 9: // get access level
- X sprintf(tmpstr,"Current access level: %d",acl);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change access level to? ");
- X gstr(str1,5);
- X if (sscanf(str1,"%d",&tmp) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X acl = tmp;
- X changed++;
- X break;
- X case 10: // get flags
- X sstrcr("Current flags:");
- X for (x=0; x<32; x++)
- X {
- X if (x%8 == 0 && x != 0)
- X cr();
- X sprintf(tmpstr,"%.2d:%d ",x,flags&1<<x?1:0);
- X sstr(tmpstr);
- X }
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Set or Clear a flag? ");
- X gstr(str1,2);
- X for (c=0; c<strlen(str1); c++)
- X str1[c] = tolower(str1[c]);
- X if (strchr(str1,'s') != NULL)
- X {
- X sstr("Set which flag? (0-31) ");
- X gstr(str1,3);
- X if (sscanf(str1,"%d",&tmp) != 1 || (tmp < 0 || tmp > 31))
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X flags |= 1<<tmp;
- X }
- X else if (strchr(str1,'c') != NULL)
- X {
- X sstr("Clear which flag? (0-31) ");
- X gstr(str1,3);
- X if (sscanf(str1,"%d",&tmp) != 1 || (tmp < 0 || tmp > 31))
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X flags &= ~(1<<tmp);
- X }
- X else
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X changed++;
- X break;
- X case 11: // get timelimit
- X sprintf(tmpstr,"Current timelimit: %d",timelimit);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change timelimit to? ");
- X gstr(str1,5);
- X if (sscanf(str1,"%d",&tmp) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X timelimit = tmp;
- X changed++;
- X break;
- X case 12: // get terminal types
- X sprintf(tmpstr,"Current terminal type: %s",uterm);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change terminal type to? ");
- X gstr(str1,20);
- X if (sscanf(str1,"%s",str2) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X strcpy(uterm,str2);
- X changed++;
- X break;
- X case 13: // get card color
- X sprintf(tmpstr,"Current card color: %s",card->colr);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change card color to? ");
- X gstr(str1,10);
- X if (sscanf(str1,"%s",str2) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X for (c = 0; c < strlen(str2); c++) // convert to lower case
- X str2[c] = tolower(str2[c]);
- X if (!strcmp(str2,"red"))
- X card_color = 0;
- X else if (!strcmp(str2,"blue"))
- X card_color = 1;
- X else if (!strcmp(str2,"green"))
- X card_color = 2;
- X else if (!strcmp(str2,"white"))
- X card_color = 3;
- X else if (!strcmp(str2,"grey"))
- X card_color = 4;
- X else if (!strcmp(str2,"pink"))
- X card_color = 5;
- X else if (!strcmp(str2,"yellow"))
- X card_color = 6;
- X else if (!strcmp(str2,"black"))
- X card_color = 7;
- X else
- X {
- X sstrcr("Unable to determine card color.");
- X sstrcr("Card color unchanged.");
- X waitcr();
- X continue;
- X }
- X check_card();
- X changed++;
- X break;
- X case 14: // get lines
- X sprintf(tmpstr,"Current lines: %d",lines);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change lines to? ");
- X gstr(str1,4);
- X if (sscanf(str1,"%d",&tmp) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X lines = tmp;
- X changed++;
- X break;
- X case 15: // get columns
- X sprintf(tmpstr,"Current columns : %d",cols);
- X sstrcr(tmpstr);
- X cr();
- X sstrcr("Press return to exit.");
- X cr();
- X sstr("Change columns to? ");
- X gstr(str1,4);
- X if (sscanf(str1,"%d",&tmp) != 1)
- X {
- X sstrcr("Not changed.");
- X waitcr();
- X continue;
- X }
- X cols = tmp;
- X changed++;
- X break;
- X }
- X }
- X return(0);
- X};
- X// Function: constructor
- X// Purpose: initialize all object variables
- X// Input: none
- X// Output: (object is initialized)
- X// Author: Greg Shaw
- X// Created: 6/1/93
- X
- XUser::User()
- X{
- X card = NULL;
- X if (card_color = def_card(), card_color == -1)
- X ap_log("Unable to get default card color.");
- X if (card_color != -1 && (card = cardinfo(card_color), card == NULL))
- X ap_log("Unable to get card information.");
- X fname[0] = 0;
- X lname[0] = 0;
- X alias[0] = 0;
- X login_name[0] = 0;
- X editor[0] = 0;
- X city[0] = 0;
- X state[0] = 0;
- X uterm[0] = 0;
- X time(&last_login);
- X time(&login_time);
- X time(&anniversary);
- X mail_check = 0;
- X logins = 1;
- X lines = 24;
- X cols = 80;
- X downloads = 0;
- X uploads = 0;
- X priv_msgs = 0;
- X pub_msgs = 0;
- X credited = 0;
- X flags = 0;
- X tmpflags = 0;
- X acl = card->acl;
- X tmpacl = acl;
- X timelimit = card->tl;
- X tmptl = timelimit;
- X credited = 0;
- X timeused = 0;
- X kused = 0;
- X has_color = 0;
- X}
- X
- X// Function: destructor
- X// Purpose: clean up the object
- X// Input: none
- X// Output: none ( null destructor at this point )
- X// Author: Greg Shaw
- X// Created: 6/1/93
- X
- XUser::~User()
- X{
- X}
- X#endif // _USER_C_
- END_OF_FILE
- if test 45033 -ne `wc -c <'rocat-0.75/src/user.C'`; then
- echo shar: \"'rocat-0.75/src/user.C'\" unpacked with wrong size!
- fi
- chmod +x 'rocat-0.75/src/user.C'
- # end of 'rocat-0.75/src/user.C'
- fi
- echo shar: End of archive 4 \(of 9\).
- cp /dev/null ark4isdone
- MISSING=""
- for I in 1 2 3 4 5 6 7 8 9 ; do
- if test ! -f ark${I}isdone ; then
- MISSING="${MISSING} ${I}"
- fi
- done
- if test "${MISSING}" = "" ; then
- echo You have unpacked all 9 archives.
- rm -f ark[1-9]isdone ark[1-9][0-9]isdone
- else
- echo You still must unpack the following archives:
- echo " " ${MISSING}
- fi
- exit 0
- exit 0 # Just in case...
-