Permission denied error when binding a port

This Knowledge Base article was written specifically for the Atlassian Server platform. Due to the Restricted functions in Atlassian Cloud apps, the contents of this article cannot be applied to Atlassian Cloud applications.

Problem

You're trying to bind a port in a Linux environment and are receiving a "Permission denied" error. Typically this is either port 80 or 443.

The following appears in the catalina.out

Jun 7, 2012 4:58:57 PM org.apache.coyote.http11.Http11Protocol init
SEVERE: Error initializing endpoint
java.net.BindException: Permission denied <null>:80
        at org.apache.tomcat.util.net.JIoEndpoint.init(JIoEndpoint.java:549)
        at org.apache.coyote.http11.Http11Protocol.init(Http11Protocol.java:176)
        at org.apache.catalina.connector.Connector.initialize(Connector.java:1022)
        at org.apache.catalina.core.StandardService.initialize(StandardService.java:703)
        at org.apache.catalina.core.StandardServer.initialize(StandardServer.java:838)
        at org.apache.catalina.startup.Catalina.load(Catalina.java:538)
        at org.apache.catalina.startup.Catalina.load(Catalina.java:562)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
        at java.lang.reflect.Method.invoke(Method.java:597)
        at org.apache.catalina.startup.Bootstrap.load(Bootstrap.java:261)
        at org.apache.catalina.startup.Bootstrap.main(Bootstrap.java:413)
Caused by: java.net.BindException: Permission denied
        at java.net.PlainSocketImpl.socketBind(Native Method)
        at java.net.PlainSocketImpl.bind(PlainSocketImpl.java:383)
        at java.net.ServerSocket.bind(ServerSocket.java:328)
        at java.net.ServerSocket.<init>(ServerSocket.java:194)
        at java.net.ServerSocket.<init>(ServerSocket.java:150)
        at org.apache.tomcat.util.net.DefaultServerSocketFactory.createSocket(DefaultServerSocketFactory.java:50)
        at org.apache.tomcat.util.net.JIoEndpoint.init(JIoEndpoint.java:538)
        ... 12 more
Jun 7, 2012 4:58:57 PM org.apache.catalina.core.StandardService initialize
SEVERE: Failed to initialize connector [Connector[HTTP/1.1-80]]
LifecycleException:  Protocol handler initialization failed: java.net.BindException: Permission denied <null>:80
        at org.apache.catalina.connector.Connector.initialize(Connector.java:1024)
        at org.apache.catalina.core.StandardService.initialize(StandardService.java:703)
        at org.apache.catalina.core.StandardServer.initialize(StandardServer.java:838)
        at org.apache.catalina.startup.Catalina.load(Catalina.java:538)
        at org.apache.catalina.startup.Catalina.load(Catalina.java:562)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
        at java.lang.reflect.Method.invoke(Method.java:597)
        at org.apache.catalina.startup.Bootstrap.load(Bootstrap.java:261)
        at org.apache.catalina.startup.Bootstrap.main(Bootstrap.java:413)

Cause

Ports below 1024 are called Privileged Ports and in Linux (and most UNIX flavors and UNIX-like systems), they are not allowed to be opened by any non-root user. This is a security feature originally implemented as a way to prevent a malicious user from setting up a malicious service on a well-known service port.

Resolution

There are a few different solutions to work around this:

  1. Install and configure Apache or nginx as a reverse proxy server, which can be started as root to open the port, and then downgrade its privileges back to a normal user.
  2. Set up a firewall on the server using iptables or an alternative, so that the lower port number is forwarded internally to a higher port number listened by Confluence.
  3. Use jsvc, which is able to open ports as root, and then downgrade privileges.
  4. Use authbind to grant privileges for a non-root user to open a privileged port.
  5. If using Linux 2.6.24 or later, you can set up a file capability on the java executable, to give elevated privileges to allow opening privileged ports only, and no other superuser privileges:

    # setcap cap_net_bind_service+ep /path/to/bin/java

    After setting this you may notice errors when starting Java like this, for example:

    $ java -version
    /path/to/bin/java: error while loading shared libraries: libjli.so: cannot open shared object file: No such file or directory

    This means that the library is being imported from a dynamic path, and not in the trusted ld.so path. See http://bugs.sun.com/view_bug.do?bug_id=7157699 for details. To fix this, you need to locate the library, and add its path to the ld.so configuration. Note that the below is an example, and this may differ depending on Linux distribution. Replace JAVA_HOME with the correct location:

    $ find JAVA_HOME -name 'libjli.so'
    JAVA_HOME/lib/amd64/jli/libjli.so
     
    # echo "JAVA_HOME/lib/amd64/jli" > /etc/ld.so.conf.d/java-libjli.conf
    # ldconfig -v

    After setting this all up, you need to make sure that Confluence only starts java with the direct binary path, and not via a symbolic link, otherwise the capability will not be picked up.

    Setting this up means that any user can open privileged ports using Java, which may or may not be acceptable for you


Whilst it may get things working, it is not recommended to run Confluence as root. If there is ever any security vulnerability where an attacker may execute arbitrary code as the running user, then they will gain root access.


Last modified on Mar 30, 2016

Was this helpful?

Yes
No
Provide feedback about this article

Not finding the help you need?

Ask the community

Powered by Confluence and Scroll Viewport.