summaryrefslogtreecommitdiff
path: root/lib/jinterface/java_src/com/ericsson/otp/erlang/AbstractConnection.java
diff options
context:
space:
mode:
Diffstat (limited to 'lib/jinterface/java_src/com/ericsson/otp/erlang/AbstractConnection.java')
-rw-r--r--lib/jinterface/java_src/com/ericsson/otp/erlang/AbstractConnection.java194
1 files changed, 88 insertions, 106 deletions
diff --git a/lib/jinterface/java_src/com/ericsson/otp/erlang/AbstractConnection.java b/lib/jinterface/java_src/com/ericsson/otp/erlang/AbstractConnection.java
index 7ea5d52da7..9e6a35ec36 100644
--- a/lib/jinterface/java_src/com/ericsson/otp/erlang/AbstractConnection.java
+++ b/lib/jinterface/java_src/com/ericsson/otp/erlang/AbstractConnection.java
@@ -1,7 +1,7 @@
/*
* %CopyrightBegin%
*
- * Copyright Ericsson AB 2000-2021. All Rights Reserved.
+ * Copyright Ericsson AB 2000-2023. All Rights Reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -79,7 +79,7 @@ public abstract class AbstractConnection extends Thread {
protected static final int unlinkIdTag = 35;
protected static final int unlinkIdAckTag = 36;
- // MD5 challenge messsage tags
+ // MD5 challenge message tags
protected static final int ChallengeReply = 'r';
protected static final int ChallengeAck = 'a';
protected static final int ChallengeStatus = 's';
@@ -166,18 +166,12 @@ public abstract class AbstractConnection extends Thread {
throws IOException, OtpAuthException {
peer = other;
localNode = self;
- socket = null;
int port;
traceLevel = defaultLevel;
setDaemon(true);
- // now get a connection between the two...
- port = OtpEpmd.lookupPort(peer);
- if (port == 0)
- throw new IOException("No remote node found - cannot connect");
-
- // now find highest common dist value
+ // Find highest common dist value
if (peer.proto != self.proto || self.distHigh < peer.distLow
|| self.distLow > peer.distHigh) {
throw new IOException("No common protocol found - cannot connect");
@@ -187,7 +181,21 @@ public abstract class AbstractConnection extends Thread {
peer.distChoose = peer.distHigh > self.distHigh ? self.distHigh
: peer.distHigh;
- doConnect(port);
+ // Now get a connection between the two nodes
+ if (self.transportFactory instanceof OtpGenericTransportFactory) {
+ // For alternative distribution protocols using a transport factory
+ // extending the OtpGenericTransportFactory class, the notion of
+ // socket port is not used so the remote node is not registered
+ // with Epmd.
+ doGenericConnect();
+
+ } else {
+ // Get the listening port of the remote node registered with Epmd
+ port = OtpEpmd.lookupPort(peer);
+ if (port == 0)
+ throw new IOException("No remote node found - cannot connect");
+ doPortConnect(port);
+ }
name = peer.node();
connected = true;
@@ -1052,27 +1060,51 @@ public abstract class AbstractConnection extends Thread {
}
}
- protected void doConnect(final int port) throws IOException,
+ protected void doPortConnect(final int port) throws IOException,
OtpAuthException {
try {
socket = peer.createTransport(peer.host(), port);
-
if (traceLevel >= handshakeThreshold) {
System.out.println("-> MD5 CONNECT TO " + peer.host() + ":"
+ port);
}
+ doConnect();
+
+ } catch (final OtpAuthException ae) {
+ close();
+ throw ae;
+ } catch (final Exception e) {
+ close();
+ final IOException ioe = new IOException(
+ "Cannot connect to peer node");
+ ioe.initCause(e);
+ throw ioe;
+ }
+ }
+
+ protected void doConnect() throws IOException, OtpAuthException {
final int send_name_tag = sendName(peer.distChoose, localNode.flags,
- localNode.creation);
+ localNode.creation());
recvStatus();
final int her_challenge = recvChallenge();
final byte[] our_digest = genDigest(her_challenge,
localNode.cookie());
final int our_challenge = genChallenge();
- sendComplement(send_name_tag);
sendChallengeReply(our_challenge, our_digest);
recvChallengeAck(our_challenge);
cookieOk = true;
sendCookie = false;
+ }
+
+ protected void doGenericConnect() throws IOException,
+ OtpAuthException {
+ try {
+ socket = peer.createTransport(peer);
+ if (traceLevel >= handshakeThreshold) {
+ System.out.println("-> MD5 CONNECT TO " + peer.node());
+ }
+ doConnect();
+
} catch (final OtpAuthException ae) {
close();
throw ae;
@@ -1149,79 +1181,36 @@ public abstract class AbstractConnection extends Thread {
final OtpOutputStream obuf = new OtpOutputStream();
final String str = localNode.node();
int send_name_tag;
- if (dist == 5) {
- obuf.write2BE(1+2+4 + str.length());
- send_name_tag = 'n';
- obuf.write1(send_name_tag);
- obuf.write2BE(dist);
- obuf.write4BE(aflags);
- obuf.write(str.getBytes());
- }
- else {
- obuf.write2BE(1+8+4+2 + str.length());
- send_name_tag = 'N';
- obuf.write1(send_name_tag);
- obuf.write8BE(aflags);
- obuf.write4BE(creation);
- obuf.write2BE(str.length());
- obuf.write(str.getBytes());
- }
+ obuf.write2BE(1+8+4+2 + str.length());
+ send_name_tag = 'N';
+ obuf.write1(send_name_tag);
+ obuf.write8BE(aflags);
+ obuf.write4BE(creation);
+ obuf.write2BE(str.length());
+ obuf.write(str.getBytes());
obuf.writeToAndFlush(socket.getOutputStream());
if (traceLevel >= handshakeThreshold) {
System.out.println("-> " + "HANDSHAKE sendName" + " flags="
- + aflags + " dist=" + dist + " local=" + localNode);
+ + aflags + " local=" + localNode);
}
return send_name_tag;
}
- protected void sendComplement(final int send_name_tag)
- throws IOException {
-
- if (send_name_tag == 'n' &&
- (peer.flags & AbstractNode.dFlagHandshake23) != 0) {
- @SuppressWarnings("resource")
- final OtpOutputStream obuf = new OtpOutputStream();
- obuf.write2BE(1+4+4);
- obuf.write1('c');
- final int flagsHigh = (int)(localNode.flags >> 32);
- obuf.write4BE(flagsHigh);
- obuf.write4BE(localNode.creation);
-
- obuf.writeToAndFlush(socket.getOutputStream());
-
- if (traceLevel >= handshakeThreshold) {
- System.out.println("-> " + "HANDSHAKE sendComplement" +
- " flagsHigh=" + flagsHigh +
- " creation=" + localNode.creation);
- }
- }
- }
-
protected void sendChallenge(final long her_flags, final long our_flags,
final int challenge) throws IOException {
@SuppressWarnings("resource")
final OtpOutputStream obuf = new OtpOutputStream();
final String str = localNode.node();
- if ((her_flags & AbstractNode.dFlagHandshake23) == 0) {
- obuf.write2BE(1+2+4+4 + str.length());
- obuf.write1('n');
- obuf.write2BE(5);
- obuf.write4BE(our_flags & 0xffffffff);
- obuf.write4BE(challenge);
- obuf.write(str.getBytes());
- }
- else {
- obuf.write2BE(1+8+4+4+2 + str.length());
- obuf.write1('N');
- obuf.write8BE(our_flags);
- obuf.write4BE(challenge);
- obuf.write4BE(localNode.creation);
- obuf.write2BE(str.length());
- obuf.write(str.getBytes());
- }
+ obuf.write2BE(1+8+4+4+2 + str.length());
+ obuf.write1('N');
+ obuf.write8BE(our_flags);
+ obuf.write4BE(challenge);
+ obuf.write4BE(localNode.creation());
+ obuf.write2BE(str.length());
+ obuf.write(str.getBytes());
obuf.writeToAndFlush(socket.getOutputStream());
@@ -1257,13 +1246,18 @@ public abstract class AbstractConnection extends Thread {
final OtpInputStream ibuf = new OtpInputStream(tmpbuf, 0);
byte[] tmpname;
final int len = tmpbuf.length;
+ long flag_mask;
+
send_name_tag = ibuf.read1();
switch (send_name_tag) {
case 'n':
- apeer.distLow = apeer.distHigh = ibuf.read2BE();
- if (apeer.distLow != 5)
+ if (ibuf.read2BE() != 5)
throw new IOException("Invalid handshake version");
apeer.flags = ibuf.read4BE();
+ flag_mask = (1L << 32) - 1;
+ if ((apeer.flags & AbstractNode.dFlagHandshake23) == 0)
+ throw new IOException("Missing DFLAG_HANDSHAKE_23");
+ apeer.distLow = apeer.distHigh = 6;
tmpname = new byte[len - 7];
ibuf.readN(tmpname);
hisname = OtpErlangString.newString(tmpname);
@@ -1271,9 +1265,13 @@ public abstract class AbstractConnection extends Thread {
case 'N':
apeer.distLow = apeer.distHigh = 6;
apeer.flags = ibuf.read8BE();
+ flag_mask = ~0L;
+ if ((apeer.flags & AbstractNode.dFlagMandatory25Digest) != 0) {
+ apeer.flags |= AbstractNode.mandatoryFlags25;
+ }
if ((apeer.flags & AbstractNode.dFlagHandshake23) == 0)
throw new IOException("Missing DFLAG_HANDSHAKE_23");
- apeer.creation = ibuf.read4BE();
+ apeer.setCreation(ibuf.read4BE());
int namelen = ibuf.read2BE();
tmpname = new byte[namelen];
ibuf.readN(tmpname);
@@ -1283,21 +1281,16 @@ public abstract class AbstractConnection extends Thread {
throw new IOException("Unknown remote node type");
}
- if ((apeer.flags & AbstractNode.dFlagExtendedReferences) == 0) {
- throw new IOException(
- "Handshake failed - peer cannot handle extended references");
- }
-
- if ((apeer.flags & AbstractNode.dFlagExtendedPidsPorts) == 0) {
+ if ((~apeer.flags & flag_mask & AbstractNode.mandatoryFlags) != 0) {
throw new IOException(
- "Handshake failed - peer cannot handle extended pids and ports");
+ "Handshake failed - peer cannot handle all mandatory capabilities");
}
} catch (final OtpErlangDecodeException e) {
throw new IOException("Handshake failed - not enough data");
}
- final int i = hisname.indexOf('@', 0);
+ final int i = hisname.indexOf('@');
apeer.node = hisname;
apeer.alive = hisname.substring(0, i);
apeer.host = hisname.substring(i + 1, hisname.length());
@@ -1319,23 +1312,16 @@ public abstract class AbstractConnection extends Thread {
final OtpInputStream ibuf = new OtpInputStream(buf, 0);
int namelen;
switch (ibuf.read1()) {
- case 'n':
- if (peer.distChoose != 5)
- throw new IOException("Old challenge wrong version");
- peer.distLow = peer.distHigh = ibuf.read2BE();
- peer.flags = ibuf.read4BE();
- if ((peer.flags & AbstractNode.dFlagHandshake23) != 0)
- throw new IOException("Old challenge unexpected DFLAG_HANDHAKE_23");
- challenge = ibuf.read4BE();
- namelen = buf.length - (1+2+4+4);
- break;
case 'N':
peer.distLow = peer.distHigh = peer.distChoose = 6;
peer.flags = ibuf.read8BE();
+ if ((peer.flags & AbstractNode.dFlagMandatory25Digest) != 0) {
+ peer.flags |= AbstractNode.mandatoryFlags25;
+ }
if ((peer.flags & AbstractNode.dFlagHandshake23) == 0)
throw new IOException("New challenge missing DFLAG_HANDHAKE_23");
challenge = ibuf.read4BE();
- peer.creation = ibuf.read4BE();
+ peer.setCreation(ibuf.read4BE());
namelen = ibuf.read2BE();
break;
default:
@@ -1348,15 +1334,9 @@ public abstract class AbstractConnection extends Thread {
throw new IOException(
"Handshake failed - peer has wrong name: " + hisname);
}
-
- if ((peer.flags & AbstractNode.dFlagExtendedReferences) == 0) {
+ if ((peer.flags & AbstractNode.mandatoryFlags) != AbstractNode.mandatoryFlags) {
throw new IOException(
- "Handshake failed - peer cannot handle extended references");
- }
-
- if ((peer.flags & AbstractNode.dFlagExtendedPidsPorts) == 0) {
- throw new IOException(
- "Handshake failed - peer cannot handle extended pids and ports");
+ "Handshake failed - peer cannot handle all mandatory capabilities");
}
} catch (final OtpErlangDecodeException e) {
@@ -1374,8 +1354,7 @@ public abstract class AbstractConnection extends Thread {
protected void recvComplement(int send_name_tag) throws IOException {
- if (send_name_tag == 'n' &&
- (peer.flags & AbstractNode.dFlagHandshake23) != 0) {
+ if (send_name_tag == 'n') {
try {
final byte[] tmpbuf = read2BytePackage();
@SuppressWarnings("resource")
@@ -1385,8 +1364,11 @@ public abstract class AbstractConnection extends Thread {
final long flagsHigh = ibuf.read4BE();
peer.flags |= flagsHigh << 32;
- peer.creation = ibuf.read4BE();
-
+ if ((~peer.flags & AbstractNode.mandatoryFlags) != 0) {
+ throw new IOException("Handshake failed - peer missing" +
+ " mandatory capabilities");
+ }
+ peer.setCreation(ibuf.read4BE());
} catch (final OtpErlangDecodeException e) {
throw new IOException("Handshake failed - not enough data");
}