+Tue Mar 27 22:22:38 EEST 2001 Pekka Riikonen <priikone@poseidon.pspt.fi>
+
+ * Added silc_server_connection_auth_request to handle the
+ incoming CONNECTION_AUTH_REQUEST packet. Affected file is
+ silcd/packet_receive.[ch].
+
+ * Added silc_server_send_connection_auth_request into the
+ silcd/packet_send.c to send the connection auth request packet.
+
+ * Cleaned up the silcd/protocol.c a bit and fixed some memory
+ leaks.
+
+ * Fixed the public key authentication in responder side in the
+ server. The `auth_data' pointer includes the SilcPublicKey
+ not the path to the public key. Affected file silcd/protocol.c.
+
+ * Implemented the public key authentication in the initiator side
+ in the server. Affected file silcd/protocol.c.
+
+ * Removed the [RedirectClient] config section from the server
+ configuration. Is not needed and I don't want to implement it.
+
Tue Mar 27 12:49:56 EEST 2001 Pekka Riikonen <priikone@poseidon.pspt.fi>
* Cleaned up the CMODE command in the server. It now works
Do not send SilcPKCS but SilcPublicKey as argument.
* Implemented the public key authentication support to the
- serverconfig. The public key is loaded fromthe provided path
+ serverconfig. The public key is loaded from the provided path
and saved as authentication data to void * pointer. Thus,
changed the unsigned char *auth_data to void *auth_data;
from file and using them (see corresponding code in server, it should
support public key authentication already).
- o Connection Authentication request resolving is missing and must be
- done. This is required by the protocol.
+ o Non-blocking connection on the background must be stopped if some
+ other connection on same window has established. Now it is possible
+ that some non-blocking connection timeouts on the background when
+ we already have a working connection to some other place; things
+ goes bad.
o Add client library parameters or options that handle what kind of
messages the library should print out (using `say' client operation,
for example) and what is left for the application to print. The
appliation could for example set that it handles all command printing
but all error printing should be handled by the library, etc...
-
- o Non-blocking connection on the background must be stopped if some
- other connection on same window has established. Now it is possible
- that some non-blocking connection timeouts on the background when
- we already have a working connection to some other place; things
- goes bad.
+ This is not a showstopper.
o Input line on UI is buggy. Cursor movement etc bugs. Too lazy to
fix it.
o SERVER_SIGNOFF notify type is not implemented
- o TODO in authentication protocol (protocol.c):
-
- o Public key authentication is missing in initiator side. It must
- be implemented by creating the authentication data.
-
- o TODO in general server (server.c):
-
- o SILC_PACKET_CONNECTION_AUTH_REQUEST packet type is not
- implemented.
-
- o silc_server_connect_to_router_second checks the authentication
- method to be used in the connection. However, if it does not
- find it it must resolve it from the responder by sending the
- SILC_PACKET_CONNECTION_AUTH_REQUEST packet.
-
o Packet processing can be made faster. All packet function in the
packet_receive.c has same prototypes. Instead of calling those from
huge switch() make a table of callback functions that can be called
o Connection classes should be actually implemented in serverconfig.c.
They can be defined but they are totally ignored currently.
- o Connection redirect, if server is full, is not implemented. I also
- don't know how to do it currently. Maybe it shouldn't be done at all.
-
TODO In SILC Libraries
======================
as for the private message flags. This way we can implement
for example the CTCP style ACTION (/ME command) messages.
- o New feature in the KE/auth protocol
+ o New features in the KE/auth protocol
(draft-riikonen-silc-ke-auth-xx.txt):
o Define group exchange support for the SKE so that the SKE
}
}
- return FALSE;
+ *auth_meth = SILC_AUTH_NONE;
+ *auth_data = NULL;
+ *auth_data_len = 0;
+
+ return TRUE;
}
/* Notifies application that failure packet was received. This is called
silc_server_relay_packet(server, dst_sock, idata->send_key,
idata->hmac, packet, FALSE);
}
+
+/* Received connection auth request packet that is used during connection
+ phase to resolve the mandatory authentication method. This packet can
+ actually be received at anytime but usually it is used only during
+ the connection authentication phase. Now, protocol says that this packet
+ can come from client or server, however, we support only this coming
+ from client and expect that server's always knows what authentication
+ method to use. */
+
+void silc_server_connection_auth_request(SilcServer server,
+ SilcSocketConnection sock,
+ SilcPacketContext *packet)
+{
+ SilcServerConfigSectionClientConnection *client = NULL;
+ unsigned short conn_type;
+ int ret;
+ SilcAuthMethod auth_meth;
+
+ SILC_LOG_DEBUG(("Start"));
+
+ if (packet->src_id_type && packet->src_id_type != SILC_ID_CLIENT)
+ return;
+
+ /* Parse the payload */
+ ret = silc_buffer_unformat(packet->buffer,
+ SILC_STR_UI_SHORT(&conn_type),
+ SILC_STR_UI_SHORT(NULL),
+ SILC_STR_END);
+ if (ret == -1)
+ return;
+
+ if (conn_type != SILC_SOCKET_TYPE_CLIENT)
+ return;
+
+ /* Get the authentication method for the client */
+ auth_meth = SILC_AUTH_NONE;
+ client = silc_server_config_find_client_conn(server->config,
+ sock->ip,
+ sock->port);
+ if (!client)
+ client = silc_server_config_find_client_conn(server->config,
+ sock->hostname,
+ sock->port);
+ if (client)
+ auth_meth = client->auth_meth;
+
+ /* Send it back to the client */
+ silc_server_send_connection_auth_request(server, sock,
+ conn_type,
+ auth_meth);
+}
void silc_server_key_agreement(SilcServer server,
SilcSocketConnection sock,
SilcPacketContext *packet);
+void silc_server_connection_auth_request(SilcServer server,
+ SilcSocketConnection sock,
+ SilcPacketContext *packet);
#endif
silc_buffer_pull(packet->buffer, SILC_PACKET_HEADER_LEN + packet->src_id_len
+ packet->dst_id_len + packet->padlen);
}
+
+/* Routine used to send the connection authentication packet. */
+
+void silc_server_send_connection_auth_request(SilcServer server,
+ SilcSocketConnection sock,
+ unsigned short conn_type,
+ SilcAuthMethod auth_meth)
+{
+ SilcBuffer packet;
+
+ packet = silc_buffer_alloc(4);
+ silc_buffer_pull_tail(packet, SILC_BUFFER_END(packet));
+ silc_buffer_format(packet,
+ SILC_STR_UI_SHORT(conn_type),
+ SILC_STR_UI_SHORT(auth_meth),
+ SILC_STR_END);
+
+ silc_server_packet_send(server, sock, SILC_PACKET_CONNECTION_AUTH_REQUEST,
+ 0, packet->data, packet->len, FALSE);
+ silc_buffer_free(packet);
+}
SilcHmac hmac,
SilcPacketContext *packet,
int force_send);
+void silc_server_send_connection_auth_request(SilcServer server,
+ SilcSocketConnection sock,
+ unsigned short conn_type,
+ SilcAuthMethod auth_meth);
#endif
* Connection Authentication protocol functions
*/
-int silc_server_password_authentication(SilcServer server, char *auth1,
- char *auth2)
+static int
+silc_server_password_authentication(SilcServer server, char *auth1,
+ char *auth2)
{
if (!auth1 || !auth2)
return FALSE;
return FALSE;
}
-int silc_server_public_key_authentication(SilcServer server,
- char *pkfile,
- unsigned char *sign,
- unsigned int sign_len,
- SilcSKE ske)
+static int
+silc_server_public_key_authentication(SilcServer server,
+ SilcPublicKey pub_key,
+ unsigned char *sign,
+ unsigned int sign_len,
+ SilcSKE ske)
{
- SilcPublicKey pub_key;
SilcPKCS pkcs;
int len;
SilcBuffer auth;
- if (!pkfile || !sign)
+ if (!pub_key || !sign)
return FALSE;
- /* Load public key from file */
- if (!silc_pkcs_load_public_key(pkfile, &pub_key, SILC_PKCS_FILE_PEM))
- if (!silc_pkcs_load_public_key(pkfile, &pub_key, SILC_PKCS_FILE_BIN))
- return FALSE;
-
silc_pkcs_alloc(pub_key->name, &pkcs);
if (!silc_pkcs_public_key_set(pkcs, pub_key)) {
silc_pkcs_free(pkcs);
SILC_STR_END);
/* Verify signature */
- if (pkcs->pkcs->verify(pkcs->context, sign, sign_len,
- auth->data, auth->len))
- {
- silc_pkcs_free(pkcs);
- silc_pkcs_public_key_free(pub_key);
- silc_buffer_free(auth);
- return TRUE;
- }
+ if (silc_pkcs_verify(pkcs, sign, sign_len, auth->data, auth->len)) {
+ silc_pkcs_free(pkcs);
+ silc_buffer_free(auth);
+ return TRUE;
+ }
+
+ silc_pkcs_free(pkcs);
+ silc_buffer_free(auth);
+ return FALSE;
+}
+
+static int
+silc_server_get_public_key_auth(SilcServer server,
+ SilcPublicKey pub_key,
+ unsigned char *auth_data,
+ unsigned int *auth_data_len,
+ SilcSKE ske)
+{
+ int len;
+ SilcPKCS pkcs;
+ SilcBuffer auth;
+
+ if (!pub_key)
+ return FALSE;
+
+ silc_pkcs_alloc(pub_key->name, &pkcs);
+ if (!silc_pkcs_public_key_set(pkcs, pub_key)) {
+ silc_pkcs_free(pkcs);
+ return FALSE;
+ }
+
+ /* Make the authentication data. Protocol says it is HASH plus
+ KE Start Payload. */
+ len = ske->hash_len + ske->start_payload_copy->len;
+ auth = silc_buffer_alloc(len);
+ silc_buffer_pull_tail(auth, len);
+ silc_buffer_format(auth,
+ SILC_STR_UI_XNSTRING(ske->hash, ske->hash_len),
+ SILC_STR_UI_XNSTRING(ske->start_payload_copy->data,
+ ske->start_payload_copy->len),
+ SILC_STR_END);
+
+ if (silc_pkcs_sign(pkcs, auth->data, auth->len, auth_data, auth_data_len)) {
+ silc_pkcs_free(pkcs);
+ silc_buffer_free(auth);
+ return TRUE;
+ }
silc_pkcs_free(pkcs);
- silc_pkcs_public_key_free(pub_key);
silc_buffer_free(auth);
return FALSE;
}
int ret;
unsigned short payload_len;
unsigned short conn_type;
- unsigned char *auth_data;
+ unsigned char *auth_data = NULL;
SILC_LOG_INFO(("Performing authentication protocol for %s (%s)",
ctx->sock->hostname, ctx->sock->ip));
/* Get authentication data */
silc_buffer_pull(ctx->packet->buffer, 4);
ret = silc_buffer_unformat(ctx->packet->buffer,
- SILC_STR_UI_XNSTRING_ALLOC(&auth_data,
- payload_len),
+ SILC_STR_UI_XNSTRING(&auth_data,
+ payload_len),
SILC_STR_END);
if (ret == -1) {
SILC_LOG_DEBUG(("Bad payload in authentication packet"));
protocol, fd, 0, 300000);
return;
}
- } else {
- auth_data = NULL;
}
/*
/* Remote end is client */
if (conn_type == SILC_SOCKET_TYPE_CLIENT) {
SilcServerConfigSectionClientConnection *client = NULL;
- client =
- silc_server_config_find_client_conn(server->config,
- ctx->sock->ip,
- ctx->sock->port);
+ client = silc_server_config_find_client_conn(server->config,
+ ctx->sock->ip,
+ ctx->sock->port);
if (!client)
- client =
- silc_server_config_find_client_conn(server->config,
- ctx->sock->hostname,
- ctx->sock->port);
+ client = silc_server_config_find_client_conn(server->config,
+ ctx->sock->hostname,
+ ctx->sock->port);
if (client) {
switch(client->auth_meth) {
ret = silc_server_password_authentication(server, auth_data,
client->auth_data);
- if (ret) {
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
+ if (ret)
break;
- }
/* Authentication failed */
SILC_LOG_ERROR(("Authentication failed"));
payload_len,
ctx->ske);
- if (ret) {
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
+ if (ret)
break;
- }
SILC_LOG_ERROR(("Authentication failed"));
SILC_LOG_DEBUG(("Authentication failed"));
SILC_LOG_DEBUG(("No configuration for remote connection"));
SILC_LOG_ERROR(("Remote connection not configured"));
SILC_LOG_ERROR(("Authentication failed"));
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
protocol->state = SILC_PROTOCOL_STATE_ERROR;
protocol->execute(server->timeout_queue, 0,
protocol, fd, 0, 300000);
/* Remote end is server */
if (conn_type == SILC_SOCKET_TYPE_SERVER) {
SilcServerConfigSectionServerConnection *serv = NULL;
- serv =
- silc_server_config_find_server_conn(server->config,
- ctx->sock->ip,
- ctx->sock->port);
+ serv = silc_server_config_find_server_conn(server->config,
+ ctx->sock->ip,
+ ctx->sock->port);
if (!serv)
- serv =
- silc_server_config_find_server_conn(server->config,
- ctx->sock->hostname,
- ctx->sock->port);
-
+ serv = silc_server_config_find_server_conn(server->config,
+ ctx->sock->hostname,
+ ctx->sock->port);
+
if (serv) {
switch(serv->auth_meth) {
case SILC_AUTH_NONE:
ret = silc_server_password_authentication(server, auth_data,
serv->auth_data);
- if (ret) {
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
+ if (ret)
break;
- }
/* Authentication failed */
SILC_LOG_ERROR(("Authentication failed"));
payload_len,
ctx->ske);
- if (ret) {
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
+ if (ret)
break;
- }
SILC_LOG_ERROR(("Authentication failed"));
SILC_LOG_DEBUG(("Authentication failed"));
SILC_LOG_DEBUG(("No configuration for remote connection"));
SILC_LOG_ERROR(("Remote connection not configured"));
SILC_LOG_ERROR(("Authentication failed"));
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
protocol->state = SILC_PROTOCOL_STATE_ERROR;
protocol->execute(server->timeout_queue, 0,
protocol, fd, 0, 300000);
/* Remote end is router */
if (conn_type == SILC_SOCKET_TYPE_ROUTER) {
SilcServerConfigSectionServerConnection *serv = NULL;
- serv =
- silc_server_config_find_router_conn(server->config,
- ctx->sock->ip,
- ctx->sock->port);
+ serv = silc_server_config_find_router_conn(server->config,
+ ctx->sock->ip,
+ ctx->sock->port);
if (!serv)
- serv =
- silc_server_config_find_router_conn(server->config,
- ctx->sock->hostname,
- ctx->sock->port);
+ serv = silc_server_config_find_router_conn(server->config,
+ ctx->sock->hostname,
+ ctx->sock->port);
if (serv) {
switch(serv->auth_meth) {
ret = silc_server_password_authentication(server, auth_data,
serv->auth_data);
- if (ret) {
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
+ if (ret)
break;
- }
/* Authentication failed */
SILC_LOG_ERROR(("Authentication failed"));
payload_len,
ctx->ske);
- if (ret) {
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
+ if (ret)
break;
- }
SILC_LOG_ERROR(("Authentication failed"));
SILC_LOG_DEBUG(("Authentication failed"));
SILC_LOG_DEBUG(("No configuration for remote connection"));
SILC_LOG_ERROR(("Remote connection not configured"));
SILC_LOG_ERROR(("Authentication failed"));
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- auth_data = NULL;
protocol->state = SILC_PROTOCOL_STATE_ERROR;
protocol->execute(server->timeout_queue, 0,
protocol, fd, 0, 300000);
}
}
- if (auth_data) {
- memset(auth_data, 0, payload_len);
- silc_free(auth_data);
- }
-
/* Save connection type. This is later used to create the
ID for the connection. */
ctx->conn_type = conn_type;
case SILC_AUTH_PASSWORD:
/* Password authentication */
if (ctx->auth_data && ctx->auth_data_len) {
- auth_data = ctx->auth_data;
+ auth_data = strdup(ctx->auth_data);
auth_data_len = ctx->auth_data_len;
break;
}
break;
case SILC_AUTH_PUBLIC_KEY:
- /* Public key authentication */
- /* XXX TODO */
- break;
+ {
+ unsigned char sign[1024];
+
+ /* Public key authentication */
+ silc_server_get_public_key_auth(server, ctx->auth_data,
+ sign, &auth_data_len,
+ ctx->ske);
+ break;
+ }
}
payload_len = 4 + auth_data_len;
/* Authentication data if we alreay know it. This is filled before
starting the protocol if we know the authentication data. Otherwise
these are and remain NULL. Used when we are initiating. */
- unsigned char *auth_data;
+ void *auth_data;
unsigned int auth_data_len;
/* Destinations ID from KE protocol context */
SilcServerConnection sconn = (SilcServerConnection)ctx->context;
SilcSocketConnection sock = NULL;
SilcServerConnAuthInternalContext *proto_ctx;
+ SilcServerConfigSectionServerConnection *conn = NULL;
SILC_LOG_DEBUG(("Start"));
proto_ctx->dest_id_type = ctx->dest_id_type;
proto_ctx->dest_id = ctx->dest_id;
- /* Resolve the authentication method used in this connection */
- proto_ctx->auth_meth = SILC_AUTH_PASSWORD;
- if (server->config->routers) {
- SilcServerConfigSectionServerConnection *conn = NULL;
-
- /* Check if we find a match from user configured connections */
- conn = silc_server_config_find_router_conn(server->config,
- sock->hostname,
- sock->port);
- if (conn) {
- /* Match found. Use the configured authentication method */
- proto_ctx->auth_meth = conn->auth_meth;
- if (conn->auth_data) {
- proto_ctx->auth_data = strdup(conn->auth_data);
- proto_ctx->auth_data_len = strlen(conn->auth_data);
- }
- } else {
- /* No match found. */
- /* XXX */
+ /* Resolve the authentication method used in this connection. Check if
+ we find a match from user configured connections */
+ conn = silc_server_config_find_router_conn(server->config,
+ sock->hostname,
+ sock->port);
+ if (conn) {
+ /* Match found. Use the configured authentication method */
+ proto_ctx->auth_meth = conn->auth_meth;
+ if (conn->auth_data) {
+ proto_ctx->auth_data = strdup(conn->auth_data);
+ proto_ctx->auth_data_len = strlen(conn->auth_data);
}
} else {
- /* XXX */
+ SILC_LOG_ERROR(("Could not find connection data for %s (%s) on port",
+ sock->hostname, sock->ip, sock->port));
+ silc_protocol_free(protocol);
+ silc_ske_free_key_material(ctx->keymat);
+ if (ctx->packet)
+ silc_packet_context_free(ctx->packet);
+ if (ctx->ske)
+ silc_ske_free(ctx->ske);
+ if (ctx->dest_id)
+ silc_free(ctx->dest_id);
+ silc_free(ctx);
+ silc_task_unregister_by_callback(server->timeout_queue,
+ silc_server_failure_callback);
+ silc_server_disconnect_remote(server, sock, "Server closed connection: "
+ "Key exchange failed");
+ return;
}
/* Free old protocol as it is finished now */
/* Check max connections */
if (sock > SILC_SERVER_MAX_CONNECTIONS) {
- if (server->config->redirect) {
- /* XXX Redirecting connection to somewhere else now?? */
- /*silc_server_send_notify("Server is full, trying to redirect..."); */
- } else {
- SILC_LOG_ERROR(("Refusing connection, server is full"));
- server->stat.conn_failures++;
- }
+ SILC_LOG_ERROR(("Refusing connection, server is full"));
+ server->stat.conn_failures++;
return;
}
SILC_LOG_DEBUG(("Connection authentication request packet"));
if (packet->flags & SILC_PACKET_FLAG_LIST)
break;
+ silc_server_connection_auth_request(server, sock, packet);
break;
/*
SILC_CONFIG_SERVER_SECTION_TYPE_ADMIN_CONNECTION, 5 },
{ "[DenyConnection]",
SILC_CONFIG_SERVER_SECTION_TYPE_DENY_CONNECTION, 4 },
- { "[RedirectClient]",
- SILC_CONFIG_SERVER_SECTION_TYPE_REDIRECT_CLIENT, 2 },
{ "[motd]",
SILC_CONFIG_SERVER_SECTION_TYPE_MOTD, 1 },
silc_free(config->servers);
silc_free(config->routers);
silc_free(config->denied);
- silc_free(config->redirect);
silc_free(config->motd);
silc_free(config);
}
check = TRUE;
break;
- case SILC_CONFIG_SERVER_SECTION_TYPE_REDIRECT_CLIENT:
- /* Not implemented yet */
- check = TRUE;
- break;
-
case SILC_CONFIG_SERVER_SECTION_TYPE_MOTD:
if (!config->motd)
<RouterConnection>
<DenyConnection>
-<RedirectClient>
*/
fprintf(stdout, "%s\n", buf);
unsigned short port;
} SilcServerConfigSectionDenyConnection;
-/* Holds all client redirections from config file */
-typedef struct {
- char *host;
- unsigned short port;
-} SilcServerConfigSectionRedirectClient;
-
/* Holds motd file */
typedef struct {
char *motd_file;
SilcServerConfigSectionServerConnection *routers;
SilcServerConfigSectionAdminConnection *admins;
SilcServerConfigSectionDenyConnection *denied;
- SilcServerConfigSectionRedirectClient *redirect;
SilcServerConfigSectionMotd *motd;
} SilcServerConfigObject;
SILC_CONFIG_SERVER_SECTION_TYPE_ROUTER_CONNECTION,
SILC_CONFIG_SERVER_SECTION_TYPE_ADMIN_CONNECTION,
SILC_CONFIG_SERVER_SECTION_TYPE_DENY_CONNECTION,
- SILC_CONFIG_SERVER_SECTION_TYPE_REDIRECT_CLIENT,
SILC_CONFIG_SERVER_SECTION_TYPE_MOTD,
} SilcServerConfigSectionType;
SILC_PACKET_CONNECTION_AUTH packet with Connection Auth Payload,
described in the next section. This payload must include the
authentication data. Authentication data is set according
-authentication method that must be known by both parties. If connecting
-party does not know what is the mandatory authentication method it must
+authentication method that must be known by both parties. If connecting
+party does not know what is the mandatory authentication method it may
request it from the server by sending SILC_PACKET_CONNECTION_AUTH_REQUEST
packet. This packet is not part of this protocol and is described in
section Connection Auth Request Payload in [SILC2]. However, if
This packet is used to request the authentication method to
be used in the SILC Connection Authentication Protocol. If
initiator of the protocol does not know the mandatory
- authentication method this packet is used to determine it.
+ authentication method this packet may be used to determine it.
The party receiving this payload must respond with the same
packet including the mandatory authentication method.
# Format: <remote host/nickname>:<time interval>:<comment>:<port>
#
[DenyConnection]
-
-#
-# Redirected client connections.
-#
-# Clients will be redirected to these servers when our server is full.
-#
-# Format: <remote host>:<port>
-#
-[RedirectClient]
if (!client->ops->get_auth_method(client, sock->user_data, sock->hostname,
sock->port, &proto_ctx->auth_meth,
&proto_ctx->auth_data,
- &proto_ctx->auth_data_len))
- {
- /* XXX do AUTH_REQUEST resolcing with server */
- proto_ctx->auth_meth = SILC_AUTH_NONE;
- }
+ &proto_ctx->auth_data_len)) {
+ client->ops->say(client, ctx->sock->user_data,
+ "Could not resolve authentication method to use, "
+ "assume no authentication");
+ proto_ctx->auth_meth = SILC_AUTH_NONE;
+ }
/* Free old protocol as it is finished now */
silc_protocol_free(protocol);
if (ctx->packet)
silc_packet_context_free(ctx->packet);
silc_free(ctx);
- /* silc_free(ctx->keymat....); */
sock->protocol = NULL;
/* Allocate the authentication protocol. This is allocated here
SilcSKEStatus status = SILC_SKE_STATUS_OK;
SilcBuffer payload_buf;
SilcInt *KEY;
- unsigned char hash[32], sign[256], *pk;
+ unsigned char hash[32], sign[1024], *pk;
unsigned int hash_len, sign_len, pk_len;
SILC_LOG_DEBUG(("Start"));