I have 3 projects in one solution.
I have :
So when I launch the application all work. But when I push the button "Generer" in my winform wich execute the function NativeMethod::Test() of the C++/CLI that it crash and I have this pop-up message :
An unhandled exception of type 'System.BadImageFormatException' occurred in System.Windows.Forms.dll
Additional information: Could not load file or assembly 'EngineInterfaceWrapper.dll' or one of its dependencies. n'est pas une application Win32 valide. (Exception from HRESULT: 0x800700C1)
When I go in project proprieties in Conf. Properties -> Linker -> Advanced : Target Machine, it's set with the value "MachineX86" for my C++ native and managed DLL and my WinForm is in X86 too. I tired many configurations but it don't work.
Edit:
The problem is may be the header "TradeEngine.h"" in the C++/CLI header : EngineInterfaceWrapper.h. Because when I unlink the native C++ Dll (and deleting all code in the CLI wrapper) if I build the solution it will work but if "#include "TradeEngine.h"" is always in the CLI header, I will have the same error. Do you have an idea?
Edit: --Resolved--
I have finally found the problem. It's the boost library called in my native C++ .h. As the wrapper need to have the native header, it link also the Boost library (even with my pragma in the code, it's strange) and Boost create many problems when is invoked in a managed code so I put the headers from the native .h to the native .cpp and all works. Thank you all for your help me.
Code :
native C++
TradeEngine.h
#ifdef TRADEENGINE_EXPORTS
#define SYMBOL_DECLSPEC __declspec(dllexport)
#define SYMBOL_DEF
#else
#define SYMBOL_DECLSPEC __declspec(dllimport)
#define SYMBOL_DEF __declspec(dllimport)
#endif
#pragma managed(push, off)
#include <curl/curl.h>
#include <boost\filesystem.hpp>
#include <boost\tokenizer.hpp>
#include <boost\lexical_cast.hpp>
#include <boost\thread.hpp>
#pragma managed(pop)
EXTERN_C SYMBOL_DECLSPEC void __stdcall Test(void);
TradeEngine.cpp
SYMBOL_DECLSPEC void __stdcall Test(void)
{
}
C++/CLI
EngineInterfaceWrapper.h
#pragma once
#include "TradeEngine.h"
using namespace System;
using namespace System::Runtime::InteropServices;
namespace EngineInterfaceWrapper {
public ref class NativeMethod
{
public:
static void AjoutColonneDifferenceCourtClotureOuvertureReelle(void);
static void Test();
};
}
EngineInterfaceWrapper.cpp
#pragma region Includes
#include "stdafx.h"
#include "EngineInterfaceWrapper.h"
using namespace EngineInterfaceWrapper;
#include <msclr/marshal.h>
using namespace msclr::interop;
#pragma endregion
void NativeMethod::Test()
{
::Test();
}
C# Winform
Program.cs
namespace TradeInterface
{
static class Program
{
/// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
}
}
}
Form1.cs
generer_Click() is the event launched by the button when the user click on Generer.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;
using EngineInterfaceWrapper;
namespace TradeInterface
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void generer_Click(object sender, EventArgs e)
{
NativeMethod.Test();
}
}
}
I have found the solution :
http://marc.info/?l=boost-users&m=123425857320026
In Configuration Properties -> C/C++ -> Preprocessor -> Preprocessor Definitions add BOOST_ALL_DYN_LINK in order to force the usage of the DLLs. In addition copy the necessary DLLs to the directory where the executable resides. E.g. copy boost_thread-vc90-mt-gd-1_XX.dll to MyApp/bin/Debug.
One reason can be you are trying to load a native 32-bit dll in a 64-bit process. Make sure you have platform target set to x86
in your app to force your application to run inside WoW64.
User contributions licensed under CC BY-SA 3.0