deltanovember
deltanovember

Reputation: 44091

C# Attempted to read or write protected memory error

Addendum: it seems to run correctly when I uncheck "optimize code" which leads me to believe it is some quirky configuration problem

Firstly I am trying to run unmanaged code. I have "allow unsafe code" checked. It is pointing to this line of code here where I am trying to read a bitmap without using the relatively slow getpixel:

byte[] buff = { scanline[xo], scanline[xo + 1], scanline[xo + 2], 0xff };

Entire snippet is below. How can I correct this problem?

private const int PIXELSIZE = 4;              // Number of bytes in a pixel

BitmapData mainImageData = mainImage.LockBits(new Rectangle(0, 0, mainImage.Width, mainImage.Height), ImageLockMode.ReadOnly, mainImage.PixelFormat);
List<Point> results = new List<Point>();

foundRects = new List<Rectangle>();

for (int y = 0; y < mainImageData.Height
{
        byte* scanline = (byte*)mainImageData.Scan0 + (y * mainImageData.Stride);

        for (int x = 0; x < mainImageData.Width; x++)
        {
            int xo = x * PIXELSIZE;
            byte[] buff = { scanline[xo], scanline[xo + 1], 
                    scanline[xo + 2], 0xff };
            int val = BitConverter.ToInt32(buff, 0);

            // Pixle value from subimage in desktop image
            if (pixels.ContainsKey(val) && NotFound(x, y))
            {
                Point loc = (Point)pixels[val];

                int sx = x - loc.X;
                int sy = y - loc.Y;
                // Subimage occurs in desktop image 
                if (ImageThere(mainImageData, subImage, sx, sy))
                {
                    Point p = new Point(x - loc.X, y - loc.Y);
                    results.Add(p);
                    foundRects.Add(new Rectangle(x, y, subImage.Width,
                                                               subImage.Height));
                }
          }
        }

Upvotes: 3

Views: 2060

Answers (3)

John Knoeller
John Knoeller

Reputation: 34218

The most likely reason is that the image isn't 32bpp. it could be 24bpp, or possibly even 8 or 16 bit.

You should be getting PIXELSIZE from PixelFormat Rather than hard-coding it to 4.

Check to see that the value you are getting for Stride agrees with the Width.

Upvotes: 0

Ed Swangren
Ed Swangren

Reputation: 124790

It's hard to say with the limited information we have, but I see a couple of obvious problems, one of which addresses your issue directly:

  1. You are not checking the pixel format, but are assuming that it is 32bppRGB. It is likely 24bppRGB, and that would explain the error.

  2. You are reading the RGB values incorrectly; Windows internally stores bitmaps in BGR order.

  3. You are not calling UnlockBits at the end of the method.

Upvotes: 3

Logan Capaldo
Logan Capaldo

Reputation: 40346

What are the values xo + 1 and xo + 2 when x is mainImageData.Width - 1? They are surely walking off the reservation.

Upvotes: 0

Related Questions