Exemple #1
0
/**
 * Write a file named index/stable that contains the size of
 * repoFile1 when the repository is shut down.
 */
static int
r_store_write_stable_point(struct ccnr_handle *h)
{
    struct ccn_charbuf *path = NULL;
    struct ccn_charbuf *cb = NULL;
    int fd;
    
    path = ccn_charbuf_create();
    cb = ccn_charbuf_create();
    ccn_charbuf_putf(path, "%s/index/stable", h->directory);
    unlink(ccn_charbuf_as_string(path)); /* Should not exist, but just in case. */
    fd = open(ccn_charbuf_as_string(path),
              O_CREAT | O_EXCL | O_WRONLY | O_TRUNC, 0666);
    if (fd == -1) {
        ccnr_msg(h, "cannot write stable mark %s: %s",
                 ccn_charbuf_as_string(path), strerror(errno));
        unlink(ccn_charbuf_as_string(path));
    }
    else {
        ccn_charbuf_putf(cb, "%ju", (uintmax_t)(h->stable));
        write(fd, cb->buf, cb->length);
        close(fd);
        if (CCNSHOULDLOG(h, dfsdf, CCNL_INFO))
            ccnr_msg(h, "Index marked stable - %s", ccn_charbuf_as_string(cb));
    }
    ccn_charbuf_destroy(&path);
    ccn_charbuf_destroy(&cb);
    return(0);
}
Exemple #2
0
char * 
get_orig_router_from_info_content_name(struct ccn_charbuf * content_name)
{
	int start,end;

	start=0;

	struct ccn_indexbuf *comps=ccn_indexbuf_create();
	ccn_name_split (content_name, comps);

	end=check_for_name_component_in_name(content_name,comps,"nlsr");


	struct ccn_charbuf *temp=ccn_charbuf_create();
	ccn_name_init(temp);	
	ccn_name_append_components( temp,	content_name->buf,
								comps->buf[start], 
								comps->buf[end]);

	struct ccn_charbuf *temp1=ccn_charbuf_create();
	ccn_uri_append(temp1, temp->buf, temp->length, 0);

	char *orig_router=(char *)calloc(strlen(ccn_charbuf_as_string(temp1))+1,
																sizeof(char));
	memcpy(orig_router,ccn_charbuf_as_string(temp1),
										strlen(ccn_charbuf_as_string(temp1)));
	orig_router[strlen(orig_router)]='\0';
	
	ccn_charbuf_destroy(&temp);
	ccn_charbuf_destroy(&temp1);
	ccn_indexbuf_destroy(&comps);
	return orig_router;
	

}
Exemple #3
0
char * 
get_orig_router_from_lsa_name(struct ccn_charbuf * content_name)
{
	int start=0;

	size_t comp_size;
	const unsigned char *second_last_comp;
	char *second_comp_type;
	char *sep=".";
	char *rem;

	struct ccn_indexbuf *components=ccn_indexbuf_create();
	struct ccn_charbuf *name=ccn_charbuf_create();
	ccn_name_from_uri(name,nlsr->slice_prefix);
	ccn_name_split (name, components);
	start=components->n-2;
	ccn_charbuf_destroy(&name);
	ccn_indexbuf_destroy(&components);

	struct ccn_indexbuf *comps=ccn_indexbuf_create();
	ccn_name_split (content_name, comps);
	ccn_name_comp_get( content_name->buf, comps, 
					  comps->n-1-2, &second_last_comp, &comp_size);

	second_comp_type=strtok_r((char *)second_last_comp, sep, &rem);
	if ( strcmp( second_comp_type, "lsId" ) == 0 ){
		ccn_name_chop(content_name,comps,-3);
	}
	else{
		ccn_name_chop(content_name,comps,-2);
	}
	

	struct ccn_charbuf *temp=ccn_charbuf_create();
	ccn_name_init(temp);	
	ccn_name_append_components( temp,	content_name->buf,
								comps->buf[start+1], 
								comps->buf[comps->n - 1]);

	struct ccn_charbuf *temp1=ccn_charbuf_create();
	ccn_uri_append(temp1, temp->buf, temp->length, 0);

	char *orig_router=(char *)calloc(strlen(ccn_charbuf_as_string(temp1))+1,
																sizeof(char));
	memcpy(orig_router,ccn_charbuf_as_string(temp1),
										strlen(ccn_charbuf_as_string(temp1)));
	orig_router[strlen(orig_router)]='\0';
	
	ccn_charbuf_destroy(&temp);
	ccn_charbuf_destroy(&temp1);
	ccn_indexbuf_destroy(&comps);
	return orig_router;
	

}
Exemple #4
0
/**
 * Basic tests of ccn_btree_io_from_directory() and its methods.
 *
 * Assumes TEST_DIRECTORY has been set.
 */
static int
test_btree_io(void)
{
    int res;
    struct ccn_btree_node nodespace = {0};
    struct ccn_btree_node *node = &nodespace;
    struct ccn_btree_io *io = NULL;

    /* Open it up. */
    io = ccn_btree_io_from_directory(getenv("TEST_DIRECTORY"), NULL);
    CHKPTR(io);
    node->buf = ccn_charbuf_create();
    CHKPTR(node->buf);
    node->nodeid = 12345;
    res = io->btopen(io, node);
    CHKSYS(res);
    FAILIF(node->iodata == NULL);
    ccn_charbuf_putf(node->buf, "smoke");
    res = io->btwrite(io, node);
    CHKSYS(res);
    node->buf->length = 0;
    ccn_charbuf_putf(node->buf, "garbage");
    res = io->btread(io, node, 500000);
    CHKSYS(res);
    FAILIF(node->buf->length != 5);
    FAILIF(node->buf->limit > 10000);
    node->clean = 5;
    ccn_charbuf_putf(node->buf, "r");
    res = io->btwrite(io, node);
    CHKSYS(res);
    node->buf->length--;
    ccn_charbuf_putf(node->buf, "d");
    res = io->btread(io, node, 1000);
    CHKSYS(res);
    FAILIF(0 != strcmp("smoker", ccn_charbuf_as_string(node->buf)));
    node->buf->length--;
    res = io->btwrite(io, node);
    CHKSYS(res);
    node->buf->length = 0;
    ccn_charbuf_putf(node->buf, "garbage");
    node->clean = 0;
    res = io->btread(io, node, 1000);
    CHKSYS(res);
    res = io->btclose(io, node);
    CHKSYS(res);
    FAILIF(node->iodata != NULL);
    FAILIF(0 != strcmp("smoke", ccn_charbuf_as_string(node->buf)));
    res = io->btdestroy(&io);
    CHKSYS(res);
    ccn_charbuf_destroy(&node->buf);
    return(res);
}
Exemple #5
0
/**
 *  Produce ccnr debug output.
 *  Output is produced via h->logger under the control of h->debug;
 *  prepends decimal timestamp and process identification.
 *  Caller should not supply newlines.
 *  @param      h  the ccnr handle
 *  @param      fmt  printf-like format string
 */
void
ccnr_msg(struct ccnr_handle *h, const char *fmt, ...)
{
    struct timeval t;
    va_list ap;
    struct ccn_charbuf *b;
    int res;
    if (h == NULL || h->debug == 0 || h->logger == 0)
        return;
    b = ccn_charbuf_create();
    if (b == NULL)
        return;
    gettimeofday(&t, NULL);
    if ((h->debug >= CCNL_FINE) &&
        ((h->logbreak-- < 0 && t.tv_sec != h->logtime) ||
          t.tv_sec >= h->logtime + 30)) {
        ccn_charbuf_putf(b, "%ld.000000 ccnr[%d]: %s ____________________ %s",
                         (long)t.tv_sec, h->logpid, h->portstr ? h->portstr : "", ctime(&t.tv_sec));
        h->logtime = t.tv_sec;
        h->logbreak = 30;
    }
    ccn_charbuf_putf(b, "%ld.%06u ccnr[%d]: %s\n",
        (long)t.tv_sec, (unsigned)t.tv_usec, h->logpid, fmt);
    va_start(ap, fmt);
    /* b should already have null termination, but use call for cleanliness */
    res = (*h->logger)(h->loggerdata, ccn_charbuf_as_string(b), ap);
    va_end(ap);
    ccn_charbuf_destroy(&b);
    /* if there's no one to hear, don't make a sound */
    if (res < 0)
        h->debug = 0;
}
Exemple #6
0
int
sync_cb(struct ccns_handle *h,
        struct ccn_charbuf *lhash,
        struct ccn_charbuf *rhash,
        struct ccn_charbuf *name)
{
    char *hexL;
    char *hexR;
    struct ccn_charbuf *uri = ccn_charbuf_create();
    ccn_uri_append(uri, name->buf, name->length, 1);
    if (lhash == NULL || lhash->length == 0) {
        hexL = strdup("none");
    } else
        hexL = hex_string(lhash->buf, lhash->length);
    if (rhash == NULL || rhash->length == 0) {
        hexR = strdup("none");
    } else
        hexR = hex_string(rhash->buf, rhash->length);
    printf("%s %s %s\n", ccn_charbuf_as_string(uri), hexL, hexR);
    fflush(stdout);
    free(hexL);
    free(hexR);
    ccn_charbuf_destroy(&uri);
    return(0);
}
Exemple #7
0
int
main(int argc, char **argv)
{
    struct ccn *ccn = NULL;
    struct ccn_charbuf *name = NULL;
    int opt;
    int res;
        
    while ((opt = getopt(argc, argv, "h")) != -1) {
        switch (opt) {
            case 'h':
            default:
                usage(argv[0]);
        }
    }
    ccn = ccn_create();
    if (ccn_connect(ccn, NULL) == -1) {
        perror("Could not connect to ccnd");
        exit(1);
    }
    name = ccn_charbuf_create();
    res = ccn_guest_prefix(ccn, name, 500);
    if (res < 0)
        exit(1);
    printf("%s\n", ccn_charbuf_as_string(name));
    exit(0);
}
Exemple #8
0
/**
 * Read the contents of the repository config file
 *
 * Calls r_init_fail and returns NULL in case of error.
 * @returns unparsed content of config file in a newly allocated charbuf
 */
struct ccn_charbuf *
r_init_read_config(struct ccnr_handle *h)
{
    struct ccn_charbuf *path = NULL;
    struct ccn_charbuf *contents = NULL;
    size_t sz = 800;
    ssize_t sres = -1;
    int fd;
    
    h->directory = getenv("CCNR_DIRECTORY");
    if (h->directory == NULL || h->directory[0] == 0)
        h->directory = ".";
    path = ccn_charbuf_create();
    contents = ccn_charbuf_create();
    if (path == NULL || contents == NULL)
        return(NULL);
    ccn_charbuf_putf(path, "%s/config", h->directory);
    fd = open(ccn_charbuf_as_string(path), O_RDONLY);
    if (fd == -1) {
        if (errno == ENOENT)
            sres = 0;
        else
            r_init_fail(h, __LINE__, ccn_charbuf_as_string(path), errno);
    }
    else {
        for (;;) {
            sres = read(fd, ccn_charbuf_reserve(contents, sz), sz);
            if (sres == 0)
                break;
            if (sres < 0) {
                r_init_fail(h, __LINE__, "Read failed reading config", errno);
                break;
            }
            contents->length += sres;
            if (contents->length > 999999) {
                r_init_fail(h, __LINE__, "config file too large", 0);
                sres = -1;
                break;
            }
        }
        close(fd);
    }
    ccn_charbuf_destroy(&path);
    if (sres < 0)
        ccn_charbuf_destroy(&contents);
    return(contents);
}
static void init_cached_keystore() {
    ccn_keystore *keystore = cached_keystore;
    int res;
    if (keystore == NULL) {
	ccn_charbuf *temp = ccn_charbuf_create();
	keystore = ccn_keystore_create();
	ccn_charbuf_putf(temp, "%s/.ccnx/.ccnx_keystore", getenv("HOME"));
	res = ccn_keystore_init(keystore,
				ccn_charbuf_as_string(temp),
				(char *)"Th1s1sn0t8g00dp8ssw0rd.");
	if (res != 0) {
	    printf("Failed to initialize keystore %s\n", ccn_charbuf_as_string(temp));
	    exit(1);
	}
	ccn_charbuf_destroy(&temp);
	cached_keystore = keystore;
    }
}
Exemple #10
0
PUBLIC struct content_entry *
r_store_content_next(struct ccnr_handle *h, struct content_entry *content)
{
    if (content == NULL)
        return(0);
    /* We need to go past the current name, so make sure there is a 0 byte */
    ccn_charbuf_as_string(content->flatname);
    content = r_store_look(h, content->flatname->buf, content->flatname->length + 1);
    return(content);
}
Exemple #11
0
void NdnlpSvc_link2ccn(NdnlpSvc self) {
	NdnlpPkt pkt;
	while (NULL != (pkt = Link_read(self->link))) {
		if (D) printf("===== link2ccn ===== \n");
		if (NdnlpPkt_isData(pkt)) {
			printf("pkt: %s\n", ccn_charbuf_as_string(pkt));
			FILE *dumpfile;
			dumpfile = fopen("dumpfile.txt", "a");
			fprintf(dumpfile, "%s\n", ccn_charbuf_as_string(pkt));
			fclose(dumpfile);
			NdnlpSvc_data(self, NdnlpPkt_asData(pkt));
		}
		else if (NdnlpPkt_isAck(pkt)) {
			NdnlpSvc_ack(self, NdnlpPkt_asAck(pkt));
		}
		else {
			NdnlpPkt_dtor(pkt);
		}
	}
}
Exemple #12
0
/**
 * Read the former size of repoFile1 from index/stable, and remove
 * the latter.
 */
static void
r_store_read_stable_point(struct ccnr_handle *h)
{
    struct ccn_charbuf *path = NULL;
    struct ccn_charbuf *cb = NULL;
    int fd;
    int i;
    ssize_t rres;
    uintmax_t val;
    unsigned char c;
    
    path = ccn_charbuf_create();
    cb = ccn_charbuf_create();
    ccn_charbuf_putf(path, "%s/index/stable", h->directory);
    fd = open(ccn_charbuf_as_string(path), O_RDONLY, 0666);
    if (fd != -1) {
        rres = read(fd, ccn_charbuf_reserve(cb, 80), 80);
        if (rres > 0)
            cb->length = rres;
        close(fd);
        if (CCNSHOULDLOG(h, dfsdf, CCNL_INFO))
            ccnr_msg(h, "Last stable at %s", ccn_charbuf_as_string(cb));
    }
    for (val = 0, i = 0; i < cb->length; i++) {
        c = cb->buf[i];
        if ('0' <= c && c <= '9')
            val = val * 10 + (c - '0');
        else
            break;
    }
    if (i == 0 || i < cb->length) {
        ccnr_msg(h, "Bad stable mark - %s", ccn_charbuf_as_string(cb));
        h->stable = 0;
    }
    else {
        h->stable = val;
        unlink(ccn_charbuf_as_string(path));
    }
    ccn_charbuf_destroy(&path);
    ccn_charbuf_destroy(&cb);
}
Exemple #13
0
static int
merge_files(struct ccnr_handle *h)
{
    int i, last_file;
    int res;
    struct ccn_charbuf *filename = ccn_charbuf_create();
    
    // first parse the file(s) making sure there are no errors
    for (i = 2;; i++) {
        filename->length = 0;
        ccn_charbuf_putf(filename, "repoFile%d", i);
        res = r_init_map_and_process_file(h, filename, 0);
        if (res == 1)
            break;
        if (res < 0) {
            ccnr_msg(h, "Error parsing repository file %s", ccn_charbuf_as_string(filename));
            return (-1);
        }
    }
    last_file = i - 1;
    
    for (i = 2; i <= last_file; i++) {
        filename->length = 0;
        ccn_charbuf_putf(filename, "repoFile%d", i);
        res = r_init_map_and_process_file(h, filename, 1);
        if (res < 0) {
            ccnr_msg(h, "Error in phase 2 incorporating repository file %s", ccn_charbuf_as_string(filename));
            return (-1);
        }
    }
    
    for (i = last_file; i > 1; --i) {
        filename->length = 0;
        ccn_charbuf_putf(filename, "%s/repoFile%d", h->directory, i);
        if (CCNSHOULDLOG(h, LM_128, CCNL_INFO))
            ccnr_msg(h, "unlinking %s", ccn_charbuf_as_string(filename));   
        unlink(ccn_charbuf_as_string(filename));
    }
    ccn_charbuf_destroy(&filename);
    return (0);
}
Exemple #14
0
/**
 * Base loop for the background CCN task
 *
 * This is the main execution loop for the background task responsible for
 * interacting with the CCN network. It is from this point that many of the above methods are
 * called to work the inbound messages from ccnx as well as sending out the data messages.
 *
 * \param data		the task context information setup by the parent sink element thread
 */
static void
ccn_event_thread (void *data)
{
  Gstccnxsink *me = (Gstccnxsink *) data;
  struct ccn_charbuf *filtName;
  struct ccn_charbuf *temp;
  int res = 0;

  GST_DEBUG ("CCNxSink event: *** event thread starting");

  temp = ccn_charbuf_create ();
  filtName = ccn_charbuf_create ();

  /* A closure is what defines what to do when an inbound interest arrives */
  if ((me->ccn_closure = calloc (1, sizeof (struct ccn_closure))) == NULL) {
    GST_ELEMENT_ERROR (me, RESOURCE, READ, (NULL), ("closure alloc failed"));
    return;
  }

  /* We setup the closure to contain the sink element context reference, and also tell it what function to call */
  me->ccn_closure->data = me;
  me->ccn_closure->p = new_interests;
  me->timeouts = 0;
  ccn_charbuf_append (filtName, me->name->buf, me->name->length);

  /* This call will set up a handler for interests we expect to get from clients */

  // hDump(DUMP_ADDR(filtName->buf), DUMP_SIZE(filtName->length));
  ccn_set_interest_filter (me->ccn, filtName, me->ccn_closure);
  GST_DEBUG ("CCNxSink event: interest filter registered\n");

  /* Some debugging information */
  temp->length = 0;
  ccn_uri_append (temp, me->name->buf, me->name->length, TRUE);
  GST_DEBUG ("CCNxSink event: using uri: %s\n", ccn_charbuf_as_string (temp));

  /* Now that the interest is registered, we loop around waiting for something to do */
  /* We pass control to ccnx for a while so it can work with any incoming or outgoing data */
  /* and then we check our fifo queue for work to do. That's about it! */
  /* We check to see if any problems have caused our ccnd connection to fail, and we reconnect */
  while (res >= 0) {
    GST_DEBUG ("CCNxSink event: *** looping");
    res = ccn_run (me->ccn, 50);
    check_fifo (me);
    if (res < 0 && ccn_get_connection_fd (me->ccn) == -1) {
      GST_DEBUG ("CCNxSink event: need to reconnect...");
      /* Try reconnecting, after a bit of delay */
      msleep ((30 + (getpid () % 30)) * 1000);
      res = ccn_connect (me->ccn, ccndHost ());
    }
  }
  GST_DEBUG ("CCNxSink event: *** event thread ending");
}
Exemple #15
0
/**
 * Use standard mkdtemp() to create a subdirectory of the
 * current working directory, and set the TEST_DIRECTORY environment
 * variable with its name.
 */
static int
test_directory_creation(void)
{
    int res;
    struct ccn_charbuf *dirbuf;
    char *temp;
    
    dirbuf = ccn_charbuf_create();
    CHKPTR(dirbuf);
    res = ccn_charbuf_putf(dirbuf, "./%s", "_bt_XXXXXX");
    CHKSYS(res);
    temp = mkdtemp(ccn_charbuf_as_string(dirbuf));
    CHKPTR(temp);
    res = ccn_charbuf_putf(dirbuf, "/%s", "_test");
    CHKSYS(res);
    res = mkdir(ccn_charbuf_as_string(dirbuf), 0777);
    CHKSYS(res);
    printf("Created directory %s\n", ccn_charbuf_as_string(dirbuf));
    setenv("TEST_DIRECTORY", ccn_charbuf_as_string(dirbuf), 1);
    ccn_charbuf_destroy(&dirbuf);
    return(res);
}
Exemple #16
0
static void
collect_faces_html(struct ccnd_handle *h, struct ccn_charbuf *b)
{
    int i;
    struct ccn_charbuf *nodebuf;
    int port;
    
    nodebuf = ccn_charbuf_create();
    ccn_charbuf_putf(b, "<h4>Faces</h4>" NL);
    ccn_charbuf_putf(b, "<ul>");
    for (i = 0; i < h->face_limit; i++) {
        struct face *face = h->faces_by_faceid[i];
        if (face != NULL && (face->flags & CCN_FACE_UNDECIDED) == 0) {
            ccn_charbuf_putf(b, " <li>");
            ccn_charbuf_putf(b, "<b>face:</b> %u <b>flags:</b> 0x%x",
                             face->faceid, face->flags);
            ccn_charbuf_putf(b, " <b>pending:</b> %d",
                             face->pending_interests);
            if (face->recvcount != 0)
                ccn_charbuf_putf(b, " <b>activity:</b> %d",
                                 face->recvcount);
            nodebuf->length = 0;
            port = ccn_charbuf_append_sockaddr(nodebuf, face->addr);
            if (port > 0) {
                const char *node = ccn_charbuf_as_string(nodebuf);
                int chk = CCN_FACE_MCAST | CCN_FACE_UNDECIDED |
                CCN_FACE_NOSEND | CCN_FACE_GG | CCN_FACE_PASSIVE;
                if ((face->flags & chk) == 0)
                    ccn_charbuf_putf(b,
                                     " <b>remote:</b> "
                                     "<a href='http://%s:%s/'>"
                                     "%s:%d</a>",
                                     node, CCN_DEFAULT_UNICAST_PORT,
                                     node, port);
                else if ((face->flags & CCN_FACE_PASSIVE) == 0)
                    ccn_charbuf_putf(b, " <b>remote:</b> %s:%d",
                                     node, port);
                else
                    ccn_charbuf_putf(b, " <b>local:</b> %s:%d",
                                     node, port);
                if (face->sendface != face->faceid &&
                    face->sendface != CCN_NOFACEID)
                    ccn_charbuf_putf(b, " <b>via:</b> %u", face->sendface);
            }
            ccn_charbuf_putf(b, "</li>" NL);
        }
    }
    ccn_charbuf_putf(b, "</ul>");
    ccn_charbuf_destroy(&nodebuf);
}
Exemple #17
0
void NdnlpSvc_msg(NdnlpSvc self, CcnbMsg msg) {
	NdnlpPktA pkts = MsgSlicer_slice(self->msgSlicer, msg);
	for (int i = 0, len = NdnlpPktA_length(pkts); i < len; ++i) {
		NdnlpPkt pkt = NdnlpPktA_get(pkts, i);
		if (NdnlpSvc_RLAPolicy(self, msg, pkt)) {
			DataPkt_setFlags(pkt, DataPkt_getFlags(pkt) | DataPktFlag_RLA);
			SentPkts_insert(self->sentPkts, pkt);
		}
		printf("pkt: %s\n", ccn_charbuf_as_string(pkt));
		Link_write(self->link, pkt);
	}
	NdnlpPktA_dtor(pkts, false);
	CcnbMsg_dtor(msg);
}
Exemple #18
0
PUBLIC int
r_io_open_repo_data_file(struct ccnr_handle *h, const char *name, int output)
{
    struct ccn_charbuf *temp = NULL;
    int fd = -1;
    struct fdholder *fdholder = NULL;

    temp = ccn_charbuf_create();
    ccn_charbuf_putf(temp, "%s/%s", h->directory, name);
    fd = open(ccn_charbuf_as_string(temp), output ? (O_CREAT | O_WRONLY | O_APPEND) : O_RDONLY, 0666);
    if (fd == -1) {
        if (CCNSHOULDLOG(h, sdf, CCNL_FINE))
            ccnr_msg(h, "open(%s): %s", ccn_charbuf_as_string(temp), strerror(errno));
        ccn_charbuf_destroy(&temp);
        return(-1);
    }
    fdholder = r_io_record_fd(h, fd,
                            temp->buf, temp->length,
                            CCNR_FACE_REPODATA | (output ? CCNR_FACE_NORECV : CCNR_FACE_NOSEND));
    if (fdholder == NULL)
        close_fd(&fd);
    else {
        if (!output) {
            /* Use a larger buffer for indexing an existing repo file */
            if (fdholder->inbuf == NULL) {
                fdholder->inbuf = ccn_charbuf_create();
                fdholder->bufoffset = 0;
            }
            if (fdholder->inbuf != NULL)
                ccn_charbuf_reserve(fdholder->inbuf, 256 * 1024);
        }
        if (CCNSHOULDLOG(h, sdf, CCNL_INFO))
            ccnr_msg(h, "opened fd=%d file=%s", fd, ccn_charbuf_as_string(temp));
    }
    ccn_charbuf_destroy(&temp);
    return(fd);
}
Exemple #19
0
void
get_name_part(struct name_prefix *name_part,struct ccn_charbuf * interest_ccnb, 
		struct ccn_indexbuf *interest_comps, int offset)
{
	int lsa_position=0;
	
	struct ccn_indexbuf *components=ccn_indexbuf_create();
	struct ccn_charbuf *name=ccn_charbuf_create();
	ccn_name_from_uri(name,nlsr->slice_prefix);
	ccn_name_split (name, components);
	lsa_position=components->n-2;
	ccn_charbuf_destroy(&name);

	struct ccn_charbuf *temp=ccn_charbuf_create();
	ccn_name_init(temp);	
	ccn_name_append_components( temp,	interest_ccnb->buf,
								interest_comps->buf[lsa_position+1], 
								interest_comps->buf[interest_comps->n - 1]);

	struct ccn_charbuf *temp1=ccn_charbuf_create();
	ccn_uri_append(temp1, temp->buf, temp->length, 0);

	name_part->name=(char *)calloc(strlen(ccn_charbuf_as_string(temp1))+1,
																sizeof(char));
	memcpy(name_part->name,ccn_charbuf_as_string(temp1),
										strlen(ccn_charbuf_as_string(temp1)));
	name_part->name[strlen(ccn_charbuf_as_string(temp1))]='\0';
	name_part->length=strlen(ccn_charbuf_as_string(temp1))+1;

	ccn_charbuf_destroy(&temp1);
	ccn_charbuf_destroy(&temp);
	ccn_indexbuf_destroy(&components);

	if ( nlsr->debugging )
		printf("Name Part: %s \n",name_part->name);
	
}
Exemple #20
0
static void
collect_faces_xml(struct ccnd_handle *h, struct ccn_charbuf *b)
{
    int i;
    int m;
    int port;
    struct ccn_charbuf *nodebuf;
    
    nodebuf = ccn_charbuf_create();
    ccn_charbuf_putf(b, "<faces>");
    for (i = 0; i < h->face_limit; i++) {
        struct face *face = h->faces_by_faceid[i];
        if (face != NULL && (face->flags & CCN_FACE_UNDECIDED) == 0) {
            ccn_charbuf_putf(b, "<face>");
            ccn_charbuf_putf(b,
                             "<faceid>%u</faceid>"
                             "<faceflags>%04x</faceflags>",
                             face->faceid, face->flags);
            ccn_charbuf_putf(b, "<pending>%d</pending>",
                             face->pending_interests);
            ccn_charbuf_putf(b, "<recvcount>%d</recvcount>",
                             face->recvcount);
            nodebuf->length = 0;
            port = ccn_charbuf_append_sockaddr(nodebuf, face->addr);
            if (port > 0) {
                const char *node = ccn_charbuf_as_string(nodebuf);
                ccn_charbuf_putf(b, "<ip>%s:%d</ip>", node, port);
            }
            if (face->sendface != face->faceid &&
                face->sendface != CCN_NOFACEID)
                ccn_charbuf_putf(b, "<via>%u</via>", face->sendface);
            if (face != NULL && (face->flags & CCN_FACE_PASSIVE) == 0) {
                ccn_charbuf_putf(b, "<meters>");
                for (m = 0; m < CCND_FACE_METER_N; m++)
                    collect_meter_xml(h, b, face->meter[m]);
                ccn_charbuf_putf(b, "</meters>");
            }
            ccn_charbuf_putf(b, "</face>" NL);
        }
    }
    ccn_charbuf_putf(b, "</faces>");
    ccn_charbuf_destroy(&nodebuf);
}
Exemple #21
0
/**
 *  Produce a ccnd debug trace entry.
 *  Output is produced by calling ccnd_msg.
 *  @param      h  the ccnd handle
 *  @param      lineno  caller's source line number (usually __LINE__)
 *  @param      msg  a short text tag to identify the entry
 *  @param      face    handle of associated face; may be NULL
 *  @param      ccnb    points to ccnb-encoded Interest or ContentObject
 *  @param      ccnb_size   is in bytes
 */
void
ccnd_debug_ccnb(struct ccnd_handle *h,
                int lineno,
                const char *msg,
                struct face *face,
                const unsigned char *ccnb,
                size_t ccnb_size)
{
    struct ccn_charbuf *c;
    struct ccn_parsed_interest pi;
    const unsigned char *nonce = NULL;
    size_t nonce_size = 0;
    size_t i;
    
    
    if (h != NULL && h->debug == 0)
        return;
    c = ccn_charbuf_create();
    ccn_charbuf_putf(c, "debug.%d %s ", lineno, msg);
    if (face != NULL)
        ccn_charbuf_putf(c, "%u ", face->faceid);
    ccn_uri_append(c, ccnb, ccnb_size, 1);
    ccn_charbuf_putf(c, " (%u bytes)", (unsigned)ccnb_size);
    if (ccn_parse_interest(ccnb, ccnb_size, &pi, NULL) >= 0) {
        const char *p = "";
        ccn_ref_tagged_BLOB(CCN_DTAG_Nonce, ccnb,
                  pi.offset[CCN_PI_B_Nonce],
                  pi.offset[CCN_PI_E_Nonce],
                  &nonce,
                  &nonce_size);
        if (nonce_size > 0) {
            ccn_charbuf_putf(c, " ");
            if (nonce_size == 12)
                p = "CCC-P-F-T-NN";
            for (i = 0; i < nonce_size; i++)
                ccn_charbuf_putf(c, "%s%02X", (*p) && (*p++)=='-' ? "-" : "", nonce[i]);
        }
    }
    ccnd_msg(h, "%s", ccn_charbuf_as_string(c));
    ccn_charbuf_destroy(&c);
}
Exemple #22
0
PUBLIC void
ccnr_debug_content(struct ccnr_handle *h,
                   int lineno,
                   const char *msg,
                   struct fdholder *fdholder,
                   struct content_entry *content)
{
    struct ccn_charbuf *c = ccn_charbuf_create();
    struct ccn_charbuf *flat = content->flatname;
    
    if (c == NULL)
        return;
    ccn_charbuf_putf(c, "debug.%d %s ", lineno, msg);
    if (fdholder != NULL)
        ccn_charbuf_putf(c, "%u ", fdholder->filedesc);
    if (flat != NULL)
        ccn_uri_append_flatname(c, flat->buf, flat->length, 1);
    ccn_charbuf_putf(c, " (%d bytes)", content->size);
    ccnr_msg(h, "%s", ccn_charbuf_as_string(c));
    ccn_charbuf_destroy(&c);
}
Exemple #23
0
// my_response is used to handle a reply
static enum ccn_upcall_res
my_response(struct ccn_closure *selfp,
            enum ccn_upcall_kind kind,
            struct ccn_upcall_info *info) {
    static char *here = "sync_track.my_response";
    enum ccn_upcall_res ret = CCN_UPCALL_RESULT_ERR;
    switch (kind) {
        case CCN_UPCALL_FINAL:
            free(selfp);
            ret = CCN_UPCALL_RESULT_OK;
            break;
        case CCN_UPCALL_CONTENT_UNVERIFIED:
            ret = CCN_UPCALL_RESULT_VERIFY;
            break;
        case CCN_UPCALL_CONTENT_KEYMISSING:
            ret = CCN_UPCALL_RESULT_FETCHKEY;
            break;
        case CCN_UPCALL_INTEREST_TIMED_OUT: {
            struct sync_diff_fetch_data *fd = selfp->data;
            //enum local_flags flags = selfp->intdata;
            if (fd == NULL) break;
            struct sync_diff_data *diff_data = fd->diff_data;
            if (diff_data == NULL) break;
            struct ccns_handle *ch = diff_data->client_data;
            free_fetch_data(ch, fd);
            start_round(ch, 10);
            ret = CCN_UPCALL_RESULT_OK;
            break;
        }
        case CCN_UPCALL_CONTENT_RAW:
        case CCN_UPCALL_CONTENT: {
            struct sync_diff_fetch_data *fd = selfp->data;
            enum local_flags flags = selfp->intdata;
            if (fd == NULL) break;
            struct sync_diff_data *diff_data = fd->diff_data;
            if (diff_data == NULL) break;
            struct SyncRootStruct *root = diff_data->root;
            if (root == NULL) break;
            struct ccns_handle *ch = diff_data->client_data;
            struct SyncNodeComposite *nc = extractNode(root, info);
            if (ch->debug >= CCNL_FINE) {
                char fs[1024];
                int pos = 0;
                switch (flags) {
                    case LF_NULL: 
                        pos += snprintf(fs+pos, sizeof(fs)-pos, "null");
                        break;
                    case LF_ADVISE:
                        pos += snprintf(fs+pos, sizeof(fs)-pos, "advise");
                        break;
                    case LF_NODE:
                        pos += snprintf(fs+pos, sizeof(fs)-pos, "node");
                        break;
                    default: 
                        pos += snprintf(fs+pos, sizeof(fs)-pos, "??%d", flags);
                        break;
                }
                if (nc != NULL)
                    pos += snprintf(fs+pos, sizeof(fs)-pos, ", nc OK");
                struct ccn_charbuf *nm = SyncNameForIndexbuf(info->content_ccnb,
                                                             info->content_comps);
                struct ccn_charbuf *uri = SyncUriForName(nm);
                pos += snprintf(fs+pos, sizeof(fs)-pos, ", %s", ccn_charbuf_as_string(uri));
                SyncNoteSimple(diff_data->root, here, fs);
                ccn_charbuf_destroy(&nm);
                ccn_charbuf_destroy(&uri);
            }
            if (nc != NULL) {
                // the node exists, so store it
                // TBD: check the hash?
                struct ccns_handle *ch = diff_data->client_data;
                struct SyncHashCacheEntry *ce = SyncHashEnter(root->ch,
                                                              nc->hash->buf, nc->hash->length,
                                                              SyncHashState_remote);
                if (flags == LF_ADVISE) {
                    ch->hashSeen = SyncNoteHash(ch->hashSeen, ce);
                    if (ch->next_ce == NULL)
                        // have to have an initial place to start
                        ch->next_ce = ce;
                }
                if (ce->ncR == NULL) {
                    // store the node
                    ce->ncR = nc;
                    SyncNodeIncRC(nc);
                } else {
                    // flush the node
                    SyncNodeDecRC(nc);
                    nc = NULL;
                }
                if (flags != LF_NULL) {
                    // from start_interest
                    start_round(ch, 10);
                } else {
                    // from sync_diff
                    sync_diff_note_node(diff_data, ce);
                }
                ret = CCN_UPCALL_RESULT_OK;
            }
            free_fetch_data(ch, fd);
            break;
        default:
            // SHOULD NOT HAPPEN
            break;
        }
    }
    return ret;
}
Exemple #24
0
int
ccndc_srv(struct ccndc_data *self,
          const unsigned char *domain,
          size_t domain_size)
{
    char *proto = NULL;
    char *host = NULL;
    int port = 0;
    char port_str[10];
    struct ccn_charbuf *uri;
    struct ccn_charbuf *uri_auto;
    struct ccn_face_instance *face;
    struct ccn_face_instance *newface;
    struct ccn_forwarding_entry *prefix;
    struct ccn_forwarding_entry *prefix_auto;
    int res;
    
    res = ccndc_query_srv(domain, domain_size, &host, &port, &proto);
    if (res < 0) {
        return -1;
    }
    
    uri = ccn_charbuf_create();
    ccn_charbuf_append_string(uri, "ccnx:/");
    if (domain_size != 0) {
        ccn_uri_append_percentescaped(uri, domain, domain_size);
    }
    
    snprintf (port_str, sizeof(port_str), "%d", port);
    
    /* now process the results */
    /* pflhead, lineno=0, "add" "ccnx:/asdfasdf.com/" "tcp|udp", host, portstring, NULL NULL NULL */
    
    ccndc_note(__LINE__, " >>> trying:   add %s %s %s %s <<<\n", ccn_charbuf_as_string(uri), proto, host, port_str);
    
    face = parse_ccn_face_instance(self, proto, host, port_str, NULL, NULL,
                                   (~0U) >> 1);
    
    prefix = parse_ccn_forwarding_entry(self, ccn_charbuf_as_string(uri), NULL,
                                        self->lifetime);
    if (face == NULL || prefix == NULL) {
        res = -1;
        goto Cleanup;
    }
    
    // crazy operation
    // First. "Create" face, which will do nothing if face already exists
    // Second. Destroy the face
    // Third. Create face for real
    
    newface = ccndc_do_face_action(self, "newface", face);
    if (newface == NULL) {
        ccndc_warn(__LINE__, "Cannot create/lookup face");
        res = -1;
        goto Cleanup;
    }
    
    face->faceid = newface->faceid;
    ccn_face_instance_destroy(&newface);
    
    newface = ccndc_do_face_action(self, "destroyface", face);
    if (newface == NULL) {
        ccndc_warn(__LINE__, "Cannot destroy face");
    } else {
        ccn_face_instance_destroy(&newface);
    }
    
    newface = ccndc_do_face_action(self, "newface", face);
    if (newface == NULL) {
        ccndc_warn(__LINE__, "Cannot create/lookup face");
        res = -1;
        goto Cleanup;
    }
    
    prefix->faceid = newface->faceid;
    ccn_face_instance_destroy(&newface);
    
    res = ccndc_do_prefix_action(self, "prefixreg", prefix);
    if (res < 0) {
        ccndc_warn(__LINE__, "Cannot register prefix [%s]\n", ccn_charbuf_as_string(uri));
    }

    uri_auto = ccn_charbuf_create();
    ccn_charbuf_append_string(uri_auto, "ccnx:/autoconf-route");
    prefix_auto = parse_ccn_forwarding_entry(self, ccn_charbuf_as_string(uri_auto), NULL,
                                        self->lifetime);
    if (prefix_auto == NULL) {
        res = -1;
        goto Cleanup;
    }

    prefix_auto->faceid = prefix->faceid;
    res = ccndc_do_prefix_action(self, "prefixreg", prefix_auto);
    if (res < 0) {
        ccndc_warn(__LINE__, "Cannot register prefix_auto [%s]\n", ccn_charbuf_as_string(uri_auto));
    }
    
Cleanup:
    free(host);
    ccn_charbuf_destroy(&uri);
    ccn_charbuf_destroy(&uri_auto);
    ccn_face_instance_destroy(&face);
    ccn_forwarding_entry_destroy(&prefix);
    ccn_forwarding_entry_destroy(&prefix_auto);
    return res;
}
Exemple #25
0
int
main(int argc, char **argv)
{
    int opt;
    int res;
    char *prog = argv[0];
    struct ccn *h;
    struct ccns_slice *slice;
    struct ccn_charbuf *prefix = ccn_charbuf_create();
    struct ccn_charbuf *topo = ccn_charbuf_create();
    struct ccn_charbuf *clause = ccn_charbuf_create();
    struct ccn_charbuf *slice_name = ccn_charbuf_create();
    struct ccn_charbuf *slice_uri = ccn_charbuf_create();
    enum {
        CREATE = 0,
        DELETE = 1
    } cmd = CREATE;
    unsigned verbose = 0;
    unsigned i;
    
    if (prefix == NULL || topo == NULL || clause == NULL ||
        slice_name == NULL || slice_uri == NULL) {
        fprintf(stderr, "Unable to allocate required memory.\n");
        exit(1);
    }
    
    while ((opt = getopt(argc, argv, "vh")) != -1) {
        switch (opt) {
            case 'v':
                verbose = 1;
                break;
            default:
            case 'h':
                usage(prog);
                break;
        }
    }
    argc -= optind;
    argv += optind;
    
    if (argc < 3)
        usage(prog);
    if (strcmp(argv[0], "create") == 0)
        cmd = CREATE;
    else if (strcmp(argv[0], "delete") == 0)
        cmd = DELETE;
    else
        usage(prog);
    
    slice = ccns_slice_create();
    
    ccn_charbuf_reset(topo);
    if (0 > ccn_name_from_uri(topo, argv[1])) usage(prog);
    ccn_charbuf_reset(prefix);
    if (0 > ccn_name_from_uri(prefix, argv[2])) usage(prog);
    if (0 > ccns_slice_set_topo_prefix(slice, topo, prefix)) usage(prog);
    for (i = 3; i < argc; i++) {
        ccn_charbuf_reset(clause);
        if (0 > ccn_name_from_uri(clause, argv[i])) usage(prog);
        else
            if (0 > ccns_slice_add_clause(slice, clause)) usage(prog);
    }
    
    h = ccn_create();
    res = ccn_connect(h, NULL);
    if (0 > res) {
        fprintf(stderr, "Unable to connect to ccnd.\n");
        exit(1);
    }
    switch(cmd) {
        case CREATE:
            res = ccns_write_slice(h, slice, slice_name);
            break;
        case DELETE:
            ccns_slice_name(slice_name, slice);
            res = ccns_delete_slice(h, slice_name);
            break;
    }
    if (verbose || res < 0) {
        ccn_uri_append(slice_uri, slice_name->buf, slice_name->length, 1);
        printf("%s slice %s %s\n",
               cmd == CREATE ? "create" : "delete",
               ccn_charbuf_as_string(slice_uri),
               (res < 0) ? "failed" : "succeeded");
    }
    ccns_slice_destroy(&slice);
    ccn_destroy(&h);
    ccn_charbuf_destroy(&prefix);
    ccn_charbuf_destroy(&topo);
    ccn_charbuf_destroy(&clause);
    ccn_charbuf_destroy(&slice_name);
    ccn_charbuf_destroy(&slice_uri);
    
    exit(res);
}
Exemple #26
0
/*
 * This upcall gets called for each piece of incoming content that
 * matches one of our interests.  We need to issue a new interest that
 * excludes another component at the current level, and perhaps also
 * and interest to start exploring the next level.  Thus if the matched
 * interest is
 *   /a/b/c exclude {d,e,f,i,j,k}
 * and we get
 *   /a/b/c/g/h
 * we would issue a new interest
 *   /a/b/c exclude {d,e,f,g,i,j,k}
 * to continue exploring the current level, plus a simple interest
 *   /a/b/c/g
 * to start exploring the next level as well.
 *
 * This does end up fetching each piece of content multiple times, once for
 * each level in the name. The repeated requests will be answered from the local
 * content store, though, and so should not generate extra network traffic.
 * There is a lot of unanswerable interest generated, though.
 *
 * To prevent the interests from becoming too huge, we may need to split them.
 * Thus if the first new interest above were deemed too large, we could instead
 * issue the two interests
 *   /a/b/c exclude {d,e,f,g,*}
 *   /a/b/c exclude {*,g,i,j,k}
 * where * stands for a Bloom filter that excludes anything.  Note the
 * repetition of g to ensure that these two interests cover disjoint portions
 * of the hierarchy. We need to keep track of the endpoint conditions
 * as well as the excluded set in our upcall data.
 * When a split happens, we need a new closure to track it, as we do when
 * we start exploring a new level.
 */
static enum ccn_upcall_res
incoming_content(
    struct ccn_closure *selfp,
    enum ccn_upcall_kind kind,
    struct ccn_upcall_info *info)
{
    struct ccn_charbuf *c = NULL;
    struct ccn_charbuf *comp = NULL;
    struct ccn_charbuf *uri = NULL;
    const unsigned char *ccnb = NULL;
    size_t ccnb_size = 0;
    struct ccn_indexbuf *comps = NULL;
    int matched_comps = 0;
    int res;
    int i;
    struct ccn_traversal *data = get_my_data(selfp);

    if (kind == CCN_UPCALL_FINAL) {
        for (i = 0; i < data->n_excl; i++)
            ccn_charbuf_destroy(&(data->excl[i]));
        if (data->excl != NULL)
            free(data->excl);
        free(data);
        free(selfp);
        return(0);
    }
    if (kind == CCN_UPCALL_INTEREST_TIMED_OUT)
        return(0);
    if (kind == CCN_UPCALL_CONTENT_BAD)
        return(0);
    if (kind == CCN_UPCALL_CONTENT_UNVERIFIED) {
        if ((data->flags & MUST_VERIFY) != 0)
            return(CCN_UPCALL_RESULT_VERIFY);
    }
    if (kind != CCN_UPCALL_CONTENT && kind != CCN_UPCALL_CONTENT_UNVERIFIED) abort();

    ccnb = info->content_ccnb;
    ccnb_size = info->pco->offset[CCN_PCO_E];
    comps = info->content_comps;
    matched_comps = info->pi->prefix_comps;
    c = ccn_charbuf_create();
    uri = ccn_charbuf_create();

    if (matched_comps + 1 > comps->n) {
        ccn_uri_append(c, ccnb, ccnb_size, 1);
        fprintf(stderr, "How did this happen?  %s\n", ccn_charbuf_as_string(uri));
        exit(1);
    }

    data->counter[0]++; /* Tell main that something new came in */

    /* Recover the same prefix as before */
    ccn_name_init(c);
    ccn_name_append_components(c, ccnb, comps->buf[0], comps->buf[matched_comps]);

    comp = ccn_charbuf_create();
    ccn_name_init(comp);
    if (matched_comps + 1 == comps->n) {
        /* Reconstruct the implicit content digest component */
        ccn_digest_ContentObject(ccnb, info->pco);
        ccn_name_append(comp, info->pco->digest, info->pco->digest_bytes);
    }
    else {
        ccn_name_append_components(comp, ccnb,
        comps->buf[matched_comps],
        comps->buf[matched_comps + 1]);
    }
    data->excl = realloc(data->excl, (data->n_excl + 1) * sizeof(data->excl[0]));
    data->excl[data->n_excl++] = comp;
    comp = NULL;
    qsort(data->excl, data->n_excl, sizeof(data->excl[0]), &namecompare);
    res = express_my_interest(info->h, selfp, c);
    if (res == -1) {
        struct ccn_closure *high = split_my_excludes(selfp);
        if (high == NULL) abort();
        express_my_interest(info->h, selfp, c);
        express_my_interest(info->h, high, c);
    }
    /* Explore the next level, if there is one. */
    if (matched_comps + 2 < comps->n) {
        struct ccn_traversal *newdat = NULL;
        struct ccn_closure *cl;
        newdat = calloc(1, sizeof(*newdat));
        newdat->magic = 68955871;
        newdat->warn = 1492;
        newdat->counter = data->counter;
        newdat->flags = data->flags & ~(EXCLUDE_LOW | EXCLUDE_HIGH);
        newdat->n_excl = 0;
        newdat->excl = NULL;
        cl = calloc(1, sizeof(*cl));
        cl->p = &incoming_content;
        cl->data = newdat;
        ccn_name_init(c);
        ccn_name_append_components(c, ccnb,
        comps->buf[0],
        comps->buf[matched_comps + 1]);
        express_my_interest(info->h, cl, c);
    }
    else {
        res = ccn_uri_append(uri, info->content_ccnb, info->pco->offset[CCN_PCO_E], 1);
        if (res < 0)
            fprintf(stderr, "*** Error: ccn_traverse line %d res=%d\n", __LINE__, res);
        else
            printf("%s\n", ccn_charbuf_as_string(uri));
    }
    ccn_charbuf_destroy(&c);
    ccn_charbuf_destroy(&uri);
    return(0);
}
Exemple #27
0
static int
dissect_ccn_contentobject(const unsigned char *ccnb, size_t ccnb_size, tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
    proto_tree *signature_tree;
    proto_tree *name_tree;
    proto_tree *signedinfo_tree;
    proto_tree *content_tree;
    proto_item *titem;
    struct ccn_parsed_ContentObject co;
    struct ccn_parsed_ContentObject *pco = &co;
    struct ccn_charbuf *c;
    struct ccn_indexbuf *comps;
    const unsigned char *comp;
    size_t comp_size;
    size_t blob_size;
    const unsigned char *blob;
    int l;
    unsigned int i;
    double dt;
    nstime_t timestamp;
    int res;

    comps = ccn_indexbuf_create();
    res = ccn_parse_ContentObject(ccnb, ccnb_size, pco, comps);
    if (res < 0) return (-1);

    /* Signature */
    l = pco->offset[CCN_PCO_E_Signature] - pco->offset[CCN_PCO_B_Signature];
    titem = proto_tree_add_item(tree, hf_ccn_signature, tvb, pco->offset[CCN_PCO_B_Signature], l, FALSE);
    signature_tree = proto_item_add_subtree(titem, ett_signature);

    /* DigestAlgorithm */
    l = pco->offset[CCN_PCO_E_DigestAlgorithm] - pco->offset[CCN_PCO_B_DigestAlgorithm];
    if (l > 0) {
        res = ccn_ref_tagged_BLOB(CCN_DTAG_DigestAlgorithm, ccnb,
                                  pco->offset[CCN_PCO_B_DigestAlgorithm],
                                  pco->offset[CCN_PCO_E_DigestAlgorithm],
                                  &blob, &blob_size);
        titem = proto_tree_add_item(signature_tree, hf_ccn_signaturedigestalg, tvb,
                                    blob - ccnb, blob_size, FALSE);
    }
    /* Witness */
    l = pco->offset[CCN_PCO_E_Witness] - pco->offset[CCN_PCO_B_Witness];
    if (l > 0) {
        /* add the witness item to the signature tree */
    }

    /* Signature bits */
    l = pco->offset[CCN_PCO_E_SignatureBits] - pco->offset[CCN_PCO_B_SignatureBits];
    if (l > 0) {
        res = ccn_ref_tagged_BLOB(CCN_DTAG_SignatureBits, ccnb,
                                  pco->offset[CCN_PCO_B_SignatureBits],
                                  pco->offset[CCN_PCO_E_SignatureBits],
                                  &blob, &blob_size);
        titem = proto_tree_add_bytes(signature_tree, hf_ccn_signaturebits, tvb,
                                     blob - ccnb, blob_size, blob);
    }

    /* /Signature */

    /* Name */
    l = pco->offset[CCN_PCO_E_Name] - pco->offset[CCN_PCO_B_Name];
    c = ccn_charbuf_create();
    ccn_uri_append(c, ccnb, ccnb_size, 1);
    titem = proto_tree_add_string(tree, hf_ccn_name, tvb,
                                      pco->offset[CCN_PCO_B_Name], l,
                                      ccn_charbuf_as_string(c));
    name_tree = proto_item_add_subtree(titem, ett_name);
    ccn_charbuf_destroy(&c);

    /* Name Components */
    for (i = 0; i < comps->n - 1; i++) {
        res = ccn_name_comp_get(ccnb, comps, i, &comp, &comp_size);
        titem = proto_tree_add_item(name_tree, hf_ccn_name_components, tvb, comp - ccnb, comp_size, FALSE);
    }

    /* /Name */

    /* SignedInfo */
    l = pco->offset[CCN_PCO_E_SignedInfo] - pco->offset[CCN_PCO_B_SignedInfo];
    titem = proto_tree_add_text(tree, tvb,
                                         pco->offset[CCN_PCO_B_SignedInfo], l,
                                         "SignedInfo");
    signedinfo_tree = proto_item_add_subtree(titem, ett_signedinfo);

    /* PublisherPublicKeyDigest */
    l = pco->offset[CCN_PCO_E_PublisherPublicKeyDigest] - pco->offset[CCN_PCO_B_PublisherPublicKeyDigest];
    if (l > 0) {
        res = ccn_ref_tagged_BLOB(CCN_DTAG_PublisherPublicKeyDigest, ccnb,
                                  pco->offset[CCN_PCO_B_PublisherPublicKeyDigest],
                                  pco->offset[CCN_PCO_E_PublisherPublicKeyDigest],
                                  &blob, &blob_size);
        titem = proto_tree_add_bytes(signedinfo_tree, hf_ccn_publisherpublickeydigest, tvb, blob - ccnb, blob_size, blob);
    }

    /* Timestamp */
    l = pco->offset[CCN_PCO_E_Timestamp] - pco->offset[CCN_PCO_B_Timestamp];
    if (l > 0) {
        res = ccn_ref_tagged_BLOB(CCN_DTAG_Timestamp, ccnb,
                                  pco->offset[CCN_PCO_B_Timestamp],
                                  pco->offset[CCN_PCO_E_Timestamp],
                                  &blob, &blob_size);
        dt = 0.0;
        for (i = 0; i < blob_size; i++)
            dt = dt * 256.0 + (double)blob[i];
        dt /= 4096.0;
        timestamp.secs = dt; /* truncates */
        timestamp.nsecs = (dt - (double) timestamp.secs) *  1000000000.0;
        titem = proto_tree_add_time(signedinfo_tree, hf_ccn_timestamp, tvb, blob - ccnb, blob_size, &timestamp);
    }

    /* Type */
    l = pco->offset[CCN_PCO_E_Type] - pco->offset[CCN_PCO_B_Type];
    if (l > 0) {
        res = ccn_ref_tagged_BLOB(CCN_DTAG_Type, ccnb,
                                  pco->offset[CCN_PCO_B_Type],
                                  pco->offset[CCN_PCO_E_Type],
                                  &blob, &blob_size);
        titem = proto_tree_add_int(signedinfo_tree, hf_ccn_contenttype, tvb, blob - ccnb, blob_size, pco->type);
    } else {
        titem = proto_tree_add_int(signedinfo_tree, hf_ccn_contenttype, NULL, 0, 0, pco->type);
    }

    /* FreshnessSeconds */
    l = pco->offset[CCN_PCO_E_FreshnessSeconds] - pco->offset[CCN_PCO_B_FreshnessSeconds];
    if (l > 0) {
        res = ccn_ref_tagged_BLOB(CCN_DTAG_FreshnessSeconds, ccnb,
                                  pco->offset[CCN_PCO_B_FreshnessSeconds],
                                  pco->offset[CCN_PCO_E_FreshnessSeconds],
                                  &blob, &blob_size);
        i = ccn_fetch_tagged_nonNegativeInteger(CCN_DTAG_FreshnessSeconds, ccnb,
                                                  pco->offset[CCN_PCO_B_FreshnessSeconds],
                                                  pco->offset[CCN_PCO_E_FreshnessSeconds]);

        titem = proto_tree_add_uint(signedinfo_tree, hf_ccn_freshnessseconds, tvb, blob - ccnb, blob_size, i);
    }

    /* FinalBlockID */
    l = pco->offset[CCN_PCO_E_FinalBlockID] - pco->offset[CCN_PCO_B_FinalBlockID];
    if (l > 0) {
        res = ccn_ref_tagged_BLOB(CCN_DTAG_FinalBlockID, ccnb,
                                  pco->offset[CCN_PCO_B_FinalBlockID],
                                  pco->offset[CCN_PCO_E_FinalBlockID],
                                  &blob, &blob_size);

        titem = proto_tree_add_item(signedinfo_tree, hf_ccn_finalblockid, tvb, blob - ccnb, blob_size, FALSE);
    }
    /* TODO: KeyLocator */
    /* /SignedInfo */

    /* Content */
    l = pco->offset[CCN_PCO_E_Content] - pco->offset[CCN_PCO_B_Content];
    res = ccn_ref_tagged_BLOB(CCN_DTAG_Content, ccnb,
                                  pco->offset[CCN_PCO_B_Content],
                                  pco->offset[CCN_PCO_E_Content],
                                  &blob, &blob_size);
    titem = proto_tree_add_text(tree, tvb,
                                         pco->offset[CCN_PCO_B_Content], l,
                                         "Content: %d bytes", blob_size);
    if (blob_size > 0) {
        content_tree = proto_item_add_subtree(titem, ett_content);
        titem = proto_tree_add_item(content_tree, hf_ccn_contentdata, tvb, blob - ccnb, blob_size, FALSE);
    }

    return (ccnb_size);
}
Exemple #28
0
static int
dissect_ccn_interest(const unsigned char *ccnb, size_t ccnb_size, tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
    proto_tree *name_tree;
    proto_tree *exclude_tree;
    proto_item *titem;
    struct ccn_parsed_interest interest;
    struct ccn_parsed_interest *pi = &interest;
    struct ccn_charbuf *c;
    struct ccn_indexbuf *comps;
    const unsigned char *comp;
    size_t comp_size;
    const unsigned char *blob;
    size_t blob_size;
    ssize_t l;
    unsigned int i;
    int res;

    comps = ccn_indexbuf_create();
    res = ccn_parse_interest(ccnb, ccnb_size, pi, comps);

    /* Name */
    l = pi->offset[CCN_PI_E_Name] - pi->offset[CCN_PI_B_Name];
    c = ccn_charbuf_create();
    ccn_uri_append(c, ccnb, ccnb_size, 1);
    titem = proto_tree_add_string(tree, hf_ccn_name, tvb,
                                      pi->offset[CCN_PI_B_Name], l,
                                      ccn_charbuf_as_string(c));
    name_tree = proto_item_add_subtree(titem, ett_name);
    ccn_charbuf_destroy(&c);

    for (i = 0; i < comps->n - 1; i++) {
        res = ccn_name_comp_get(ccnb, comps, i, &comp, &comp_size);
        titem = proto_tree_add_item(name_tree, hf_ccn_name_components, tvb, comp - ccnb, comp_size, FALSE);
    }

    /* MinSuffixComponents */
    l = pi->offset[CCN_PI_E_MinSuffixComponents] - pi->offset[CCN_PI_B_MinSuffixComponents];
    if (l > 0) {
        i = pi->min_suffix_comps;
        titem = proto_tree_add_uint(tree, hf_ccn_minsuffixcomponents, tvb, pi->offset[CCN_PI_B_MinSuffixComponents], l, i);
    }

    /* MaxSuffixComponents */
    l = pi->offset[CCN_PI_E_MaxSuffixComponents] - pi->offset[CCN_PI_B_MaxSuffixComponents];
    if (l > 0) {
        i = pi->max_suffix_comps;
        titem = proto_tree_add_uint(tree, hf_ccn_maxsuffixcomponents, tvb, pi->offset[CCN_PI_B_MaxSuffixComponents], l, i);
    }

    /* PublisherIDKeyDigest? */
    /* Exclude */
    l = pi->offset[CCN_PI_E_Exclude] - pi->offset[CCN_PI_B_Exclude];
    if (l > 0) {
            titem = proto_tree_add_text(tree, tvb, pi->offset[CCN_PI_B_Exclude], l,
                                         "Exclude");
            exclude_tree = proto_item_add_subtree(titem, ett_exclude);
    }
    /* ChildSelector */
    l = pi->offset[CCN_PI_E_ChildSelector] - pi->offset[CCN_PI_B_ChildSelector];
    if (l > 0) {
        i = pi->orderpref;
        titem = proto_tree_add_uint(tree, hf_ccn_childselector, tvb, pi->offset[CCN_PI_B_ChildSelector], l, i);
        proto_item_append_text(titem, ", %s", val_to_str(i & 1, VALS(childselectordirection_vals), ""));

    }

    /* AnswerOriginKind */
    l = pi->offset[CCN_PI_E_AnswerOriginKind] - pi->offset[CCN_PI_B_AnswerOriginKind];
    if (l > 0) {
        i = pi->answerfrom;
        titem = proto_tree_add_uint(tree, hf_ccn_answeroriginkind, tvb, pi->offset[CCN_PI_B_AnswerOriginKind], l, i);
    }

    /* Scope */
    l = pi->offset[CCN_PI_E_Scope] - pi->offset[CCN_PI_B_Scope];
    if (l > 0) {
        i = pi->scope;
        titem = proto_tree_add_uint(tree, hf_ccn_scope, tvb, pi->offset[CCN_PI_B_Scope], l, i);
    }

    /* Nonce */
    /* Nonce */
    l = pi->offset[CCN_PI_E_Nonce] - pi->offset[CCN_PI_B_Nonce];
    if (l > 0) {
        i = ccn_ref_tagged_BLOB(CCN_DTAG_Nonce, ccnb,
                                pi->offset[CCN_PI_B_Nonce],
                                pi->offset[CCN_PI_E_Nonce],
                                &blob, &blob_size);
        if (check_col(pinfo->cinfo, COL_INFO)) {
            col_append_str(pinfo->cinfo, COL_INFO, ", <");
            for (i = 0; i < blob_size; i++)
                col_append_fstr(pinfo->cinfo, COL_INFO, "%02x", blob[i]);
            col_append_str(pinfo->cinfo, COL_INFO, ">");
        }
        titem = proto_tree_add_item(tree, hf_ccn_nonce, tvb,
                                    blob - ccnb, blob_size, FALSE);
    }
    
    return (1);

}
Exemple #29
0
/*
 * Dissector that returns:
 *
 *	The amount of data in the protocol's PDU, if it was able to
 *	dissect all the data;
 *
 *	0, if the tvbuff doesn't contain a PDU for that protocol;
 *
 *	The negative of the amount of additional data needed, if
 *	we need more data (e.g., from subsequent TCP segments) to
 *	dissect the entire PDU.
 */
static int
dissect_ccn(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
    guint tvb_size = 0;
    proto_tree *ccn_tree;
    proto_item *ti = NULL;
    const unsigned char *ccnb;
    struct ccn_skeleton_decoder skel_decoder;
    struct ccn_skeleton_decoder *sd;
    struct ccn_charbuf *c;
    int packet_type = 0;
    int packet_type_length = 0;
    /* a couple of basic checks to rule out packets that are definitely not ours */
    tvb_size = tvb_length(tvb);
    if (tvb_size < CCN_MIN_PACKET_SIZE || tvb_get_guint8(tvb, 0) == 0)
        return (0);

    sd = &skel_decoder;
    memset(sd, 0, sizeof(*sd));
    sd->state |= CCN_DSTATE_PAUSE;
    ccnb = ep_tvb_memdup(tvb, 0, tvb_size);
    ccn_skeleton_decode(sd, ccnb, tvb_size);
    if (sd->state < 0)
        return (0);
    if (CCN_GET_TT_FROM_DSTATE(sd->state) == CCN_DTAG) {
        packet_type = sd->numval;
        packet_type_length = sd->index;
    } else {
        return (0);
    }
    memset(sd, 0, sizeof(*sd));
    ccn_skeleton_decode(sd, ccnb, tvb_size);
    if (!CCN_FINAL_DSTATE(sd->state)) {
        pinfo->desegment_offset = 0;
        pinfo->desegment_len = DESEGMENT_ONE_MORE_SEGMENT;
        return (-1); /* what should this be? */
    }

    /* Make it visible that we're taking this packet */
    if (check_col(pinfo->cinfo, COL_PROTOCOL)) {
        col_set_str(pinfo->cinfo, COL_PROTOCOL, "CCN");
    }

    /* Clear out stuff in the info column */
    if (check_col(pinfo->cinfo, COL_INFO)) {
        col_clear(pinfo->cinfo, COL_INFO);
    }

    c = ccn_charbuf_create();
    ccn_uri_append(c, ccnb, tvb_size, 1);

    /* Add the packet type and CCN URI to the info column */
    if (check_col(pinfo->cinfo, COL_INFO)) {
        col_add_str(pinfo->cinfo, COL_INFO,
                    val_to_str(packet_type, VALS(ccn_dtag_dict.dict), "Unknown (0x%02x"));
        col_append_sep_str(pinfo->cinfo, COL_INFO, NULL, ccn_charbuf_as_string(c));
    }

    if (tree == NULL) {
        ccn_charbuf_destroy(&c);
        return (sd->index);
    }

    ti = proto_tree_add_protocol_format(tree, proto_ccn, tvb, 0, -1,
                                        "Content-centric Networking Protocol, %s, %s",
                                        val_to_str(packet_type, VALS(ccn_dtag_dict.dict), "Unknown (0x%02x"),
                                        ccn_charbuf_as_string(c));
    ccn_tree = proto_item_add_subtree(ti, ett_ccn);
    ccn_charbuf_destroy(&c);
    ti = proto_tree_add_uint(ccn_tree, hf_ccn_type, tvb, 0, packet_type_length, packet_type);

    switch (packet_type) {
    case CCN_DTAG_ContentObject:
        if (0 > dissect_ccn_contentobject(ccnb, sd->index, tvb, pinfo, ccn_tree))
            return (0);
        break;
    case CCN_DTAG_Interest:
        if (0 > dissect_ccn_interest(ccnb, sd->index, tvb, pinfo, ccn_tree))
            return (0);
        break;
    }

    return (sd->index);
}
Exemple #30
0
/**
 * Call-back from the CCN network that something has arrived
 *
 * We get notified that a client has interests in things we are producing.
 * This function will do some basic checking to see what exactly the client has
 * an interest in, and will produce what is appropriate.
 * Currently the things we produce are:
 * \li last block - we resend the last block we have published for a given name
 * \li last segment - we produce a data message that only contains the latest segment number we used
 *
 * \param	selfp		-> a context structure we created when registering this call-back
 * \param	kind		specifies the type of call-back being processed, see the \b switch statement
 * \param	info		context information about the call-back itself; interests, data, etc.
 * \return a response as to how successful we were in processing the call-back
 * \retval CCN_UPCALL_RESULT_OK		things went well
 * \retval CCN_UPCALL_RESULT_VERIFY	need to verify the contents of what we received
 * \retval CCN_UPCALL_RESULT_REEXPRESS an interest timedout waiting for data, so we try again
 * \retval CCN_UPCALL_RESULT_ERR	some error was encountered
 */
static enum ccn_upcall_res
new_interests (struct ccn_closure *selfp,
    enum ccn_upcall_kind kind, struct ccn_upcall_info *info)
{
  Gstccnxsink *me = GST_CCNXSINK (selfp->data);
  struct ccn_charbuf *cb;
  struct ccn_charbuf *sname = NULL;
  const unsigned char *cp1, *cp2;
  size_t sz1;
  size_t sz2;
  long lastSeq;
  struct ccn_signing_params myparams;
  unsigned int i;
  int rc;


  GST_DEBUG ("something has arrived!");
  GST_DEBUG ("matched is: %d", info->matched_comps);    // number of filter components that were matched by the interest
  cb = interestAsUri (info);
  GST_DEBUG ("as URI: %s", ccn_charbuf_as_string (cb));
  ccn_charbuf_destroy (&cb);

  myparams = me->sp;

  /* Some debugging stuff */
  for (i = 0; i < 10; ++i) {
    const unsigned char *cp;
    size_t sz;
    GST_DEBUG ("%3d: ", i);
    if (0 > ccn_name_comp_get (info->interest_ccnb, info->interest_comps, i,
            &cp, &sz)) {
      // fprintf(stderr, "could not get comp\n");
      break;
    } else {
      // hDump( DUMP_ADDR( cp ), DUMP_SIZE( sz ) );
    }
  }

  switch (kind) {

    case CCN_UPCALL_FINAL:
      GST_LOG_OBJECT (me, "CCN upcall final %p", selfp);
      return (0);

    case CCN_UPCALL_INTEREST_TIMED_OUT:
      if (selfp != me->ccn_closure) {
        GST_LOG_OBJECT (me, "CCN Interest timed out on dead closure %p", selfp);
        return (0);
      }
      GST_LOG_OBJECT (me, "CCN upcall reexpress -- timed out");
      if (me->timeouts > 5) {
        GST_LOG_OBJECT (me, "CCN upcall reexpress -- too many reexpressions");
        return (0);
      }
      me->timeouts++;
      return (CCN_UPCALL_RESULT_REEXPRESS);

    case CCN_UPCALL_CONTENT_UNVERIFIED:
      if (selfp != me->ccn_closure) {
        GST_LOG_OBJECT (me, "CCN unverified content on dead closure %p", selfp);
        return (0);
      }
      return (CCN_UPCALL_RESULT_VERIFY);

    case CCN_UPCALL_CONTENT:
      if (selfp != me->ccn_closure) {
        GST_LOG_OBJECT (me, "CCN content on dead closure %p", selfp);
        return (0);
      }
      break;

    case CCN_UPCALL_CONTENT_BAD:
      GST_LOG_OBJECT (me,
          "Content signature verification failed! Discarding.\n");
      return (CCN_UPCALL_RESULT_ERR);

    case CCN_UPCALL_CONSUMED_INTEREST:
      GST_LOG_OBJECT (me, "Upcall consumed interest\n");
      return (CCN_UPCALL_RESULT_ERR);   /* no data */

      /* Here is the most interesting case...when an interest arrives */
    case CCN_UPCALL_INTEREST:
      GST_INFO ("We got an interest\n");
      myparams.freshness = 1;   /* meta data is old very quickly */

      /* See if any meta information is sought */
      for (i = 0;; ++i) {
        if (0 > ccn_name_comp_get (info->interest_ccnb, info->interest_comps, i,
                &cp1, &sz1)) {
          cp1 = NULL;
          break;
        } else {
          if (!strncmp ((const char *) cp1, "_meta_", 6)) {     // OK, found meta, now which one is needed?
            if (0 > ccn_name_comp_get (info->interest_ccnb,
                    info->interest_comps, i + 1, &cp2, &sz2)) {
              GST_LOG_OBJECT (me,
                  "CCN interest received with invalid meta request");
              cp1 = NULL;
            }
            break;
          }                     // Component not meta, keep looking
        }
      }                         // At this point, i is left pointing at '_meta_' or at the end of component list

      if (cp1) {
        // hDump( DUMP_ADDR(cp1), DUMP_SIZE(sz1) );
        // hDump( DUMP_ADDR(cp2), DUMP_SIZE(sz2) );
        if (strncmp ((const char *) cp2, ".segment", 8))
          goto Exit_Interest;   /* not a match */

        /* publish what segment we are up to in reply to the meta request */
        lastSeq = me->segment - 1;
        GST_INFO ("sending meta data....segment: %d", lastSeq);

        sname = ccn_charbuf_create ();
        ccn_name_init (sname);
        rc = ccn_name_append_components (sname, info->interest_ccnb,
            info->interest_comps->buf[0], info->interest_comps->buf[i + 2]);
        if (rc < 0)
          goto Error_Interest;
        // rc = ccn_create_version(me->ccn, sname, CCN_V_REPLACE | CCN_V_NOW | CCN_V_HIGH, 0, 0);
        // if (rc < 0) goto Error_Interest;
        me->temp->length = 0;
        rc = ccn_sign_content (me->ccn, me->temp, sname, &myparams,
            &lastSeq, sizeof (lastSeq));
        // hDump(DUMP_ADDR(sname->buf), DUMP_SIZE(sname->length));
        if (rc != 0) {
          GST_LOG_OBJECT (me, "Failed to encode ContentObject (rc == %d)\n",
              rc);
          goto Error_Interest;
        }

        GST_INFO ("sending meta data...");
        // hDump(DUMP_ADDR(me->temp->buf), DUMP_SIZE(me->temp->length));
        rc = ccn_put (me->ccn, me->temp->buf, me->temp->length);
        me->temp->length = 0;
        if (rc < 0) {
          GST_LOG_OBJECT (me, "ccn_put failed (res == %d)\n", rc);
          goto Error_Interest;
        }
        GST_INFO ("meta data sent");

      } else
        goto Exit_Interest;     /* do not have _meta_ */

    Exit_Interest:
      ccn_charbuf_destroy (&sname);
      break;

    Error_Interest:
      ccn_charbuf_destroy (&sname);
      return CCN_UPCALL_RESULT_ERR;


    default:
      GST_LOG_OBJECT (me, "CCN upcall result error");
      return (CCN_UPCALL_RESULT_ERR);
  }


  me->timeouts = 0;


  return (CCN_UPCALL_RESULT_OK);

}