/*

 * Copyright Daniel Industries.
 *
 * Created by: Vipin Malik (vipin.malik@daniel.com)
 *
 * This code is released under the GPL version 2. See the file COPYING
 * for more details.
 *
 * Software distributed under the Licence is distributed on an "AS IS"
 * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied.
 * See the Licence for the specific language governing rights and
 * limitations under the Licence.

  This program opens files in progression (file00001, file00002 etc),
  upto MAX_NUM_FILES and checks their CRC. If a file is not found or the
  CRC does not match it stops it's operation.

  Everything is logged in a logfile called './logfile'.

  If everything is ok this program sends a signal, via com1, to the remote
  power control box to power cycle this computer.

  This program then proceeds to create new files file0....file<MAX_NUM_FILES>
  in a endless loop and checksum each before closing them.

  STRUCTURE OF THE FILES:
  The fist int is the size of the file in bytes.
  The last 2 bytes are the CRC for the entire file.
  There is random data in between.

  The files are opened in the current dir.

  $Id: checkfs.c,v 1.8 2005/11/07 11:15:17 gleixner Exp $
  $Log: checkfs.c,v $
  Revision 1.8  2005/11/07 11:15:17  gleixner
  [MTD / JFFS2] Clean up trailing white spaces

  Revision 1.7  2001/06/21 23:04:17  dwmw2
  Initial import to MTD CVS

  Revision 1.6  2001/06/08 22:26:05  vipin
  Split the modbus comm part of the program (that sends the ok to pwr me down
  message) into another file "comm.c"

  Revision 1.5  2001/06/08 21:29:56  vipin
  fixed small issue with write() checking for < 0 instead of < (bytes to be written).
  Now it does the latter (as it should).

  Revision 1.4  2001/05/11 22:29:40  vipin
  Added a test to check and err out if the first int in file (which tells us
  how many bytes there are in the file) is zero. This will prevent a corrupt
  file with zero's in it from passing the crc test.

  Revision 1.3  2001/05/11 21:33:54  vipin
  Changed to use write() rather than fwrite() when creating new file. Additionally,
  and more important, it now does a single write() for the entire data. This will
  enable us to use this program to test for power fail *data* reliability when
  writing over an existing file, specially on powr fail "safe" file systems as
  jffs/jffs2. Also added a new cmdline parameter "-e" that specifies the max # of
  errors that can be tolerated. This should be set to ZERO to test for the above,
  as old data should be reliabily maintained if the newer write never "took" before
  power failed. If the write did succeed, then the newer data will have its own
  CRC in place when it gets checked => hence no error. In theory at least!


  Revision 1.2  2001/05/11 19:27:33  vipin
  Added cmd line args to change serial port, and specify max size of
  random files created. Some cleanup. Added -Wall to Makefile.

  Revision 1.1  2001/05/11 16:06:28  vipin
  Importing checkfs (the power fail test program) into CVS. This was
  originally done for NEWS. NEWS had a lot of version, this is
  based off the last one done for NEWS. The "makefiles" program
  is run once initially to create the files in the current dir.
  "checkfs" is then run on every powerup to check consistancy
  of the files. See checkfs.c for more details.


*/
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <termios.h>
#include <unistd.h>
#include <errno.h>
#include <unistd.h>
#include <string.h>
#include <time.h>
#include "common.h"



extern int do_pwr_dn(int fd, int cycleCnt);

#define CMDLINE_PORT "-p"
#define CMDLINE_MAXFILEBYTES "-s"
#define CMDLINE_MAXERROR "-e"
#define CMDLINE_HELPSHORT "-?"
#define CMDLINE_HELPLONG "--help"


int CycleCount;

char SerialDevice[255] = "/dev/ttyS0"; /* default, can be changed
                                        through cmd line. */

#define MAX_INTS_ALLOW 100000 /* max # of int's in the file written.
                                 Statis limit to size struct. */
float FileSizeMax = 1024.0; /*= (file size in bytes), MUST be float*/

int MaxErrAllowed = 1; /* default, can ge changed thru cmd line*/


/* Needed for CRC generation/checking */
static const unsigned short crc_ccitt_table[] = {
    0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
    0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
    0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
    0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
    0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
    0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
    0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
    0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
    0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
    0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
    0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
    0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
    0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
    0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
    0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
    0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
    0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
    0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
    0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
    0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
    0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
    0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
    0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
    0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
    0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
    0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
    0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
    0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
    0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
    0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
    0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
    0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78
};


/*
  Set's up the Linux serial port. Must be passed string to device to
  open. Parameters are fixed to 9600,e,1

  [A possible enhancement to this program would be to pass these
  parameters via the command line.]

  Returns file descriptor to open port. Use this fd to write to port
  and close it later, when done.
*/
int setupSerial (const char *dev) {
    int i, fd;
    struct termios tios;

    fd = open(dev,O_RDWR | O_NDELAY );
    if (fd < 0) {
        fprintf(stderr, "%s: %s\n", dev, sys_errlist[errno]);
        exit(1);
    }
    if (tcgetattr(fd, &tios) < 0) {
        fprintf(stderr,"Could not get terminal attributes: %s",sys_errlist[errno]);
        exit(1);
    }

    tios.c_cflag =
        CS7 |
        CREAD |			// Enable Receiver
        HUPCL |			// Hangup after close
        CLOCAL |                // Ignore modem control lines
        PARENB;			// Enable parity (even by default)



    tios.c_iflag      = IGNBRK; // Ignore break
    tios.c_oflag      = 0;
    tios.c_lflag      = 0;
    for(i = 0; i < NCCS; i++) {
        tios.c_cc[i] = '\0';           // no special characters
    }
    tios.c_cc[VMIN] = 1;
    tios.c_cc[VTIME] = 0;

    cfsetospeed (&tios, B9600);
    cfsetispeed (&tios, B9600);

    if (tcsetattr(fd, TCSAFLUSH, &tios) < 0) {
        fprintf(stderr,"Could not set attributes: ,%s",sys_errlist[errno]);
        exit(1);
    }
    return fd;
}





//A portion of this code was taken from the AX.25 HDLC packet driver
//in LINUX. Once I test and have a better understanding of what
//it is doing, it will be better commented.

//For now one can speculate that the CRC routine always expects the
//CRC to calculate out to 0xf0b8 (the hardcoded value at the end)
//and returns TRUE if it is and FALSE if it doesn't.
//Why don't people document better!!!!
int check_crc_ccitt(char *filename)
{
    FILE *fp;
    FILE *logfp;
    unsigned short crc = 0xffff;
    int len;
    char dataByte;
    int retry;
    char done;

    fp =   fopen(filename,"rb");
    if(!fp){
        logfp = fopen("logfile","a"); /*open for appending only.*/
        fprintf(logfp, "Verify checksum:Error! Cannot open filename passed for verify checksum: %s\n",filename);
        fclose(logfp);
        return FALSE;
    }


    /*the first int contains an int that is the length of the file in long.*/
    if(fread(&len, sizeof(int), 1, fp) != 1){
        logfp = fopen("logfile","a"); /*open for appending only.*/
        fprintf(logfp, "verify checksum:Error reading from file: %s\n", filename);
        fclose(fp);
        fclose(logfp);
        return FALSE;
    }

    /* printf("Checking %i bytes for CRC in \"%s\".\n", len, filename); */

    /* Make sure that we did not read 0 as the number of bytes in file. This
       check prevents a corrupt file with zero's in it from passing the
       CRC test. A good file will always have some data in it. */
    if(len == 0)
    {

        logfp = fopen("logfile","a"); /*open for appending only.*/
        fprintf(logfp, "verify checksum: first int claims there are 0 data in file. Error!: %s\n", filename);
        fclose(fp);
        fclose(logfp);
        return FALSE;
    }


    rewind(fp);
    len+=2; /*the file has two extra bytes at the end, it's checksum. Those
              two MUST also be included in the checksum calculation.
            */

    for (;len>0;len--){
        retry=5; /*retry 5 times*/
        done = FALSE;
        while(!done){
            if(fread(&dataByte, sizeof(char), 1, fp) != 1){
                retry--;
            }else{
                done = TRUE;
            }
            if(retry == 0){
                done = TRUE;
            }
        }
        if(!retry){
            logfp = fopen("logfile","a"); /*open for appending only.*/
            fprintf(logfp, "Unexpected end of file: %s\n", filename);
            fprintf(logfp, "...bytes left to be read %i.\n",len);
            fclose(logfp);
            fclose(fp);
            return FALSE;
        }
        crc = (crc >> 8) ^ crc_ccitt_table[(crc ^ dataByte) & 0xff];
    }
    fclose(fp);
    if( (crc & 0xffff) != 0xf0b8){
        /*printf("The CRC of read file:%x\n", crc); */
        return FALSE;
    }
    return TRUE;
}/*end check_crc_ccitt() */



/*
  Sends "OK to power me down" message to the remote
  power cycling box, via the serial port.
  Also updates the num power cycle count in a local
  file.
  This file "./cycleCnt" must be present. This is
  initially (and once) created by the separate "makefiles.c"
  program.
*/
void send_pwrdn_ok(void){

    int fd;
    FILE *cyclefp;
    int cycle_fd;

    cyclefp =   fopen("cycleCnt","rb");
    if(!cyclefp){
        printf("expecting file \"cycleCnt\". Cannot continue.\n");
        exit(1);
    }
    if(fread(&CycleCount, sizeof(CycleCount),1,cyclefp) != 1){
        fprintf(stderr, "Error! Unexpected end of file cycleCnt.\n");
        exit(1);
    }
    fclose(cyclefp);

    CycleCount++;

    /*now write this puppy back*/
    cyclefp  = fopen("cycleCnt","wb");
    cycle_fd = fileno(cyclefp);
    if(!cyclefp){
        fprintf(stderr, "Error! cannot open file for write:\"cycleCnt\". Cannot continue.\n");
        exit(1);
    }
    if(fwrite(&CycleCount, sizeof(CycleCount), 1,cyclefp) !=1){
        fprintf(stderr, "Error writing to file cycleCnt. Cannot continue.\n");
        exit(1);
    }
    if(fdatasync(cycle_fd)){
        fprintf(stderr, "Error! cannot sync file buffer with disk.\n");
        exit(1);
    }

    fclose(cyclefp);
    (void)sync();

    printf("\n\n Sending Power down command to the remote box.\n");
    fd = setupSerial(SerialDevice);

    if(do_pwr_dn(fd, CycleCount) < 0)
    {
        fprintf(stderr, "Error sending power down command.\n");
        exit(1);
    }

    close(fd);
}//end send_pwrnd_ok()




/*
  Appends 16bit CRC at the end of numBytes long buffer.
  Make sure buf, extends at least 2 bytes beyond.
 */
void appendChecksum(char *buf, int numBytes){

    unsigned short crc = 0xffff;
    int index = 0;

    /* printf("Added CRC (2 bytes) to %i bytes.\n", numBytes); */

    for (; numBytes > 0; numBytes--){

        crc = (crc >> 8) ^ crc_ccitt_table[(crc ^ buf[index++]) & 0xff];
    }
    crc ^= 0xffff;
    /*printf("The CRC: %x\n\n", crc);*/

    buf[index++] = crc;
    buf[index++] = crc >> 8;



}/*end checksum()*/





/*
  This guy make a new "random data file" with the filename
  passed to it. This file is checksummed with the checksum
  stored at the end. The first "int" in the file is the
  number of int's in it (this is needed to know how much
  data to read and checksum later).
*/
void make_new_file(char *filename){


    int dfd; /* data file descriptor */
    int rand_data;
    int data_size;
    int temp_size;
    int dataIndex = 0;
    int err;


    struct {
        int sizeInBytes; /* must be int */
        int dataInt[MAX_INTS_ALLOW+1]; /* how many int's can we write? */
    }__attribute((packed)) dataBuf;


    fprintf(stderr, "Creating File:%s. ", filename);

    if((dfd = open(filename, O_RDWR | O_CREAT | O_SYNC)) <= 0)
    {
        printf("Error! Cannot open file: %s\n",filename);
        perror("Error");
        exit(1);
    }

    /*now write a bunch of random binary data to the file*/
    /*first figure out how much data to write. That is random also.*/

    /*file should not be less than 5 ints long. (so that we have decent length files,
      that's all)*/
    while(
	((data_size = (int)(1+(int)((FileSizeMax/sizeof(int))*rand()/(RAND_MAX+1.0)))) < 5)
    );

    /* printf("Writing %i ints to the file.\n", data_size); */

    temp_size = data_size * sizeof(int);

    /* Make sure that all data is written in one go! This is important to
       check for reliability of file systems like JFFS/JFFS that purport to
       have "reliable" writes during powre fail.
     */

    dataBuf.sizeInBytes = temp_size;

    data_size--; /*one alrady written*/
    dataIndex = 0;

    while(data_size--){
        rand_data =  (int)(1 + (int)(10000.0*rand()/(RAND_MAX+1.0)));

        dataBuf.dataInt[dataIndex++] = rand_data;

    }

    /*now calculate the file checksum and append it to the end*/
    appendChecksum((char *)&dataBuf, dataBuf.sizeInBytes);

    /* Don't forget to increase the size of data written by the 2 chars of CRC at end.
     These 2 bytes are NOT included in the sizeInBytes field. */
    if((err = write(dfd, (void *)&dataBuf, dataBuf.sizeInBytes + sizeof(short))) <
       (dataBuf.sizeInBytes + sizeof(short))
    )
    {
        printf("Error writing data buffer to file. Written %i bytes rather than %i bytes.",
               err, dataBuf.sizeInBytes);
        perror("Error");
        exit(1);
    }

    /* Now that the data is (hopefully) safely written. I can truncate the file to the new
       length so that I can reclaim any unused space, if the older file was larger.
     */
    if(ftruncate(dfd, dataBuf.sizeInBytes + sizeof(short)) < 0)
    {
        perror("Error: Unable to truncate file.");
        exit(1);
    }


    close(dfd);


}//end make_new_file()



/*
  Show's help on stdout
 */
void printHelp(char **argv)
{
    printf("Usage:%s <options, defined below>\n", argv[0]);
    printf("%s </dev/ttyS0,1,2...>: Set com port to send ok to pwr dn msg on\n",
           CMDLINE_PORT);
    printf("%s <n>: Set Max size in bytes of each file to be created.\n",
           CMDLINE_MAXFILEBYTES);
    printf("%s <n>: Set Max errors allowed when checking all files for CRC on start.\n",
           CMDLINE_MAXERROR);
    printf("%s or %s: This Help screen.\n", CMDLINE_HELPSHORT,
           CMDLINE_HELPLONG);

}/* end printHelp()*/



void processCmdLine(int argc, char **argv)
{

    int cnt;

    /* skip past name of this program, process rest */
    for(cnt = 1; cnt < argc; cnt++)
    {
        if(strcmp(argv[cnt], CMDLINE_PORT) == 0)
        {
            strncpy(SerialDevice, argv[++cnt], sizeof(SerialDevice));
            continue;
        }else
            if(strcmp(argv[cnt], CMDLINE_MAXFILEBYTES) == 0)
            {
                FileSizeMax = (float)atoi(argv[++cnt]);
                if(FileSizeMax > (MAX_INTS_ALLOW*sizeof(int)))
                {
                    printf("Max file size allowd is %i.\n",
                           MAX_INTS_ALLOW*sizeof(int));
                    exit(0);
                }

                continue;
            }else
                if(strcmp(argv[cnt], CMDLINE_HELPSHORT) == 0)
                {
                    printHelp(argv);
                    exit(0);

                }else
                    if(strcmp(argv[cnt], CMDLINE_HELPLONG) == 0)
                    {
                        printHelp(argv);
                        exit(0);
                    }else

                        if(strcmp(argv[cnt], CMDLINE_MAXERROR) == 0)
                        {
                            MaxErrAllowed = atoi(argv[++cnt]);
                        }
                        else
                        {
                            printf("Unknown cmd line option:%s\n", argv[cnt]);
                            printHelp(argv);
                            exit(0);

                        }
    }


}/* end processCmdLine() */





int main(int argc, char **argv){

    FILE *logfp;
    int log_fd;
    char filename[30];
    short filenameCounter = 0;
    unsigned short counter;
    unsigned short numberFiles;
    char error = FALSE;
    short errorCnt = 0;
    time_t timep;
    char * time_string;
    unsigned int seed;


    numberFiles = MAX_NUM_FILES;

    if(argc >= 1)
    {
        processCmdLine(argc, argv);
    }


    /*
      First open MAX_NUM_FILES and make sure that the checksum is ok.
      Also make an intry into the logfile.
    */
    /* timestamp! */
    time(&timep);
    time_string = (char *)ctime((time_t *)&timep);

    /*start a new check, make a log entry and continue*/
    logfp = fopen("logfile","a"); /*open for appending only.*/
    log_fd = fileno(logfp);
    fprintf(logfp,"%s", time_string);
    fprintf(logfp,"Starting new check.\n");
    if(fdatasync(log_fd) == -1){
        fprintf(stderr,"Error! Cannot sync file data with disk.\n");
        exit(1);
    }

    fclose(logfp);
    (void)sync();

    /*
      Now check all random data files in this dir.
    */
    for(counter=0;counter<MAX_NUM_FILES;counter++){

        fprintf(stderr, "%i.", counter);

        /*create the filename in sequence. The number of files
          to check and the algorithm to create the filename is
          fixed and known in advance.*/
        sprintf(filename,"file%i",filenameCounter++);

        if(!check_crc_ccitt(filename)){
            /*oops, checksum does not match. Make an entry into the log file
              and decide if we can continue or not.*/
            fprintf(stderr, "crcError:%s ", filename);
            logfp = fopen("logfile","a"); /*open for appending only.*/
            log_fd = fileno(logfp);
            fprintf(logfp,"CRC error in file: %s\n", filename);
            if(fdatasync(log_fd) == -1){
                fprintf(stderr,"Error! Cannot sync file data with disk.\n");
                exit(1);
            }
            fclose(logfp);
            (void)sync();

            error = TRUE;
            errorCnt++;

            if(errorCnt > MaxErrAllowed){
                logfp = fopen("logfile","a"); /*open for appending only.*/
                log_fd = fileno(logfp);
                fprintf(logfp,"\nMax Error count exceed. Stopping!\n");
                if(fdatasync(log_fd) == -1){
                    fprintf(stderr,"Error! Cannot sync file data with disk.\n");
                    exit(1);
                }
                fclose(logfp);
                (void)sync();

                fprintf(stderr, "Too many errors. See \"logfile\".\n");
                exit(1);
            }/* if too many errors */

            /*we have decided to continue, however first repair this file
              so that we do not cumulate errors across power cycles.*/
            make_new_file(filename);
        }
    }//for

    /*all files checked, make a log entry and continue*/
    logfp = fopen("logfile","a"); /*open for appending only.*/
    log_fd = fileno(logfp);
    fprintf(logfp,"All files checked. Total errors found: %i\n\n", errorCnt);
    if(fdatasync(log_fd)){
        fprintf(stderr, "Error! cannot sync file buffer with disk.\n");
        exit(1);
    }

    fclose(logfp);
    (void)sync();

    /*now send a message to the remote power box and have it start a random
      pwer down timer after which power will be killed to this unit.
    */
    send_pwrdn_ok();

    /*now go into a forever loop of writing to files and CRC'ing them on
      a continious basis.*/

    /*start from a random file #*/
    /*seed rand based on the current time*/
    seed = (unsigned int)time(NULL);
    srand(seed);

    filenameCounter=(int)(1+(int)((float)(MAX_NUM_FILES-1)*rand()/(RAND_MAX+1.0)));

    while(1){

        for(;filenameCounter<MAX_NUM_FILES;filenameCounter++){

            /*create the filename in sequence*/
            sprintf(filename,"file%i",filenameCounter);
            make_new_file(filename);
        }
        filenameCounter = 0;
    }

    exit(0); /* though we will never reach here, but keeps the compiler happy*/
}/*end main()*/
