Commit 57ec6fff authored by pedroGitt's avatar pedroGitt
Browse files

Temp commit.. adding group session API in progress

parent 147df845
......@@ -152,9 +152,8 @@ public class OlmAccountTest {
long sessionId = olmSession.getOlmSessionId();
assertTrue(0 != sessionId);
int sessionRetCode = mOlmAccount.removeOneTimeKeysForSession(sessionId);
// no one time key has been use in the session, so removeOneTimeKeysForSession() returns an error
assertTrue(0 != sessionRetCode);
int sessionRetCode = mOlmAccount.removeOneTimeKeysForSession(olmSession);
assertTrue(0 == sessionRetCode);
olmSession.releaseSession();
sessionId = olmSession.getOlmSessionId();
......
package org.matrix.olm;
import android.support.test.runner.AndroidJUnit4;
import android.util.Log;
import org.junit.BeforeClass;
import org.junit.FixMethodOrder;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.MethodSorters;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
@RunWith(AndroidJUnit4.class)
@FixMethodOrder(MethodSorters.NAME_ASCENDING)
public class OlmGroupTest {
private static final String LOG_TAG = "OlmSessionTest";
private static OlmManager mOlmManager;
@BeforeClass
public static void setUpClass(){
// load native lib
mOlmManager = new OlmManager();
String version = mOlmManager.getOlmLibVersion();
assertNotNull(version);
Log.d(LOG_TAG, "## setUpClass(): lib version="+version);
}
@Test
public void test00AliceToBob() {
// TBD
}
/**
* Basic test:
* - alice creates an account
* - bob creates an account
* - alice creates an outbound group session
* - bob creates an inbound group session with alice's outbound session key
* - alice encrypts a message with its session
* - bob decrypts the encrypted message with its session
*/
//@Test
public void test01AliceToBob() {
// creates alice outbound session
OlmOutboundGroupSession aliceOutboundSession = new OlmOutboundGroupSession();
// test accounts creation
String aliceSessionIdentifier = aliceOutboundSession.sessionIdentifier();
assertNotNull(aliceSessionIdentifier);
assertTrue(aliceSessionIdentifier.length()>0);
String aliceOutboundSessionKey = aliceOutboundSession.sessionKey();
assertNotNull(aliceOutboundSessionKey);
assertTrue(aliceOutboundSessionKey.length()>0);
long messageIndex = aliceOutboundSession.messageIndex();
assertTrue(0==messageIndex);
String clearMessage = "Hello!";
String encryptedMessage = aliceOutboundSession.encryptMessage(clearMessage);
assertNotNull(encryptedMessage);
messageIndex = aliceOutboundSession.messageIndex();
assertTrue(1==messageIndex);
assertTrue(encryptedMessage.length()>=0);
OlmInboundGroupSession bobInboundSession = new OlmInboundGroupSession();
bobInboundSession.initInboundGroupSessionWithSessionKey(aliceOutboundSessionKey);
// check session identifiers are equals
aliceSessionIdentifier = aliceOutboundSession.sessionIdentifier();
String bobSessionIdentifier = aliceOutboundSession.sessionIdentifier();
assertTrue(aliceSessionIdentifier.equals(bobSessionIdentifier ));
String decryptedMessage = bobInboundSession.decryptMessage(encryptedMessage);
assertTrue(decryptedMessage.equals(bobSessionIdentifier ));
}
//@Test
public void test02InboundGroupSession() {
// creates alice outbound session
OlmInboundGroupSession aliceInboundSession = new OlmInboundGroupSession();
// test session identifier
String sessionIdentifier = aliceInboundSession.sessionIdentifier();
assertNotNull(sessionIdentifier);
assertTrue(sessionIdentifier.length()>0);
}
}
......@@ -105,7 +105,7 @@ public class OlmSessionTest {
assertTrue(clearMsg.equals(decryptedMsg));
// clean objects..
assertTrue(0==bobAccount.removeOneTimeKeysForSession(bobSession.getOlmSessionId()));
assertTrue(0==bobAccount.removeOneTimeKeysForSession(bobSession));
// release accounts
bobAccount.releaseAccount();
aliceAccount.releaseAccount();
......@@ -191,7 +191,7 @@ public class OlmSessionTest {
// MESSAGE COMPARISON: decrypted vs encrypted
assertTrue(helloClearMsg.equals(decryptedMsg01));
assertTrue(0==bobAccount.removeOneTimeKeysForSession(bobSession.getOlmSessionId()));
assertTrue(0==bobAccount.removeOneTimeKeysForSession(bobSession));
// BACK/FORTH MESSAGE COMPARISON
String clearMsg1 = "Hello I'm Bob!";
......
......@@ -21,7 +21,9 @@ import android.util.Log;
import org.json.JSONException;
import org.json.JSONObject;
public class OlmAccount {
import java.io.Serializable;
public class OlmAccount implements Serializable {
private static final String LOG_TAG = "OlmAccount";
// JSON keys used in the JSON objects returned by JNI
......@@ -67,7 +69,6 @@ public class OlmAccount {
/**
* Create the corresponding OLM account in native side.<br>
* The return value is a long casted C ptr on the OlmAccount.
* Do not forget to call {@link #releaseAccount()} when JAVA side is done.
* @return native account instance identifier (see {@link #mNativeOlmAccountId})
*/
......@@ -87,14 +88,6 @@ public class OlmAccount {
return retCode;
}
/**
* Get the public identity keys (Ed25519 fingerprint key and Curve25519 identity key).<br>
* Keys are Base64 encoded.
* These keys must be published on the server.
* @return byte array containing the identity keys if operation succeed, null otherwise
*/
private native byte[] identityKeysJni();
/**
* Return the identity keys (identity & fingerprint keys) in a JSON array.<br>
* Public API for {@link #identityKeysJni()}.<br>
......@@ -123,6 +116,13 @@ public class OlmAccount {
return identityKeysJsonObj;
}
/**
* Get the public identity keys (Ed25519 fingerprint key and Curve25519 identity key).<br>
* Keys are Base64 encoded.
* These keys must be published on the server.
* @return byte array containing the identity keys if operation succeed, null otherwise
*/
private native byte[] identityKeysJni();
/**
* Return the largest number of "one time keys" this account can store.
......@@ -139,15 +139,6 @@ public class OlmAccount {
*/
public native int generateOneTimeKeys(int aNumberOfKeys);
/**
* Get the public parts of the unpublished "one time keys" for the account.<br>
* The returned data is a JSON-formatted object with the single property
* <tt>curve25519</tt>, which is itself an object mapping key id to
* base64-encoded Curve25519 key.<br>
* @return byte array containing the one time keys if operation succeed, null otherwise
*/
private native byte[] oneTimeKeysJni();
/**
* Return the "one time keys" in a JSON array.<br>
* The number of "one time keys", is specified by {@link #generateOneTimeKeys(int)}<br>
......@@ -181,24 +172,61 @@ public class OlmAccount {
return identityKeysJsonObj;
}
/**
* Get the public parts of the unpublished "one time keys" for the account.<br>
* The returned data is a JSON-formatted object with the single property
* <tt>curve25519</tt>, which is itself an object mapping key id to
* base64-encoded Curve25519 key.<br>
* @return byte array containing the one time keys if operation succeed, null otherwise
*/
private native byte[] oneTimeKeysJni();
/**
* Remove the "one time keys" that the session used from the account.
* @param aSession session instance
* @return 0 if operation succeed, -1 otherwise
*/
public int removeOneTimeKeysForSession(OlmSession aSession) {
int retCode = 0;
if(null != aSession) {
int result = removeOneTimeKeysForSessionJni(aSession.getOlmSessionId());
Log.d(LOG_TAG,"## removeOneTimeKeysForSession(): result="+result);
if(-1 == result) {
retCode = -1;
}
}
return retCode;
}
/**
* Remove the "one time keys" that the session used from the account.
* @param aNativeOlmSessionId native session instance identifier
* @return 0 if operation succeed, 1 if no matching keys in the sessions to be removed, -1 if operation failed
*/
public native int removeOneTimeKeysForSession(long aNativeOlmSessionId);
private native int removeOneTimeKeysForSessionJni(long aNativeOlmSessionId);
/**
* Marks the current set of "one time keys" as being published.
* @return 0 if operation succeed, -1 otherwise
*/
public native int markOneTimeKeysAsPublished();
public int markOneTimeKeysAsPublished() {
return markOneTimeKeysAsPublishedJni();
}
private native int markOneTimeKeysAsPublishedJni();
/**
* Sign a message with the ed25519 fingerprint key for this account.
* @param aMessage message to sign
* @return the signed message if operation succeed, null otherwise
*/
public native String signMessage(String aMessage);
public String signMessage(String aMessage){
return signMessageJni(aMessage);
}
private native String signMessageJni(String aMessage);
// TODO missing API: initWithSerializedData
// TODO missing API: serializeDataWithKey
// TODO missing API: initWithCoder
// TODO missing API: encodeWithCoder
}
/**
* Created by pedrocon on 13/10/2016.
*/
/*
* Copyright 2016 OpenMarket Ltd
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.matrix.olm;
import android.text.TextUtils;
import android.util.Log;
import java.io.Serializable;
public class OlmInboundGroupSession implements Serializable {
private static final String LOG_TAG = "OlmInboundGroupSession";
/** session raw pointer value returned by JNI.<br>
* this value uniquely identifies the native inbound group session instance.
*/
private long mNativeOlmInboundGroupSessionId;
public OlmInboundGroupSession() {
initNewSession();
}
/**
* Getter on the native inbound group session ID.
* @return native inbound group session ID
*/
public long getOlmInboundGroupSessionId(){
return mNativeOlmInboundGroupSessionId;
}
/**
* Release native session and invalid its JAVA reference counter part.<br>
* Public API for {@link #releaseSessionJni()}.
* To be called before any other API call.
*/
public void releaseSession(){
releaseSessionJni();
mNativeOlmInboundGroupSessionId = 0;
}
/**
* Destroy the corresponding OLM inbound group session native object.<br>
* This method must ALWAYS be called when this JAVA instance
* is destroyed (ie. garbage collected) to prevent memory leak in native side.
* See {@link #initNewSessionJni()}.
*/
private native void releaseSessionJni();
/**
* Create and save the session native instance ID.
* Wrapper for {@link #initNewSessionJni()}.<br>
* To be called before any other API call.
* @return true if init succeed, false otherwise.
*/
private boolean initNewSession() {
boolean retCode = false;
if(0 != (mNativeOlmInboundGroupSessionId = initNewSessionJni())){
retCode = true;
}
return retCode;
}
/**
* Create the corresponding OLM inbound group session in native side.<br>
* Do not forget to call {@link #releaseSession()} when JAVA side is done.
* @return native session instance identifier (see {@link #mNativeOlmInboundGroupSessionId})
*/
private native long initNewSessionJni();
/**
* Creates a new inbound group session.<br>
* The session key parameter is retrieved from a outbound group session.
* @param aSessionKey session key
* @return 0 if operation succeed, -1 otherwise
*/
public int initInboundGroupSessionWithSessionKey(String aSessionKey) {
int retCode = -1;
if(TextUtils.isEmpty(aSessionKey)){
Log.e(LOG_TAG, "## initInboundGroupSessionWithSessionKey(): invalid session key");
} else {
retCode = initInboundGroupSessionWithSessionKeyJni(aSessionKey);
}
return retCode;
}
private native int initInboundGroupSessionWithSessionKeyJni(String aSessionKey);
public String sessionIdentifier() {
return sessionIdentifierJni();
}
private native String sessionIdentifierJni();
public String decryptMessage(String aEncryptedMsg) {
return decryptMessageJni(aEncryptedMsg);
}
private native String decryptMessageJni(String aEncryptedMsg);
// TODO missing API: initWithSerializedData
// TODO missing API: serializeDataWithKey
// TODO missing API: initWithCoder
// TODO missing API: encodeWithCoder
}
/*
* Copyright 2016 OpenMarket Ltd
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.matrix.olm;
import android.text.TextUtils;
import android.util.Log;
public class OlmOutboundGroupSession {
private static final String LOG_TAG = "OlmOutboundGroupSession";
/** session raw pointer value returned by JNI.<br>
* this value uniquely identifies the native inbound group session instance.
*/
private long mNativeOlmOutboundGroupSessionId;
public OlmOutboundGroupSession() {
initNewSession();
}
/**
* Getter on the native outbound group session ID.
* @return native outbound group session ID
*/
public long getOlmInboundGroupSessionId(){
return mNativeOlmInboundGroupSessionId;
}
/**
* Release native session and invalid its JAVA reference counter part.<br>
* Public API for {@link #releaseSessionJni()}.
* To be called before any other API call.
*/
public void releaseSession(){
releaseSessionJni();
mNativeOlmOutboundGroupSessionId = 0;
}
/**
* Destroy the corresponding OLM outbound group session native object.<br>
* This method must ALWAYS be called when this JAVA instance
* is destroyed (ie. garbage collected) to prevent memory leak in native side.
* See {@link #initNewSessionJni()}.
*/
private native void releaseSessionJni();
/**
* Create and save the session native instance ID.
* Wrapper for {@link #initNewSessionJni()}.<br>
* To be called before any other API call.
* @return true if init succeed, false otherwise.
*/
private boolean initNewSession() {
boolean retCode = false;
if(0 != (mNativeOlmOutboundGroupSessionId = initNewSessionJni())){
retCode = true;
}
return retCode;
}
/**
* Create the corresponding OLM outbound group session in native side.<br>
* Do not forget to call {@link #releaseSession()} when JAVA side is done.
* @return native session instance identifier (see {@link #mNativeOlmOutboundGroupSessionId})
*/
private native long initNewSessionJni();
/**
* Creates a new outbound group session.<br>
* The session key parameter is retrieved from a outbound group session.
* @return 0 if operation succeed, -1 otherwise
*/
public int initOutboundGroupSession() {
return initOutboundGroupSessionJni();
}
public native int initOutboundGroupSessionJni();
public String sessionIdentifier() {
String retValue = null;
//retValue = sessionIdentifierJni();
return retValue;
}
public native String sessionIdentifierJni();
public long messageIndex() {
long retValue =0;
//retValue = messageIndexJni();
return retValue;
}
private native long messageIndexJni();
public String sessionKey() {
String retValue = null;
//retValue = sessionKeyJni();
return retValue;
}
private native String sessionKeyJni();
public String encryptMessage(String aClearMsg) {
String retValue = null;
//retValue = encryptMessageJni(aClearMsg);
return retValue;
}
private native String encryptMessageJni(String aClearMsg);
}
......@@ -19,7 +19,9 @@ package org.matrix.olm;
import android.text.TextUtils;
import android.util.Log;
public class OlmSession {
import java.io.Serializable;
public class OlmSession implements Serializable {
private static final String LOG_TAG = "OlmSession";
/** session raw pointer value (OlmSession*) returned by JNI.
......@@ -85,7 +87,6 @@ public class OlmSession {
/**
* Create the corresponding OLM session in native side.<br>
* The return value is a long casted C ptr on the OlmSession.
* Do not forget to call {@link #releaseSession()} when JAVA side is done.
* @return native session instance identifier (see {@link #mNativeOlmSessionId})
*/
......@@ -159,6 +160,7 @@ public class OlmSession {
* @param aTheirIdentityKey the sender identity key
* @param aOneTimeKeyMsg PRE KEY message
* @return this if operation succeed, null otherwise
* TODO unit test missing: initInboundSessionWithAccountFrom
*/
public OlmSession initInboundSessionWithAccountFrom(OlmAccount aAccount, String aTheirIdentityKey, String aOneTimeKeyMsg) {
OlmSession retObj=null;
......@@ -198,6 +200,7 @@ public class OlmSession {
* Public API for {@link #matchesInboundSessionJni(String)}.
* @param aOneTimeKeyMsg PRE KEY message
* @return this if operation succeed, null otherwise
* TODO unit test missing: matchesInboundSession
*/
public boolean matchesInboundSession(String aOneTimeKeyMsg) {
boolean retCode = false;
......@@ -218,6 +221,7 @@ public class OlmSession {
* @param aTheirIdentityKey the sender identity key
* @param aOneTimeKeyMsg PRE KEY message
* @return this if operation succeed, null otherwise
* TODO unit test missing: matchesInboundSessionFrom
*/
public boolean matchesInboundSessionFrom(String aTheirIdentityKey, String aOneTimeKeyMsg) {
boolean retCode = false;
......@@ -261,5 +265,10 @@ public class OlmSession {
}
private native String decryptMessageJni(OlmMessage aEncryptedMsg);
// TODO missing API: initWithSerializedData
// TODO missing API: serializeDataWithKey
// TODO missing API: initWithCoder
// TODO missing API: encodeWithCoder
}
......@@ -45,7 +45,8 @@ $(SRC_ROOT_DIR)/lib/crypto-algorithms/aes.c \
$(SRC_ROOT_DIR)/lib/curve25519-donna/curve25519-donna.c \
olm_account.cpp \
olm_session.cpp \
olm_utility.cpp
olm_utility.cpp \
olm_inbound_group_session.cpp
LOCAL_LDLIBS := -llog
......