What happened to the Messenger Plus! forums on msghelp.net?
Shoutbox » MsgHelp Archive » Messenger Plus! for Live Messenger » Scripting » DLL return value

DLL return value
Author: Message:
CookieRevised
Elite Member
*****

Avatar

Posts: 15517
Reputation: 173
– / Male / Flag
Joined: Jul 2003
Status: Away
RE: DLL return value
quote:
Originally posted by deAd
What if you don't know how much space you need?
As I explained in the MSN chat, by creating the data in the first function and storing it until the second function has been called. Or by creating the data with the first call and with a specific set of parameters (eg: everything 0, except the buffersize) and storing it until a second call is done with a valid buffer as one of the parameters.

Look at the Windows APIs which can return variable sized data...

They either consist of actually two APIs, where you first need to call the first API to get the size of the returned data, and then call the second API to get the actual data.

Or it is 1 function which you need to call twice. The first time with all the parameters being null, except the buffersize parameter. And the second time with a pointer to the actual buffer.

Many times, in the second call they return the length of the written data too. So you, as a caller, can check if how much has been written to the buffer (the returned datalength is non zero).

See the registry APIs for example: RegQueryValue which works in exact the same way.

Another example, and a slightly different method, but with the same principles (a large enough buffersize must be given, or yuo need to call the function twice to recieve the appropiate buffersize) is done by RegQueryMultipleValues. This API works with an array btw.

Also, in your DLL, make sure you first check the size of the actual allocated memory space by the caller. In this check, the given buffersize is of no matter, you need to check the allocated memory size against the size it would require to write all your data to the memory. This is very mandatory so that you don't write beyond the memory space available to your function.

^^ and if you do this properly, you can even make it that the caller must only call your function once, on the condition that the buffer is large enough so the function can directly write all the data to the buffer. If the buffer is not large enough, still write data to the buffer (until the end) and set the return value of your function to ERROR_MORE_DATA or something.

thus, for example the user can do:

// This will allocate the exact amount of needed memory
var BufferSize = 0
var ReturnValue = Interop.Call("your.dll", yourfunc, 0, BufferSize)
var Buffer = Interop.Allocate(BufferSize)
var ReturnValue = Interop.Call("your.dll", yourfunc, Buffer.DataPtr, BufferSize)

ReturnValue is 0
Buffer is filled with BufferSize bytes of data
BufferSize is the amount of data bytes in the buffer

or

// This will allocate more memory than needed
var BufferSize = 4096
var Buffer = Interop.Allocate(BufferSize)
var ReturnValue = Interop.Call("your.dll", yourfunc, Buffer.DataPtr, BufferSize)

ReturnValue is 0
Buffer is filled with x bytes of data
BufferSize is the amount of data bytes in the buffer (thus x)

or

// This will allocate too little memory
var BufferSize = 10
var Buffer = Interop.Allocate(BufferSize)
var ReturnValue = Interop.Call("your.dll", yourfunc, Buffer.DataPtr, BufferSize)

ReturnValue is ERROR_MORE_DATA
Buffer is filled with 10 bytes of data
BufferSize contains the actual needed bytes



PS: as a sidenote, many people use those registry APIs (or any other API which requires a big enough buffer by the user) in the wrong way. Many calll such APIs with a fixed buffersize and do not first retrieve the appropiate buffersize. And they even less check if the returned buffer and returned size is non zero to see if the buffer wasn't too small...


------------------------------------------------------------------------------------------

A total other approach you can take, and much easier for you to program (I think) is to use a VBArray aka SafeArray as return value of your function. Provided C++ knows this kind of data type of course, dunno (but it should though).

var vbArray = new VBArray(Interop.Call("your.dll", yourfunc))
var jsArray = vbArray.toArray()

This post was edited on 12-31-2006 at 12:12 AM by CookieRevised.
.-= A 'frrrrrrrituurrr' for Wacky =-.
12-29-2006 05:12 PM
Profile PM Find Quote Report
« Next Oldest Return to Top Next Newest »

Messages In This Thread
DLL return value - by deAd on 12-28-2006 at 07:54 PM
RE: Calling a DLL (two questions) - by J-Thread on 12-28-2006 at 08:59 PM
RE: Calling a DLL (two questions) - by deAd on 12-28-2006 at 09:02 PM
RE: DLL return value - by CookieRevised on 12-29-2006 at 09:57 AM
RE: DLL return value - by deAd on 12-29-2006 at 04:28 PM
RE: DLL return value - by CookieRevised on 12-29-2006 at 05:12 PM


Threaded Mode | Linear Mode
View a Printable Version
Send this Thread to a Friend
Subscribe | Add to Favorites
Rate This Thread:

Forum Jump:

Forum Rules:
You cannot post new threads
You cannot post replies
You cannot post attachments
You can edit your posts
HTML is Off
myCode is On
Smilies are On
[img] Code is On