@Override
    public Key engineDoPhase(Key key, boolean lastPhase) throws InvalidKeyException {
        if (mPrivateKey == null) {
            throw new IllegalStateException("Not initialized");
        }
        if (!lastPhase) {
            throw new IllegalStateException("DH only has one phase");
        }

        if (key == null) {
            throw new InvalidKeyException("key == null");
        }
        if (!(key instanceof PublicKey)) {
            throw new InvalidKeyException("Not a public key: " + key.getClass());
        }
        T openSslPublicKey = convertPublicKey((PublicKey) key);

        byte[] buffer = new byte[mExpectedResultLength];
        int actualResultLength = computeKey(buffer, openSslPublicKey, mPrivateKey);
        byte[] result;
        if (actualResultLength == -1) {
            throw new RuntimeException("Engine returned -1");
        } else if (actualResultLength == mExpectedResultLength) {
            // The output is as long as expected -- use the whole buffer
            result = buffer;
        } else if (actualResultLength < mExpectedResultLength) {
            // The output is shorter than expected -- use only what's produced by the engine
            result = new byte[actualResultLength];
            System.arraycopy(buffer, 0, mResult, 0, mResult.length);
        } else {
            // The output is longer than expected
            throw new RuntimeException("Engine produced a longer than expected result. Expected: "
                + mExpectedResultLength + ", actual: " + actualResultLength);
        }
        mResult = result;

        return null; // No intermediate key
    }
Agreed key. Only available after {@link #engineDoPhase(Key, boolean)} completes.
common/src/main/java/org/conscrypt/OpenSSLBaseDHKeyAgreement.java