/* ************************************************** */
int do_configuration(void) {
    xmlSchemaValidCtxtPtr sv_ctxt = NULL;
    xmlSchemaParserCtxtPtr sp_ctxt = NULL;
    xmlSchemaPtr schema = NULL;
    xmlParserCtxtPtr p_ctxt = NULL;
    xmlDocPtr doc = NULL;
    xmlXPathContextPtr xp_ctx = NULL; 
    xmlXPathObjectPtr simul_xobj = NULL;
    xmlXPathObjectPtr entity_xobj = NULL; 
    xmlXPathObjectPtr environment_xobj = NULL; 
    xmlXPathObjectPtr bundle_xobj = NULL; 
    xmlXPathObjectPtr node_xobj = NULL; 
    xmlNodeSetPtr nodeset;
    xmlpathobj_t xpathobj[] = {{&simul_xobj, (xmlChar *) XML_X_SIMULATION}, 
                               {&entity_xobj, (xmlChar *) XML_X_ENTITY},
                               {&environment_xobj, (xmlChar *) XML_X_ENVIRONMENT},
                               {&bundle_xobj, (xmlChar *) XML_X_BUNDLE},
                               {&node_xobj, (xmlChar *) XML_X_NODE}};
    int ok = 0, i;

    /* Check XML version */
    LIBXML_TEST_VERSION;
        
    /* Initialise and parse schema */
    sp_ctxt = xmlSchemaNewParserCtxt(schemafile);
    if (sp_ctxt == NULL) {
        fprintf(stderr, "config: XML schema parser initialisation failure (do_configuration())\n");
        ok = -1;
        goto cleanup;
    }
    xmlSchemaSetParserErrors(sp_ctxt,
                             (xmlSchemaValidityErrorFunc)   xml_error,
                             (xmlSchemaValidityWarningFunc) xml_warning,
                             NULL);
    
    schema = xmlSchemaParse(sp_ctxt);
    if (schema == NULL) {
        fprintf(stderr, "config: error in schema %s (do_configuration())\n", schemafile);
        ok = -1;
        goto cleanup;
    }
    xmlSchemaSetValidErrors(sv_ctxt,
                            (xmlSchemaValidityErrorFunc)   xml_error,
                            (xmlSchemaValidityWarningFunc) xml_warning,
                            NULL);
    
    sv_ctxt = xmlSchemaNewValidCtxt(schema);
    if (sv_ctxt == NULL) {
        fprintf(stderr, "config: XML schema validator initialisation failure (do_configuration())\n");
        ok = -1;
        goto cleanup;
    }
    
    /* Initialise and parse document */
    p_ctxt = xmlNewParserCtxt();
    if (p_ctxt == NULL) {
        fprintf(stderr, "config: XML parser initialisation failure (do_configuration())\n");
        ok = -1;
        goto cleanup;
    }
    
    doc = xmlCtxtReadFile(p_ctxt, configfile, NULL, XML_PARSE_NONET | XML_PARSE_NOBLANKS | XML_PARSE_NSCLEAN);
    if (doc == NULL) {
        fprintf(stderr, "config: failed to parse %s (do_configuration())\n", configfile);
        ok = -1;
        goto cleanup;
    }

    /* Validate document */
    if (xmlSchemaValidateDoc(sv_ctxt, doc)) {
        fprintf(stderr, "config: error in configuration file %s (do_configuration())\n", configfile);
        ok = -1;
        goto cleanup;
    }
    
    /* Create xpath context */
    xp_ctx = xmlXPathNewContext(doc);
    if (xp_ctx == NULL) {
        fprintf(stderr, "config: XPath initialisation failure (do_configuration())\n");
        ok = -1;
        goto cleanup;
    }
    xmlXPathRegisterNs(xp_ctx, (xmlChar *) XML_NS_ID, (xmlChar *) XML_NS_URL); 
    
    
    /* Get xpath obj */
    for (i = 0 ; i < (int) (sizeof(xpathobj) / sizeof(xpathobj[0])); i++) {
        *xpathobj[i].ptr = xmlXPathEvalExpression(xpathobj[i].expr, xp_ctx);
        if (*xpathobj[i].ptr == NULL) {
            fprintf(stderr, "config: unable to evaluate xpath \"%s\" (do_configuration())\n", xpathobj[i].expr);
            ok = -1;
            goto cleanup;
            
        }
    }

    /***************/
    /* Counting... */
    /***************/
    nodeset = entity_xobj->nodesetval;
    if ((entities.size = (nodeset) ? nodeset->nodeNr : 0) == 0) {
        fprintf(stderr, "config: no entity defined (do_configuration())\n");
        ok = -1; 
        goto cleanup;
    }
    fprintf(stderr, "\nFound %d entities...\n", entities.size);
    nodeset = environment_xobj->nodesetval;
    if (((nodeset) ? nodeset->nodeNr : 0) == 0) {
        fprintf(stderr, "config: no environment defined (do_configuration())\n");
        ok = -1; 
        goto cleanup;
    }
    fprintf(stderr, "Found 1 environment...\n");
    nodeset = bundle_xobj->nodesetval;
    if ((bundles.size = (nodeset) ? nodeset->nodeNr : 0) == 0) {
        fprintf(stderr, "config: no bundle defined (do_configuration())\n");
        ok = -1; 
        goto cleanup;
    }
    fprintf(stderr, "Found %d bundles...\n", bundles.size);
    

    if ((dflt_params = das_create()) == NULL) {
        ok = -1; 
        goto cleanup;
    }

    /**************/
    /* Simulation */
    /**************/
    if (parse_simulation(simul_xobj->nodesetval)) {
        ok = -1;
        goto cleanup;
    }
                                                          
    /**********/
    /* Entity */
    /**********/
    /* initialize library paths */
    config_set_usr_modulesdir();
    user_path_list = g_strsplit(user_modulesdir, ":", 0); /* TOCLEAN */
    sys_path_list = g_strsplit(sys_modulesdir, ":", 0); /* TOCLEAN */

    /* parse */
    if (parse_entities(entity_xobj->nodesetval)) {
        ok = -1;
        goto cleanup;
    }

    /**************/
    /* Measure    */
    /**************/
    if (parse_measure()) {
        ok = -1;
        goto cleanup;
    }

    /***************/
    /* Environment */
    /***************/
    if (parse_environment(environment_xobj->nodesetval)) {
        ok = -1;
        goto cleanup;
    }
    
    /***************/
    /* Bundle      */
    /***************/
    if (parse_bundles(bundle_xobj->nodesetval)) {
        ok = -1;
        goto cleanup;
    }

    /***************/
    /* Nodes      */
    /***************/
    if (parse_nodes(node_xobj->nodesetval)) {
        ok = -1;
        goto cleanup;
    }
 
    /* edit by Quentin Lampin <*****@*****.**> */
    gchar **path = NULL;
    for (path = user_path_list ; *path ; path++) {
        g_free(*path);
    }
    path = NULL;
    for (path = sys_path_list  ; *path ; path++) {
        g_free(*path);
    }
    /* end of edition */

 cleanup:
    clean_params();
    
    for (i = 0 ; i < (int) (sizeof(xpathobj) / sizeof(xpathobj[0])); i++) {
        xmlXPathFreeObject(*xpathobj[i].ptr);
    }

    if (xp_ctx) {
        xmlXPathFreeContext(xp_ctx);
    }

    if (sp_ctxt) {
        xmlSchemaFreeParserCtxt(sp_ctxt);		
    }

    if (schema) {
        xmlSchemaFree(schema);
    }

    if (sv_ctxt) {
        xmlSchemaFreeValidCtxt(sv_ctxt);
    }

    if (doc) {
        xmlFreeDoc(doc);
    }

    if (p_ctxt) {
        xmlFreeParserCtxt(p_ctxt);
    }

    xmlCleanupParser();
    return ok;
}
示例#2
0
/* Main
 */
int main (int argc, char *argv[])
{
	int ret, nth;
	long dur;

	/* Initialize the measure list */
	mes_t sentinel;
	mes_t *m_cur, *m_tmp;
	m_cur = &sentinel;
	m_cur->next = NULL;

	/* Initialize the output */
	output_init();

	/* Test machine capabilities */
	/* -> clockid_t; pshared; ... */
	altclk_ok = sysconf(_SC_CLOCK_SELECTION);
	if (altclk_ok > 0)
		altclk_ok = sysconf(_SC_MONOTONIC_CLOCK);
	#ifndef USE_ALTCLK
	if (altclk_ok > 0)
		output("Implementation supports the MONOTONIC CLOCK but option is disabled in test.\n");
	#endif

	pshared_ok = sysconf(_SC_THREAD_PROCESS_SHARED);

	#if VERBOSE > 0
	output("Test starting\n");
	output(" Process-shared primitive %s be tested\n", (pshared_ok>0)?"will":"won't");
	output(" Alternative clock for cond %s be tested\n", (altclk_ok>0)?"will":"won't");
	#endif

	/* Prepare thread attribute */
	ret = pthread_attr_init(&ta);
	if (ret != 0)  {  UNRESOLVED(ret, "Unable to initialize thread attributes");  }

	ret = pthread_attr_setstacksize(&ta, sysconf(_SC_THREAD_STACK_MIN));
	if (ret != 0)
	{  UNRESOLVED(ret, "Unable to set stack size to minimum value");  }

	#ifdef PLOT_OUTPUT
	output("# COLUMNS %d #threads", NSCENAR + 1);
	for (nth=0; nth<NSCENAR; nth++)
		output(" %s", test_scenar[nth].desc);
	output("\n");
	#endif

	/* Do the testing */
	nth = 0;
	do
	{
		nth += 100 * SCALABILITY_FACTOR;

		/* Create a new measure item */
		m_tmp = (mes_t *) malloc(sizeof(mes_t));
		if (m_tmp == NULL) { UNRESOLVED(errno, "Unable to alloc memory for measure saving");  }
		m_tmp->nthreads = nth;
		m_tmp->next = NULL;

		/* Run the test */
		dur = do_threads_test(nth, m_tmp);

		/* If test was success, add this measure to the list. Otherwise, free the mem */
		if (dur >= 0)
		{
			m_cur->next = m_tmp;
			m_cur = m_tmp;
		}
		else
		{
			free(m_tmp);
		}
	}
	while (dur >= 0);

	/* We will now parse the results to determine if the measure is ~ constant or is growing. */

	ret = parse_measure(&sentinel);

	/* Free the memory from the list */
	m_cur = sentinel.next;
	while (m_cur != NULL)
	{
		m_tmp = m_cur;
		m_cur = m_tmp->next;
		free(m_tmp);
	}

	if (ret != 0)
	{
		FAILED("This function is not scalable");
	}

	#if VERBOSE > 0
	output("The function is scalable\n");
	#endif

	PASSED;
}
示例#3
0
int main (int argc, char *argv[])
{
	int ret, status;
	pid_t pidctl;
	pid_t *pr;

	int nprocesses, i;

	struct timespec ts_ref, ts_fin;

	mes_t sentinel;
	mes_t *m_cur, *m_tmp;

	long CHILD_MAX = sysconf(_SC_CHILD_MAX);
	long my_max = 1000 * SCALABILITY_FACTOR ;

	/* Initialize the measure list */
	m_cur = &sentinel;
	m_cur->next = NULL;

	/* Initialize output routine */
	output_init();

	if (CHILD_MAX > 0)
		my_max = CHILD_MAX;

	pr = (pid_t *) calloc(1 + my_max, sizeof(pid_t));

	if (pr == NULL)
	{
		UNRESOLVED(errno, "Not enough memory for process IDs storage");
	}

#if VERBOSE > 1
	output("CHILD_MAX: %d\n", CHILD_MAX);

#endif

#ifdef PLOT_OUTPUT
	output("# COLUMNS 2 #Process Duration\n");

#endif

	/* Initilaize the semaphores */
	sem_synchro = sem_open("/fork_scal_sync", O_CREAT, O_RDWR, 0);

	if (sem_synchro == SEM_FAILED)
	{
		UNRESOLVED(errno, "Failed to open a named semaphore\n");
	}

	sem_unlink("/fork_scal_sync");

	sem_ending = sem_open("/fork_scal_end", O_CREAT, O_RDWR, 0);

	if (sem_ending == SEM_FAILED)
	{
		UNRESOLVED(errno, "Failed to open a named semaphore\n");
	}

	sem_unlink("/fork_scal_end");

	nprocesses = 0;
	m_cur = &sentinel;

	while (1)                                      /* we will break */
	{
		/* read clock */
		ret = clock_gettime(CLOCK_REALTIME, &ts_ref);

		if (ret != 0)
		{
			UNRESOLVED(errno, "Unable to read clock");
		}

		/* create a new child */
		pr[nprocesses] = fork();

		if (pr[nprocesses] == -1)
		{
			if (errno == EAGAIN || errno == ENOMEM)
				break;

			FAILED("Failed to fork and received an unexpected error");
			/* Post the semaphore so running processes will terminate */

			do {
				ret = sem_post(sem_ending);
			} while (ret != 0 && errno == EINTR);

			if (ret != 0)
				output("Failed to post the semaphore on termination: error %d\n", errno);

		}

		if (pr[nprocesses] == 0) {
			/* Child */
			/* Post the synchro semaphore*/

			do {
				ret = sem_post(sem_synchro);
			} while ((ret != 0) && (errno == EINTR));

			if (ret != 0)
			{
				/* In this case the test will hang... */
				UNRESOLVED(errno, "Failed post the sync semaphore");
			}

			/* Wait the end semaphore */
			do {
				ret = sem_wait(sem_ending);
			} while ((ret != 0) && (errno == EINTR));

			if (ret != 0)
			{
				UNRESOLVED(errno, "Failed wait for the end semaphore");
			}

			/* Cascade-post the end semaphore */
			do
			{
				ret = sem_post(sem_ending);
			} while ((ret != 0) && (errno == EINTR));

			if (ret != 0)
			{
				UNRESOLVED(errno, "Failed post the end semaphore");
			}

			/* Exit */
			exit(PTS_PASS);
		}

		/* Parent */
		nprocesses++;

		/* FAILED if nprocesses > CHILD_MAX */
		if (nprocesses > my_max)
		{
			errno = 0;

			if (CHILD_MAX > 0)
			{
#if VERBOSE > 0
				output("WARNING! We were able to create more than CHILD_MAX processes\n");
#endif

			}

			break;
		}

		/* wait for the semaphore */
		do {
			ret = sem_wait(sem_synchro);
		} while ((ret == -1) && (errno == EINTR));

		if (ret == -1)
		{
			sem_post(sem_ending);
			UNRESOLVED(errno, "Failed to wait for the sync semaphore");
		}

		/* read clock */
		ret = clock_gettime(CLOCK_REALTIME, &ts_fin);

		if (ret != 0)
		{
			UNRESOLVED(errno, "Unable to read clock");
		}

		/* add to the measure list if nprocesses % resolution == 0 */
		if (((nprocesses % RESOLUTION) == 0) && (nprocesses != 0))
		{
			/* Create an empty new element */
			m_tmp = (mes_t *) malloc(sizeof(mes_t));

			if (m_tmp == NULL)
			{
				sem_post(sem_ending);
				UNRESOLVED(errno, "Unable to alloc memory for measure saving");
			}

			m_tmp->nprocess = nprocesses;
			m_tmp->next = NULL;
			m_tmp->_data = 0;
			m_cur->next = m_tmp;

			m_cur = m_cur->next;

			m_cur->_data = ((ts_fin.tv_sec - ts_ref.tv_sec) * 1000000) + ((ts_fin.tv_nsec - ts_ref.tv_nsec) / 1000) ;

#if VERBOSE > 5
			output("Added the following measure: n=%i, v=%li\n", nprocesses, m_cur->_data);
#endif

		}

	}
#if VERBOSE > 3

	if (errno)
		output("Could not create anymore processes. Current count is %i\n", nprocesses);
	else
		output("Should not create anymore processes. Current count is %i\n", nprocesses);

#endif

	/* Unblock every created children: post once, then cascade signaling */

	do
	{
		ret = sem_post(sem_ending);
	}
	while ((ret != 0) && (errno == EINTR));

	if (ret != 0)
	{
		UNRESOLVED(errno, "Failed post the end semaphore");
	}

#if VERBOSE > 3
	output("Waiting children termination\n");

#endif

	for (i = 0; i < nprocesses; i++)
	{
		pidctl = waitpid(pr[ i ], &status, 0);

		if (pidctl != pr[ i ])
		{
			UNRESOLVED(errno, "Waitpid returned the wrong PID");
		}

		if ((!WIFEXITED(status)) || (WEXITSTATUS(status) != PTS_PASS))
		{
			FAILED("Child exited abnormally");
		}

	}

	/* Free some memory before result parsing */
	free(pr);

	/* Compute the results */
	ret = parse_measure(&sentinel);

	/* Free the resources and output the results */

#if VERBOSE > 5
	output("Dump : \n");

	output("  nproc  |  dur  \n");

#endif
	while (sentinel.next != NULL)
	{
		m_cur = sentinel.next;
#if (VERBOSE > 5) || defined(PLOT_OUTPUT)
		output("%8.8i %1.1li.%6.6li\n", m_cur->nprocess, m_cur->_data / 1000000, m_cur->_data % 1000000);

#endif
		sentinel.next = m_cur->next;

		free(m_cur);
	}

	if (ret != 0)
	{
		FAILED("The function is not scalable, add verbosity for more information");
	}

#if VERBOSE > 0
	output("-----\n");

	output("All test data destroyed\n");

	output("Test PASSED\n");

#endif

	PASSED;
}
示例#4
0
int main (int argc, char *argv[])
{
	int ret=0;
	pthread_t child;
	pthread_t *th;

	int nthreads, ctl, i, tmp;

	struct timespec ts_ref, ts_fin;

	mes_t sentinel;
	mes_t *m_cur, *m_tmp;

	long PTHREAD_THREADS_MAX = sysconf(_SC_THREAD_THREADS_MAX);
	long my_max = 1000 * SCALABILITY_FACTOR ;

	/* Initialize the measure list */
	m_cur = &sentinel;
	m_cur->next = NULL;

	/* Initialize output routine */
	output_init();

	if (PTHREAD_THREADS_MAX > 0)
		my_max = PTHREAD_THREADS_MAX;

	th = (pthread_t *)calloc(1 + my_max, sizeof(pthread_t));
	if (th == NULL)  {  UNRESOLVED(errno, "Not enough memory for thread storage");  }

	/* Initialize thread attribute objects */
	scenar_init();

	#ifdef PLOT_OUTPUT
	printf("# COLUMNS %d #threads", NSCENAR + 1);
	for (sc=0; sc<NSCENAR; sc++)
		printf(" %i", sc);
	printf("\n");
	#endif

	for (sc=0; sc < NSCENAR; sc++)
	{
		if (scenarii[sc].bottom == NULL) /* skip the alternate stacks as we could create only 1 */
		{
			#if VERBOSE > 0
			output("-----\n");
			output("Starting test with scenario (%i): %s\n", sc, scenarii[sc].descr);
			#endif

			/* Block every (about to be) created threads */
			ret = pthread_mutex_lock(&m_synchro);
			if (ret != 0)  {  UNRESOLVED(ret, "Mutex lock failed");  }

			ctl=0;
			nthreads=0;
			m_cur = &sentinel;

			/* Create 1 thread for testing purpose */
			ret = pthread_create(&child, &scenarii[sc].ta, threaded, &ctl);
			switch (scenarii[sc].result)
			{
				case 0: /* Operation was expected to succeed */
					if (ret != 0)  {  UNRESOLVED(ret, "Failed to create this thread");  }
					break;

				case 1: /* Operation was expected to fail */
					if (ret == 0)  {  UNRESOLVED(-1, "An error was expected but the thread creation succeeded");  }
					break;

				case 2: /* We did not know the expected result */
				default:
					#if VERBOSE > 0
					if (ret == 0)
						{ output("Thread has been created successfully for this scenario\n"); }
					else
						{ output("Thread creation failed with the error: %s\n", strerror(ret)); }
					#endif
					;
			}
			if (ret == 0) /* The new thread is running */
			{

				while (1) /* we will break */
				{
					/* read clock */
					ret = clock_gettime(CLOCK_REALTIME, &ts_ref);
					if (ret != 0)  {  UNRESOLVED(errno, "Unable to read clock");  }

					/* create a new thread */
					ret = pthread_create(&th[nthreads], &scenarii[sc].ta, threaded, &ctl);

					/* stop here if we've got EAGAIN */
					if (ret == EAGAIN)
						break;

// temporary hack
if (ret == ENOMEM)  break;
					nthreads++;

					/* FAILED if error is != EAGAIN or nthreads > PTHREAD_THREADS_MAX */
					if (ret != 0)
					{
						output("pthread_create returned: %i (%s)\n", ret, strerror(ret));
						FAILED("pthread_create did not return EAGAIN on a lack of resource");
					}
					if (nthreads > my_max)
					{
						if (PTHREAD_THREADS_MAX > 0)
						{
							FAILED("We were able to create more than PTHREAD_THREADS_MAX threads");
						}
						else
						{
							break;
						}
					}

					/* wait for the semaphore */
					do { ret = sem_wait(&scenarii[sc].sem); }
					while ((ret == -1) && (errno == EINTR));
					if (ret == -1)  {  UNRESOLVED(errno, "Failed to wait for the semaphore");  }

					/* read clock */
					ret = clock_gettime(CLOCK_REALTIME, &ts_fin);
					if (ret != 0)  {  UNRESOLVED(errno, "Unable to read clock");  }

					/* add to the measure list if nthreads % resolution == 0 */
					if ((nthreads % RESOLUTION) == 0)
					{
						if (m_cur->next == NULL)
						{
							/* Create an empty new element */
							m_tmp = (mes_t *) malloc(sizeof(mes_t));
							if (m_tmp == NULL) { UNRESOLVED(errno, "Unable to alloc memory for measure saving");  }
							m_tmp->nthreads = nthreads;
							m_tmp->next = NULL;
							for (tmp=0; tmp<NSCENAR; tmp++)
								m_tmp->_data[tmp]= 0;
							m_cur->next = m_tmp;
						}

						/* Add this measure to the next element */
						m_cur = m_cur->next;
						m_cur->_data[sc] = ((ts_fin.tv_sec - ts_ref.tv_sec) * 1000000) + ((ts_fin.tv_nsec - ts_ref.tv_nsec) / 1000) ;

						#if VERBOSE > 5
						output("Added the following measure: sc=%i, n=%i, v=%li\n", sc, nthreads, m_cur->_data[sc]);
						#endif
					}
				}
				#if VERBOSE > 3
				output("Could not create anymore thread. Current count is %i\n", nthreads);
				#endif

				/* Unblock every created threads */
				ret = pthread_mutex_unlock(&m_synchro);
				if (ret != 0)  {  UNRESOLVED(ret, "Mutex unlock failed");  }

				if (scenarii[sc].detached == 0)
				{
					#if VERBOSE > 3
					output("Joining the threads\n");
					#endif
					for (i = 0; i < nthreads; i++)
					{
						ret = pthread_join(th[i], NULL);
						if (ret != 0)  {  UNRESOLVED(ret, "Unable to join a thread");  }
					}

					ret = pthread_join(child, NULL);
					if (ret != 0)  {  UNRESOLVED(ret, "Unalbe to join a thread");  }

				}
				#if VERBOSE > 3
				output("Waiting for threads (almost) termination\n");
				#endif
				do {
					ret = pthread_mutex_lock(&m_synchro);
					if (ret != 0)  {  UNRESOLVED(ret, "Mutex lock failed");  }

					tmp = ctl;

					ret = pthread_mutex_unlock(&m_synchro);
					if (ret != 0)  {  UNRESOLVED(ret, "Mutex unlock failed");  }
				} while (tmp != nthreads + 1);

			} /* The thread was created */

	}	} /* next scenario */

	/* Free some memory before result parsing */
	free(th);

	/* Compute the results */
	ret = parse_measure(&sentinel);

	/* Free the resources and output the results */

	#if VERBOSE > 5
	printf("Dump : \n");
	printf("%8.8s", "nth");
	for (i = 0; i<NSCENAR; i++)
		printf("|   %2.2i   ", i);
	printf("\n");
	#endif
	while (sentinel.next != NULL)
	{
		m_cur = sentinel.next;
		#if (VERBOSE > 5) || defined(PLOT_OUTPUT)
		printf("%8.8i", m_cur->nthreads);
		for (i=0; i<NSCENAR; i++)
			printf(" %1.1li.%6.6li", m_cur->_data[i] / 1000000, m_cur->_data[i] % 1000000);
		printf("\n");
		#endif
		sentinel.next = m_cur->next;
		free(m_cur);
	}

	scenar_fini();

	#if VERBOSE > 0
	output("-----\n");
	output("All test data destroyed\n");
	output("Test PASSED\n");
	#endif

	PASSED;
}