aboutsummaryrefslogtreecommitdiff
path: root/src/gns/gnunet-service-gns_resolver.h
blob: 44c10fc5203571b8f083fb3f97fb8cf28ae5529c (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
#ifndef GNS_RESOLVER_H
#define GNS_RESOLVER_H

#include "gns.h"
#include "gnunet_dht_service.h"

#define DHT_OPERATION_TIMEOUT  GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 60)
#define GNUNET_GNS_DEFAULT_LOOKUP_TIMEOUT \
  GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10)
#define DHT_LOOKUP_TIMEOUT DHT_OPERATION_TIMEOUT
#define DHT_GNS_REPLICATION_LEVEL 5

#define GNUNET_GNS_MAX_PARALLEL_LOOKUPS 500

/*
 * DLL to hold the authority chain
 * we had to pass in the resolution process
 */
struct AuthorityChain
{
  struct AuthorityChain *prev;

  struct AuthorityChain *next;
  
  /* the zone hash of the authority */
  struct GNUNET_CRYPTO_ShortHashCode zone;

  /* (local) name of the authority */
  char name[MAX_DNS_LABEL_LENGTH];

  /* was the ns entry fresh */
  int fresh;
};

/* handle to a resolution process */
struct ResolverHandle;

/**
 * continuation called when cleanup of resolver finishes
 */
typedef void (*ResolverCleanupContinuation) (void);

/**
 * processor for a record lookup result
 *
 * @param cls the closure
 * @param rd_count number of results
 * @param rd result data
 */
typedef void (*RecordLookupProcessor) (void *cls,
                                  uint32_t rd_count,
                                  const struct GNUNET_NAMESTORE_RecordData *rd);


/**
 * processor for a shorten result
 *
 * @param cls the closure
 * @param name shortened name
 */
typedef void (*ShortenResultProcessor) (void *cls, const char* name);


/**
 * processor for an authority result
 *
 * @param cls the closure
 * @param name name
 */
typedef void (*GetAuthorityResultProcessor) (void *cls, const char* name);

/**
 * processor for a resolution result
 *
 * @param cls the closure
 * @param rh the resolution handle
 * @param rd_count number of results
 * @param rd result data
 */
typedef void (*ResolutionResultProcessor) (void *cls,
                                  struct ResolverHandle *rh,
                                  uint32_t rd_count,
                                  const struct GNUNET_NAMESTORE_RecordData *rd);


/**
 * Resolution status indicator
 * RSL_RECORD_EXISTS: the name to lookup exists
 * RSL_RECORD_EXPIRED: the name in the record expired
 * RSL_TIMED_OUT: resolution timed out
 */
enum ResolutionStatus
{
  RSL_RECORD_EXISTS = 1,
  RSL_RECORD_EXPIRED = 2,
  RSL_TIMED_OUT = 4
};

/**
 * Handle to a currenty pending resolution
 * a ResolverHandle is passed to, for example
 * resolve_record_ns to resolve a record in the namestore.
 * On result (positive or negative) the ResolutionResultProcessor
 * is called.
 * If a timeout is set timeout_cont will be called.
 * If no timeout is set (ie timeout forever) then background resolutions
 * might be triggered.
 */
struct ResolverHandle
{
  /* The name to resolve */
  char name[MAX_DNS_NAME_LENGTH];

  /* has this query been answered? how many matches */
  int answered;

  /* the authoritative zone to query */
  struct GNUNET_CRYPTO_ShortHashCode authority;

  /* the name of the authoritative zone to query */
  char authority_name[MAX_DNS_LABEL_LENGTH];

  /* a handle for dht lookups. should be NULL if no lookups are in progress */
  struct GNUNET_DHT_GetHandle *get_handle;

  /* timeout set for this lookup task */
  struct GNUNET_TIME_Relative timeout;

  /* timeout task for the lookup */
  GNUNET_SCHEDULER_TaskIdentifier timeout_task;

  /* continuation to call on timeout */
  GNUNET_SCHEDULER_Task timeout_cont;

  /* closure for timeout cont */
  void* timeout_cont_cls;

  /* called when resolution phase finishes */
  ResolutionResultProcessor proc;
  
  /* closure passed to proc */
  void* proc_cls;

  /* DLL to store the authority chain */
  struct AuthorityChain *authority_chain_head;

  /* DLL to store the authority chain */
  struct AuthorityChain *authority_chain_tail;

  /* status of the resolution result */
  enum ResolutionStatus status;

  /**
   * private key of an/our authoritative zone
   * can be NULL but automatical PKEY import will not work
   */
  struct GNUNET_CRYPTO_RsaPrivateKey *priv_key;

  /**
   * the heap node associated with this lookup, null if timeout is set
   * used for DHT background lookups.
   */
  struct GNUNET_CONTAINER_HeapNode *dht_heap_node;

  /**
   * Id for resolution process
   */
  unsigned long long id;

};


/**
 * Handle to a record lookup
 */
struct RecordLookupHandle
{
  /* the record type to look up */
  enum GNUNET_GNS_RecordType record_type;

  /* the name to look up */
  char name[MAX_DNS_NAME_LENGTH];

  /* Method to call on record resolution result */
  RecordLookupProcessor proc;

  /* closure to pass to proc */
  void* proc_cls;

};


/**
 * Handle to a shorten context
 */
struct NameShortenHandle
{
  /* Method to call on shorten result */
  ShortenResultProcessor proc;

  /* closure to pass to proc */
  void* proc_cls;
};

/**
 * Handle to a get authority context
 */
struct GetNameAuthorityHandle
{
  /* the name to look up authority for */
  char name[MAX_DNS_NAME_LENGTH];
  
  /* Method to call on result */
  GetAuthorityResultProcessor proc;

  /* closure to pass to proc */
  void* proc_cls;
};

/**
 * Handle to a pseu lookup
 */
struct GetPseuAuthorityHandle
{
  /* the name given from delegation */
  char name[MAX_DNS_LABEL_LENGTH];

  /* name to store the pseu under */
  char new_name[MAX_DNS_LABEL_LENGTH];
  
  /* the zone of discovered authority */
  struct GNUNET_CRYPTO_ShortHashCode new_zone;

  /* the zone of our authority */
  struct GNUNET_CRYPTO_ShortHashCode zone;

  /* the private key of the zone to store the pseu in */
  struct GNUNET_CRYPTO_RsaPrivateKey *key;

  /* a handle for dht lookups. should be NULL if no lookups are in progress */
  struct GNUNET_DHT_GetHandle *get_handle;

  /* timeout task for lookup */
  GNUNET_SCHEDULER_TaskIdentifier timeout;
};

/**
 * Initialize the resolver
 * MUST be called before other gns_resolver_* methods
 *
 * @param nh handle to the namestore
 * @param dh handle to the dht
 * @param lz the local zone
 * @param max_bg_queries maximum amount of background queries
 * @param ignore_pending ignore records that still require user confirmation
 *        on lookup
 * @returns GNUNET_OK on success
 */
int
gns_resolver_init(struct GNUNET_NAMESTORE_Handle *nh,
                  struct GNUNET_DHT_Handle *dh,
                  struct GNUNET_CRYPTO_ShortHashCode lz,
                  unsigned long long max_bg_queries,
                  int ignore_pending);

/**
 * Cleanup resolver: Terminate pending lookups
 * 
 * @param cont continuation to call when finished
 */
void
gns_resolver_cleanup(ResolverCleanupContinuation cont);

/**
 * Lookup of a record in a specific zone
 * calls RecordLookupProcessor on result or timeout
 *
 * @param zone the root zone
 * @param record_type the record type to look up
 * @param name the name to look up
 * @param key optional private key for authority caching
 * @param timeout timeout for the resolution
 * @param proc the processor to call
 * @param cls the closure to pass to proc
 */
void
gns_resolver_lookup_record(struct GNUNET_CRYPTO_ShortHashCode zone,
                           uint32_t record_type,
                           const char* name,
                           struct GNUNET_CRYPTO_RsaPrivateKey *key,
                           struct GNUNET_TIME_Relative timeout,
                           RecordLookupProcessor proc,
                           void* cls);

/**
 * Shortens a name if possible. If the shortening fails
 * name will be returned as shortened string. Else
 * a shorter version of the name will be returned.
 * There is no guarantee that the shortened name will
 * actually be canonical/short etc.
 *
 * @param zone the zone to perform the operation in
 * @param name name to shorten
 * @param key optional private key for background lookups and PSEU import
 * @param proc the processor to call on shorten result
 * @param proc_cls the closure to pass to proc
 */
void
gns_resolver_shorten_name(struct GNUNET_CRYPTO_ShortHashCode zone,
                          const char* name,
                          struct GNUNET_CRYPTO_RsaPrivateKey *key,
                          ShortenResultProcessor proc,
                          void* proc_cls);

/**
 * Tries to resolve the authority for name
 * in our namestore
 *
 * @param zone the root zone to look up for
 * @param name the name to lookup up
 * @param proc the processor to call when finished
 * @param proc_cls the closure to pass to the processor
 */
void
gns_resolver_get_authority(struct GNUNET_CRYPTO_ShortHashCode zone,
                           const char* name,
                           GetAuthorityResultProcessor proc,
                           void* proc_cls);

/**
 * Generic function to check for TLDs
 *
 * @param name the name to check
 * @param tld the tld to check
 * @return GNUNET_YES or GNUNET_NO
 */
int
is_tld(const char* name, const char* tld);

/**
 * Checks for gnunet/zkey
 */
#define is_gnunet_tld(name) is_tld(name, GNUNET_GNS_TLD)
#define is_zkey_tld(name) is_tld(name, GNUNET_GNS_TLD_ZKEY)


#endif