5 Author: Pekka Riikonen <priikone@poseidon.pspt.fi>
7 Copyright (C) 1997 - 2000 Pekka Riikonen
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
22 #include "serverincludes.h"
23 #include "server_internal.h"
25 SilcServerConfigSection silc_server_config_sections[] = {
27 SILC_CONFIG_SERVER_SECTION_TYPE_CIPHER, 4 },
29 SILC_CONFIG_SERVER_SECTION_TYPE_PKCS, 1 },
31 SILC_CONFIG_SERVER_SECTION_TYPE_HASH_FUNCTION, 4 },
33 SILC_CONFIG_SERVER_SECTION_TYPE_HMAC, 3 },
35 SILC_CONFIG_SERVER_SECTION_TYPE_SERVER_KEYS, 2 },
37 SILC_CONFIG_SERVER_SECTION_TYPE_SERVER_INFO, 4 },
39 SILC_CONFIG_SERVER_SECTION_TYPE_ADMIN_INFO, 4 },
41 SILC_CONFIG_SERVER_SECTION_TYPE_LISTEN_PORT, 3 },
43 SILC_CONFIG_SERVER_SECTION_TYPE_IDENTITY, 2 },
45 SILC_CONFIG_SERVER_SECTION_TYPE_LOGGING, 3 },
46 { "[ConnectionClass]",
47 SILC_CONFIG_SERVER_SECTION_TYPE_CONNECTION_CLASS, 4 },
48 { "[ClientConnection]",
49 SILC_CONFIG_SERVER_SECTION_TYPE_CLIENT_CONNECTION, 5 },
50 { "[ServerConnection]",
51 SILC_CONFIG_SERVER_SECTION_TYPE_SERVER_CONNECTION, 6 },
52 { "[RouterConnection]",
53 SILC_CONFIG_SERVER_SECTION_TYPE_ROUTER_CONNECTION, 7 },
54 { "[AdminConnection]",
55 SILC_CONFIG_SERVER_SECTION_TYPE_ADMIN_CONNECTION, 5 },
57 SILC_CONFIG_SERVER_SECTION_TYPE_DENY_CONNECTION, 3 },
59 SILC_CONFIG_SERVER_SECTION_TYPE_MOTD, 1 },
61 SILC_CONFIG_SERVER_SECTION_TYPE_PID, 1},
63 { NULL, SILC_CONFIG_SERVER_SECTION_TYPE_NONE, 0 }
66 /* Allocates a new configuration object, opens configuration file and
67 parses the file. The parsed data is returned to the newly allocated
68 configuration object. */
70 SilcServerConfig silc_server_config_alloc(char *filename)
74 SilcServerConfigParse config_parse;
76 SILC_LOG_DEBUG(("Allocating new configuration object"));
78 new = silc_calloc(1, sizeof(*new));
80 fprintf(stderr, "Could not allocate new configuration object");
84 new->filename = filename;
86 SILC_LOG_DEBUG(("Loading config data from `%s'", filename));
88 /* Open configuration file and parse it */
91 silc_config_open(filename, &buffer);
94 if ((silc_server_config_parse(new, buffer, &config_parse)) == FALSE)
96 if ((silc_server_config_parse_lines(new, config_parse)) == FALSE)
108 /* Free's a configuration object. */
110 void silc_server_config_free(SilcServerConfig config)
113 silc_free(config->filename);
114 silc_free(config->server_keys);
115 silc_free(config->server_info);
116 silc_free(config->admin_info);
117 silc_free(config->listen_port);
118 silc_free(config->identity);
119 silc_free(config->conn_class);
120 silc_free(config->clients);
121 silc_free(config->admins);
122 silc_free(config->servers);
123 silc_free(config->routers);
124 silc_free(config->denied);
125 silc_free(config->motd);
126 silc_free(config->pidfile);
131 /* Parses the the buffer and returns the parsed lines into return_config
132 argument. The return_config argument doesn't have to be initialized
133 before calling this. It will be initialized during the parsing. The
134 buffer sent as argument can be safely free'd after this function has
135 succesfully returned. */
137 int silc_server_config_parse(SilcServerConfig config, SilcBuffer buffer,
138 SilcServerConfigParse *return_config)
140 int i, begin, linenum;
141 char line[1024], *cp;
142 SilcServerConfigSection *cptr = NULL;
143 SilcServerConfigParse parse = *return_config, first = NULL;
145 SILC_LOG_DEBUG(("Parsing configuration file"));
149 while((begin = silc_gets(line, sizeof(line),
150 buffer->data, buffer->len, begin)) != EOF) {
154 /* Check for bad line */
155 if (silc_check_line(cp))
158 /* Remove tabs and whitespaces from the line */
159 if (strchr(cp, '\t')) {
161 while(strchr(cp + i, '\t')) {
162 *strchr(cp + i, '\t') = ' ';
166 for (i = 0; i < strlen(cp); i++) {
182 /* Remove new line sign */
183 if (strchr(cp, '\n'))
184 *strchr(cp, '\n') = '\0';
186 /* Check for matching sections */
187 for (cptr = silc_server_config_sections; cptr->section; cptr++)
188 if (!strncasecmp(cp, cptr->section, strlen(cptr->section)))
191 if (!cptr->section) {
192 fprintf(stderr, "%s:%d: Unknown section `%s'\n",
193 config->filename, linenum, cp);
200 * Start of a configuration line
203 if (cptr->type != SILC_CONFIG_SERVER_SECTION_TYPE_NONE) {
205 if (strchr(cp, '\n'))
206 *strchr(cp, '\n') = ':';
209 parse = silc_calloc(1, sizeof(*parse));
211 parse->section = NULL;
215 if (parse->next == NULL) {
216 parse->next = silc_calloc(1, sizeof(*parse->next));
217 parse->next->line = NULL;
218 parse->next->section = NULL;
219 parse->next->next = NULL;
220 parse->next->prev = parse;
228 /* Add the line to parsing structure for further parsing. */
230 parse->section = cptr;
231 parse->line = silc_buffer_alloc(strlen(cp) + 1);
232 parse->linenum = linenum;
233 silc_buffer_pull_tail(parse->line, strlen(cp));
234 silc_buffer_put(parse->line, cp, strlen(cp));
241 /* Set the return_config argument to its first value so that further
242 parsing can be started from the first line. */
243 *return_config = first;
248 /* Parses the lines earlier read from configuration file. The config object
249 must not be initialized, it will be initialized in this function. The
250 parse_config argument is uninitialized automatically during this
253 int silc_server_config_parse_lines(SilcServerConfig config,
254 SilcServerConfigParse parse_config)
256 int ret, check = FALSE;
259 SilcServerConfigParse pc = parse_config;
262 SILC_LOG_DEBUG(("Parsing configuration lines"));
272 /* Get number of tokens in line */
273 ret = silc_config_check_num_token(line);
274 if (ret < pc->section->maxfields) {
276 fprintf(stderr, "%s:%d: Missing tokens, %d tokens (should be %d)\n",
277 config->filename, pc->linenum, ret,
278 pc->section->maxfields);
283 switch(pc->section->type) {
284 case SILC_CONFIG_SERVER_SECTION_TYPE_CIPHER:
286 SILC_SERVER_CONFIG_LIST_ALLOC(config->cipher);
288 /* Get cipher name */
289 ret = silc_config_get_token(line, &config->cipher->alg_name);
293 fprintf(stderr, "%s:%d: Cipher name not defined\n",
294 config->filename, pc->linenum);
298 /* Get module name */
299 config->cipher->sim_name = NULL;
300 ret = silc_config_get_token(line, &config->cipher->sim_name);
305 ret = silc_config_get_token(line, &tmp);
309 fprintf(stderr, "%s:%d: Cipher key length not defined\n",
310 config->filename, pc->linenum);
313 config->cipher->key_len = atoi(tmp);
316 /* Get block length */
317 ret = silc_config_get_token(line, &tmp);
321 fprintf(stderr, "%s:%d: Cipher block length not defined\n",
322 config->filename, pc->linenum);
325 config->cipher->block_len = atoi(tmp);
329 checkmask |= (1L << pc->section->type);
332 case SILC_CONFIG_SERVER_SECTION_TYPE_PKCS:
334 SILC_SERVER_CONFIG_LIST_ALLOC(config->pkcs);
337 ret = silc_config_get_token(line, &config->pkcs->alg_name);
341 fprintf(stderr, "%s:%d: PKCS name not defined\n",
342 config->filename, pc->linenum);
347 checkmask |= (1L << pc->section->type);
350 case SILC_CONFIG_SERVER_SECTION_TYPE_HASH_FUNCTION:
352 SILC_SERVER_CONFIG_LIST_ALLOC(config->hash_func);
354 /* Get Hash function name */
355 ret = silc_config_get_token(line, &config->hash_func->alg_name);
359 fprintf(stderr, "%s:%d: Hash function name not defined\n",
360 config->filename, pc->linenum);
364 /* Get Hash function module name */
365 config->hash_func->sim_name = NULL;
366 ret = silc_config_get_token(line, &config->hash_func->sim_name);
370 /* Get block length */
371 ret = silc_config_get_token(line, &tmp);
375 fprintf(stderr, "%s:%d: Hash function block length not defined\n",
376 config->filename, pc->linenum);
379 config->hash_func->block_len = atoi(tmp);
382 /* Get hash length */
383 ret = silc_config_get_token(line, &tmp);
387 fprintf(stderr, "%s:%d: Hash function hash length not defined\n",
388 config->filename, pc->linenum);
391 config->hash_func->key_len = atoi(tmp);
395 checkmask |= (1L << pc->section->type);
398 case SILC_CONFIG_SERVER_SECTION_TYPE_HMAC:
400 SILC_SERVER_CONFIG_LIST_ALLOC(config->hmac);
403 ret = silc_config_get_token(line, &config->hmac->alg_name);
407 fprintf(stderr, "%s:%d: HMAC name not defined\n",
408 config->filename, pc->linenum);
413 ret = silc_config_get_token(line, &config->hmac->sim_name);
417 fprintf(stderr, "%s:%d: Hash function name not defined\n",
418 config->filename, pc->linenum);
423 ret = silc_config_get_token(line, &tmp);
427 fprintf(stderr, "%s:%d: HMAC's MAC length not defined\n",
428 config->filename, pc->linenum);
431 config->hmac->key_len = atoi(tmp);
435 checkmask |= (1L << pc->section->type);
438 case SILC_CONFIG_SERVER_SECTION_TYPE_SERVER_KEYS:
440 if (!config->server_keys)
441 config->server_keys = silc_calloc(1, sizeof(*config->server_keys));
443 ret = silc_config_get_token(line, &tmp);
447 fprintf(stderr, "%s:%d: Public key name not defined\n",
448 config->filename, pc->linenum);
452 if (!silc_pkcs_load_public_key(tmp, &config->server_keys->public_key,
454 if (!silc_pkcs_load_public_key(tmp, &config->server_keys->public_key,
455 SILC_PKCS_FILE_BIN)) {
456 fprintf(stderr, "%s:%d: Could not load public key file `%s'\n",
457 config->filename, pc->linenum, tmp);
462 ret = silc_config_get_token(line, &tmp);
466 fprintf(stderr, "%s:%d: Private key name not defined\n",
467 config->filename, pc->linenum);
471 if (!silc_pkcs_load_private_key(tmp, &config->server_keys->private_key,
473 if (!silc_pkcs_load_private_key(tmp,
474 &config->server_keys->private_key,
475 SILC_PKCS_FILE_PEM)) {
476 fprintf(stderr, "%s:%d: Could not load private key file `%s'\n",
477 config->filename, pc->linenum, tmp);
483 checkmask |= (1L << pc->section->type);
486 case SILC_CONFIG_SERVER_SECTION_TYPE_SERVER_INFO:
488 if (!config->server_info)
489 config->server_info = silc_calloc(1, sizeof(*config->server_info));
491 /* Get server name */
492 ret = silc_config_get_token(line, &config->server_info->server_name);
496 /* Server name not defined */
501 ret = silc_config_get_token(line, &config->server_info->server_ip);
505 /* Server IP not defined */
509 /* Get server location */
510 ret = silc_config_get_token(line, &config->server_info->location);
514 /* Get server port */
515 /* XXX: Need port here??? */
516 ret = silc_config_get_token(line, &tmp);
520 /* Port not defined */
523 config->server_info->port = atoi(tmp);
527 checkmask |= (1L << pc->section->type);
530 case SILC_CONFIG_SERVER_SECTION_TYPE_ADMIN_INFO:
532 if (!config->admin_info)
533 config->admin_info = silc_calloc(1, sizeof(*config->admin_info));
536 ret = silc_config_get_token(line, &config->admin_info->location);
540 /* Get server type */
541 ret = silc_config_get_token(line, &config->admin_info->server_type);
545 /* Get admins name */
546 ret = silc_config_get_token(line, &config->admin_info->admin_name);
550 /* Get admins email address */
551 ret = silc_config_get_token(line, &config->admin_info->admin_email);
556 checkmask |= (1L << pc->section->type);
559 case SILC_CONFIG_SERVER_SECTION_TYPE_LISTEN_PORT:
561 SILC_SERVER_CONFIG_LIST_ALLOC(config->listen_port);
564 ret = silc_config_get_token(line, &config->listen_port->local_ip);
568 /* Get listener IP */
569 ret = silc_config_get_token(line, &config->listen_port->listener_ip);
574 ret = silc_config_get_token(line, &tmp);
579 config->listen_port->port = 0;
581 config->listen_port->port = atoi(tmp);
586 checkmask |= (1L << pc->section->type);
589 case SILC_CONFIG_SERVER_SECTION_TYPE_IDENTITY:
591 if (!config->identity)
592 config->identity = silc_calloc(1, sizeof(*config->identity));
595 ret = silc_config_get_token(line, &config->identity->user);
599 ret = silc_config_get_token(line, &config->identity->group);
604 checkmask |= (1L << pc->section->type);
606 case SILC_CONFIG_SERVER_SECTION_TYPE_CONNECTION_CLASS:
608 SILC_SERVER_CONFIG_LIST_ALLOC(config->conn_class);
610 /* Get class number */
611 ret = silc_config_get_token(line, &tmp);
615 /* Class number not defined */
618 config->conn_class->class = atoi(tmp);
621 /* Get ping frequency */
622 ret = silc_config_get_token(line, &tmp);
625 config->conn_class->ping_freq = atoi(tmp);
628 /* Get connect frequency */
629 ret = silc_config_get_token(line, &tmp);
632 config->conn_class->connect_freq = atoi(tmp);
636 ret = silc_config_get_token(line, &tmp);
639 config->conn_class->max_links = atoi(tmp);
643 checkmask |= (1L << pc->section->type);
646 case SILC_CONFIG_SERVER_SECTION_TYPE_LOGGING:
648 SILC_SERVER_CONFIG_LIST_ALLOC(config->logging);
650 /* Get log section type and check it */
651 ret = silc_config_get_token(line, &config->logging->logtype);
655 fprintf(stderr, "%s:%d: Log file section not defined\n",
656 config->filename, pc->linenum);
659 if (strcmp(config->logging->logtype, SILC_CONFIG_SERVER_LF_INFO)
660 && strcmp(config->logging->logtype, SILC_CONFIG_SERVER_LF_WARNING)
661 && strcmp(config->logging->logtype, SILC_CONFIG_SERVER_LF_ERROR)
662 && strcmp(config->logging->logtype, SILC_CONFIG_SERVER_LF_FATAL)) {
663 fprintf(stderr, "%s:%d: Unknown log file section '%s'\n",
664 config->filename, pc->linenum, config->logging->logtype);
668 /* Get log filename */
669 ret = silc_config_get_token(line, &config->logging->filename);
673 fprintf(stderr, "%s:%d: Log file name not defined\n",
674 config->filename, pc->linenum);
678 /* Get max byte size */
679 ret = silc_config_get_token(line, &tmp);
683 config->logging->maxsize = atoi(tmp);
688 checkmask |= (1L << pc->section->type);
691 case SILC_CONFIG_SERVER_SECTION_TYPE_CLIENT_CONNECTION:
693 SILC_SERVER_CONFIG_LIST_ALLOC(config->clients);
696 ret = silc_config_get_token(line, &config->clients->host);
701 config->clients->host = strdup("*");
703 /* Get authentication method */
704 ret = silc_config_get_token(line, &tmp);
708 if (strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PASSWD) &&
709 strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PUBKEY)) {
710 fprintf(stderr, "%s:%d: Unknown authentication method '%s'\n",
711 config->filename, pc->linenum, tmp);
715 if (!strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PASSWD))
716 config->clients->auth_meth = SILC_AUTH_PASSWORD;
718 if (!strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PUBKEY))
719 config->clients->auth_meth = SILC_AUTH_PUBLIC_KEY;
724 /* Get authentication data */
725 ret = silc_config_get_token(line, (char **)&config->clients->auth_data);
729 if (config->clients->auth_meth == SILC_AUTH_PASSWORD) {
730 config->clients->auth_data_len = strlen(config->clients->auth_data);
731 } else if (config->clients->auth_meth == SILC_AUTH_PUBLIC_KEY) {
732 /* Get the public key */
733 SilcPublicKey public_key;
735 if (!silc_pkcs_load_public_key(config->clients->auth_data,
736 &public_key, SILC_PKCS_FILE_PEM))
737 if (!silc_pkcs_load_public_key(config->clients->auth_data,
738 &public_key, SILC_PKCS_FILE_BIN)) {
739 fprintf(stderr, "%s:%d: Could not load public key file `%s'\n",
740 config->filename, pc->linenum,
741 (char *)config->clients->auth_data);
745 silc_free(config->clients->auth_data);
746 config->clients->auth_data = (void *)public_key;
747 config->clients->auth_data_len = 0;
751 ret = silc_config_get_token(line, &tmp);
755 config->clients->port = atoi(tmp);
759 /* Get class number */
760 ret = silc_config_get_token(line, &tmp);
764 config->clients->class = atoi(tmp);
769 checkmask |= (1L << pc->section->type);
772 case SILC_CONFIG_SERVER_SECTION_TYPE_SERVER_CONNECTION:
774 SILC_SERVER_CONFIG_LIST_ALLOC(config->servers);
777 ret = silc_config_get_token(line, &config->servers->host);
782 config->servers->host = strdup("*");
784 /* Get authentication method */
785 ret = silc_config_get_token(line, &tmp);
789 if (strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PASSWD) &&
790 strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PUBKEY)) {
791 fprintf(stderr, "%s:%d: Unknown authentication method '%s'\n",
792 config->filename, pc->linenum, tmp);
796 if (!strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PASSWD))
797 config->servers->auth_meth = SILC_AUTH_PASSWORD;
799 if (!strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PUBKEY))
800 config->servers->auth_meth = SILC_AUTH_PUBLIC_KEY;
805 /* Get authentication data */
806 ret = silc_config_get_token(line, (char **)&config->servers->auth_data);
810 if (config->servers->auth_meth == SILC_AUTH_PASSWORD) {
811 config->servers->auth_data_len = strlen(config->servers->auth_data);
812 } else if (config->servers->auth_meth == SILC_AUTH_PUBLIC_KEY) {
813 /* Get the public key */
814 SilcPublicKey public_key;
816 if (!silc_pkcs_load_public_key(config->servers->auth_data,
817 &public_key, SILC_PKCS_FILE_PEM))
818 if (!silc_pkcs_load_public_key(config->servers->auth_data,
819 &public_key, SILC_PKCS_FILE_BIN)) {
820 fprintf(stderr, "%s:%d: Could not load public key file `%s'\n",
821 config->filename, pc->linenum,
822 (char *)config->servers->auth_data);
826 silc_free(config->servers->auth_data);
827 config->servers->auth_data = (void *)public_key;
828 config->servers->auth_data_len = 0;
832 ret = silc_config_get_token(line, &tmp);
836 config->servers->port = atoi(tmp);
841 ret = silc_config_get_token(line, &config->servers->version);
845 /* Get class number */
846 ret = silc_config_get_token(line, &tmp);
850 config->servers->class = atoi(tmp);
854 /* Check whether this connection is backup router connection */
855 ret = silc_config_get_token(line, &tmp);
857 config->servers->backup_router = atoi(tmp);
858 if (config->servers->backup_router != 0)
859 config->servers->backup_router = TRUE;
864 checkmask |= (1L << pc->section->type);
867 case SILC_CONFIG_SERVER_SECTION_TYPE_ROUTER_CONNECTION:
869 SILC_SERVER_CONFIG_LIST_ALLOC(config->routers);
872 ret = silc_config_get_token(line, &config->routers->host);
876 /* Get authentication method */
877 ret = silc_config_get_token(line, &tmp);
881 if (strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PASSWD) &&
882 strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PUBKEY)) {
883 fprintf(stderr, "%s:%d: Unknown authentication method '%s'\n",
884 config->filename, pc->linenum, tmp);
888 if (!strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PASSWD))
889 config->routers->auth_meth = SILC_AUTH_PASSWORD;
891 if (!strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PUBKEY))
892 config->routers->auth_meth = SILC_AUTH_PUBLIC_KEY;
897 /* Get authentication data */
898 ret = silc_config_get_token(line, (char **)&config->routers->auth_data);
902 if (config->routers->auth_meth == SILC_AUTH_PASSWORD) {
903 config->routers->auth_data_len = strlen(config->routers->auth_data);
904 } else if (config->routers->auth_meth == SILC_AUTH_PUBLIC_KEY) {
905 /* Get the public key */
906 SilcPublicKey public_key;
908 if (!silc_pkcs_load_public_key(config->routers->auth_data,
909 &public_key, SILC_PKCS_FILE_PEM))
910 if (!silc_pkcs_load_public_key(config->routers->auth_data,
911 &public_key, SILC_PKCS_FILE_BIN)) {
912 fprintf(stderr, "%s:%d: Could not load public key file `%s'\n",
913 config->filename, pc->linenum,
914 (char *)config->routers->auth_data);
918 silc_free(config->routers->auth_data);
919 config->routers->auth_data = (void *)public_key;
920 config->routers->auth_data_len = 0;
924 ret = silc_config_get_token(line, &tmp);
928 config->routers->port = atoi(tmp);
933 ret = silc_config_get_token(line, &config->routers->version);
937 /* Get class number */
938 ret = silc_config_get_token(line, &tmp);
942 config->routers->class = atoi(tmp);
946 /* Get whether we are initiator or not */
947 ret = silc_config_get_token(line, &tmp);
951 config->routers->initiator = atoi(tmp);
952 if (config->routers->initiator != 0)
953 config->routers->initiator = TRUE;
957 /* Get backup replace IP */
958 ret = silc_config_get_token(line, &config->routers->backup_replace_ip);
960 config->routers->backup_router = TRUE;
962 if (config->routers->backup_router) {
963 /* Get backup replace port */
964 ret = silc_config_get_token(line, &tmp);
966 config->routers->backup_replace_port = atoi(tmp);
970 /* Check whether the backup connection is local */
971 ret = silc_config_get_token(line, &tmp);
973 config->routers->backup_local = atoi(tmp);
974 if (config->routers->backup_local != 0)
975 config->routers->backup_local = TRUE;
981 checkmask |= (1L << pc->section->type);
984 case SILC_CONFIG_SERVER_SECTION_TYPE_ADMIN_CONNECTION:
986 SILC_SERVER_CONFIG_LIST_ALLOC(config->admins);
989 ret = silc_config_get_token(line, &config->admins->host);
994 config->admins->host = strdup("*");
997 ret = silc_config_get_token(line, &config->admins->username);
1002 config->admins->username = strdup("*");
1005 ret = silc_config_get_token(line, &config->admins->nickname);
1010 config->admins->nickname = strdup("*");
1012 /* Get authentication method */
1013 ret = silc_config_get_token(line, &tmp);
1017 if (strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PASSWD) &&
1018 strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PUBKEY)) {
1019 fprintf(stderr, "%s:%d: Unknown authentication method '%s'\n",
1020 config->filename, pc->linenum, tmp);
1024 if (!strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PASSWD))
1025 config->admins->auth_meth = SILC_AUTH_PASSWORD;
1027 if (!strcmp(tmp, SILC_CONFIG_SERVER_AUTH_METH_PUBKEY))
1028 config->admins->auth_meth = SILC_AUTH_PUBLIC_KEY;
1033 /* Get authentication data */
1034 ret = silc_config_get_token(line, (char **)&config->admins->auth_data);
1038 if (config->admins->auth_meth == SILC_AUTH_PASSWORD) {
1039 config->admins->auth_data_len = strlen(config->admins->auth_data);
1040 } else if (config->admins->auth_meth == SILC_AUTH_PUBLIC_KEY) {
1041 /* Get the public key */
1042 SilcPublicKey public_key;
1044 if (!silc_pkcs_load_public_key(config->admins->auth_data,
1045 &public_key, SILC_PKCS_FILE_PEM))
1046 if (!silc_pkcs_load_public_key(config->admins->auth_data,
1047 &public_key, SILC_PKCS_FILE_BIN)) {
1048 fprintf(stderr, "%s:%d: Could not load public key file `%s'\n",
1049 config->filename, pc->linenum,
1050 (char *)config->admins->auth_data);
1054 silc_free(config->admins->auth_data);
1055 config->admins->auth_data = (void *)public_key;
1056 config->admins->auth_data_len = 0;
1060 checkmask |= (1L << pc->section->type);
1063 case SILC_CONFIG_SERVER_SECTION_TYPE_DENY_CONNECTION:
1065 SILC_SERVER_CONFIG_LIST_ALLOC(config->denied);
1068 ret = silc_config_get_token(line, &config->denied->host);
1073 config->denied->host = strdup("*");
1074 fprintf(stderr, "warning: %s:%d: Denying all connections",
1075 config->filename, pc->linenum);
1079 ret = silc_config_get_token(line, &tmp);
1084 config->denied->port = 0;
1086 config->denied->port = atoi(tmp);
1091 ret = silc_config_get_token(line, &config->denied->comment);
1096 checkmask |= (1L << pc->section->type);
1099 case SILC_CONFIG_SERVER_SECTION_TYPE_MOTD:
1102 config->motd = silc_calloc(1, sizeof(*config->motd));
1105 ret = silc_config_get_token(line, &config->motd->motd_file);
1110 checkmask |= (1L << pc->section->type);
1113 case SILC_CONFIG_SERVER_SECTION_TYPE_PID:
1115 if (!config->pidfile)
1116 config->pidfile = silc_calloc(1, sizeof(*config->pidfile));
1118 ret = silc_config_get_token(line, &config->pidfile->pid_file);
1123 checkmask |= (1L << pc->section->type);
1126 case SILC_CONFIG_SERVER_SECTION_TYPE_NONE:
1132 /* Check for error */
1133 if (check == FALSE) {
1134 /* Line could not be parsed */
1135 fprintf(stderr, "%s:%d: Parse error\n", config->filename, pc->linenum);
1145 /* Check that all mandatory sections really were found. If not, the server
1146 cannot function and we return error. */
1147 ret = silc_server_config_check_sections(checkmask);
1153 /* Before returning all the lists in the config object must be set
1154 to their first values (the last value is first here). */
1155 while (config->cipher && config->cipher->prev)
1156 config->cipher = config->cipher->prev;
1157 while (config->pkcs && config->pkcs->prev)
1158 config->pkcs = config->pkcs->prev;
1159 while (config->hash_func && config->hash_func->prev)
1160 config->hash_func = config->hash_func->prev;
1161 while (config->hmac && config->hmac->prev)
1162 config->hmac = config->hmac->prev;
1163 while (config->listen_port && config->listen_port->prev)
1164 config->listen_port = config->listen_port->prev;
1165 while (config->logging && config->logging->prev)
1166 config->logging = config->logging->prev;
1167 while (config->conn_class && config->conn_class->prev)
1168 config->conn_class = config->conn_class->prev;
1169 while (config->clients && config->clients->prev)
1170 config->clients = config->clients->prev;
1171 while (config->servers && config->servers->prev)
1172 config->servers = config->servers->prev;
1173 while (config->admins && config->admins->prev)
1174 config->admins = config->admins->prev;
1175 while (config->routers && config->routers->prev)
1176 config->routers = config->routers->prev;
1178 SILC_LOG_DEBUG(("Done"));
1183 /* This function checks that the mask sent as argument includes all the
1184 sections that are mandatory in SILC server. */
1186 int silc_server_config_check_sections(uint32 checkmask)
1188 if (!(checkmask & (1L << SILC_CONFIG_SERVER_SECTION_TYPE_SERVER_INFO))) {
1192 if (!(checkmask & (1L << SILC_CONFIG_SERVER_SECTION_TYPE_ADMIN_INFO))) {
1196 if (!(checkmask & (1L << SILC_CONFIG_SERVER_SECTION_TYPE_LISTEN_PORT))) {
1201 (1L << SILC_CONFIG_SERVER_SECTION_TYPE_CLIENT_CONNECTION))) {
1206 & (1L << SILC_CONFIG_SERVER_SECTION_TYPE_SERVER_CONNECTION))) {
1211 & (1L << SILC_CONFIG_SERVER_SECTION_TYPE_ROUTER_CONNECTION))) {
1219 /* Sets log files where log messages is saved by the server. */
1221 void silc_server_config_setlogfiles(SilcServerConfig config)
1223 SilcServerConfigSectionLogging *log;
1224 char *info, *warning, *error, *fatal;
1225 uint32 info_size, warning_size, error_size, fatal_size;
1227 SILC_LOG_DEBUG(("Setting configured log file names"));
1229 /* Set default files before checking configuration */
1230 info = SILC_LOG_FILE_INFO;
1231 warning = SILC_LOG_FILE_WARNING;
1232 error = SILC_LOG_FILE_ERROR;
1233 fatal = SILC_LOG_FILE_FATAL;
1239 log = config->logging;
1241 if (!strcmp(log->logtype, SILC_CONFIG_SERVER_LF_INFO)) {
1242 info = log->filename;
1243 info_size = log->maxsize;
1245 if (!strcmp(log->logtype, SILC_CONFIG_SERVER_LF_WARNING)) {
1246 warning = log->filename;
1247 warning_size = log->maxsize;
1249 if (!strcmp(log->logtype, SILC_CONFIG_SERVER_LF_ERROR)) {
1250 error = log->filename;
1251 error_size = log->maxsize;
1253 if (!strcmp(log->logtype, SILC_CONFIG_SERVER_LF_FATAL)) {
1254 fatal = log->filename;
1255 fatal_size = log->maxsize;
1261 silc_log_set_files(info, info_size, warning, warning_size,
1262 error, error_size, fatal, fatal_size);
1265 /* Registers configured ciphers. These can then be allocated by the
1266 server when needed. */
1268 bool silc_server_config_register_ciphers(SilcServerConfig config)
1270 SilcServerConfigSectionAlg *alg;
1271 SilcServer server = (SilcServer)config->server;
1273 SILC_LOG_DEBUG(("Registering configured ciphers"));
1275 if (!config->cipher)
1278 alg = config->cipher;
1281 if (!alg->sim_name) {
1284 for (i = 0; silc_default_ciphers[i].name; i++)
1285 if (!strcmp(silc_default_ciphers[i].name, alg->alg_name)) {
1286 silc_cipher_register(&silc_default_ciphers[i]);
1290 if (!silc_cipher_is_supported(alg->alg_name)) {
1291 SILC_LOG_ERROR(("Unknown cipher `%s'", alg->alg_name));
1292 silc_server_stop(server);
1297 /* Load (try at least) the crypto SIM module */
1298 SilcCipherObject cipher;
1299 SilcSimContext *sim;
1302 memset(&cipher, 0, sizeof(cipher));
1303 cipher.name = alg->alg_name;
1304 cipher.block_len = alg->block_len;
1305 cipher.key_len = alg->key_len * 8;
1307 sim = silc_sim_alloc();
1308 sim->type = SILC_SIM_CIPHER;
1309 sim->libname = alg->sim_name;
1311 alg_name = strdup(alg->alg_name);
1312 if (strchr(alg_name, '-'))
1313 *strchr(alg_name, '-') = '\0';
1315 if ((silc_sim_load(sim))) {
1317 silc_sim_getsym(sim, silc_sim_symname(alg_name,
1318 SILC_CIPHER_SIM_SET_KEY));
1319 SILC_LOG_DEBUG(("set_key=%p", cipher.set_key));
1320 cipher.set_key_with_string =
1321 silc_sim_getsym(sim, silc_sim_symname(alg_name,
1322 SILC_CIPHER_SIM_SET_KEY_WITH_STRING));
1323 SILC_LOG_DEBUG(("set_key_with_string=%p", cipher.set_key_with_string));
1325 silc_sim_getsym(sim, silc_sim_symname(alg_name,
1326 SILC_CIPHER_SIM_ENCRYPT_CBC));
1327 SILC_LOG_DEBUG(("encrypt_cbc=%p", cipher.encrypt));
1329 silc_sim_getsym(sim, silc_sim_symname(alg_name,
1330 SILC_CIPHER_SIM_DECRYPT_CBC));
1331 SILC_LOG_DEBUG(("decrypt_cbc=%p", cipher.decrypt));
1332 cipher.context_len =
1333 silc_sim_getsym(sim, silc_sim_symname(alg_name,
1334 SILC_CIPHER_SIM_CONTEXT_LEN));
1335 SILC_LOG_DEBUG(("context_len=%p", cipher.context_len));
1337 /* Put the SIM to the list of all SIM's in server */
1338 silc_dlist_add(server->sim, sim);
1340 silc_free(alg_name);
1342 SILC_LOG_ERROR(("Error configuring ciphers"));
1343 silc_server_stop(server);
1347 /* Register the cipher */
1348 silc_cipher_register(&cipher);
1358 /* Registers configured PKCS's. */
1360 bool silc_server_config_register_pkcs(SilcServerConfig config)
1362 SilcServerConfigSectionAlg *alg = config->pkcs;
1363 SilcServer server = (SilcServer)config->server;
1365 SILC_LOG_DEBUG(("Registering configured PKCS"));
1373 for (i = 0; silc_default_pkcs[i].name; i++)
1374 if (!strcmp(silc_default_pkcs[i].name, alg->alg_name)) {
1375 silc_pkcs_register(&silc_default_pkcs[i]);
1379 if (!silc_pkcs_is_supported(alg->alg_name)) {
1380 SILC_LOG_ERROR(("Unknown PKCS `%s'", alg->alg_name));
1381 silc_server_stop(server);
1391 /* Registers configured hash functions. These can then be allocated by the
1392 server when needed. */
1394 bool silc_server_config_register_hashfuncs(SilcServerConfig config)
1396 SilcServerConfigSectionAlg *alg;
1397 SilcServer server = (SilcServer)config->server;
1399 SILC_LOG_DEBUG(("Registering configured hash functions"));
1401 if (!config->hash_func)
1404 alg = config->hash_func;
1407 if (!alg->sim_name) {
1410 for (i = 0; silc_default_hash[i].name; i++)
1411 if (!strcmp(silc_default_hash[i].name, alg->alg_name)) {
1412 silc_hash_register(&silc_default_hash[i]);
1416 if (!silc_hash_is_supported(alg->alg_name)) {
1417 SILC_LOG_ERROR(("Unknown hash funtion `%s'", alg->alg_name));
1418 silc_server_stop(server);
1424 /* Load (try at least) the hash SIM module */
1425 SilcHashObject hash;
1426 SilcSimContext *sim;
1428 memset(&hash, 0, sizeof(hash));
1429 hash.name = alg->alg_name;
1430 hash.block_len = alg->block_len;
1431 hash.hash_len = alg->key_len;
1433 sim = silc_sim_alloc();
1434 sim->type = SILC_SIM_HASH;
1435 sim->libname = alg->sim_name;
1437 if ((silc_sim_load(sim))) {
1439 silc_sim_getsym(sim, silc_sim_symname(alg->alg_name,
1440 SILC_HASH_SIM_INIT));
1441 SILC_LOG_DEBUG(("init=%p", hash.init));
1443 silc_sim_getsym(sim, silc_sim_symname(alg->alg_name,
1444 SILC_HASH_SIM_UPDATE));
1445 SILC_LOG_DEBUG(("update=%p", hash.update));
1447 silc_sim_getsym(sim, silc_sim_symname(alg->alg_name,
1448 SILC_HASH_SIM_FINAL));
1449 SILC_LOG_DEBUG(("final=%p", hash.final));
1451 silc_sim_getsym(sim, silc_sim_symname(alg->alg_name,
1452 SILC_HASH_SIM_CONTEXT_LEN));
1453 SILC_LOG_DEBUG(("context_len=%p", hash.context_len));
1455 /* Put the SIM to the table of all SIM's in server */
1456 silc_dlist_add(server->sim, sim);
1458 SILC_LOG_ERROR(("Error configuring hash functions"));
1459 silc_server_stop(server);
1463 /* Register the hash function */
1464 silc_hash_register(&hash);
1474 /* Registers configure HMACs. These can then be allocated by the server
1477 bool silc_server_config_register_hmacs(SilcServerConfig config)
1479 SilcServerConfigSectionAlg *alg;
1480 SilcServer server = (SilcServer)config->server;
1482 SILC_LOG_DEBUG(("Registering configured HMACs"));
1489 SilcHmacObject hmac;
1491 if (!silc_hash_is_supported(alg->sim_name)) {
1492 SILC_LOG_ERROR(("Unknown hash function `%s'", alg->sim_name));
1493 silc_server_stop(server);
1497 /* Register the HMAC */
1498 memset(&hmac, 0, sizeof(hmac));
1499 hmac.name = alg->alg_name;
1500 hmac.len = alg->key_len;
1501 silc_hmac_register(&hmac);
1509 /* Returns client authentication information from server configuration
1510 by host (name or ip). If `port' is non-null then both name or IP and
1511 the port must match. */
1513 SilcServerConfigSectionClientConnection *
1514 silc_server_config_find_client_conn(SilcServerConfig config,
1515 char *host, int port)
1518 SilcServerConfigSectionClientConnection *client = NULL;
1524 if (!config->clients)
1527 client = config->clients;
1529 for (i = 0; client; i++) {
1530 if (silc_string_compare(client->host, host))
1533 if (port && client->port && client->port != port)
1539 client = client->next;
1548 /* Returns server connection info from server configuartion by host
1549 (name or ip). If `port' is non-null then both name or IP and the port
1552 SilcServerConfigSectionServerConnection *
1553 silc_server_config_find_server_conn(SilcServerConfig config,
1554 char *host, int port)
1557 SilcServerConfigSectionServerConnection *serv = NULL;
1563 if (!config->servers)
1566 serv = config->servers;
1567 for (i = 0; serv; i++) {
1568 if (silc_string_compare(serv->host, host))
1571 if (port && serv->port && serv->port != port)
1586 /* Returns router connection info from server configuartion by
1587 host (name or ip). */
1589 SilcServerConfigSectionServerConnection *
1590 silc_server_config_find_router_conn(SilcServerConfig config,
1591 char *host, int port)
1594 SilcServerConfigSectionServerConnection *serv = NULL;
1600 if (!config->routers)
1603 serv = config->routers;
1604 for (i = 0; serv; i++) {
1605 if (silc_string_compare(serv->host, host))
1608 if (port && serv->port && serv->port != port)
1623 /* Returns TRUE if configuartion for a router connection that we are
1624 initiating exists. */
1626 bool silc_server_config_is_primary_route(SilcServerConfig config)
1629 SilcServerConfigSectionServerConnection *serv = NULL;
1632 serv = config->routers;
1633 for (i = 0; serv; i++) {
1634 if (serv->initiator == TRUE && serv->backup_router == FALSE) {
1645 /* Returns our primary connection configuration or NULL if we do not
1646 have primary router configured. */
1648 SilcServerConfigSectionServerConnection *
1649 silc_server_config_get_primary_router(SilcServerConfig config)
1652 SilcServerConfigSectionServerConnection *serv = NULL;
1654 serv = config->routers;
1655 for (i = 0; serv; i++) {
1656 if (serv->initiator == TRUE && serv->backup_router == FALSE)
1664 /* Returns Admin connection configuration by host, username and/or
1667 SilcServerConfigSectionAdminConnection *
1668 silc_server_config_find_admin(SilcServerConfig config,
1669 char *host, char *username, char *nickname)
1671 SilcServerConfigSectionAdminConnection *admin = NULL;
1674 if (!config->admins)
1684 admin = config->admins;
1685 for (i = 0; admin; i++) {
1686 if (silc_string_compare(admin->host, host) &&
1687 silc_string_compare(admin->username, username) &&
1688 silc_string_compare(admin->nickname, nickname))
1691 admin = admin->next;
1700 /* Returns the Denied connection configuration by host and port. */
1702 SilcServerConfigSectionDenyConnection *
1703 silc_server_config_denied_conn(SilcServerConfig config, char *host,
1707 SilcServerConfigSectionDenyConnection *deny = NULL;
1713 if (!config->denied)
1716 deny = config->denied;
1717 for (i = 0; deny; i++) {
1718 if (silc_string_compare(deny->host, host))
1721 if (port && deny->port && deny->port != port)