⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 search.c

📁 GNUnet是一个安全的点对点网络框架
💻 C
📖 第 1 页 / 共 2 页
字号:
/*     This file is part of GNUnet.     (C) 2001, 2002, 2003, 2004, 2005, 2006, 2008 Christian Grothoff (and other contributing authors)     GNUnet is free software; you can redistribute it and/or modify     it under the terms of the GNU General Public License as published     by the Free Software Foundation; either version 2, or (at your     option) any later version.     GNUnet is distributed in the hope that it will be useful, but     WITHOUT ANY WARRANTY; without even the implied warranty of     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU     General Public License for more details.     You should have received a copy of the GNU General Public License     along with GNUnet; see the file COPYING.  If not, write to the     Free Software Foundation, Inc., 59 Temple Place - Suite 330,     Boston, MA 02111-1307, USA.*//** * @file applications/fs/ecrs/search.c * @brief Helper functions for searching. * @author Christian Grothoff */#include "platform.h"#include "gnunet_protocols.h"#include "gnunet_fs_lib.h"#include "gnunet_ecrs_lib.h"#include "ecrs_core.h"#include "ecrs.h"#define DEBUG_SEARCH GNUNET_NO/** * Context for an individual search.  Followed *  by keyCount keys of type GNUNET_HashCode. */struct PendingSearch{  struct PendingSearch *next;  struct GNUNET_ECRS_SearchContext *context;  /**   * The key (for decryption)   */  GNUNET_HashCode decryptKey;  unsigned int keyCount;  /**   * What type of query is it?   */  unsigned int type;};/** * Context for search operation. */struct GNUNET_ECRS_SearchContext{  /**   * Time when the cron-job was first started.   */  GNUNET_CronTime start;  /**   * What is the global timeout?   */  GNUNET_CronTime timeout;  /**   * Search context   */  struct GNUNET_FS_SearchContext *sctx;  /**   * Active searches.   */  struct PendingSearch *queries;  GNUNET_ECRS_SearchResultProcessor spcb;  void *spcbClosure;  struct GNUNET_GE_Context *ectx;  struct GNUNET_GC_Configuration *cfg;  int aborted;  int my_sctx;  unsigned int anonymityLevel;};static intreceive_response_callback (const GNUNET_HashCode * key,                           const GNUNET_DatastoreValue * value,                           void *cls, unsigned long long uid);/** * Add a query to the SQC. */static voidadd_search (unsigned int type,            unsigned int keyCount,            const GNUNET_HashCode * keys,            const GNUNET_HashCode * dkey,            struct GNUNET_ECRS_SearchContext *sqc){  struct PendingSearch *ps;  ps =    GNUNET_malloc (sizeof (struct PendingSearch) +                   sizeof (GNUNET_HashCode) * keyCount);  ps->type = type;  ps->keyCount = keyCount;  memcpy (&ps[1], keys, sizeof (GNUNET_HashCode) * keyCount);  ps->decryptKey = *dkey;  ps->context = sqc;  ps->next = sqc->queries;  sqc->queries = ps;  GNUNET_FS_start_search (sqc->sctx,                          NULL,                          type,                          keyCount,                          keys,                          sqc->anonymityLevel,                          &receive_response_callback, ps);}/** * Add the query that corresponds to the given URI * to the SQC. */static voidadd_search_for_uri (const struct GNUNET_ECRS_URI *uri,                    struct GNUNET_ECRS_SearchContext *sqc){  struct GNUNET_GE_Context *ectx = sqc->ectx;  switch (uri->type)    {    case chk:      GNUNET_GE_LOG (ectx,                     GNUNET_GE_ERROR | GNUNET_GE_BULK | GNUNET_GE_USER,                     _("CHK URI not allowed for search.\n"));      break;    case sks:      {        GNUNET_HashCode keys[2];        GNUNET_HashCode hk;     /* hk = GNUNET_hash(identifier) */        GNUNET_HashCode hk2;    /* hk2 = GNUNET_hash(hk) */        GNUNET_hash (uri->data.sks.identifier,                     strlen (uri->data.sks.identifier), &hk);        GNUNET_hash (&hk, sizeof (GNUNET_HashCode), &hk2);        /* compute routing key keys[0] = H(key) ^ namespace */        GNUNET_hash_xor (&hk2, &uri->data.sks.namespace, &keys[0]);        keys[1] = uri->data.sks.namespace;        add_search (GNUNET_ECRS_BLOCKTYPE_SIGNED, 2, &keys[0], &hk, sqc);        break;      }    case ksk:      {        GNUNET_HashCode hc;        GNUNET_HashCode query;        struct GNUNET_RSA_PrivateKey *pk;        GNUNET_RSA_PublicKey pub;        int i;        const char *keyword;#if DEBUG_SEARCH        GNUNET_GE_LOG (ectx,                       GNUNET_GE_DEBUG | GNUNET_GE_REQUEST | GNUNET_GE_USER,                       "Computing queries (this may take a while).\n");#endif        for (i = 0; i < uri->data.ksk.keywordCount; i++)          {            keyword = uri->data.ksk.keywords[i];            /* first character of the keyword is               "+" or " " to indicate mandatory or               not -- ignore for hashing! */            GNUNET_hash (&keyword[1], strlen (&keyword[1]), &hc);            pk = GNUNET_RSA_create_key_from_hash (&hc);            GNUNET_RSA_get_public_key (pk, &pub);            GNUNET_hash (&pub, sizeof (GNUNET_RSA_PublicKey), &query);            add_search (GNUNET_ECRS_BLOCKTYPE_ANY,      /* GNUNET_ECRS_BLOCKTYPE_KEYWORD, GNUNET_ECRS_BLOCKTYPE_NAMESPACE or GNUNET_ECRS_BLOCKTYPE_KEYWORD_FOR_NAMESPACE ok */                        1, &query, &hc, sqc);            GNUNET_RSA_free_key (pk);          }#if DEBUG_SEARCH        GNUNET_GE_LOG (ectx,                       GNUNET_GE_DEBUG | GNUNET_GE_REQUEST | GNUNET_GE_USER,                       "Queries ready.\n");#endif        break;      }    case loc:      GNUNET_GE_LOG (ectx,                     GNUNET_GE_ERROR | GNUNET_GE_BULK | GNUNET_GE_USER,                     _("LOC URI not allowed for search.\n"));      break;    default:      GNUNET_GE_BREAK (ectx, 0);      /* unknown URI type */      break;    }}/** * We found an GNUNET_EC_SBlock.  Decode the meta-data and call * the callback of the SQC with the root-URI for the namespace, * together with the namespace advertisement.  Also, if this is * a result with updates, automatically start the search for * updates. */static intprocess_sblock_result (const GNUNET_EC_SBlock * sb,                       const GNUNET_HashCode * key,                       unsigned int size,                       struct GNUNET_ECRS_SearchContext *sqc){  static GNUNET_HashCode allZeros;  struct GNUNET_GE_Context *ectx = sqc->ectx;  GNUNET_ECRS_FileInfo fi;  URI updateURI;  int ret;  const char *id;  const char *uris;  unsigned int len;  unsigned int off;  int isRoot;  len = size - sizeof (GNUNET_EC_SBlock);  off = GNUNET_string_buffer_tokenize ((const char *) &sb[1],                                       len, 2, &id, &uris);  if (off == 0)    {      GNUNET_GE_BREAK_OP (ectx, 0);     /* sblock malformed */      return GNUNET_SYSERR;    }  fi.meta = GNUNET_meta_data_deserialize (ectx, &id[off], len - off);  if (fi.meta == NULL)    {      GNUNET_GE_BREAK_OP (ectx, 0);     /* sblock malformed */      return GNUNET_SYSERR;    }  isRoot = 0 == memcmp (&sb->identifier, &allZeros, sizeof (GNUNET_HashCode));  fi.uri = GNUNET_ECRS_string_to_uri (ectx, uris);  if ((isRoot) && (fi.uri == NULL))    {      fi.uri = GNUNET_malloc (sizeof (URI));      fi.uri->type = sks;      GNUNET_hash (&sb->subspace,                   sizeof (GNUNET_RSA_PublicKey),                   &fi.uri->data.sks.namespace);      fi.uri->data.sks.identifier = GNUNET_strdup (id);    }  if (fi.uri == NULL)    {      GNUNET_GE_BREAK_OP (ectx, 0);     /* sblock malformed */      GNUNET_meta_data_destroy (fi.meta);      return GNUNET_SYSERR;    }  if (sqc->spcb != NULL)    {      ret = sqc->spcb (&fi, key, isRoot, sqc->spcbClosure);      if (ret == GNUNET_SYSERR)        sqc->aborted = GNUNET_YES;    }  else    ret = GNUNET_OK;  if ((strlen (id) > 0) && (strlen (uris) > 0))    {      updateURI.type = sks;      GNUNET_hash (&sb->subspace,                   sizeof (GNUNET_RSA_PublicKey),                   &updateURI.data.sks.namespace);      updateURI.data.sks.identifier = GNUNET_strdup (id);      add_search_for_uri (&updateURI, sqc);      GNUNET_free (updateURI.data.sks.identifier);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -