diff options
Diffstat (limited to 'src/core/function')
-rw-r--r-- | src/core/function/gpg/GpgAbstractKeyGetter.cpp | 2 | ||||
-rw-r--r-- | src/core/function/gpg/GpgAutomatonHandler.cpp | 99 | ||||
-rw-r--r-- | src/core/function/gpg/GpgAutomatonHandler.h | 64 | ||||
-rw-r--r-- | src/core/function/gpg/GpgKeyImportExporter.cpp | 5 | ||||
-rw-r--r-- | src/core/function/gpg/GpgKeyImportExporter.h | 2 | ||||
-rw-r--r-- | src/core/function/gpg/GpgKeyManager.cpp | 200 | ||||
-rw-r--r-- | src/core/function/gpg/GpgSmartCardManager.cpp | 159 | ||||
-rw-r--r-- | src/core/function/gpg/GpgSmartCardManager.h | 10 | ||||
-rw-r--r-- | src/core/function/gpg/GpgUIDOperator.cpp | 144 |
9 files changed, 419 insertions, 266 deletions
diff --git a/src/core/function/gpg/GpgAbstractKeyGetter.cpp b/src/core/function/gpg/GpgAbstractKeyGetter.cpp index 193fec0e..581d027e 100644 --- a/src/core/function/gpg/GpgAbstractKeyGetter.cpp +++ b/src/core/function/gpg/GpgAbstractKeyGetter.cpp @@ -54,7 +54,7 @@ auto GpgAbstractKeyGetter::Fetch() -> GpgAbstractKeyPtrList { auto GpgAbstractKeyGetter::GetGpgKeyTableModel() -> QSharedPointer<GpgKeyTableModel> { - return SecureCreateQSharedObject<GpgKeyTableModel>( + return SecureCreateSharedObject<GpgKeyTableModel>( SingletonFunctionObject::GetChannel(), Fetch(), nullptr); } diff --git a/src/core/function/gpg/GpgAutomatonHandler.cpp b/src/core/function/gpg/GpgAutomatonHandler.cpp index 33c94436..6cf06ab6 100644 --- a/src/core/function/gpg/GpgAutomatonHandler.cpp +++ b/src/core/function/gpg/GpgAutomatonHandler.cpp @@ -28,6 +28,8 @@ #include "GpgAutomatonHandler.h" +#include <utility> + #include "core/model/GpgData.h" #include "core/model/GpgKey.h" #include "core/utils/GpgUtils.h" @@ -37,9 +39,8 @@ namespace GpgFrontend { GpgAutomatonHandler::GpgAutomatonHandler(int channel) : SingletonFunctionObject<GpgAutomatonHandler>(channel) {} -auto GpgAutomatonHandler::interator_cb_func(void* handle, const char* status, - const char* args, - int fd) -> gpgme_error_t { +auto InteratorCbFunc(void* handle, const char* status, const char* args, + int fd) -> gpgme_error_t { auto* handle_struct = static_cast<AutomatonHandelStruct*>(handle); QString status_s = status; QString args_s = args; @@ -47,8 +48,26 @@ auto GpgAutomatonHandler::interator_cb_func(void* handle, const char* status, if (status_s == "KEY_CONSIDERED") { auto tokens = QString(args).split(' '); + if (handle_struct->KeyFpr().isEmpty()) return 0; + if (tokens.empty() || tokens[0] != handle_struct->KeyFpr()) { - LOG_W() << "handle struct key fpr " << handle_struct->KeyFpr() + LOG_W() << "handle struct key fpr: " << handle_struct->KeyFpr() + << "mismatch token: " << tokens[0] << ", exit..."; + + return -1; + } + + return 0; + } + + if (status_s == "CARDCTRL") { + auto tokens = QString(args).split(' '); + + if (handle_struct->SerialNumber().isEmpty()) return 0; + + if (tokens.empty() || tokens[0] != handle_struct->SerialNumber()) { + LOG_W() << "handle struct serial number: " + << handle_struct->SerialNumber() << "mismatch token: " << tokens[0] << ", exit..."; return -1; @@ -65,20 +84,22 @@ auto GpgAutomatonHandler::interator_cb_func(void* handle, const char* status, LOG_D() << "current state" << handle_struct->CurrentStatus() << "gpg status: " << status_s << ", args: " << args_s; + handle_struct->SetPromptStatus(status_s, args_s); + AutomatonState next_state = handle_struct->NextState(status_s, args_s); - if (next_state == AS_ERROR) { + if (next_state == GpgAutomatonHandler::kAS_ERROR) { FLOG_D("handle struct next state caught error, abort..."); return -1; } LOG_D() << "next state" << next_state; - if (next_state == AS_SAVE) { + if (next_state == GpgAutomatonHandler::kAS_SAVE) { handle_struct->SetSuccess(true); } // set state and preform action handle_struct->SetStatus(next_state); - Command cmd = handle_struct->Action(); + GpgAutomatonHandler::Command cmd = handle_struct->Action(); LOG_D() << "next action, cmd:" << cmd; @@ -86,7 +107,7 @@ auto GpgAutomatonHandler::interator_cb_func(void* handle, const char* status, auto btye_array = cmd.toUtf8(); gpgme_io_write(fd, btye_array, btye_array.size()); gpgme_io_write(fd, "\n", 1); - } else if (status_s == "GET_LINE") { + } else if (status_s.startsWith("GET_")) { // avoid trapping in this state return GPG_ERR_FALSE; } @@ -94,30 +115,40 @@ auto GpgAutomatonHandler::interator_cb_func(void* handle, const char* status, return 0; } -auto GpgAutomatonHandler::DoInteract( - const GpgKeyPtr& key, AutomatonNextStateHandler next_state_handler, - AutomatonActionHandler action_handler, int flags) -> bool { - gpgme_key_t p_key = - flags == GPGME_INTERACT_CARD ? nullptr : static_cast<gpgme_key_t>(*key); +auto DoInteractImpl(GpgContext& ctx_, const GpgKeyPtr& key, bool card_edit, + const QString& id, + AutomatonNextStateHandler next_state_handler, + AutomatonActionHandler action_handler, int flags) -> bool { + gpgme_key_t p_key = key == nullptr ? nullptr : static_cast<gpgme_key_t>(*key); - AutomatonHandelStruct handel_struct( - flags == GPGME_INTERACT_CARD ? "" : key->Fingerprint()); + AutomatonHandelStruct handel_struct(card_edit, id); handel_struct.SetHandler(std::move(next_state_handler), std::move(action_handler)); GpgData data_out; - auto err = gpgme_op_interact(ctx_.DefaultContext(), p_key, flags, - GpgAutomatonHandler::interator_cb_func, - static_cast<void*>(&handel_struct), data_out); + auto err = + gpgme_op_interact(ctx_.DefaultContext(), p_key, flags, InteratorCbFunc, + static_cast<void*>(&handel_struct), data_out); return CheckGpgError(err) == GPG_ERR_NO_ERROR && handel_struct.Success(); } +auto GpgAutomatonHandler::DoInteract( + const GpgKeyPtr& key, AutomatonNextStateHandler next_state_handler, + AutomatonActionHandler action_handler, int flags) -> bool { + assert(key != nullptr); + if (key == nullptr) return false; + return DoInteractImpl(ctx_, key, false, key->ID(), + std::move(next_state_handler), + std::move(action_handler), flags); +} + auto GpgAutomatonHandler::DoCardInteract( - AutomatonNextStateHandler next_state_handler, + const QString& serial_number, AutomatonNextStateHandler next_state_handler, AutomatonActionHandler action_handler) -> bool { - return DoInteract({}, std::move(next_state_handler), - std::move(action_handler), GPGME_INTERACT_CARD); + return DoInteractImpl(ctx_, nullptr, true, serial_number, + std::move(next_state_handler), + std::move(action_handler), GPGME_INTERACT_CARD); } auto GpgAutomatonHandler::AutomatonHandelStruct::NextState( @@ -133,7 +164,7 @@ void GpgAutomatonHandler::AutomatonHandelStruct::SetHandler( action_handler_ = std::move(action_handler); } -auto GpgAutomatonHandler::AutomatonHandelStruct::CurrentStatus() +auto GpgAutomatonHandler::AutomatonHandelStruct::CurrentStatus() const -> AutomatonState { return current_state_; } @@ -154,11 +185,27 @@ void GpgAutomatonHandler::AutomatonHandelStruct::SetSuccess(bool success) { auto GpgAutomatonHandler::AutomatonHandelStruct::Success() const -> bool { return success_; } -auto GpgAutomatonHandler::AutomatonHandelStruct::KeyFpr() -> QString { - return key_fpr_; +auto GpgAutomatonHandler::AutomatonHandelStruct::KeyFpr() const -> QString { + return card_edit_ ? "" : id_; } GpgAutomatonHandler::AutomatonHandelStruct::AutomatonHandelStruct( - QString key_fpr) - : key_fpr_(std::move(key_fpr)) {} + bool card_edit, QString id) + : card_edit_(card_edit), id_(std::move(id)) {} + +auto GpgAutomatonHandler::AutomatonHandelStruct::PromptStatus() const + -> std::tuple<QString, QString> { + return {prompt_status_, prompt_args_}; +} + +void GpgAutomatonHandler::AutomatonHandelStruct::SetPromptStatus(QString status, + QString args) { + prompt_status_ = std::move(status); + prompt_args_ = std::move(args); +} + +auto GpgAutomatonHandler::AutomatonHandelStruct::SerialNumber() const + -> QString { + return card_edit_ ? id_ : ""; +} } // namespace GpgFrontend
\ No newline at end of file diff --git a/src/core/function/gpg/GpgAutomatonHandler.h b/src/core/function/gpg/GpgAutomatonHandler.h index cdf96060..d142bbcc 100644 --- a/src/core/function/gpg/GpgAutomatonHandler.h +++ b/src/core/function/gpg/GpgAutomatonHandler.h @@ -28,6 +28,8 @@ #pragma once +#include <utility> + #include "core/GpgFrontendCore.h" #include "core/function/basic/GpgFunctionObject.h" #include "core/function/gpg/GpgContext.h" @@ -40,16 +42,18 @@ class GpgAutomatonHandler public: using Command = QString; using AutomatonState = enum { - AS_START, - AS_SELECT, - AS_COMMAND, - AS_VALUE, - AS_REASON_CODE, - AS_REASON_TEXT, - AS_REALLY_ULTIMATE, - AS_SAVE, - AS_ERROR, - AS_QUIT, + kAS_START, + kAS_SELECT, + kAS_COMMAND, + kAS_VALUE, + kAS_ADMIN, + kAS_REASON_CODE, + kAS_REASON_TEXT, + kAS_REALLY_ULTIMATE, + kAS_SAVE, + kAS_INFO, + kAS_ERROR, + kAS_QUIT, }; struct AutomatonHandelStruct; @@ -60,23 +64,32 @@ class GpgAutomatonHandler std::function<AutomatonState(AutomatonState, QString, QString)>; struct AutomatonHandelStruct { - explicit AutomatonHandelStruct(QString key_fpr); - void SetStatus(AutomatonState next_state); - auto CurrentStatus() -> AutomatonState; - void SetHandler(AutomatonNextStateHandler next_state_handler, - AutomatonActionHandler action_handler); + explicit AutomatonHandelStruct(bool card_edit, QString id); + auto NextState(QString gpg_status, QString args) -> AutomatonState; auto Action() -> Command; + + void SetStatus(AutomatonState next_state); void SetSuccess(bool success); + void SetPromptStatus(QString status, QString args); + void SetHandler(AutomatonNextStateHandler next_state_handler, + AutomatonActionHandler action_handler); + + [[nodiscard]] auto CurrentStatus() const -> AutomatonState; [[nodiscard]] auto Success() const -> bool; - auto KeyFpr() -> QString; + [[nodiscard]] auto KeyFpr() const -> QString; + [[nodiscard]] auto SerialNumber() const -> QString; + [[nodiscard]] auto PromptStatus() const -> std::tuple<QString, QString>; private: - AutomatonState current_state_ = AS_START; + AutomatonState current_state_ = kAS_START; AutomatonNextStateHandler next_state_handler_; AutomatonActionHandler action_handler_; bool success_ = false; - QString key_fpr_; + bool card_edit_; + QString id_; + QString prompt_status_; + QString prompt_args_; }; /** @@ -109,24 +122,13 @@ class GpgAutomatonHandler * @return true * @return false */ - auto DoCardInteract(AutomatonNextStateHandler next_state_handler, + auto DoCardInteract(const QString& serial_number, + AutomatonNextStateHandler next_state_handler, AutomatonActionHandler action_handler) -> bool; private: GpgContext& ctx_ = GpgContext::GetInstance(SingletonFunctionObject::GetChannel()); ///< - - /** - * @brief - * - * @param handle - * @param status - * @param args - * @param fd - * @return gpgme_error_t - */ - static auto interator_cb_func(void* handle, const char* status, - const char* args, int fd) -> gpgme_error_t; }; using AutomatonNextStateHandler = diff --git a/src/core/function/gpg/GpgKeyImportExporter.cpp b/src/core/function/gpg/GpgKeyImportExporter.cpp index f42c84ce..eda36273 100644 --- a/src/core/function/gpg/GpgKeyImportExporter.cpp +++ b/src/core/function/gpg/GpgKeyImportExporter.cpp @@ -45,7 +45,7 @@ GpgKeyImportExporter::GpgKeyImportExporter(int channel) * @return Import information */ auto GpgKeyImportExporter::ImportKey(const GFBuffer& in_buffer) - -> std::shared_ptr<GpgImportInformation> { + -> QSharedPointer<GpgImportInformation> { if (in_buffer.Empty()) return {}; GpgData data_in(in_buffer); @@ -55,7 +55,8 @@ auto GpgKeyImportExporter::ImportKey(const GFBuffer& in_buffer) gpgme_import_result_t result; result = gpgme_op_import_result(ctx_.BinaryContext()); gpgme_import_status_t status = result->imports; - auto import_info = SecureCreateSharedObject<GpgImportInformation>(result); + + auto import_info = QSharedPointer<GpgImportInformation>::create(result); while (status != nullptr) { GpgImportInformation::GpgImportedKey key; key.import_status = static_cast<int>(status->status); diff --git a/src/core/function/gpg/GpgKeyImportExporter.h b/src/core/function/gpg/GpgKeyImportExporter.h index 4f938cb7..dcadec36 100644 --- a/src/core/function/gpg/GpgKeyImportExporter.h +++ b/src/core/function/gpg/GpgKeyImportExporter.h @@ -58,7 +58,7 @@ class GPGFRONTEND_CORE_EXPORT GpgKeyImportExporter * @param inBuffer * @return GpgImportInformation */ - auto ImportKey(const GFBuffer&) -> std::shared_ptr<GpgImportInformation>; + auto ImportKey(const GFBuffer&) -> QSharedPointer<GpgImportInformation>; /** * @brief diff --git a/src/core/function/gpg/GpgKeyManager.cpp b/src/core/function/gpg/GpgKeyManager.cpp index 9f43d03d..1fa050bb 100644 --- a/src/core/function/gpg/GpgKeyManager.cpp +++ b/src/core/function/gpg/GpgKeyManager.cpp @@ -106,62 +106,62 @@ auto GpgKeyManager::SetOwnerTrustLevel(const GpgKeyPtr& key, auto tokens = args.split(' '); switch (state) { - case GpgAutomatonHandler::AS_START: + case GpgAutomatonHandler::kAS_START: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_COMMAND; + return GpgAutomatonHandler::kAS_COMMAND; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_COMMAND: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_COMMAND: if (status == "GET_LINE" && args == "edit_ownertrust.value") { - return GpgAutomatonHandler::AS_VALUE; + return GpgAutomatonHandler::kAS_VALUE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_VALUE: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_VALUE: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_BOOL" && args == "edit_ownertrust.set_ultimate.okay") { - return GpgAutomatonHandler::AS_REALLY_ULTIMATE; + return GpgAutomatonHandler::kAS_REALLY_ULTIMATE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_QUIT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_QUIT: if (status == "GET_BOOL" && args == "keyedit.save.okay") { - return GpgAutomatonHandler::AS_SAVE; + return GpgAutomatonHandler::kAS_SAVE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_ERROR: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_ERROR: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; default: - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; }; }; AutomatonActionHandler action_handler = [trust_level](AutomatonHandelStruct& handler, AutomatonState state) { switch (state) { - case GpgAutomatonHandler::AS_COMMAND: + case GpgAutomatonHandler::kAS_COMMAND: return QString("trust"); - case GpgAutomatonHandler::AS_VALUE: + case GpgAutomatonHandler::kAS_VALUE: handler.SetSuccess(true); return QString::number(trust_level); - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: handler.SetSuccess(true); return QString("Y"); - case GpgAutomatonHandler::AS_QUIT: + case GpgAutomatonHandler::kAS_QUIT: return QString("quit"); - case GpgAutomatonHandler::AS_SAVE: + case GpgAutomatonHandler::kAS_SAVE: handler.SetSuccess(true); return QString("Y"); - case GpgAutomatonHandler::AS_START: - case GpgAutomatonHandler::AS_ERROR: + case GpgAutomatonHandler::kAS_START: + case GpgAutomatonHandler::kAS_ERROR: return QString(""); default: return QString(""); @@ -186,74 +186,67 @@ auto GpgKeyManager::DeleteSubkey(const GpgKeyPtr& key, auto tokens = args.split(' '); switch (state) { - case GpgAutomatonHandler::AS_START: + case GpgAutomatonHandler::kAS_START: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_SELECT; + return GpgAutomatonHandler::kAS_SELECT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_SELECT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_SELECT: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_COMMAND; + return GpgAutomatonHandler::kAS_COMMAND; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_COMMAND: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_COMMAND: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_BOOL" && args == "keyedit.remove.subkey.okay") { - return GpgAutomatonHandler::AS_REALLY_ULTIMATE; + return GpgAutomatonHandler::kAS_REALLY_ULTIMATE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_QUIT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_QUIT: if (status == "GET_BOOL" && args == "keyedit.save.okay") { - return GpgAutomatonHandler::AS_SAVE; + return GpgAutomatonHandler::kAS_SAVE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_ERROR: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_ERROR: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; default: - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; }; }; AutomatonActionHandler action_handler = [subkey_index](AutomatonHandelStruct& handler, AutomatonState state) { switch (state) { - case GpgAutomatonHandler::AS_SELECT: + case GpgAutomatonHandler::kAS_SELECT: return QString("key %1").arg(subkey_index); - case GpgAutomatonHandler::AS_COMMAND: + case GpgAutomatonHandler::kAS_COMMAND: return QString("delkey"); - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: handler.SetSuccess(true); return QString("Y"); - case GpgAutomatonHandler::AS_QUIT: + case GpgAutomatonHandler::kAS_QUIT: return QString("quit"); - case GpgAutomatonHandler::AS_SAVE: + case GpgAutomatonHandler::kAS_SAVE: handler.SetSuccess(true); return QString("Y"); - case GpgAutomatonHandler::AS_START: - case GpgAutomatonHandler::AS_ERROR: - return QString(""); + case GpgAutomatonHandler::kAS_START: + case GpgAutomatonHandler::kAS_ERROR: default: return QString(""); } return QString(""); }; - auto key_fpr = key->Fingerprint(); - AutomatonHandelStruct handel_struct(key_fpr); - handel_struct.SetHandler(next_state_handler, action_handler); - - GpgData data_out; - return GpgAutomatonHandler::GetInstance(GetChannel()) .DoInteract(key, next_state_handler, action_handler); } @@ -281,63 +274,63 @@ auto GpgKeyManager::RevokeSubkey(const GpgKeyPtr& key, int subkey_index, auto tokens = args.split(' '); switch (state) { - case GpgAutomatonHandler::AS_START: + case GpgAutomatonHandler::kAS_START: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_SELECT; + return GpgAutomatonHandler::kAS_SELECT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_SELECT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_SELECT: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_COMMAND; + return GpgAutomatonHandler::kAS_COMMAND; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_COMMAND: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_COMMAND: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_BOOL" && args == "keyedit.revoke.subkey.okay") { - return GpgAutomatonHandler::AS_REALLY_ULTIMATE; + return GpgAutomatonHandler::kAS_REALLY_ULTIMATE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REASON_CODE: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REASON_CODE: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_LINE" && args == "ask_revocation_reason.text") { - return GpgAutomatonHandler::AS_REASON_TEXT; + return GpgAutomatonHandler::kAS_REASON_TEXT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REASON_TEXT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REASON_TEXT: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_LINE" && args == "ask_revocation_reason.text") { - return GpgAutomatonHandler::AS_REASON_TEXT; + return GpgAutomatonHandler::kAS_REASON_TEXT; } else if (status == "GET_BOOL" && args == "ask_revocation_reason.okay") { - return GpgAutomatonHandler::AS_REALLY_ULTIMATE; + return GpgAutomatonHandler::kAS_REALLY_ULTIMATE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_LINE" && args == "ask_revocation_reason.code") { - return GpgAutomatonHandler::AS_REASON_CODE; + return GpgAutomatonHandler::kAS_REASON_CODE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_QUIT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_QUIT: if (status == "GET_BOOL" && args == "keyedit.save.okay") { - return GpgAutomatonHandler::AS_SAVE; + return GpgAutomatonHandler::kAS_SAVE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_ERROR: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_ERROR: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; default: - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; }; }; @@ -345,38 +338,31 @@ auto GpgKeyManager::RevokeSubkey(const GpgKeyPtr& key, int subkey_index, [subkey_index, reason_code, reason_text_lines]( AutomatonHandelStruct& handler, AutomatonState state) { switch (state) { - case GpgAutomatonHandler::AS_SELECT: + case GpgAutomatonHandler::kAS_SELECT: return QString("key %1").arg(subkey_index); - case GpgAutomatonHandler::AS_COMMAND: + case GpgAutomatonHandler::kAS_COMMAND: return QString("revkey"); - case GpgAutomatonHandler::AS_REASON_CODE: + case GpgAutomatonHandler::kAS_REASON_CODE: return QString::number(reason_code); - case GpgAutomatonHandler::AS_REASON_TEXT: + case GpgAutomatonHandler::kAS_REASON_TEXT: return reason_text_lines->isEmpty() ? QString("") : QString(reason_text_lines->takeFirst().toUtf8()); - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: return QString("Y"); - case GpgAutomatonHandler::AS_QUIT: + case GpgAutomatonHandler::kAS_QUIT: return QString("quit"); - case GpgAutomatonHandler::AS_SAVE: + case GpgAutomatonHandler::kAS_SAVE: handler.SetSuccess(true); return QString("Y"); - case GpgAutomatonHandler::AS_START: - case GpgAutomatonHandler::AS_ERROR: - return QString(""); + case GpgAutomatonHandler::kAS_START: + case GpgAutomatonHandler::kAS_ERROR: default: return QString(""); } return QString(""); }; - auto key_fpr = key->Fingerprint(); - AutomatonHandelStruct handel_struct(key_fpr); - handel_struct.SetHandler(next_state_handler, action_handler); - - GpgData data_out; - return GpgAutomatonHandler::GetInstance(GetChannel()) .DoInteract(key, next_state_handler, action_handler); } diff --git a/src/core/function/gpg/GpgSmartCardManager.cpp b/src/core/function/gpg/GpgSmartCardManager.cpp index 4c55b63d..9937ef7a 100644 --- a/src/core/function/gpg/GpgSmartCardManager.cpp +++ b/src/core/function/gpg/GpgSmartCardManager.cpp @@ -41,39 +41,36 @@ auto GpgSmartCardManager::Fetch(const QString& serial_number) -> bool { auto tokens = args.split(' '); switch (state) { - case GpgAutomatonHandler::AS_START: - if (status == "CARDCTRL" && args.contains(serial_number)) { - return GpgAutomatonHandler::AS_START; - } else if (status == "GET_LINE" && args == "cardedit.prompt") { - return GpgAutomatonHandler::AS_COMMAND; + case GpgAutomatonHandler::kAS_START: + if (status == "GET_LINE" && args == "cardedit.prompt") { + return GpgAutomatonHandler::kAS_COMMAND; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_COMMAND: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_COMMAND: if (status == "GET_LINE" && args == "cardedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_QUIT: - case GpgAutomatonHandler::AS_ERROR: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_QUIT: + case GpgAutomatonHandler::kAS_ERROR: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; default: - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; }; }; AutomatonActionHandler action_handler = [](AutomatonHandelStruct& handler, AutomatonState state) { switch (state) { - case GpgAutomatonHandler::AS_COMMAND: + case GpgAutomatonHandler::kAS_COMMAND: return QString("fetch"); - case GpgAutomatonHandler::AS_QUIT: + case GpgAutomatonHandler::kAS_QUIT: return QString("quit"); - case GpgAutomatonHandler::AS_START: - case GpgAutomatonHandler::AS_ERROR: - return QString(""); + case GpgAutomatonHandler::kAS_START: + case GpgAutomatonHandler::kAS_ERROR: default: return QString(""); } @@ -81,7 +78,7 @@ auto GpgSmartCardManager::Fetch(const QString& serial_number) -> bool { }; return GpgAutomatonHandler::GetInstance(GetChannel()) - .DoCardInteract(next_state_handler, action_handler); + .DoCardInteract(serial_number, next_state_handler, action_handler); } auto GpgSmartCardManager::GetSerialNumbers() -> QStringList { @@ -256,4 +253,126 @@ auto GpgSmartCardManager::ModifyPin(const QString& pin_ref) return {true, {}}; } +auto GpgSmartCardManager::GenerateKey( + const QString& serial_number, const QString& name, const QString& email, + const QString& comment, const QDateTime& expire, + bool non_expire) -> std::tuple<bool, QString> { + if (name.isEmpty() || email.isEmpty()) { + return {false, "name or email is empty"}; + } + + qint64 days_before_expire = 0; + if (!non_expire) { + days_before_expire = QDateTime::currentDateTime().daysTo(expire); + } + + GpgAutomatonHandler::AutomatonNextStateHandler next_state_handler = + [=](AutomatonState state, const QString& status, const QString& args) { + auto tokens = args.split(' '); + + switch (state) { + case GpgAutomatonHandler::kAS_START: + if (status == "GET_LINE" && args == "cardedit.prompt") { + return GpgAutomatonHandler::kAS_ADMIN; + } + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_ADMIN: + if (status == "GET_LINE" && args == "cardedit.prompt") { + return GpgAutomatonHandler::kAS_COMMAND; + } + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_COMMAND: + if (status == "GET_LINE" && args == "cardedit.genkeys.backup_enc") { + return GpgAutomatonHandler::kAS_COMMAND; + } + if (status == "GET_BOOL" && + args == "cardedit.genkeys.replace_keys") { + return GpgAutomatonHandler::kAS_COMMAND; + } + if (status == "GET_LINE" && args == "keygen.valid") { + return GpgAutomatonHandler::kAS_COMMAND; + } + if (status == "GET_LINE" && args == "keygen.name") { + return GpgAutomatonHandler::kAS_COMMAND; + } + if (status == "GET_LINE" && args == "keygen.email") { + return GpgAutomatonHandler::kAS_COMMAND; + } + if (status == "GET_LINE" && args == "keygen.comment") { + return GpgAutomatonHandler::kAS_COMMAND; + } + if (status == "PINENTRY_LAUNCHED" || + status == "BACKUP_KEY_CREATED" || status == "KEY_CONSIDERED" || + status == "KEY_CREATED") { + return GpgAutomatonHandler::kAS_INFO; + } + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_INFO: + if (status == "PINENTRY_LAUNCHED" || + status == "BACKUP_KEY_CREATED" || status == "KEY_CONSIDERED" || + status == "KEY_CREATED") { + return GpgAutomatonHandler::kAS_INFO; + } + if (status == "GET_LINE" && args == "cardedit.prompt") { + return GpgAutomatonHandler::kAS_QUIT; + } + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_QUIT: + case GpgAutomatonHandler::kAS_ERROR: + if (status == "GET_LINE" && args == "keyedit.prompt") { + return GpgAutomatonHandler::kAS_QUIT; + } + return GpgAutomatonHandler::kAS_ERROR; + default: + return GpgAutomatonHandler::kAS_ERROR; + }; + }; + + AutomatonActionHandler action_handler = [=](AutomatonHandelStruct& handler, + AutomatonState state) { + switch (state) { + case GpgAutomatonHandler::kAS_ADMIN: + return QString("admin"); + case GpgAutomatonHandler::kAS_COMMAND: { + auto [status, args] = handler.PromptStatus(); + if (args == "cardedit.prompt") { + return QString("generate"); + } + if (args == "cardedit.genkeys.backup_enc") { + return QString("y"); + } + if (args == "cardedit.genkeys.replace_keys") { + return QString("y"); + } + if (args == "keygen.valid") { + return QString::number(days_before_expire); + } + if (args == "keygen.name") { + return name; + } + if (args == "keygen.email") { + return email; + } + if (args == "keygen.comment") { + return comment; + } + return QString{}; + } + case GpgAutomatonHandler::kAS_QUIT: + return QString("quit"); + case GpgAutomatonHandler::kAS_INFO: + case GpgAutomatonHandler::kAS_START: + case GpgAutomatonHandler::kAS_ERROR: + default: + return QString{}; + } + + return QString{}; + }; + + GpgAutomatonHandler::GetInstance(GetChannel()) + .DoCardInteract(serial_number, next_state_handler, action_handler); + + return {true, {}}; +} } // namespace GpgFrontend
\ No newline at end of file diff --git a/src/core/function/gpg/GpgSmartCardManager.h b/src/core/function/gpg/GpgSmartCardManager.h index 2d3038b4..78c21bc0 100644 --- a/src/core/function/gpg/GpgSmartCardManager.h +++ b/src/core/function/gpg/GpgSmartCardManager.h @@ -99,6 +99,16 @@ class GPGFRONTEND_CORE_EXPORT GpgSmartCardManager */ auto ModifyPin(const QString& pin_ref) -> std::tuple<bool, QString>; + /** + * @brief + * + * @return auto + */ + auto GenerateKey(const QString& serial_number, const QString& name, + const QString& email, const QString& comment, + const QDateTime& expire, + bool non_expire) -> std::tuple<bool, QString>; + private: GpgContext& ctx_ = GpgContext::GetInstance(SingletonFunctionObject::GetChannel()); ///< diff --git a/src/core/function/gpg/GpgUIDOperator.cpp b/src/core/function/gpg/GpgUIDOperator.cpp index e34d224a..e07b4192 100644 --- a/src/core/function/gpg/GpgUIDOperator.cpp +++ b/src/core/function/gpg/GpgUIDOperator.cpp @@ -70,60 +70,60 @@ auto GpgUIDOperator::DeleteUID(const GpgKeyPtr& key, int uid_index) -> bool { auto tokens = args.split(' '); switch (state) { - case GpgAutomatonHandler::AS_START: + case GpgAutomatonHandler::kAS_START: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_SELECT; + return GpgAutomatonHandler::kAS_SELECT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_SELECT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_SELECT: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_COMMAND; + return GpgAutomatonHandler::kAS_COMMAND; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_COMMAND: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_COMMAND: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_BOOL" && args == "keyedit.remove.uid.okay") { - return GpgAutomatonHandler::AS_REALLY_ULTIMATE; + return GpgAutomatonHandler::kAS_REALLY_ULTIMATE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_QUIT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_QUIT: if (status == "GET_BOOL" && args == "keyedit.save.okay") { - return GpgAutomatonHandler::AS_SAVE; + return GpgAutomatonHandler::kAS_SAVE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_ERROR: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_ERROR: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; default: - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; }; }; AutomatonActionHandler action_handler = [uid_index](AutomatonHandelStruct& handler, AutomatonState state) { switch (state) { - case GpgAutomatonHandler::AS_SELECT: + case GpgAutomatonHandler::kAS_SELECT: return QString("uid %1").arg(uid_index); - case GpgAutomatonHandler::AS_COMMAND: + case GpgAutomatonHandler::kAS_COMMAND: return QString("deluid"); - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: handler.SetSuccess(true); return QString("Y"); - case GpgAutomatonHandler::AS_QUIT: + case GpgAutomatonHandler::kAS_QUIT: return QString("quit"); - case GpgAutomatonHandler::AS_SAVE: + case GpgAutomatonHandler::kAS_SAVE: handler.SetSuccess(true); return QString("Y"); - case GpgAutomatonHandler::AS_START: - case GpgAutomatonHandler::AS_ERROR: + case GpgAutomatonHandler::kAS_START: + case GpgAutomatonHandler::kAS_ERROR: return QString(""); default: return QString(""); @@ -131,12 +131,6 @@ auto GpgUIDOperator::DeleteUID(const GpgKeyPtr& key, int uid_index) -> bool { return QString(""); }; - auto key_fpr = key->Fingerprint(); - AutomatonHandelStruct handel_struct(key_fpr); - handel_struct.SetHandler(next_state_handler, action_handler); - - GpgData data_out; - return GpgAutomatonHandler::GetInstance(GetChannel()) .DoInteract(key, next_state_handler, action_handler); } @@ -164,62 +158,62 @@ auto GpgUIDOperator::RevokeUID(const GpgKeyPtr& key, int uid_index, auto tokens = args.split(' '); switch (state) { - case GpgAutomatonHandler::AS_START: + case GpgAutomatonHandler::kAS_START: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_SELECT; + return GpgAutomatonHandler::kAS_SELECT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_SELECT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_SELECT: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_COMMAND; + return GpgAutomatonHandler::kAS_COMMAND; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_COMMAND: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_COMMAND: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_BOOL" && args == "keyedit.revoke.uid.okay") { - return GpgAutomatonHandler::AS_REALLY_ULTIMATE; + return GpgAutomatonHandler::kAS_REALLY_ULTIMATE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REASON_CODE: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REASON_CODE: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_LINE" && args == "ask_revocation_reason.text") { - return GpgAutomatonHandler::AS_REASON_TEXT; + return GpgAutomatonHandler::kAS_REASON_TEXT; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REASON_TEXT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REASON_TEXT: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_LINE" && args == "ask_revocation_reason.text") { - return GpgAutomatonHandler::AS_REASON_TEXT; + return GpgAutomatonHandler::kAS_REASON_TEXT; } else if (status == "GET_BOOL" && args == "ask_revocation_reason.okay") { - return GpgAutomatonHandler::AS_REALLY_ULTIMATE; + return GpgAutomatonHandler::kAS_REALLY_ULTIMATE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } else if (status == "GET_LINE" && args == "ask_revocation_reason.code") { - return GpgAutomatonHandler::AS_REASON_CODE; + return GpgAutomatonHandler::kAS_REASON_CODE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_QUIT: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_QUIT: if (status == "GET_BOOL" && args == "keyedit.save.okay") { - return GpgAutomatonHandler::AS_SAVE; + return GpgAutomatonHandler::kAS_SAVE; } - return GpgAutomatonHandler::AS_ERROR; - case GpgAutomatonHandler::AS_ERROR: + return GpgAutomatonHandler::kAS_ERROR; + case GpgAutomatonHandler::kAS_ERROR: if (status == "GET_LINE" && args == "keyedit.prompt") { - return GpgAutomatonHandler::AS_QUIT; + return GpgAutomatonHandler::kAS_QUIT; } - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; default: - return GpgAutomatonHandler::AS_ERROR; + return GpgAutomatonHandler::kAS_ERROR; }; }; @@ -227,25 +221,25 @@ auto GpgUIDOperator::RevokeUID(const GpgKeyPtr& key, int uid_index, [uid_index, reason_code, reason_text_lines]( AutomatonHandelStruct& handler, AutomatonState state) { switch (state) { - case GpgAutomatonHandler::AS_SELECT: + case GpgAutomatonHandler::kAS_SELECT: return QString("uid %1").arg(uid_index); - case GpgAutomatonHandler::AS_COMMAND: + case GpgAutomatonHandler::kAS_COMMAND: return QString("revuid"); - case GpgAutomatonHandler::AS_REASON_CODE: + case GpgAutomatonHandler::kAS_REASON_CODE: return QString::number(reason_code); - case GpgAutomatonHandler::AS_REASON_TEXT: + case GpgAutomatonHandler::kAS_REASON_TEXT: return reason_text_lines->isEmpty() ? QString("") : QString(reason_text_lines->takeFirst().toUtf8()); - case GpgAutomatonHandler::AS_REALLY_ULTIMATE: + case GpgAutomatonHandler::kAS_REALLY_ULTIMATE: return QString("Y"); - case GpgAutomatonHandler::AS_QUIT: + case GpgAutomatonHandler::kAS_QUIT: return QString("quit"); - case GpgAutomatonHandler::AS_SAVE: + case GpgAutomatonHandler::kAS_SAVE: handler.SetSuccess(true); return QString("Y"); - case GpgAutomatonHandler::AS_START: - case GpgAutomatonHandler::AS_ERROR: + case GpgAutomatonHandler::kAS_START: + case GpgAutomatonHandler::kAS_ERROR: return QString(""); default: return QString(""); @@ -253,12 +247,6 @@ auto GpgUIDOperator::RevokeUID(const GpgKeyPtr& key, int uid_index, return QString(""); }; - auto key_fpr = key->Fingerprint(); - AutomatonHandelStruct handel_struct(key_fpr); - handel_struct.SetHandler(next_state_handler, action_handler); - - GpgData data_out; - return GpgAutomatonHandler::GetInstance(GetChannel()) .DoInteract(key, next_state_handler, action_handler); } |