diff --git a/bin/tests/scheduler b/bin/tests/scheduler deleted file mode 100755 index b4fb232..0000000 Binary files a/bin/tests/scheduler and /dev/null differ diff --git a/include/base.h b/include/base.h index 9fa9168..5f7b0ea 100644 --- a/include/base.h +++ b/include/base.h @@ -29,10 +29,16 @@ #define BASE_H +struct { + int x; + int y; + int z; +} typedef Arrow_t; + struct { size_t size; - bool *space; -} typedef BoolArray_t; + Arrow_t *space; +} typedef ArrowArray_t; //XXX struct { size_t size; @@ -42,24 +48,24 @@ struct { #define LOGMSG "[%s]" #define printLog(FORMAT, ...) printf(LOGMSG " " FORMAT, __func__, ##__VA_ARGS__) +/* -------------------------------------------------------------------------- */ + // // Scheduler // struct { - BoolArray_t *globalPreemptionSpace; IntArray_t *globalDrawingSpace; IntArray_t *transitionsTree; - IntArray_t *arrowList; + ArrowArray_t *arrowList; int nmaxThread; int nmaxCycles; + int ruleRadius; pthread_t *id; bool stopped; } typedef Scheduler_t; -struct { - pthread_t *id; -} typedef Worker_t; +/* -------------------------------------------------------------------------- */ // // Local threads @@ -76,4 +82,4 @@ struct Center_t { struct { pthread_t *id; Center_t *localWorkAreaCenter; -} typedef Thread_t; +} typedef Worker_t; diff --git a/include/localworker.h b/include/localworker.h index 5b6aaea..99cbcd2 100644 --- a/include/localworker.h +++ b/include/localworker.h @@ -26,21 +26,20 @@ // -------------------------------------------------------------------------- // // Worker init function // // -------------------------------------------------------------------------- // -pthread_t *WorkerInit(Worker_t *parameters); +pthread_t *WorkerInit(Worker_t *worker); // -------------------------------------------------------------------------- // // Worker destructor function // // -------------------------------------------------------------------------- // -static inline int WorkerDestroy(pthread_t *schedThread) +static inline void WorkerDestroy(Worker_t *worker) { - free(schedThread); - return 0; + free(worker->id); } // -------------------------------------------------------------------------- // // Worker wait function // // -------------------------------------------------------------------------- // -static inline void WorkerWait(pthread_t *schedThread) +static inline void WorkerWait(Worker_t *worker) { - pthread_join(*schedThread, NULL); + pthread_join(*worker->id, NULL); } diff --git a/include/scheduler.h b/include/scheduler.h index 990d9b1..4dc6493 100644 --- a/include/scheduler.h +++ b/include/scheduler.h @@ -26,21 +26,20 @@ // -------------------------------------------------------------------------- // // Scheduler init function // // -------------------------------------------------------------------------- // -pthread_t *SchedInit(Scheduler_t *parameters); +pthread_t *SchedInit(Scheduler_t *scheduler); // -------------------------------------------------------------------------- // // Scheduler destructor function // // -------------------------------------------------------------------------- // -static inline int SchedDestroy(pthread_t *schedThread) +static inline void SchedDestroy(Scheduler_t *scheduler) { - free(schedThread); - return 0; + free(scheduler->id); } // -------------------------------------------------------------------------- // // Scheduler wait function // // -------------------------------------------------------------------------- // -static inline void SchedWait(pthread_t *schedThread) +static inline void SchedWait(Scheduler_t *scheduler) { - pthread_join(*schedThread, NULL); + pthread_join(*scheduler->id, NULL); } diff --git a/src/localworker.c b/src/localworker.c index 528194c..610c7c5 100644 --- a/src/localworker.c +++ b/src/localworker.c @@ -21,31 +21,31 @@ #include "../include/base.h" -static void *LittleWorker(void *parameters); +static void *LittleWorker(void *worker); /* -------------------------------------------------------------------------- */ // -------------------------------------------------------------------------- // // Scheduler init function // // -------------------------------------------------------------------------- // -pthread_t *WorkerInit(Scheduler_t *parameters) +pthread_t *WorkerInit(Worker_t *worker) { - parameters->id = (pthread_t*) malloc(sizeof(pthread_t)); - pthread_create(parameters->id, NULL, LittleWorker, parameters); - return parameters->id; + worker->id = (pthread_t*) malloc(sizeof(pthread_t)); + pthread_create(worker->id, NULL, LittleWorker, worker); + return worker->id; } // -------------------------------------------------------------------------- // // Scheduler thread main function // // -------------------------------------------------------------------------- // -static void *LittleWorker(void *params) +static void *LittleWorker(void *worker) { - Worker_t *parameters = (Worker_t*) params; + Worker_t *args = (Worker_t*) worker; int a = 4; for (int i = 0; i < 45000; i++) { for (int j = i; j < 45000; j++) { - a = (a + (long)parameters->id) * i * j; + a = (a + (long)args->id) * i * j; } } diff --git a/src/main.c b/src/main.c index 4717805..5b0edb4 100644 --- a/src/main.c +++ b/src/main.c @@ -29,28 +29,6 @@ #define SPACE_SIZE 10000 #define MAX_THREAD 0 -void SchedulerCrashTest(void) -{ - const int maxthread = 16; - - Scheduler_t *scheduler0 = - (Scheduler_t*) calloc(1, sizeof(Scheduler_t)); - - pthread_t **schedThread = - (pthread_t**) malloc(sizeof(pthread_t*) * maxthread); - - for (int i=0; i < maxthread; i++) { - schedThread[i] = SchedInit(scheduler0); - } - - for (int i=0; i < maxthread; i++) { - SchedWait(schedThread[i]); - SchedDestroy(schedThread[i]); - } - - free(scheduler0); -} - int main(int argc, char **argv) { time_t t; @@ -70,19 +48,13 @@ int main(int argc, char **argv) // scheduler0 = (Scheduler_t*) malloc(sizeof(Scheduler_t)); - scheduler0->globalPreemptionSpace = - (BoolArray_t*) malloc(sizeof(BoolArray_t)); - scheduler0->globalPreemptionSpace->space = - (bool*) malloc(sizeof(bool)*SPACE_SIZE); - scheduler0->globalPreemptionSpace->size = SPACE_SIZE; - scheduler0->globalDrawingSpace = (IntArray_t*) malloc(sizeof(IntArray_t)); scheduler0->globalDrawingSpace->space = (int*) malloc(sizeof(int)*SPACE_SIZE); scheduler0->globalDrawingSpace->size = SPACE_SIZE; - scheduler0->arrowList = (IntArray_t*) malloc(sizeof(IntArray_t)); - scheduler0->arrowList->space = (int*) malloc(sizeof(int)*ARROW_NUMBER); + scheduler0->arrowList = (ArrowArray_t*) malloc(sizeof(ArrowArray_t)); + scheduler0->arrowList->space = (Arrow_t*) malloc(sizeof(Arrow_t)*ARROW_NUMBER); scheduler0->arrowList->size = ARROW_NUMBER; scheduler0->nmaxThread = MAX_THREAD; @@ -93,16 +65,13 @@ int main(int argc, char **argv) // SchedInit(scheduler0); - SchedWait(scheduler0->id); + SchedWait(scheduler0); - SchedDestroy(scheduler0->id); + SchedDestroy(scheduler0); free(scheduler0->globalDrawingSpace->space); free(scheduler0->globalDrawingSpace); - free(scheduler0->globalPreemptionSpace->space); - free(scheduler0->globalPreemptionSpace); - free(scheduler0->arrowList->space); free(scheduler0->arrowList); diff --git a/src/scheduler.c b/src/scheduler.c index c38ae1c..341d075 100644 --- a/src/scheduler.c +++ b/src/scheduler.c @@ -31,11 +31,11 @@ static void *GreatScheduler(void *parameters); // -------------------------------------------------------------------------- // // Scheduler init function // // -------------------------------------------------------------------------- // -pthread_t *SchedInit(Scheduler_t *parameters) +pthread_t *SchedInit(Scheduler_t *scheduler) { - parameters->id = (pthread_t*) malloc(sizeof(pthread_t)); - pthread_create(parameters->id, NULL, GreatScheduler, parameters); - return parameters->id; + scheduler->id = (pthread_t*) malloc(sizeof(pthread_t)); + pthread_create(scheduler->id, NULL, GreatScheduler, scheduler); + return scheduler->id; } // -------------------------------------------------------------------------- // @@ -68,56 +68,110 @@ static inline void centerRemove(Center_t *oldCenter) if (oldCenter->next) oldCenter->next->prev = oldCenter->prev; } +/* -------------------------------------------------------------------------- */ + // -------------------------------------------------------------------------- // // Scheduler area finder function // // -------------------------------------------------------------------------- // -static Center_t *findWorkArea(Center_t *centerList, int ruleRadius, size_t spaceSize) +static Center_t *findWorkArea(Center_t *centersList, Arrow_t *electedArrow, + int ruleRadius, size_t spaceSize) { - Center_t *myCenter = (Center_t*) malloc(sizeof(Center_t)); - centerAssign(myCenter, rand() % spaceSize, 0, 0); /* Je suis né quelque part.(ou pas !).*/ + register Center_t *currentCenter = centersList; - while (centerList != NULL){ - //printLog("Center : %d\n", centerList->x); - if (abs(myCenter->x - centerList->x) < ruleRadius){ - printLog("FAIL: no work area available at %d\n", myCenter->x); - free(myCenter); - return NULL; + while (currentCenter){ + //printLog("Center : %d\n", currentCenter->x); + if ( abs(electedArrow->x - currentCenter->x) >= ruleRadius + && abs(electedArrow->y - currentCenter->y) >= ruleRadius + && abs(electedArrow->z - currentCenter->z) >= ruleRadius + ){ + return currentCenter; } - centerList = centerList->next; - } - - printLog("SUCCESS ! at %d: < I've found a center.\n", myCenter->x); - - return myCenter; -} - -// -------------------------------------------------------------------------- // -// Scheduler thread main function // -// -------------------------------------------------------------------------- // -static void *GreatScheduler(void *params) -{ - // récupération des paramètres et annonce - Scheduler_t *args = (Scheduler_t*) params; - printLog("Scheduler id %lu: Bonjour I'm the boss !\n", *(args->id)); - - int ncpu = get_nprocs(); - printLog("%d CPUs available.\n", ncpu); - - Thread_t *workerArray = (Thread_t*) malloc(sizeof(Thread_t) * 3 * ncpu); - Center_t *centersList = (Center_t*) malloc(sizeof(Center_t)); - - centerAssign(centersList, -1, -1, -1); - - Center_t *workArea; - int i = 0; - - while (!args->stopped) { - while ((workArea = findWorkArea(centersList, 4, 30))) { - i++; - centerAdd(centersList, workArea); - } - printLog("New centers : %d\n", i); + currentCenter = currentCenter->next; } return NULL; } + +/* -------------------------------------------------------------------------- */ + +// -------------------------------------------------------------------------- // +// Scheduler thread main function // +// -------------------------------------------------------------------------- // +static void *GreatScheduler(void *scheduler) +{ + Scheduler_t *args; + Worker_t *workerArray; + Center_t *centersList, *workArea; + Arrow_t *electedArrow; + long ncycles; + int ncpu, nworker; + + + // Getting scheduler argument structure + args = (Scheduler_t*) scheduler; + printLog("Scheduler #%lu online\n", *(args->id)); + + ncpu = get_nprocs(); + printLog("%d CPUs available.\n", ncpu); + + // Data structures + workerArray = (Worker_t*) calloc(ncpu, sizeof(Worker_t)); + nworker = 0; + centersList = (Center_t*) calloc(1, sizeof(Center_t)); + ncycles = 0; + + // + // MAIN LOOP + // + while (!args->stopped && ncycles <= args->nmaxCycles) { + // Increment cycles + ncycles++; + + // TODO statistics here + + // Create a new thread + if (nworker < ncpu) { + // Random choice of an arrow + electedArrow = + &args->arrowList->space[rand() % args->arrowList->size]; + + // Find a local area + workArea = findWorkArea(centersList, electedArrow, args->ruleRadius, + args->globalDrawingSpace->size); + + // If a free area exists, + if (workArea) { + // preempt it, + centerAdd(centersList, workArea); + // find a worker socket, + for (int i = 0; i < ncpu; i++) { + if (!workerArray[i].id) { + // prepare the worker for the area, + workerArray[i].localWorkAreaCenter = workArea; + // create the worker, + WorkerInit(&workerArray[i]); + // and increment worker count. + nworker++; + break; + } + } + } + } + + // TODO Delete finished workers + for (int i = 0; i < ncpu; i++) { + // XXX + } + } + + // TODO Exiting scheduler properly + + // Waiting for remaining workers + for (int i = 0; i < ncpu; i++) { + // XXX + } + + printLog("Scheduler #%lu offline\n", *(args->id)); + + return NULL; +}