473,806 Members | 2,967 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

UINT16 error

I am trying to create a managed c++ wrapper and have run into a problem is
when SetNewNetworkCa llBack is run. It doesn't like that NetworkID isn't an
UInt16. I get the error:

CCommManager::S etNewNetworkCal lBack' : cannot convert parameter 1 from 'void
(unsigned short,void *)' to 'void (__cdecl *)(UInt16,void *)'

Any help would be appreicated. Offending code is below.

James
Managed Code:

CCommApp::CComm App(char chan, long baud, String * ServerAddress, int
ListenPort, bool Logging)
{
m_pComm->SetNewNetworkC allBack(NewNetw ork, this); //Problem
line
}

void CCommApp::NewNe twork(unsigned short NetworkID, void *Parameter)

Unmanaged Code Header:

void SetNewNetworkCa llBack(void(*Ne wNetworkCallBac k)(UInt16 NetworkID, void*
Parameter), void* Parameter);
Nov 17 '05 #1
11 1719
On Tue, 20 Sep 2005 11:04:33 -0400, "James Crouch"
<ja**********@w pafb.af.mil> wrote:
I am trying to create a managed c++ wrapper and have run into a problem is
when SetNewNetworkCa llBack is run. It doesn't like that NetworkID isn't an
UInt16. I get the error:

CCommManager:: SetNewNetworkCa llBack' : cannot convert parameter 1 from 'void
(unsigned short,void *)' to 'void (__cdecl *)(UInt16,void *)'

Any help would be appreicated. Offending code is below.

James
Managed Code:

CCommApp::CCom mApp(char chan, long baud, String * ServerAddress, int
ListenPort, bool Logging)
{
m_pComm->SetNewNetworkC allBack(NewNetw ork, this); //Problem
line
}

void CCommApp::NewNe twork(unsigned short NetworkID, void *Parameter)

Unmanaged Code Header:

void SetNewNetworkCa llBack(void(*Ne wNetworkCallBac k)(UInt16 NetworkID, void*
Parameter), void* Parameter);


This has got nothing to do with managed vs unmanaged code or UINT16.
Apparently NewNetwork is a non-static member function, and VC7.1 is not
only allowing the illegal syntax for referring to it in your
SetNewNetworkCa llBack call, it's emitting a misleading error message which
implies it's a static member. IIRC, VC8 fixes the syntax problem, so the
bare "NewNetwork " reference will be disallowed; instead, you'll have to use
&CCommApp::NewN etwork to form a pointer to member. In any case, the
solution is to make NewNetwork static.

P.S. It would be useful in the future to include the complete text of the
error message, including error number, and to abstract the problem into a
simple console program. For example (removing all the managed stuff doesn't
affect the error message):

#using <mscorlib.dll >
using namespace System;

#pragma unmanaged

void f(void (*)(unsigned short))
{
}

#pragma managed

struct X
{
void g(unsigned short)
{
}

void h()
{
f(g);
}
};

int main()
{
}

C>ccr k.cpp
Microsoft (R) C/C++ Optimizing Compiler Version 13.10.3077 for .NET
Framework
Copyright (C) Microsoft Corporation 1984-2002. All rights reserved.

k.cpp
k.cpp(20) : error C2664: 'f' : cannot convert parameter 1 from 'void
(unsigned short)' to 'void (__cdecl *)(unsigned short)'
None of the functions with this name in scope match the target type

--
Doug Harrison
VC++ MVP
Nov 17 '05 #2
James Crouch wrote:
I am trying to create a managed c++ wrapper and have run into a problem is
when SetNewNetworkCa llBack is run. It doesn't like that NetworkID isn't an
UInt16. I get the error:

CCommManager::S etNewNetworkCal lBack' : cannot convert parameter 1 from 'void
(unsigned short,void *)' to 'void (__cdecl *)(UInt16,void *)'

Any help would be appreicated. Offending code is below.

James
Managed Code:

CCommApp::CComm App(char chan, long baud, String * ServerAddress, int
ListenPort, bool Logging)
{
m_pComm->SetNewNetworkC allBack(NewNetw ork, this); //Problem
line
}

void CCommApp::NewNe twork(unsigned short NetworkID, void *Parameter)

Unmanaged Code Header:

void SetNewNetworkCa llBack(void(*Ne wNetworkCallBac k)(UInt16 NetworkID, void*
Parameter), void* Parameter);


Is CCommApp::NewNe twork static? The NewNetworkCallB ack prototype
requires that the function is non-member or at least static. Just move
the NewNetwork function outside of the CComApp class, it doesn't belong
there.

Also check that UInt16 is exactly the same type as unsigned short
(better to rename Uint16 to unsigned short), and the calling conventions
must match too (both __stdcall or __cdecl, better to specify it explicitly).

Tom
Nov 17 '05 #3
James Crouch wrote:

If I see it correctly, you're passing a managed method as an unmanaged
pointer. That's not going to work. You have to write a global unmanaged
function (in MC++ or C++/CLI) that calls back to the managed code, and
pass this intermediate function to the unmanaged API. There's no way you
can pass a managed callback to an unmanaged library without this
intermediate layer.

Also, you can't pass a managed void* to the unmanaged part either, at
least not without pinning it.

Tom
Nov 17 '05 #4
>
This has got nothing to do with managed vs unmanaged code or UINT16.
Apparently NewNetwork is a non-static member function, and VC7.1 is not
only allowing the illegal syntax for referring to it in your
SetNewNetworkCa llBack call, it's emitting a misleading error message which
implies it's a static member. IIRC, VC8 fixes the syntax problem, so the
bare "NewNetwork " reference will be disallowed; instead, you'll have to
use
&CCommApp::NewN etwork to form a pointer to member. In any case, the
solution is to make NewNetwork static.

P.S. It would be useful in the future to include the complete text of the
error message, including error number, and to abstract the problem into a
simple console program. For example (removing all the managed stuff
doesn't
affect the error message):

#using <mscorlib.dll >
using namespace System;

#pragma unmanaged

void f(void (*)(unsigned short))
{
}

#pragma managed

struct X
{
void g(unsigned short)
{
}

void h()
{
f(g);
}
};

int main()
{
}

C>ccr k.cpp
Microsoft (R) C/C++ Optimizing Compiler Version 13.10.3077 for .NET
Framework
Copyright (C) Microsoft Corporation 1984-2002. All rights reserved.

k.cpp
k.cpp(20) : error C2664: 'f' : cannot convert parameter 1 from 'void
(unsigned short)' to 'void (__cdecl *)(unsigned short)'
None of the functions with this name in scope match the target type

--
Doug Harrison
VC++ MVP


Thanks for the info and advice. But how do I go about creating that pointer
to member? Thanks.

James
Nov 17 '05 #5
I've pulled the NewNetwork method out and made it global which solved my
inital problem. Now however, I an error while trying to pass "this" to
NewNetwork. The "void *Parameter" is an echo of SetNewNetworkCa llBack's
"this". Do I need to do some pinning and if so how?

Thanks.

James

"Tamas Demjen" <td*****@yahoo. com> wrote in message
news:Ot******** ******@TK2MSFTN GP12.phx.gbl...
James Crouch wrote:

If I see it correctly, you're passing a managed method as an unmanaged
pointer. That's not going to work. You have to write a global unmanaged
function (in MC++ or C++/CLI) that calls back to the managed code, and
pass this intermediate function to the unmanaged API. There's no way you
can pass a managed callback to an unmanaged library without this
intermediate layer.

Also, you can't pass a managed void* to the unmanaged part either, at
least not without pinning it.

Tom

Nov 17 '05 #6
James Crouch wrote:
I've pulled the NewNetwork method out and made it global which solved my
inital problem. Now however, I an error while trying to pass "this" to
NewNetwork. The "void *Parameter" is an echo of SetNewNetworkCa llBack's
"this". Do I need to do some pinning and if so how?

Thanks.

James


You probably figured out that I replied without noticing James' post.

Well, I believe you're taking chances if you don't pin the "this". What
happens is that you pass the managed handle "this" to an unmanaged code,
which will in turn call back to the managed code passing back the
"this". The problem is that the .NET framework may move data around in
the memory in the meantime. I don't know how safe it is to pass a GC
handle to an unmanaged code, which passes the same handle back to
managed code. When you convert the GC handle into unmanaged void*, you
essentially store its internal representation (IntPtr). If the GC
decides to compact the heap, small objects may be moved around in the
memory, unless they are pinned. Now what happens if your "this" handle
is moved around while your unmanaged code is being executed? My rule of
thumb is to never get an IntPtr for a managed object without first
pinning it.

Can anybody confirm this?

Tom
Nov 17 '05 #7
I was curious how to do this, and worked out two very simple examples.
This is how I would implement a C-callback in managed C++ code. I
couldn't find anything that allowed a managed function to be passed
directly to an unmanaged call (first I couldn't convert between void*
and the managed type, second I couldn't convert between __clrcall and
__cdecl functions). So I had to introduced the intermediate class
"Bridge". gcroot<> is a wrapper for GCHandle, which allows us to store a
managed handle in a native class. It also ensures that the managed class
is pinned, so the garbage collector doesn't move around the "c" object
while the native code is running. After the native "Process" is done,
the bridge goes out of scope, so the pin gets released.

//////////////////////////////////////////////////////////////////
// For MC++:
#include "stdafx.h"
#include <vcclr.h>

#using <mscorlib.dll >

using namespace System;

typedef void (*Callback)(voi d* param);

void Process(Callbac k callback, void* param)
{
if(callback) callback(param) ;
}

__gc class C
{
public:
void ProcessMe();
void OnProcess() // the callback implementation
{
Console::WriteL ine(S"OnProcess ");
}
};

class Bridge
{
public:
Bridge(C* in) : c(in) { }
static void ForwardOnProces s(void* param)
{ static_cast<Bri dge*>(param)->c->OnProcess(); }
private:
gcroot<C*> c;
};

void C::ProcessMe()
{
Bridge b(this);
::Process(&Brid ge::ForwardOnPr ocess, &b);
}

int _tmain()
{
C* c = new C;
c->ProcessMe();
return 0;
}
//////////////////////////////////////////////////////////////////
// For C++/CLI:
#include "stdafx.h"
#include <vcclr.h>

using namespace System;

typedef void (*Callback)(voi d* param);

void Process(Callbac k callback, void* param)
{
if(callback) callback(param) ;
}

ref class C
{
public:
void ProcessMe();
void OnProcess() // the callback implementation
{
Console::WriteL ine(L"OnProcess ");
}
};

class Bridge
{
public:
Bridge(C^ in) : c(in) { }
static void ForwardOnProces s(void* param)
{ static_cast<Bri dge*>(param)->c->OnProcess(); }
private:
gcroot<C^> c;
};

void C::ProcessMe()
{
Bridge b(this);
::Process(&Brid ge::ForwardOnPr ocess, &b);
}

int main(array<Syst em::String^>^ args)
{
C^ c = gcnew C;
c->ProcessMe();
return 0;
}

Tom
Nov 17 '05 #8
IMO it's more flexible when using (typesafe) delegates...

#pragma unmanaged
class Unmanaged
{
public:
void Process( void (__stdcall *ptr) (int))
{
int i = 10;
if(ptr != 0)
ptr(i);
}
};

// managed code from here
#pragma managed
public __gc class C
{
public:
static C* m_pClass = 0;
__delegate void CbckProc(int v);
private:
// private inner non GC class used as thunk to callback into managed code
__nogc class _C
{
// private:
public:
static void __stdcall CallbackProc(in t v)
{
m_pClass->m_cbProc->Invoke(v); // Invoke delegate target
}
};

public:
C() { m_pClass = this; }
~C() { m_pClass = 0; }
//Managed callback
void OnProcess(int i)
{
System::Console ::WriteLine(__b ox(i));
}
void ProcessMe()
{
m_cbProc = new CbckProc(this, &C::OnProces s);
Unmanaged* n = new Unmanaged();
n->Process(_C::Ca llbackProc);
}
CbckProc* m_cbProc;
private:
_C* m_c;
};

int main()
{
C* c = new C();
c->ProcessMe();
}

Willy.

"Tamas Demjen" <td*****@yahoo. com> wrote in message
news:u4******** ******@TK2MSFTN GP10.phx.gbl...
I was curious how to do this, and worked out two very simple examples. This
is how I would implement a C-callback in managed C++ code. I couldn't find
anything that allowed a managed function to be passed directly to an
unmanaged call (first I couldn't convert between void* and the managed
type, second I couldn't convert between __clrcall and __cdecl functions).
So I had to introduced the intermediate class "Bridge". gcroot<> is a
wrapper for GCHandle, which allows us to store a managed handle in a native
class. It also ensures that the managed class is pinned, so the garbage
collector doesn't move around the "c" object while the native code is
running. After the native "Process" is done, the bridge goes out of scope,
so the pin gets released.

//////////////////////////////////////////////////////////////////
// For MC++:
#include "stdafx.h"
#include <vcclr.h>

#using <mscorlib.dll >

using namespace System;

typedef void (*Callback)(voi d* param);

void Process(Callbac k callback, void* param)
{
if(callback) callback(param) ;
}

__gc class C
{
public:
void ProcessMe();
void OnProcess() // the callback implementation
{
Console::WriteL ine(S"OnProcess ");
}
};

class Bridge
{
public:
Bridge(C* in) : c(in) { }
static void ForwardOnProces s(void* param)
{ static_cast<Bri dge*>(param)->c->OnProcess(); }
private:
gcroot<C*> c;
};

void C::ProcessMe()
{
Bridge b(this);
::Process(&Brid ge::ForwardOnPr ocess, &b);
}

int _tmain()
{
C* c = new C;
c->ProcessMe();
return 0;
}
//////////////////////////////////////////////////////////////////
// For C++/CLI:
#include "stdafx.h"
#include <vcclr.h>

using namespace System;

typedef void (*Callback)(voi d* param);

void Process(Callbac k callback, void* param)
{
if(callback) callback(param) ;
}

ref class C
{
public:
void ProcessMe();
void OnProcess() // the callback implementation
{
Console::WriteL ine(L"OnProcess ");
}
};

class Bridge
{
public:
Bridge(C^ in) : c(in) { }
static void ForwardOnProces s(void* param)
{ static_cast<Bri dge*>(param)->c->OnProcess(); }
private:
gcroot<C^> c;
};

void C::ProcessMe()
{
Bridge b(this);
::Process(&Brid ge::ForwardOnPr ocess, &b);
}

int main(array<Syst em::String^>^ args)
{
C^ c = gcnew C;
c->ProcessMe();
return 0;
}

Tom

Nov 17 '05 #9
Willy Denoyette [MVP] wrote:
IMO it's more flexible when using (typesafe) delegates...
Good idea, thanks Willy.
// private inner non GC class used as thunk to callback into managed code
__nogc class _C


VC++ 2005 doesn't allow me to define an unmanaged class in a managed one:

ref class Managed
{
private:
class Unmanaged
{
};
};

error C2814: 'Managed::Unman aged' : a native type cannot be nested
within a managed type 'Managed'

Tom
Nov 17 '05 #10

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

Similar topics

2
2167
by: boki | last post by:
Dear All, I knew "&apple" could get the address of apple variable, about why we use a (UINT16 *) command before "&apple" ? What is this function for? Thank you very much for your help.
3
1618
by: Norman | last post by:
I have a collection that can have a reference to various types of arrays. String was easy: ... string sPropertyArray = (string)oReturn; foreach( string sItem in sPropertyArray ) { ...
1
12055
by: rawCoder | last post by:
Hi, Ok this shud b simple but i cant seem to find it. I want to convert a System.UInt16 data to 2 Byte array and System.UInt32 data to 4 Byte array ( BigEndian) something like Public Sub GetBytes(ByVal n as System.UInt16, ByRef b As Byte()) 'Converts the System.UInt16 to a 2 Byte array
6
8236
by: barcaroller | last post by:
I'm looking for a hash function (in C) that will convert a string of arbitrary length (but less than 1024 chars) to a reasonably-unique 16-bit short integer. Can anyone point me to such a hash function?
5
4454
by: Sakharam Phapale | last post by:
Hi All, I am using Microsoft Speech DLL "sapi.dll". I want to use following method of "SpeechLib.SpStream" object (following is a signature which I copied from Quick Info feature of .NET code editor) Public Overridable Overloads Sub BindToFile (Byref pszFileName as System.UInt16 ,eMode as SpeechLib.SPFILEMODE ,ByRef pFormatId as System.Guid ,ByRef pWaveFormatEx as SpeechLib.WaveFormatEx, ullEventInterest as
4
6174
by: Mark Hollander | last post by:
Hi, Is there an easier way to convert a UInt16 to Int16 than the way I am currently doing it Dim iValue As Int16 Dim uValue As UInt16 Try uValue = GetValue(WMI.NetworkAdapter, "Availability") iValue = CType(uValue.ToString, Int16)
1
17066
by: dissectcode | last post by:
Hello - I am looking at a scanf function that takes in a 16 bit unsigned int(UINT16), but its format specifier is %hd. According to http://publib.boulder.ibm.com/infocenter/comphelp/v8v101/index.jsp?topic=/com.ibm.xlcpp8a.doc/standlib/ref/printconversionspecifiers.htm that specifier is for a short int, so won't I lose precision here? Also - %hd is for base 8. I am confused about bases. Is UInt16 base 16 or how does that work?? ...
5
5430
by: | last post by:
Hi group, Is there an easy way to convert a UInt16 value in to a string which presents it in a binary format. I need a conversion with a fixed length. so 6 must be presented as '0000000000000110' Any help or code examples would be higly appreciated. Thanks a lot in advance,
1
3756
by: Slaunger | last post by:
Hi, This is my first post here, I am looking forward to being here. I have actually posted almost the same question on comp.lang.python: http://groups.google.dk/group/comp.lang.python/browse_thread/thread/2f0e7ee3ad76d5a3/e2eae3719c6e3fe8?hl=en#e2eae3719c6e3fe8 and got some hints at what i could do, but it is a little bit too complicated for me (yet), and i was wondering if there is a simpler way to do this.
0
9597
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 synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
10620
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. Here is my compilation command: g++-12 -std=c++20 -Wnarrowing bit_field.cpp Here is the code in...
0
10369
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that captivates audiences and drives business growth. The Art of Business Website Design Your website is...
0
10110
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each protocol has its own unique characteristics and advantages, but as a user who is planning to build a smart home system, I am a bit confused by the choice of these technologies. I'm particularly interested in Zigbee because I've heard it does some...
0
9187
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 launch it, all on its own.... Now, this would greatly impact the work of software developers. The idea...
0
6877
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 into image. Globals.ThisAddIn.Application.ActiveDocument.Select();...
0
5546
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
0
5682
by: adsilva | last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
3
3008
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 effective websites that not only look great but also perform exceptionally well. In this comprehensive...

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.