svnno****@sourc*****
svnno****@sourc*****
2016年 11月 3日 (木) 01:12:29 JST
Revision: 6528 http://sourceforge.jp/projects/ttssh2/scm/svn/commits/6528 Author: yutakapon Date: 2016-11-03 01:12:28 +0900 (Thu, 03 Nov 2016) Log Message: ----------- チケット #34056 SCPダウンロードすると応答なしになる SCPファイルの受信処理において、スレッドのメッセージキューの使用を廃止して、 代わりに独自のリンクドリスト方式に変更した。 Ticket Links: ------------ http://sourceforge.jp/projects/ttssh2/tracker/detail/34056 Modified Paths: -------------- trunk/ttssh2/ttxssh/ssh.c trunk/ttssh2/ttxssh/ssh.h -------------- next part -------------- Modified: trunk/ttssh2/ttxssh/ssh.c =================================================================== --- trunk/ttssh2/ttxssh/ssh.c 2016-11-02 15:53:04 UTC (rev 6527) +++ trunk/ttssh2/ttxssh/ssh.c 2016-11-02 16:12:28 UTC (rev 6528) @@ -84,6 +84,8 @@ static char ssh_ttymodes[] = "\x01\x03\x02\x1c\x03\x08\x04\x15\x05\x04"; +static CRITICAL_SECTION g_ssh_scp_lock; /* SCP\x8E\xF3\x90M\x97p\x83\x8D\x83b\x83N */ + static void try_send_credentials(PTInstVar pvar); static void prep_compression(PTInstVar pvar); @@ -122,7 +124,10 @@ static void start_ssh_heartbeat_thread(PTInstVar pvar); void ssh2_channel_send_close(PTInstVar pvar, Channel_t *c); static BOOL SSH_agent_response(PTInstVar pvar, Channel_t *c, int local_channel_num, unsigned char *data, unsigned int buflen); +static void ssh2_scp_get_packetlist(Channel_t *c, unsigned char **buf, unsigned int *buflen); +static void ssh2_scp_free_packetlist(Channel_t *c); + // // Global request confirm // @@ -300,6 +305,8 @@ CloseHandle(c->scp.thread); c->scp.thread = (HANDLE)-1L; } + + ssh2_scp_free_packetlist(c); } if (c->type == TYPE_AGENT) { buffer_free(c->agent_msg); @@ -8182,11 +8189,14 @@ if (is_canceled_window(hWnd)) goto cancel_abort; - if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE) != 0) { + ssh2_scp_get_packetlist(c, &data, &buflen); + if (data && buflen) { + msg.message = WM_RECEIVING_FILE; + switch (msg.message) { case WM_RECEIVING_FILE: - data = (unsigned char *)msg.wParam; - buflen = (unsigned int)msg.lParam; + //data = (unsigned char *)msg.wParam; + //buflen = (unsigned int)msg.lParam; eof = 0; if (c->scp.filercvsize >= c->scp.filetotalsize) { // EOF @@ -8261,6 +8271,86 @@ return 0; } +static void ssh2_scp_add_packetlist(Channel_t *c, unsigned char *buf, unsigned int buflen) +{ + PacketList_t *p, *old; + + EnterCriticalSection(&g_ssh_scp_lock); + + // allocate new buffer + p = malloc(sizeof(PacketList_t)); + if (p == NULL) + goto error; + p->buf = buf; + p->buflen = buflen; + p->next = NULL; + + if (c->scp.pktlist_head == NULL) { + c->scp.pktlist_head = p; + c->scp.pktlist_tail = p; + } + else { + old = c->scp.pktlist_tail; + old->next = p; + c->scp.pktlist_tail = p; + } + +error:; + LeaveCriticalSection(&g_ssh_scp_lock); +} + +static void ssh2_scp_get_packetlist(Channel_t *c, unsigned char **buf, unsigned int *buflen) +{ + PacketList_t *p; + + EnterCriticalSection(&g_ssh_scp_lock); + + if (c->scp.pktlist_head == NULL) { + *buf = NULL; + *buflen = 0; + goto end; + } + + p = c->scp.pktlist_head; + *buf = p->buf; + *buflen = p->buflen; + + c->scp.pktlist_head = p->next; + + if (c->scp.pktlist_head == NULL) + c->scp.pktlist_tail = NULL; + + free(p); + +end:; + LeaveCriticalSection(&g_ssh_scp_lock); +} + +static void ssh2_scp_alloc_packetlist(Channel_t *c) +{ + c->scp.pktlist_head = NULL; + c->scp.pktlist_tail = NULL; + InitializeCriticalSection(&g_ssh_scp_lock); +} + +static void ssh2_scp_free_packetlist(Channel_t *c) +{ + PacketList_t *p, *old; + + p = c->scp.pktlist_head; + while (p) { + old = p; + p = p->next; + + free(old->buf); + free(old); + } + + c->scp.pktlist_head = NULL; + c->scp.pktlist_tail = NULL; + DeleteCriticalSection(&g_ssh_scp_lock); +} + static BOOL SSH2_scp_fromremote(PTInstVar pvar, Channel_t *c, unsigned char *data, unsigned int buflen) { int permission; @@ -8314,6 +8404,7 @@ ShowWindow(hDlgWnd, SW_SHOW); } + ssh2_scp_alloc_packetlist(c); thread = (HANDLE)_beginthreadex(NULL, 0, ssh_scp_receive_thread, c, 0, &tid); if (thread == (HANDLE)-1) { // TODO: @@ -8335,26 +8426,15 @@ } else if (c->scp.state == SCP_DATA) { // payload\x82̎\xF3\x90M unsigned char *newdata = malloc(buflen); - BOOL ret; - DWORD texit; if (newdata != NULL) { memcpy(newdata, data, buflen); - do { - // SCP\x83t\x83@\x83C\x83\x8B\x8E\xF3\x90M\x92\x86\x82ɁA\x83t\x83@\x83C\x83\x8B\x8E\xF3\x90M\x82𒆒f\x82\xB7\x82\xE9\x82ƁA\x96\xB3\x8C\xC0\x83\x8B\x81[\x83v\x82Ɋׂ邱\x82Ƃ\xAA\x82\xA0\x82邽\x82߁A - // \x83X\x83\x8C\x83b\x83h\x82\xAA\x8FI\x97\xB9\x82\xB5\x82Ă\xA2\x82邩\x82ǂ\xA4\x82\xA9\x82ʂ\xB7\x82\xE9\x81B - // (2014.7.6 yutaka) - texit = STILL_ACTIVE; - GetExitCodeThread(c->scp.thread, &texit); - if (texit != STILL_ACTIVE) { - texit = texit; - break; - } - // \x83X\x83\x8C\x83b\x83h\x82\xAA\x83L\x83\x85\x81[\x82\xF0\x8D\xEC\x82\xC1\x82Ă\xA2\x82Ȃ\xA2\x8Fꍇ\x81A\x83\x81\x83b\x83Z\x81[\x83W\x83|\x83X\x83g\x82\xAA\x8E\xB8\x94s\x82\xB7\x82邱\x82Ƃ\xAA\x82\xA0\x82\xE9\x82̂ŁA - // \x96\xB3\x8C\xC0\x83\x8A\x83g\x83\x89\x83C\x82\xB7\x82\xE9\x81BMSDN\x82ɂ\xBB\x82\xA4\x82\xB5\x82\xEB\x82Ə\x91\x82\xA2\x82Ă\xA0\x82\xE9\x81B - // (2011.6.15 yutaka) - ret = PostThreadMessage(c->scp.thread_id, WM_RECEIVING_FILE, (WPARAM)newdata, (LPARAM)buflen); - } while (ret == FALSE); + // SCP\x8E\xF3\x90M\x8F\x88\x97\x9D\x82̃X\x83s\x81[\x83h\x82\xAA\x91\xAC\x82\xA2\x8Fꍇ\x81A\x83X\x83\x8C\x83b\x83h\x82̃\x81\x83b\x83Z\x81[\x83W\x83L\x83\x85\x81[\x82\xAA\x83t\x83\x8B(10000\x8C\xC2)\x82\xC9 + // \x82Ȃ\xE8\x81A\x82\xA9\x82X\x83\x8C\x83b\x83h\x8F\xE3\x82ł\xCC SendMessage \x82\xAA\x83u\x83\x8D\x83b\x83N\x82\xB7\x82邱\x82Ƃɂ\xE6\x82\xE8\x81ATera Term(TTSSH) + // \x8E\xA9\x91̂\xAA\x83X\x83g\x81[\x83\x8B\x82\xB5\x82Ă\xB5\x82܂\xA4\x81B\x82\xB1\x82̖\xE2\x91\xE8\x82\xF0\x89\xF1\x94\xF0\x82\xB7\x82邽\x82߁A\x83X\x83\x8C\x83b\x83h\x82̃\x81\x83b\x83Z\x81[\x83W\x83L\x83\x85\x81[\x82\xF0 + // \x8Eg\x82\xA4\x82̂\xF0\x82\xE2\x82߂āA\x83\x8A\x83\x93\x83N\x83h\x83\x8A\x83X\x83g\x95\xFB\x8E\xAE\x82ɐ\xE8\x91ւ\xA6\x82\xE9\x81B + // (2016.11.3 yutaka) + ssh2_scp_add_packetlist(c, newdata, buflen); } } else if (c->scp.state == SCP_CLOSING) { // EOF\x82̎\xF3\x90M Modified: trunk/ttssh2/ttxssh/ssh.h =================================================================== --- trunk/ttssh2/ttxssh/ssh.h 2016-11-02 15:53:04 UTC (rev 6527) +++ trunk/ttssh2/ttxssh/ssh.h 2016-11-02 16:12:28 UTC (rev 6528) @@ -750,6 +750,12 @@ struct bufchain *next; } bufchain_t; +typedef struct PacketList { + char *buf; + unsigned int buflen; + struct PacketList *next; +} PacketList_t; + typedef struct scp { enum scp_dir dir; // transfer direction enum scp_state state; // SCP state @@ -767,6 +773,8 @@ long long filercvsize; DWORD filemtime; DWORD fileatime; + PacketList_t *pktlist_head; + PacketList_t *pktlist_tail; } scp_t; enum sftp_state {