# Include <VCL. h>
# Pragma hdrstop
# Include <stdio. h>
# Include "unit1.h"
# Include "file1.h"
Struct bitmapfileheader _
{
Short type;
Int bfsize;
Short RE1, re2;
Int offbits;
};
Struct bitmapinfo _
{
Long size;
Long width, height;
Short planes, bitcount;
Long comp, sizeimg;
Long xpels, ypels;
Long used, important;
};
Struct colortable _
{
Char blue, green, red, Res;
};
Void XXX ()
{
File * f = fopen ("F: // projects // BMP // 1.bmp", "rb ");
If (F = NULL)/* determines whether the file is successfully opened */
{
Showmessage ("file open error ");
Return;
}
Fseek (F, 0, 0 );
Bitmapfileheader _ * bmp h = new bitmapfileheader _();
If (fgets (char *) bmp h, sizeof (bitmapfileheader _), f) = NULL)
{
Showmessage ("file read error ");
Return;
}
Bitmapinfo _ * BMP I = new bitmapinfo _();
If (fgets (char *) bmp I, sizeof (bitmapinfo _), f) = NULL)
{
Showmessage ("File Read error2 ");
Return;
}
Form1-> edit1-> text = inttostr (bmp h-> bfsize );
Form1-> edit2-> text = inttostr (bmp I-> width );
Form1-> edit3-> text = inttostr (bmp I-> height );
Fclose (f );
};
This is a simple program that uses BCB to read the header information of BMP files, but it does not work properly.
Display result
Edit1: 0
Edit2: 1073741824
Edit3: 16777216
You can't explain it by thinking deeply. Open the BMP file with Ultra edit and find that the file starts
42 4D 38 14 00 00 00 00 00 36 04 00 00 28 00
The file is correct. 42 4D is the BMP file mark "BM". The next 38 14 00 00 is the file size, and the int value is 0x1438 = 5176 bytes, which is the same as that shown in windows, yes.
Later, I wrote a program to read the first 'B' and 2nd byte 'M', but it is correct. Then, when the read size is reached, it will become 0, it can only be suspected that a problem occurs when the bitmapfileheader _ structure matches the data. For further verification, another program fills the BMP file header, writes the file to the disk, and then uses ultra Edit to view the program code.
# Pragma argsused
# Include <stdio. h>
# Include <stdlib. h>
Struct bitmapfileheader _
{
Short type;
Int bfsize;
Short RE1, re2;
Int offbits;
};
Int main (INT argc, char * argv [])
{
File * f = fopen ("F: // abc.txt", "WB ");
Bitmapfileheader _ * B = new bitmapfileheader _();
B-> type = 1;
B-> bfsize = 1;
B-> RE1 = B-> re2 = 1;
B-> offbits = 1;
If (F = NULL)
{
Printf ("XXX ");
System ("pause ");
Return 0;
}
Fwrite (B, sizeof (bitmapfileheader _), 1, F );
System ("pause ");
Return 0;
}
You can use ultra Edit to check whether 16 bytes are written, as shown below:
01 00 67 32 01 00 00 00 01 00 01 00 00 00
After I wrote the type, I added 67 32 for no reason, and there was no problem later. I suddenly remembered that the C language's byte alignment was discussed on the forum, and I suspected it was a byte alignment problem, find the BCB byte alignment command on the Internet. The original BCB is 4 byte alignment by default. You can use # pragma pack (1) to set the byte alignment to 1 byte.
With the # pragma pack (1) added, the data read is correct.
The Pentium machine is a 32-bit system with a 32-bit data bus width. The CPU transmits 4 bytes of data from the memory at a time. In order to obtain one data, the memory access can be minimized, by default, the compiler alignment the data of the structure in 4 bytes. In this way, the bitmapfileheader _ structure above requires four accesses to the memory (16 bytes read 4 bytes each time ), the data following this structure is also aligned in the memory. If a bitmapfileheader _ structure is followed, only four accesses are required to read the bitmapfileheader _ structure, if the # pragma pack (1) is used to force the 1-byte alignment, when the first bitmapfileheader _ is accessed, the memory is still accessed four times, however, when accessing the bitmapfileheader _ next to it, you need to access the memory five times, and the subsequent data is not consistent.
Although the compiler defaults to 4-byte alignment for performance considerations, sometimes users have their own needs not alignment, just like in the above case, then the IDE command # pragma pack (1) is required) forced non-alignment.