updates.
[silc.git] / lib / silcclient / protocol.c
index ef570d8159118d0ddd60e72cd10bfe1527407354..40bffdf826450a9eaf58004961ce7d7e213dd42b 100644 (file)
@@ -112,7 +112,8 @@ void silc_client_protocol_ke_set_keys(SilcSKE ske,
                                      SilcPKCS pkcs,
                                      SilcHash hash,
                                      SilcHmac hmac,
-                                     SilcSKEDiffieHellmanGroup group)
+                                     SilcSKEDiffieHellmanGroup group,
+                                     bool is_responder)
 {
   SilcClientConnection conn = (SilcClientConnection)sock->user_data;
 
@@ -124,16 +125,29 @@ void silc_client_protocol_ke_set_keys(SilcSKE ske,
   silc_hmac_alloc((char *)silc_hmac_get_name(hmac), NULL, &conn->hmac_send);
   silc_hmac_alloc((char *)silc_hmac_get_name(hmac), NULL, &conn->hmac_receive);
 
-  silc_cipher_set_key(conn->send_key, keymat->send_enc_key, 
-                     keymat->enc_key_len);
-  silc_cipher_set_iv(conn->send_key, keymat->send_iv);
-  silc_cipher_set_key(conn->receive_key, keymat->receive_enc_key, 
-                     keymat->enc_key_len);
-  silc_cipher_set_iv(conn->receive_key, keymat->receive_iv);
-  silc_hmac_set_key(conn->hmac_send, keymat->send_hmac_key, 
-                   keymat->hmac_key_len);
-  silc_hmac_set_key(conn->hmac_receive, keymat->receive_hmac_key, 
-                   keymat->hmac_key_len);
+  if (is_responder == TRUE) {
+    silc_cipher_set_key(conn->send_key, keymat->receive_enc_key, 
+                       keymat->enc_key_len);
+    silc_cipher_set_iv(conn->send_key, keymat->receive_iv);
+    silc_cipher_set_key(conn->receive_key, keymat->send_enc_key, 
+                       keymat->enc_key_len);
+    silc_cipher_set_iv(conn->receive_key, keymat->send_iv);
+    silc_hmac_set_key(conn->hmac_send, keymat->receive_hmac_key, 
+                     keymat->hmac_key_len);
+    silc_hmac_set_key(conn->hmac_receive, keymat->send_hmac_key, 
+                     keymat->hmac_key_len);
+  } else {
+    silc_cipher_set_key(conn->send_key, keymat->send_enc_key, 
+                       keymat->enc_key_len);
+    silc_cipher_set_iv(conn->send_key, keymat->send_iv);
+    silc_cipher_set_key(conn->receive_key, keymat->receive_enc_key, 
+                       keymat->enc_key_len);
+    silc_cipher_set_iv(conn->receive_key, keymat->receive_iv);
+    silc_hmac_set_key(conn->hmac_send, keymat->send_hmac_key, 
+                     keymat->hmac_key_len);
+    silc_hmac_set_key(conn->hmac_receive, keymat->receive_hmac_key, 
+                     keymat->hmac_key_len);
+  }
 
   /* Rekey stuff */
   conn->rekey = silc_calloc(1, sizeof(*conn->rekey));
@@ -199,8 +213,10 @@ SilcSKEStatus silc_ske_check_version(SilcSKE ske, unsigned char *version,
 
   if (maj != maj2)
     status = SILC_SKE_STATUS_BAD_VERSION;
-  if (min < min2)
-    status = SILC_SKE_STATUS_BAD_VERSION;
+
+  /* XXX backward support for 0.6.1 */
+  if (maj == 0 && min == 6 && build < 2)
+    ske->backward_version = 1;
 
   if (status != SILC_SKE_STATUS_OK)
     client->ops->say(client, conn, SILC_CLIENT_MESSAGE_AUDIT,
@@ -228,20 +244,8 @@ static void silc_client_protocol_ke_continue(SilcSKE ske,
   SILC_LOG_DEBUG(("Start"));
 
   if (ske->status != SILC_SKE_STATUS_OK) {
-    if (ske->status == SILC_SKE_STATUS_UNSUPPORTED_PUBLIC_KEY) {
-      client->ops->say(client, conn, SILC_CLIENT_MESSAGE_AUDIT, 
-                      "Received unsupported server %s public key",
-                      ctx->sock->hostname);
-    } else if (ske->status == SILC_SKE_STATUS_PUBLIC_KEY_NOT_PROVIDED) {
-      client->ops->say(client, conn, SILC_CLIENT_MESSAGE_AUDIT,
-                      "Remote host did not send its public key, even though "
-                      "it must send it");
-    } else {
-      client->ops->say(client, conn, SILC_CLIENT_MESSAGE_ERROR,
-                      "Error during key exchange protocol with server %s",
-                      ctx->sock->hostname);
-    }
-    
+    /* Call failure client operation */
+    client->ops->failure(client, conn, protocol, (void *)ske->status);
     protocol->state = SILC_PROTOCOL_STATE_ERROR;
     silc_protocol_execute(protocol, client->schedule, 0, 0);
     return;
@@ -314,7 +318,7 @@ SILC_TASK_CALLBACK(silc_client_protocol_key_exchange)
        SilcSKEStartPayload *start_payload;
 
        /* Assemble security properties. */
-       silc_ske_assemble_security_properties(ske, SILC_SKE_SP_FLAG_NONE
+       silc_ske_assemble_security_properties(ske, SILC_SKE_SP_FLAG_MUTUAL
                                              client->silc_client_version,
                                              &start_payload);