Java RMI AccessControlException: access denied
Asked Answered
B

3

19

Hey I'm getting a AccessControlException: access denied when attempting to start up a RMI app I'm writing, I can't work out why I get this exception if I open it on the default port 1099, or on another dynamic port, my policy file currently grants everything (will change when app is finished).

I am stuck as to where it is going wrong, any help would be of great use

My code

public class Main {

/**
 * @param args the command line arguments
 */
public static void main(String[] args) throws RemoteException, AlreadyBoundException, MalformedURLException {
     if (System.getSecurityManager() == null)
     {
        System.setSecurityManager ( new RMISecurityManager() );
     }

     CreditCardServer ccs = new CreditCardServer();

     int port = 1099;

     try {
        port = Integer.valueOf(args[0]);
        }
     catch (Exception e)
        {
        System.out.println("Invlaid Port");
        }

     if (((port <= 65535) && (port >= 49152)) || port ==1099)
     {
     System.out.println("Valid Port");
     }
     else
     {
         port = 1099;
        System.out.println("Port not in Dynamic Range 49152<-->65535");
     }

     System.out.println(port);

     LocateRegistry.createRegistry(port);

     LocateRegistry.getRegistry().bind("CreditCardServer", ccs);

     while (true)
     {
        //hum?
     }
}

}

The Stack Trace

vega3 [ia32.linux] 23% java -Djava.security.policy=wideopen.policy -jar "BookStore-CreditCardServer.jar 65000"

Valid Port

65000

Exception in thread "main" java.security.AccessControlException: access denied (java.net.SocketPermission 127.0.0.1:1099 connect,resolve)
        at java.security.AccessControlContext.checkPermission(AccessControlContext.java:342)
        at java.security.AccessController.checkPermission(AccessController.java:553)
        at java.lang.SecurityManager.checkPermission(SecurityManager.java:549)
        at java.lang.SecurityManager.checkConnect(SecurityManager.java:1051)
        at java.net.Socket.connect(Socket.java:536)
        at java.net.Socket.connect(Socket.java:492)
        at java.net.Socket.<init>(Socket.java:389)
        at java.net.Socket.<init>(Socket.java:203)
        at sun.rmi.transport.proxy.RMIDirectSocketFactory.createSocket(RMIDirectSocketFactory.java:40)
        at sun.rmi.transport.proxy.RMIMasterSocketFactory.createSocket(RMIMasterSocketFactory.java:146)
        at sun.rmi.transport.tcp.TCPEndpoint.newSocket(TCPEndpoint.java:613)
        at sun.rmi.transport.tcp.TCPChannel.createConnection(TCPChannel.java:216)
        at sun.rmi.transport.tcp.TCPChannel.newConnection(TCPChannel.java:202)
        at sun.rmi.server.UnicastRef.newCall(UnicastRef.java:340)
        at sun.rmi.registry.RegistryImpl_Stub.bind(Unknown Source)
        at bookstorecreditcardserver.Main.main(Main.java:56)

My Policy File

grant {
// Allow everything for now
permission java.security.AllPermission;
};
Bombacaceous answered 11/3, 2010 at 18:8 Comment(1)
Can you do an nmap on your machine to make sure something isn't already using that port (for example, you ran this program before and it didn't die cleanly).Keilakeily
B
3

Basically, I'm stupid, i assumed that because Java was not complaining it was finding the .policy file AOK, turns out it was not moving a new copy of the.policy file into the working directory solves all :-D

Bombacaceous answered 11/3, 2010 at 18:24 Comment(1)
" moving a new copy of the.policy file into the working directory" what do you mean by new copy? you had the copy in the root directory of the project right? how creating another policy file in the root folder solved the problem?Heliport
D
30

I've been stuck on this all day (after figuring out I had to start the rmiregistry from the commandline), trying to make this work locally with Eclipse, and finally solved it. A few pointers to save others this cruel fate:

1 - assign the policy file correctly, either with a commandline flag:

java -Djava.security.policy=/home/.../<filename>.policy ...

or by putting this directly in your code:

System.setProperty("java.security.policy","file:///home/.../<filename>.policy");

You can also put it in the same folder as your project root), to reduce the URI to

file:./<filename>.policy

(use a relative instead of absolute URI - I actually didn't understand this until today).

2 - make sure the format of the policy file is correct, e.g.:

grant codeBase "file:<path>/bin/-" {
    permission java.security.AllPermission;
};

This should refer to the folder where your binary is located! A thorough explanation of the format of the policy file is here.

That's about it, I'd also recommend this tutorial, I found it very helpful to get on the right track.

Dalmatia answered 14/4, 2012 at 22:33 Comment(3)
+1 Thanks for this expansive answer to this old but still very valid question Nauta & wecome.Rigel
The explanation of the format of the policy file link is outdated.Capsulize
How do I get the proper path for the security.policy file?Club
B
3

Basically, I'm stupid, i assumed that because Java was not complaining it was finding the .policy file AOK, turns out it was not moving a new copy of the.policy file into the working directory solves all :-D

Bombacaceous answered 11/3, 2010 at 18:24 Comment(1)
" moving a new copy of the.policy file into the working directory" what do you mean by new copy? you had the copy in the root directory of the project right? how creating another policy file in the root folder solved the problem?Heliport
S
0

I found most of the answers on this topic vague and unhelpful, and spent several hours debugging this. More than likely, your error is because the policy file is either incorrectly formatted or you're not correctly setting it as a command line argument.

If you're getting a java.security.AccessControlException: access denied ("java.net.SocketPermission" "127.0.0.1:1099" "connect,resolve")

  1. Create a security policy file with all permissions, just to test it out

grant codeBase "file:/-" { permission java.security.AllPermission; };

  1. Use this security file for both the client and the server, just to get it running.

  2. Make sure you don't have any typos. I spent hours trying to figure out why it wasn't working, and i had typed -Djava.rmi.security.policy instead of -Djava.security.policy=...

For those of us that just want to get the RMI tutorial from Oracle up and running, this security policy will be more than enough for that example.

Sheepwalk answered 15/2, 2018 at 15:41 Comment(2)
Your answer is basically identical to this one which was posted six years ago, and which is neither vague nor unhelpful. Or else yours is too.Cornflakes
Having spent hours debugging this, I can assure you that there needs to be more answers out there for this issue. I found this line particularly widely overcomplicated the issue "This should refer to the folder where your binary is located!"Sheepwalk

© 2022 - 2024 — McMap. All rights reserved.