mirror of
https://github.com/moparisthebest/open-keychain
synced 2024-11-30 04:22:18 -05:00
Moved checks from fragment to operation, impoved logging.
This commit is contained in:
parent
76241e90ad
commit
a0107afd3e
@ -19,6 +19,7 @@ package org.sufficientlysecure.keychain.operations;
|
|||||||
|
|
||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
|
|
||||||
|
import org.spongycastle.bcpg.PublicKeyAlgorithmTags;
|
||||||
import org.sufficientlysecure.keychain.operations.results.NfcKeyToCardResult;
|
import org.sufficientlysecure.keychain.operations.results.NfcKeyToCardResult;
|
||||||
import org.sufficientlysecure.keychain.operations.results.OperationResult;
|
import org.sufficientlysecure.keychain.operations.results.OperationResult;
|
||||||
import org.sufficientlysecure.keychain.pgp.CanonicalizedSecretKey;
|
import org.sufficientlysecure.keychain.pgp.CanonicalizedSecretKey;
|
||||||
@ -26,6 +27,7 @@ import org.sufficientlysecure.keychain.pgp.CanonicalizedSecretKeyRing;
|
|||||||
import org.sufficientlysecure.keychain.pgp.Progressable;
|
import org.sufficientlysecure.keychain.pgp.Progressable;
|
||||||
import org.sufficientlysecure.keychain.provider.ProviderHelper;
|
import org.sufficientlysecure.keychain.provider.ProviderHelper;
|
||||||
import org.sufficientlysecure.keychain.service.input.RequiredInputParcel;
|
import org.sufficientlysecure.keychain.service.input.RequiredInputParcel;
|
||||||
|
import org.sufficientlysecure.keychain.ui.util.KeyFormattingUtils;
|
||||||
|
|
||||||
public class NfcKeyToCardOperation extends BaseOperation {
|
public class NfcKeyToCardOperation extends BaseOperation {
|
||||||
public NfcKeyToCardOperation(Context context, ProviderHelper providerHelper, Progressable progressable) {
|
public NfcKeyToCardOperation(Context context, ProviderHelper providerHelper, Progressable progressable) {
|
||||||
@ -43,32 +45,46 @@ public class NfcKeyToCardOperation extends BaseOperation {
|
|||||||
CanonicalizedSecretKeyRing keyRing =
|
CanonicalizedSecretKeyRing keyRing =
|
||||||
mProviderHelper.getCanonicalizedSecretKeyRing(masterKeyId);
|
mProviderHelper.getCanonicalizedSecretKeyRing(masterKeyId);
|
||||||
|
|
||||||
log.add(OperationResult.LogType.MSG_KC_SECRET, indent);
|
log.add(OperationResult.LogType.MSG_KC_SECRET, indent,
|
||||||
|
KeyFormattingUtils.convertKeyIdToHex(masterKeyId));
|
||||||
|
|
||||||
// fetch the specific subkey
|
// fetch the specific subkey
|
||||||
CanonicalizedSecretKey subKey = keyRing.getSecretKey(subKeyId);
|
CanonicalizedSecretKey subKey = keyRing.getSecretKey(subKeyId);
|
||||||
|
|
||||||
switch (subKey.getSecretKeyType()) {
|
// Key algorithm must be RSA
|
||||||
case DIVERT_TO_CARD:
|
int algorithm = subKey.getAlgorithm();
|
||||||
case GNU_DUMMY: {
|
if (algorithm != PublicKeyAlgorithmTags.RSA_ENCRYPT &&
|
||||||
throw new AssertionError(
|
algorithm != PublicKeyAlgorithmTags.RSA_SIGN &&
|
||||||
"Cannot export GNU_DUMMY/DIVERT_TO_CARD key to a smart card!"
|
algorithm != PublicKeyAlgorithmTags.RSA_GENERAL) {
|
||||||
+ " This is a programming error!");
|
log.add(OperationResult.LogType.MSG_K2C_ERROR_BAD_ALGO, indent + 1);
|
||||||
}
|
return new NfcKeyToCardResult(NfcKeyToCardResult.RESULT_ERROR, log);
|
||||||
|
|
||||||
case PIN:
|
|
||||||
case PATTERN:
|
|
||||||
case PASSPHRASE: {
|
|
||||||
log.add(OperationResult.LogType.MSG_PSE_PENDING_NFC, indent);
|
|
||||||
return new NfcKeyToCardResult(log, RequiredInputParcel
|
|
||||||
.createNfcKeyToCardOperation(masterKeyId, subKeyId));
|
|
||||||
}
|
|
||||||
|
|
||||||
default: {
|
|
||||||
throw new AssertionError("Unhandled SecretKeyType! (should not happen)");
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Key size must be 2048
|
||||||
|
int keySize = subKey.getBitStrength();
|
||||||
|
if (keySize != 2048) {
|
||||||
|
log.add(OperationResult.LogType.MSG_K2C_ERROR_BAD_SIZE, indent + 1);
|
||||||
|
return new NfcKeyToCardResult(NfcKeyToCardResult.RESULT_ERROR, log);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Secret key parts must be available
|
||||||
|
CanonicalizedSecretKey.SecretKeyType type = subKey.getSecretKeyType();
|
||||||
|
if (type == CanonicalizedSecretKey.SecretKeyType.DIVERT_TO_CARD ||
|
||||||
|
type == CanonicalizedSecretKey.SecretKeyType.GNU_DUMMY) {
|
||||||
|
log.add(OperationResult.LogType.MSG_K2C_ERROR_BAD_STRIPPED, indent + 1);
|
||||||
|
return new NfcKeyToCardResult(NfcKeyToCardResult.RESULT_ERROR, log);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (type == CanonicalizedSecretKey.SecretKeyType.PIN ||
|
||||||
|
type == CanonicalizedSecretKey.SecretKeyType.PATTERN ||
|
||||||
|
type == CanonicalizedSecretKey.SecretKeyType.PASSPHRASE ||
|
||||||
|
type == CanonicalizedSecretKey.SecretKeyType.PASSPHRASE_EMPTY) {
|
||||||
|
log.add(OperationResult.LogType.MSG_PSE_PENDING_NFC, indent);
|
||||||
|
return new NfcKeyToCardResult(log, RequiredInputParcel
|
||||||
|
.createNfcKeyToCardOperation(masterKeyId, subKeyId));
|
||||||
|
}
|
||||||
|
|
||||||
|
throw new AssertionError("Unhandled SecretKeyType! (should not happen)");
|
||||||
} catch (ProviderHelper.NotFoundException e) {
|
} catch (ProviderHelper.NotFoundException e) {
|
||||||
log.add(OperationResult.LogType.MSG_PSE_ERROR_UNLOCK, indent);
|
log.add(OperationResult.LogType.MSG_PSE_ERROR_UNLOCK, indent);
|
||||||
return new NfcKeyToCardResult(NfcKeyToCardResult.RESULT_ERROR, log);
|
return new NfcKeyToCardResult(NfcKeyToCardResult.RESULT_ERROR, log);
|
||||||
|
@ -17,6 +17,8 @@
|
|||||||
|
|
||||||
package org.sufficientlysecure.keychain.operations.results;
|
package org.sufficientlysecure.keychain.operations.results;
|
||||||
|
|
||||||
|
import android.os.Parcel;
|
||||||
|
|
||||||
import org.sufficientlysecure.keychain.service.input.RequiredInputParcel;
|
import org.sufficientlysecure.keychain.service.input.RequiredInputParcel;
|
||||||
|
|
||||||
public class NfcKeyToCardResult extends InputPendingResult {
|
public class NfcKeyToCardResult extends InputPendingResult {
|
||||||
@ -27,4 +29,23 @@ public class NfcKeyToCardResult extends InputPendingResult {
|
|||||||
public NfcKeyToCardResult(OperationLog log, RequiredInputParcel requiredInput) {
|
public NfcKeyToCardResult(OperationLog log, RequiredInputParcel requiredInput) {
|
||||||
super(log, requiredInput);
|
super(log, requiredInput);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public NfcKeyToCardResult(Parcel source) {
|
||||||
|
super(source);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void writeToParcel(Parcel dest, int flags) {
|
||||||
|
super.writeToParcel(dest, flags);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Creator<NfcKeyToCardResult> CREATOR = new Creator<NfcKeyToCardResult>() {
|
||||||
|
public NfcKeyToCardResult createFromParcel(final Parcel source) {
|
||||||
|
return new NfcKeyToCardResult(source);
|
||||||
|
}
|
||||||
|
|
||||||
|
public NfcKeyToCardResult[] newArray(final int size) {
|
||||||
|
return new NfcKeyToCardResult[size];
|
||||||
|
}
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
@ -736,6 +736,11 @@ public abstract class OperationResult implements Parcelable {
|
|||||||
MSG_EXPORT_LOG_EXPORT_ERROR_FOPEN(LogLevel.ERROR,R.string.msg_export_log_error_fopen),
|
MSG_EXPORT_LOG_EXPORT_ERROR_FOPEN(LogLevel.ERROR,R.string.msg_export_log_error_fopen),
|
||||||
MSG_EXPORT_LOG_EXPORT_ERROR_WRITING(LogLevel.ERROR,R.string.msg_export_log_error_writing),
|
MSG_EXPORT_LOG_EXPORT_ERROR_WRITING(LogLevel.ERROR,R.string.msg_export_log_error_writing),
|
||||||
MSG_EXPORT_LOG_EXPORT_SUCCESS (LogLevel.OK, R.string.msg_export_log_success),
|
MSG_EXPORT_LOG_EXPORT_SUCCESS (LogLevel.OK, R.string.msg_export_log_success),
|
||||||
|
|
||||||
|
// NFC keytocard
|
||||||
|
MSG_K2C_ERROR_BAD_ALGO(LogLevel.ERROR, R.string.edit_key_error_bad_nfc_algo),
|
||||||
|
MSG_K2C_ERROR_BAD_SIZE(LogLevel.ERROR, R.string.edit_key_error_bad_nfc_size),
|
||||||
|
MSG_K2C_ERROR_BAD_STRIPPED(LogLevel.ERROR, R.string.edit_key_error_bad_nfc_stripped),
|
||||||
;
|
;
|
||||||
|
|
||||||
public final int mMsgId;
|
public final int mMsgId;
|
||||||
|
@ -36,14 +36,12 @@ import android.view.ViewGroup;
|
|||||||
import android.widget.AdapterView;
|
import android.widget.AdapterView;
|
||||||
import android.widget.ListView;
|
import android.widget.ListView;
|
||||||
|
|
||||||
import org.spongycastle.bcpg.PublicKeyAlgorithmTags;
|
|
||||||
import org.sufficientlysecure.keychain.Constants;
|
import org.sufficientlysecure.keychain.Constants;
|
||||||
import org.sufficientlysecure.keychain.R;
|
import org.sufficientlysecure.keychain.R;
|
||||||
import org.sufficientlysecure.keychain.compatibility.DialogFragmentWorkaround;
|
import org.sufficientlysecure.keychain.compatibility.DialogFragmentWorkaround;
|
||||||
import org.sufficientlysecure.keychain.operations.results.OperationResult;
|
import org.sufficientlysecure.keychain.operations.results.OperationResult;
|
||||||
import org.sufficientlysecure.keychain.operations.results.OperationResult.LogType;
|
import org.sufficientlysecure.keychain.operations.results.OperationResult.LogType;
|
||||||
import org.sufficientlysecure.keychain.operations.results.SingletonResult;
|
import org.sufficientlysecure.keychain.operations.results.SingletonResult;
|
||||||
import org.sufficientlysecure.keychain.pgp.CanonicalizedSecretKey;
|
|
||||||
import org.sufficientlysecure.keychain.pgp.KeyRing;
|
import org.sufficientlysecure.keychain.pgp.KeyRing;
|
||||||
import org.sufficientlysecure.keychain.pgp.exception.PgpKeyNotFoundException;
|
import org.sufficientlysecure.keychain.pgp.exception.PgpKeyNotFoundException;
|
||||||
import org.sufficientlysecure.keychain.provider.CachedPublicKeyRing;
|
import org.sufficientlysecure.keychain.provider.CachedPublicKeyRing;
|
||||||
@ -430,35 +428,6 @@ public class EditKeyFragment extends CryptoOperationFragment implements
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case EditSubkeyDialogFragment.MESSAGE_KEYTOCARD: {
|
case EditSubkeyDialogFragment.MESSAGE_KEYTOCARD: {
|
||||||
// Three checks to verify that this is a smart card compatible key:
|
|
||||||
|
|
||||||
// 1. Key algorithm must be RSA
|
|
||||||
int algorithm = mSubkeysAdapter.getAlgorithm(position);
|
|
||||||
if (algorithm != PublicKeyAlgorithmTags.RSA_ENCRYPT &&
|
|
||||||
algorithm != PublicKeyAlgorithmTags.RSA_SIGN &&
|
|
||||||
algorithm != PublicKeyAlgorithmTags.RSA_GENERAL) {
|
|
||||||
Notify.create(getActivity(), R.string.edit_key_error_bad_nfc_algo,
|
|
||||||
Notify.Style.ERROR).show();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// 2. Key size must be 2048
|
|
||||||
if (mSubkeysAdapter.getKeySize(position) != 2048) {
|
|
||||||
Notify.create(getActivity(), R.string.edit_key_error_bad_nfc_size,
|
|
||||||
Notify.Style.ERROR).show();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// 3. Secret key parts must be available
|
|
||||||
CanonicalizedSecretKey.SecretKeyType type =
|
|
||||||
mSubkeysAdapter.getSecretKeyType(position);
|
|
||||||
if (type == CanonicalizedSecretKey.SecretKeyType.DIVERT_TO_CARD ||
|
|
||||||
type == CanonicalizedSecretKey.SecretKeyType.GNU_DUMMY) {
|
|
||||||
Notify.create(getActivity(), R.string.edit_key_error_bad_nfc_stripped,
|
|
||||||
Notify.Style.ERROR).show();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
SubkeyChange change;
|
SubkeyChange change;
|
||||||
change = mSaveKeyringParcel.getSubkeyChange(keyId);
|
change = mSaveKeyringParcel.getSubkeyChange(keyId);
|
||||||
if (change == null) {
|
if (change == null) {
|
||||||
@ -480,7 +449,15 @@ public class EditKeyFragment extends CryptoOperationFragment implements
|
|||||||
ProgressDialogFragment.ServiceType.KEYCHAIN_INTENT) {
|
ProgressDialogFragment.ServiceType.KEYCHAIN_INTENT) {
|
||||||
public void handleMessage(Message message) {
|
public void handleMessage(Message message) {
|
||||||
super.handleMessage(message);
|
super.handleMessage(message);
|
||||||
EditKeyFragment.this.handlePendingMessage(message);
|
if (EditKeyFragment.this.handlePendingMessage(message)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
Bundle data = message.getData();
|
||||||
|
OperationResult result = data.getParcelable(OperationResult.EXTRA_RESULT);
|
||||||
|
if (result.getResult() == OperationResult.RESULT_ERROR) {
|
||||||
|
result.createNotify(getActivity()).show();
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
// Create a new Messenger for the communication back
|
// Create a new Messenger for the communication back
|
||||||
|
Loading…
Reference in New Issue
Block a user