Example #1
0
int input_instance_start_stop_handler(void *priv, struct ptype *run) {

	struct input *i = priv;

	char *new_state = PTYPE_BOOL_GETVAL(run);

	pom_mutex_lock(&i->lock);
	char cur_state = (i->running == INPUT_RUN_STOPPED ? 0 : 1);

	if (cur_state == *new_state) {
		pom_mutex_unlock(&i->lock);
		pomlog(POMLOG_ERR "Error, input is already %s", (cur_state ? "running" : "stopped"));
		return POM_ERR;
	}

	if (*new_state) {

		if (!(i->reg->info->flags & INPUT_REG_FLAG_LIVE)) {
			struct input *tmp;
			for (tmp = input_head; tmp; tmp = tmp->next) {
				if (tmp != i) {
					pom_mutex_lock(&tmp->lock);
					if (i->running) {
						pom_mutex_unlock(&tmp->lock);
						pom_mutex_unlock(&i->lock);
						pomlog(POMLOG_ERR "When using non-live input, it can only be started alone");
						return POM_ERR;
					}
					pom_mutex_unlock(&tmp->lock);
				}
			}
		}

		if (i->reg->info->open && i->reg->info->open(i) != POM_OK) {
			pomlog(POMLOG_ERR "Error while starting input %s", i->name);
			pom_mutex_unlock(&i->lock);
			return POM_ERR;
		}

		i->running = INPUT_RUN_RUNNING;
		pom_mutex_unlock(&i->lock);
		if (pthread_create(&i->thread, NULL, input_process_thread, (void*) i)) {
			pom_mutex_unlock(&i->lock);
			pomlog(POMLOG_ERR "Unable to start a new thread for input %s : %s", i->name, pom_strerror(errno));
			return POM_ERR;
		}

		input_cur_running++;

		if (input_cur_running == 1)
			core_set_state(core_state_running);
		
	} else {
		i->running = INPUT_RUN_STOPPING;
		pom_mutex_unlock(&i->lock);

		if (i->reg->info->interrupt && i->reg->info->interrupt(i) == POM_ERR) {
			pomlog(POMLOG_WARN "Warning : error while interrupting the read process of the input");
		}

		if (i->thread != pthread_self()) {
			if (pthread_join(i->thread, NULL))
				pomlog(POMLOG_WARN "Error while joining the input thread : %s", pom_strerror(errno));
		} else {
			if (pthread_detach(i->thread))
				pomlog(POMLOG_WARN "Error while detaching the input thread : %s", pom_strerror(errno));
		}

		input_cur_running--;

		if (!input_cur_running)
			core_set_state(core_state_finishing);
	}


	return POM_OK;

}
Example #2
0
File: core.c Project: k0a1a/pom-ng
void *core_processing_thread_func(void *priv) {

	struct core_processing_thread *tpriv = priv;

	if (packet_info_pool_init()) {
		halt("Error while initializing the packet_info_pool", 1);
		return NULL;
	}

	registry_perf_inc(perf_thread_active, 1);

	pom_mutex_lock(&tpriv->pkt_queue_lock);

	while (core_run) {
		
		while (!tpriv->pkt_queue_head) {
			// We are not active while waiting for a packet
			registry_perf_dec(perf_thread_active, 1);

			debug_core("thread %u : waiting", tpriv->thread_id);

			if (registry_perf_getval(perf_thread_active) == 0) {
				if (core_get_state() == core_state_finishing)
					core_set_state(core_state_idle);
			}

			if (!core_run) {
				pom_mutex_unlock(&tpriv->pkt_queue_lock);
				goto end;
			}

			int res = pthread_cond_wait(&tpriv->pkt_queue_cond, &tpriv->pkt_queue_lock);
			if (res) {
				pomlog(POMLOG_ERR "Error while waiting for restart condition : %s", pom_strerror(res));
				abort();
				return NULL;
			}
			registry_perf_inc(perf_thread_active, 1);
		}


		// Dequeue a packet
		struct core_packet_queue *tmp = tpriv->pkt_queue_head;
		tpriv->pkt_queue_head = tmp->next;
		if (!tpriv->pkt_queue_head)
			tpriv->pkt_queue_tail = NULL;


		// Add it to the unused list
		tmp->next = tpriv->pkt_queue_unused;
		tpriv->pkt_queue_unused = tmp;

		tpriv->pkt_count--;

		registry_perf_dec(perf_pkt_queue, 1);

		__sync_fetch_and_sub(&core_pkt_queue_count, 1);

		if (tpriv->pkt_count < CORE_THREAD_PKT_QUEUE_MIN) {

			pom_mutex_lock(&core_pkt_queue_wait_lock);
			// Tell the input processes that they can continue queuing packets
			int res = pthread_cond_broadcast(&core_pkt_queue_wait_cond);
			if (res) {
				pomlog(POMLOG_ERR "Error while signaling the main pkt_queue condition : %s", pom_strerror(res));
				abort();
			}
			pom_mutex_unlock(&core_pkt_queue_wait_lock);
		}

		// Keep track of our packet
		struct packet *pkt = tmp->pkt;

		debug_core("thread %u : Processing packet %p (%u.%06u)", tpriv->thread_id, pkt, pom_ptime_sec(pkt->ts), pom_ptime_usec(pkt->ts));
		pom_mutex_unlock(&tpriv->pkt_queue_lock);

		// Lock the processing lock
		pom_rwlock_rlock(&core_processing_lock);

		// Update the current clock
		if (core_clock[tpriv->thread_id] < pkt->ts) // Make sure we keep it monotonous
			core_clock[tpriv->thread_id] = pkt->ts;

		//pomlog(POMLOG_DEBUG "Thread %u processing ...", pthread_self());
		if (core_process_packet(pkt) == POM_ERR) {
			core_run = 0;
			pom_rwlock_unlock(&core_processing_lock);
			break;
		}

		// Process timers
		if (timers_process() != POM_OK) {
			pom_rwlock_unlock(&core_processing_lock);
			break;
		}

		pom_rwlock_unlock(&core_processing_lock);

		if (packet_release(pkt) != POM_OK) {
			pomlog(POMLOG_ERR "Error while releasing the packet");
			break;
		}
		
		debug_core("thread %u : Processed packet %p (%u.%06u)", tpriv->thread_id, pkt, pom_ptime_sec(pkt->ts), pom_ptime_usec(pkt->ts));
		// Re-lock our queue for the next run
		pom_mutex_lock(&tpriv->pkt_queue_lock);

	}

	halt("Processing thread encountered an error", 1);
end:
	packet_info_pool_cleanup();

	return NULL;
}
Example #3
0
void *core_processing_thread_func(void *priv) {

	struct core_processing_thread *tpriv = priv;

	pom_mutex_lock(&core_pkt_queue_mutex);

	while (core_run) {
		
		while (!core_pkt_queue_head && !tpriv->pkt_queue_head) {
			if (core_thread_active == 0) {
				if (core_get_state() == core_state_finishing)
					core_set_state(core_state_idle);
			}

			if (!core_run) {
				pom_mutex_unlock(&core_pkt_queue_mutex);
				return NULL;
			}

			if (pthread_cond_wait(&core_pkt_queue_restart_cond, &core_pkt_queue_mutex)) {
				pomlog(POMLOG_ERR "Error while waiting for restart condition : %s", pom_strerror(errno));
				// Should probably abort here
				return NULL;
			}

		}
		core_thread_active++;

		struct core_packet_queue *tmp = NULL;
		
		// Dequeue packets from our own queue first
		struct packet *pkt = NULL;
		if (tpriv->pkt_queue_head) {
			tmp = tpriv->pkt_queue_head;
			pkt = tmp->pkt;

			tpriv->pkt_queue_head = tmp->next;
			if (tpriv->pkt_queue_head)
				tpriv->pkt_queue_head->prev = NULL;
			else
				tpriv->pkt_queue_tail = NULL;

		} else {
			tmp = core_pkt_queue_head;
			pkt = tmp->pkt;

			// Remove the packet from the main queue
			core_pkt_queue_head = tmp->next;
			if (core_pkt_queue_head)
				core_pkt_queue_head->prev = NULL;
			else
				core_pkt_queue_tail = NULL;
		}

		// Add it to the unused list
		memset(tmp, 0, sizeof(struct core_packet_queue));
		tmp->next = core_pkt_queue_unused;
		if (tmp->next)
			tmp->next->prev = tmp;
		core_pkt_queue_unused = tmp;

		core_pkt_queue_usage--;

		pom_mutex_unlock(&core_pkt_queue_mutex);

		// Lock the processing thread
		if (pthread_rwlock_rdlock(&core_processing_lock)) {
			pomlog(POMLOG_ERR "Error while locking the processing lock : %s", pom_strerror(errno));
			abort();
			return NULL;
		}

		// Update the current clock
		pom_mutex_lock(&core_clock_lock);
		memcpy(&core_clock, &pkt->ts, sizeof(struct timeval));
		pom_mutex_unlock(&core_clock_lock);

		//pomlog(POMLOG_DEBUG "Thread %u processing ...", pthread_self());
		if (core_process_packet(pkt) == POM_ERR) {
			core_run = 0;
			halt("Packet processing encountered an error", 1);
			pthread_cond_broadcast(&core_pkt_queue_restart_cond);
			pthread_rwlock_unlock(&core_processing_lock);
			return NULL;
		}

		// Process timers
		if (timers_process() != POM_OK) {
			pthread_rwlock_unlock(&core_processing_lock);
			return NULL;
		}

		if (pthread_rwlock_unlock(&core_processing_lock)) {
			pomlog(POMLOG_ERR "Error while releasing the processing lock : %s", pom_strerror(errno));
			break;
		}

		if (packet_pool_release(pkt) != POM_OK) {
			pomlog(POMLOG_ERR "Error while releasing the packet to the pool");
			break;
		}
		
		pom_mutex_lock(&core_pkt_queue_mutex);
		if (pthread_cond_broadcast(&core_pkt_queue_restart_cond)) {
			pomlog(POMLOG_ERR "Error while signaling the done condition : %s", pom_strerror(errno));
			pom_mutex_unlock(&core_pkt_queue_mutex);
			break;

		}
		core_thread_active--;

	}
	pom_mutex_unlock(&core_pkt_queue_mutex);

	halt("Processing thread encountered an error", 1);
	return NULL;
}