/* * combine the http headers and html file. * return the total size to the caller. * If 0 is return, it means can't find the html file. */ unsigned int createBuffer2Send(const char *http_header_type, const char * html_file_name){ char *buffer = read2Buffer(html_file_name); if(buffer == NULL) return 0; unsigned int filesize = calculate_file_size(html_file_name); filesize += strlen(http_header_type); buffer2send = (char *)malloc(sizeof(char) * filesize+10); memset(buffer2send, 0, filesize+10); strncpy(buffer2send, http_header_type, strlen(http_header_type)); strncat(buffer2send, buffer, strlen(buffer)); free(buffer); return filesize; }
/* * read the html file to a tempoary buffer. * will later string cat to the buffer2send. * Return a char pointer which points to the html string. */ char* read2Buffer(const char *html_file_name){ unsigned int filesize = calculate_file_size(html_file_name); FILE *input = fopen(html_file_name, "rb"); if(input == NULL) return NULL; char *buffer; unsigned int counter = 0; buffer = (char *)malloc(sizeof(char)*filesize); memset(buffer, 0, filesize); while(1){ if(feof(input)) break; buffer[counter++] = fgetc(input); } buffer[filesize] = '\0'; fclose(input); return buffer; }
// Send HTTP get and wait for response (SSL/SPP) static int http_request(char *filename, char *proto, bool requestingFile, struct timeval *tvEnd){ char buf[BUFSIZZ]; int r; int len; long bytes_read = 0; // Compute expected data size fSize = atoi(filename); if (fSize == 0 && filename[0] != '0'){ if (requestingFile){ fSize = calculate_file_size(filename); }else{ fSize = strlen("HTTP/1.0 200 OK\r\n"); } } sizeCheck = fSize; experiment_info->file_size = fSize; // Request file (either by name or by size) if (requestingFile){ sendRequest(filename); } // Now read the server's response, assuming that it's terminated by a close while(1){ // SPP read if (strcmp(proto, "spp") == 0){ /* #ifdef DEBUG printf("[DEBUG] SPP_read\n"); #endif */ SPP_SLICE *slice; // slice for SPP_read SPP_CTX *ctx; // context pointer for SPP_read r = SPP_read_record(ssl, buf, BUFSIZZ, &slice, &ctx); #ifdef DEBUG printf("[INFO] Read %d bytes\n", r); #endif if (ssl->read_stats.app_bytes == fSize){ printf("[INFO] Read %d bytes as expected (fSize=%d). Stopping timer\n", ssl->read_stats.app_bytes, fSize); // Stop the timer here (avoid shutdown crap) gettimeofday(tvEnd, NULL); #ifdef VERBOSE fwrite(buf, 1, len, stdout); #endif break; //goto shutdown; } switch(SSL_get_error(ssl, r)){ case SSL_ERROR_NONE: len = r; break; case SSL_ERROR_ZERO_RETURN: goto shutdown; case SSL_ERROR_SYSCALL: fprintf(stderr, "SSL Error: Premature close\n"); goto done; default: berr_exit("SSL read problem"); } } // SSL read else if (strcmp(proto, "ssl") == 0){ /* #ifdef DEBUG printf("[DEBUG] SSL_read\n"); #endif */ r = SSL_read(ssl, buf, BUFSIZZ); #ifdef DEBUG printf("[DEBUG] Read %d bytes\n", r); #endif if (ssl->read_stats.app_bytes == fSize){ printf("[INFO] Read %d bytes as expected (fSize=%d). Stopping timer\n", ssl->read_stats.app_bytes, fSize); gettimeofday(tvEnd, NULL); // Write buf to stdout #ifdef VERBOSE fwrite(buf, 1, len, stdout); #endif break; } switch(SSL_get_error(ssl, r)){ case SSL_ERROR_NONE: len = r; break; case SSL_ERROR_ZERO_RETURN: goto shutdown; case SSL_ERROR_SYSCALL: fprintf(stderr, "SSL Error: Premature close\n"); goto done; default: berr_exit("SSL read problem"); } } // SSL read else if (strcmp(proto, "pln") == 0){ #ifdef DEBUG printf("[DEBUG] Waiting to read bytes in plain mode\n"); #endif r = read(plain_socket, buf, BUFSIZZ); experiment_info->app_bytes_read += r; bytes_read += r; #ifdef DEBUG printf("[DEBUG] Read %d bytes\n", r); #endif if ( r <= 0 || bytes_read == fSize) /* done reading */ { #ifdef DEBUG printf("[DEBUG] File transfer done, done reading socket...\n"); #endif gettimeofday(tvEnd, NULL); // Write buf to stdout #ifdef VERBOSE fwrite(buf, 1, len, stdout); #endif goto done; } } // Write buf to stdout #ifdef VERBOSE fwrite(buf, 1, len, stdout); #endif } shutdown: #ifdef DEBUG printf("[DEBUG] Shutdown was requested\n"); #endif r = SSL_shutdown(ssl); if( !r ){ shutdown(SSL_get_fd(ssl), 1); r = SSL_shutdown(ssl); } switch(r){ case 1: break; // Success case 0: case -1: default: #ifdef DEBUG printf ("Shutdown failed with code %d\n", r); #endif berr_exit("Shutdown failed"); } done: if (stats){ print_stats(ssl); } SSL_free(ssl); return(0); }