I'm calling a dll using JNA and code generated using Jnaerator. One of the methods requires an string, and the JNA signature takes a ByteBuffer.
I've tried allocating the ByteBuffer as direct (ByteBuffer.allocateDirect) and indirect (ByteBuffer.wrap) but in both cases some times the string that reaches the dll has additional random characters (e.g. ReceiptÚeœ ). The original byte[] is there (receipt = 52 65 63 65 69 70 74) but as well a variable number of additional random bytes (01 da 65 9c 19). Randomly the string is correct, with no additional bytes.
I've tried the equivalent code using BridJ instead of JNA (the method signature takes then a Pointer name) and it in that case it works fine. Unfortunately I can't switch to BridJ because I need to use the com.sun.jna.platform.win32 classes, unless I can generate a BridJ replacement for those (https://stackoverflow.com/questions/31658862/jnaerator-bridj-user32-missing-methods)
Native declaration:
HRESULT extern WINAPI WFSOpen ( LPSTR lpszLogicalName, HAPP hApp, LPSTR lpszAppID,DWORD dwTraceLevel, DWORD dwTimeOut, DWORD dwSrvcVersionsRequired, LPWFSVERSION lpSrvcVersion, LPWFSVERSION lpSPIVersion, LPHSERVICE lphService);
JNAerator JNA code:
//works
@Deprecated
NativeLong WFSOpen(Pointer lpszLogicalName, Pointer hApp, Pointer lpszAppID, int dwTraceLevel, int dwTimeOut, int dwSrvcVersionsRequired, WFSVERSION lpSrvcVersion, WFSVERSION lpSPIVersion, ShortByReference lphService);
//does not work
NativeLong WFSOpen(ByteBuffer lpszLogicalName, Pointer hApp, ByteBuffer lpszAppID, int dwTraceLevel, int dwTimeOut, int dwSrvcVersionsRequired, WFSVERSION lpSrvcVersion, WFSVERSION lpSPIVersion, ShortBuffer lphService);
Java call working (but deprecated)
Pointer m = new Memory(string.length() + 1); // WARNING: assumes ascii-only string
m.setString(0, string);
MsxfsLibrary.INSTANCE.WFSOpen(lpszLogicalName, lphApp.getValue(), lpszAppID, dwTraceLevel, dwTimeOut, dwSrvcVersionsRequired, lpSrvcVersion, lpSPIVersion, lphService);
Java call NOT working test A:
lpszLogicalName = ByteBuffer.wrap(bytes);
MsxfsLibrary.INSTANCE.WFSOpen(lpszLogicalName, lphApp.getValue(), lpszAppID, dwTraceLevel, dwTimeOut, dwSrvcVersionsRequired, lpSrvcVersion, lpSPIVersion, lphService);
Java call NOT working test B:
byte[] bytes = string.getBytes();
return ByteBuffer.wrap(bytes);
ByteBuffer bb = ByteBuffer.allocateDirect(bytes.length);
bb.put(bytes);
lpszLogicalName = bb.position(0);
msxfsLibrary.WFSOpen(lpszLogicalName, lphApp.getValue(), lpszAppID, dwTraceLevel, dwTimeOut, dwSrvcVersionsRequired, lpSrvcVersion, lpSPIVersion, lphService);
If you're referring to _wfsopen(), it's expecting a wide-character string. Either use
WString
, or configure your library to type-mapString
(seeW32APIOptions.UNICODE_OPTIONS
).