私はC++/CLIデリゲートを試しています(.NETリファレンスライブラリを作成しようとしています)。関数ポインタ(System.AccessViolationException)としてC++/CLIデリゲート
C++/CLIでデリゲートを定義してから、C#でデリゲートのインスタンスを作成し、関数ポインタ経由でアンマネージC++を通じてデリゲートのインスタンスを呼び出します。これはすべて期待通りに機能します。
コードは
using System;
namespace TestProgram
{
class Program
{
static void Main(string[] args)
{
Library.Test.MessageDelegate messageDelegate = new Library.Test.MessageDelegate(Message);
Library.Test test = new Library.Test(messageDelegate);
test.WriteMessage();
Console.Read();
}
static void Message()
{
Console.WriteLine(1024);
}
}
}
次の私のマネージC++ファイル(Managed.cpp)
#include "Unmanaged.hpp"
#include <string>
namespace Library
{
using namespace System;
using namespace System::Runtime::InteropServices;
public ref class Test
{
public:
delegate void MessageDelegate();
internal:
MessageDelegate^ Message;
void* delegatePointer;
public:
Test(MessageDelegate^ messageDelegate)
{
delegatePointer = (void*)Marshal::GetFunctionPointerForDelegate(messageDelegate).ToPointer();
}
void WriteMessage()
{
Unmanaged::WriteMessage(delegatePointer);
}
};
}
そして、私のアンマネージドC++ファイル(Unmanaged.cppを)この(最初に私のC#)を説明するために、
#include "Unmanaged.hpp"
namespace Unmanaged
{
typedef void (*WriteMessageType)();
WriteMessageType WriteMessageFunc;
void WriteMessage(void* Function)
{
WriteMessageType WriteMessageFunc = (WriteMessageType)(Function);
WriteMessageFunc();
}
}
このコードはすべて期待どおりに動作し、メソッド()がdelへの関数ポインタによって呼び出されるため、出力は "1024"です。 egateメソッド。
私の問題は、引数を持つデリゲートを使って同じメソッドを適用しようとすると発生します。デリゲートvoid MessageDelegate(int number);次のように
私のコードは(C#)となりました:私は実行すると
#include "Unmanaged.hpp"
namespace Unmanaged
{
typedef void (*WriteMessageType)(int number);
WriteMessageType WriteMessageFunc;
void WriteMessage(void* Function, int number)
{
WriteMessageType WriteMessageFunc = (WriteMessageType)(Function);
WriteMessageFunc(number);
}
}
:
#include "Unmanaged.hpp"
#include <string>
namespace Library
{
using namespace System;
using namespace System::Runtime::InteropServices;
public ref class Test
{
public:
delegate void MessageDelegate(int number);
internal:
MessageDelegate^ Message;
void* delegatePointer;
public:
Test(MessageDelegate^ messageDelegate)
{
delegatePointer = (void*)Marshal::GetFunctionPointerForDelegate(messageDelegate).ToPointer();
}
void WriteMessage(int number)
{
Unmanaged::WriteMessage(delegatePointer, number);
}
};
}
そして、私のアンマネージドC++ファイル:
using System;
namespace AddProgram
{
class Program
{
static void Main(string[] args)
{
Library.Test.MessageDelegate messageDelegate = new Library.Test.MessageDelegate(Message);
Library.Test test = new Library.Test(messageDelegate);
test.WriteMessage(1024);
Console.Read();
}
static void Message(int number)
{
Console.WriteLine(number);
}
}
}
私はC++のファイルを管理しますプログラムに次のエラーが表示されます:
未処理のライブラリ "System.AccessViolationException"の未処理の例外が発生しました。
追加情報:保護されたメモリを読み書きしようとしました。これはしばしば、他のメモリが壊れていることを示します。
ちなみに、コンソールウィンドウには1024が表示されますが、ランダムなint(〜1000000)が続き、エラーが表示されます。
私はこのエラーが発生する理由のいくつかを想像し始めることができますが、わかりませんし、見つけにくいです。なぜこのエラーが出るのか誰にでも教えてもらえれば、それを修正するために何ができるのでしょうか、私は大いに感謝します。
よく質問された質問 –