-- NewFIFOImpl.sak
-- last edited by Suzuki: 20-Apr-82 12:55:47

DIRECTORY
  FIFO,
  SakuraRT;
  
NewFIFOImpl: MONITOR IMPORTS SakuraRT
  EXPORTS FIFO ={
    
FIFOFunc: PUBLIC DEVICE [size: CARDINAL] = {
    IN Init, WriteRequest, ReadRequest: BOOLEAN,
        DIn: CARDINAL
    OUT SpaceAv, DataAv: BOOLEAN, DOut: CARDINAL
    GUARDIAN {
        Initialized: BOOLEAN ← FALSE;
        DO CHOICE {
          WHEN Init UP -> {IF ReadRequest OR WriteRequest THEN ERROR;
           Initialized ← TRUE} ||
          WHEN ReadRequest UP -> IF ~Initialized OR Init OR ~DataAv
           THEN ERROR ||
          WHEN WriteRequest UP -> IF ~Initialized OR Init OR ~SpaceAv
           THEN ERROR}
        ENDLOOP }
    CONTROL
        {
	 A: ARRAY [0..37] OF CARDINAL;
	 rp, wp: CARDINAL;
	 DO 
            WHEN Init UP : {rp ← 1; wp ← 0;
              SpaceAv ← TRUE; DataAv ← FALSE};
            PAR { 
                DO 
                    WHEN ReadRequest UP : {
                        SakuraRT.Delay[1];
			DataAv←FALSE; rp←rp+1;
                        DOut←A[rp]; SpaceAv ← ~WriteRequest AND wp<rp+size};
                    WHEN ReadRequest DOWN: DataAv←rp<=wp;
                    ENDLOOP
                        //
                DO 
                    WHEN WriteRequest UP : {
                        SakuraRT.Delay[1];
			SpaceAv←FALSE; wp←wp+1; A[wp]←DIn;
                        DOut←A[rp]; DataAv←~ReadRequest AND rp<=wp};
                    WHEN WriteRequest DOWN: SpaceAv←wp<rp+size;
                    ENDLOOP
            }
        ENDLOOP}
    };
     
NULL

}. -- end of FIFO DEFINITION