Introduction

In this lab, you will continue to add functionality to your file server. You will:

Getting Started

Since you are building on the previous labs, ensure the code in your Lab 3 directory passes all tests for Labs 1, 2, and 3 before starting in on this lab.

Begin by initializing your Lab 4 directory with your implementation from Lab 3 and then updating it with the testers from http://www.news.cs.nyu.edu/~jinyang/fa08/labs/yfs-lab4.tgz for Lab 4.

% cd ~/yfs
% wget -nc http://www.news.cs.nyu.edu/~jinyang/fa08/labs/yfs-lab4.tgz
% rsync -av l3/* l4
% tar xzvf yfs-lab4.tgz

Note that new lab files will overwrite Makefile in the l4 directory, in order to link lock_client.o in with yfs_server. So, if you modified the Lab 3 Makefile, you will need to redo those changes in l4/Makefile.

The rest of this lab has two parts.

Part 1: MKDIR,REMOVE

Part 1: Your Job

Your job in part 1 is to handle the MKDIR and REMOVE FUSE operations. This should be a straightforward extension of your Lab 3 code. Make sure that when you choose the inumber for a new directory created with MKDIR, that inumber must have its most significant bit set to 0 (as explained in Lab 2, unless you changed the way YFS tells files and directories apart). When you're done with Part 1, the following should work:

% ./start.sh
% mkdir yfs1/newdir
% echo hi > yfs1/newdir/newfile
% ls yfs1/newdir/newfile
yfs1/newdir/newfile
% rm yfs1/newdir/newfile
% ls yfs1/newdir
% ./stop.sh

If your implementation passes the test-lab-4-a.pl script, you are done with part 1. The test script creates a directory, creates and deletes lots of files in the directory, and checks file and directory mtimes and ctimes. Note that this is the first test that explicitly checks the correctness of these time attributes. A create should change both the parent directory's mtime and ctime. Here is a successful run of the tester:

% ./start.sh
% ./test-lab-4-a.pl ./yfs1
mkdir ./yfs1/d3319
create x-0
delete x-0
create x-1
checkmtime x-1
...
delete x-33
dircheck
Passed all tests!
% ./stop.sh

Par 2: Locking

Next, you are going to ensure the consistency of your file system when many clients simultaneously perform file system operations on the same file system image via different yfs_client processes. Your current implementation does not handle concurrent operations correctly. For example, your yfs_client's create method probably reads the directory's contents from the extent server, makes some changes or additions, and stores the new contents at the extent server. Suppose two clients issue simultaneous CREATEs for different file names in the same directory via different yfs_client processes. Both yfs_client processes might fetch the old dir contents at the same time and each inserts the newly created file for its client and writes back the new dir contents. As a result, only one of the file would be present in the dir in the end. The correct answer, however, is for both files to exist. The CREATE example is just one of the "race conditions". Many others exist: e.g. concurrent CREATE and UNLINK, concurrent MKDIR and LOOKUP, etc.

To fix the race conditions, the yfs_client must use locks to ensure that the two operations that access the same file or directory happen one at a time. For example, a yfs_client would acquire a lock before starting the CREATE, and only release the lock after finishing the write of the new information back to the extent server. If there are concurrent operations, the locks force one of the two operations to delay until the other one has completed. Because each yfs_client can run as a separate process on a different machine, all yfs_clients have to acquire locks from the same lock server. Now you can see why the lock server implementation from Lab1 comes in handy!

Part 2: Your Job

Your job is to implement locking for yfs_client to ensure that concurrent operations from different yfs_clients proceed correctly. The testers for this part of the lab are test-lab-4-b and test-lab-4-c (The source files are test-lab-4-b.c and test-lab-4-c.c). The testers take two directories as arguments and issue concurrent operations in the two directories and check that the results are consistent with the operations executing in some serial order. Here's a successful execution of the testers:

% ./start.sh
% ./test-lab-4-b ./yfs1 ./yfs2
Create then read: OK
Unlink: OK
Append: OK
Readdir: OK
Many sequential creates: OK
Write 20000 bytes: OK
Concurrent creates: OK
Concurrent creates of the same file: OK
Concurrent create/delete: OK
Concurrent creates, same file, same server: OK
test-lab-4-b: Passed all tests.
% ./stop.sh
%
% ./start.sh
% ./test-lab-4-c ./yfs1 ./yfs2
Create/delete in separate directories: tests completed OK
% ./stop.sh

If you try this before you add locking, it will fail at "Concurrent creates" test in test-lab-4-b.

After you are done with part 2, you should also test with test-lab-4-a.pl to make sure you didn't break anything. You might also test with test-lab-4-b with the same directory for both arguments, to make sure you handle concurrent operations correctly with only one server before you go on to test concurrent operations in two servers.

Part 2: Detailed Guidance

Handin procedure

Tar your l4/ files with the following commands:

cd ~/yfs/l4
make clean
cd ..
tar czvf yfs-lab4.tgz l4/
Go to submit site to upload yfs-lab4.tgz

For questions or comments, email dss-staff@cs.nyu.edu.