PInvoke和非托管DLL调用

PInvoke和非托管DLL调用

问题描述:

有没有人使用PKWare的PKCDL.DLL进行内爆和爆炸

功能?


我已经能够成功定义一切正确甚至

让调用函数(Explode)正常运行。这意味着数据正在被正确爆炸,通过CRC值确认并查看

实际数据。


但是在此之前非托管函数退出,我得到一个null异常

错误。我正在使用:


ReadHandler rh = new ReadHandler(this.ReadData);

WriteHandler wh = new WriteHandler(this.WriteData);


IntPtr buffer = Marshal.AllocHGlobal(bufferSize)

尝试{

对象数据=此;


//在这里调用DLL ...

PkCdl.Explode(rh,wh,buffer,ref data);


} finally {

Marshal.FreeHGlobal(缓冲区);

}


为DLL分配所需的缓冲区。在相应的

ReadData / WriteData回调方法中,我使用Marshal.Copy()方法将
数据移入/移出托管内存。


现在在某个地方,一个异常发生在

try..finally(如上所示)。


如果这响了钟声与任何人一起,我很乐意提供完整的样品

代码,并且更愿意听到你的想法。

谢谢,

Joe Martin


***通过开发人员指南 http:// www。 developersdex.com ***

不要只是参加USENET ......获得奖励!

Has anyone made use of PKWare''s PKCDL.DLL for the Implode and Explode
functions?

I have been able to successfully define everything correctly and even
get the invoked function (Explode) to run properly. This means data is
being exploded properly, confirmed with CRC values and reviewing the
actual data.

However just before the unmanaged function exits, I get a null exception
error. I am using:

ReadHandler rh = new ReadHandler(this.ReadData);
WriteHandler wh = new WriteHandler(this.WriteData);

IntPtr buffer = Marshal.AllocHGlobal(bufferSize)
try {
object data = this;

// Invoke DLL here...
PkCdl.Explode(rh, wh, buffer, ref data);

} finally {
Marshal.FreeHGlobal(buffer);
}

to allocate the needed buffer for the DLL. In the corresponding
ReadData/WriteData callback methods, I use the Marshal.Copy() methods to
move data in/out of managed memory.

Now somewhere along the way an the exception happens inside the
try..finally (shown above).

If this rings a bell with anyone, I will gladly supply complete sample
code and would be more than interested in hearing your thoughts.
Thanks,
Joe Martin

*** Sent via Developersdex http://www.developersdex.com ***
Don''t just participate in USENET...get rewarded for it!

Joe Martin写道:
Joe Martin wrote:
ReadHandler rh = new ReadHandler(this.ReadData);
WriteHandler wh = new WriteHandler(this.WriteData);

IntPtr buffer = Marshal.AllocHGlobal(bufferSize)
尝试{
对象数据=这个;

//在这里调用DLL ...
PkCdl.Explode(rh,wh,buffer,ref data);

}最后{
Marshal.FreeHGlobal(缓冲区);
}
ReadHandler rh = new ReadHandler(this.ReadData);
WriteHandler wh = new WriteHandler(this.WriteData);

IntPtr buffer = Marshal.AllocHGlobal(bufferSize)
try {
object data = this;

// Invoke DLL here...
PkCdl.Explode(rh, wh, buffer, ref data);

} finally {
Marshal.FreeHGlobal(buffer);
}




你必须固定rh和wh,否则他们是GC。


....

}终于{

Marshal.FreeHGlobal(缓冲区);

}

GC.KeepAlive(rh);

GC.KeepAlive(wh);

再见

Rob



you have to pin "rh" and "wh", otherwise they are GCed.

....
} finally {
Marshal.FreeHGlobal(buffer);
}
GC.KeepAlive(rh);
GC.KeepAlive(wh);
bye
Rob


>你必须将rh固定为rh。和wh,否则他们是GCed。
>you have to pin "rh" and "wh", otherwise they are GCed.

...
}终于{
Marshal.FreeHGlobal(缓冲区);
}
GC.KeepAlive(rh);
GC.KeepAlive(wh);

...
} finally {
Marshal.FreeHGlobal(buffer);
}
GC.KeepAlive(rh);
GC.KeepAlive(wh);



运行时将保持参数在
$期间保持活动状态b $ b电话。只有当

回调是异步时,才需要手动保持代表生存。如果他们是,那么GC.KeepAlive将不会帮助你



Mattias


-

Mattias Sj?gren [MVP] mattias @ mvps.org
http://www.msjogren.net/dotnet/ | http://www.dotnetinterop.com

请回复到新闻组。


The runtime will keep the parameters alive for the duration of the
call. Manually keeping the delegates alive is only necessary when the
callbacks are asynchronous. And if they are, GC.KeepAlive wont help
you.

Mattias

--
Mattias Sj?gren [MVP] mattias @ mvps.org
http://www.msjogren.net/dotnet/ | http://www.dotnetinterop.com
Please reply only to the newsgroup.


Mattias Sj?gren写道:
Mattias Sj?gren wrote:
你必须固定; RH"和wh,否则他们是GCed。

...
}终于{
Marshal.FreeHGlobal(缓冲区);
}
GC .KeepAlive(rh);
GC.KeepAlive(wh);
you have to pin "rh" and "wh", otherwise they are GCed.

...
} finally {
Marshal.FreeHGlobal(buffer);
}
GC.KeepAlive(rh);
GC.KeepAlive(wh);



运行时将在
调用期间保持参数处于活动状态。只有当
回调是异步时,才需要手动保持代表处于活动状态。如果他们是,GC.KeepAlive将不会帮助你。



The runtime will keep the parameters alive for the duration of the
call. Manually keeping the delegates alive is only necessary when the
callbacks are asynchronous. And if they are, GC.KeepAlive wont help
you.




好​​的。我知道了。我有一个案例,代表们必须在电话前设置




DelegateType someDelegate = new ...;

UnmanagedFuncRegisterCallback(someDelegate);

UnmanagedFuncDoWork();

GC.KeepAlive(someDelegate);


bye

Rob



Ok. I see. I had a case where the delegates had to be setup
before their call:

DelegateType someDelegate = new ...;
UnmanagedFuncRegisterCallback(someDelegate);
UnmanagedFuncDoWork();
GC.KeepAlive(someDelegate);

bye
Rob