Devendra Wani
Devendra Wani

Reputation: 121

Support for Kerberos Authentication/Authorization on JMX Client/Server running on Java 6

I have my JMX server which registers beans reading from local file and make them available to other JMX clients on demand. Server can be accessed either using "jconsole" or by Java app running under Tomcat container.

What i want is to add authentication in order to prevent "unknown" identity accessing JMX Server. To achieve this i have added Kerberos authentication @ server using following JVM options

-Dcom.sun.management.jmxremote=true
-Dcom.sun.management.jmxremote.port=5555
-Dcom.sun.management.jmxremote.authenticate=true
-Dcom.sun.management.jmxremote.ssl=false
-Djava.security.auth.login.config=./conf/jaas.conf
-Djava.security.krb5.conf=./conf/krb5.conf
-Dcom.sun.management.jmxremote.login.config=MyKrbAuth
-Ddynamic.mbean.store=./conf/mbeans
-Djava.net.preferIPv4Stack=true

my jaas.conf looks like this >>

MyKrbAuth {
com.sun.security.auth.module.Krb5LoginModule required debug=true debugNative=true;
};

When I start my JMX server with above configuration and try to connect it using "jconsole", I get the following exception at client side and connection fails>>

Cipher: Crypto Permission check failed
Cipher: granted: (CryptoPermission * 128)
Cipher: requesting: (CryptoPermission AES 256)

But at server authentication appears to be successful >>

[java] [STARTED] Mbean Server
[java] Debug is  true storeKey false useTicketCache false useKeyTab false doNotPrompt false ticketCache is null isInitiator true KeyTab is null refreshKrb5Config is false principal is null tryFirstPass is false useFirstPass is false storePass is false clearPass is false
[java] [Krb5LoginModule] user entered username: username
[java] 
[java] Acquire TGT using AS Exchange
[java] principal is [email protected]
[java] EncryptionKey: keyType=3 keyBytes (hex dump)=0000: FD 46 7C 02 19 9B 34 E9   
[java] EncryptionKey: keyType=1 keyBytes (hex dump)=0000: FD 46 7C 02 19 9B 34 E9   
[java] EncryptionKey: keyType=23 keyBytes (hex dump)=0000: FE 6D 82 01 8A D7 AB 60   98 
[java] EncryptionKey: keyType=16 keyBytes (hex dump)=0000: 89 02 31 5D F7 5B 3E 89   BC F7 8A 01 A1 80 C7 
[java] EncryptionKey: keyType=17 keyBytes (hex dump)=0000: A5 67 71 17 F6 57 A9 26   01 09 B1 EB 75 46 6C 
[java] 
[java] Commit Succeeded 
[java] 

From above it seems that client not able to decode response (which is AES256 encrypted).. How to fix it ??

Upvotes: 6

Views: 3356

Answers (3)

Devendra Wani
Devendra Wani

Reputation: 121

Managed to fixed above problem. Here are the steps to introduce Kerberos authentication/authorization at your JMX client/server

To enable Kerberos @ JMX server,

  1. Start server with following set of args =>

    -Dcom.sun.management.jmxremote=true
    -Dcom.sun.management.jmxremote.port=<port_no>
    -Dcom.sun.management.jmxremote.authenticate=true
    -Dcom.sun.management.jmxremote.ssl=false
    -Djava.security.auth.login.config=<locatin_of_jaas.conf>
    -Djava.security.krb5.conf=<locatin_of_krb5.conf>
    -Dcom.sun.management.jmxremote.login.config=<name_of_login_config_to_be_used>
    -Djava.net.preferIPv4Stack=true
    
  2. Add access entry in $JAVA_HOME/jre/lib/management/jmxremote.access. Once user get authenticated, read/write access to JMX server will be provided on basis of jmxremote.access. Location of .access file can be provided using following jvm arg at server start up

    -Dcom.sun.management.jmxremote.access.file=<acees_control_file>    
    

To enable Kerberos @ JMX Client (jconsole)

  1. Start jconsole with debug option & connect to server

    jconsole -J-Djava.security.debug=all
    
  2. if requested encryption is AES256, then download unlimited strength cryptography policy jar files, extract and place policy files at $JAVA_HOME/jre/lib/security/. [Thanks to Mark for pointing out policy inclusion.]

Above should make Kerberos work at both JMX client and JMX server side

If you are still facing problem in connection then you can enable verbose debugging for jconsole using logging.properties file =>

handlers = java.util.logging.ConsoleHandler
.level = INFO
java.util.logging.ConsoleHandler.level = FINEST
java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter
// Use FINER or FINEST for javax.management.remote.level - FINEST is very verbose...
javax.management.level = FINEST
javax.management.remote.level = FINER

And start jconsole using

jconsole -J-Djava.util.logging.config.file=<location_of_logging.properties>

Upvotes: 3

Edward
Edward

Reputation: 33

I have followed the instructions above and managed to get kerberos authentication working provided I enter my userid and password in jconsole. Inevitably this sends my password over the wire in clear text as I have set com.sun.management.jmxremote.ssl=false on the server.

Have you managed to connect jconsole by using a cached ticket on the client side? For example, if you did:

kinit user
Password for user@REALM:
New ticket is stored in cache file C:\Users\user\krb5cc_user

then tried connecting jconsole to the server without entering your userid/password?

Upvotes: 0

Mark Rotteveel
Mark Rotteveel

Reputation: 109090

You need to include the unlimited strength cryptography policy file (link is for Java 6, see java.oracle.com for others) in your Java installation. By default Java does not allow you to use strong encryption like AES256 (because of absurd US export laws which consider encryption to be weapons/munition). The policy file will unlock stronger encryption.

Upvotes: 4

Related Questions