Hacktoberfest 2026: the issues maintainers tagged for October, open and beginner-friendly. Browse Hacktoberfest issues

[Bug]: OPC UA UserNameIdentityToken sends length+password+nonce instead of the plain password when token security policy is None

Open
#2,791 2 comments 0 reactions 2 assignees View on GitHub

Maintainers usually reply within 1 day

@splatch is already working on this.

Since Oct 2, 2026.

Assessment

This issue has not been assessed yet.

Description

OPC-UA
What happened?

With PLC4J 1.0.0, the OPC UA driver cannot log in with username/password when the selected user token policy resolves to security policy None (and allow-insecure-credentials=true is set). The server answers ActivateSession with BadUserAccessDenied (0x801f0000). The same server and credentials work with 0.13.1.

The cause is in SecureChannel.getIdentityToken(...) (plc4j/drivers/opcua/src/main/java/org/apache/plc4x/java/opcua/context/SecureChannel.java, tag v1.0.0, unchanged on develop). For userTokenTypeUserName the method builds the RSA plaintext block length(4, little endian) + password + serverNonce (encodeablePassword). In the SecurityPolicy.NONE branch that block is sent as the token password instead of the password itself:

if (tokenSecurityPolicy == SecurityPolicy.NONE) {
    // No encryption: the password is sent as-is and no algorithm is declared.
    tokenPassword = encodeablePassword;   // should be passwordBytes
    encryptionAlgorithm = "";
}

OPC UA Part 4, 7.41.3 (UserNameIdentityToken): when encryptionAlgorithm is empty the password field carries the UTF-8 password itself; the length/nonce wrapping only applies to the encrypted form. A spec-conforming server therefore compares <4 length bytes> + password + nonce with the stored password and rejects the login. The code comment says "the password is sent as-is", so this looks like the wrong local variable.

Steps to reproduce
  1. OPC UA server that exposes a None endpoint with a UserName user token policy without its own securityPolicyUri and requires authentication (we used python asyncua 1.1.5 with a user manager that compares username/password in plain text).
  2. Connect with opcua:tcp://host:port?discovery=false&security-policy=NONE&allow-insecure-credentials=true&username=u&password=p and read any node.
  3. Connection fails with PlcProtocolException: Server returned error BadUserAccessDenied (0x801f0000). On the server side the received password is 4 + len(password) + 32 bytes long.
Expected

The token password is the plain UTF-8 password when no encryption algorithm is declared, as in 0.13.1, and the login succeeds.

Suggested fix

In the SecurityPolicy.NONE branch use tokenPassword = passwordBytes; (and only build encodeablePassword for the encrypted branch).

Version

1.0.0 (Java, plc4j-driver-opcua), JDK 21.

Dominant language
Java
Stars
1.8k
Forks
505
Avg merge
9h 45m
Merged PRs (30d)
48

Getting set up

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

More from apache/plc4x

All issues in apache/plc4x

Similar issues

More Java issues

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.