Sign in to follow this  
emfor

Bitmap LockBits access violation (C#)

Recommended Posts

emfor    122
Hi Everyone, I've got a class thtat grabs a frame from an avi file to Bitmap class. Then I pass the Bitmap to another class which should convert it to OpenGL texture. The problem is that when I try to use LockBits function, I get access violation exception. It's like this:
b = video.GetFrame();
gpu.CreateTexture(b);
where GetFrame() returns:
Bitmap b = new Bitmap(width, height, linesize, PixelFormat.Format24bppRgb, bufferPtr);
return b;
and
public void CreateTexture(Bitmap bitmap)
{
  int[] texture = new int[1];

  Gl.glEnable(Gl.GL_TEXTURE_2D);
  Gl.glHint(Gl.GL_PERSPECTIVE_CORRECTION_HINT, Gl.GL_NICEST);
            
  Gl.glGenTextures(1, texture);
  Gl.glBindTexture(Gl.GL_TEXTURE_2D, texture[0]);

  int w = bitmap.Width;
  int h = bitmap.Height;
  BitmapData data = bitmap.LockBits(new Rectangle(0, 0, w, h),
  ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb); //Here I get the error
  (...)
}
What am I doing wrong? Ahh, I'm using Tao Framework to access OpenGL functions. -- Best regards, Mateusz

Share this post


Link to post
Share on other sites
Kaze    948
see if any of this works


class GlImage{

public GlImage(Image image) {
Rectangle rect = new Rectangle(0, 0, image.Width, image.Height);
System.Drawing.Imaging.BitmapData bitmapdata;
Bitmap bitmap = new Bitmap(image);

bitmapdata = bitmap.LockBits(rect, System.Drawing.Imaging.ImageLockMode.ReadOnly,
System.Drawing.Imaging.PixelFormat.Format32bppPArgb);

int[] ids = new int[1];
Gl.glGenTextures(1, ids);
imageid = ids[0];
width = bitmap.Width;
height = bitmap.Height;

Gl.glBindTexture(Gl.GL_TEXTURE_2D, imageid);

//Gl.GL_RGBA
Gl.glTexImage2D(Gl.GL_TEXTURE_2D, 0, Gl.GL_RGBA, image.Width, image.Height,
0, Gl.GL_BGRA, Gl.GL_UNSIGNED_BYTE, bitmapdata.Scan0);

Gl.glTexParameteri(Gl.GL_TEXTURE_2D, Gl.GL_TEXTURE_MIN_FILTER, Gl.GL_LINEAR); // Linear Filtering
Gl.glTexParameteri(Gl.GL_TEXTURE_2D, Gl.GL_TEXTURE_MAG_FILTER, Gl.GL_LINEAR); // Linear Filtering

Gl.glTexParameterf(Gl.GL_TEXTURE_2D, Gl.GL_TEXTURE_WRAP_S, Gl.GL_CLAMP);
Gl.glTexParameterf(Gl.GL_TEXTURE_2D, Gl.GL_TEXTURE_WRAP_T, Gl.GL_CLAMP);

bitmap.UnlockBits(bitmapdata);
}
private int imageid;

private float height, width;


public float Height
{
get { return height; }
}
public float Width
{
get { return width; }
}

public void Bind() {
Gl.glBindTexture(Gl.GL_TEXTURE_2D, imageid);
}
public static void UnBind()
{
Gl.glBindTexture(Gl.GL_TEXTURE_2D, 0);
}

public void Free(){
int[] ids = new int[1];
ids[0] = imageid;
Gl.glDeleteTextures(1, ids);
}

}

Share this post


Link to post
Share on other sites
emfor    122
Thanks for the anwser!
I've tried to modyfi my function to:
public void CreateTexture(Image image)
{
Rectangle rect = new Rectangle(0, 0, image.Width, image.Height);
System.Drawing.Imaging.BitmapData bitmapdata;
Bitmap bitmap = new Bitmap(image);

bitmapdata = bitmap.LockBits(rect, System.Drawing.Imaging.ImageLockMode.ReadOnly,
System.Drawing.Imaging.PixelFormat.Format32bppPArgb);

int[] ids = new int[1];
Gl.glGenTextures(1, ids);
imageid = ids[0];
width = bitmap.Width;
height = bitmap.Height;
Gl.glBindTexture(Gl.GL_TEXTURE_2D, imageid);

Gl.glTexImage2D(Gl.GL_TEXTURE_2D, 0, Gl.GL_RGBA, image.Width, image.Height,
0, Gl.GL_BGRA, Gl.GL_UNSIGNED_BYTE, bitmapdata.Scan0);

Gl.glTexParameteri(Gl.GL_TEXTURE_2D, Gl.GL_TEXTURE_MIN_FILTER, Gl.GL_LINEAR); // Linear Filtering
Gl.glTexParameteri(Gl.GL_TEXTURE_2D, Gl.GL_TEXTURE_MAG_FILTER, Gl.GL_LINEAR); // Linear Filtering

Gl.glTexParameterf(Gl.GL_TEXTURE_2D, Gl.GL_TEXTURE_WRAP_S, Gl.GL_CLAMP);
Gl.glTexParameterf(Gl.GL_TEXTURE_2D, Gl.GL_TEXTURE_WRAP_T, Gl.GL_CLAMP);

bitmap.UnlockBits(bitmapdata);
}

Now I've got the same error in line
Bitmap bitmap = new Bitmap(image);


--
Best regards,
Mateusz

Share this post


Link to post
Share on other sites
Kaze    948
The only thing that I can think of is that unlike other exception system access violation exceptions don't always get throws from exactly where the root problem occurred,

are you using any unsafe code or wrappers to native librarys other than tao.opengl?

Share this post


Link to post
Share on other sites
emfor    122
Yes, I use Tao.ffmpeg and this function:
unsafe Bitmap SaveFrame(IntPtr pFrame, int width, int height)
{
try
{
int x, y;
int linesize = width * 3;
byte* scan0 = (byte*)Marshal.ReadIntPtr(pFrame);

IntPtr bufferPtr = Marshal.AllocHGlobal(linesize * height);
byte* buffer = (byte*)bufferPtr;

for (y = 0; y < height; y++)
{
for (x = 0; x < linesize; x = x + 3)
{
*buffer++ = (byte)*(scan0 + y * linesize + x + 2);
*buffer++ = (byte)*(scan0 + y * linesize + x + 1);
*buffer++ = (byte)*(scan0 + y * linesize + x);
}
}

Bitmap b = new Bitmap(width, height, linesize, PixelFormat.Format24bppRgb, bufferPtr);
Marshal.FreeHGlobal(bufferPtr);

return b;
}
catch (Exception ex) { throw new Exception(ex.Message); }
}

This code is put togeter from various examples and customized... maybe there is a better way to do it.

--
Best regards,
Mateusz

Share this post


Link to post
Share on other sites
emfor    122
I finally managed to make it work, as Kaze sad the error was in SaveFrame() function. I've commented out the line:
Marshal.FreeHGlobal(bufferPtr);

And the Access Violation dissapeard!
Thanks for help!

--
Best regards,
Mateusz

Share this post


Link to post
Share on other sites
CProgrammer    303
You probably shouldnt stop looking yet. If you allocated something and freeing it crashes the app then you likely have a memory problem somewhere else in your code. I may be wrong and I'm not to familiar with Marshal... but that's the first thing that comes to mind.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this