Exemplo n.º 1
0
void CcnLAC_dtor(CcnLAC self) {
	if (self->pm != NULL) PollMgr_detach(self->pm, ccn_get_connection_fd(self->ccnh), &CcnLAC_initPollCb, self);
	if (self->nbs != NULL) NBS_pollDetach(self->nbs);
	ccn_destroy(&(self->ccnh));
	if (self->ccnbor != NULL) CcnbOR_dtor(self->ccnbor);
	free(self);
}
Exemplo n.º 2
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");
}
Exemplo n.º 3
0
void CcnLAC_initPollCb(void* pself, PollMgrEvt evt, struct pollfd* fd) {
	CcnLAC self = (CcnLAC)pself;
	switch (evt) {
		case PollMgrEvt_prepare:
			CcnH_pollPrepare(self->ccnh, fd);
			break;
		case PollMgrEvt_result:
			CcnH_pollRun(self->ccnh, fd);
			break;
		case PollMgrEvt_error:
			self->error = true;
			PollMgr_detach(self->pm, ccn_get_connection_fd(self->ccnh), &CcnLAC_initPollCb, self);
			break;
	}
}
Exemplo n.º 4
0
int NdnMediaProcess::startThread() {
    struct ccn *h;

    /* Shut down any lingering session */
    while (ndnState.ccn != NULL) {
        ndnState.active = 0;
        printf("waiting for old session to die\n");
    }
    h = ccn_create();
    if (ccn_connect(h, NULL) == -1) {
        ccn_perror(h, "Failed to contact ccnd");
        ccn_destroy(&h);
        return (-1);
    }
	pthread_mutexattr_init(&ccn_attr);
	pthread_mutexattr_settype(&ccn_attr, PTHREAD_MUTEX_RECURSIVE);     
	pthread_mutex_init(&ccn_mutex, &ccn_attr);

    ndnState.ccn = h; 
	pfds[0].fd = ccn_get_connection_fd(ndnState.ccn);
	pfds[0].events = POLLIN;
	clock = new QTimer(this);
	connect(clock, SIGNAL(timeout()), this, SLOT(tick()));
	clock->start(PER_PACKET_LEN);
	
    if (! isRunning()) {
        fprintf(stderr, "Starting voice thread in media_pro\n"); 
        ndnState.active = true;

        start(QThread::HighestPriority);
#ifdef Q_OS_LINUX
        int policy;
        struct sched_param param;
        if (pthread_getschedparam(pthread_self(), &policy, &param) == 0) {
            if (policy == SCHED_OTHER) {
                policy = SCHED_FIFO;
                param.sched_priority = 1;
                pthread_setschedparam(pthread_self(), policy, &param);
            }
        }
#endif
    }
	else
		fprintf(stderr, "what the hell\n");
    return 0;
}
Exemplo n.º 5
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 new interest messages.
 *
 * \param data		the task context information setup by the parent sink element thread
 */
static void
ccn_event_thread (void *data)
{
  Gstccnxsrc *src = (Gstccnxsrc *) data;
  struct ccn *ccn = src->ccn;
  int res = 0;

  GST_DEBUG ("*** event thread starting");
  /* We pass control to ccnx for a while so it can work with any incoming or outgoing data */
  /* We check to see if any problems have caused our ccnd connection to fail, and we reconnect */
  while (res >= 0) {
    res = ccn_run (ccn, 1000);
    if (res < 0 && ccn_get_connection_fd (ccn) == -1) {
      /* Try reconnecting, after a bit of delay */
      msleep ((30 + (getpid () % 30)) * 1000);
      res = ccn_connect (ccn, ccndHost ());
    }
  }
  GST_DEBUG ("*** event thread ending");
}
Exemplo n.º 6
0
static int
ccnr_direct_client_refresh(struct ccn_schedule *sched,
               void *clienth,
               struct ccn_scheduled_event *ev,
               int flags)
{
    struct ccnr_handle *ccnr = clienth;
    int microsec = 0;
    if ((flags & CCN_SCHEDULE_CANCEL) == 0 &&
          ccnr->direct_client != NULL &&
          ccnr->direct_client_refresh == ev) {
        microsec = ccn_process_scheduled_operations(ccnr->direct_client);
        // XXX - This is not really right, since an incoming request can cause us to need to reschedule this event.
        if CCNSHOULDLOG(ccnr, refresh, CCNL_FINEST)
            ccnr_msg(ccnr, "direct_client_refresh %d in %d usec",
                     ccn_get_connection_fd(ccnr->direct_client), microsec);
        if (microsec > ev->evint)
            microsec = ev->evint;
        if (microsec == 0)
            microsec = CCN_INTEREST_LIFETIME_MICROSEC;
    }
Exemplo n.º 7
0
void GroupManager::StartThread() {
	if (! isRunning()) {
		debug("Starting Userlist Handling thread");
		bRunning = true;

		pfds[0].fd = ccn_get_connection_fd(ccn);
		pfds[0].events = POLLIN;
		start(QThread::HighestPriority);
#ifdef Q_OS_LINUX
		// QThread::HighestPriority == Same as everything else...
		int policy;
		sched_param param;
		if (pthread_getschedparam(pthread_self(), &policy, &param) == 0) {
			if (policy == SCHED_OTHER) {
				policy = SCHED_FIFO;
				param.sched_priority = 1;
				pthread_setschedparam(pthread_self(), policy, &param);
			}
		}
#endif
	}
}
Exemplo n.º 8
0
enum ccn_upcall_res CcnLAC_fetchFaceidCb(struct ccn_closure* selfp, enum ccn_upcall_kind kind, struct ccn_upcall_info* info) {
	CcnLAC self = (CcnLAC)selfp->data;
	switch (kind) {
		case CCN_UPCALL_FINAL: {
			free(selfp);
			return CCN_UPCALL_RESULT_OK;
		}
		case CCN_UPCALL_INTEREST_TIMED_OUT: {
			return CCN_UPCALL_RESULT_REEXPRESS;
		}
		case CCN_UPCALL_CONTENT_UNVERIFIED:
		case CCN_UPCALL_CONTENT_KEYMISSING:
		case CCN_UPCALL_CONTENT_RAW:
		case CCN_UPCALL_CONTENT: {
			struct ccn_forwarding_entry* fe = NULL;
			const unsigned char* fe_ccnb = NULL;
			size_t fe_ccnb_size = 0;
			int res = ccn_content_get_value(info->content_ccnb, info->pco->offset[CCN_PCO_E], info->pco, &fe_ccnb, &fe_ccnb_size);
			if (res == 0) fe = ccn_forwarding_entry_parse(fe_ccnb, fe_ccnb_size);
			if (fe != NULL) {
				self->faceid = fe->faceid;
				ccn_forwarding_entry_destroy(&fe);
			} else {
				self->error = true;
			}
			PollMgr_detach(self->pm, ccn_get_connection_fd(self->ccnh), &CcnLAC_initPollCb, self);
			void* emptyPDU = malloc(CCN_EMPTY_PDU_LENGTH);
			memcpy(emptyPDU, CCN_EMPTY_PDU, CCN_EMPTY_PDU_LENGTH);
			NBS_write(self->nbs, emptyPDU, 0, CCN_EMPTY_PDU_LENGTH, NULL);
			NBS_pollAttach(self->nbs, self->pm);
			return CCN_UPCALL_RESULT_OK;
		}
		default: {
			return CCN_UPCALL_RESULT_ERR;
		}
	}
}
Exemplo n.º 9
0
void CcnCC_pollDetach(CcnCC self, PollMgr pm) {
	PollMgr_detach(pm, ccn_get_connection_fd(self->ccnh), &CcnCC_pollCb, self);
}
Exemplo n.º 10
0
/**
 * Create a new ccnr instance
 * @param progname - name of program binary, used for locating helpers
 * @param logger - logger function
 * @param loggerdata - data to pass to logger function
 */
PUBLIC struct ccnr_handle *
r_init_create(const char *progname, ccnr_logger logger, void *loggerdata)
{
    char *sockname = NULL;
    const char *portstr = NULL;
    const char *listen_on = NULL;
    const char *d = NULL;
    struct ccnr_handle *h = NULL;
    struct hashtb_param param = {0};
    struct ccn_charbuf *config = NULL;
    int res;
    
    h = calloc(1, sizeof(*h));
    if (h == NULL)
        return(h);
    h->notify_after = 0; //CCNR_MAX_ACCESSION;
    h->logger = logger;
    h->loggerdata = loggerdata;
    h->logpid = (int)getpid();
    h->progname = progname;
    h->debug = -1;
    config = r_init_read_config(h);
    if (config == NULL)
        goto Bail;
    r_init_parse_config(h, config, 0); /* silent pass to pick up CCNR_DEBUG */
    h->debug = 1; /* so that we see any complaints */
    h->debug = r_init_debug_getenv(h, "CCNR_DEBUG");
    res = r_init_parse_config(h, config, 1);
    if (res < 0) {
        h->running = -1;
        goto Bail;
    }
    r_init_parse_config(h, config, 2);
    sockname = r_net_get_local_sockname();
    h->skiplinks = ccn_indexbuf_create();
    h->face_limit = 10; /* soft limit */
    h->fdholder_by_fd = calloc(h->face_limit, sizeof(h->fdholder_by_fd[0]));
    param.finalize_data = h;
    param.finalize = &r_fwd_finalize_nameprefix;
    h->nameprefix_tab = hashtb_create(sizeof(struct nameprefix_entry), &param);
    param.finalize = 0; // PRUNED &r_fwd_finalize_propagating;
    h->propagating_tab = hashtb_create(sizeof(struct propagating_entry), &param);
    param.finalize = &r_proto_finalize_enum_state;
    h->enum_state_tab = hashtb_create(sizeof(struct enum_state), &param);
    h->min_stale = ~0;
    h->max_stale = 0;
    h->unsol = ccn_indexbuf_create();
    h->ticktock.descr[0] = 'C';
    h->ticktock.micros_per_base = 1000000;
    h->ticktock.gettime = &r_util_gettime;
    h->ticktock.data = h;
    h->sched = ccn_schedule_create(h, &h->ticktock);
    h->starttime = h->sec;
    h->starttime_usec = h->usec;
    h->oldformatcontentgrumble = 1;
    h->oldformatinterestgrumble = 1;
    h->cob_limit = 4201;
    h->start_write_scope_limit = r_init_confval(h, "CCNR_START_WRITE_SCOPE_LIMIT", 0, 3, 3);
    h->debug = 1; /* so that we see any complaints */
    h->debug = r_init_debug_getenv(h, "CCNR_DEBUG");
    h->syncdebug = r_init_debug_getenv(h, "CCNS_DEBUG");
    portstr = getenv("CCNR_STATUS_PORT");
    if (portstr == NULL || portstr[0] == 0 || strlen(portstr) > 10)
        portstr = "";
    h->portstr = portstr;
    ccnr_msg(h, "CCNR_DEBUG=%d CCNR_DIRECTORY=%s CCNR_STATUS_PORT=%s", h->debug, h->directory, h->portstr);
    listen_on = getenv("CCNR_LISTEN_ON");
    if (listen_on != NULL && listen_on[0] != 0)
        ccnr_msg(h, "CCNR_LISTEN_ON=%s", listen_on);
    
    if (ccnr_init_repo_keystore(h, NULL) < 0) {
        h->running = -1;
        goto Bail;
    }
    r_util_reseed(h);
    r_store_init(h);
    if (h->running == -1) goto Bail;
    while (h->active_in_fd >= 0) {
        r_dispatch_process_input(h, h->active_in_fd);
        r_store_trim(h, h->cob_limit);
        ccn_schedule_run(h->sched);
    }
    ccnr_msg(h, "Repository file is indexed");
    if (h->face0 == NULL) {
        struct fdholder *fdholder;
        fdholder = calloc(1, sizeof(*fdholder));
        if (dup2(open("/dev/null", O_RDONLY), 0) == -1)
            ccnr_msg(h, "stdin: %s", strerror(errno));
        fdholder->filedesc = 0;
        fdholder->flags = (CCNR_FACE_GG | CCNR_FACE_NORECV);
        r_io_enroll_face(h, fdholder);
    }
    ccnr_direct_client_start(h);
    d = getenv("CCNR_SKIP_VERIFY");
#if (CCN_API_VERSION >= 4004)
    if (d != NULL && strcmp(d, "1") == 0) {
        ccnr_msg(h, "CCNR_SKIP_VERIFY=%s", d);
        ccn_defer_verification(h->direct_client, 1);
    }
#endif
    if (ccn_connect(h->direct_client, NULL) != -1) {
        int af = 0;
        int bufsize;
        int flags;
        int fd;
        struct fdholder *fdholder;

        fd = ccn_get_connection_fd(h->direct_client);
        // Play a dirty trick here - if this wins, we can fix it right in the c lib later on...
        af = try_tcp_instead(fd);  
        flags = CCNR_FACE_CCND;
        if (af == AF_INET)
            flags |= CCNR_FACE_INET;
        else if (af == AF_INET6)
            flags |= CCNR_FACE_INET6;
        else
            flags |= CCNR_FACE_LOCAL;
        fdholder = r_io_record_fd(h, fd, "CCND", 5, flags);
        if (fdholder == NULL) abort();
        ccnr_uri_listen(h, h->direct_client, "ccnx:/%C1.M.S.localhost/%C1.M.SRV/repository",
                        &ccnr_answer_req, OP_SERVICE);
        ccnr_uri_listen(h, h->direct_client, "ccnx:/%C1.M.S.neighborhood/%C1.M.SRV/repository",
                        &ccnr_answer_req, OP_SERVICE);
        bufsize = r_init_confval(h, "CCNR_MIN_SEND_BUFSIZE", 1, 2097152, 16384);
        establish_min_send_bufsize(h, fd, bufsize);
    }
    else
        ccn_disconnect(h->direct_client); // Apparently ccn_connect error case needs work.
    if (1 == r_init_confval(h, "CCNS_ENABLE", 0, 1, 1)) {
        h->sync_plumbing = calloc(1, sizeof(struct sync_plumbing));
        h->sync_plumbing->ccn = h->direct_client;
        h->sync_plumbing->sched = h->sched;
        h->sync_plumbing->client_methods = &sync_client_methods;
        h->sync_plumbing->client_data = h;
        h->sync_base = SyncNewBaseForActions(h->sync_plumbing);
    }
    if (-1 == load_policy(h))
        goto Bail;
    r_net_listen_on(h, listen_on);
    ccnr_internal_client_start(h);
    r_proto_init(h);
    r_proto_activate_policy(h, h->parsed_policy);
    if (merge_files(h) == -1)
        r_init_fail(h, __LINE__, "Unable to merge additional repository data files.", errno);
    if (h->running == -1) goto Bail;
    if (h->sync_plumbing) {
        // Start sync running
        // returns < 0 if a failure occurred
        // returns 0 if the name updates should fully restart
        // returns > 0 if the name updates should restart at last fence
        res = h->sync_plumbing->sync_methods->sync_start(h->sync_plumbing, NULL);
        if (res < 0) {
            r_init_fail(h, __LINE__, "starting sync", res);
            abort();
        }
        else if (res > 0) {
            // XXX: need to work out details of starting from last fence.
            // By examination of code, SyncActions won't take this path
        }
    }
Bail:
    if (sockname)
        free(sockname);
    sockname = NULL;
    ccn_charbuf_destroy(&config);
    if (h->running == -1)
        r_init_destroy(&h);
    return(h);
}