namespace imtiaz
{
using system;
using system.io;
using system.net;
using system.net.sockets;
using system.text;
using system.threading ;
class mywebserver
{
private tcplistener mylistener ;
private int port = 5050 ; // select any free port you wish
//the constructor which make the tcplistener start listening on the
//given port. it also calls a thread on the method startlisten().
public mywebserver()
{
try
{
//start listing on the given port
mylistener = new tcplistener(port) ;
mylistener.start();
console.writeline("web server running... press ^c to stop...");
//start the thread which calls the method 'startlisten'
thread th = new thread(new threadstart(startlisten));
th.start() ;
}
catch(exception e)
{
console.writeline("an exception occurred while listening :" +e.tostring());
}
}
/// <summary>
/// returns the default file name
/// input : webserverroot folder
/// output: default file name
/// </summary>
/// <param name="smywebserverroot"></param>
/// <returns></returns>
public string getthedefaultfilename(string slocaldirectory)
{
streamreader sr;
string sline = "";
try
{
//open the default.dat to find out the list
// of default file
sr = new streamreader("data//default.dat");
while ((sline = sr.readline()) != null)
{
//look for the default file in the web server root folder
if (file.exists( slocaldirectory + sline) == true)
break;
}
}
catch(exception e)
{
console.writeline("an exception occurred : " + e.tostring());
}
if (file.exists( slocaldirectory + sline) == true)
return sline;
else
return "";
}
/// <summary>
/// this function takes filename as input and returns the mime type..
/// </summary>
/// <param name="srequestedfile">to indentify the mime type</param>
/// <returns>mime type</returns>
public string getmimetype(string srequestedfile)
{
streamreader sr;
string sline = "";
string smimetype = "";
string sfileext = "";
string smimeext = "";
// convert to lowercase
srequestedfile = srequestedfile.tolower();
int istartpos = srequestedfile.indexof(".");
sfileext = srequestedfile.substring(istartpos);
try
{
//open the vdirs.dat to find out the list virtual directories
sr = new streamreader("data//mime.dat");
while ((sline = sr.readline()) != null)
{
sline.trim();
if (sline.length > 0)
{
//find the separator
istartpos = sline.indexof(";");
// convert to lower case
sline = sline.tolower();
smimeext = sline.substring(0,istartpos);
smimetype = sline.substring(istartpos + 1);
if (smimeext == sfileext)
break;
}
}
}
catch (exception e)
{
console.writeline("an exception occurred : " + e.tostring());
}
if (smimeext == sfileext)
return smimetype;
else
return "";
}
/// <summary>
/// returns the physical path
/// </summary>
/// <param name="smywebserverroot">web server root directory</param>
/// <param name="sdirname">virtual directory </param>
/// <returns>physical local path</returns>
public string getlocalpath(string smywebserverroot, string sdirname)
{
streamreader sr;
string sline = "";
string svirtualdir = "";
string srealdir = "";
int istartpos = 0;
//remove extra spaces
sdirname.trim();
// convert to lowercase
smywebserverroot = smywebserverroot.tolower();
// convert to lowercase
sdirname = sdirname.tolower();
//remove the slash
//sdirname = sdirname.substring(1, sdirname.length - 2);
try
{
//open the vdirs.dat to find out the list virtual directories
sr = new streamreader("data//vdirs.dat");
while ((sline = sr.readline()) != null)
{
//remove extra spaces
sline.trim();
if (sline.length > 0)
{
//find the separator
istartpos = sline.indexof(";");
// convert to lowercase
sline = sline.tolower();
svirtualdir = sline.substring(0,istartpos);
srealdir = sline.substring(istartpos + 1);
if (svirtualdir == sdirname)
{
break;
}
}
}
}
catch(exception e)
{
console.writeline("an exception occurred : " + e.tostring());
}
console.writeline("virtual dir : " + svirtualdir);
console.writeline("directory : " + sdirname);
console.writeline("physical dir: " + srealdir);
if (svirtualdir == sdirname)
return srealdir;
else
return "";
}
/// <summary>
/// this function send the header information to the client (browser)
/// </summary>
/// <param name="shttpversion">http version</param>
/// <param name="smimeheader">mime type</param>
/// <param name="itotbytes">total bytes to be sent in the body</param>
/// <param name="mysocket">socket reference</param>
/// <returns></returns>
public void sendheader(string shttpversion, string smimeheader, int itotbytes, string sstatuscode, ref socket mysocket)
{
string sbuffer = "";
// if mime type is not provided set default to text/html
if (smimeheader.length == 0 )
{
smimeheader = "text/html"; // default mime type is text/html
}
sbuffer = sbuffer + shttpversion + sstatuscode + "/r/n";
sbuffer = sbuffer + "server: cx1193719-b/r/n";
sbuffer = sbuffer + "content-type: " + smimeheader + "/r/n";
sbuffer = sbuffer + "accept-ranges: bytes/r/n";
sbuffer = sbuffer + "content-length: " + itotbytes + "/r/n/r/n";
byte[] bsenddata = encoding.ascii.getbytes(sbuffer);
sendtobrowser( bsenddata, ref mysocket);
console.writeline("total bytes : " + itotbytes.tostring());
}
/// <summary>
/// overloaded function, takes string, convert to bytes and calls
/// overloaded sendtobrowserfunction.
/// </summary>
/// <param name="sdata">the data to be sent to the browser(client)</param>
/// <param name="mysocket">socket reference</param>
public void sendtobrowser(string sdata, ref socket mysocket)
{
sendtobrowser (encoding.ascii.getbytes(sdata), ref mysocket);
}
/// <summary>
/// sends data to the browser (client)
/// </summary>
/// <param name="bsenddata">byte array</param>
/// <param name="mysocket">socket reference</param>
public void sendtobrowser(byte[] bsenddata, ref socket mysocket)
{
int numbytes = 0;
try
{
if (mysocket.connected)
{
if (( numbytes = mysocket.send(bsenddata, bsenddata.length,0)) == -1)
console.writeline("socket error cannot send packet");
else
{
console.writeline("no. of bytes send {0}" , numbytes);
}
}
else
console.writeline("connection dropped....");
}
catch (exception e)
{
console.writeline("error occurred : {0} ", e );
}
}
// application starts here..
public static void main()
{
mywebserver mws = new mywebserver();
}
//this method accepts new connection and
//first it receives the welcome massage from the client,
//then it sends the current date time to the client.
public void startlisten()
{
int istartpos = 0;
string srequest;
string sdirname;
string srequestedfile;
string serrormessage;
string slocaldir;
string smywebserverroot = "c://mywebserverroot//";
string sphysicalfilepath = "";
string sformattedmessage = "";
string sresponse = "";
while(true)
{
//accept a new connection
socket mysocket = mylistener.acceptsocket() ;
console.writeline ("socket type " + mysocket.sockettype );
if(mysocket.connected)
{
console.writeline("/nclient connected!!/n==================/nclient ip {0}/n",
mysocket.remoteendpoint) ;
//make a byte array and receive data from the client
byte[] breceive = new byte[1024] ;
int i = mysocket.receive(breceive,breceive.length,0) ;
//convert byte to string
string sbuffer = encoding.ascii.getstring(breceive);
//at present we will only deal with get type
if (sbuffer.substring(0,3) != "get" )
{
console.writeline("only get method is supported..");
mysocket.close();
return;
}
// look for http request
istartpos = sbuffer.indexof("http",1);
// get the http text and version e.g. it will return "http/1.1"
string shttpversion = sbuffer.substring(istartpos,8);
// extract the requested type and requested file/directory
srequest = sbuffer.substring(0,istartpos - 1);
//replace backslash with forward slash, if any
srequest.replace("file:////","/");
//if file name is not supplied add forward slash to indicate
//that it is a directory and then we will look for the
//default file name..
if ((srequest.indexof(".") <1) && (!srequest.endswith("/")))
{
srequest = srequest + "/";
}
//extract the requested file name
istartpos = srequest.lastindexof("/") + 1;
srequestedfile = srequest.substring(istartpos);
//extract the directory name
sdirname = srequest.substring(srequest.indexof("/"), srequest.lastindexof("/")-3);
/////////////////////////////////////////////////////////////////////
// identify the physical directory
/////////////////////////////////////////////////////////////////////
if ( sdirname == "/")
slocaldir = smywebserverroot;
else
{
//get the virtual directory
slocaldir = getlocalpath(smywebserverroot, sdirname);
}
console.writeline("directory requested : " + slocaldir);
//if the physical directory does not exists then
// dispaly the error message
if (slocaldir.length == 0 )
{
serrormessage = "<h2>error!! requested directory does not exists</h2><br>";
//serrormessage = serrormessage + "please check data//vdirs.dat";
//format the message
sendheader(shttpversion, "", serrormessage.length, " 404 not found", ref mysocket);
//send to the browser
sendtobrowser(serrormessage, ref mysocket);
mysocket.close();
continue;
}
/////////////////////////////////////////////////////////////////////
// identify the file name
/////////////////////////////////////////////////////////////////////
//if the file name is not supplied then look in the default file list
if (srequestedfile.length == 0 )
{
// get the default filename
srequestedfile = getthedefaultfilename(slocaldir);
if (srequestedfile == "")
{
serrormessage = "<h2>error!! no default file name specified</h2>";
sendheader(shttpversion, "", serrormessage.length, " 404 not found", ref mysocket);
sendtobrowser ( serrormessage, ref mysocket);
mysocket.close();
return;
}
}
/////////////////////////////////////////////////////////////////////
// get themime type
/////////////////////////////////////////////////////////////////////
string smimetype = getmimetype(srequestedfile);
//build the physical path
sphysicalfilepath = slocaldir + srequestedfile;
console.writeline("file requested : " + sphysicalfilepath);
if (file.exists(sphysicalfilepath) == false)
{
serrormessage = "<h2>404 error! file does not exists...</h2>";
sendheader(shttpversion, "", serrormessage.length, " 404 not found", ref mysocket);
sendtobrowser( serrormessage, ref mysocket);
console.writeline(sformattedmessage);
}
else
{
int itotbytes=0;
sresponse ="";
filestream fs = new filestream(sphysicalfilepath, filemode.open, fileaccess.read, fileshare.read);
// create a reader that can read bytes from the filestream.
binaryreader reader = new binaryreader(fs);
byte[] bytes = new byte[fs.length];
int read;
while((read = reader.read(bytes, 0, bytes.length)) != 0)
{
// read from the file and write the data to the network
sresponse = sresponse + encoding.ascii.getstring(bytes,0,read);
itotbytes = itotbytes + read;
}
reader.close();
fs.close();
sendheader(shttpversion, smimetype, itotbytes, " 200 ok", ref mysocket);
sendtobrowser(bytes, ref mysocket);
//mysocket.send(bytes, bytes.length,0);
}
mysocket.close();
}
}
}
}
}