Browse Source

save 22-11-6-2

test
nicolas-arnaud 2 years ago
parent
commit
48087a2563
  1. 5
      includes/Env.hpp
  2. 42
      includes/Nodes.hpp
  3. 21
      includes/Parser.hpp
  4. 2
      includes/Route.hpp
  5. 6
      includes/Server.hpp
  6. 18
      includes/Socket.hpp
  7. 38
      includes/Token.hpp
  8. 159
      srcs/json/Nodes.cpp
  9. 359
      srcs/json/Parser.cpp
  10. 176
      srcs/json/Token.cpp
  11. 46
      srcs/load/Env.cpp
  12. 4
      srcs/load/Route.cpp
  13. 49
      srcs/load/Server.cpp
  14. 162
      srcs/load/Socket.cpp
  15. 17
      srcs/tools.cpp
  16. 25
      srcs/webserv.cpp

5
includes/Env.hpp

@ -2,9 +2,10 @@
#include "webserv.hpp"
class Env {
std::vector<Server *> _servers;
std::vector<Server *> _servers;
public:
Env(JSONNode *conf);
Env(JSONNode *conf);
void set_fds();
void refresh();
};

42
includes/Nodes.hpp

@ -3,30 +3,30 @@
class JSONNode {
public:
JSONObject obj();
JSONList lst();
string str();
int nbr();
JSONObject obj();
JSONList lst();
string str();
int nbr();
bool boo();
private:
enum Type { OBJECT, LIST, STRING, NUMBER, BOOLEAN, NULL_TYPE };
union Values {
JSONObject *object;
JSONList *list;
string *str;
int nbr;
bool bValue;
} values;
Type type;
enum Type { OBJECT, LIST, STRING, NUMBER, BOOLEAN, NULL_TYPE };
union Values {
JSONObject *object;
JSONList *list;
string *str;
int nbr;
bool bValue;
} values;
Type type;
void setObject(JSONObject *object);
void setList(JSONList *list);
void setString(string *str);
void setNumber(int nbr);
void setBoolean(bool v);
void setNull();
void setObject(JSONObject *object);
void setList(JSONList *list);
void setString(string *str);
void setNumber(int nbr);
void setBoolean(bool v);
void setNull();
string stringify(int indentationLevel);
friend class JSONParser;
string stringify(int indentationLevel);
friend class JSONParser;
};

21
includes/Parser.hpp

@ -1,18 +1,17 @@
#pragma once
#include "webserv.hpp"
class JSONParser {
std::fstream file;
Tokenizer tokenizer;
std::fstream file;
Tokenizer tokenizer;
public:
JSONParser(const string filename);
JSONNode *parse();
JSONNode *parseObject();
JSONNode *parseList();
JSONNode *parseString();
JSONNode *parseNumber();
JSONNode *parseBoolean();
JSONNode *parseNull();
JSONParser(const string filename);
JSONNode *parse();
JSONNode *parseObject();
JSONNode *parseList();
JSONNode *parseString();
JSONNode *parseNumber();
JSONNode *parseBoolean();
JSONNode *parseNull();
};

2
includes/Route.hpp

@ -2,10 +2,12 @@
#include "webserv.hpp"
class Route {
protected:
string _root;
string _ret;
std::vector<string> _indexs;
bool _autoindex;
public:
Route(JSONNode *datas);
~Route(void);

6
includes/Server.hpp

@ -1,9 +1,9 @@
#pragma once
#include "webserv.hpp"
class Server: public Route{
string _name;
std::vector<Socket *> _sockets;
class Server : public Route {
string _name;
std::vector<Socket *> _sockets;
std::map<string, Route *> _routes;
public:

18
includes/Socket.hpp

@ -2,13 +2,14 @@
#include "webserv.hpp"
class Socket {
Server *_server;
string _ip;
int _port;
int _master_socket;
struct sockaddr_in _address;
int _clients_amount;
std::vector<int> _clients;
Server *_server;
string _ip;
int _port;
int _master_socket;
struct sockaddr_in _address;
int _clients_amount;
std::vector<int> _clients;
public:
static fd_set _readfds;
static int _max_fd;
@ -30,6 +31,3 @@ class Socket {
}
*/
};

38
includes/Token.hpp

@ -2,31 +2,31 @@
#include "webserv.hpp"
enum TOKEN {
CURLY_OPEN,
CURLY_CLOSE,
COLON,
STRING,
NUMBER,
ARRAY_OPEN,
ARRAY_CLOSE,
COMMA,
BOOLEAN,
NULL_TYPE
CURLY_OPEN,
CURLY_CLOSE,
COLON,
STRING,
NUMBER,
ARRAY_OPEN,
ARRAY_CLOSE,
COMMA,
BOOLEAN,
NULL_TYPE
};
typedef struct Token_s {
string value;
TOKEN type;
string value;
TOKEN type;
} Token;
class Tokenizer {
std::fstream file;
size_t prevPos;
std::fstream file;
size_t prevPos;
public:
Tokenizer(string fileName);
bool hasMoreTokens();
char getWithoutWhiteSpace();
void rollBackToken();
Token getToken();
Tokenizer(string fileName);
bool hasMoreTokens();
char getWithoutWhiteSpace();
void rollBackToken();
Token getToken();
};

159
srcs/json/Nodes.cpp

@ -1,111 +1,110 @@
#include "webserv.hpp"
#define DEBUG 0
JSONObject JSONNode::obj() {
if (type == OBJECT)
return *values.object;
throw std::logic_error("Improper return");
if (type == OBJECT)
return *values.object;
throw std::logic_error("Improper return");
}
JSONList JSONNode::lst() {
if (type == LIST)
return *values.list;
throw std::logic_error("Improper return");
if (type == LIST)
return *values.list;
throw std::logic_error("Improper return");
}
string JSONNode::str() {
if (type == STRING)
return *values.str;
throw std::logic_error("Improper return");
if (type == STRING)
return *values.str;
throw std::logic_error("Improper return");
}
int JSONNode::nbr() {
if (type == NUMBER)
return values.nbr;
throw std::logic_error("Improper return");
if (type == NUMBER)
return values.nbr;
throw std::logic_error("Improper return");
}
bool JSONNode::boo() {
if (type == BOOLEAN)
return values.bValue;
throw std::logic_error("Improper return");
throw std::logic_error("Improper return");
}
void JSONNode::setObject(JSONObject *object) {
this->values.object = object;
type = OBJECT;
this->values.object = object;
type = OBJECT;
}
void JSONNode::setList(JSONList *list) {
this->values.list = list;
type = LIST;
this->values.list = list;
type = LIST;
}
void JSONNode::setString(string *str) {
this->values.str = str;
type = STRING;
this->values.str = str;
type = STRING;
}
void JSONNode::setNumber(int nbr) {
this->values.nbr = nbr;
type = NUMBER;
this->values.nbr = nbr;
type = NUMBER;
}
void JSONNode::setBoolean(bool v) {
this->values.bValue = v;
type = BOOLEAN;
this->values.bValue = v;
type = BOOLEAN;
}
void JSONNode::setNull() { type = NULL_TYPE; }
string JSONNode::stringify(int indentationLevel) {
string spaceString = string(indentationLevel, ' ');
// sstreams
std::stringstream output;
// cout < type << "\n";
switch (type) {
case STRING: {
output << spaceString << *values.str;
break;
}
case NUMBER: {
output << spaceString << values.nbr;
break;
}
case BOOLEAN: {
output << spaceString << (values.bValue ? "true" : "false");
break;
}
case NULL_TYPE: {
output << spaceString << "null";
break;
}
case LIST: {
// cout << "[";
output << spaceString << "[\n";
unsigned int index = 0;
for (JSONList::iterator i = (*values.list).begin();
i != (*values.list).end(); i++) {
output << (*i)->stringify(indentationLevel + 1);
if (index < (*values.list).size() - 1) {
output << ",\n";
}
index++;
};
output << "\n" << spaceString << "]\n";
break;
}
case OBJECT: {
output << spaceString << "{\n";
for (JSONObject::iterator i = (*values.object).begin();
i != (*values.object).end(); i++) {
output << spaceString << " "
<< "\"" << i->first << "\""
<< ": ";
output << i->second->stringify(indentationLevel + 1);
JSONObject::iterator next = i;
next++;
if ((next) != (*values.object).end()) {
output << ",\n";
}
output << spaceString << "\n";
}
output << spaceString << "}";
return output.str();
}
}
return output.str();
string spaceString = string(indentationLevel, ' ');
// sstreams
std::stringstream output;
// cout < type << "\n";
switch (type) {
case STRING: {
output << spaceString << *values.str;
break;
}
case NUMBER: {
output << spaceString << values.nbr;
break;
}
case BOOLEAN: {
output << spaceString << (values.bValue ? "true" : "false");
break;
}
case NULL_TYPE: {
output << spaceString << "null";
break;
}
case LIST: {
// cout << "[";
output << spaceString << "[\n";
unsigned int index = 0;
for (JSONList::iterator i = (*values.list).begin();
i != (*values.list).end(); i++) {
output << (*i)->stringify(indentationLevel + 1);
if (index < (*values.list).size() - 1) {
output << ",\n";
}
index++;
};
output << "\n" << spaceString << "]\n";
break;
}
case OBJECT: {
output << spaceString << "{\n";
for (JSONObject::iterator i = (*values.object).begin();
i != (*values.object).end(); i++) {
output << spaceString << " "
<< "\"" << i->first << "\""
<< ": ";
output << i->second->stringify(indentationLevel + 1);
JSONObject::iterator next = i;
next++;
if ((next) != (*values.object).end()) {
output << ",\n";
}
output << spaceString << "\n";
}
output << spaceString << "}";
return output.str();
}
}
return output.str();
}

359
srcs/json/Parser.cpp

@ -1,200 +1,199 @@
#include "webserv.hpp"
JSONParser::JSONParser(const string filename) : tokenizer(filename) {}
JSONNode *JSONParser::parse() {
string key = "";
JSONNode *parsed;
while (tokenizer.hasMoreTokens()) {
Token token;
try {
token = tokenizer.getToken();
switch (token.type) {
case CURLY_OPEN: {
parsed = parseObject();
break;
}
case ARRAY_OPEN: {
parsed = parseList();
break;
}
case STRING: {
tokenizer.rollBackToken();
parsed = parseString();
break;
}
case NUMBER: {
tokenizer.rollBackToken();
parsed = parseNumber();
break;
}
case BOOLEAN: {
tokenizer.rollBackToken();
parsed = parseBoolean();
break;
}
default:
break;
}
} catch (std::logic_error &e) {
break;
}
}
return parsed;
string key = "";
JSONNode *parsed;
while (tokenizer.hasMoreTokens()) {
Token token;
try {
token = tokenizer.getToken();
switch (token.type) {
case CURLY_OPEN: {
parsed = parseObject();
break;
}
case ARRAY_OPEN: {
parsed = parseList();
break;
}
case STRING: {
tokenizer.rollBackToken();
parsed = parseString();
break;
}
case NUMBER: {
tokenizer.rollBackToken();
parsed = parseNumber();
break;
}
case BOOLEAN: {
tokenizer.rollBackToken();
parsed = parseBoolean();
break;
}
default:
break;
}
} catch (std::logic_error &e) {
break;
}
}
return parsed;
}
JSONNode *JSONParser::parseObject() {
JSONNode *node = new JSONNode;
JSONObject *keyObjectMap = new JSONObject;
while (1) {
if (tokenizer.hasMoreTokens()) {
Token token = tokenizer.getToken();
string key = token.value;
tokenizer.getToken();
token = tokenizer.getToken();
switch (token.type) {
case CURLY_OPEN: {
if (DEBUG)
cout << "=object=|" << key << "|===>>\n";
(*keyObjectMap)[key] = parseObject();
if (DEBUG)
cout << "<<===end object\n";
break;
}
case ARRAY_OPEN: {
if (DEBUG)
cout << "-list-|" << key << "|--->>\n";
(*keyObjectMap)[key] = parseList();
if (DEBUG)
cout << "<<---end list\n";
break;
}
case STRING: {
tokenizer.rollBackToken();
(*keyObjectMap)[key] = parseString();
if (DEBUG)
cout << key << "='" << (*keyObjectMap)[key]->str() << "'\n";
break;
}
case NUMBER: {
tokenizer.rollBackToken();
(*keyObjectMap)[key] = parseNumber();
if (DEBUG)
cout << key << "=" << (*keyObjectMap)[key]->nbr() << "\n";
break;
}
case BOOLEAN: {
tokenizer.rollBackToken();
(*keyObjectMap)[key] = parseBoolean();
if (DEBUG)
cout << key << "(BOOL)\n";
break;
}
case NULL_TYPE: {
(*keyObjectMap)[key] = parseNull();
break;
}
default:
break;
}
token = tokenizer.getToken();
if (token.type == CURLY_CLOSE)
break;
JSONNode *node = new JSONNode;
JSONObject *keyObjectMap = new JSONObject;
while (1) {
if (tokenizer.hasMoreTokens()) {
Token token = tokenizer.getToken();
string key = token.value;
tokenizer.getToken();
token = tokenizer.getToken();
switch (token.type) {
case CURLY_OPEN: {
if (DEBUG)
cout << "=object=|" << key << "|===>>\n";
(*keyObjectMap)[key] = parseObject();
if (DEBUG)
cout << "<<===end object\n";
break;
}
case ARRAY_OPEN: {
if (DEBUG)
cout << "-list-|" << key << "|--->>\n";
(*keyObjectMap)[key] = parseList();
if (DEBUG)
cout << "<<---end list\n";
break;
}
case STRING: {
tokenizer.rollBackToken();
(*keyObjectMap)[key] = parseString();
if (DEBUG)
cout << key << "='" << (*keyObjectMap)[key]->str() << "'\n";
break;
}
case NUMBER: {
tokenizer.rollBackToken();
(*keyObjectMap)[key] = parseNumber();
if (DEBUG)
cout << key << "=" << (*keyObjectMap)[key]->nbr() << "\n";
break;
}
case BOOLEAN: {
tokenizer.rollBackToken();
(*keyObjectMap)[key] = parseBoolean();
if (DEBUG)
cout << key << "(BOOL)\n";
break;
}
case NULL_TYPE: {
(*keyObjectMap)[key] = parseNull();
break;
}
default:
break;
}
token = tokenizer.getToken();
if (token.type == CURLY_CLOSE)
break;
} else {
throw std::logic_error("No more tokens");
}
}
node->setObject(keyObjectMap);
return node;
} else {
throw std::logic_error("No more tokens");
}
}
node->setObject(keyObjectMap);
return node;
}
JSONNode *JSONParser::parseList() {
JSONNode *node = new JSONNode();
JSONList *list = new JSONList();
bool hasCompleted = false;
while (!hasCompleted) {
if (!tokenizer.hasMoreTokens()) {
throw std::logic_error("No more tokens");
} else {
Token token = tokenizer.getToken();
JSONNode *subNode;
switch (token.type) {
case CURLY_OPEN: {
if (DEBUG)
cout << "=object===>>\n";
subNode = parseObject();
if (DEBUG)
cout << "<<===end object\n";
break;
}
case ARRAY_OPEN: {
if (DEBUG)
cout << "-list--->>\n";
subNode = parseList();
if (DEBUG)
cout << "<<---end list\n";
break;
}
case STRING: {
tokenizer.rollBackToken();
subNode = parseString();
if (DEBUG)
cout << "|'" << subNode->str() << "'";
break;
}
case NUMBER: {
tokenizer.rollBackToken();
subNode = parseNumber();
if (DEBUG)
cout << "|" << subNode->nbr();
break;
}
case BOOLEAN: {
tokenizer.rollBackToken();
subNode = parseBoolean();
break;
}
case NULL_TYPE: {
subNode = parseNull();
break;
}
default:
break;
}
list->push_back(subNode);
token = tokenizer.getToken();
if (token.type == ARRAY_CLOSE) {
hasCompleted = true;
}
}
}
node->setList(list);
return node;
JSONNode *node = new JSONNode();
JSONList *list = new JSONList();
bool hasCompleted = false;
while (!hasCompleted) {
if (!tokenizer.hasMoreTokens()) {
throw std::logic_error("No more tokens");
} else {
Token token = tokenizer.getToken();
JSONNode *subNode;
switch (token.type) {
case CURLY_OPEN: {
if (DEBUG)
cout << "=object===>>\n";
subNode = parseObject();
if (DEBUG)
cout << "<<===end object\n";
break;
}
case ARRAY_OPEN: {
if (DEBUG)
cout << "-list--->>\n";
subNode = parseList();
if (DEBUG)
cout << "<<---end list\n";
break;
}
case STRING: {
tokenizer.rollBackToken();
subNode = parseString();
if (DEBUG)
cout << "|'" << subNode->str() << "'";
break;
}
case NUMBER: {
tokenizer.rollBackToken();
subNode = parseNumber();
if (DEBUG)
cout << "|" << subNode->nbr();
break;
}
case BOOLEAN: {
tokenizer.rollBackToken();
subNode = parseBoolean();
break;
}
case NULL_TYPE: {
subNode = parseNull();
break;
}
default:
break;
}
list->push_back(subNode);
token = tokenizer.getToken();
if (token.type == ARRAY_CLOSE) {
hasCompleted = true;
}
}
}
node->setList(list);
return node;
}
JSONNode *JSONParser::parseString() {
JSONNode *node = new JSONNode();
Token token = tokenizer.getToken();
string *sValue = new string(token.value);
node->setString(sValue);
return node;
JSONNode *node = new JSONNode();
Token token = tokenizer.getToken();
string *sValue = new string(token.value);
node->setString(sValue);
return node;
}
JSONNode *JSONParser::parseNumber() {
JSONNode *node = new JSONNode();
Token token = tokenizer.getToken();
string value = token.value;
int nbr = std::atoi(value.c_str());
node->setNumber(nbr);
return node;
JSONNode *node = new JSONNode();
Token token = tokenizer.getToken();
string value = token.value;
int nbr = std::atoi(value.c_str());
node->setNumber(nbr);
return node;
}
JSONNode *JSONParser::parseBoolean() {
JSONNode *node = new JSONNode();
Token token = tokenizer.getToken();
node->setBoolean(token.value == "True" ? true : false);
return node;
JSONNode *node = new JSONNode();
Token token = tokenizer.getToken();
node->setBoolean(token.value == "True" ? true : false);
return node;
}
JSONNode *JSONParser::parseNull() {
JSONNode *node = new JSONNode();
node->setNull();
return node;
JSONNode *node = new JSONNode();
node->setNull();
return node;
}

176
srcs/json/Token.cpp

@ -1,111 +1,97 @@
#include "webserv.hpp"
/*
enum TOKEN {
CURLY_OPEN,
CURLY_CLOSE,
COLON,
STRING,
NUMBER,
ARRAY_OPEN,
ARRAY_CLOSE,
COMMA,
BOOLEAN,
NULL_TYPE
};
*/
Tokenizer::Tokenizer(string fileName) {
file.open(fileName.c_str(), std::ios::in);
if (!file.good())
cout << "File open error"
<< "\n";
file.open(fileName.c_str(), std::ios::in);
if (!file.good())
cout << "File open error"
<< "\n";
}
bool Tokenizer::hasMoreTokens() { return !file.eof(); }
char Tokenizer::getWithoutWhiteSpace() {
char c = ' ';
while ((c == ' ' || c == '\n') || c == '\t') {
file.get(c); // check
char c = ' ';
while ((c == ' ' || c == '\n') || c == '\t') {
file.get(c); // check
if ((c == ' ' || c == '\n') && !file.good()) {
// cout << file.eof() << " " << file.fail() << "\n";
throw std::logic_error("Ran out of tokens");
} else if (!file.good()) {
return c;
}
}
if ((c == ' ' || c == '\n') && !file.good()) {
// cout << file.eof() << " " << file.fail() << "\n";
throw std::logic_error("Ran out of tokens");
} else if (!file.good()) {
return c;
}
}
return c;
return c;
}
void Tokenizer::rollBackToken() {
if (file.eof())
file.clear();
file.seekg(prevPos);
if (file.eof())
file.clear();
file.seekg(prevPos);
}
Token Tokenizer::getToken() {
char c;
if (file.eof()) {
cout << "Exhaused tokens"
<< "\n";
// throw std::exception("Exhausted tokens");
}
prevPos = file.tellg();
c = getWithoutWhiteSpace();
char c;
if (file.eof()) {
cout << "Exhaused tokens"
<< "\n";
// throw std::exception("Exhausted tokens");
}
prevPos = file.tellg();
c = getWithoutWhiteSpace();
Token token;
token.type = NULL_TYPE;
if (c == '"') {
token.type = STRING;
token.value = "";
file.get(c);
while (c != '"') {
token.value += c;
file.get(c);
}
} else if (c == '{') {
token.type = CURLY_OPEN;
} else if (c == '}') {
token.type = CURLY_CLOSE;
} else if (c == '-' || (c >= '0' && c <= '9')) {
// Check if string is numeric
token.type = NUMBER;
token.value = "";
token.value += c;
std::streampos prevCharPos = file.tellg();
while ((c == '-') || (c >= '0' && c <= '9') || c == '.') {
prevCharPos = file.tellg();
file.get(c);
Token token;
token.type = NULL_TYPE;
if (c == '"') {
token.type = STRING;
token.value = "";
file.get(c);
while (c != '"') {
token.value += c;
file.get(c);
}
} else if (c == '{') {
token.type = CURLY_OPEN;
} else if (c == '}') {
token.type = CURLY_CLOSE;
} else if (c == '-' || (c >= '0' && c <= '9')) {
// Check if string is numeric
token.type = NUMBER;
token.value = "";
token.value += c;
std::streampos prevCharPos = file.tellg();
while ((c == '-') || (c >= '0' && c <= '9') || c == '.') {
prevCharPos = file.tellg();
file.get(c);
if (file.eof()) {
break;
} else {
if ((c == '-') || (c >= '0' && c <= '9') || (c == '.')) {
token.value += c;
} else {
file.seekg(prevCharPos);
}
}
}
} else if (c == 'f') {
token.type = BOOLEAN;
token.value = "False";
file.seekg(4, std::ios_base::cur);
} else if (c == 't') {
token.type = BOOLEAN;
token.value = "True";
file.seekg(3, std::ios_base::cur);
} else if (c == 'n') {
token.type = NULL_TYPE;
file.seekg(3, std::ios_base::cur);
} else if (c == '[') {
token.type = ARRAY_OPEN;
} else if (c == ']') {
token.type = ARRAY_CLOSE;
} else if (c == ':') {
token.type = COLON;
} else if (c == ',') {
token.type = COMMA;
}
// cout << token.type << " : " << token.value << "\n";
return token;
if (file.eof()) {
break;
} else {
if ((c == '-') || (c >= '0' && c <= '9') || (c == '.')) {
token.value += c;
} else {
file.seekg(prevCharPos);
}
}
}
} else if (c == 'f') {
token.type = BOOLEAN;
token.value = "False";
file.seekg(4, std::ios_base::cur);
} else if (c == 't') {
token.type = BOOLEAN;
token.value = "True";
file.seekg(3, std::ios_base::cur);
} else if (c == 'n') {
token.type = NULL_TYPE;
file.seekg(3, std::ios_base::cur);
} else if (c == '[') {
token.type = ARRAY_OPEN;
} else if (c == ']') {
token.type = ARRAY_CLOSE;
} else if (c == ':') {
token.type = COLON;
} else if (c == ',') {
token.type = COMMA;
}
// cout << token.type << " : " << token.value << "\n";
return token;
}

46
srcs/load/Env.cpp

@ -1,30 +1,34 @@
#include "webserv.hpp"
Env::Env(JSONNode *conf) {
JSONList servers = conf->obj()["servers"]->lst();
int i = 0;
string th[8] = {"first", "second", "third", "fourth",
"fifth", "sixth", "seventh", "eigth"};
for (std::vector<JSONNode *>::iterator it = servers.begin();
it < servers.end(); it++) {
Server *server = new Server(*it);
_servers.push_back(server);
// delete *it;
cout << th[i] << " server launched.\n";
i++;
}
// delete conf;
try {
JSONList servers = conf->obj()["servers"]->lst();
int i = 0;
string th[8] = {"first", "second", "third", "fourth",
"fifth", "sixth", "seventh", "eigth"};
for (std::vector<JSONNode *>::iterator it = servers.begin();
it < servers.end(); it++) {
Server *server = new Server(*it);
_servers.push_back(server);
// delete *it;
cout << th[i] << " server launched.\n";
i++;
}
} catch (std::exception &e) {
cout << e.what();
}
delete conf;
}
void Env::set_fds() {
for (std::vector<Server *>::iterator it = _servers.begin();
it < _servers.end(); it++) {
(*it)->set_fds();
}
for (std::vector<Server *>::iterator it = _servers.begin();
it < _servers.end(); it++) {
(*it)->set_fds();
}
}
void Env::refresh() {
for (std::vector<Server *>::iterator it = _servers.begin();
it < _servers.end(); it++) {
(*it)->refresh();
}
for (std::vector<Server *>::iterator it = _servers.begin();
it < _servers.end(); it++) {
(*it)->refresh();
}
}

4
srcs/load/Route.cpp

@ -20,7 +20,5 @@ Route::~Route(void) {}
string getRoot(void);
string getReturn(void);
std::vector<string> Route::getIndexs(void) {
return _indexs;
}
std::vector<string> Route::getIndexs(void) { return _indexs; }
bool getAutoindex(void);

49
srcs/load/Server.cpp

@ -1,48 +1,49 @@
#include "webserv.hpp"
Server::Server(JSONNode *server):Route(server) {
JSONObject datas = server->obj();
if (datas["server_name"])
_name = datas["server_name"]->str();
if (datas["listens"]) {
JSONList listens = datas["listens"]->lst();
for (JSONList::iterator it = listens.begin(); it < listens.end(); it++) {
Socket *sock = new Socket(this, (*it)->str());
Server::Server(JSONNode *server) : Route(server) {
JSONObject datas = server->obj();
if (datas["server_name"])
_name = datas["server_name"]->str();
if (datas["listens"]) {
JSONList listens = datas["listens"]->lst();
for (JSONList::iterator it = listens.begin(); it < listens.end();
it++) {
Socket *sock = new Socket(this, (*it)->str());
if (sock->launch() == EXIT_SUCCESS)
_sockets.push_back(sock);
_sockets.push_back(sock);
else
delete sock;
}
}
}
}
if (datas["locations"]) {
JSONObject locations = datas["locations"]->obj();
for (JSONObject::iterator it = locations.begin(); it != locations.end(); it++) {
for (JSONObject::iterator it = locations.begin(); it != locations.end();
it++) {
Route *route = new Route((*it).second);
_routes[(*it).first] = route;
}
}
}
Server::~Server(void) {
cout << "Server destroyed!\n";
}
Server::~Server(void) { cout << "Server destroyed!\n"; }
void Server::set_fds(void) {
for (std::vector<Socket *>::iterator it = _sockets.begin();
it < _sockets.end(); it++) {
(*it)->set_fds();
}
for (std::vector<Socket *>::iterator it = _sockets.begin();
it < _sockets.end(); it++) {
(*it)->set_fds();
}
}
void Server::refresh(void) {
for (std::vector<Socket *>::iterator it = _sockets.begin();
it < _sockets.end(); it++) {
(*it)->refresh();
}
for (std::vector<Socket *>::iterator it = _sockets.begin();
it < _sockets.end(); it++) {
(*it)->refresh();
}
}
Route *Server::get_route(string uri) {
for (std::map<string, Route *>::iterator it = _routes.begin(); it != _routes.end(); it++) {
for (std::map<string, Route *>::iterator it = _routes.begin();
it != _routes.end(); it++) {
if (uri == (*it).first)
return (*it).second;
}

162
srcs/load/Socket.cpp

@ -1,114 +1,116 @@
#include "webserv.hpp"
Socket::Socket(Server *server, string def): _server(server) {
size_t sep_pos = def.rfind(':');
size_t ip6_endpos = def.rfind(']');
Socket::Socket(Server *server, string def) : _server(server) {
size_t sep_pos = def.rfind(':');
size_t ip6_endpos = def.rfind(']');
string tmp = def.substr(0, sep_pos);
if (ip6_endpos > sep_pos)
_ip = def;
else
_ip = isInt(tmp) || tmp == "localhost" ? "127.0.0.1" : tmp;
tmp = def.substr(sep_pos + 1, def.length() - sep_pos - 1).c_str();
_port = !isInt(tmp) ? 80 : std::atoi(tmp.c_str());
_clients_amount = 0;
string tmp = def.substr(0, sep_pos);
if (ip6_endpos > sep_pos)
_ip = def;
else
_ip = isInt(tmp) || tmp == "localhost" ? "127.0.0.1" : tmp;
tmp = def.substr(sep_pos + 1, def.length() - sep_pos - 1).c_str();
_port = !isInt(tmp) ? 80 : std::atoi(tmp.c_str());
_clients_amount = 0;
}
Socket::~Socket() {
close(_master_socket);
cout << "Socket destroyed!\n";
close(_master_socket);
cout << "Socket destroyed!\n";
}
int Socket::launch() {
int opt = 1;
_master_socket = socket(AF_INET, SOCK_STREAM, 0);
if (_master_socket == 0) {
cout << "Socket creation: " << strerror(errno) << "\n";
return (EXIT_FAILURE);
}
int opt_ret = setsockopt(_master_socket, SOL_SOCKET, SO_REUSEADDR,
(char *)&opt, sizeof(opt));
if (opt_ret < 0) {
cout << "Sockopt: " << strerror(errno) << "\n";
return (EXIT_FAILURE);
}
int opt = 1;
_master_socket = socket(AF_INET, SOCK_STREAM, 0);
if (_master_socket == 0) {
cout << "Socket creation: " << strerror(errno) << "\n";
return (EXIT_FAILURE);
}
int opt_ret = setsockopt(_master_socket, SOL_SOCKET, SO_REUSEADDR,
(char *)&opt, sizeof(opt));
if (opt_ret < 0) {
cout << "Sockopt: " << strerror(errno) << "\n";
return (EXIT_FAILURE);
}
_address.sin_family = AF_INET;
_address.sin_addr.s_addr = inet_addr(_ip.c_str());
_address.sin_port = htons(_port);
_address.sin_family = AF_INET;
_address.sin_addr.s_addr = inet_addr(_ip.c_str());
_address.sin_port = htons(_port);
if (bind(_master_socket, (struct sockaddr *)&_address, sizeof(_address)) <
0) {
cout << "Bind: " << strerror(errno) << "\n";
return (EXIT_FAILURE);
}
cout << "Listener " << _ip << " on port " << _port << "\n";
if (bind(_master_socket, (struct sockaddr *)&_address, sizeof(_address)) <
0) {
cout << "Bind: " << strerror(errno) << "\n";
return (EXIT_FAILURE);
}
cout << "Listener " << _ip << " on port " << _port << "\n";
if (listen(_master_socket, 3) < 0) {
cout << "Listen: " << strerror(errno) << "\n";
return (EXIT_FAILURE);
}
cout << "Socket::_master_socket: " << _master_socket << "\n";
if (_master_socket < _min_fd)
_min_fd = _master_socket;
_amount++;
return (EXIT_SUCCESS);
if (listen(_master_socket, 3) < 0) {
cout << "Listen: " << strerror(errno) << "\n";
return (EXIT_FAILURE);
}
cout << "Socket::_master_socket: " << _master_socket << "\n";
if (_master_socket < _min_fd)
_min_fd = _master_socket;
_amount++;
return (EXIT_SUCCESS);
}
void Socket::set_fds() {
FD_SET(_master_socket, &_readfds);
FD_SET(_master_socket, &_readfds);
for (std::vector<int>::iterator it = _clients.begin(); it < _clients.end();
it++) {
FD_SET(*it, &_readfds);
if (*it > _max_fd)
_max_fd = *it;
}
for (std::vector<int>::iterator it = _clients.begin(); it < _clients.end();
it++) {
FD_SET(*it, &_readfds);
if (*it > _max_fd)
_max_fd = *it;
}
}
void Socket::refresh() {
std::vector<int>::iterator it;
int valread;
int addrlen = sizeof(_address);
char buffer[1024];
if (FD_ISSET(_master_socket, &_readfds)) {
int new_socket = accept(_master_socket, (struct sockaddr *)&_address,
(socklen_t *)&addrlen);
if (new_socket < 0) {
cout << "Accept: " << strerror(errno) << "\n";
exit(EXIT_FAILURE);
}
int valread;
int addrlen = sizeof(_address);
char buffer[10000];
if (FD_ISSET(_master_socket, &_readfds)) {
int new_socket = accept(_master_socket, (struct sockaddr *)&_address,
(socklen_t *)&addrlen);
if (new_socket < 0) {
cout << "Accept: " << strerror(errno) << "\n";
exit(EXIT_FAILURE);
}
#ifdef __APPLE__
fcntl(new_socket, F_GETNOSIGPIPE);
fcntl(new_socket, F_GETNOSIGPIPE);
#endif
cout << "New connection, socket fd is " << new_socket
<< ", ip is : " << inet_ntoa(_address.sin_addr)
<< ", port : " << ntohs(_address.sin_port) << "\n";
cout << "New connection, socket fd is " << new_socket
<< ", ip is : " << inet_ntoa(_address.sin_addr)
<< ", port : " << ntohs(_address.sin_port) << "\n";
_clients.push_back(new_socket);
}
for (it = _clients.begin(); it < _clients.end(); it++) {
if (FD_ISSET(*it, &_readfds)) {
valread = read(*it, buffer, 1024);
if (valread == 0) {
getpeername(*it, (struct sockaddr *)&_address,
(socklen_t *)&addrlen);
cout << "Host disconnected, ip " << inet_ntoa(_address.sin_addr)
<< ", port " << ntohs(_address.sin_port) << "\n";
close(*it);
}
for (it = _clients.begin(); it < _clients.end(); it++) {
if (FD_ISSET(*it, &_readfds)) {
valread = read(*it, buffer, 10000);
if (valread == 0) {
getpeername(*it, (struct sockaddr *)&_address,
(socklen_t *)&addrlen);
cout << "Host disconnected, ip " << inet_ntoa(_address.sin_addr)
<< ", port " << ntohs(_address.sin_port) << "\n";
close(*it);
_clients.erase(it);
} else
} else {
buffer[valread]='\0';
this->answer(*it, buffer);
}
}
}
}
}
}
void Socket::answer(int fd, string request) {
string uri = "path/to/page/";
Route *route = _server->get_route(uri);
(void)route;
char r404[72] =
"HTTP/1.1 200 OK\nContent-Type: text/plain\nContent-Length: 4\n\n404!";
cout << request << "\n";
char r404[72] =
"HTTP/1.1 200 OK\nContent-Type: text/plain\nContent-Length: 4\n\n404!";
cout << request << "\n|===|===|===|\n";
#ifdef __linux__
send(fd, r404, strlen(r404), MSG_NOSIGNAL);
#elif __APPLE__

17
srcs/tools.cpp

@ -1,18 +1,19 @@
#include "webserv.hpp"
void *ft_memset(void *b, int c, size_t len) {
size_t i;
unsigned char *b_cpy;
size_t i;
unsigned char *b_cpy;
b_cpy = (unsigned char *)b;
i = 0;
while (i < len)
*(unsigned char *)(b_cpy + i++) = (unsigned char)c;
return ((void *)b);
b_cpy = (unsigned char *)b;
i = 0;
while (i < len)
*(unsigned char *)(b_cpy + i++) = (unsigned char)c;
return ((void *)b);
}
bool isInt(string str) {
for (string::iterator it = str.begin(); it < str.end(); it++)
if (*it < '0' || *it > '9') return false;
if (*it < '0' || *it > '9')
return false;
return true;
}

25
srcs/webserv.cpp

@ -1,5 +1,4 @@
#include "webserv.hpp"
#include <time.h>
fd_set Socket::_readfds;
int Socket::_max_fd;
@ -8,24 +7,26 @@ int Socket::_amount = 0;
int main(int ac, char **av) {
if (ac > 1) {
if (ac > 1) {
cout << "Parsing configuration file...\n";
JSONParser parser(av[1]);
JSONNode *conf = parser.parse();
cout << "Configuration parsed.\n";
cout << "Parsing configuration file...\n";
JSONParser parser(av[1]);
JSONNode *conf = parser.parse();
cout << "Configuration parsed.\n";
cout << "Setting environment...\n";
Env env(conf);
while (1) {
cout << "Setting environment...\n";
Env env(conf);
while (1) {
cout << "|===|===|===| CYCLE |===|===|===|\n";
FD_ZERO(&Socket::_readfds);
Socket::_max_fd = Socket::_min_fd;
env.set_fds();
int activity = select(Socket::_max_fd + Socket::_amount, &(Socket::_readfds), NULL, NULL, NULL);
env.set_fds();
int activity = select(Socket::_max_fd + Socket::_amount,
&(Socket::_readfds), NULL, NULL, NULL);
if ((activity < 0) && (errno != EINTR))
cout << "Select: " << strerror(errno) << "\n";
env.refresh();
}
}
return (0);
return (0);
}

Loading…
Cancel
Save