我是opengl的新手。我正在尝试使用opengl加载图像。但我无法这样做。它给了我这个错误:
*** Error in `./lena': double free or corruption (top) : 0x0000000001353070 ***
我不知道自己做错了什么。我的代码已在下面给出。实际上这不是我的代码。我在Stack Overflow的另一篇文章中看到了它,名字叫Ollo。
#include <bits/stdc++.h>
#include <GL/glut.h>
using namespace std;
struct BITMAPFILEHEADER
{
int bfType; //specifies the file type
long long bfSize; //specifies the size in bytes of the bitmap file
int bfReserved1; //reserved; must be 0
int bfReserved2; //reserved; must be 0
long long bOffBits; //species the offset in bytes from the bitmapfileheader to the bitmap bits
};
struct BITMAPINFOHEADER
{
long long biSize; //specifies the number of bytes required by the struct
long long biWidth; //specifies width in pixels
long long biHeight; //species height in pixels
int biPlanes; //specifies the number of color planes, must be 1
int biBitCount; //specifies the number of bit per pixel
long long biCompression;//spcifies the type of compression
long long biSizeImage; //size of image in bytes
long long biXPelsPerMeter; //number of pixels per meter in x axis
long long biYPelsPerMeter; //number of pixels per meter in y axis
long long biClrUsed; //number of colors used by th ebitmap
long long biClrImportant; //number of colors that are important
};
int main(void){
FILE *filePtr;
BITMAPFILEHEADER bitmapFileHeader;
BITMAPINFOHEADER *bitmapInfoHeader = new BITMAPINFOHEADER;
unsigned char *bitmapImage; //store image data
int imageIdx=0; //image index counter
unsigned char tempRGB; //our swap variable
filePtr = fopen("lena.bmp","rb");
if (filePtr == NULL)
cout << "ERROR!!! 1" << endl;
fread(&bitmapFileHeader, sizeof(BITMAPFILEHEADER),1,filePtr);
fread(bitmapInfoHeader, sizeof(BITMAPINFOHEADER),1,filePtr); // small edit. forgot to add the closing bracket at sizeof
//move file point to the begging of bitmap data
fseek(filePtr, bitmapFileHeader.bOffBits, SEEK_SET);
//allocate enough memory for the bitmap image data
bitmapImage = (unsigned char*)malloc(bitmapInfoHeader->biSizeImage);
//verify memory allocation
if (!bitmapImage)
{
free(bitmapImage);
fclose(filePtr);
}
//read in the bitmap image data
fread(bitmapImage, bitmapInfoHeader->biSizeImage, 1, filePtr);
//make sure bitmap image data was read
if (bitmapImage == NULL)
{
fclose(filePtr);
}
//swap the r and b values to get RGB (bitmap is BGR)
for (imageIdx = 0;imageIdx < bitmapInfoHeader->biSizeImage;imageIdx+=3)
{
tempRGB = bitmapImage[imageIdx];
bitmapImage[imageIdx] = bitmapImage[imageIdx + 2];
bitmapImage[imageIdx + 2] = tempRGB;
}
return 0;
}
答案 0 :(得分:2)
bitmapImage
是否 0 ,如果是,则会立即拨打free (...)
上的bitmapImage
fread (...)
不会更改bitmapImage
是NULL
if (filePtr == NULL) {
cout << "ERROR!!! 1" << endl;
return -1; // FAILURE, so return!
}
[...]
//allocate enough memory for the bitmap image data
bitmapImage = (unsigned char*)malloc(bitmapInfoHeader->biSizeImage);
//verify memory allocation
if (!bitmapImage)
{
//free(bitmapImage); // This does not belong here!
fclose(filePtr);
return -2; // FAILURE, so return!
}
//read in the bitmap image data
fread(bitmapImage, bitmapInfoHeader->biSizeImage, 1, filePtr);
// THIS IS POINTLESS TOO, fread (...) is not going to change the address of
// bitmapImage.
/*
//make sure bitmap image data was read
if (bitmapImage == NULL)
{
fclose(filePtr);
}
*/
//swap the r and b values to get RGB (bitmap is BGR)
for (imageIdx = 0;imageIdx < bitmapInfoHeader->biSizeImage;imageIdx+=3)
{
tempRGB = bitmapImage[imageIdx];
bitmapImage[imageIdx] = bitmapImage[imageIdx + 2];
bitmapImage[imageIdx + 2] = tempRGB;
}
答案 1 :(得分:0)
正如我在评论中所提到的,你不应该编写自己的代码来读取.bmp文件(除非是为了作业,或类似的东西)。你说你是关于模仿linux的,所以你可以试试FreeImage或ImageMagick。您使用的代码不会处理索引颜色图像,例如,可能还有许多其他东西。
答案 2 :(得分:0)
这就是我加载每个像素24位的BMP文件的方式,而不是索引颜色位图的加载方式,请从此处下载winbgim:http://www.mediafire.com/file/z9wnl0c70tiacqn/winbgim_DevCpp.zip/file,是在dev-c ++中,您可能必须加载几个参数链接器,路径为:项目,项目选项,参数,并编写:-lbgi -lgdi32 -luser32 -lcomdlg32 -luuid -loleaut32 -lole32 -mwindows -lwinmm,在安装winbgim之后,转到dev c并创建新的作为控制台图形应用程序的项目,如果正确安装了winbgim,则该项目必须在项目列表中, 我写了“写到共享内存”,因为虽然我不是用这种方式访问文件的,但也是从同一个文件访问的,所以我也在内存中写了文件
#include <winbgim.h>
#include <string.h>
#include<windows.h>
#include<stdio.h>
#include <stdlib.h>
const char *Filename;
BITMAPFILEHEADER FileHeader;
BITMAPINFOHEADER InfoHeader;
int k;
typedef struct{
BYTE colorr;
BYTE colorg;
BYTE colorb;
}cine;
cine color;
HANDLE hArch, hProy;
LPSTR base,puntero;
DWORD tam;
int main()
{
int gdriver=9;
int gmode=2;
// initgraph(&gdriver,&gmode, "");
cleardevice();
UnmapViewOfFile(base);
CloseHandle(hProy);
CloseHandle(hArch);
char *p;
char *base;
DWORD buf;
Filename="D:\\music\\IMSLP00795-BWV0971\\01.bmp";
int gd = DETECT, gm;
int x = 320, y = 240, radius;
k=0;
int i;
int j;
FILE *File=NULL;
if(!Filename)
{
MessageBox(NULL,"Konnte Filename nicht finden!","Error",MB_OK|MB_ICONERROR);
}
else
{
File=fopen("D:\\music\\IMSLP00795-BWV0971\\01.bmp","rb");
}
fread(&FileHeader,sizeof(BITMAPFILEHEADER),1,File);
if(FileHeader.bfType != 0x4D42)
{
MessageBox(NULL,"Ungültiges Bildformat!","Error",MB_OK|MB_ICONERROR);
exit(1);
}
printf("tamaño total del archivo %d\n",FileHeader.bfSize);
printf("comienzo del mapa de bits (imagen en pixels) en bits %d\n",FileHeader.bfOffBits);
buf=FileHeader.bfOffBits/8; //offset from the begining of BMP file (pixel array)
printf("comienzo del mapa de bits en bytes desde el origen del archivo %d\n",buf);
fread(&InfoHeader,sizeof(BITMAPINFOHEADER),1,File);
printf("horizontal resolution in pixels por metro %li\n",InfoHeader.biWidth);
printf("vertical resolution in pixels por metro %li\n",InfoHeader.biHeight);
printf("numero de bits por pixel %d", InfoHeader.biBitCount);
initwindow(InfoHeader.biWidth,InfoHeader.biHeight);
hArch = CreateFile("D:\\music\\IMSLP00795-BWV0971\\01.bmp", /* file name */
GENERIC_ALL , /* read/write access */
0, /* no sharing of the file */
NULL, /* default security */
OPEN_ALWAYS, /* open new or existing file */
FILE_ATTRIBUTE_NORMAL, /* routine file attributes */
NULL); /* no file template */
if (hArch==INVALID_HANDLE_VALUE){
fprintf(stderr,"no puede abrirse el archivo");
}
hProy = CreateFileMapping(hArch, /* file handle */
NULL, /* default security */
PAGE_READWRITE, /* read/write access to mapped pages */
0, /* map entire file */
0,
TEXT("SharedObject")); /* named shared memory object */
/* write to shared memory */
base=(LPSTR)MapViewOfFile(hProy,FILE_MAP_ALL_ACCESS,0,0,0);
tam=GetFileSize(hArch,NULL);
int cont=0;
puntero=base;
p=base+FileHeader.bfOffBits;
k=0;int t=0,v,l;
fseek(File,FileHeader.bfOffBits,SEEK_SET );
int read=0,read2=0;
k=0;
for( i=0; i<InfoHeader.biWidth; i++ ) {
fread(&color,sizeof(cine),1,File);
read += sizeof(cine);
printf( "Pixel %d: %3d %3d %3d\n", i+1, int(color.colorb), int(color.colorg), int(color.colorr) );
}
if( read % 4 != 0 ) {
read2 = 4 - (read%4);
printf( "Padding: %d bytes\n", read2 );
//fread( &color, read2, 1, File );
}
fseek(File,FileHeader.bfOffBits,SEEK_SET );
for (i=0;i<InfoHeader.biHeight;i++)
for(j=0;j<InfoHeader.biWidth ;j++)
{
fread(&color,sizeof(cine),1,File);
putpixel(j,InfoHeader.biHeight- i,COLOR(int(color.colorb),int(color.colorg),int(color.colorr)));
if(j==InfoHeader.biWidth-1&&read2!=0)fseek(File,read2,SEEK_CUR);
}
fclose(File);
UnmapViewOfFile(base);
CloseHandle(hProy);
CloseHandle(hArch);
getch();
}