00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "ClientWriteCallback.h"
00023 #include "CODEX_Events/Event.h"
00024 #include "CODEX_Server/ServerExceptions.h"
00025 #include "CODEX_Server/ServerState.h"
00026 #include "StateInfo.h"
00027 #include "CODEX_Client/Message.h"
00028 #include "SupportedClientResponse.h"
00029 #include "CODEX_Server/SignRequestEvent.h"
00030 #include "ClientDelegation.h"
00031 #include "VerifyWriteCallback.h"
00032
00033 #include "timing.h"
00034
00035 using namespace CODEX_KeyService;
00036
00037 ClientWriteCallback::ClientWriteCallback(
00038 CODEX_Events::DeadPileType& deadPile,
00039 CODEX_Events::QType& eventQueue,
00040 CODEX_Server::SignRequestHandler* destination,
00041 ClientResponseHandler* clientAct,
00042 const CODEX_Client::SignedWriteKeyMsg& req,
00043 const unsigned char* seqNum ) :
00044 ResponseCallback( seqNum ),
00045 CODEX_Events::Activity( deadPile, eventQueue ),
00046 m_destination( destination ),
00047 m_clientAct( clientAct ),
00048 m_request( req ),
00049 m_complete( false )
00050 {
00051 m_digest =
00052 m_request.digest( CODEX_Server::ServerState::instance()->hashFunc() );
00053 }
00054
00055 ClientWriteCallback::~ClientWriteCallback()
00056 {
00057 if ( NULL != m_digest ) BN_free( m_digest );
00058 }
00059
00063 bool
00064 ClientWriteCallback::operator()( unsigned int server,
00065 CODEX_Quorum::Message* msg )
00066 {
00067 if ( NULL == msg )
00068 {
00069 return false;
00070 }
00071
00072 if ( m_complete )
00073 {
00074 delete msg;
00075 return true;
00076 }
00077
00078 #ifdef TIMING
00079 ActiveTimer.start();
00080 #endif
00081
00082 CODEX_Server::ServerState* serverState =
00083 CODEX_Server::ServerState::instance();
00084 if ( NULL == serverState )
00085 {
00086 delete msg;
00087 #ifdef TIMING
00088 ActiveTimer.stop();
00089 #endif
00090 return false;
00091 }
00092
00093 StateInfo* stateInfo = StateInfo::instance();
00094 if ( NULL == stateInfo )
00095 {
00096 delete msg;
00097 #ifdef TIMING
00098 ActiveTimer.stop();
00099 #endif
00100 return false;
00101 }
00102
00103
00104 if ( NULL == stateInfo->getActFromSeqNum( seqNum() ) )
00105 {
00106 delete msg;
00107 #ifdef TIMING
00108 ActiveTimer.stop();
00109 #endif
00110 return false;
00111 }
00112
00113 unsigned char* data = (unsigned char*)msg->buffer();
00114 int length = msg->length();
00115
00116 if ( length < 2 )
00117 {
00118 delete msg;
00119 #ifdef TIMING
00120 ActiveTimer.stop();
00121 #endif
00122 return false;
00123 }
00124
00125
00126 if ( stateInfo->delegationDomain() != data[0] )
00127 {
00128 delete msg;
00129 #ifdef TIMING
00130 ActiveTimer.stop();
00131 #endif
00132 return false;
00133 }
00134 ++data;
00135 --length;
00136
00137 if ( ClientDelegation::kApproveClientRequest != data[0] )
00138 {
00139 delete msg;
00140 #ifdef TIMING
00141 ActiveTimer.stop();
00142 #endif
00143 return false;
00144 }
00145 ++data;
00146 --length;
00147
00148
00149 CODEX_Ciphers::RSASignature signature;
00150 if ( NULL == signature.unmarshal( NULL, &data, length ) )
00151 {
00152 delete msg;
00153 #ifdef TIMING
00154 ActiveTimer.stop();
00155 #endif
00156 return false;
00157 }
00158 delete msg;
00159
00160 CODEX_Server::ServerSignature* servSig = NULL;
00161 try
00162 {
00163
00164 if ( ! serverState->publicKey(server).verifySignature(
00165 signature, m_digest ) )
00166 {
00167 throw CODEX_Server::SignatureVerificationFailedException( __FILE__ ,
00168 __LINE__ );
00169 }
00170
00171
00172 servSig = new CODEX_Server::ServerSignature( server, signature );
00173
00174
00175 m_evidence.append( servSig );
00176
00177
00178
00179 CODEX_Quorum::QuorumSystem* qs = serverState->quorumSystem();
00180 if ( NULL == qs )
00181 {
00182 throw CODEX_Server::NoQuorumSystemException( __FILE__ , __LINE__ );
00183 }
00184 if ( m_evidence.size() >= qs->quorumSize() )
00185 {
00186 typedef CODEX_Client::KeyStoredMsg RespType;
00187 typedef CODEX_Client::SignedWriteKeyMsg ReqType;
00188 RespType ksMsg( m_request.message().name(),
00189 m_request.signature() );
00190 const CODEX_Server::ServerState::LSType::LabelType& label =
00191 serverState->defaultSignatureLabel();
00192
00193 SupportedClientResponse< RespType, ReqType > resp( ksMsg,
00194 m_request,
00195 m_evidence,
00196 label );
00197 unsigned char* seqNum = serverState->newSequenceNumber();
00198 stateInfo->registerSequenceNumber( seqNum, m_clientAct );
00199 VerifyWriteCallback* cb = new VerifyWriteCallback( m_deadPile,
00200 m_queue,
00201 m_destination,
00202 m_clientAct,
00203 ksMsg,
00204 seqNum );
00205
00206 CODEX_Quorum::Message request;
00207 unsigned char self = serverState->hostNum();
00208 request.fill( self | CODEX_Server::ServerState::OutgoingMask );
00209 request.fill( seqNum, CODEX_Server::ServerState::nMID );
00210 request.fill( stateInfo->delegationDomain() );
00211 request.fill( ClientDelegation::kRequestSignature );
00212 request.fill( CODEX_Client::kKeyStoredMsg );
00213 int reqLen = resp.marshal(0);
00214 unsigned char* reqBuff = new unsigned char[reqLen];
00215 unsigned char* pReqBuff = reqBuff;
00216 resp.marshal(&pReqBuff);
00217 request.fill( reqBuff, reqLen );
00218 delete [] reqBuff;
00219
00220 CODEX_Server::SignRequestEvent* event =
00221 new CODEX_Server::SignRequestEvent(this,
00222 m_destination,
00223 request,
00224 cb);
00225 sendEvent( event, 0 );
00226 m_complete = true;
00227 }
00228 #ifdef TIMING
00229 ActiveTimer.stop();
00230 #endif
00231 return true;
00232 }
00233
00234 catch ( CODEX_Server::NoQuorumSystemException& e )
00235 {
00236 if ( NULL != servSig ) delete servSig;
00237
00238 #ifdef TIMING
00239 ActiveTimer.stop();
00240 #endif
00241 throw;
00242 }
00243 catch ( ... )
00244 {
00245 if ( NULL != servSig ) delete servSig;
00246 #ifdef TIMING
00247 ActiveTimer.stop();
00248 #endif
00249 return false;
00250 }
00251 }