From: tomdickens on
David,

The code fails when stripped to:

CImg<unsigned char> img(640,400,1,3);
img.fill(0);
img.display();

at the img.display() call.


From CImg.h, I believe the relevant part of the constructor code is:

explicit CImg(const unsigned int dx, const unsigned int dy=1, const unsigned
int dz=1, const unsigned int dv=1):
is_shared(false) {
const unsigned long siz = dx*dy*dz*dv;
if (siz) { width = dx; height = dy; depth = dz; dim = dv; data = new
T[siz]; }
else { width = height = depth = dim = 0; data = 0; }
}

Then the call to display() is:
//! Display an image in a window with a title \p title, and wait a
'is_closed' or 'keyboard' event.\n
const CImg<T>& display(const char *const title=0, const bool
display_info=true) const {
CImgDisplay disp;
return _display(disp,title,display_info);
}

The CImgDisplay constructor is:
//! Create an empty display window.
CImgDisplay():
width(0),height(0),normalization(0),title(0),
window_x(0),window_y(0),window_width(0),window_height(0),

mouse_x(0),mouse_y(0),button(*buttons),wheel(0),key(*keys),released_key(*released_keys),

is_closed(true),is_resized(false),is_moved(false),is_event(false),is_fullscreen(false),
min(0),max(0) {}

CImgDisplay is a struct containing all these variables that define a display.

I'm not very experienced using interop between managed (/clr) and unmanaged
code, such as in CImg.h. Could the use of "new" by CImg to allocate memory be
the culprit??

I'm certainly not sure that this is enough detail to help you see what the
problem might be.

Thanks a lot,
Tom




"David Wilkinson" wrote:

> tomdickens wrote:
> > I have a Windows Forms application, Visual C++ 2005, compiling it using /clr.
> > I need to use the image-handling library CImg, which is packaged simply as a
> > header file CImg.h that you include in your project.
> >
> > I added CImg.h to stdafx.h, inside #pragma unmanaged/managed preprocessor
> > instructions. The code compiles just fine.
> >
> > However, when I construct a CImg object and then try to write text into it
> > to display, I get a memory error -
> > System.AccessViolationException: Attempted to read or write protected
> > memory. This is often an indication that other memory is corrupt.
> > at cimg_library.CImg<unsigned char>.draw_text<unsigned char>(CImg<unsigned
> > char>* , Int32 , Int32 , SByte* , Byte* , Int32 , Single , UInt32 )
> >
> > Is this because of using unmanaged memory in a managed code? I thought IJW
> > would handle this. I've asked this same question on the CImg forum but have
> > no reszponse yet.
> >
> >
> > Thanks,
> > Tom
> >
> > Here is the detailed code:
> >
> > Put in stdafx.h:
> > #pragma once
> > #pragma unmanaged
> > #pragma comment (lib, "shell32.lib")
> > #pragma comment (lib, "gdi32.lib")
> > #pragma comment (lib, "user32.lib")
> > #define cimg_OS 2
> > #define cimg_display_type 2
> > #include "CImg.h"
> > using namespace cimg_library;
> > #pragma managed
> >
> > Call the functions:
> > CImg<unsigned char> img(640,400,1,3); // Define a 640x400 color image with 8
> > bits per color component.
> > img.fill(0); // Set pixel values to 0 (color : black)
> > unsigned char purple[] = { 255,0,255 }; // Define a purple color
> > img.draw_text(100,100,"Hello World",purple); // IT DIES HERE ---- Draw a
> > purple "Hello world" at coordinates (100,100).
> > img.display("My first CImg code"); // Display the image in a display window.
>
> What is the precise C++ declaration of the method, and how are you calling it?
>
> --
> David Wilkinson
> Visual C++ MVP
> .
>
From: tomdickens on
David,

The code fails when stripped to:

CImg<unsigned char> img(640,400,1,3);
img.fill(0);
img.display();

at the img.display() call.


From CImg.h, I believe the relevant part of the constructor code is:

explicit CImg(const unsigned int dx, const unsigned int dy=1, const unsigned
int dz=1, const unsigned int dv=1):
is_shared(false) {
const unsigned long siz = dx*dy*dz*dv;
if (siz) { width = dx; height = dy; depth = dz; dim = dv; data = new
T[siz]; }
else { width = height = depth = dim = 0; data = 0; }
}

Then the call to display() is:
//! Display an image in a window with a title \p title, and wait a
'is_closed' or 'keyboard' event.\n
const CImg<T>& display(const char *const title=0, const bool
display_info=true) const {
CImgDisplay disp;
return _display(disp,title,display_info);
}

The CImgDisplay constructor is:
//! Create an empty display window.
CImgDisplay():
width(0),height(0),normalization(0),title(0),
window_x(0),window_y(0),window_width(0),window_height(0),

mouse_x(0),mouse_y(0),button(*buttons),wheel(0),key(*keys),released_key(*released_keys),

is_closed(true),is_resized(false),is_moved(false),is_event(false),is_fullscreen(false),
min(0),max(0) {}

CImgDisplay is a struct containing all these variables that define a display.

I'm not very experienced using interop between managed (/clr) and unmanaged
code, such as in CImg.h. Could the use of "new" by CImg to allocate memory be
the culprit??

I'm certainly not sure that this is enough detail to help you see what the
problem might be.

Thanks a lot,
Tom

"David Lowndes" wrote:

> >The same code works fine in an MFC application.
>
> OK. Is the code absolutely correct though? i.e. is the native version
> working partly by chance/circumstance?
>
> >I could post the CImg.h parts that are required here, but I don't know if
> >that would be productive.
>
> Unlikely.
>
> > Probably the most important part is that the image
> >memory is allocated using 'new.' Since this worked in MFC, I'm really
> >thinking that the managed/unmanaged interop is not working here.
>
> Can you show just the relevant part of the code (if you think it would
> make sense to someone not familiar with using CImg)?
>
> Dave
> .
>
From: David Lowndes on
>The code fails when stripped to:
>
>CImg<unsigned char> img(640,400,1,3);
>img.fill(0);
>img.display();
>
>at the img.display() call.

Tom,

Is the call to display failing, or somewhere deeper inside the guts of
display?
I'd assume it's deeper inside (what you showed looks straightforward
enough), and if so where precisely? If it's a template library you
should have the source.

Dave