2012-05-30 56 views
-1

這個長代碼使用Socket發送POST請求,整個代碼沒有任何抱怨,但我現在面臨的是,它吃東西大量的CPU功耗,使用太多的內存(RAM)使用套接字發送POST請求,但使用大量內存電源

我可以看到,因爲我的筆記本電腦變得非常快,並通過查看我的Mac。

我試圖找到錯誤或其中,那個非常大的內存問題是,但不能。我花了一個多月的時間嘗試着自己解決這個問題,但不知道我在說些什麼來說實話。

我是如此絕望,我的推杆都挺釋放梅託德的..甚至是錯誤..只是,看看是否能做出了改變,但無濟於事..

所以現在我不知道自己做錯了什麼或如何解決此問題,請幫我...

去更新與選擇,時刻代碼...試圖把它清理乾淨第一

+1

這裏的一個特技:只使用的C或C++之一。這段代碼是兩個糟糕的壞壞混合物。它不會僅調用未定義的行爲*,因爲它存在泄漏*並且不良清理代碼從不運行。 –

+0

我同意你的看法,但我試圖修復大內存泄漏第一個 – user1417815

+0

問題是在數據庫()函數 - memleak在最後,看到我的答案。您也可以通過刪除這些例程中未使用的strip_copy()來清除代碼。 –

回答

4

第一件事:不要混合malloc()和delete []。他們可能會或可能不會引用相同的內存分配器。所以使用malloc()/ free()或new char []/delete []對。

問題出在這裏(在Database()函數中):你有一個可怕的memleak。不要像這樣分配內存來傳遞結果。更好使用緩衝區。你的程序是多線程的,所以使用堆棧上的緩衝區。不要在任何你未分配的東西上調用delete [](var聲明,如「char Buf [100];」是而不是的分配)。

新版本(I省略main()和條帶()函數還包括的):

#define MAX_ECHO_SIZE (1024) 
#define MAX_RESPONSE_SIZE (1024) 

void process_http(int sockfd, const char *host, const char *page, const char *poststr, char* OutResponse) 
{ 
    char* ptr; 
    char sendline[MAXLINE + 1], recvline[MAXLINE + 1]; 
    ssize_t n; 

    snprintf(sendline, MAXSUB, 
     "POST %s HTTP/1.0\r\n" // POST or GET, both tested and works. Both HTTP 1.0 HTTP 1.1 works, but sometimes 
     "Host: %s\r\n"  //oth HTTP 1.0 HTTP 1.1 works, but sometimes HTTP 1.0 works better in localhost type 
     "Content-type: application/x-www-form-urlencoded\r\n" 
     "Content-length: %d\r\n\r\n" 
     "%s\r\n", page, host, (unsigned int)strlen(poststr), poststr); 

    if (write(sockfd, sendline, strlen(sendline))>= 0) 
    { 
     while ((n = read(sockfd, recvline, MAXLINE)) > 0) 
     { 
      recvline[n] = '\0'; 

      if(fputs(recvline,stdout) ==EOF) { cout << ("fputs erros"); } 
      ptr = strstr(recvline, "\r\n\r\n"); 
      strip(ptr, "\r\n\r\n"); 

      // check len for OutResponse here ? 
      snprintf(OutResponse, 6000,"%s", ptr); 
     } 
    } 
} 

int Database(const char * hname, const char * page, const char * var, const char * poststr, int port, char* EchoResponse, int MaxEchoLen){ 

    char url[MAXLINE]; 
    char response[MAX_RESPONSE_SIZE]; 

    snprintf(url, MAXLINE, "%s=%s", var, poststr); 

    short int sockfd ; 
    struct sockaddr_in servaddr; 
    struct hostent *hptr; 
    char str[MAXLINE]; 
    char** pptr; 

    hptr = gethostbyname(hname); 

    sockfd = socket(AF_INET, SOCK_STREAM, 0); 

    if (!hptr) { 
     cout << ("host not found\n"); 
     return -1; // "host not found"; 
    } 

    if (hptr->h_addrtype == AF_INET && (pptr = hptr->h_addr_list) != NULL) { 
     inet_ntop(hptr->h_addrtype, *pptr, str, sizeof(str)); 
    } 
    if (sockfd >= 0 ) { 
     bzero(&servaddr, sizeof(servaddr)); 
     servaddr.sin_family = AF_INET; 
     servaddr.sin_port = htons(port); 
     inet_pton(AF_INET, str, &servaddr.sin_addr); 

     if (connect(sockfd, (SA *) & servaddr, sizeof(servaddr)) < 0) { 
      return -2; // "Server down, connect error"; 
     } 
     else { 
      process_http(sockfd, hname, page, url, &response[0], MAX_RESPONSE_SIZE); 

      int len = strlen(response)+1; 
      if(len >= MaxEchoLen) { return -3; /* buffer too small*/ } 

      // Copy the contents with 
      strcpy(EchoResponse, response); 

      /// You must not free all of char[] allocated on stack 
      close(sockfd); 

      return 0; // OK 
     } 
    } 
} 

void *multithreading1(void *ptr) { 
    char LocalEchoResponse[MAX_ECHO_SIZE]; 

    while (1) { 
      int RetCode = Database("2.107.xx.xxx", "/ajax.php", "submit", "HEllo WORLD", 80, &LocalEchoResponse[0], MAX_ECHO_SIZE); 
      /// check the error 
    } 
} 
+1

如果那是全部... –

+0

Viktor如何可以改變工作..沒有問題? – user1417815

+0

-1您的快速「修復」會調用未定義的行爲! –

1

你有strip_copy一個相當大的內存泄漏。無論你在迴歸之後放置什麼,都不會執行。我驚訝編譯器沒有抱怨這個。 process_http()函數中的同樣問題。

修復這樣的:

static void strip_copy(char const *s, char *buf, const char * SPACE) 
{ 
    if (buf) 
    { 
     char *p = buf; 
     char const *q; 
     int n; 
     for (q = s; *q; q += n + strspn(q+n, SPACE)) 
     { 
      n = strcspn(q, SPACE); 
      strncpy(p, q, n); 
      p += n; 
     } 
     *p++ = '\0'; 
     buf = (char*)realloc(buf, p - buf); 
    } 
} 

// Then call it like this 
char *buf = new[1 + strlen(s)]; 
strip_copy(s, buf, ' '); 
// use buf 
delete [] buf; 

而且在process_http()

const char* process_http(int sockfd, const char *host, const char *page, const char *poststr) 
{ 
    .... 
    // delete here only what you dynamically 
    // allocated with new() BEFORE the return 
    return response; // n 
} 

並且不要混用的malloc()用delete():

  • 的malloc()去與免費()
  • new()附帶delete()

這不是與所用的內存有關,而是直接調用read()/ write(),而不是直接調用read(),您應該使用select()來知道何時準備讀取或寫入。這裏有一個相關的問題:https://stackoverflow.com/a/10800029/1158895

+0

strip_copy()不使用,謝天謝地:) –

+0

這是真的,但怎麼可以'這是固定的?你能指出什麼改變什麼? – user1417815

+0

-1您的「修復」調用未定義的行爲! –