473,580 Members | 2,797 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

Managed C++ wrapper with abstract base return types

I am trying to create an Managed C++ Wrapper around an unmanaged library
which contains C++ code.

Some of the unmanaged methods returns an returntype which is of the abstract
base type (for example unmanagedObject ). How can i convert this to the
managed abstract basetype?

Hope somebody can help me

Thanx

Nov 17 '05 #1
9 2410
WithPit wrote:
I am trying to create an Managed C++ Wrapper around an unmanaged library
which contains C++ code.

Some of the unmanaged methods returns an returntype which is of the abstract
base type (for example unmanagedObject ). How can i convert this to the
managed abstract basetype?

What about something like this:

__gc class SomeClass
{
UnmanagedObject *pobj;

// ...

public:

UnmanagedObject *GetUnmanagedOb ject() { return pobj; }

// ...
};
Nov 17 '05 #2
Hi WithPit!
I am trying to create an Managed C++ Wrapper around an unmanaged library
which contains C++ code.

Some of the unmanaged methods returns an returntype which is of the abstract
base type (for example unmanagedObject ). How can i convert this to the
managed abstract basetype?


If you really write an wrapper then your class should look like:

public __gc Wrapper : public IDisposable
{
public:
Wrapper() {pNative = new NativeClass;)
int WrapperFunction 1(...) {return pNative->Function1(...) ;}
void WrapperFunction 2(...) {return pNative->Function2(...) ;}
void Dispose() (delete pNative;);
private:
NativeClass *pNative;
};

(Of course, sometimes you need to do some marshalling...)

And now, if it returns the object itself, you just need to create an new
instance of the Wrapper-class (and you also must be sure to call the
correctly deletefuntion):

public __gc Wrapper : public IDisposable
{
public:
Wrapper() {pNative = new NativeClass;)
int WrapperFunction 1(...) {return pNative->Function1(...) ;}
void WrapperFunction 2(...) {return pNative->Function2(...) ;}
void Dispose() (delete pNative;);

// *the following is important!*
Wrapper *Function3 {return new Wrapper(pNative->Function3()) ;}
private:
// *the following is important!*
Wrapper(NativeC lass *pRef) {pNative = pRef;}
NativeClass *pNative;
};

--
Greetings
Jochen

My blog about Win32 and .NET
http://blog.kalmbachnet.de/
Nov 17 '05 #3
Jochen, great and clear examples! Can you please show how to do marshalling
if function2 were to return the following native/unmanaged type:

class MyClass
{
public:
...
char* myStr;
CPoint myPoint;
int myInt;
...
CPoint getPoint();
}

Also, while at it, from the wrapper, how can you return a .NET String from
say native function4 that actually returns char*, tchar*, w_char* or
whatever?

Thx!!!

/Tommy

"Jochen Kalmbach [MVP]" <no************ ********@holzma .de> skrev i
meddelandet news:eH******** ******@TK2MSFTN GP15.phx.gbl...
Hi WithPit!
I am trying to create an Managed C++ Wrapper around an unmanaged library
which contains C++ code.

Some of the unmanaged methods returns an returntype which is of the abstract base type (for example unmanagedObject ). How can i convert this to the
managed abstract basetype?


If you really write an wrapper then your class should look like:

public __gc Wrapper : public IDisposable
{
public:
Wrapper() {pNative = new NativeClass;)
int WrapperFunction 1(...) {return pNative->Function1(...) ;}
void WrapperFunction 2(...) {return pNative->Function2(...) ;}
void Dispose() (delete pNative;);
private:
NativeClass *pNative;
};

(Of course, sometimes you need to do some marshalling...)

And now, if it returns the object itself, you just need to create an new
instance of the Wrapper-class (and you also must be sure to call the
correctly deletefuntion):

public __gc Wrapper : public IDisposable
{
public:
Wrapper() {pNative = new NativeClass;)
int WrapperFunction 1(...) {return pNative->Function1(...) ;}
void WrapperFunction 2(...) {return pNative->Function2(...) ;}
void Dispose() (delete pNative;);

// *the following is important!*
Wrapper *Function3 {return new Wrapper(pNative->Function3()) ;}
private:
// *the following is important!*
Wrapper(NativeC lass *pRef) {pNative = pRef;}
NativeClass *pNative;
};

--
Greetings
Jochen

My blog about Win32 and .NET
http://blog.kalmbachnet.de/

Nov 17 '05 #4
Hi Tommy!
class MyClass
{
public:
...
char* myStr;
CPoint myPoint;
int myInt;
...
CPoint getPoint();
}
Is this a native class?
Maybe you should implement CPoint as a value-type instad of a class...
Also, while at it, from the wrapper, how can you return a .NET String from
say native function4 that actually returns char*, tchar*, w_char* or
whatever?


..NET only uses System::String as the representation of "strings". This
string is always UNICODE.
To convert from "char", "wchar_t" or "TCHAR" simple return the string or
pass it to the System::String-Constructor:

<code>
System::String *GetString1()
{
char *szString = "Hello world1";
return new System::String( szString);
}
System::String *GetString2()
{
wchar_t *szString = L"Hello world2";
return new System::String( szString);
}
System::String *GetString3()
{
TCHAR *szString = _T("Hello world3");
return new System::String( szString);
}
</code>

--
Greetings
Jochen

My blog about Win32 and .NET
http://blog.kalmbachnet.de/
Nov 17 '05 #5
Thx for your fast reply and thx for the System::String example!

Ok, maybe MyClass is not native but it's unmanaged and it is the actual
definition of the class, which I can't change... it's inside a third party
dll. Anyhow, I have functions in a dll API that return objects of this type,
so how can I deal with it in for example C#?

I can't do like this, right?

In C#:
""""""
using MyWrapperNS; // Access to a MyWrapper type
using MyWrapperNSInte rnalNativeNS; //access to MyClass

MyWrapper myW = new MyWrapper();
MyClass myClass = myWrapper.callN ativeFunction1( );

If not (it doesn't :)), then how do I do?

Thx again Jochen for all help,

/TOmmy

"Jochen Kalmbach [MVP]" <no************ ********@holzma .de> skrev i
meddelandet news:uu******** ******@TK2MSFTN GP15.phx.gbl...
Hi Tommy!
class MyClass
{
public:
...
char* myStr;
CPoint myPoint;
int myInt;
...
CPoint getPoint();
}


Is this a native class?
Maybe you should implement CPoint as a value-type instad of a class...
Also, while at it, from the wrapper, how can you return a .NET String from say native function4 that actually returns char*, tchar*, w_char* or
whatever?


.NET only uses System::String as the representation of "strings". This
string is always UNICODE.
To convert from "char", "wchar_t" or "TCHAR" simple return the string or
pass it to the System::String-Constructor:

<code>
System::String *GetString1()
{
char *szString = "Hello world1";
return new System::String( szString);
}
System::String *GetString2()
{
wchar_t *szString = L"Hello world2";
return new System::String( szString);
}
System::String *GetString3()
{
TCHAR *szString = _T("Hello world3");
return new System::String( szString);
}
</code>

--
Greetings
Jochen

My blog about Win32 and .NET
http://blog.kalmbachnet.de/

Nov 17 '05 #6
Hi Tommy!
Ok, maybe MyClass is not native but it's unmanaged and it is the actual
definition of the class, which I can't change... it's inside a third party
dll. Anyhow, I have functions in a dll API that return objects of this type,
so how can I deal with it in for example C#?

I can't do like this, right?

In C#:
""""""
using MyWrapperNS; // Access to a MyWrapper type
using MyWrapperNSInte rnalNativeNS; //access to MyClass


You can´t access any unmanaged object (in a good way) from a managed
language.

So for your example it looks like the following:

<code>
#pragma unmanaged
class MyClass
{
public:
char* myStr;
CPoint myPoint;
int myInt;
CPoint getPoint() { return CPoint();}
};
#pragma managed
public __gc class MyClassWrapper : public IDisposable
{
public:
MyClassWrapper( )
{
pMyClass = new MyClass();
}
__property System::String *get_MyStr()
{
if (pMyClass == NULL)
throw new System::Invalid OperationExcept ion(S"Object already
disposed!");
if (pMyClass->myStr == NULL)
return 0;
return new System::String( pMyClass->myStr);
}

__property int get_MyInt()
{
if (pMyClass == NULL)
throw new System::Invalid OperationExcept ion(S"Object already
disposed!");
return pMyClass->myInt;
}

__property System::Drawing ::Point get_MyPoint()
{
if (pMyClass == NULL)
throw new System::Invalid OperationExcept ion(S"Object already
disposed!");
return System::Drawing ::Point(pMyClas s->myPoint.x,
pMyClass->myPoint.y);
}
System::Drawing ::Point GetPoint()
{
if (pMyClass == NULL)
throw new System::Invalid OperationExcept ion(S"Object already
disposed!");
CPoint p = pMyClass->getPoint();
return System::Drawing ::Point(p.x, p.y);
}
void Dispose()
{
Dispose(true);
}
private:
~MyClassWrapper ()
{
Dispose(false);
}
void Dispose(bool disposing)
{
if (pMyClass != NULL)
delete pMyClass;
pMyClass = NULL;
if (disposing == true)
System::GC::Sup pressFinalize(t his);
}
MyClass *pMyClass;
};
</code>

--
Greetings
Jochen

My blog about Win32 and .NET
http://blog.kalmbachnet.de/
Nov 17 '05 #7
> So for your example it looks like the following:

<code>
#pragma unmanaged

Hey, wait a minute... this "#pragma unmanaged" is specific for C++/CLI
right...? I only have VS 2003 with Managed Extensions for C++... or is this
valid in VS 2003 too?

class MyClass
{
public:
char* myStr;
CPoint myPoint;
int myInt;
CPoint getPoint() { return CPoint();}
};
#pragma managed

Ok, now the definition of MyClass is in the same file as my wrapper but the
fact is that the unmanaged API functions reside in a DLL (or a .lib). How
can I get access to them?

Do I need to derive from IDisposable? What happens if I don't?

Thx!!!
public __gc class MyClassWrapper : public IDisposable
{
public:
MyClassWrapper( )
{
pMyClass = new MyClass();
}
__property System::String *get_MyStr()
{
if (pMyClass == NULL)
throw new System::Invalid OperationExcept ion(S"Object already
disposed!");
if (pMyClass->myStr == NULL)
return 0;
return new System::String( pMyClass->myStr);
}

__property int get_MyInt()
{
if (pMyClass == NULL)
throw new System::Invalid OperationExcept ion(S"Object already
disposed!");
return pMyClass->myInt;
}

__property System::Drawing ::Point get_MyPoint()
{
if (pMyClass == NULL)
throw new System::Invalid OperationExcept ion(S"Object already
disposed!");
return System::Drawing ::Point(pMyClas s->myPoint.x,
pMyClass->myPoint.y);
}
System::Drawing ::Point GetPoint()
{
if (pMyClass == NULL)
throw new System::Invalid OperationExcept ion(S"Object already
disposed!");
CPoint p = pMyClass->getPoint();
return System::Drawing ::Point(p.x, p.y);
}
void Dispose()
{
Dispose(true);
}
private:
~MyClassWrapper ()
{
Dispose(false);
}
void Dispose(bool disposing)
{
if (pMyClass != NULL)
delete pMyClass;
pMyClass = NULL;
if (disposing == true)
System::GC::Sup pressFinalize(t his);
}
MyClass *pMyClass;
};
</code>

--
Greetings
Jochen

My blog about Win32 and .NET
http://blog.kalmbachnet.de/

Nov 17 '05 #8
Hi Tommy!
<code>
#pragma unmanaged
Hey, wait a minute... this "#pragma unmanaged" is specific for C++/CLI
right...? I only have VS 2003 with Managed Extensions for C++... or is this
valid in VS 2003 too?


It is also valid in VC2003.
By the way: You do not need to set this pragma! I just wanted to show
that this class really can be an unmanaged or native class!
Ok, now the definition of MyClass is in the same file as my wrapper but the
fact is that the unmanaged API functions reside in a DLL (or a .lib). How
can I get access to them?
Äh... whyt should be the problem?
Include the h-File, and add the LIB to your linker settings.
Do I need to derive from IDisposable? What happens if I don't?


An managed class has a non-deterministic life-time!
If you have references to native resources, then you *should* implement
the "IDisposabl e" pattern.
There are only two other ways to overcome this:
1. It does not matter if the native-resource will be freed from a
different thread during finalization
2. You do not allocate a native-resource in the cinstructor; instead you
allocate it on every method and destroy it before you leave the method.

--
Greetings
Jochen

My blog about Win32 and .NET
http://blog.kalmbachnet.de/
Nov 17 '05 #9
Thanx for all the replies but that was not my question. I will explain it a
little bit more.

In my unmanaged library code i had the following three classes with the
following hierarchy

Referenced (class)
Object (abstract class, inheriting from referenced)
Node (class, inheriting from object)

I want to make an managed wrapper for it with the same type of classes. So i
created an managed referenced class, and because this is the base class i
give it the pointer to the unmanaged object referenced.

The object class will be an managed abstract class with no constructor,
because abstract class should not have one. One of the methods of the
unmanaged class is cloneObject which should be implemented by the classes
that are inheriting of the abstract class Node. CloneObject gives as result
an value of the type Object.

So now the problem, i create an managed class Node which implements the
cloneObject method. But how to define the body of this method. Because with
not abstract classes i have created an extra constructor which get the
unmanagedobject en wrapped it. But with an abstract return type this is not
possible.

Hope this gives you more details about my question, and i hope somebody had
an solution for it.

Thanx

WithPit

"WithPit" wrote:
I am trying to create an Managed C++ Wrapper around an unmanaged library
which contains C++ code.

Some of the unmanaged methods returns an returntype which is of the abstract
base type (for example unmanagedObject ). How can i convert this to the
managed abstract basetype?

Hope somebody can help me

Thanx

Nov 17 '05 #10

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

33
3330
by: Chris Capel | last post by:
What is the rationale behind the decision not to allow abstract static class members? It doesn't seem like it's a logically contradictory concept, or that the implementation would be difficult or near-impossible. It seems like it would be useful. In fact, there's a place in my code that I could make good use of it. So why not? Chris
6
5794
by: Dan Sikorsky | last post by:
If we were to define all abstract methods in an abstract class, thereby making that class non-abstract, and then override the heretofore 'abstract' methods in a derived class, wouldn't that remove the need to have abstract class types in C#? Derived classes from abstract base classes must overrided the abstract method defininition anyway,...
3
1941
by: Tommy Svensson \(InfoGrafix\) | last post by:
I've been instructed to work againt a huge unmanaged C++ API from a C# application. Now, the only way, as I've understood it, is to go the Managed Extensions for C++ way. This means I have to write a wrapper between unmanaged API and my managed app. Now on to the question: If there's an unmanaged API class called X with a defined method
3
1796
by: WithPit | last post by:
I am trying to create an managed wrapper but have some problems with it by using abstract classes. In my unmanaged library code i had the following three classes with the following hierarchy Referenced (class) Object (abstract class, inheriting from referenced) Node (class, inheriting from object)
13
5028
by: bonk | last post by:
Hello, I am trying to create a dll that internally uses managed types but exposes a plain unmanaged interface. All the managed stuff shall be "wrapped out of sight". So that I would be able to use that dll from pure unmanaged code (for example inherit from classes in that dll). Is something like that possible. I heared something called...
17
3556
by: baibaichen | last post by:
i have written some code to verify how to disable slicing copy according C++ Gotchas item 30 the follow is my class hierarchy, and note that B is abstract class!! class B { public: explicit B(INT32 i =0):i_(i){} virtual ~B(){}
6
3130
by: Alden Pierre | last post by:
Hello, http://www.parashift.com/c++-faq-lite/virtual-functions.html#faq-20.7 As per the link above it's wise to have a virtual deconstructor when creating an abstract class. Here is when I'm little confused. Am I deleting the right object when I call the virtual deconstructor? I was under impression when creating a class if I'm not...
7
4460
by: jason | last post by:
In the microsoft starter kit Time Tracker application, the data access layer code consist of three cs files. DataAccessHelper.cs DataAcess.cs SQLDataAccessLayer.cs DataAcccessHelper appears to be checking that the correct data type is used DataAcess sets an abstract class and methods
1
2679
by: thedbflow | last post by:
Folks, I have a bit of a quandary I was hoping for some expert guidance on. Keep in mind I am not a C++ developer, but I have worked with the language a bit. I have a native C++ API which I am currently wrapping in managed C++ in order to expose the API to .Net clients. So far, so good, everything is working out just fine. However, I have...
0
7854
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However, people are often confused as to whether an ONU can Work As a Router. In this blog post, we’ll explore What is ONU, What Is Router, ONU & Router’s main...
0
7783
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language...
0
8132
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. ...
1
7878
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For...
0
6533
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then...
0
5349
by: conductexam | last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and then checking html paragraph one by one. At the time of converting from word file to html my equations which are in the word document file was convert...
0
3806
by: adsilva | last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
1
2295
by: 6302768590 | last post by:
Hai team i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated we have to send another system
0
1118
bsmnconsultancy
by: bsmnconsultancy | last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.