diff --git a/.vscode/tasks.json b/.vscode/tasks.json new file mode 100644 index 0000000..d1a8525 --- /dev/null +++ b/.vscode/tasks.json @@ -0,0 +1,26 @@ +{ + "version": "2.0.0", + "tasks": [ + { + "type": "shell", + "label": "g++ build active file", + "command": "/usr/bin/g++", + "args": [ + "-g", + "${file}", + "-o", + "${fileDirname}" + ], + "options": { + "cwd": "/home/barant/Development/HTTPServer/" + }, + "problemMatcher": [ + "$gcc" + ], + "group": { + "kind": "build", + "isDefault": true + } + } + ] + } \ No newline at end of file diff --git a/File.cpp b/File.cpp index e79f3b1..722ada1 100644 --- a/File.cpp +++ b/File.cpp @@ -2,40 +2,40 @@ #include "Exception.h" namespace coreutils { - + File::File(std::string fileName, int mode, int authority) { - + this->fileName = fileName; - + struct stat status; stat(fileName.c_str(), &status); - + buffer = NULL; - + setBufferSize(status.st_size); - - fd = open(fileName.c_str(), mode, authority); + + fd = open(fileName.c_str(), mode, authority); if(fd < 0) { std::stringstream temp; temp << "Error opening file " << fileName << "."; throw Exception(temp.str(), __FILE__, __LINE__); } } - + File::~File() { - + } - + void File::setBufferSize(size_t size) { buffer = (char *)realloc(buffer, size); this->size = size; } - + void File::read() { size = ::read(fd, buffer, size); - setBufferSize(size); + setBufferSize(size); } - + void File::write(std::string data) { ::write(fd, data.c_str(), data.length()); } @@ -43,5 +43,5 @@ namespace coreutils { std::string File::asString() { return std::string(buffer, size); } - + } diff --git a/IMFBody.h b/IMFBody.h index 3d7a218..8bd27d4 100644 --- a/IMFBody.h +++ b/IMFBody.h @@ -2,9 +2,9 @@ #define __IMFBody_h__ namespace coreutils { - + class IMFBody {}; - + } #endif diff --git a/IMFMessage.cpp b/IMFMessage.cpp index ef7421a..78ea512 100644 --- a/IMFMessage.cpp +++ b/IMFMessage.cpp @@ -5,51 +5,61 @@ #include "Log.h" namespace coreutils { - - IMFMessage::IMFMessage() {} - - IMFMessage::IMFMessage(PString &in) { + + IMFMessage::IMFMessage() { body = NULL; + first = true; + } + + IMFMessage::IMFMessage(PString &in) : IMFMessage() { parse(in); } - + bool IMFMessage::parse(PString &in) { coreutils::Log(coreutils::LOG_DEBUG_4) << "parse [" << in.str() << "]"; - if(in.str() != "") { - headers.emplace_back(in); + if(first) { + if(in.str().find(" ") != std::string::npos) { + parse(in); + first = false; + return true; + } + } + + if(in.str() != "") { + headers.emplace_back(in); return true; } coreutils::Log(coreutils::LOG_DEBUG_2) << "End of header with Content Type = " << getHeader("Content-Type") << " for " << getHeader("Content-Length") << " bytes."; - + std::string type = getHeader("Content-Type"); - + if(type.size() == 0) type = "text/plain"; - - if(type == "multipart/form-data") - body = new IMFMultipart(in, getHeaderKeyPairValue("Content-Type", "boundary")); + + if(type == "multipart/form-data") + body = new IMFMultipart(in, getHeaderKeyPairValue("Content-Type", "boundary")); else if(type == "text/plain") body = new IMFPlainText(in); - else + else body = new IMFBody(); return false; } - + void IMFMessage::output(std::stringstream &out) { for(IMFHeader header: headers) { out << header.getKey() << ": " << header.getValue() << "\r\n"; } out << "\r\n"; } - + void IMFMessage::addHeader(std::string key, std::string value) { headers.emplace_back(key, value); - + } - + std::string IMFMessage::getHeader(std::string key, bool valueOnly) { for(IMFHeader header: headers) { if(header.getKey() == key) { @@ -57,13 +67,13 @@ namespace coreutils { if(valueOnly) { std::vector split = PString(value).split(";"); value = split[0].str(); - } - return value; + } + return value; } } return std::string(""); } - + std::string IMFMessage::getHeaderKeyPairValue(std::string headerKey, std::string key) { std::string value; coreutils::PString psource(getHeader(headerKey, false)); @@ -75,30 +85,30 @@ namespace coreutils { if(token == key) { if(work.ifNext("\"")) { value = work.getTokenExclude("\""); - return value; + return value; } else { value = work.str(); return value; } } - else + else continue; - - + + } else if (work.ifNext(";") || work.ifNext(" ")) { - if(token == key) + if(token == key) return std::string("true"); else continue; - + } } return std::string("false"); } - + IMFBody * IMFMessage::getBody() { return body; } - + } diff --git a/IMFMessage.h b/IMFMessage.h index 897b0ec..243adbf 100644 --- a/IMFMessage.h +++ b/IMFMessage.h @@ -9,29 +9,32 @@ namespace coreutils { class IMFMessage { - + public: IMFMessage(); IMFMessage(PString &in); - + bool parse(PString &in); - + void output(std::stringstream &out); - IMFRequest *request; - + void addHeader(std::string key, std::string value); - + std::string getHeader(std::string key, bool valueOnly = true); std::string getHeaderKeyPairValue(std::string headerKey, std::string key); - + IMFBody *getBody(); - + protected: + IMFRequest request; std::vector headers; IMFBody *body; - + + private: + bool first = true; + }; - + } #endif diff --git a/IMFRequest.cpp b/IMFRequest.cpp index 6ae2a68..166111b 100644 --- a/IMFRequest.cpp +++ b/IMFRequest.cpp @@ -3,46 +3,37 @@ #include "Log.h" namespace coreutils { - + IMFRequest::IMFRequest() {} - + IMFRequest::IMFRequest(PString &in) { - method = in.getTokenExclude(" "); - if(!in.ifNext(" ")) - throw coreutils::Exception("Expecting space after method."); - uri = in.getTokenExclude(" "); - if(!in.ifNext(" ")) - throw coreutils::Exception("Expecting space after URI."); - protocol = in.str(); - - } - - std::string IMFRequest::getMethod() { - return method; - } - - void IMFRequest::setMethod(std::string method) { - this->method = method; - } - - std::string IMFRequest::getURI() { - return uri; - } - - void IMFRequest::setURI(std::string uri) { - this->uri = uri; - } - - std::string IMFRequest::getProtocol() { - return protocol; - } - - void IMFRequest::setProtocol(std::string protocol) { - this->protocol = protocol; + parse(in); } - void IMFRequest::output(std::stringstream &out) { - out << method << " " << uri << " " << protocol << "\r\n"; + bool IMFRequest::parse(PString &in) { + parts = in.split(" "); + return parts.size() == 3; + } + + std::string IMFRequest::getMethod() { + if(parts.size() == 3) + return parts[0].str(); + else + return NULL; + } + + std::string IMFRequest::getURI() { + if(parts.size() == 3) + return parts[1].str(); + else + return NULL; + } + + std::string IMFRequest::getProtocol() { + if(parts.size() == 3) + return parts[2].str(); + else + return NULL; } } diff --git a/IMFRequest.h b/IMFRequest.h index 74d724f..0ac6b20 100644 --- a/IMFRequest.h +++ b/IMFRequest.h @@ -11,22 +11,17 @@ namespace coreutils { IMFRequest(); IMFRequest(PString &in); + bool parse(PString &in); + std::string getMethod(); - void setMethod(std::string method); std::string getURI(); - void setURI(std::string uri); std::string getProtocol(); - void setProtocol(std::string protocol); - - void output(std::stringstream &out); private: - std::string method; - std::string uri; - std::string protocol; - + std::vector parts; + }; - + } #endif diff --git a/PString.cpp b/PString.cpp index 8513a90..6eb34b9 100644 --- a/PString.cpp +++ b/PString.cpp @@ -5,7 +5,7 @@ namespace coreutils { PString::PString() { } - + PString::PString(std::string pstring) { this->pstring = pstring; } @@ -13,29 +13,29 @@ namespace coreutils { std::vector & PString::getList() { return list; } - + std::string PString::str() { return pstring.substr(cursor); } std::vector PString::split(std::string delimiter, int maxSize) { list.clear(); - + if(pstring.size() == 0) { list.push_back(PString("")); return list; - } - + } + size_t end; size_t pos = cursor; - + while(pos < pstring.length()) { end = pstring.find(delimiter, pos); if(end == -1) end = pstring.length(); list.push_back(PString(pstring.substr(pos, end - pos))); pos = end + delimiter.size(); - if(pos > pstring.size()) + if(pos > pstring.size()) break; if(maxSize != 0) { if(list.size() >= maxSize) { @@ -43,42 +43,42 @@ namespace coreutils { break; } } - } + } return list; - } - + } + std::string PString::getTokenInclude(std::string include) { int start = cursor; cursor = pstring.find_first_not_of(include, cursor); return pstring.substr(start, cursor - start); } - + std::string PString::getTokenExclude(std::string exclude) { int start = cursor; cursor = pstring.find_first_of(exclude, cursor); - if(cursor == -1) + if(cursor == -1) cursor = pstring.size(); - return pstring.substr(start, cursor - start); + return pstring.substr(start, cursor - start); } coreutils::PString PString::operator[](int index) { - return list[index]; + return list[index]; } bool PString::eod() { return cursor >= pstring.size(); } - + bool PString::ifNext(std::string value) { bool test = (value == pstring.substr(cursor, value.length())); - if(test) + if(test) cursor += value.size(); return test; } - + int PString::skipWhitespace() { size_t temp = cursor; - cursor = pstring.find_first_not_of(" \t", cursor); + cursor = pstring.find_first_not_of(" \t", cursor); cursor = cursor == -1 ? temp: cursor; coreutils::Log(coreutils::LOG_DEBUG_2) << "Skipping whitespace for " << (cursor - temp) << " spaces."; return cursor - temp; diff --git a/PString.h b/PString.h index 11611e2..43495c6 100644 --- a/PString.h +++ b/PString.h @@ -7,101 +7,101 @@ namespace coreutils { /// /// Use the PString object when advanced parsing algorithms are required to simplify - /// parsing. Two methods of parsing are available within the PString object. One - /// method involves using the split method to divide the string into several PString - /// objects. Split separates the string based upon a delimiter. Another method employs - /// the use of the getToken methods provided to move to through the string and assign + /// parsing. Two methods of parsing are available within the PString object. One + /// method involves using the split method to divide the string into several PString + /// objects. Split separates the string based upon a delimiter. Another method employs + /// the use of the getToken methods provided to move to through the string and assign /// values based upon the followed path. /// - + class PString { - + public: - + /// /// /// - + PString(); - + /// /// /// - + PString(std::string pstring); /// /// /// - - std::vector & getList(); + + std::vector & getList(); /// /// /// - + std::string str(); - - /// - /// - /// - - std::vector split(std::string delimiter, int maxSize = 0); /// /// /// - + + std::vector split(std::string delimiter, int maxSize = 0); + + /// + /// + /// + std::string getTokenInclude(std::string include); /// /// /// - + std::string getTokenExclude(std::string exclude); /// /// /// - + coreutils::PString operator[](int index); - + /// /// /// - + bool eod(); - + /// /// /// - + bool ifNext(std::string value); - + /// /// /// - - int skipWhitespace(); - + + int skipWhitespace(); + /// /// /// - + int cursor = 0; - + /// /// /// - + int size(); private: std::string pstring; std::vector list; - + }; - + } #endif diff --git a/compile b/compile index 9121962..930a795 100755 --- a/compile +++ b/compile @@ -3,17 +3,17 @@ for file in *.cpp do filename="${file%.*}" - list="$list $filename.o" + list="$list $filename.o" echo -n "Compiling $filename..." - g++ -g -c $file + g++ -g -c $file if [ $? = '0' ] then echo "OK" else echo "ERROR" exit -1 - fi - + fi + done wait @@ -25,6 +25,6 @@ then else echo "ERROR" exit -1 -fi +fi