diff options
author | Christian Grothoff <christian@grothoff.org> | 2018-04-15 20:42:00 +0200 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2018-04-15 20:42:00 +0200 |
commit | 284cfac7a521ad275b7536ce1075f62b6e45ea44 (patch) | |
tree | 5fa13df4b6493ed95a21105a7c9af428d1a128e3 /src/namestore | |
parent | 66a629d3bee4652268ffd0e4b15b9cc490d3974f (diff) | |
download | gnunet-284cfac7a521ad275b7536ce1075f62b6e45ea44.tar.gz gnunet-284cfac7a521ad275b7536ce1075f62b6e45ea44.zip |
modify zoneimport to deal with non-TLD zones due to difference in zone cuts between DNS and GNS
Diffstat (limited to 'src/namestore')
-rw-r--r-- | src/namestore/gnunet-zoneimport.c | 129 |
1 files changed, 85 insertions, 44 deletions
diff --git a/src/namestore/gnunet-zoneimport.c b/src/namestore/gnunet-zoneimport.c index bac3d2603..e1d5b650d 100644 --- a/src/namestore/gnunet-zoneimport.c +++ b/src/namestore/gnunet-zoneimport.c | |||
@@ -32,6 +32,38 @@ | |||
32 | 32 | ||
33 | 33 | ||
34 | /** | 34 | /** |
35 | * Some zones may include authoritative records for other | ||
36 | * zones, such as foo.com.uk or bar.com.fr. As for GNS | ||
37 | * each dot represents a zone cut, we then need to create a | ||
38 | * zone on-the-fly to capture those records properly. | ||
39 | */ | ||
40 | struct Zone | ||
41 | { | ||
42 | |||
43 | /** | ||
44 | * Kept in a DLL. | ||
45 | */ | ||
46 | struct Zone *next; | ||
47 | |||
48 | /** | ||
49 | * Kept in a DLL. | ||
50 | */ | ||
51 | struct Zone *prev; | ||
52 | |||
53 | /** | ||
54 | * Domain of the zone (i.e. "fr" or "com.fr") | ||
55 | */ | ||
56 | char *domain; | ||
57 | |||
58 | /** | ||
59 | * Private key of the zone. | ||
60 | */ | ||
61 | struct GNUNET_CRYPTO_EcdsaPrivateKey key; | ||
62 | |||
63 | }; | ||
64 | |||
65 | |||
66 | /** | ||
35 | * Record for the request to be stored by GNS. | 67 | * Record for the request to be stored by GNS. |
36 | */ | 68 | */ |
37 | struct Record | 69 | struct Record |
@@ -97,6 +129,11 @@ struct Request | |||
97 | char *label; | 129 | char *label; |
98 | 130 | ||
99 | /** | 131 | /** |
132 | * Zone responsible for this request. | ||
133 | */ | ||
134 | const struct Zone *zone; | ||
135 | |||
136 | /** | ||
100 | * Answer we got back and are currently parsing, or NULL | 137 | * Answer we got back and are currently parsing, or NULL |
101 | * if not active. | 138 | * if not active. |
102 | */ | 139 | */ |
@@ -194,20 +231,14 @@ static char *dns_server; | |||
194 | static char *db_lib_name; | 231 | static char *db_lib_name; |
195 | 232 | ||
196 | /** | 233 | /** |
197 | * Which zone are we importing into? | 234 | * Head of list of zones we are managing. |
198 | */ | 235 | */ |
199 | static struct GNUNET_CRYPTO_EcdsaPrivateKey zone; | 236 | static struct Zone *zone_head; |
200 | 237 | ||
201 | /** | 238 | /** |
202 | * Which zone should records be imported into? | 239 | * Tail of list of zones we are managing. |
203 | */ | 240 | */ |
204 | static char *zone_name; | 241 | static struct Zone *zone_tail; |
205 | |||
206 | /** | ||
207 | * Did we find #zone_name and initialize #zone? | ||
208 | */ | ||
209 | static int zone_found; | ||
210 | |||
211 | 242 | ||
212 | /** | 243 | /** |
213 | * Maximum number of queries pending at the same time. | 244 | * Maximum number of queries pending at the same time. |
@@ -789,7 +820,7 @@ process_result (void *cls, | |||
789 | rd[off++] = rec->grd; | 820 | rd[off++] = rec->grd; |
790 | if (GNUNET_OK != | 821 | if (GNUNET_OK != |
791 | ns->store_records (ns->cls, | 822 | ns->store_records (ns->cls, |
792 | &zone, | 823 | &req->zone->key, |
793 | req->label, | 824 | req->label, |
794 | rd_count, | 825 | rd_count, |
795 | rd)) | 826 | rd)) |
@@ -915,6 +946,7 @@ static void | |||
915 | do_shutdown (void *cls) | 946 | do_shutdown (void *cls) |
916 | { | 947 | { |
917 | struct Request *req; | 948 | struct Request *req; |
949 | struct Zone *zone; | ||
918 | 950 | ||
919 | (void) cls; | 951 | (void) cls; |
920 | if (NULL != id) | 952 | if (NULL != id) |
@@ -952,6 +984,14 @@ do_shutdown (void *cls) | |||
952 | GNUNET_CONTAINER_heap_destroy (req_heap); | 984 | GNUNET_CONTAINER_heap_destroy (req_heap); |
953 | req_heap = NULL; | 985 | req_heap = NULL; |
954 | } | 986 | } |
987 | while (NULL != (zone = zone_head)) | ||
988 | { | ||
989 | GNUNET_CONTAINER_DLL_remove (zone_head, | ||
990 | zone_tail, | ||
991 | zone); | ||
992 | GNUNET_free (zone->domain); | ||
993 | GNUNET_free (zone); | ||
994 | } | ||
955 | } | 995 | } |
956 | 996 | ||
957 | 997 | ||
@@ -974,8 +1014,8 @@ import_records (void *cls, | |||
974 | struct Request *req = cls; | 1014 | struct Request *req = cls; |
975 | 1015 | ||
976 | GNUNET_break (0 == memcmp (private_key, | 1016 | GNUNET_break (0 == memcmp (private_key, |
977 | &zone, | 1017 | &req->zone->key, |
978 | sizeof (zone))); | 1018 | sizeof (*private_key))); |
979 | GNUNET_break (0 == strcasecmp (label, | 1019 | GNUNET_break (0 == strcasecmp (label, |
980 | req->label)); | 1020 | req->label)); |
981 | for (unsigned int i=0;i<rd_count;i++) | 1021 | for (unsigned int i=0;i<rd_count;i++) |
@@ -1006,6 +1046,7 @@ queue (const char *hostname) | |||
1006 | char *raw; | 1046 | char *raw; |
1007 | size_t raw_size; | 1047 | size_t raw_size; |
1008 | const char *dot; | 1048 | const char *dot; |
1049 | struct Zone *zone; | ||
1009 | 1050 | ||
1010 | if (GNUNET_OK != | 1051 | if (GNUNET_OK != |
1011 | GNUNET_DNSPARSER_check_name (hostname)) | 1052 | GNUNET_DNSPARSER_check_name (hostname)) |
@@ -1016,12 +1057,8 @@ queue (const char *hostname) | |||
1016 | rejects++; | 1057 | rejects++; |
1017 | return; | 1058 | return; |
1018 | } | 1059 | } |
1019 | /* TODO: may later support importing zones that | 1060 | dot = strchr (hostname, |
1020 | are not TLD, for this we mostly need to change | 1061 | (unsigned char) '.'); |
1021 | the logic here to remove the zone's suffix | ||
1022 | instead of just ".tld" */ | ||
1023 | dot = strrchr (hostname, | ||
1024 | (unsigned char) '.'); | ||
1025 | if (NULL == dot) | 1062 | if (NULL == dot) |
1026 | { | 1063 | { |
1027 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 1064 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
@@ -1030,6 +1067,21 @@ queue (const char *hostname) | |||
1030 | rejects++; | 1067 | rejects++; |
1031 | return; | 1068 | return; |
1032 | } | 1069 | } |
1070 | for (zone = zone_head; NULL != zone; zone = zone->next) | ||
1071 | if ( (0 == strncmp (zone->domain, | ||
1072 | hostname, | ||
1073 | dot - hostname)) && | ||
1074 | (strlen (zone->domain) == dot - hostname) ) | ||
1075 | break; | ||
1076 | if (NULL == zone) | ||
1077 | { | ||
1078 | rejects++; | ||
1079 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1080 | "Domain name `%.*s' not in ego list!\n", | ||
1081 | (int) (dot - hostname), | ||
1082 | hostname); | ||
1083 | return; | ||
1084 | } | ||
1033 | q.name = (char *) hostname; | 1085 | q.name = (char *) hostname; |
1034 | q.type = GNUNET_DNSPARSER_TYPE_NS; | 1086 | q.type = GNUNET_DNSPARSER_TYPE_NS; |
1035 | q.dns_traffic_class = GNUNET_TUN_DNS_CLASS_INTERNET; | 1087 | q.dns_traffic_class = GNUNET_TUN_DNS_CLASS_INTERNET; |
@@ -1056,27 +1108,16 @@ queue (const char *hostname) | |||
1056 | } | 1108 | } |
1057 | 1109 | ||
1058 | req = GNUNET_new (struct Request); | 1110 | req = GNUNET_new (struct Request); |
1111 | req->zone = zone; | ||
1059 | req->hostname = GNUNET_strdup (hostname); | 1112 | req->hostname = GNUNET_strdup (hostname); |
1060 | req->raw = raw; | 1113 | req->raw = raw; |
1061 | req->raw_len = raw_size; | 1114 | req->raw_len = raw_size; |
1062 | req->id = p.id; | 1115 | req->id = p.id; |
1063 | req->label = GNUNET_strndup (hostname, | 1116 | req->label = GNUNET_strndup (hostname, |
1064 | dot - hostname); | 1117 | dot - hostname); |
1065 | if (NULL != strchr (req->label, | ||
1066 | (unsigned char) '.')) | ||
1067 | { | ||
1068 | GNUNET_free (req->hostname); | ||
1069 | GNUNET_free (req->label); | ||
1070 | GNUNET_free (req); | ||
1071 | rejects++; | ||
1072 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1073 | "Label contained a `.', invalid hostname `%s'\n", | ||
1074 | hostname); | ||
1075 | return; | ||
1076 | } | ||
1077 | if (GNUNET_OK != | 1118 | if (GNUNET_OK != |
1078 | ns->lookup_records (ns->cls, | 1119 | ns->lookup_records (ns->cls, |
1079 | &zone, | 1120 | &req->zone->key, |
1080 | req->label, | 1121 | req->label, |
1081 | &import_records, | 1122 | &import_records, |
1082 | req)) | 1123 | req)) |
@@ -1188,9 +1229,11 @@ identity_cb (void *cls, | |||
1188 | (void) ctx; | 1229 | (void) ctx; |
1189 | if (NULL == ego) | 1230 | if (NULL == ego) |
1190 | { | 1231 | { |
1191 | if (zone_found) | 1232 | if (NULL != zone_head) |
1233 | { | ||
1192 | t = GNUNET_SCHEDULER_add_now (&process_stdin, | 1234 | t = GNUNET_SCHEDULER_add_now (&process_stdin, |
1193 | NULL); | 1235 | NULL); |
1236 | } | ||
1194 | else | 1237 | else |
1195 | { | 1238 | { |
1196 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 1239 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
@@ -1199,12 +1242,16 @@ identity_cb (void *cls, | |||
1199 | return; | 1242 | return; |
1200 | } | 1243 | } |
1201 | } | 1244 | } |
1202 | if ( (NULL != name) && | 1245 | if (NULL != name) |
1203 | (0 == strcasecmp (name, | ||
1204 | zone_name)) ) | ||
1205 | { | 1246 | { |
1206 | zone_found = GNUNET_YES; | 1247 | struct Zone *zone; |
1207 | zone = *GNUNET_IDENTITY_ego_get_private_key (ego); | 1248 | |
1249 | zone = GNUNET_new (struct Zone); | ||
1250 | zone->key = *GNUNET_IDENTITY_ego_get_private_key (ego); | ||
1251 | zone->domain = GNUNET_strdup (name); | ||
1252 | GNUNET_CONTAINER_DLL_insert (zone_head, | ||
1253 | zone_tail, | ||
1254 | zone); | ||
1208 | } | 1255 | } |
1209 | } | 1256 | } |
1210 | 1257 | ||
@@ -1282,12 +1329,6 @@ main (int argc, | |||
1282 | "IP", | 1329 | "IP", |
1283 | "which DNS server should be used", | 1330 | "which DNS server should be used", |
1284 | &dns_server)), | 1331 | &dns_server)), |
1285 | GNUNET_GETOPT_option_mandatory | ||
1286 | (GNUNET_GETOPT_option_string ('i', | ||
1287 | "identity", | ||
1288 | "ZONENAME", | ||
1289 | "which GNS zone should we import data into", | ||
1290 | &zone_name)), | ||
1291 | GNUNET_GETOPT_OPTION_END | 1332 | GNUNET_GETOPT_OPTION_END |
1292 | }; | 1333 | }; |
1293 | 1334 | ||