Recently, I'd been observing something interesting on our environment AIX 7.1. In an attempt to track down the issue, I created a small locking application in Java:
import java.io.File;
import java.io.RandomAccessFile;
import java.nio.channels.FileChannel;
import java.nio.channels.FileLock;
import java.nio.channels.OverlappingFileLockException;
public class Locker {
public static void main(String[] args) throws Exception {
File file = new File("/etc/passwd");
FileChannel channel = new RandomAccessFile(file, "rw").getChannel();
FileLock lock;
try {
lock = channel.tryLock();
if (lock != null) {
System.out.println("I have the lock");
while(true) {}
}
} catch (OverlappingFileLockException e) {
e.printStackTrace();
}
}
}
As far as I can tell, this gets a read-write lock on /etc/passwd. If I try to run two instances of this application, I can only get the lock in one instance as expected. Similarly, if I run this command:
su user2 -c echo test
The command hangs until I release the lock from the Java application. On the other hand, reading the file with:
cat /etc/passwd
runs successfully. And even writing to the file with:
cat /etc/passwd > /etc/passwd
is fine as well. Now, clearly the Java FileLock implementation is system dependent and there is no specified behaviour due to this nature. However, what I'm curious about is why 'su' needed to wait. Is it possible that the 'cat' redirection simply deletes the file and recreates it with the new output or is this simply a case of the locking mechanism being inconsistent across commands?
Edit: Since asking the question I added some write statements to the Java application so the structure of the program was as follows:
Acquire Java Lock on /etc/passwd
IO-Redirect with a small change to /etc/passwd
Append some text to /etc/passwd in the Java application
And all this info was reflected in the updated /etc/passwd, so it appears that the IO-Redirection was not simply deleting the file. Therefore, why the difference between 'su' and '>' (and presumably many other things)?