Click here to Skip to main content
15,867,568 members
Please Sign up or sign in to vote.
1.00/5 (1 vote)
See more:
Hi All ,

Could you please let me know How to pass a datacontract from a C#/WCF code (application) to C++/CLI code method.


From C# code i can pass a data contract, but at managed (C++/CLI) code side how can I receive that data contract as a parameter?

Please explain me with some examples.


in other words what is the equvialent of datacontract in managed C++ , so that i can pass it to the method as a parameter which can be called from C#.


////////

in C# application, i have some code like this
SubscriptionDataContract subscriptionData = null;
subscriptionData = new SubscriptionDataContract();

From C# code application , I need to call the below method in Managed C++ (C++/CLI)
in which i want to pass the above data contact.

ClientSideWrapper.ClientInterface iClient = new ClientSideWrapper.ClientInterface();

iClient.sendMessage(handle,subscriptionData);


I need to create a method in Managed C++ (C++/CLI) , so that i can pass that datacontract (details) from C# to Managed C++ code and do the required processing.


But it seems Managed C++ will not take datacontract as i am getting the below error:
with this function in Manged C++ .


EXPORT_VOID sendMessage(handle_t binding,DataContracts::NotificationDataContract^ dc);


error C3395: 'sendMessage' : __declspec(dllexport) cannot be applied to a function with the __clrcall calling convention


Please let me know how to handle this scenario.

Appreciate your help.

Thanks,
Sudhakar
Posted
Updated 22-Apr-15 19:48pm
v6
Comments
Sergey Alexandrovich Kryukov 22-Apr-15 9:33am    
At this time, there is no such thing as "Managed C++". C++/CLI is essentially different thing. :-)
The "problem" is not clear. There is no a problem of C++/CLI working with data contract.
—SA
Member 3975629 23-Apr-15 1:45am    
in C# application, i have some code like this
SubscriptionDataContract subscriptionData = null;
subscriptionData = new SubscriptionDataContract();

From C# code application , I need to call the below method in Managed C++ (C++/CLI)
in which i want to pass the above data contact.

ClientSideWrapper.ClientInterface iClient = new ClientSideWrapper.ClientInterface();

iClient.sendMessage(handle,subscriptionData);


I need to create a method in Managed C++ (C++/CLI) , so that i can pass that datacontract (details) from C# to Managed C++ code and do the required processing.


But it seems Managed C++ will not take datacontract as parameter , as i am getting the below error:
with this function in Manged C++ .


EXPORT_VOID sendMessage(handle_t binding,DataContracts::NotificationDataContract^ dc);


error C3395: 'sendMessage' : __declspec(dllexport) cannot be applied to a function with the __clrcall calling convention


Please let me know how to handle this scenario.

Appreciate your help.

Thanks,
Sudhakar

1 solution

Please see my comment to the question.

Data contract cannot be passed as a parameters. Data contract is the conceptual structure expressed as a combination of some set of related data types and some data contract attributes over those types and members; more exactly, this is some invariant of that set of types: when you change it but the types and the members marked as the part of contract remains the same and keep their structural relationships, the contract remains the same despite of the change in the type set. This way, this can be the invariant of some product's life time, or even some data standard.

As you can see, this is all pure metadata, which is pretty hard to express as data (but possible). This is not what you pass "as a parameter".

Serialization based on data contract takes any object graph created with the contract (in general case, not even necessarily a tree, any arbitrary graph) and comprehensively serialize it into any stream. Later on, this stream can be deserialized back to the object graph, a memory structure logically identically to the original object graph.

Please see:
Using Data Contracts:
https://msdn.microsoft.com/en-us/library/ms733127%28v=vs.110%29.aspx
.

Therefore, each time, each instance of the data is represented either as a data graph, or a stream content; and these representations are mutually reversible and comprehensive. And yes, the reference to a stream or to a graph can be passed anywhere where a reference remains valid, so there is no such problem.

If you have some related problems, feel free to ask your follow-up questions.

—SA
 
Share this answer
 
Comments
Member 3975629 23-Apr-15 1:44am    
in C# application, i have some code like this
SubscriptionDataContract subscriptionData = null;
subscriptionData = new SubscriptionDataContract();

From C# code application , I need to call the below method in Managed C++ (C++/CLI)
in which i want to pass the above data contact.

ClientSideWrapper.ClientInterface iClient = new ClientSideWrapper.ClientInterface();

iClient.sendMessage(handle,subscriptionData);


I need to create a method in Managed C++ (C++/CLI) , so that i can pass that datacontract (details) from C# to Managed C++ code and do the required processing.


But it seems Managed C++ will not take datacontract as parameter as i am getting the below error:
with this function in Manged C++ .


EXPORT_VOID sendMessage(handle_t binding,DataContracts::NotificationDataContract^ dc);


error C3395: 'sendMessage' : __declspec(dllexport) cannot be applied to a function with the __clrcall calling convention


Please let me know how to handle this scenario.

Appreciate your help.

Thanks,
Sudhakar
Sergey Alexandrovich Kryukov 23-Apr-15 9:48am    
All wrong. 1) it is not related to data contract; 2) dllexport is related to unmanaged code; 3) there is no such thing as "managed C++". You are mixing up all things together.
—SA
Member 3975629 24-Apr-15 5:05am    
Hi ,

Sorry for the confusion. My requirement is: I have a data contract as follows.it has another 2 data contracts inside it. which contains the values as objects,list etc...
Now i need to call a native C++ method from C# and pass this datacontract to the native c++. here my question is how can i manage the the passing of the below data contract to native C++ method .How to handle this datacontract inside C++ ??

I would like to have the method some thing like this:
EXPORT_VOID sendSubscriptions(handle_t binding_h, SubscriptionDataContract dc );


My Datacontract(s)-nested data contracts are as below:

I think i can use struct inside C++ , which is equivalent to data contract in C#.
but how to handle data members like this in C++ : object BaseObjectType

[DataContract(Name = "TopicDetails")]

public class TopicDetails
{
protected object topic;

protected object baseObjectType;

[DataMember]
public object BaseObjectType
{
get
{
return baseObjectType;
}
set
{
baseObjectType = value;
}
}

[DataMember]
public object TopicID
{
get
{
return topic;
}
set
{
topic = value;
}
}

static public TopicDetails CreateTopic<t, mt="">(IComparable<t> objectType, IComparable<mt> objectID)
{
var topicDetails = new TopicDetails();
topicDetails.BaseObjectType = objectType;
topicDetails.TopicID = objectID;
return topicDetails;

}

}

[DataContract(Name = "SubscriptionTopic")]
[KnownType(typeof(List<topicdetails>))]
public class SubscriptionTopic
{
private object topic;
private object target;
private object creator;

[DataMember]
public object Topic
{
get
{
return topic;
}
set
{
topic = value;
}
}

[DataMember]
public object Target
{
get
{
return target;
}
set
{
target = value;
}
}

[DataMember]
public object DBHandle
{
get
{
return creator;
}
set
{
creator = value;
}
}
static public SubscriptionTopic CreateSubscriptions<t, mt,="" nt="">(IList<topicdetails> topic, IComparable<mt> target, IComparable<nt> handle)
{
var subscriptionTopic = new SubscriptionTopic();

subscriptionTopic.Target = target;
subscriptionTopic.Topic = topic;
subscriptionTopic.DBHandle = handle;

return subscriptionTopic;
}

}

[DataContract(Name = "SubscriptionData")]
[KnownType(typeof(List<subscriptiontopic>))]
public class SubscriptionDataContracts : IExtensibleDataObject
{
private ExtensionDataObject extensionDataObjectValue;

[DataMember]
public string UserID
{
get;
set;

}

[DataMember]
public string ProjectID
{
get;
set;

}

[DataMember]
public string FromDiscipline
{
get;
set;

}

[DataMember]
public string ModuleID
{
get;
set;

}

[DataMember]
public string SessionID
{
get;
set;

}

[DataMember]
public List<subscriptiontopic> TopicList
Sergey Alexandrovich Kryukov 24-Apr-15 9:39am    
Sorry, the code in comment is not readable enough to read it; you should have put it in the body of the question, and in a shortened version. Why would you ever do such a tricky stuff as interop with unmanaged C++? This is really hard to do.
—SA
Member 3975629 24-Apr-15 5:10am    
Hi ,

Sorry for the confusion. My requirement is: I have a data contract as follows.it has another 2 data contracts inside it. which contains the values as objects,list etc...
Now i need to call a native C++ method from C# and pass this datacontract to the native c++. here my question is how can i manage the the passing of the below data contract to native C++ method .How to handle this datacontract inside C++ ??

I would like to have the method some thing like this:
EXPORT_VOID sendSubscriptions(handle_t binding_h, SubscriptionDataContract dc );


My Datacontract(s)-nested data contracts are as below:

I think i can use struct inside C++ , which is equivalent to data contract in C#.
but how to handle data members like this in C++ : object BaseObjectType

[DataContract(Name = "TopicDetails")]

public class TopicDetails
{
protected object topic;

protected object baseObjectType;

[DataMember]
public object BaseObjectType
{
get
{
return baseObjectType;
}
set
{
baseObjectType = value;
}
}

[DataMember]
public object TopicID
{
get
{
return topic;
}
set
{
topic = value;
}
}

static public TopicDetails CreateTopic<t, mt="">(IComparable<t> objectType, IComparable<mt> objectID)
{
var topicDetails = new TopicDetails();
topicDetails.BaseObjectType = objectType;
topicDetails.TopicID = objectID;
return topicDetails;

}

}

[DataContract(Name = "SubscriptionTopic")]
[KnownType(typeof(List<topicdetails>))]
public class SubscriptionTopic
{
private object topic;
private object target;
private object creator;

[DataMember]
public object Topic
{
get
{
return topic;
}
set
{
topic = value;
}
}

[DataMember]
public object Target
{
get
{
return target;
}
set
{
target = value;
}
}

[DataMember]
public object DBHandle
{
get
{
return creator;
}
set
{
creator = value;
}
}
static public SubscriptionTopic CreateSubscriptions<t, mt,="" nt="">(IList<topicdetails> topic, IComparable<mt> target, IComparable<nt> handle)
{
var subscriptionTopic = new SubscriptionTopic();

subscriptionTopic.Target = target;
subscriptionTopic.Topic = topic;
subscriptionTopic.DBHandle = handle;

return subscriptionTopic;
}

}

[DataContract(Name = "SubscriptionData")]
[KnownType(typeof(List<subscriptiontopic>))]
public class SubscriptionDataContracts : IExtensibleDataObject
{
private ExtensionDataObject extensionDataObjectValue;

[DataMember]
public string UserID
{
get;
set;

}

[DataMember]
public string ProjectID
{
get;
set;

}

[DataMember]
public string FromDiscipline
{
get;
set;

}

[DataMember]
public string ModuleID
{
get;
set;

}

[DataMember]
public string SessionID
{
get;
set;

}

[DataMember]
public List<subscriptiontopic> TopicList
{

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900