Search code examples
javajna

Invalid Parameter Error using NetShareAdd windows Api using JNA Library


I am trying to use NetShareAdd Windows API in my java code using JNA library - 5.5.0,JNA Platform -5.5.0, on a Windows 10 machine using Java 8. I amgetting an Invalid Parameter Error for the sharename. I am using the below code:

import com.sun.jna.Pointer;
import com.sun.jna.platform.win32.LMAccess;
import com.sun.jna.platform.win32.LMShare;
import com.sun.jna.platform.win32.Netapi32;
import com.sun.jna.ptr.IntByReference;

import java.io.File;

public class JNATest {

    public static void createLocalShare(File shareFolder)
    {
        TestwareLMShare.SHARE_INFO_2 shi = new TestwareLMShare.SHARE_INFO_2();
        shi.shi2_netname = shareFolder.getName();
        shi.shi2_type = LMShare.STYPE_DISKTREE;
        shi.shi2_remark = "";
        shi.shi2_permissions = LMAccess.ACCESS_ALL;
        shi.shi2_max_uses = -1;
        shi.shi2_current_uses = 0;
        shi.shi2_path = shareFolder.getAbsolutePath();
        shi.shi2_passwd = "";
        IntByReference parm_err=new IntByReference();
        Pointer pointer=shi.getPointer();
        int result= Netapi32.INSTANCE.NetShareAdd(null,2,shi.getPointer(),parm_err); // share folder in local system
        System.out.println("errorcode:"+result);//errorcode 87 -invalid parameter
        System.out.println("parameter:"+parm_err.getValue());// 1 - shi2_netname is invalid
    }
    public static void main(String args[])
    {
        File file=new File("e:\\testfolder"); // folder present in local system
        createLocalShare(file);
    }
}

Output:

errorcode:87
parameter:1

I have checked using net share testfolder=e:\testfolder in Windows command prompt and it works. I have also tested the Windows API NetShareAdd directly in a cpp program and it also works. But I am unable to make the same function work with JNA library. I have used other JNA functions regarding networking but they work fine. Please help me find the fault.


Solution

  • You have populated the Java class fields for your SHARE_INFO_2 structure after instantiating it, but you haven't written the new fields to native memory prior to using the structure, so the native function is seeing null pointers and the initial values of the instantiated structure.

    When a method mapping uses the Structure class, this java-to-native write is done automatically. In this case, however, the NetShareAdd() method expects a Pointer (since there are multiple different classes which could be used). JNA doesn't know where the pointer came from or how big the buffer is, etc., so it can't automatically copy over the memory to the native side after you've made java-side changes.

    Adding a shi.write() after setting all the Java-side values of shi will copy that data to native memory and your buffer will then contain the data and pointers that the method expects.