+Fri Aug 17 23:07:45 EEST 2001 Pekka Riikonen <priikone@silcnet.org>
+
+ * Fixed the getkey command handling in the server. Send just
+ empty OK reply to the sender if the key could not be fetched
+ (but everything else was ok, like the key just was not available).
+ Changed the public key parameter to optional in the protocol
+ specs so that empty OK reply can be sent. Affected file
+ silcd/command.c.
+
+ Added a message to Irssi SILC client to tell to user if the
+ server did not return a public key.
+
Tue Aug 14 07:29:27 CEST 2001 Pekka Riikonen <priikone@silcnet.org>
* Fixed a channel key regeneration bug. It registered new
{ "pubkey_no_match", "{hilight $0} key does not match with your local copy", 1, { 0 } },
{ "pubkey_maybe_expired", "It is possible that the key has expired or changed", 0 },
{ "pubkey_mitm_attach", "It is also possible that someone is performing man-in-the-middle attack", 0 },
+ { "getkey_notkey", "Server did not return any public key", 0 },
/* Misc messages */
{ NULL, "Misc", 0 },
SILCTXT_PUBKEY_NO_MATCH,
SILCTXT_PUBKEY_MAYBE_EXPIRED,
SILCTXT_PUBKEY_MITM_ATTACK,
+ SILCTXT_GETKEY_NOKEY,
SILCTXT_FILL_4,
id_type = va_arg(vp, uint32);
entry = va_arg(vp, void *);
public_key = va_arg(vp, SilcPublicKey);
-
- pk = silc_pkcs_public_key_encode(public_key, &pk_len);
-
- silc_verify_public_key_internal(client, conn,
- (id_type == SILC_ID_CLIENT ?
- SILC_SOCKET_TYPE_CLIENT :
- SILC_SOCKET_TYPE_SERVER),
- pk, pk_len, SILC_SKE_PK_TYPE_SILC,
- NULL, NULL);
- silc_free(pk);
+
+ if (public_key) {
+ pk = silc_pkcs_public_key_encode(public_key, &pk_len);
+
+ silc_verify_public_key_internal(client, conn,
+ (id_type == SILC_ID_CLIENT ?
+ SILC_SOCKET_TYPE_CLIENT :
+ SILC_SOCKET_TYPE_SERVER),
+ pk, pk_len, SILC_SKE_PK_TYPE_SILC,
+ NULL, NULL);
+ silc_free(pk);
+ } else {
+ printformat_module("fe-common/silc", server, NULL,
+ MSGLEVEL_CRAP, SILCTXT_GETKEY_NOKEY);
+ }
}
break;
SilcServerID *server_id = NULL;
SilcIDPayload idp = NULL;
uint16 ident = silc_command_get_ident(cmd->payload);
- unsigned char *tmp;
- uint32 tmp_len;
- SilcBuffer pk;
+ unsigned char *tmp, *pkdata;
+ uint32 tmp_len, pklen;
+ SilcBuffer pk = NULL;
SilcIdType id_type;
SILC_LOG_DEBUG(("Start"));
return;
}
- if (!client && cmd->pending) {
+ if (!client) {
silc_server_command_send_status_reply(cmd, SILC_COMMAND_GETKEY,
SILC_STATUS_ERR_NO_SUCH_CLIENT_ID);
goto out;
SILC_STR_UI_XNSTRING(tmp, tmp_len),
SILC_STR_END);
silc_free(tmp);
-
+ pkdata = pk->data;
+ pklen = pk->len;
} else if (id_type == SILC_ID_SERVER) {
server_id = silc_id_payload_get_id(idp);
server_entry = silc_idlist_find_server_by_id(server->global_list,
server_id, TRUE, NULL);
- if ((!server_entry && !cmd->pending && !server->standalone) ||
- (server_entry && !server_entry->connection && !cmd->pending &&
- !server->standalone) ||
- (server_entry && !server_entry->data.public_key && !cmd->pending &&
- !server->standalone)) {
+ if (server_entry != server->id_entry &&
+ ((!server_entry && !cmd->pending && !server->standalone) ||
+ (server_entry && !server_entry->connection && !cmd->pending &&
+ !server->standalone) ||
+ (server_entry && !server_entry->data.public_key && !cmd->pending &&
+ !server->standalone))) {
SilcBuffer tmpbuf;
uint16 old_ident;
return;
}
- if (!server_entry && cmd->pending) {
+ if (!server_entry) {
silc_server_command_send_status_reply(cmd, SILC_COMMAND_GETKEY,
SILC_STATUS_ERR_NO_SUCH_SERVER_ID);
goto out;
}
- /* The client is locally connected, just get the public key and
- send it back. */
- tmp = silc_pkcs_public_key_encode(server_entry->data.public_key, &tmp_len);
- pk = silc_buffer_alloc(4 + tmp_len);
- silc_buffer_pull_tail(pk, SILC_BUFFER_END(pk));
- silc_buffer_format(pk,
+ /* If they key does not exist then do not send it, send just OK reply */
+ if (!server_entry->data.public_key) {
+ pkdata = NULL;
+ pklen = 0;
+ } else {
+ tmp = silc_pkcs_public_key_encode(server_entry->data.public_key,
+ &tmp_len);
+ pk = silc_buffer_alloc(4 + tmp_len);
+ silc_buffer_pull_tail(pk, SILC_BUFFER_END(pk));
+ silc_buffer_format(pk,
SILC_STR_UI_SHORT(tmp_len),
- SILC_STR_UI_SHORT(SILC_SKE_PK_TYPE_SILC),
- SILC_STR_UI_XNSTRING(tmp, tmp_len),
- SILC_STR_END);
- silc_free(tmp);
+ SILC_STR_UI_SHORT(SILC_SKE_PK_TYPE_SILC),
+ SILC_STR_UI_XNSTRING(tmp, tmp_len),
+ SILC_STR_END);
+ silc_free(tmp);
+ pkdata = pk->data;
+ pklen = pk->len;
+ }
} else {
goto out;
}
tmp = silc_argument_get_arg_type(cmd->args, 1, &tmp_len);
packet = silc_command_reply_payload_encode_va(SILC_COMMAND_GETKEY,
- SILC_STATUS_OK, ident, 2,
+ SILC_STATUS_OK, ident,
+ pkdata ? 2 : 1,
2, tmp, tmp_len,
- 3, pk->data, pk->len);
+ 3, pkdata, pklen);
silc_server_packet_send(server, cmd->sock, SILC_PACKET_COMMAND_REPLY, 0,
packet->data, packet->len, FALSE);
silc_buffer_free(packet);
- silc_buffer_free(pk);
+
+ if (pk)
+ silc_buffer_free(pk);
out:
if (idp)
Max Arguments: 3
Arguments: (1) <Status Payload> (2) <ID Payload>
- (3) <Public Key Payload>
+ (3) [<Public Key Payload>]
This command replies with the client's or server's ID and with
the <Public Key Payload>.
/* Get the public key payload */
tmp = silc_argument_get_arg_type(cmd->args, 3, &len);
- if (!tmp)
- goto out;
-
- /* Decode the public key */
-
- SILC_GET16_MSB(pk_len, tmp);
- SILC_GET16_MSB(type, tmp + 2);
- pk = tmp + 4;
-
- if (type != SILC_SKE_PK_TYPE_SILC)
- goto out;
-
- if (!silc_pkcs_public_key_decode(pk, pk_len, &public_key))
- goto out;
-
+ if (tmp) {
+ /* Decode the public key */
+ SILC_GET16_MSB(pk_len, tmp);
+ SILC_GET16_MSB(type, tmp + 2);
+ pk = tmp + 4;
+
+ if (type != SILC_SKE_PK_TYPE_SILC)
+ goto out;
+
+ if (!silc_pkcs_public_key_decode(pk, pk_len, &public_key))
+ goto out;
+ }
+
id_type = silc_id_payload_get_type(idp);
if (id_type == SILC_ID_CLIENT) {
/* Received client's public key */