improve documentation

pull/5/head
Felix Prahl-Kamps 2019-05-27 20:03:27 +02:00
parent b386fb0501
commit 0505507d1d
8 changed files with 119 additions and 40 deletions

View File

@ -1,15 +0,0 @@
<component name="InspectionProjectProfileManager">
<profile version="1.0">
<option name="myName" value="Project Default" />
<inspection_tool class="NullableProblems" enabled="false" level="WARNING" enabled_by_default="false">
<option name="REPORT_NULLABLE_METHOD_OVERRIDES_NOTNULL" value="true" />
<option name="REPORT_NOT_ANNOTATED_METHOD_OVERRIDES_NOTNULL" value="true" />
<option name="REPORT_NOTNULL_PARAMETER_OVERRIDES_NULLABLE" value="true" />
<option name="REPORT_NOT_ANNOTATED_PARAMETER_OVERRIDES_NOTNULL" value="true" />
<option name="REPORT_NOT_ANNOTATED_GETTER" value="true" />
<option name="REPORT_NOT_ANNOTATED_SETTER_PARAMETER" value="true" />
<option name="REPORT_ANNOTATION_NOT_PROPAGATED_TO_OVERRIDERS" value="true" />
<option name="REPORT_NULLS_PASSED_TO_NON_ANNOTATED_METHOD" value="true" />
</inspection_tool>
</profile>
</component>

View File

@ -1,6 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<project version="4"> <project version="4">
<component name="JavadocGenerationManager">
<option name="OUTPUT_DIRECTORY" value="$PROJECT_DIR$/.." />
</component>
<component name="ProjectRootManager" version="2" languageLevel="JDK_1_7" project-jdk-name="1.8" project-jdk-type="JavaSDK"> <component name="ProjectRootManager" version="2" languageLevel="JDK_1_7" project-jdk-name="1.8" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/build/classes" /> <output url="file://$PROJECT_DIR$/build/classes" />
</component> </component>
<component name="ProjectType">
<option name="id" value="Android" />
</component>
</project> </project>

View File

@ -4,6 +4,11 @@ public class KeyValue<K, V> {
public K key; public K key;
public V value; public V value;
/**
* Generates a generic key value pair.
* @param key key
* @param value value
*/
public KeyValue(K key, V value) { public KeyValue(K key, V value) {
this.key = key; this.key = key;
this.value = value; this.value = value;

View File

@ -5,10 +5,14 @@ import android.content.SharedPreferences;
import com.google.gson.Gson; import com.google.gson.Gson;
import java.io.IOException;
import java.security.InvalidAlgorithmParameterException; import java.security.InvalidAlgorithmParameterException;
import java.security.InvalidKeyException; import java.security.InvalidKeyException;
import java.security.Key; import java.security.Key;
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException; import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;
import javax.crypto.BadPaddingException; import javax.crypto.BadPaddingException;
import javax.crypto.IllegalBlockSizeException; import javax.crypto.IllegalBlockSizeException;
@ -39,11 +43,12 @@ public class PreferenceManager {
/** /**
* Helper class to save and retrieve (sensitive) information to and from SharedPreferences. * Helper class to save and retrieve (sensitive) information to and from SharedPreferences.
*
* @param context for accessing the SharedPreferences file. * @param context for accessing the SharedPreferences file.
* @return singleton instance * @return singleton instance
*/ */
public static PreferenceManager getInstance(Context context) { public static PreferenceManager getInstance(Context context) {
if(instance == null) { if (instance == null) {
instance = new PreferenceManager(context); instance = new PreferenceManager(context);
} }
@ -53,6 +58,7 @@ public class PreferenceManager {
/** /**
* Saves user infos from "users/view/me" (encrypted) * Saves user infos from "users/view/me" (encrypted)
*
* @param user * @param user
*/ */
public void setUserInfo(User user) { public void setUserInfo(User user) {
@ -77,6 +83,7 @@ public class PreferenceManager {
} }
/** /**
* Returns the user information if already stored and decrypts it.
* *
* @return decrypted user info if any, else null * @return decrypted user info if any, else null
*/ */
@ -110,6 +117,7 @@ public class PreferenceManager {
/** /**
* Save user org infos from "organisations/view/{orgId}" (encrypted) * Save user org infos from "organisations/view/{orgId}" (encrypted)
*
* @param organisation Object representation of json organisation information * @param organisation Object representation of json organisation information
*/ */
public void setUserOrgInfo(Organisation organisation) { public void setUserOrgInfo(Organisation organisation) {
@ -135,12 +143,13 @@ public class PreferenceManager {
} }
/** /**
* Returns the user organisation information if already stored and decrypts it.
* *
* @return decrypted user org info if any, else null * @return decrypted user org info if any, else null
*/ */
public Organisation getUserOrganisation() { public Organisation getUserOrganisation() {
if(!preferences.contains(USER_ORG_INFOS)) { if (!preferences.contains(USER_ORG_INFOS)) {
return null; return null;
} }
@ -167,7 +176,8 @@ public class PreferenceManager {
/** /**
* Saves the encrypted auth key/automation key * Encrypts the automation key and stores it in preferences.
*
* @param automationKey * @param automationKey
*/ */
public void setAutomationKey(String automationKey) { public void setAutomationKey(String automationKey) {
@ -189,6 +199,11 @@ public class PreferenceManager {
} }
} }
/**
* Decrypts the stored automation key and returns it.
*
* @return the decr
*/
public String getAutomationKey() { public String getAutomationKey() {
if (!preferences.contains(AUTOMATION_KEY)) { if (!preferences.contains(AUTOMATION_KEY)) {
@ -215,6 +230,9 @@ public class PreferenceManager {
return ""; return "";
} }
/**
* Delete the key to decrypt this entry and the entry itself.
*/
public void clearAutomationKey() { public void clearAutomationKey() {
// remove the key from KeyStore // remove the key from KeyStore
KeyStoreWrapper keyStoreWrapper = new KeyStoreWrapper(KeyStoreWrapper.AUTOMATION_ALIAS); KeyStoreWrapper keyStoreWrapper = new KeyStoreWrapper(KeyStoreWrapper.AUTOMATION_ALIAS);
@ -227,8 +245,9 @@ public class PreferenceManager {
/** /**
* Saves the encrypted URL of Misp Server * Encrypts the server url and stores it in preferences.
* @param serverUrl *
* @param serverUrl url of the corresponding misp instance
*/ */
public void setServerUrl(String serverUrl) { public void setServerUrl(String serverUrl) {
try { try {
@ -251,6 +270,11 @@ public class PreferenceManager {
} }
} }
/**
* Decrypts the stored server url and returns it
*
* @return decrypted misp instance url
*/
public String getServerUrl() { public String getServerUrl() {
if (!preferences.contains(SERVER_URL)) { if (!preferences.contains(SERVER_URL)) {
@ -278,6 +302,9 @@ public class PreferenceManager {
return ""; return "";
} }
/**
* Delete the key to decrypt this entry and the entry itself.
*/
public void clearServerUrl() { public void clearServerUrl() {
// remove the key from KeyStore // remove the key from KeyStore
KeyStoreWrapper keyStoreWrapper = new KeyStoreWrapper(KeyStoreWrapper.SERVER_URL_ALIAS); KeyStoreWrapper keyStoreWrapper = new KeyStoreWrapper(KeyStoreWrapper.SERVER_URL_ALIAS);
@ -291,7 +318,10 @@ public class PreferenceManager {
/** /**
* Set if credentials (authkey & server url) should be saved locally. * Set if credentials (authkey & server url) should be saved locally.
*
* @param save enable or disable * @param save enable or disable
* @deprecated currently not used because automation key is needed to do requests to your misp instance.
* If this should be an option in future: misp automation key would be needed on each sync process.
*/ */
public void setSaveCredentials(boolean save) { public void setSaveCredentials(boolean save) {
SharedPreferences.Editor editor = preferences.edit(); SharedPreferences.Editor editor = preferences.edit();

View File

@ -25,6 +25,10 @@ import retrofit2.Response;
import retrofit2.Retrofit; import retrofit2.Retrofit;
import retrofit2.converter.gson.GsonConverterFactory; import retrofit2.converter.gson.GsonConverterFactory;
/**
* Implementation of the RetroFit2 Misp client.
* In order to conveniently use this api some wrapper interfaces are implemented to return the requested API endpoint as java object.
*/
public class MispRestClient { public class MispRestClient {
// callbacks and interfaces // callbacks and interfaces
@ -81,7 +85,7 @@ public class MispRestClient {
} }
/** /**
* For development only! * NOTE: for development only!
* Accepts all certificates so self signed certs are also accepted. * Accepts all certificates so self signed certs are also accepted.
* @return OkHttpClient which accepts all certificates * @return OkHttpClient which accepts all certificates
*/ */

View File

@ -8,6 +8,9 @@ import retrofit2.http.GET;
import retrofit2.http.POST; import retrofit2.http.POST;
import retrofit2.http.Path; import retrofit2.http.Path;
/**
* RetroFit2 interface for communication with misp instances
*/
public interface MispRestService { public interface MispRestService {
// user routes // user routes

View File

@ -18,6 +18,7 @@ public class AESSecurity {
private static final String KEY_PAIR_ALGORITHM = "EC"; private static final String KEY_PAIR_ALGORITHM = "EC";
private static final int KEY_SIZE = 521; // 224 | 256 | 384 | 521 private static final int KEY_SIZE = 521; // 224 | 256 | 384 | 521
private static final String KEY_AGREEMENT_ALGORITHM = "ECDH"; private static final String KEY_AGREEMENT_ALGORITHM = "ECDH";
private static final String KEY_FACTORY_ALGORITHM = "EC";
private static AESSecurity instance; private static AESSecurity instance;
@ -31,9 +32,9 @@ public class AESSecurity {
initialize(); initialize();
} }
/*** /**
* Generates a public and a private key using an elliptic curve algorithm (256 bit) * Generates a public and a private key using an elliptic curve algorithm.
* The private key is fed into the key agreement instance * The private key is fed into the key agreement instance.
*/ */
private void initialize() { private void initialize() {
@ -52,9 +53,9 @@ public class AESSecurity {
} }
} }
/*** /**
* Generates a shared secret with a given public key * Generates a shared secret and derives an initialisation vector from it.
* @param publickey * @param publickey public key of the sync partner
*/ */
public void setForeignPublicKey(PublicKey publickey) { public void setForeignPublicKey(PublicKey publickey) {
@ -72,6 +73,11 @@ public class AESSecurity {
} }
} }
/**
*
* @param data
* @return
*/
public String encrypt(String data) { public String encrypt(String data) {
try { try {
@ -93,6 +99,11 @@ public class AESSecurity {
return data; return data;
} }
/**
*
* @param data
* @return
*/
public String decrypt(String data) { public String decrypt(String data) {
try { try {
Key key = generateKey(); Key key = generateKey();
@ -119,9 +130,7 @@ public class AESSecurity {
} }
private Key generateKey() { private Key generateKey() {
return new SecretKeySpec(sharedSecret, ENCRYPT_ALGORITHM); return new SecretKeySpec(sharedSecret, ENCRYPT_ALGORITHM);
} }
public static String publicKeyToString(PublicKey key) { public static String publicKeyToString(PublicKey key) {
@ -129,11 +138,10 @@ public class AESSecurity {
} }
public static PublicKey publicKeyFromString(String key) { public static PublicKey publicKeyFromString(String key) {
try { try {
byte[] input = Base64.decode(key, Base64.DEFAULT); byte[] input = Base64.decode(key, Base64.DEFAULT);
return KeyFactory.getInstance("EC").generatePublic(new X509EncodedKeySpec(input)); return KeyFactory.getInstance(KEY_FACTORY_ALGORITHM).generatePublic(new X509EncodedKeySpec(input));
} catch (NoSuchAlgorithmException | InvalidKeySpecException e) { } catch (NoSuchAlgorithmException | InvalidKeySpecException e) {
e.printStackTrace(); e.printStackTrace();
@ -143,12 +151,9 @@ public class AESSecurity {
} }
public static AESSecurity getInstance() { public static AESSecurity getInstance() {
if(instance == null) { if(instance == null) {
instance = new AESSecurity(); instance = new AESSecurity();
} }
return instance; return instance;
} }
} }

View File

@ -40,10 +40,17 @@ public class KeyStoreWrapper {
private String KEYSTORE_ALIAS; private String KEYSTORE_ALIAS;
/**
* Wraps the android key store to easily encrypt and decrypt sensitive data.
* @param alias identifies a key store entry (see public static ALIAS variables).
*/
public KeyStoreWrapper(String alias) { public KeyStoreWrapper(String alias) {
KEYSTORE_ALIAS = alias; KEYSTORE_ALIAS = alias;
} }
/**
* @return wheter an entry for this alias already exists.
*/
private boolean isInitialized() { private boolean isInitialized() {
try { try {
KeyStore ks = KeyStore.getInstance(KEYSTORE_PROVIDER); KeyStore ks = KeyStore.getInstance(KEYSTORE_PROVIDER);
@ -66,6 +73,10 @@ public class KeyStoreWrapper {
} }
/**
*
* @return SecretKey associated with the given alias.
*/
private SecretKey getStoredKey() { private SecretKey getStoredKey() {
try { try {
@ -88,6 +99,10 @@ public class KeyStoreWrapper {
return null; return null;
} }
/**
* Generates a new key.
* @return the newly generated key.
*/
private SecretKey generateKey() { private SecretKey generateKey() {
try { try {
@ -117,7 +132,9 @@ public class KeyStoreWrapper {
return null; return null;
} }
/**
* Deletes the key associated with the current alias.
*/
public void deleteStoredKey() { public void deleteStoredKey() {
try { try {
KeyStore ks = KeyStore.getInstance(KEYSTORE_PROVIDER); KeyStore ks = KeyStore.getInstance(KEYSTORE_PROVIDER);
@ -134,6 +151,16 @@ public class KeyStoreWrapper {
} }
} }
/**
* Encrypt data with given algorithm and key associated with alias.
* @param data data to encrypt.
* @return encrypted data as String.
* @throws NoSuchPaddingException
* @throws NoSuchAlgorithmException
* @throws InvalidKeyException
* @throws BadPaddingException
* @throws IllegalBlockSizeException
*/
public String encrypt(String data) throws NoSuchPaddingException, NoSuchAlgorithmException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException { public String encrypt(String data) throws NoSuchPaddingException, NoSuchAlgorithmException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
SecretKey secretKey; SecretKey secretKey;
@ -153,6 +180,17 @@ public class KeyStoreWrapper {
return ivString + ":::" + encryptedDataString; return ivString + ":::" + encryptedDataString;
} }
/**
* Decrypts data with given algorithm and key associated with alias.
* @param input encrypted data.
* @return decrypted data as String.
* @throws NoSuchPaddingException
* @throws NoSuchAlgorithmException
* @throws InvalidAlgorithmParameterException
* @throws InvalidKeyException
* @throws BadPaddingException
* @throws IllegalBlockSizeException
*/
public String decrypt(String input) throws NoSuchPaddingException, NoSuchAlgorithmException, InvalidAlgorithmParameterException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException { public String decrypt(String input) throws NoSuchPaddingException, NoSuchAlgorithmException, InvalidAlgorithmParameterException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
// extract iv from save data // extract iv from save data
@ -169,7 +207,10 @@ public class KeyStoreWrapper {
return new String(cipher.doFinal(data), StandardCharsets.UTF_8); return new String(cipher.doFinal(data), StandardCharsets.UTF_8);
} }
/**
* Removes all aliases and the associated keys.
* Note: all encrypted data cannot be decrypted anymore!
*/
public static void deleteAllStoredKeys() { public static void deleteAllStoredKeys() {
try { try {