Project : Peer-to-Peer (P2P) File Sharing System with Messaging (template)(FAQ)(Testing and Grading for phase1) (Testing and Grading for phase2)

Phase 1: Messenger with P2P tree framework(Complete sockcomm.c, and steps 1-16 ,21 and 25 in peer.c)

Due: 24th March (midnight)


Phase 2: P2P File retrieval (Complete remaining steps in peer.c)

Due: 21st April (midnight)

In this programming assignment, you are asked to develop a simple peer-to-peer (p2p) file sharing system that emulates the behavior of Gnutella with simple messaging facility. The objective of this project is to let you get hands-on experiences in computer network programming, in particular, socket programming, and in network application development.

You are asked to develop only one program, called 'peer'. Multiple hosts execute their own copy of this program in certain order (which will be elaborated later) to form a p2p system. We call such a host with a running 'peer' program as a 'peer host'. Every peer host designates a directory containing several files as its shared directory when it started. Once a peer-to-peer system is set up, any peer host can use command 'get ' to download the specified file from some peer host holding the file. In order to simplify the problem, we assume all shared files have distinct file names.

What you need to do?
You are provided with template source codes: peer.c, peer.h, sockcomm.c and sockcomm.h. In peer.c and sockcomm.c, you can follow the instructions to fill missing parts. You are responsible for declaring additional variables and for adding some code blocks if necessary.

You are also provided with a compiled binary code 'peer'. It can be executed on SunOS machines. You can follow the example in the later part of this description to see how the program is supposed to behave.

You are not restricted to work on the template provided. As long as your final program has the same function of 'peer' (including output messages), it will be acceptable. Any programming language is acceptable.

In order to compile your program, put files peer.c, sockcomm.c, sockcomm.h and Makefile under the same directory. Change your current working directory to that directory. Type command "make" and you will get binary code "peer". You can also use command line "gcc -lsocket -lnsl peer.c sockcomm.c -o peer" under Solaris, or use "gcc -lnsl peer.c sockcomm.c -o peer" under Linux.

If you don't have 'gcc' on your CS or itlab machine, that is, only because you haven't loaded the module yet. You can load the module using command 'module load soft/egcs/3.4'. In order to avoid doing this repeatedly, you can add this command line into your '.cshrc' file that is under your home directory.

Forming a P2P System:
The SYNOPSIS of the 'peer' program is as follows:

   peer pathname [ hostname ]

pramod@venus (~) % mkdir /home/grad05/pramod/venus
pramod@venus (~) % echo "this is mydoc1" > /home/grad05/pramod/venus/mydoc1

pramod@mercury (~) % mkdir /home/grad05/pramod/mercury
pramod@mercury (~) % echo "this is mydoc2" > /home/grad05/pramod/mercury/mydoc2

pramod@atto (~) % mkdir /home/grad05/pramod/atto
pramod@atto (~) % echo "this is mydoc3" > /home/grad05/pramod/atto/mydoc3

pramod@caesar (~) % mkdir /home/grad05/pramod/caesar
pramod@caesar (~) % echo "this is mydoc4" > /home/grad05/pramod/caesar/mydoc4

pramod@venus (~) % peer venus

pramod@mercury (~) % peer mercury venus.cs.umn.edu

pramod@atto (~) % peer atto mercury.cs.umn.edu

pramod@caesar (~) % peer caesar mercury.cs.umn.edu

get mydoc4

The file 'mydoc4' is downloaded from 'caesar' to 'venus' and stored in the cwd (current working directory) of the 'peer' program. In my example, you can find the downloaded file at '/home/grad05/pramod/venus/mydoc4'. The following figure shows how the peer-to-peer system looks like following aforementioned steps.

 

Joining the P2P System:
In our system, a new peer host can join the existing p2p system from any present peer host in the system. Therefore, every peer host has to have a listen socket to accept connection request from new peers. In our program, every peer host has a listen socket on port for this purpose (port # 10419 in case of example peer, pick a random port to avoid running into conflicts). A TCP connection is set up between the new peer host and its joining peer host. They are called a 'neighbor' to each other.

 

 


Figure 1. A Tree-based P2P System

Chat service:

After the peer-to-peer system is setup, a user can type command like 'IM aqua Hello World' on a peer which is directly connected to aqua. Only aqua will receive this message along with information about the sender. If any peer wants to send a message to every other node in the peer-2-peer tree, the client can type 'IM broadcast Hello World'. All directly connected nodes/peers receive this message and they intern broadcast this message to all of their other directly connected peers. This way the message propagates through the peer-2-peer tree and reaches every node in the system.

Lookup service:

After the peer-to-peer system is set up, a user can type command like 'get mydoc4' on a peer host to download the specified file. This actually involves two steps - lookup and download. The lookup service used in our simple file sharing system is based on flooding. In the previous example, after 'get mydoc4' is input on peer host 'venus', a message looks like 'GET mydoc4 128.101.189.164 36953' is constructed. In this message, '128.101.189.164' is the IP address of host 'venus'. '36953' is the port number of the listen socket that 'venus' has created to set up a data channel (or TCP connection) with the peer which has 'mydoc4'.

This message is flooded to all neighbors of 'venus'. For every peer host receiving this message, they first do a local lookup to see whether the specified file is in its shared directory. If it is not there, the peer host forwards the same message to all of its known neighbors, except the one from which it got the message. If the specified file is in a peer host's shared directory, it makes a connection request to the originating peer host whose IP address and port number is in the message (in our example, it should make a connection to host 128.101.189.164 at port 36953). Once the connection is set up, the requested file is sent in multiple IP packets in the case where the file's size is bigger than 1500 bytes.

Download Files considering Timeout:
A new listen socket needs to be created when a 'get' command is received from stdin. Each time, the port number will be different so it is included in the "GET" message. Since such listen sockets have timeout requirement, a new process is created using fork(). The new process uses a select() with timeout period, e.g., 10 seconds, to wait for connection requests on the listen socket. In our example, 'venus' creates a listen socket waiting for connection request from some peer host holding 'mydoc4'. However, it's possible that 'mydoc4' doesn't exist in any peer host. To handle this case, such listen socket has a timeout period, for example, 10 seconds. If there is no connection setup after timeout, the listen socket is closed and a message "admin: the requested file doesn't exist in the p2p system" is displayed. On the other hand, when the download is completed, the child process should display a message "the requested file has been downloaded successfully". Like this, this fork structure should allow the user to request a new file while the previously requested files are being downloaded from peers.

Servicing the Files downloaded from Other Peers:
When a peer downloaded a new file from other peer, the file can be provided to other peers which request it. Therefore, you need to update the file list after completing each download. For example, in Figure.1, assume that 'mercury' downloaded 'mydoc4' from 'caesar' and 'atto' requests 'mydoc4'. Since 'caesar' has 'mydoc4' now, it can provide it for 'atto' instead of 'caesar'.

Support of Transfer of Big File:
You should support the transfer of big file, such as an mp3 file of 3MB. You need to make a loop structure in the sending and receiving sides in order to allow for the multiple transfers of file packets.

Terminate a Peer Host:
Use 'Ctrl-C' to terminate a copy of 'peer'. It is required the termination to be handled gracefully, e.g., the connected neighbor(s) should display message like "admin: disconnected from 'mercury.cs.umn.edu(35032)'". Be assured that there is no crash on any neighboring peers.