diff --git a/go.sum b/go.sum index 95f3e70..84eb062 100644 --- a/go.sum +++ b/go.sum @@ -8,6 +8,7 @@ github.com/kylelemons/godebug v0.0.0-20170820004349-d65d576e9348 h1:MtvEpTB6LX3v github.com/kylelemons/godebug v0.0.0-20170820004349-d65d576e9348/go.mod h1:B69LEHPfb2qLo0BaaOLcbitczOKLWTsrBG9LczfCD4k= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/stretchr/objx v0.1.0 h1:4G4v2dO3VZwixGIRoQ5Lfboy6nUhCyYzaqnIAPPhYs4= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= diff --git a/internal/lockserver/lockserver.go b/internal/lockserver/lockserver.go index 0ecc49c..a8599b0 100644 --- a/internal/lockserver/lockserver.go +++ b/internal/lockserver/lockserver.go @@ -38,7 +38,7 @@ func (s *Service) HealthCheck(ip string, counter *int) error { } // CheckAcquire returns nil if the file is acquired -func (s *Service) CheckAcquire(fileID string) error { +func (s *Service) CheckAcquire(fileID string, counter *float32) error { lockMap.Mutex.Lock() if lockMap.LockMap[fileID] { lockMap.Mutex.Unlock() @@ -62,7 +62,7 @@ func (s *Service) Acquire(fileID string, counter *float32) error { } // CheckRelease returns nil if the file is released -func (s *Service) CheckRelease(fileID string) error { +func (s *Service) CheckRelease(fileID string, counter *float32) error { lockMap.Mutex.Lock() if lockMap.LockMap[fileID] { lockMap.Mutex.Unlock() @@ -74,6 +74,7 @@ func (s *Service) CheckRelease(fileID string) error { // Release lets a client to release a lock on an object. func (s *Service) Release(fileID string, counter *float32) error { + fmt.Println("WE") lockMap.Mutex.Lock() if lockMap.LockMap[fileID] { delete(lockMap.LockMap, fileID) diff --git a/internal/lockserver/lockserver_test.go b/internal/lockserver/lockserver_test.go index 0521149..63c63a1 100644 --- a/internal/lockserver/lockserver_test.go +++ b/internal/lockserver/lockserver_test.go @@ -65,12 +65,145 @@ func TestSingleLockAndRelease1(t *testing.T) { if err != nil { assert.Fail(fmt.Sprintf("Failed to acquire lock: %v", err)) } + result := client.Call("Service.CheckAcquire", "1", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not acquired")) + } err = client.Call("Service.Release", "1", &y) if err != nil { assert.Fail(fmt.Sprintf("Failed to release lock: %v", err)) } + + result = client.Call("Service.CheckRelease", "1", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not released")) + } + + err = client.Call("Service.Acquire", "1", &y) + + if err != nil { + assert.Fail(fmt.Sprintf("Failed to acquire lock: %v", err)) + } + + result = client.Call("Service.CheckAcquire", "1", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not acquired")) + } + + err = client.Call("Service.Release", "1", &y) + if err != nil { + assert.Fail(fmt.Sprintf("Failed to release lock: %v", err)) + } + + result = client.Call("Service.CheckRelease", "1", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not released")) + } + + shutdownSignal <- os.Kill + timer1 = time.NewTimer(5 * time.Millisecond) + <-timer1.C +} + +func TestMultipleLockAndRelease(t *testing.T) { + t.Logf("acquire a acquire b release b release a\n") + shutdownSignal := make(chan os.Signal, 1) + go StartServer(shutdownSignal) + + timer1 := time.NewTimer(5 * time.Millisecond) + <-timer1.C + + assert := assert.New(t) + client, err := rpc.DialHTTP("tcp", "localhost:55550") + + var y float32 + y = 3.4 + if err != nil { + log.Fatal("Connection error: ", err) + } + err = client.Call("Service.Acquire", "1", &y) + + if err != nil { + assert.Fail(fmt.Sprintf("Failed to acquire lock: %v", err)) + } + + result := client.Call("Service.CheckAcquire", "1", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not acquired")) + } + + err = client.Call("Service.Acquire", "2", &y) + if err != nil { + assert.Fail(fmt.Sprintf("Failed to release lock: %v", err)) + } + + result = client.Call("Service.CheckAcquire", "2", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not acquired")) + } + + err = client.Call("Service.Release", "2", &y) + if err != nil { + assert.Fail(fmt.Sprintf("Failed to release lock: %v", err)) + } + result = client.Call("Service.CheckRelease", "2", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not released")) + } + + err = client.Call("Service.Release", "1", &y) + if err != nil { + assert.Fail(fmt.Sprintf("Failed to release lock: %v", err)) + } + result = client.Call("Service.CheckRelease", "1", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not released")) + } + + shutdownSignal <- os.Kill + timer1 = time.NewTimer(5 * time.Millisecond) + <-timer1.C +} + +func TestConcurrentRoutinesAcquiringSameLock(t *testing.T) { + shutdownSignal := make(chan os.Signal, 1) + go StartServer(shutdownSignal) + + timer1 := time.NewTimer(5 * time.Millisecond) + <-timer1.C + + client, err := rpc.DialHTTP("tcp", "localhost:55550") + var y float32 + y = 3.4 + + for i := 0; i < 5; i++ { + go func(t *testing.T, tid int) { + assert := assert.New(t) + t.Logf("client %d acquire a release a", tid) + err = client.Call("Service.Release", "1", &y) + if err != nil { + assert.Fail(fmt.Sprintf("Failed to release lock: %v", err)) + } + t.Logf("client %d acquire done", tid) + result := client.Call("Service.CheckAcquire", "1", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not acquired")) + } + time.Sleep(1) + t.Logf("client %d release", tid) + err = client.Call("Service.Release", "1", &y) + if err != nil { + assert.Fail(fmt.Sprintf("Failed to release lock: %v", err)) + } + result = client.Call("Service.CheckRelease", "1", &y) + if result != nil { + assert.Fail(fmt.Sprintf("Lock was not released")) + } + t.Logf("client %d release done", tid) + }(t, i) + } shutdownSignal <- os.Kill timer1 = time.NewTimer(5 * time.Millisecond) <-timer1.C