diff --git a/green-serv.c b/green-serv.c index 8014774..4ea69df 100644 --- a/green-serv.c +++ b/green-serv.c @@ -58,7 +58,7 @@ int main(int argc, const char* argv[]) { char buff[1024]; bzero(buff,1024); /*What a silly cast we have to make...*/ - test_network(buff,1024,(void*(*)(void*))&doNetWork); + run_network(buff,1024,(void*(*)(void*))&doNetWork); /*Clean Up database connection*/ mysql_library_end(); diff --git a/headers/controllers/comments.h b/headers/controllers/comments.h index b1a5527..72ee334 100644 --- a/headers/controllers/comments.h +++ b/headers/controllers/comments.h @@ -36,6 +36,7 @@ #ifndef MISSING_ID_KEY #define MISSING_ID_KEY "Required key id not found" #endif + #define EMPTY_COMMENT_MESSAGE "Message may not be empty" int comment_controller(const struct http_request * request, char * stringToReturn, int strLength); diff --git a/headers/network/net.h b/headers/network/net.h index 5695c3f..29ca5ee 100644 --- a/headers/network/net.h +++ b/headers/network/net.h @@ -4,9 +4,9 @@ #define METHOD_LENGTH 7 #define FIRSTLINEBUFFSIZE 256 - #define NUMTHREADS 1/*00*/ + #define NUMTHREADS 100 #define DETACHED_THREADS - #undef DETACHED_THREADS + #undef DETACHED_THREADS /* Using detacthed threads runs the risk of leaving fd's open */ /* Simple struct to contain data to be sent to worker threads */ struct threadData{ char msg[16384]; @@ -64,6 +64,8 @@ /* This function is unlikely to live beyond testing things */ int test_network(char * buffer, int bufferLength, void*( *func )(void*) ); + int run_network(char * buffer, int bufferLength, void*( *func )(void*) ); + #endif \ No newline at end of file diff --git a/src/controllers/comments.c b/src/controllers/comments.c index 50ed493..a387159 100644 --- a/src/controllers/comments.c +++ b/src/controllers/comments.c @@ -43,7 +43,7 @@ int comment_controller(const struct http_request * request, char * stringToRetur page = atoi(tempBuf); if(page <= 0){ /* Err */ - status = 400; + status = 422; sm_delete(sm); goto cc_badpage; } @@ -55,7 +55,7 @@ int comment_controller(const struct http_request * request, char * stringToRetur if(strncasecmp(cType, CTYPE_1,COMMENTS_CTYPE_SIZE) != 0) if(strncasecmp(cType, CTYPE_2,COMMENTS_CTYPE_SIZE) != 0) if(strncasecmp(cType, CTYPE_3,COMMENTS_CTYPE_SIZE) != 0){ - status = 400; + status = 422; sm_delete(sm); goto cc_badtype; } @@ -95,12 +95,17 @@ int comment_controller(const struct http_request * request, char * stringToRetur if( status == -1 ){ sm_delete(sm); goto cc_nomem; - } else if(status == 400) { + } else if(status == 422) { sm_delete(sm); goto cc_badtype; } else if(status == -400) { + status = 400; sm_delete(sm); goto cc_missing; + }else if(status == -422){ + sm_delete(sm); + status = 422; + goto cc_emptymessage; } snprintf(stringToReturn,strLength,"%s",buffer); break; @@ -150,6 +155,10 @@ int comment_controller(const struct http_request * request, char * stringToRetur snprintf(stringToReturn, strLength, ERROR_STR_FORMAT, status, MISSING_ID_KEY); return status; + cc_emptymessage: + snprintf(stringToReturn, strLength, ERROR_STR_FORMAT, status, EMPTY_COMMENT_MESSAGE); + return status; + } /*Accepts NULL for cType if no filter @@ -243,15 +252,17 @@ int comment_post(char * buffer, int buffSize, const struct http_request * reques struct gs_comment insComment; StrMap * sm; int i; + int empty; int j; int strFlag; char keyBuffer[GS_COMMENT_MAX_LENGTH+1]; char valBuffer[GS_COMMENT_MAX_LENGTH+1]; - + char **convertSuccess; bzero(keyBuffer,sizeof keyBuffer); gs_comment_ZeroStruct(&insComment); strFlag = 0; + convertSuccess = NULL; sm = sm_new(HASH_TABLE_CAPACITY); if(sm == NULL){ @@ -272,14 +283,14 @@ int comment_post(char * buffer, int buffSize, const struct http_request * reques /*find the beginning of the value *which is either a " or a number. So skip spaces and commas */ - for(i++; i < request->contentLength && request->data[i] != '\0' && (request->data[i] == ',' || request->data[i] == ' ' || request->data[i] == ':'); ++i) + for(i++; i< (int)(sizeof valBuffer)-1 && i < request->contentLength && request->data[i] != '\0' && (request->data[i] == ',' || request->data[i] == ' ' || request->data[i] == ':'); ++i) ; /*Skip any opening qoute */ - if(request->data[i] != '\0' && request->data[i] == '"'){ + if( i < (int)(sizeof valBuffer)-1 && request->data[i] != '\0' && request->data[i] == '"'){ i++; strFlag = 1; } - for(j=0; i < request->contentLength && request->data[i] != '\0'; ++j,++i){ + for(j=0; i < request->contentLength && request->data[i] != '\0' && i < (int)(sizeof valBuffer)-1; ++j,++i){ if(strFlag == 0){ if(request->data[i] == ' ' || request->data[i] == '\n') break; /*break out if num data*/ @@ -291,11 +302,12 @@ int comment_post(char * buffer, int buffSize, const struct http_request * reques } valBuffer[j] = '\0'; /* Skip any closing paren. */ - if(request->data[i] == '"') + if(i < (int)(sizeof valBuffer) && request->data[i] == '"') i++; - if(strlen(keyBuffer) > 0 && strlen(valBuffer) > 0) + if(strlen(keyBuffer) > 0 && strlen(valBuffer) > 0){ if(sm_put(sm, keyBuffer, valBuffer) == 0) fprintf(stderr, "Failed to copy parameters into hash table while parsing url\n"); + } } strFlag = 0; } @@ -306,6 +318,14 @@ int comment_post(char * buffer, int buffSize, const struct http_request * reques fprintf(stderr, "required keys not found\n"); return -400; }else{ + if(sm_exists(sm,"message") == 1){ + if(sm_get(sm,"type",keyBuffer, sizeof keyBuffer) == 1){ + if(strlen(keyBuffer) > GS_COMMENT_MAX_LENGTH){ + sm_delete(sm); + return 422; + } + } + } if(sm_exists(sm, "type") ==1){ if(sm_get(sm,"type", valBuffer, sizeof valBuffer) == 1){ /* Verify that it is a correct type */ @@ -313,7 +333,7 @@ int comment_post(char * buffer, int buffSize, const struct http_request * reques if(strncasecmp(valBuffer, CTYPE_2,COMMENTS_CTYPE_SIZE) != 0) if(strncasecmp(valBuffer, CTYPE_3,COMMENTS_CTYPE_SIZE) != 0){ sm_delete(sm); - return 400; + return 422; } } @@ -323,10 +343,25 @@ int comment_post(char * buffer, int buffSize, const struct http_request * reques /* valid, cary on and copy over */ gs_comment_setScopeId(_shared_campaign_id, &insComment); sm_get(sm, "message",valBuffer, sizeof valBuffer); + /* Check for message being empty */ + empty = 1; + for(i=0; i < (int)strlen(valBuffer); ++i){ + empty = empty && (valBuffer[i] == ' '); + } + if(empty){ + sm_delete(sm); + return -422; + } + fprintf(stderr, "val::%s\n", valBuffer); gs_comment_setContent(valBuffer, &insComment); if(sm_exists(sm, "pin")){ sm_get(sm, "pin",keyBuffer,sizeof keyBuffer); - gs_comment_setPinId(atol(keyBuffer),&insComment); + if(strtod(keyBuffer,convertSuccess) != 0 && convertSuccess == NULL){ + gs_comment_setPinId(atol(keyBuffer),&insComment); + }else{ + sm_delete(sm); + return 422; + } } sm_get(sm, "type", insComment.cType, sizeof insComment.cType); sm_delete(sm); diff --git a/src/network/net.c b/src/network/net.c index d2e14d7..db82aa8 100644 --- a/src/network/net.c +++ b/src/network/net.c @@ -319,4 +319,99 @@ int test_network(char * buffer, int bufferLength, void*(*func)(void*)){ sleep(2); return 0; -} \ No newline at end of file +} + + +#include +#include +#include + +volatile sig_atomic_t stop; +void stop_server(int signum){ + /* Call me with ctrl Z if ctrl c doesnt work*/ + stop = 1; + if(signum == SIGINT) + stop =1; + +} + +int run_network(char * buffer, int bufferLength, void*(*func)(void*)){ + struct sockaddr_in sockserv,sockclient; + int socketfd,clientfd; + socklen_t clientsocklen; + char buff[BUFSIZ]; + pthread_t children[NUMTHREADS]; + struct threadData data[NUMTHREADS]; + int i,j; + stop = 0; + #ifdef DETACHED_THREADS + pthread_attr_t attr; + #endif + + clientfd = socketfd = 0; + bzero(buff,BUFSIZ); + bzero(&sockserv,sizeof(sockserv)); + + socketfd = createSocket(); + setupSockAndBind(socketfd, &sockserv, PORT); + listen(socketfd,NUMTHREADS); + + clientsocklen = sizeof socketfd; + + #ifdef DETACHED_THREADS + pthread_attr_init(&attr); + pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); + #endif + + signal(SIGINT, stop_server); + signal(SIGTERM, stop_server); + signal(SIGQUIT, stop_server); + signal(SIGHUP, stop_server); + + i=j=0; + if(errno != 13){ + while(stop == 0){ + for(i=0; i < NUMTHREADS && stop == 0; i++){ + clientfd = accept(socketfd,(struct sockaddr*)&sockclient,&clientsocklen); + buff[read(clientfd,buff,BUFSIZ)] = '\0'; + strncpy(buffer, buff ,bufferLength); + + /* A thread pool would be intelligent here */ + sprintf(data[i].msg, "%s", buffer); + data[i].clientfd = clientfd; + #ifndef DETACHED_THREADS + pthread_create(&children[i],NULL,func,&data[i]); + #else + pthread_create(&children[i],&attr,func,&data[i]); + #endif + bzero(buff,BUFSIZ); + bzero(buffer,bufferLength); + + } + /*Gobble Up the resources (if not detaching threads) + *If you do want to detach threads change the define. + *in net.h + */ + #ifndef DETACHED_THREADS + for(j=0; j < NUMTHREADS && j < i; ++j) + pthread_join(children[j],NULL); + #endif + } + } + #ifndef DETACHED_THREADS + for(j=0; j < i && j < NUMTHREADS; ++j) + pthread_join(children[j],NULL); + #endif + #ifdef DETACHED_THREADS + pthread_attr_destroy(&attr); + #endif + if(shutdown(socketfd,2) <0) + fprintf(stderr, "%s\n", "Problem shutting down socket descriptor"); + if(close(socketfd) < 0) + fprintf(stderr, "%s\n", "Problem closing socket descriptor"); + /* Sleep a moment to hope that any running threads will finish */ + fprintf(stdout, "%s\n", "Exiting Server..."); + sleep(2); + + return 0; +}