0

I am trying to read and display the disk geometry of a floppy in C. I was able to manage the first few entries (as far as I know of they're correct at least) such as:

  • Bytes per Sector
  • Sectors per Cluster
  • Reserved Sectors for the Boot Record
  • Number of FATS

My problem is I'm stuck at trying to figure out bit shifting for the rest of the geometry, which is what I was told to do in order to properly read in the values. I don't believe it's a problem with my code, but here is what I'm doing (SECTORSIZE is a const 512)::

void getSector(char *sector, int secNum, FILE *fp) 
{
   fseek(fp, (secNum*SECTORSIZE), SEEK_SET);
   fread(sector, sizeof(char), SECTORSIZE, fp);
}

FILE *fp;
char sector[512];
unsigned int fileSize;
int i;
int diroffset;
char name[8];
name[0] = 0;

fp = fopen("floppy", "r");

//sector 0 contains the disk geometry
getSector(sector, 0, fp);

printf("Bytes per Sector: %d\n", (((unsigned int)sector[0x0c]) << 8u) | (unsigned int)sector[11]);
printf("Sectors per Cluster: %d\n", ((unsigned int)sector[0x0d] ));
printf("Reserved Sectors for the Boot Record: %d\n", (((unsigned int)sector[0x0f]) << 8u) | (unsigned int)sector[0x0e]);
printf("Number of FATS: %d\n", ((unsigned int)sector[0x10]));
//printf("Max # of Root Directory Entries: %d\n", (((unsigned int)sector[0x12]) << 8u) | (unsigned int)sector[0x11]);
//printf("Number of Sectors: %d\n", (((unsigned int)sector[12])) | (unsigned int)sector[11]);
//printf("Sectors per FAT: %d\n", ((unsigned int)sector[13] << 8u));
//printf("Sectors per Track: %d\n", (((unsigned int)sector[12]) << 8u) | (unsigned int)sector[11]);
//printf("Number of Surfaces: %d\n", (((unsigned int)sector[12]) << 8u) | (unsigned int)sector[11]);

The commented out sections are the parts where I'm still working on them. I pretty much just copied the first line and just changed the string name to match. The next one after number of FATS is the max # of root directories which is where I'm running into trouble. I have a list of the hex representation for each geometry location but the bit shifting is what's throwing me off.

However I am also noticing that when I'm displaying filenames I'm displaying an extra name of random characters. Below is how I'm finding filenames:

diroffset = 0;

while(diroffset <= 512) {

    getSector(sector, 19, fp);
    // print name of the file
    if((void *) sector[0] != NULL)
        for(i = 0; i < 8; i++)
            name[i] = sector[diroffset + i];

    if(name[0] != 0) {
        printf("Filename: ");
        for(i = 0; i < 8; i++)
            printf("%c", name[i]);
        putchar('\n');
    }

    name[0] = 0;

    diroffset += 32;
}

It was my understanding that every 32 you would have a new filename, which it works as far as I know except displaying these characters as the last file found:

  • Filename: É·╬╩ 

I would like some more clarification on bit shifting in general, such as when and where to bit shift. I was trying to follow examples provided to me but maybe I'm just over complicating something and I'm not seeing it.

PS: If you're curious why I have so many unsigned int it's because my IDE complains otherwise when using bit operators

BpVx
  • 23
  • 6
  • If I have the intention of the code correct, I assume this is FAT, you are checking for `NUL` at position 0, then don't check it otherwise. I'm not an expert, but I don't think that's right. – Neil Feb 23 '20 at 19:12
  • 5
    Try to use `unsigned char sector[512];` to get rid of the casts. – the busybee Feb 23 '20 at 20:16
  • 1
    The first character of a filename can be also 0xE5 for a deleted or unused entry. [The Wikipedia page](https://en.wikipedia.org/wiki/Design_of_the_FAT_file_system) has valuable information on nearly all details. – the busybee Feb 23 '20 at 20:19
  • 1
    You're not opening the floppy image in **binary format** (`"rb"`) – Antti Haapala -- Слава Україні Feb 23 '20 at 20:41
  • @thebusybee doing that didn't change anything, after removing the unsigned int my IDE was complaining again. I'll take a look at that wiki though – BpVx Feb 23 '20 at 21:06
  • @Neil I know its probably not right, but I tried looking up ways to accomplish that. – BpVx Feb 23 '20 at 21:06
  • @AnttiHaapala I'm not sure what that would matter but it hasn't changed any of my output – BpVx Feb 23 '20 at 21:07
  • What are the actual messages that your IDE gives you? Are you aware that an IDE has not necessarily the same opinion as the compiler? Which IDE do you use? -- Can you please elaborate on the actual question you have? Is it just the bit shifting? And if so, which problem do you face? – the busybee Feb 23 '20 at 21:20
  • @thebusybee So my main question is trying to understand bit shifting. I added the filename stuff as well instead of making a new post since its somewhat related. I am trying to understand how to properly read the geography information from the boot sector. I was told that bits needed to be shifted, and that it would depend on how many bytes it took to store the information I wanted. My program works, I just need to understand bit shifting – BpVx Feb 23 '20 at 21:29
  • In case of FAT12 you need bit shifting because the FAT entries are 12 bit wide (sic!). They are packed so that 2 of them are stored in 3 bytes. The details are on the mentioned page. -- Additionally the time and date values in the directory entries are packed bits, too. -- Do you need guidance of bit shifting in general? If yes, I'd recommend a good book or tutorial on C. – the busybee Feb 24 '20 at 13:05
  • @thebusybee In further looking, I realized if I leave everything unsigned and change my char sector to unsigned as well, I am not getting the proper output which is similar to what busybee mentioned except I'm not getting rid of any casts. So there was nothing wrong with my bit shifting after all. Appreciate the help – BpVx Feb 24 '20 at 15:37

0 Answers0