added some code for implementing semaphore

This commit is contained in:
hyunghwan.chung 2016-02-29 15:27:10 +00:00
parent 351239bdf4
commit 55a43371d5
7 changed files with 71 additions and 52 deletions

View File

@ -1,37 +0,0 @@
#class Number(Magnitude)
{
#method add: aNumber
{
<primitive: 7>
}
#method + aNumber
{
<primitive: 7>
}
#method - aNumber
{
<primitive: 8>
}
#method * aNumber
{
<primitive: 8>
}
#method = aNumber
{
<primitive: 10>
}
#method < aNumber
{
<primitive: 11>
}
#method > aNumber
{
<primitive: 12>
}
}

View File

@ -88,6 +88,7 @@
#method initialize #method initialize
{ {
count := 0.
} }
#method signal #method signal

View File

@ -199,13 +199,23 @@
self > 0 ifTrue: [^1]. self > 0 ifTrue: [^1].
^0. ^0.
} }
} }
#class SmallInteger(Number)
#class Integer(Number)
{
#method timesRepeat: aBlock
{
1 to: self by: 1 do: [ :count | aBlock value ].
}
}
#class SmallInteger(Integer)
{ {
} }
#class(#liword) LargeInteger(Number) #class(#liword) LargeInteger(Integer)
{ {
} }

View File

@ -160,7 +160,7 @@ printf ("PROCESS %p SIZE => %ld\n", proc, (long int)STIX_OBJ_GET_SIZE(proc));
return proc; return proc;
} }
static void switch_to_process (stix_t* stix, stix_oop_process_t proc) static void switch_to_process (stix_t* stix, stix_oop_process_t proc, int new_state_for_old_active)
{ {
/* the new process must not be the currently active process */ /* the new process must not be the currently active process */
STIX_ASSERT (stix->processor->active != proc); STIX_ASSERT (stix->processor->active != proc);
@ -183,7 +183,8 @@ printf ("ACTUAL PROCESS SWITCHING BF...%d %p\n", (int)stix->ip, stix->active_con
* it is the suspended context of the process to be suspended */ * it is the suspended context of the process to be suspended */
STIX_ASSERT ((stix_oop_t)stix->processor->active != stix->_nil); STIX_ASSERT ((stix_oop_t)stix->processor->active != stix->_nil);
stix->processor->active->current_context = stix->active_context; stix->processor->active->current_context = stix->active_context;
stix->processor->active->state = STIX_SMOOI_TO_OOP(PROCESS_STATE_RUNNABLE); /*stix->processor->active->state = STIX_SMOOI_TO_OOP(PROCESS_STATE_RUNNABLE);*/
stix->processor->active->state = STIX_SMOOI_TO_OOP(new_state_for_old_active);
/* activate the given process */ /* activate the given process */
proc->state = STIX_SMOOI_TO_OOP(PROCESS_STATE_RUNNING); proc->state = STIX_SMOOI_TO_OOP(PROCESS_STATE_RUNNING);
@ -219,7 +220,7 @@ static STIX_INLINE void switch_to_next_runnable_process (stix_t* stix)
stix_oop_process_t nrp; stix_oop_process_t nrp;
nrp = find_next_runnable_process (stix); nrp = find_next_runnable_process (stix);
if (nrp != stix->processor->active) switch_to_process (stix, nrp); if (nrp != stix->processor->active) switch_to_process (stix, nrp, PROCESS_STATE_RUNNABLE);
} }
static STIX_INLINE int chain_into_processor (stix_t* stix, stix_oop_process_t proc) static STIX_INLINE int chain_into_processor (stix_t* stix, stix_oop_process_t proc)
@ -306,7 +307,7 @@ static void terminate_process (stix_t* stix, stix_oop_process_t proc)
} }
else else
{ {
switch_to_process (stix, nrp); switch_to_process (stix, nrp, PROCESS_STATE_TERMINATED);
} }
} }
else else
@ -331,6 +332,7 @@ static void terminate_process (stix_t* stix, stix_oop_process_t proc)
static void resume_process (stix_t* stix, stix_oop_process_t proc) static void resume_process (stix_t* stix, stix_oop_process_t proc)
{ {
printf ("TO RESUME PROCESS = %p %d\n", proc, STIX_OOP_TO_SMOOI(proc->state));
if (proc->state == STIX_SMOOI_TO_OOP(PROCESS_STATE_SUSPENDED)) if (proc->state == STIX_SMOOI_TO_OOP(PROCESS_STATE_SUSPENDED))
{ {
/* SUSPENED ---> RUNNING */ /* SUSPENED ---> RUNNING */
@ -340,7 +342,7 @@ static void resume_process (stix_t* stix, stix_oop_process_t proc)
chain_into_processor (stix, proc); /* TODO: error check */ chain_into_processor (stix, proc); /* TODO: error check */
proc->current_context = proc->initial_context; /*proc->current_context = proc->initial_context;*/
proc->state = STIX_SMOOI_TO_OOP(PROCESS_STATE_RUNNABLE); proc->state = STIX_SMOOI_TO_OOP(PROCESS_STATE_RUNNABLE);
/*switch_to_process (stix, proc);*/ /*switch_to_process (stix, proc);*/
@ -351,7 +353,7 @@ static void resume_process (stix_t* stix, stix_oop_process_t proc)
/* RUNNABLE ---> RUNNING */ /* RUNNABLE ---> RUNNING */
/* TODO: should i allow this? */ /* TODO: should i allow this? */
STIX_ASSERT (stix->processor->active != proc); STIX_ASSERT (stix->processor->active != proc);
switch_to_process (stix, proc); switch_to_process (stix, proc, PROCESS_STATE_RUNNABLE);
} }
#endif #endif
} }
@ -370,17 +372,19 @@ static void suspend_process (stix_t* stix, stix_oop_process_t proc)
nrp = find_next_runnable_process (stix); nrp = find_next_runnable_process (stix);
unchain_from_processor (stix, proc); unchain_from_processor (stix, proc);
proc->state = STIX_SMOOI_TO_OOP(PROCESS_STATE_SUSPENDED); printf ("TO SUSPEND...%p %d\n", proc, (int)STIX_OOP_TO_SMOOI(proc->state));
proc->current_context = stix->active_context;
if (nrp == proc) if (nrp == proc)
{ {
/* no runnable process after suspension */ /* no runnable process after suspension */
STIX_ASSERT (stix->processor->active == stix->nil_process); STIX_ASSERT (stix->processor->active == stix->nil_process);
printf ("NO RUNNABLE PROCESS AFTER SUPSENDISION\n");
proc->state = STIX_SMOOI_TO_OOP(PROCESS_STATE_SUSPENDED);
proc->current_context = stix->active_context;
} }
else else
{ {
switch_to_process (stix, nrp); switch_to_process (stix, nrp, PROCESS_STATE_SUSPENDED);
} }
} }
else else
@ -404,10 +408,28 @@ static void yield_process (stix_t* stix, stix_oop_process_t proc)
nrp = find_next_runnable_process (stix); nrp = find_next_runnable_process (stix);
/* if there are more than 1 runnable processes, the next /* if there are more than 1 runnable processes, the next
* runnable process must be different from proc */ * runnable process must be different from proc */
if (nrp != proc) switch_to_process (stix, proc); if (nrp != proc)
{
switch_to_process (stix, nrp, PROCESS_STATE_RUNNABLE);
}
} }
} }
static int async_signal_semaphore (stix_t* stix, stix_oop_semaphore_t sem)
{
if (stix->sem_count > STIX_COUNTOF(stix->sem_list))
{
/* TOO MANY ASYNC SEMAPHORES.. */
/* TODO: PROPER ERROR HANDLING */
stix->errnum = STIX_ESYSMEM;
return -1;
}
stix->sem_list[stix->sem_count] = sem;
stix->sem_count++;
return 0;
}
static void signal_semaphore (stix_t* stix, stix_oop_semaphore_t sem) static void signal_semaphore (stix_t* stix, stix_oop_semaphore_t sem)
{ {
stix_oop_process_t proc; stix_oop_process_t proc;
@ -415,12 +437,15 @@ static void signal_semaphore (stix_t* stix, stix_oop_semaphore_t sem)
if ((stix_oop_t)sem->waiting_head == stix->_nil) if ((stix_oop_t)sem->waiting_head == stix->_nil)
{ {
printf ("signal semaphore...1111\n");
/* no process is waiting on this semaphore */
count = STIX_OOP_TO_SMOOI(sem->count); count = STIX_OOP_TO_SMOOI(sem->count);
count++; count++;
sem->count = STIX_SMOOI_TO_OOP(count); sem->count = STIX_SMOOI_TO_OOP(count);
} }
else else
{ {
printf ("signal semaphore...2222\n");
proc = sem->waiting_head; proc = sem->waiting_head;
sem->waiting_head = proc->sem_next; sem->waiting_head = proc->sem_next;
if ((stix_oop_t)sem->waiting_head == stix->_nil) if ((stix_oop_t)sem->waiting_head == stix->_nil)
@ -439,14 +464,18 @@ static void await_semaphore (stix_t* stix, stix_oop_semaphore_t sem)
count = STIX_OOP_TO_SMOOI(sem->count); count = STIX_OOP_TO_SMOOI(sem->count);
if (count > 0) if (count > 0)
{ {
/* it's already signalled */
count--; count--;
sem->count = STIX_SMOOI_TO_OOP(count); sem->count = STIX_SMOOI_TO_OOP(count);
printf (">>>>>>>>>>>>>> AWAIT SEMAPHORE - NO SUSPENDING ...................\n");
} }
else else
{ {
/* not signaled. need to wait */
proc = stix->processor->active; proc = stix->processor->active;
STIX_ASSERT ((stix_oop_t)proc->sem_next == stix->_nil); STIX_ASSERT ((stix_oop_t)proc->sem_next == stix->_nil);
/* add the active process to the semaphore's waiting list */
if ((stix_oop_t)sem->waiting_tail == stix->_nil) if ((stix_oop_t)sem->waiting_tail == stix->_nil)
{ {
STIX_ASSERT ((stix_oop_t)sem->waiting_head == stix->_nil); STIX_ASSERT ((stix_oop_t)sem->waiting_head == stix->_nil);
@ -459,7 +488,8 @@ static void await_semaphore (stix_t* stix, stix_oop_semaphore_t sem)
} }
sem->waiting_tail = proc; sem->waiting_tail = proc;
suspend_process (stix, proc); printf (">>>>>>>>>>>>>> AWAIT SEMAPHORE - SUEPENDING PROCESS...............\n");
suspend_process (stix, proc); /* suspend the active process */
STIX_ASSERT (stix->processor->active != proc); STIX_ASSERT (stix->processor->active != proc);
} }
} }
@ -2496,6 +2526,7 @@ int stix_execute (stix_t* stix)
{ {
/* no more process in the system */ /* no more process in the system */
STIX_ASSERT (stix->processor->tally = STIX_SMOOI_TO_OOP(0)); STIX_ASSERT (stix->processor->tally = STIX_SMOOI_TO_OOP(0));
printf ("NO MORE RUNNABLE PROCESS...\n");
break; break;
} }
/* /*
@ -2505,6 +2536,12 @@ IDLEING WAITING FOR PROCESS WAKE-UP...
} }
*/ */
while (stix->sem_count > 0)
{
--stix->sem_count;
signal_semaphore (stix, stix->sem_list[stix->sem_count]);
}
/* TODO: implement different process switching scheme - time-slice or clock based??? */ /* TODO: implement different process switching scheme - time-slice or clock based??? */
if (!stix->proc_switched) { switch_to_next_runnable_process (stix); } if (!stix->proc_switched) { switch_to_next_runnable_process (stix); }
stix->proc_switched = 0; stix->proc_switched = 0;

View File

@ -339,6 +339,11 @@ printf ("STARTING GC curheap base %p ptr %p newheap base %p ptr %p\n",
stix->processor = (stix_oop_process_scheduler_t) stix_moveoop (stix, (stix_oop_t)stix->processor); stix->processor = (stix_oop_process_scheduler_t) stix_moveoop (stix, (stix_oop_t)stix->processor);
stix->nil_process = (stix_oop_process_t) stix_moveoop (stix, (stix_oop_t)stix->nil_process); stix->nil_process = (stix_oop_process_t) stix_moveoop (stix, (stix_oop_t)stix->nil_process);
for (i = 0; i < stix->sem_count; i++)
{
stix->sem_list[i] = stix_moveoop (stix, stix->sem_list[i]);
}
for (i = 0; i < stix->tmp_count; i++) for (i = 0; i < stix->tmp_count; i++)
{ {
*stix->tmp_stack[i] = stix_moveoop (stix, *stix->tmp_stack[i]); *stix->tmp_stack[i] = stix_moveoop (stix, *stix->tmp_stack[i]);

View File

@ -54,7 +54,7 @@
/* this is for gc debugging */ /* this is for gc debugging */
/*#define STIX_DEBUG_PROCESSOR*/ /*#define STIX_DEBUG_PROCESSOR*/
#define STIX_DEBUG_GC_001 /*#define STIX_DEBUG_GC_001*/
/*#define STIX_DEBUG_GC_002*/ /*#define STIX_DEBUG_GC_002*/
#define STIX_DEBUG_COMP_001 #define STIX_DEBUG_COMP_001
/*#define STIX_DEBUG_COMP_002*/ /*#define STIX_DEBUG_COMP_002*/

View File

@ -766,6 +766,9 @@ struct stix_t
stix_oop_process_scheduler_t processor; /* instance of ProcessScheduler */ stix_oop_process_scheduler_t processor; /* instance of ProcessScheduler */
stix_oop_process_t nil_process; /* instance of Process */ stix_oop_process_t nil_process; /* instance of Process */
stix_oop_semaphore_t sem_list[256]; /* TODO: make it dynamic */
stix_oow_t sem_count;
stix_oop_t* tmp_stack[256]; /* stack for temporaries */ stix_oop_t* tmp_stack[256]; /* stack for temporaries */
stix_oow_t tmp_count; stix_oow_t tmp_count;