CFM RamDisk 0.1

Maniace 09.06.04 13:54

Pienehkö purkkapallo, joka yhdistää parametreina annetut tiedostot yhdeksi tiedostoksi(tehty ennenkö hokasin, että GRUBilla voi ladata ZIPejä...)

 Tekstiversio  Arvo: 0 (0 ääntä)  Äänestä: +  -
// Aikamoista purukumia, mutta pääasia, että se toimii.
// Ulosteena tulleen tiedoston voi ladata vaikka GRUBin moduulina bootissa.
// Mikäli ihmisillä on kiinnostusta, voin jossain vaiheessa myös
// laittaa tänne koodin tiedoston käsittelyyn omasta järjestelmästä käsin.
// Ikävä kyllä kommenteja ei juurikaan ole, kun en tiennyt, että koodin
// joskus laitan jakoon.
// Taisipa täällä jossakin olla ikävää fgetc:n käyttöäkin, hokasin sitten jossain
// vaiheessa koodailua, että semmonenkin funktio on kun fseek.
// Bugikorjauksen voi jättää lukijalle harjoitustyöksi, ainakaan harjoitus
// ei lopu kesken.


#include <stdio.h>

#define MAX_FILES       10
#define MAX_NAMELEN     32
#define SIGNATURE       "CFM_RDSK"

int main(int argc, char **argv) {
   printf("CFM Ramdisk 1.0\n");
   FILE *datafile, *infile;
   unsigned long argpos, tablepos, loop, loop2, cont = 0;
   char filename[MAX_FILES][MAX_NAMELEN], signature[32] = { 0 }, tmpchr = 0;
   unsigned long filesize[MAX_FILES], offset = 0, tmp = 0;
   unsigned long fileoffset[MAX_FILES];

   if (argc < 2) {
      printf("Creates CFM ramdisk.\nUsage: ramdisk filename [-i] [-e] [-c file1 file2 ...]\n");
      printf("filename : File to use for operation\n");
      printf("-i       : Print ramdisk information\n");
      printf("-c       : Create ramdisk from files\n");
      printf("-e       : Extract all\n");
      return 1;
   }

   if (!strcmp(argv[2], "-i") || !strcmp(argv[2], "-e")) {
      datafile = fopen(argv[1], "rb");

      if (datafile == NULL) {
         printf("Couldn't open input file.\n");
         return 1;
      }

      fread(signature, sizeof(unsigned char), strlen(SIGNATURE), datafile);

      if (strcmp(signature, SIGNATURE)) {                        // Get Signature
         printf("Not valid or corrupted.\n");
         fclose(datafile);
         return 1;
      }

      // Main header: Signature(default 8 bytes), ramdisk size(4 bytes), how many files(4 bytes),
      // File offsets(4 bytes * file count)

      // Subheaders: Name length in bytes(4 bytes), name(name length in bytes bytes :), data

      fread(&tmp, sizeof(unsigned long), 1, datafile);           // Get ramdisk size
      printf("Ramdisk size %i bytes.\n\r", tmp);

      fread(&tmp, sizeof(unsigned long), 1, datafile);           // Get file count
      printf("Total %i files in %s:\n", tmp, argv[1]);

      for (loop = 0; loop < tmp; loop++) {                       // Get file offsets
         fread(&fileoffset[loop], sizeof(unsigned long), 1, datafile);
      }

      fileoffset[loop] = filelength(fileno(datafile));

      for (loop = 0; loop < tmp; loop++) {
         fread(&filesize[loop], sizeof(unsigned long), 1, datafile);    // Now used in name sizing, get file name size
         fread(&filename[loop], sizeof(unsigned char), filesize[loop], datafile); // Get file name
         filename[loop][filesize[loop]] = 0;

         printf("Name: %s Bytes: %i Offset: %i\n", filename[loop], fileoffset[loop + 1] - fileoffset[loop] - sizeof(unsigned long) - filesize[loop], fileoffset[loop]);

         if (!strcmp(argv[2], "-e")) {
            infile = fopen(filename[loop], "rb");

            if (infile) {
               printf("File %s already exists. Overwrite? (Y/N)\n", filename[loop]);
               tmpchr = getch();

               if (tmpchr != 'y' || tmpchr != 'Y') {
                  fclose(infile);

                  fseek(datafile, fileoffset[loop + 1] - fileoffset[loop] - sizeof(unsigned long) - filesize[loop], SEEK_CUR);

                  continue;
               }
            }

            infile = fopen(filename[loop], "wb");

            if (infile == NULL) {
               printf("Couldn't open %s for write, passing...\n", filename[loop]);
               for (loop2 = 0; loop2 < fileoffset[loop + 1] - fileoffset[loop] - sizeof(unsigned long) - filesize[loop]; loop2++)
                  fgetc(datafile);

               continue;
            }

            for (loop2 = 0; loop2 < fileoffset[loop + 1] - fileoffset[loop] - sizeof(unsigned long) - filesize[loop]; loop2++)
               fputc(fgetc(datafile), infile);

            fclose(infile);
            printf("Extracted.\n");
         } else {
            fseek(datafile, fileoffset[loop + 1] - fileoffset[loop] - sizeof(unsigned long) - filesize[loop], SEEK_CUR);
         }
      }

      fclose(datafile);
      return 0;
   }

   if (!strcmp(argv[2], "-c")) {
      datafile = fopen(argv[1], "wb");

      if (datafile == NULL) {
         printf("Couldn't open output file.\n");
         return 1;
      }

      printf("Creating control tables...\n");

      tmp = 0;
      for (argpos = 3, tablepos = 0; argpos < argc; argpos++, tablepos++) {
         cont = 0;
         infile = fopen(argv[argpos], "rb");

         if (infile == NULL) {
            printf("Couldn't open file %s, passing...\n", argv[argpos]);
            tablepos--;
            cont = 1;
         }

         for (loop2 = 0; loop2 < argpos; loop2++)
            if (!strcmp(filename[loop2], argv[argpos])) {
               printf("File %s already in, passing...\n", argv[argpos]);
               tablepos--;
               fclose(infile);
               cont = 1;
            }

         if (cont) continue;

         sprintf(filename[tablepos], "%s", argv[argpos]);
         filesize[tablepos] = filelength(fileno(infile));
         fclose(infile);
         tmp += filesize[tablepos] + sizeof(unsigned long) + strlen(argv[argpos]);
      }

      printf("Writing main header...\n");
      tmp += strlen(SIGNATURE) + sizeof(unsigned long) * (2 + tablepos);
      fwrite(SIGNATURE, sizeof(unsigned char), strlen(SIGNATURE), datafile);      // Signature
      fwrite(&tmp, sizeof(unsigned long), 1, datafile);                            // Ramdisk size
      fwrite(&tablepos, sizeof(unsigned long), 1, datafile);                      // How many files

      offset = strlen(SIGNATURE) + sizeof(unsigned long);
      for (loop = 0; loop < tablepos; loop++) {
         fwrite(&offset, sizeof(unsigned long), 1, datafile);
         fileoffset[loop] = offset;
         offset += sizeof(unsigned long) + strlen(filename[loop]) + filesize[loop];
                // size of subheaderinfo + name length            + file size
      }

      printf("Writing subheaders and files...\n");
      for (loop = 0; loop < tablepos; loop++) {
         printf("Name: %s Bytes: %i Offset: %i\n", filename[loop], filesize[loop], fileoffset[loop]);

         infile = fopen(filename[loop], "rb");

         if (infile == NULL) {
            printf("Couldn't open %s at second time...\n", filename[loop]);
            fclose(datafile);
            return 1;
         }

         tmp = strlen(filename[loop]);
         fwrite(&tmp, sizeof(unsigned long), 1, datafile);        // Name length
         fwrite(filename[loop], sizeof(unsigned char), strlen(filename[loop]), datafile); // Name

         for (loop2 = 0; loop2 < filesize[loop]; loop2++) {
            tmpchr = fgetc(infile);
            fwrite(&tmpchr, sizeof(unsigned char), 1, datafile);
         }

         fclose(infile);
      }

      fclose(datafile);
   }

   printf("%i files total. Ramdisk size %i bytes\n", tablepos, offset + sizeof(unsigned long) * (tablepos + 1));

   return 0;
}

// PS. Tällaista koodia tulee kun nyypiö ottaa itselleen liian ison projektin.
 

Maniace 14:04 9.6.04 
Niin juu, Wintöötin alla kääntyy GCC:llä, esim. gcc -o ramdisk.exe ramdisk.c.