views:

102

answers:

1

Possible Duplicate:
Peterson algorithm in Java?

I am trying to implement a lock in Java (lock interface) in the lines of petersen method. What is the simplest possible non-reentrant implementation to guarantee mutual exclusion.

flag[0]   = 0;
flag[1]   = 0;
turn;

P0: flag[0] = 1;                            P1: flag[1] = 1;
    turn = 1;                                   turn = 0;
    while (flag[1] == 1 && turn == 1)           while (flag[0] == 1 && turn == 0)
    {                                           {
           // busy wait                                  // busy wait
    }                                           }                                 
    // critical section                         // critical section 
       ...                                        ...
    // end of critical section                  // end of critical section
    flag[0] = 0;                                flag[1] = 0;

I am using the above algorithm (from wiki). It doesn't seem to work as I am getting many data races despite using volatile flag and turn variables. What are the things to take care of?

Here the code:

public class TestLock implements Lock {

    private final long thread1ID;
    private final long thread2ID;
    private volatile AtomicIntegerArray flagArr = new AtomicIntegerArray(50);
    private volatile long turn = 0;
    private volatile long currentThreadID = 0;

    public TestLock(Thread thread1, Thread thread2) {       
        thread1ID = t0.getId();
        thread2ID = t1.getId();         
        flagArr.set((int)thread1ID, 0);
        flagArr.set((int)thread2ID, 0);     
    }
    public void lock() {        
        currentThreadID = Thread.currentThread().getId();
        flagArr.set((int)Thread.currentThread().getId(), 1);            
        turn = next();          
        while(turn == next() && flagArr.get((int)next()) == 1)
        {
            System.out.println(Thread.currentThread().getId()+" waiting");              
        }
        //critical section
        System.out.println(Thread.currentThread().getId()+" executing");
        }

    private long next() {
        return Thread.currentThread().getId() == thread1ID ? thread2ID : thread1ID;     
    }

    public void unlock() {      
        flagArr.set((int)Thread.currentThread().getId(), 0);    
    }
}
A: 

Well, based on the comments in the accepted answer to this SO question, one problem is that you cannot use a boolean [] and expect the cells to have volatile semantics.

If you posted your code, we might be able to offer more suggestions.

Stephen C
I have updated the code. Could you pls have a look.
Deeju