| /* Licensed to the Apache Software Foundation (ASF) under one or more |
| * contributor license agreements. See the NOTICE file distributed with |
| * this work for additional information regarding copyright ownership. |
| * The ASF licenses this file to You under the Apache License, Version 2.0 |
| * (the "License"); you may not use this file except in compliance with |
| * the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| package org.apache.harmony.nio.tests.java.nio.channels; |
| |
| import java.io.File; |
| import java.io.FileInputStream; |
| import java.io.FileOutputStream; |
| import java.io.FileWriter; |
| import java.io.IOException; |
| import java.io.RandomAccessFile; |
| import java.nio.channels.FileChannel; |
| import java.nio.channels.FileLock; |
| import java.nio.channels.NonReadableChannelException; |
| import java.nio.channels.NonWritableChannelException; |
| import java.nio.channels.OverlappingFileLockException; |
| |
| import junit.framework.TestCase; |
| |
| /** |
| * API tests for the NIO FileChannel locking APIs |
| */ |
| public class FileChannelLockingTest extends TestCase { |
| |
| private FileChannel readOnlyChannel; |
| |
| private FileChannel writeOnlyChannel; |
| |
| private FileChannel readWriteChannel; |
| |
| private final String CONTENT = "The best things in life are nearest: Breath in your nostrils, light in your eyes, " |
| + "flowers at your feet, duties at your hand, the path of right just before you. Then do not grasp at the stars, " |
| + "but do life's plain, common work as it comes, certain that daily duties and daily bread are the sweetest " |
| + " things in life.--Robert Louis Stevenson"; |
| |
| protected void setUp() throws Exception { |
| super.setUp(); |
| |
| // Create a three temporary files with content. |
| File[] tempFiles = new File[3]; |
| for (int i = 0; i < tempFiles.length; i++) { |
| tempFiles[i] = File.createTempFile("testing", "tmp"); |
| tempFiles[i].deleteOnExit(); |
| FileWriter writer = new FileWriter(tempFiles[i]); |
| writer.write(CONTENT); |
| writer.close(); |
| } |
| |
| // Open read, write, and read/write channels on the temp files. |
| FileInputStream fileInputStream = new FileInputStream(tempFiles[0]); |
| readOnlyChannel = fileInputStream.getChannel(); |
| |
| FileOutputStream fileOutputStream = new FileOutputStream(tempFiles[1]); |
| writeOnlyChannel = fileOutputStream.getChannel(); |
| |
| RandomAccessFile randomAccessFile = new RandomAccessFile(tempFiles[2], |
| "rw"); |
| readWriteChannel = randomAccessFile.getChannel(); |
| } |
| |
| protected void tearDown() throws IOException { |
| if (readOnlyChannel != null) { |
| readOnlyChannel.close(); |
| } |
| if (writeOnlyChannel != null) { |
| writeOnlyChannel.close(); |
| } |
| if (readWriteChannel != null) { |
| readWriteChannel.close(); |
| } |
| } |
| |
| public void test_illegalLocks() throws IOException { |
| // Cannot acquire an exclusive lock on a read-only file channel |
| try { |
| readOnlyChannel.lock(); |
| fail("Acquiring a full exclusive lock on a read only channel should fail."); |
| } catch (NonWritableChannelException ex) { |
| // Expected. |
| } |
| |
| // Cannot get a shared lock on a write-only file channel. |
| try { |
| writeOnlyChannel.lock(1, 10, true); |
| fail("Acquiring a shared lock on a write-only channel should fail."); |
| } catch (NonReadableChannelException ex) { |
| // expected |
| } |
| } |
| |
| public void test_lockReadWrite() throws IOException { |
| // Acquire an exclusive lock across the entire file. |
| FileLock flock = readWriteChannel.lock(); |
| if (flock != null) { |
| flock.release(); |
| } |
| } |
| |
| public void test_illegalLockParameters() throws IOException { |
| // Cannot lock negative positions |
| try { |
| readOnlyChannel.lock(-1, 10, true); |
| fail("Passing illegal args to lock should fail."); |
| } catch (IllegalArgumentException ex) { |
| // expected |
| } |
| try { |
| writeOnlyChannel.lock(-1, 10, false); |
| fail("Passing illegal args to lock should fail."); |
| } catch (IllegalArgumentException ex) { |
| // expected |
| } |
| try { |
| readWriteChannel.lock(-1, 10, false); |
| fail("Passing illegal args to lock should fail."); |
| } catch (IllegalArgumentException ex) { |
| // expected |
| } |
| |
| // Lock a range at the front, shared. |
| FileLock flock1 = readWriteChannel.lock(22, 110, true); |
| |
| // Try to acquire an overlapping lock. |
| try { |
| readWriteChannel.lock(75, 210, true); |
| } catch (OverlappingFileLockException exception) { |
| // expected |
| flock1.release(); |
| } |
| } |
| |
| public void test_lockLLZ() throws IOException { |
| // Lock a range at the front, non-shared. |
| FileLock flock1 = readWriteChannel.lock(0, 10, false); |
| |
| // Lock a shared range further in the same file. |
| FileLock flock2 = readWriteChannel.lock(22, 100, true); |
| |
| // The spec allows the impl to refuse shared locks |
| flock1.release(); |
| flock2.release(); |
| } |
| |
| public void test_tryLock() throws IOException { |
| try { |
| readOnlyChannel.tryLock(); |
| fail("Acquiring a full exclusive lock on a read channel should have thrown an exception."); |
| } catch (NonWritableChannelException ex) { |
| // Expected. |
| } |
| } |
| |
| public void test_tryLockLLZ() throws IOException { |
| // It is illegal to request an exclusive lock on a read-only channel |
| try { |
| readOnlyChannel.tryLock(0, 99, false); |
| fail("Acquiring exclusive lock on read-only channel should fail"); |
| } catch (NonWritableChannelException ex) { |
| // Expected |
| } |
| |
| // It is invalid to request a lock starting before the file start |
| try { |
| readOnlyChannel.tryLock(-99, 0, true); |
| fail("Acquiring an illegal lock value should fail."); |
| } catch (IllegalArgumentException ex) { |
| // expected |
| } |
| |
| // Acquire a valid lock |
| FileLock tmpLock = readOnlyChannel.tryLock(0, 10, true); |
| assertTrue(tmpLock.isValid()); |
| tmpLock.release(); |
| |
| // Acquire another valid lock -- and don't release it yet |
| FileLock lock = readOnlyChannel.tryLock(10, 788, true); |
| assertTrue(lock.isValid()); |
| |
| // Overlapping locks are illegal |
| try { |
| readOnlyChannel.tryLock(1, 23, true); |
| fail("Acquiring an overlapping lock should fail."); |
| } catch (OverlappingFileLockException ex) { |
| // Expected |
| } |
| |
| // Adjacent locks are legal |
| FileLock adjacentLock = readOnlyChannel.tryLock(1, 3, true); |
| assertTrue(adjacentLock.isValid()); |
| adjacentLock.release(); |
| |
| // Release longer lived lock |
| lock.release(); |
| } |
| } |