/server.cpp

https://bitbucket.org/Tuxilero/ipk-2 · C++ · 269 lines · 192 code · 52 blank · 25 comment · 37 complexity · 6db12f4dd8484b00bca738bc8a9fb8da MD5 · raw file

  1. #include <iostream>
  2. #include <fstream>
  3. #include <vector>
  4. #include <sys/wait.h>
  5. #include "socket.h"
  6. using namespace std;
  7. // ------------------ STRUCT ----------------
  8. typedef struct struct_params
  9. {
  10. int p;
  11. } struct_params;
  12. // ------------------ STRUCT ----------------
  13. struct_params get_params(int, char**);
  14. void child_die(int sig)
  15. {
  16. sig = sig; // get rid of warning!
  17. while(waitpid(-1,0,WNOHANG)>0);
  18. }
  19. // ------------------ MAIN ----------------
  20. int main(int argc, char** argv)
  21. {
  22. (void) signal(SIGCHLD, child_die);
  23. struct_params params = get_params(argc, argv);
  24. // ------- Listen on socket -------------
  25. class_socket socket;
  26. if(socket.s_listen(params.p) != 0)
  27. {
  28. cout << "Cannost listen!" << endl << flush;
  29. exit(-1);
  30. }
  31. // ------- Listen on socket -------------
  32. while(1)
  33. {
  34. pid_t child_pid;
  35. //cout << "Server listening on port: " << htons(params.p) << endl << flush;
  36. sockaddr_in clientAddr;
  37. socklen_t sin_size=sizeof(struct sockaddr_in);
  38. class_socket client_sock;
  39. client_sock.sock = accept(socket.sock, (struct sockaddr*)&clientAddr, &sin_size);
  40. //cout << "Client connected! ID: " << client_sock.sock << endl << flush;
  41. child_pid = fork();
  42. for(int z = 0; child_pid < 0 && z < 6; z++)
  43. {
  44. cerr << "FORK FAILED!" << endl;
  45. usleep(10000);
  46. child_pid = fork();
  47. }
  48. if (child_pid < 0)
  49. {
  50. cerr << "OU OU Fork Failed 5 times... exiting!" << endl;
  51. exit(-1);
  52. }
  53. if (child_pid == 0)
  54. {
  55. string received_string = client_sock.s_read();
  56. //cout << "Server received: " << received_string << endl << flush;
  57. string response_params;
  58. string response;
  59. response_params = received_string.substr(0,6);
  60. string data = received_string.substr(7,received_string.size()-7);
  61. string uid = received_string.substr(6,1);
  62. vector<string> find;
  63. unsigned r_start = 0;
  64. unsigned cmp = -1;
  65. //cout << "START: " << r_start << " END: " << r_end << endl << flush;
  66. data.append(" ");
  67. while(r_start != cmp)
  68. {
  69. unsigned r_mezera = data.find(" ",r_start);
  70. if (r_mezera != cmp)
  71. find.push_back(data.substr(r_start, r_mezera - r_start));
  72. else
  73. break;
  74. r_start = r_mezera+1;
  75. }
  76. ifstream file;
  77. file.open("/etc/passwd");
  78. if(!file.good())
  79. {
  80. cerr << "/etc/passwd does not exist... what?" << endl;
  81. return 1; // exit if file not found
  82. }
  83. // Loop for all logins or uids
  84. for(unsigned int y=0;y<find.size();y++)
  85. {
  86. file.clear();
  87. file.seekg (0, file.beg);
  88. bool parsed = false;
  89. while (!file.eof())
  90. {
  91. bool parse = false;
  92. string radek;
  93. getline(file,radek);
  94. if(uid == "0")
  95. {
  96. string s_uid;
  97. unsigned uid_start = radek.find(":");
  98. uid_start = radek.find(":",uid_start+1);
  99. unsigned uid_end = radek.find(":",uid_start+1);
  100. s_uid = radek.substr(uid_start+1,uid_end-uid_start-1);
  101. if(find.at(y) == s_uid)
  102. {
  103. parse = true;
  104. parsed = true;
  105. }
  106. }
  107. else
  108. {
  109. string s_login;
  110. unsigned login_start = 0;
  111. unsigned login_end = radek.find(":",login_start);
  112. s_login = radek.substr(login_start,login_end-login_start);
  113. if(find.at(y) == s_login)
  114. {
  115. parse = true;
  116. parsed = true;
  117. }
  118. }
  119. if(parse)
  120. {
  121. //cout << "Parse: " << radek << endl << flush;
  122. // login_name:passwd:UID:GID:user_name:directory:shell
  123. // L U G N H S
  124. // 1 2 3 4 5 6
  125. // LOGIN_NAME
  126. unsigned parser_start = 0;
  127. unsigned parser_end = radek.find(":");
  128. unsigned data_end = radek.size();
  129. vector<string> parsed;
  130. parsed.push_back(""); // 0
  131. parsed.push_back(radek.substr(parser_start,parser_end-parser_start)); // 1
  132. // PASSWORD
  133. parser_start = parser_end;
  134. parser_end = radek.find(":",parser_start+1);
  135. // UID
  136. parser_start = parser_end;
  137. parser_end = radek.find(":",parser_start+1);
  138. parsed.push_back(radek.substr(parser_start+1,parser_end-parser_start-1)); // 2
  139. // GID
  140. parser_start = parser_end;
  141. parser_end = radek.find(":",parser_start+1);
  142. parsed.push_back(radek.substr(parser_start+1,parser_end-parser_start-1)); // 3
  143. // USER_NAME
  144. parser_start = parser_end;
  145. parser_end = radek.find(":",parser_start+1);
  146. parsed.push_back(radek.substr(parser_start+1,parser_end-parser_start-1)); // 4
  147. // DIRECTORY
  148. parser_start = parser_end;
  149. parser_end = radek.find(":",parser_start+1);
  150. parsed.push_back(radek.substr(parser_start+1,parser_end-parser_start-1)); // 5
  151. // SHELL
  152. parser_start = parser_end;
  153. parsed.push_back(radek.substr(parser_start+1,data_end-2)); // 6
  154. for(int i=0;i<6;i++)
  155. {
  156. int num = response_params.at(i);
  157. num = num - '0';
  158. response.append(parsed.at(num));
  159. if(((i+1) < 6) && response_params.at(i+1) != '0')
  160. {
  161. //cout << " Next is: \"" << response_params.at(i+1) << "\" Appending space!" << endl;
  162. response.append(" ");
  163. }
  164. }
  165. response.append("\n");
  166. }
  167. }
  168. if(!parsed)
  169. {
  170. if(uid == "0")
  171. response.append("::ERROR:: UID unknown:"+find.at(y)+"\n");
  172. else
  173. response.append("::ERROR:: Login unknown:"+find.at(y)+"\n");
  174. }
  175. }
  176. client_sock.s_write(response);
  177. client_sock.s_write("::END::");
  178. client_sock.s_disconnect();
  179. }
  180. }
  181. return 0;
  182. }
  183. // ------------------ MAIN ----------------
  184. // ---------------- GET_PARAMS ----------------
  185. struct_params get_params(int argc, char** argv)
  186. {
  187. struct_params par;
  188. par.p = -1;
  189. int c;
  190. while( (c = getopt(argc, (char**)argv, "p:?")) != -1)
  191. {
  192. if(c == 'p' && optarg)
  193. {
  194. istringstream stream(optarg);
  195. stream >> par.p;
  196. ostringstream o_stream;
  197. o_stream << par.p;
  198. if(o_stream.str().compare(optarg))
  199. {
  200. cerr << "Chyba: zadany port neni cislo!" << endl;
  201. exit (-1);
  202. }
  203. }
  204. else
  205. {
  206. cerr << "Chyba: neznamy parametr!" << endl;
  207. exit(-1);
  208. }
  209. }
  210. if(par.p < 0)
  211. {
  212. cout << "server -p port" << endl;
  213. exit(1);
  214. }
  215. return par;
  216. }
  217. // ---------------- GET_PARAMS ----------------