QUARK  0.9.0
QUARK-QUeuingAndRuntimeforKernels
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Groups
quark.c File Reference
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <limits.h>
#include <errno.h>
#include <pthread.h>
#include "icl_list.h"
#include "icl_hash.h"
#include "bsd_queue.h"
#include "bsd_tree.h"
#include "quark.h"
#include "quark_unpack_args.h"
#include "quark_trace.h"
Include dependency graph for quark.c:

Go to the source code of this file.

Data Types

struct  quark_s
struct  Quark_sequence_s
struct  worker_s
struct  quark_task_s
struct  dependency_s
struct  scratch_s
struct  address_set_node_s
struct  ll_list_node_s
struct  completed_tasks_node_s
struct  task_priority_tree_node_s

Macros

#define inline   __inline
#define fopen(ppfile, name, mode)   *ppfile = fopen(name, mode)
#define ULLONG_MAX   18446744073709551615ULL
#define tasklevel_width_max_level   5000
#define DEPCOLOR   "black"
#define DEPCOLOR_R_FIRST   "black"
#define DEPCOLOR_W_FIRST   "black"
#define DEPCOLOR_RAR   "black"
#define DEPCOLOR_WAW   "black"
#define DEPCOLOR_RAW   "black"
#define DEPCOLOR_WAR   "red"
#define DEPCOLOR_GATHERV   "green"
#define DOT_DAG_FILENAME   "dot_dag_file.dot"
#define dot_dag_print_edge(quark, parentid, parent_level, childid, child_level, color)
#define quark_atomic_add(pval, addvalue, pmutex)
#define quark_atomic_set(pval, setvalue, pmutex)
#define quark_atomic_get(retval, pval, pmutex)

Typedefs

typedef struct worker_s Worker
typedef struct quark_task_s Task
typedef struct dependency_s Dependency
typedef struct scratch_s Scratch
typedef struct address_set_node_s Address_Set_Node
typedef struct ll_list_node_s ll_list_node_t
typedef struct ll_list_head_s ll_list_head_t
typedef struct
completed_tasks_node_s 
completed_tasks_node_t
typedef struct
completed_tasks_head_s 
completed_tasks_head_t
typedef struct
task_priority_tree_node_s 
task_priority_tree_node_t
typedef struct
task_priority_tree_head_s 
task_priority_tree_head_t

Enumerations

enum  task_status {
  ALLOCATED_ONLY, NOTREADY, QUEUED, RUNNING,
  DONE, CANCELLED
}
enum  bool { FALSE, TRUE }
enum  worker_status { WORKER_SLEEPING, WORKER_NOT_SLEEPING }

Functions/Subroutines

 LIST_HEAD (ll_list_head_s, ll_list_node_s)
 TAILQ_HEAD (completed_tasks_head_s, completed_tasks_node_s)
 RB_HEAD (task_priority_tree_head_s, task_priority_tree_node_s)
 RB_GENERATE (task_priority_tree_head_s, task_priority_tree_node_s, n_entry, compare_task_priority_tree_nodes)
int quark_setaffinity (int rank)
void quark_topology_init ()
void quark_topology_finalize ()
int quark_get_numthreads ()
int * quark_get_affthreads ()
int quark_yield ()
int quark_getenv_int (char *name, int defval)
void quark_warning (const char *func_name, char *msg_text)
int QUARK_Thread_Rank (Quark *quark)
void * QUARK_Args_List (Quark *quark)
int QUARK_Get_RankInTask (Quark *quark)
void * QUARK_Args_Pop (void *args_list, void **last_arg)
QuarkQUARK_Setup (int num_threads)
QuarkQUARK_New (int num_threads)
void QUARK_Barrier (Quark *quark)
void QUARK_Waitall (Quark *quark)
void QUARK_Free (Quark *quark)
void QUARK_Delete (Quark *quark)
Taskquark_set_task_flags_in_task_structure (Quark *quark, Task *task, Quark_Task_Flags *task_flags)
TaskQUARK_Task_Init (Quark *quark, void(*function)(Quark *), Quark_Task_Flags *task_flags)
void QUARK_Task_Pack_Arg (Quark *quark, Task *task, int arg_size, void *arg_ptr, int arg_flags)
unsigned long long QUARK_Insert_Task_Packed (Quark *quark, Task *task)
unsigned long long QUARK_Insert_Task (Quark *quark, void(*function)(Quark *), Quark_Task_Flags *task_flags,...)
unsigned long long QUARK_Execute_Task (Quark *quark, void(*function)(Quark *), Quark_Task_Flags *task_flags,...)
int QUARK_Cancel_Task (Quark *quark, unsigned long long taskid)
void quark_avoid_war_dependencies (Quark *quark, Address_Set_Node *asn_old, Task *parent_task)
void QUARK_Worker_Loop (Quark *quark, int thread_rank)
Quark_SequenceQUARK_Sequence_Create (Quark *quark)
int QUARK_Sequence_Cancel (Quark *quark, Quark_Sequence *sequence)
Quark_SequenceQUARK_Sequence_Destroy (Quark *quark, Quark_Sequence *sequence)
int QUARK_Sequence_Wait (Quark *quark, Quark_Sequence *sequence)
Quark_SequenceQUARK_Get_Sequence (Quark *quark)
int QUARK_Get_Priority (Quark *quark)
char * QUARK_Get_Task_Label (Quark *quark)
Quark_Task_FlagsQUARK_Task_Flag_Set (Quark_Task_Flags *task_flags, int flag, intptr_t val)
intptr_t QUARK_Task_Flag_Get (Quark *quark, int flag)
void QUARK_DOT_DAG_Enable (Quark *quark, int enable)

Variables

FILE * dot_dag_file = NULL

Detailed Description

QUARK (QUeuing And Runtime for Kernels) provides a runtime enviornment for the dynamic execution of precedence-constrained tasks.

QUARK is a software package provided by Univ. of Tennessee, Univ. of California Berkeley and Univ. of Colorado Denver.

Version:
2.4.5
Author:
Asim YarKhan
Date:
2010-11-15

Definition in file quark.c.


Macro Definition Documentation

#define DEPCOLOR   "black"

Definition at line 324 of file quark.c.

#define DEPCOLOR_GATHERV   "green"

Definition at line 331 of file quark.c.

#define DEPCOLOR_R_FIRST   "black"

Definition at line 325 of file quark.c.

#define DEPCOLOR_RAR   "black"

Definition at line 327 of file quark.c.

#define DEPCOLOR_RAW   "black"

Definition at line 329 of file quark.c.

#define DEPCOLOR_W_FIRST   "black"

Definition at line 326 of file quark.c.

#define DEPCOLOR_WAR   "red"

Definition at line 330 of file quark.c.

#define DEPCOLOR_WAW   "black"

Definition at line 328 of file quark.c.

#define DOT_DAG_FILENAME   "dot_dag_file.dot"

Definition at line 332 of file quark.c.

#define dot_dag_print_edge (   quark,
  parentid,
  parent_level,
  childid,
  child_level,
  color 
)
Value:
if ( quark->dot_dag_enable ) { \
pthread_mutex_lock_wrap( &quark->dot_dag_mutex ); \
if ( parentid>0 ) fprintf(dot_dag_file, "t%lld->t%lld [color=\"%s\"];\n", parentid, childid, color); \
fflush(dot_dag_file); \
child_level = (parent_level+1 <= child_level ? child_level : parent_level+1 ); \
pthread_mutex_unlock_wrap( &quark->dot_dag_mutex ); \
}

Definition at line 334 of file quark.c.

#define fopen (   ppfile,
  name,
  mode 
)    *ppfile = fopen(name, mode)

Definition at line 73 of file quark.c.

#define inline   __inline

Definition at line 65 of file quark.c.

#define quark_atomic_add (   pval,
  addvalue,
  pmutex 
)
Value:
{ \
pthread_mutex_lock_atomic_add(pmutex); pval += addvalue; pthread_mutex_unlock_atomic(pmutex); \
/* pval += addvalue; */ \
}

Define a macro to add to value. Setup to shorten some code by locking/unlocking a mutex around the operation.

Definition at line 348 of file quark.c.

#define quark_atomic_get (   retval,
  pval,
  pmutex 
)
Value:
{ \
/* pthread_mutex_lock_atomic_get(pmutex); retval = pval; pthread_mutex_unlock_atomic(pmutex); */\
retval = pval; \
}

Define a macro get a value. Setup to shorten some code by locking/unlocking a mutex around the operation. Can disable the mutex for performance, since the exact current value of the variable is not needed. The variables used here are declared volatile, and can lag behind the real value without a loss of accuracy.

Definition at line 373 of file quark.c.

#define quark_atomic_set (   pval,
  setvalue,
  pmutex 
)
Value:
{ \
pthread_mutex_lock_atomic_set(pmutex); pval = setvalue; pthread_mutex_unlock_atomic(pmutex); \
/* pval = setvalue; */ \
}

Define a macro to set a value. Setup to shorten some code by locking/unlocking a mutex around the operation.

Definition at line 359 of file quark.c.

#define tasklevel_width_max_level   5000

Definition at line 129 of file quark.c.

#define ULLONG_MAX   18446744073709551615ULL

Definition at line 99 of file quark.c.


Typedef Documentation

typedef struct completed_tasks_head_s completed_tasks_head_t

Definition at line 234 of file quark.c.

typedef struct dependency_s Dependency
typedef struct ll_list_head_s ll_list_head_t

Definition at line 226 of file quark.c.

typedef struct scratch_s Scratch
typedef struct quark_task_s Task
typedef struct task_priority_tree_head_s task_priority_tree_head_t

Definition at line 244 of file quark.c.

typedef struct worker_s Worker

Enumeration Type Documentation

enum bool
Enumerator:
FALSE 
TRUE 

Definition at line 103 of file quark.c.

Enumerator:
ALLOCATED_ONLY 
NOTREADY 
QUEUED 
RUNNING 
DONE 
CANCELLED 

Definition at line 102 of file quark.c.

Enumerator:
WORKER_SLEEPING 
WORKER_NOT_SLEEPING 

Definition at line 104 of file quark.c.


Function/Subroutine Documentation

LIST_HEAD ( ll_list_head_s  ,
ll_list_node_s   
)
void quark_avoid_war_dependencies ( Quark quark,
Address_Set_Node asn_old,
Task parent_task 
)

Routine to avoid false (WAR write-after-read) dependencies by making copies of the data. Check if there are suffient INPUTS in the beginning of a address dependency followed by a OUTPUT or an INOUT (data<-RRRRW). If so, make a copy of the data, adjust the pointers of the read dependencies to point to the new copy (copy<-RRRR and data<-W) and send to workers if the tasks are ready. The copy can be automacally freed when all the reads are done. The write can proceed at once. The asn_old->asn_mutex is already locked when this is called.

Definition at line 1565 of file quark.c.

References dependency_s::address, address_set_node_s::address, quark_s::address_set, quark_s::address_set_mutex, dependency_s::address_set_node_ptr, dependency_s::address_set_waiting_deps_node_ptr, icl_list_s::data, address_set_node_s::delete_data_at_address_when_node_is_deleted, DEPCOLOR, dependency_s::direction, DONE, dot_dag_print_edge, FALSE, icl_hash_insert(), icl_list_append(), icl_list_delete(), icl_list_first(), icl_list_next(), INOUT, INPUT, quark_s::low_water_mark, NOTREADY, quark_task_s::num_dependencies_remaining, quark_s::num_queued_tasks, quark_s::num_queued_tasks_mutex, quark_s::num_tasks, quark_s::num_threads, OUTPUT, quark_atomic_get, quark_getenv_int(), dependency_s::ready, address_set_node_s::size, quark_task_s::status, dependency_s::task, dependency_s::task_args_list_node_ptr, quark_task_s::task_mutex, quark_task_s::taskid, quark_task_s::tasklevel, TRUE, address_set_node_s::waiting_deps, and quark_s::war_dependencies_enable.

{
/* Quick return if this is not enabled */
if ( !quark->war_dependencies_enable ) return;
/* Figure out if there are enough input dependencies to make this worthwhile */
int count_initial_input_deps = 0;
bool output_dep_reached = FALSE;
int quark_num_queued_tasks;
quark_atomic_get( quark_num_queued_tasks, quark->num_queued_tasks, &quark->num_queued_tasks_mutex );
double avg_queued_tasks_per_thread = (double)quark_num_queued_tasks/(double)quark->num_threads;
double avg_tasks_per_thread = (double)quark->num_tasks/(double)quark->num_threads;
int min_input_deps;
icl_list_t *dep_node_old;
/* This stuff is still under development.... */
if ( avg_queued_tasks_per_thread < 0.4 ) min_input_deps = 1;
else if ( avg_queued_tasks_per_thread < 0.75 ) min_input_deps = 6;
else if ( avg_queued_tasks_per_thread < 0.90 ) min_input_deps = 7;
else if ( avg_queued_tasks_per_thread < 1.20 ) min_input_deps = 10;
else if ( avg_queued_tasks_per_thread > 1.80 ) min_input_deps = 2000;
else if ( avg_tasks_per_thread < (double)quark->low_water_mark/(double)quark->num_threads/2 ) min_input_deps = 2000;
else min_input_deps = (int)(7 + 27 * avg_queued_tasks_per_thread);
/* Override computed value using environment variable */
min_input_deps = quark_getenv_int( "QUARK_AVOID_WAR_WHEN_NUM_WAITING_READS", min_input_deps );
/* Scan thru initial deps, make sure they are inputs and that there
* are enough of them to make data copying worthwhile */
for (dep_node_old=icl_list_first(asn_old->waiting_deps);
dep_node_old!=NULL;
dep_node_old=icl_list_next(asn_old->waiting_deps, dep_node_old)) {
Dependency *dep = (Dependency *)dep_node_old->data;
Task *task = dep->task;
if ( dep->direction==INPUT && task->status==NOTREADY ) {
count_initial_input_deps++;
} else if ( (dep->direction==OUTPUT || dep->direction==INOUT) && task->status!=DONE ) {
output_dep_reached = TRUE;
break;
}
}
/* if ( count_initial_input_deps>=quark->min_input_deps_to_avoid_war_dependencies && output_dep_reached ) { */
if ( count_initial_input_deps>=min_input_deps && output_dep_reached ) {
icl_list_t *dep_node_asn_old;
Address_Set_Node *asn_new;
/* Allocate and copy data */
void *datacopy = quark_malloc( asn_old->size );
/* Still need to track the allocated memory in datacopies TODO */
/* quark->mem_allocated_to_war_dependency_data += asn_old->size; */
memcpy( datacopy, asn_old->address, asn_old->size );
/* Create address set node, attach to hash, and set it to clean up when done */
asn_new = quark_address_set_node_new( datacopy, asn_old->size );
/* Update task dependences to point to this new data */
/* Grab input deps from the old list, copy to new list, delete, then repeat */
for ( dep_node_asn_old=icl_list_first(asn_old->waiting_deps);
dep_node_asn_old!=NULL; ) {
icl_list_t *dep_node_asn_old_to_be_deleted = NULL;
Dependency *dep = (Dependency *)dep_node_asn_old->data;
Task *task = dep->task;
if ( dep->direction==INPUT && task->status==NOTREADY ) {
dep_node_asn_old_to_be_deleted = dep_node_asn_old;
icl_list_t *dep_node_new = icl_list_append( asn_new->waiting_deps, dep );
/* In the args list, set the arg pointer to the new datacopy address */
*(void **)dep->task_args_list_node_ptr->data = datacopy;
dep->address = asn_new->address;
dep->address_set_node_ptr = asn_new;
dep->address_set_waiting_deps_node_ptr = dep_node_new;
if (dep->ready == FALSE) { /* dep->ready will always be FALSE */
dep->ready = TRUE;
dot_dag_print_edge( quark, parent_task->taskid, parent_task->tasklevel, task->taskid, task->tasklevel, DEPCOLOR );
pthread_mutex_lock_task( &task->task_mutex );
task->num_dependencies_remaining--;
quark_check_and_queue_ready_task( quark, task, -1 );
pthread_mutex_unlock_task( &task->task_mutex );
}
} else if ( (dep->direction==OUTPUT || dep->direction==INOUT) && task->status!=DONE ) {
/* Once we return from this routine, this dep dependency will be processed */
break;
}
dep_node_asn_old = icl_list_next(asn_old->waiting_deps, dep_node_asn_old);
if (dep_node_asn_old_to_be_deleted!=NULL) {
icl_list_delete(asn_old->waiting_deps, dep_node_asn_old_to_be_deleted, NULL);
}
}
/* Insert the constructed asn_new into the address_set */
pthread_mutex_lock_wrap( &quark->address_set_mutex );
icl_hash_insert( quark->address_set, asn_new->address, asn_new );
pthread_mutex_unlock_wrap( &quark->address_set_mutex );
}
}

Here is the call graph for this function:

int* quark_get_affthreads ( )

Definition at line 329 of file quarkos.c.

References CONTEXT_THREADS_MAX, QUARK_CLEANENV, and QUARK_GETENV.

{
char *envstr = NULL;
int i;
int *coresbind = (int *)malloc(CONTEXT_THREADS_MAX*sizeof(int));
/* Env variable does not exist, we search the system number of core */
QUARK_GETENV("QUARK_AFF_THREADS", envstr);
if ( envstr == NULL) {
for (i = 0; i < CONTEXT_THREADS_MAX; i++)
coresbind[i] = i % sys_corenbr;
}
else {
char *endptr;
int wrap = 0;
int nbr = 0;
long int val;
/* We use the content of the QUARK_AFF_THREADS env. variable */
for (i = 0; i < CONTEXT_THREADS_MAX; i++) {
if (!wrap) {
val = strtol(envstr, &endptr, 10);
if (endptr != envstr) {
coresbind[i] = (int)val;
envstr = endptr;
}
else {
/* there must be at least one entry */
if (i < 1) {
//quark_error("quark_get_affthreads", "QUARK_AFF_THREADS should have at least one entry => everything will be bind on core 0");
fprintf(stderr, "quark_get_affthreads: QUARK_AFF_THREADS should have at least one entry => everything will be bind on core 0");
coresbind[i] = 0;
i++;
}
/* there is no more values in the string */
/* the next threads are binded with a round robin policy over this array */
wrap = 1;
nbr = i;
coresbind[i] = coresbind[0];
}
}
else {
coresbind[i] = coresbind[i % nbr];
}
}
}
QUARK_CLEANENV(envstr);
/* return QUARK_SUCCESS; */
return coresbind;
}

Here is the caller graph for this function:

int quark_get_numthreads ( )

Check for an integer in an environment variable, returning the integer value or a provided default value

Definition at line 306 of file quarkos.c.

References QUARK_CLEANENV, and QUARK_GETENV.

{
char *envstr = NULL;
char *endptr;
long int thrdnbr = -1;
extern int errno;
/* Env variable does not exist, we search the system number of core */
QUARK_GETENV("QUARK_NUM_THREADS", envstr);
if ( envstr == NULL ) {
thrdnbr = sys_corenbr;
} else {
/* Convert to long, checking for errors */
thrdnbr = strtol(envstr, &endptr, 10);
if ((errno == ERANGE) || ((thrdnbr==0) && (endptr==envstr))) {
QUARK_CLEANENV(envstr);
return -1;
}
}
QUARK_CLEANENV(envstr);
return (int)thrdnbr;
}

Here is the caller graph for this function:

int quark_getenv_int ( char *  name,
int  defval 
)

Definition at line 384 of file quarkos.c.

References QUARK_CLEANENV, and QUARK_GETENV.

{
char *envstr = NULL;
char *endptr;
long int longval = -1;
extern int errno;
QUARK_GETENV(name, envstr);
if ( envstr == NULL ) {
longval = defval;
} else {
/* Convert to long, checking for errors */
longval = strtol(envstr, &endptr, 10);
if ((errno == ERANGE) || ((longval==0) && (endptr==envstr))) {
longval = defval;
}
}
QUARK_CLEANENV(envstr);
return (int)longval;
}

Here is the caller graph for this function:

Task* quark_set_task_flags_in_task_structure ( Quark quark,
Task task,
Quark_Task_Flags task_flags 
)

Use the task_flags data structure to set various items in the task (priority, lock_to_thread, color, labels, etc ).

Definition at line 1031 of file quark.c.

References quark_s::dot_dag_enable, quark_task_s::lock_to_thread, quark_task_s::lock_to_thread_mask, quark_task_s::priority, quark_task_s::sequence, quark_task_flags_s::task_color, quark_task_s::task_color, quark_task_flags_s::task_label, quark_task_s::task_label, quark_task_flags_s::task_lock_to_thread, quark_task_flags_s::task_lock_to_thread_mask, quark_task_flags_s::task_priority, quark_task_flags_s::task_sequence, quark_task_flags_s::task_thread_count, quark_task_s::task_thread_count, quark_task_flags_s::thread_set_to_manual_scheduling, and quark_task_s::thread_set_to_manual_scheduling.

{
if ( task_flags ) {
if ( task_flags->task_priority ) task->priority = task_flags->task_priority;
if ( task_flags->task_lock_to_thread >= 0 ) task->lock_to_thread = task_flags->task_lock_to_thread;
if ( task_flags->task_color && quark->dot_dag_enable ) task->task_color = strdup(task_flags->task_color);
if ( task_flags->task_label && quark->dot_dag_enable ) task->task_label = strdup(task_flags->task_label);
if ( task_flags->task_sequence ) task->sequence = task_flags->task_sequence;
if ( task_flags->task_thread_count > 1 ) task->task_thread_count = task_flags->task_thread_count;
}
return task;
}

Here is the caller graph for this function:

int quark_setaffinity ( int  rank)

This routine will set affinity for the calling thread that has rank 'rank'. Ranks start with 0.

If there are multiple instances of QUARK then affinity will be wrong: all ranks 0 will be pinned to core 0.

Also, affinity is not resotred when QUARK_Finalize() is called.

Definition at line 129 of file quarkos.c.

References QUARK_ERR_NOT_SUPPORTED, QUARK_ERR_UNEXPECTED, and QUARK_SUCCESS.

{
#ifndef QUARK_AFFINITY_DISABLE
#if (defined QUARK_OS_LINUX)
{
cpu_set_t set;
CPU_ZERO( &set );
CPU_SET( rank, &set );
#if (defined HAVE_OLD_SCHED_SETAFFINITY)
if( sched_setaffinity( 0, &set ) < 0 )
#else /* HAVE_OLD_SCHED_SETAFFINITY */
if( sched_setaffinity( 0, sizeof(set), &set) < 0 )
#endif /* HAVE_OLD_SCHED_SETAFFINITY */
{
}
return QUARK_SUCCESS;
}
#elif (defined QUARK_OS_MACOS)
{
thread_affinity_policy_data_t ap;
int ret;
ap.affinity_tag = 1; /* non-null affinity tag */
ret = thread_policy_set( mach_thread_self(),
THREAD_AFFINITY_POLICY,
(integer_t*) &ap,
THREAD_AFFINITY_POLICY_COUNT
);
if(ret != 0)
return QUARK_SUCCESS;
}
#elif (defined QUARK_OS_WINDOWS)
{
DWORD mask = 1 << rank;
if( SetThreadAffinityMask(GetCurrentThread(), mask) == 0)
return QUARK_SUCCESS;
}
#elif (defined QUARK_OS_AIX)
{
tid_t self_ktid = thread_self ();
bindprocessor(BINDTHREAD, self_ktid, rank);
return QUARK_SUCCESS;
}
#else
#endif
#endif /* QUARK_AFFINITY_DISABLE */
}

Here is the caller graph for this function:

void quark_topology_finalize ( )

Definition at line 115 of file quarkos.c.

References quark_unsetaffinity().

Here is the call graph for this function:

Here is the caller graph for this function:

void quark_topology_init ( )

Definition at line 79 of file quarkos.c.

References pthread_mutex_lock(), and pthread_mutex_unlock().

{
pthread_mutex_lock(&mutextopo);
if ( !topo_initialized ) {
#if (defined QUARK_OS_LINUX) || (defined QUARK_OS_AIX)
sys_corenbr = sysconf(_SC_NPROCESSORS_ONLN);
#elif (defined QUARK_OS_MACOS)
int mib[4];
int cpu;
size_t len = sizeof(cpu);
/* set the mib for hw.ncpu */
mib[0] = CTL_HW;
mib[1] = HW_AVAILCPU;
/* get the number of CPUs from the system */
sysctl(mib, 2, &cpu, &len, NULL, 0);
if( cpu < 1 ) {
mib[1] = HW_NCPU;
sysctl( mib, 2, &cpu, &len, NULL, 0 );
}
if( cpu < 1 ) {
cpu = 1;
}
sys_corenbr = cpu;
#elif (defined QUARK_OS_WINDOWS)
SYSTEM_INFO sysinfo;
GetSystemInfo(&sysinfo);
sys_corenbr = sysinfo.dwNumberOfProcessors;
#endif
}
pthread_mutex_unlock(&mutextopo);
}

Here is the call graph for this function:

Here is the caller graph for this function:

void quark_warning ( const char *  func_name,
char *  msg_text 
)

Warning messages

Parameters:
[in]func_nameFunction location where warning occurred
[in]msg_textWarning message to display.

Definition at line 404 of file quark.c.

{
fprintf(stderr, "QUARK_WARNING: %s(): %s\n", func_name, msg_text);
}

Here is the caller graph for this function:

int quark_yield ( )

A thread can unlock the CPU if it has nothing to do to let another thread of less priority running for example for I/O.

Definition at line 271 of file quarkos.c.

References QUARK_ERR_NOT_SUPPORTED.

{
#if (defined QUARK_OS_LINUX) || (defined QUARK_OS_MACOS) || (defined QUARK_OS_AIX)
return sched_yield();
#elif QUARK_OS_WINDOWS
return SleepEx(0,0);
#else
#endif
}
RB_GENERATE ( task_priority_tree_head_s  ,
task_priority_tree_node_s  ,
n_entry  ,
compare_task_priority_tree_nodes   
)
RB_HEAD ( task_priority_tree_head_s  ,
task_priority_tree_node_s   
)
TAILQ_HEAD ( completed_tasks_head_s  ,
completed_tasks_node_s   
)

Variable Documentation

FILE* dot_dag_file = NULL

Definition at line 333 of file quark.c.