OSDN Git Service

Fix bugs of playing sound.
[ffftp/ffftp.git] / getput.c
index 2e3b93f..1c287b6 100644 (file)
--- a/getput.c
+++ b/getput.c
@@ -1,6 +1,6 @@
-/*=============================================================================\r
+/*=============================================================================\r
 *\r
-*                                                      \83_\83E\83\93\83\8d\81[\83h\81^\83A\83b\83v\83\8d\81[\83h\r
+*                                                      ダウンロード/アップロード\r
 *\r
 ===============================================================================\r
 / Copyright (C) 1997-2007 Sota. All rights reserved.\r
 / THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\r
 /============================================================================*/\r
 \r
-/* \82±\82Ì\83\\81[\83X\82Í\88ê\95\94\81AWS_FTP Version 93.12.05 \82Ì\83\\81[\83X\82ð\8eQ\8dl\82É\82µ\82Ü\82µ\82½\81B */\r
-/* \83X\83\8c\83b\83h\82Ì\8dì\90¬\81^\8fI\97¹\82É\8aÖ\82µ\82Ä\81A\94ó\8cû\93a\8dì\90¬\82Ì\83p\83b\83`\82ð\91g\82Ý\8d\9e\82Ý\82Ü\82µ\82½\81B */\r
+/* このソースは一部、WS_FTP Version 93.12.05 のソースを参考にしました。 */\r
+/* スレッドの作成/終了に関して、樋口殿作成のパッチを組み込みました。 */\r
 \r
 /*\r
-       \88ê\95\94\81A\8d\82\91¬\89»\82Ì\82½\82ß\82Ì\83R\81[\83h\92Ç\89Á by H.Shirouzu at 2002/10/02\r
+       一部、高速化のためのコード追加 by H.Shirouzu at 2002/10/02\r
 */\r
 \r
 #define        STRICT\r
 #define SOCKBUF_SIZE   (256 * 1024)\r
 /* End */\r
 \r
-#ifdef DISABLE_NETWORK_BUFFERS\r
+#ifdef DISABLE_TRANSFER_NETWORK_BUFFERS\r
 #undef BUFSIZE\r
-#define BUFSIZE                        (63 * 1024)     // RWIN\92l\88È\89º\82Å\8f[\95ª\82È\91å\82«\82³\82ª\96]\82Ü\82µ\82¢\82Æ\8ev\82í\82ê\82é\81B\r
+#define BUFSIZE                        (64 * 1024)     // RWIN値以下で充分な大きさが望ましいと思われる。\r
 #undef SET_BUFFER_SIZE\r
 #endif\r
 \r
-#define TIMER_DISPLAY          1               /* \95\\8e¦\8dX\90V\97p\83^\83C\83}\82ÌID */\r
-#define DISPLAY_TIMING         500             /* \95\\8e¦\8dX\90V\8e\9e\8aÔ 0.5\95b */\r
+#define TIMER_DISPLAY          1               /* 表示更新用タイマのID */\r
+#define DISPLAY_TIMING         500             /* 表示更新時間 0.5秒 */\r
 \r
 #define ERR_MSG_LEN                    1024\r
 \r
 \r
-/* \8dí\8f\9c\8am\94F\83_\83C\83A\83\8d\83O\82Ì\8fî\95ñ */\r
+/* 削除確認ダイアログの情報 */\r
 typedef struct {\r
        int Cur;\r
        TRANSPACKET *Pkt;\r
 } MIRRORDELETEINFO;\r
 \r
 \r
-/*===== \83v\83\8d\83g\83^\83C\83v =====*/\r
+/*===== プロトタイプ =====*/\r
 \r
 static void DispTransPacket(TRANSPACKET *Pkt);\r
 static void EraseTransFileList(void);\r
@@ -94,7 +94,9 @@ static int DoUpLoad(SOCKET cSkt, TRANSPACKET *Pkt);
 static int UpLoadNonPassive(TRANSPACKET *Pkt);\r
 static int UpLoadPassive(TRANSPACKET *Pkt);\r
 static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt);\r
-static int TermCodeConvAndSend(TERMCODECONVINFO *tInfo, SOCKET Skt, char *Data, int Size, int Ascii);\r
+// 同時接続対応\r
+//static int TermCodeConvAndSend(TERMCODECONVINFO *tInfo, SOCKET Skt, char *Data, int Size, int Ascii);\r
+static int TermCodeConvAndSend(int ThreadCount, TERMCODECONVINFO *tInfo, SOCKET Skt, char *Data, int Size, int Ascii);\r
 static void DispUploadFinishMsg(TRANSPACKET *Pkt, int iRetCode);\r
 static int SetUploadResume(TRANSPACKET *Pkt, int ProcMode, LONGLONG Size, int *Mode);\r
 static LRESULT CALLBACK TransDlgProc(HWND hDlg, UINT Msg, WPARAM wParam, LPARAM lParam);\r
@@ -106,35 +108,44 @@ static int MirrorDelNotify(int Cur, int Notify, TRANSPACKET *Pkt);
 static BOOL CALLBACK MirrorDeleteDialogCallBack(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam);\r
 static void SetErrorMsg(char *fmt, ...);\r
 \r
-/*===== \83\8d\81[\83J\83\8b\82È\83\8f\81[\83N =====*/\r
+/*===== ローカルなワーク =====*/\r
 \r
-static HANDLE hTransferThread;\r
+// 同時接続対応\r
+//static HANDLE hTransferThread;\r
+static HANDLE hTransferThread[MAX_DATA_CONNECTION];\r
 static int fTransferThreadExit = FALSE;\r
 \r
-static HANDLE hRunMutex;                               /* \93]\91\97\83X\83\8c\83b\83h\8eÀ\8ds\83~\83\85\81[\83e\83b\83N\83X */\r
-static HANDLE hListAccMutex;                   /* \93]\91\97\83t\83@\83C\83\8b\83A\83N\83Z\83X\97p\83~\83\85\81[\83e\83b\83N\83X */\r
+static HANDLE hRunMutex;                               /* 転送スレッド実行ミューテックス */\r
+static HANDLE hListAccMutex;                   /* 転送ファイルアクセス用ミューテックス */\r
 \r
-static int TransFiles = 0;                             /* \93]\91\97\91Ò\82¿\83t\83@\83C\83\8b\90\94 */\r
-static TRANSPACKET *TransPacketBase = NULL;    /* \93]\91\97\83t\83@\83C\83\8b\83\8a\83X\83g */\r
+static int TransFiles = 0;                             /* 転送待ちファイル数 */\r
+static TRANSPACKET *TransPacketBase = NULL;    /* 転送ファイルリスト */\r
+// 同時接続対応\r
+static TRANSPACKET *NextTransPacketBase = NULL;\r
 \r
-static int Canceled;           /* \92\86\8e~\83t\83\89\83O YES/NO */\r
-static int ClearAll;           /* \91S\82Ä\92\86\8e~\83t\83\89\83O YES/NO */\r
+// 同時接続対応\r
+//static int Canceled;         /* 中止フラグ YES/NO */\r
+static int Canceled[MAX_DATA_CONNECTION];              /* 中止フラグ YES/NO */\r
+static int ClearAll;           /* 全て中止フラグ YES/NO */\r
 \r
-static int ForceAbort;         /* \93]\91\97\92\86\8e~\83t\83\89\83O */\r
-                                                       /* \82±\82Ì\83t\83\89\83O\82Í\83X\83\8c\83b\83h\82ð\8fI\97¹\82³\82¹\82é\82Æ\82«\82É\8eg\82¤ */\r
+static int ForceAbort;         /* 転送中止フラグ */\r
+                                                       /* このフラグはスレッドを終了させるときに使う */\r
 \r
-static LONGLONG AllTransSizeNow;       /* \8d¡\89ñ\82Ì\93]\91\97\82Å\93]\91\97\82µ\82½\83T\83C\83Y */\r
-static time_t TimeStart;       /* \93]\91\97\8aJ\8en\8e\9e\8aÔ */\r
+// 同時接続対応\r
+//static LONGLONG AllTransSizeNow;     /* 今回の転送で転送したサイズ */\r
+//static time_t TimeStart;     /* 転送開始時間 */\r
+static LONGLONG AllTransSizeNow[MAX_DATA_CONNECTION];  /* 今回の転送で転送したサイズ */\r
+static time_t TimeStart[MAX_DATA_CONNECTION];  /* 転送開始時間 */\r
 \r
-static int KeepDlg = NO;       /* \93]\91\97\92\86\83_\83C\83A\83\8d\83O\82ð\8fÁ\82³\82È\82¢\82©\82Ç\82¤\82© (YES/NO) */\r
-static int MoveToForeground = NO;              /* \83E\83C\83\93\83h\83E\82ð\91O\96Ê\82É\88Ú\93®\82·\82é\82©\82Ç\82¤\82© (YES/NO) */\r
+static int KeepDlg = NO;       /* 転送中ダイアログを消さないかどうか (YES/NO) */\r
+static int MoveToForeground = NO;              /* ウインドウを前面に移動するかどうか (YES/NO) */\r
 \r
 static char CurDir[FMAX_PATH+1] = { "" };\r
 static char ErrMsg[ERR_MSG_LEN+7];\r
 \r
-/*===== \8aO\95\94\8eQ\8fÆ =====*/\r
+/*===== 外部参照 =====*/\r
 \r
-/* \90Ý\92è\92l */\r
+/* 設定値 */\r
 extern int SaveTimeStamp;\r
 extern int RmEOF;\r
 // extern int TimeOut;\r
@@ -145,18 +156,19 @@ extern int FolderAttr;
 extern int FolderAttrNum;\r
 \r
 \r
-/*----- \83t\83@\83C\83\8b\93]\91\97\83X\83\8c\83b\83h\82ð\8bN\93®\82·\82é ----------------------------------------\r
+/*----- ファイル転送スレッドを起動する ----------------------------------------\r
 *\r
 *      Parameter\r
-*              \82È\82µ\r
+*              なし\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 int MakeTransferThread(void)\r
 {\r
        DWORD dwID;\r
+       int i;\r
 \r
        hListAccMutex = CreateMutex( NULL, FALSE, NULL );\r
        hRunMutex = CreateMutex( NULL, TRUE, NULL );\r
@@ -165,36 +177,57 @@ int MakeTransferThread(void)
        ForceAbort = NO;\r
 \r
        fTransferThreadExit = FALSE;\r
-       hTransferThread = (HANDLE)_beginthreadex(NULL, 0, TransferThread, 0, 0, &dwID);\r
-       if (hTransferThread == NULL)\r
-               return(FAIL); /* XXX */\r
+       // 同時接続対応\r
+//     hTransferThread = (HANDLE)_beginthreadex(NULL, 0, TransferThread, 0, 0, &dwID);\r
+//     if (hTransferThread == NULL)\r
+//             return(FFFTP_FAIL); /* XXX */\r
+       for(i = 0; i < MAX_DATA_CONNECTION; i++)\r
+       {\r
+               hTransferThread[i] = (HANDLE)_beginthreadex(NULL, 0, TransferThread, (void*)i, 0, &dwID);\r
+               if(hTransferThread[i] == NULL)\r
+                       return FFFTP_FAIL;\r
+       }\r
 \r
-       return(SUCCESS);\r
+       return(FFFTP_SUCCESS);\r
 }\r
 \r
 \r
-/*----- \83t\83@\83C\83\8b\93]\91\97\83X\83\8c\83b\83h\82ð\8fI\97¹\82·\82é ----------------------------------------\r
+/*----- ファイル転送スレッドを終了する ----------------------------------------\r
 *\r
 *      Parameter\r
-*              \82È\82µ\r
+*              なし\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 void CloseTransferThread(void)\r
 {\r
-       Canceled = YES;\r
+       int i;\r
+       // 同時接続対応\r
+//     Canceled = YES;\r
+       for(i = 0; i < MAX_DATA_CONNECTION; i++)\r
+               Canceled[i] = YES;\r
        ClearAll = YES;\r
        ForceAbort = YES;\r
 \r
        fTransferThreadExit = TRUE;\r
-       while(WaitForSingleObject(hTransferThread, 10) == WAIT_TIMEOUT)\r
+       // 同時接続対応\r
+//     while(WaitForSingleObject(hTransferThread, 10) == WAIT_TIMEOUT)\r
+//     {\r
+//             BackgrndMessageProc();\r
+//             Canceled = YES;\r
+//     }\r
+//     CloseHandle(hTransferThread);\r
+       for(i = 0; i < MAX_DATA_CONNECTION; i++)\r
        {\r
-               BackgrndMessageProc();\r
-               Canceled = YES;\r
+               while(WaitForSingleObject(hTransferThread[i], 10) == WAIT_TIMEOUT)\r
+               {\r
+                       BackgrndMessageProc();\r
+                       Canceled[i] = YES;\r
+               }\r
+               CloseHandle(hTransferThread[i]);\r
        }\r
-       CloseHandle(hTransferThread);\r
 \r
        ReleaseMutex( hRunMutex );\r
 \r
@@ -204,15 +237,15 @@ void CloseTransferThread(void)
 }\r
 \r
 \r
-/*----- \93]\91\97\82·\82é\83t\83@\83C\83\8b\8fî\95ñ\82ð\83\8a\83X\83g\82É\92Ç\89Á\82·\82é --------------------------------\r
+/*----- 転送するファイル情報をリストに追加する --------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              TRANSPACKET **Base : \83\8a\83X\83g\82Ì\90æ\93ª\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              TRANSPACKET **Base : リストの先頭\r
 *\r
 *      Return Value\r
-*              int \83X\83e\81[\83^\83X\r
-*                      SUCCESS/FAIL\r
+*              int ステータス\r
+*                      FFFTP_SUCCESS/FFFTP_FAIL\r
 *----------------------------------------------------------------------------*/\r
 \r
 int AddTmpTransFileList(TRANSPACKET *Pkt, TRANSPACKET **Base)\r
@@ -221,7 +254,7 @@ int AddTmpTransFileList(TRANSPACKET *Pkt, TRANSPACKET **Base)
        TRANSPACKET *Prev;\r
        int Sts;\r
 \r
-       Sts = FAIL;\r
+       Sts = FFFTP_FAIL;\r
        if((Pos = malloc(sizeof(TRANSPACKET))) != NULL)\r
        {\r
                memcpy(Pos, Pkt, sizeof(TRANSPACKET));\r
@@ -236,19 +269,19 @@ int AddTmpTransFileList(TRANSPACKET *Pkt, TRANSPACKET **Base)
                                Prev = Prev->Next;\r
                        Prev->Next = Pos;\r
                }\r
-               Sts = SUCCESS;\r
+               Sts = FFFTP_SUCCESS;\r
        }\r
        return(Sts);\r
 }\r
 \r
 \r
-/*----- \93]\91\97\82·\82é\83t\83@\83C\83\8b\8fî\95ñ\83\8a\83X\83g\82ð\83N\83\8a\83A\82·\82é --------------------------------\r
+/*----- 転送するファイル情報リストをクリアする --------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET **Base : \83\8a\83X\83g\82Ì\90æ\93ª\r
+*              TRANSPACKET **Base : リストの先頭\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 void EraseTmpTransFileList(TRANSPACKET **Base)\r
@@ -268,15 +301,15 @@ void EraseTmpTransFileList(TRANSPACKET **Base)
 }\r
 \r
 \r
-/*----- \93]\91\97\82·\82é\83t\83@\83C\83\8b\8fî\95ñ\83\8a\83X\83g\82©\82ç\82P\82Â\82Ì\8fî\95ñ\82ð\8eæ\82è\8f\9c\82­ --------------------\r
+/*----- 転送するファイル情報リストから1つの情報を取り除く --------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              TRANSPACKET **Base : \83\8a\83X\83g\82Ì\90æ\93ª\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              TRANSPACKET **Base : リストの先頭\r
 *\r
 *      Return Value\r
-*              int \83X\83e\81[\83^\83X\r
-*                      SUCCESS/FAIL\r
+*              int ステータス\r
+*                      FFFTP_SUCCESS/FFFTP_FAIL\r
 *----------------------------------------------------------------------------*/\r
 \r
 int RemoveTmpTransFileListItem(TRANSPACKET **Base, int Num)\r
@@ -285,13 +318,13 @@ int RemoveTmpTransFileListItem(TRANSPACKET **Base, int Num)
        TRANSPACKET *Prev;\r
        int Sts;\r
 \r
-       Sts = FAIL;\r
+       Sts = FFFTP_FAIL;\r
        Pos = *Base;\r
        if(Num == 0)\r
        {\r
                *Base = Pos->Next;\r
                free(Pos);\r
-               Sts = SUCCESS;\r
+               Sts = FFFTP_SUCCESS;\r
        }\r
        else\r
        {\r
@@ -303,7 +336,7 @@ int RemoveTmpTransFileListItem(TRANSPACKET **Base, int Num)
                        {\r
                                Prev->Next = Pos->Next;\r
                                free(Pos);\r
-                               Sts = SUCCESS;\r
+                               Sts = FFFTP_SUCCESS;\r
                                break;\r
                        }\r
                }\r
@@ -312,22 +345,28 @@ int RemoveTmpTransFileListItem(TRANSPACKET **Base, int Num)
 }\r
 \r
 \r
-/*----- \93]\91\97\82·\82é\83t\83@\83C\83\8b\8fî\95ñ\82ð\93]\91\97\83t\83@\83C\83\8b\83\8a\83X\83g\82É\93o\98^\82·\82é --------------------\r
+/*----- 転送するファイル情報を転送ファイルリストに登録する --------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 void AddTransFileList(TRANSPACKET *Pkt)\r
 {\r
        DispTransPacket(Pkt);\r
 \r
-       WaitForSingleObject(hListAccMutex, INFINITE);\r
+       // 同時接続対応\r
+//     WaitForSingleObject(hListAccMutex, INFINITE);\r
+       while(WaitForSingleObject(hListAccMutex, 0) == WAIT_TIMEOUT)\r
+       {\r
+               BackgrndMessageProc();\r
+               Sleep(1);\r
+       }\r
 \r
-       if(AddTmpTransFileList(Pkt, &TransPacketBase) == SUCCESS)\r
+       if(AddTmpTransFileList(Pkt, &TransPacketBase) == FFFTP_SUCCESS)\r
        {\r
                if((strncmp(Pkt->Cmd, "RETR", 4) == 0) ||\r
                   (strncmp(Pkt->Cmd, "STOR", 4) == 0))\r
@@ -336,30 +375,39 @@ void AddTransFileList(TRANSPACKET *Pkt)
                        PostMessage(GetMainHwnd(), WM_CHANGE_COND, 0, 0);\r
                }\r
        }\r
+       // 同時接続対応\r
+       if(NextTransPacketBase == NULL)\r
+               NextTransPacketBase = TransPacketBase;\r
        ReleaseMutex(hListAccMutex);\r
 \r
        return;\r
 }\r
 \r
 \r
-/*----- \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\82ð\93]\91\97\83t\83@\83C\83\8b\83\8a\83X\83g\82É\92Ç\89Á\82·\82é ------------------------\r
+/*----- 転送ファイル情報を転送ファイルリストに追加する ------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              TRANSPACKET **Base : \83\8a\83X\83g\82Ì\90æ\93ª\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              TRANSPACKET **Base : リストの先頭\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *\r
 *      Note\r
-*              Pkt\8e©\91Ì\82ð\83\8a\83X\83g\82É\98A\8c\8b\82·\82é\r
+*              Pkt自体をリストに連結する\r
 *----------------------------------------------------------------------------*/\r
 \r
 void AppendTransFileList(TRANSPACKET *Pkt)\r
 {\r
        TRANSPACKET *Pos;\r
 \r
-       WaitForSingleObject(hListAccMutex, INFINITE);\r
+       // 同時接続対応\r
+//     WaitForSingleObject(hListAccMutex, INFINITE);\r
+       while(WaitForSingleObject(hListAccMutex, 0) == WAIT_TIMEOUT)\r
+       {\r
+               BackgrndMessageProc();\r
+               Sleep(1);\r
+       }\r
 \r
        if(TransPacketBase == NULL)\r
                TransPacketBase = Pkt;\r
@@ -370,6 +418,9 @@ void AppendTransFileList(TRANSPACKET *Pkt)
                        Pos = Pos->Next;\r
                Pos->Next = Pkt;\r
        }\r
+       // 同時接続対応\r
+       if(NextTransPacketBase == NULL)\r
+               NextTransPacketBase = TransPacketBase;\r
 \r
        while(Pkt != NULL)\r
        {\r
@@ -389,13 +440,13 @@ void AppendTransFileList(TRANSPACKET *Pkt)
 }\r
 \r
 \r
-/*----- \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\82ð\95\\8e¦\82·\82é --------------------------------------------\r
+/*----- 転送ファイル情報を表示する --------------------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 static void DispTransPacket(TRANSPACKET *Pkt)\r
@@ -419,13 +470,13 @@ static void DispTransPacket(TRANSPACKET *Pkt)
 }\r
 \r
 \r
-/*----- \93]\91\97\83t\83@\83C\83\8b\83\8a\83X\83g\82ð\83N\83\8a\83A\82·\82é ----------------------------------------\r
+/*----- 転送ファイルリストをクリアする ----------------------------------------\r
 *\r
 *      Parameter\r
-*              \82È\82µ\r
+*              なし\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 static void EraseTransFileList(void)\r
@@ -437,27 +488,40 @@ static void EraseTransFileList(void)
 \r
        NotDel = NULL;\r
 \r
-       WaitForSingleObject(hListAccMutex, INFINITE);\r
+       // 同時接続対応\r
+//     WaitForSingleObject(hListAccMutex, INFINITE);\r
+       while(WaitForSingleObject(hListAccMutex, 0) == WAIT_TIMEOUT)\r
+       {\r
+               BackgrndMessageProc();\r
+               Sleep(1);\r
+       }\r
        New = TransPacketBase;\r
        while(New != NULL)\r
        {\r
-               /* \8dÅ\8cã\82Ì"BACKCUR"\82Í\95K\97v\82È\82Ì\82Å\8fÁ\82³\82È\82¢ */\r
+               /* 最後の"BACKCUR"は必要なので消さない */\r
                if(strcmp(New->Cmd, "BACKCUR") == 0)\r
                {\r
                        if(NotDel != NULL)\r
-                               free(NotDel);\r
+                               // 同時接続対応\r
+//                             free(NotDel);\r
+                               strcpy(NotDel->Cmd, "");\r
                        NotDel = New;\r
                        New = New->Next;\r
-                       NotDel->Next = NULL;\r
+                       // 同時接続対応\r
+//                     NotDel->Next = NULL;\r
                }\r
                else\r
                {\r
                        Next = New->Next;\r
-                       free(New);\r
+                       // 同時接続対応\r
+//                     free(New);\r
+                       strcpy(New->Cmd, "");\r
                        New = Next;\r
                }\r
        }\r
        TransPacketBase = NotDel;\r
+       // 同時接続対応\r
+       NextTransPacketBase = TransPacketBase;\r
        TransFiles = 0;\r
        PostMessage(GetMainHwnd(), WM_CHANGE_COND, 0, 0);\r
        ReleaseMutex(hListAccMutex);\r
@@ -468,13 +532,13 @@ static void EraseTransFileList(void)
 }\r
 \r
 \r
-/*----- \93]\91\97\92\86\83_\83C\83A\83\8d\83O\82ð\8fÁ\82³\82È\82¢\82æ\82¤\82É\82·\82é\82©\82Ç\82¤\82©\82ð\90Ý\92è --------------------\r
+/*----- 転送中ダイアログを消さないようにするかどうかを設定 --------------------\r
 *\r
 *      Parameter\r
-*              int Sw : \93]\91\97\92\86\83_\83C\83A\83\8d\83O\82ð\8fÁ\82³\82È\82¢\82©\82Ç\82¤\82© (YES/NO)\r
+*              int Sw : 転送中ダイアログを消さないかどうか (YES/NO)\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 void KeepTransferDialog(int Sw)\r
@@ -484,13 +548,13 @@ void KeepTransferDialog(int Sw)
 }\r
 \r
 \r
-/*----- \8c»\8dÝ\93]\91\97\92\86\82©\82Ç\82¤\82©\82ð\95Ô\82· ----------------------------------------------\r
+/*----- 現在転送中かどうかを返す ----------------------------------------------\r
 *\r
 *      Parameter\r
-*              \82È\82µ\r
+*              なし\r
 *\r
 *      Return Value\r
-*              int \83X\83e\81[\83^\83X (YES/NO=\93]\91\97\92\86\82Å\82Í\82È\82¢)\r
+*              int ステータス (YES/NO=転送中ではない)\r
 *----------------------------------------------------------------------------*/\r
 \r
 int AskTransferNow(void)\r
@@ -499,13 +563,13 @@ int AskTransferNow(void)
 }\r
 \r
 \r
-/*----- \93]\91\97\82·\82é\83t\83@\83C\83\8b\82Ì\90\94\82ð\95Ô\82· --------------------------------------------\r
+/*----- 転送するファイルの数を返す --------------------------------------------\r
 *\r
 *      Parameter\r
-*              \82È\82µ\r
+*              なし\r
 *\r
 *      Return Value\r
-*              int \93]\91\97\82·\82é\83t\83@\83C\83\8b\82Ì\90\94\r
+*              int 転送するファイルの数\r
 *----------------------------------------------------------------------------*/\r
 \r
 int AskTransferFileNum(void)\r
@@ -514,13 +578,13 @@ int AskTransferFileNum(void)
 }\r
 \r
 \r
-/*----- \93]\91\97\92\86\83E\83C\83\93\83h\83E\82ð\91O\96Ê\82É\8fo\82· ------------------------------------------\r
+/*----- 転送中ウインドウを前面に出す ------------------------------------------\r
 *\r
 *      Parameter\r
-*              \82È\82µ\r
+*              なし\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 void GoForwardTransWindow(void)\r
@@ -530,13 +594,13 @@ void GoForwardTransWindow(void)
 }\r
 \r
 \r
-/*----- \93]\91\97\83\\83P\83b\83g\82Ì\83J\83\8c\83\93\83g\83f\83B\83\8c\83N\83g\83\8a\8fî\95ñ\82ð\8f\89\8aú\89» ------------------------\r
+/*----- 転送ソケットのカレントディレクトリ情報を初期化 ------------------------\r
 *\r
 *      Parameter\r
-*              \82È\82µ\r
+*              なし\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 void InitTransCurDir(void)\r
@@ -546,13 +610,13 @@ void InitTransCurDir(void)
 }\r
 \r
 \r
-/*----- \83t\83@\83C\83\8b\93]\91\97\83X\83\8c\83b\83h\82Ì\83\81\83C\83\93\83\8b\81[\83v ------------------------------------\r
+/*----- ファイル転送スレッドのメインループ ------------------------------------\r
 *\r
 *      Parameter\r
-*              void *Dummy : \8eg\82í\82È\82¢\r
+*              void *Dummy : 使わない\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 static ULONG WINAPI TransferThread(void *Dummy)\r
@@ -562,15 +626,29 @@ static ULONG WINAPI TransferThread(void *Dummy)
        char Tmp[FMAX_PATH+1];\r
        int CwdSts;\r
        int GoExit;\r
-       int Down;\r
-       int Up;\r
+//     int Down;\r
+//     int Up;\r
+       static int Down;\r
+       static int Up;\r
        int DelNotify;\r
+       int ThreadCount;\r
+       SOCKET CmdSkt;\r
+       SOCKET NewCmdSkt;\r
+       SOCKET TrnSkt;\r
+       RECT WndRect;\r
+       int i;\r
 \r
        hWndTrans = NULL;\r
        Down = NO;\r
        Up = NO;\r
        GoExit = NO;\r
        DelNotify = NO;\r
+       // 同時接続対応\r
+       // ソケットは各転送スレッドが管理\r
+       ThreadCount = (int)Dummy;\r
+       CmdSkt = INVALID_SOCKET;\r
+       NewCmdSkt = INVALID_SOCKET;\r
+       TrnSkt = INVALID_SOCKET;\r
 \r
        while((TransPacketBase != NULL) ||\r
                  (WaitForSingleObject(hRunMutex, 200) == WAIT_TIMEOUT))\r
@@ -578,29 +656,86 @@ static ULONG WINAPI TransferThread(void *Dummy)
                if(fTransferThreadExit == TRUE)\r
                        break;\r
 \r
-               WaitForSingleObject(hListAccMutex, INFINITE);\r
+//             WaitForSingleObject(hListAccMutex, INFINITE);\r
+               while(WaitForSingleObject(hListAccMutex, 0) == WAIT_TIMEOUT)\r
+               {\r
+                       BackgrndMessageProc();\r
+                       Sleep(1);\r
+               }\r
                memset(ErrMsg, NUL, ERR_MSG_LEN+7);\r
 \r
-               Canceled = NO;\r
+//             Canceled = NO;\r
+               Canceled[ThreadCount] = NO;\r
 \r
-               if(TransPacketBase != NULL)\r
+               while(TransPacketBase != NULL && strcmp(TransPacketBase->Cmd, "") == 0)\r
                {\r
-                       ReleaseMutex(hListAccMutex);\r
+                       Pos = TransPacketBase;\r
+                       TransPacketBase = TransPacketBase->Next;\r
+                       free(Pos);\r
+               }\r
+               NewCmdSkt = AskCmdCtrlSkt();\r
+               if(TransPacketBase && NewCmdSkt != INVALID_SOCKET && ThreadCount < AskMaxThreadCount())\r
+               {\r
+                       if(TrnSkt == INVALID_SOCKET || NewCmdSkt != CmdSkt)\r
+                       {\r
+                               ReleaseMutex(hListAccMutex);\r
+                               ReConnectTrnSkt(&TrnSkt);\r
+//                             WaitForSingleObject(hListAccMutex, INFINITE);\r
+                               while(WaitForSingleObject(hListAccMutex, 0) == WAIT_TIMEOUT)\r
+                               {\r
+                                       BackgrndMessageProc();\r
+                                       Sleep(1);\r
+                               }\r
+                       }\r
+               }\r
+               else\r
+               {\r
+                       if(TrnSkt != INVALID_SOCKET)\r
+                       {\r
+                               ReleaseMutex(hListAccMutex);\r
+                               DoClose(TrnSkt);\r
+                               TrnSkt = INVALID_SOCKET;\r
+//                             WaitForSingleObject(hListAccMutex, INFINITE);\r
+                               while(WaitForSingleObject(hListAccMutex, 0) == WAIT_TIMEOUT)\r
+                               {\r
+                                       BackgrndMessageProc();\r
+                                       Sleep(1);\r
+                               }\r
+                       }\r
+               }\r
+               CmdSkt = NewCmdSkt;\r
+//             if(TransPacketBase != NULL)\r
+               if(TrnSkt != INVALID_SOCKET && NextTransPacketBase != NULL)\r
+               {\r
+                       Pos = NextTransPacketBase;\r
+                       NextTransPacketBase = NextTransPacketBase->Next;\r
+                       // ディレクトリ操作は非同期で行わない\r
+//                     ReleaseMutex(hListAccMutex);\r
                        if(hWndTrans == NULL)\r
                        {\r
-                               if((strncmp(TransPacketBase->Cmd, "RETR", 4) == 0) ||\r
-                                  (strncmp(TransPacketBase->Cmd, "STOR", 4) == 0) ||\r
-                                  (strncmp(TransPacketBase->Cmd, "MKD", 3) == 0) ||\r
-                                  (strncmp(TransPacketBase->Cmd, "L-", 2) == 0) ||\r
-                                  (strncmp(TransPacketBase->Cmd, "R-", 2) == 0))\r
+//                             if((strncmp(TransPacketBase->Cmd, "RETR", 4) == 0) ||\r
+//                                (strncmp(TransPacketBase->Cmd, "STOR", 4) == 0) ||\r
+//                                (strncmp(TransPacketBase->Cmd, "MKD", 3) == 0) ||\r
+//                                (strncmp(TransPacketBase->Cmd, "L-", 2) == 0) ||\r
+//                                (strncmp(TransPacketBase->Cmd, "R-", 2) == 0))\r
+                               if((strncmp(Pos->Cmd, "RETR", 4) == 0) ||\r
+                                  (strncmp(Pos->Cmd, "STOR", 4) == 0) ||\r
+                                  (strncmp(Pos->Cmd, "MKD", 3) == 0) ||\r
+                                  (strncmp(Pos->Cmd, "L-", 2) == 0) ||\r
+                                  (strncmp(Pos->Cmd, "R-", 2) == 0))\r
                                {\r
                                        hWndTrans = CreateDialog(GetFtpInst(), MAKEINTRESOURCE(transfer_dlg), HWND_DESKTOP, (DLGPROC)TransDlgProc);\r
                                        if(MoveToForeground == YES)\r
                                                SetForegroundWindow(hWndTrans);\r
                                        ShowWindow(hWndTrans, SW_SHOWNOACTIVATE);\r
+                                       GetWindowRect(hWndTrans, &WndRect);\r
+                                       SetWindowPos(hWndTrans, NULL, WndRect.left, WndRect.top + (WndRect.bottom - WndRect.top) * ThreadCount - (WndRect.bottom - WndRect.top) * (AskMaxThreadCount() - 1) / 2, 0, 0, SWP_NOSIZE | SWP_NOZORDER);\r
                                }\r
                        }\r
-                       TransPacketBase->hWndTrans = hWndTrans;\r
+//                     TransPacketBase->hWndTrans = hWndTrans;\r
+                       Pos->hWndTrans = hWndTrans;\r
+                       Pos->ctrl_skt = TrnSkt;\r
+                       Pos->ThreadCount = ThreadCount;\r
 \r
                        if(hWndTrans != NULL)\r
                        {\r
@@ -612,60 +747,85 @@ static ULONG WINAPI TransferThread(void *Dummy)
                        }\r
 \r
                        if(hWndTrans != NULL)\r
-                               SendMessage(hWndTrans, WM_SET_PACKET, 0, (LPARAM)TransPacketBase);\r
+//                             SendMessage(hWndTrans, WM_SET_PACKET, 0, (LPARAM)TransPacketBase);\r
+                               SendMessage(hWndTrans, WM_SET_PACKET, 0, (LPARAM)Pos);\r
 \r
-                       /* \83_\83E\83\93\83\8d\81[\83h */\r
-                       if(strncmp(TransPacketBase->Cmd, "RETR", 4) == 0)\r
+                       /* ダウンロード */\r
+//                     if(strncmp(TransPacketBase->Cmd, "RETR", 4) == 0)\r
+                       if(strncmp(Pos->Cmd, "RETR", 4) == 0)\r
                        {\r
-                               /* \95s\90³\82È\83p\83X\82ð\8c\9f\8fo */\r
-                               if(CheckPathViolation(TransPacketBase) == NO)\r
+                               // 一部TYPE、STOR(RETR)、PORT(PASV)を並列に処理できないホストがあるため\r
+//                             ReleaseMutex(hListAccMutex);\r
+                               /* 不正なパスを検出 */\r
+//                             if(CheckPathViolation(TransPacketBase) == NO)\r
+                               if(CheckPathViolation(Pos) == NO)\r
                                {\r
-                                       /* \83t\83\8b\83p\83X\82ð\8eg\82í\82È\82¢\82½\82ß\82Ì\8f\88\97\9d */\r
-                                       if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == SUCCESS)\r
+                                       /* フルパスを使わないための処理 */\r
+//                                     if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == FFFTP_SUCCESS)\r
+                                       if(MakeNonFullPath(Pos, CurDir, Tmp) == FFFTP_SUCCESS)\r
                                        {\r
-                                               if(strncmp(TransPacketBase->Cmd, "RETR-S", 6) == 0)\r
+//                                             if(strncmp(TransPacketBase->Cmd, "RETR-S", 6) == 0)\r
+                                               if(strncmp(Pos->Cmd, "RETR-S", 6) == 0)\r
                                                {\r
-                                                       /* \83T\83C\83Y\82Æ\93ú\95t\82ð\8eæ\93¾ */\r
-                                                       DoSIZE(TransPacketBase->RemoteFile, &TransPacketBase->Size);\r
-                                                       DoMDTM(TransPacketBase->RemoteFile, &TransPacketBase->Time);\r
-                                                       strcpy(TransPacketBase->Cmd, "RETR ");\r
+                                                       /* サイズと日付を取得 */\r
+//                                                     DoSIZE(TransPacketBase->RemoteFile, &TransPacketBase->Size);\r
+//                                                     DoMDTM(TransPacketBase->RemoteFile, &TransPacketBase->Time);\r
+//                                                     strcpy(TransPacketBase->Cmd, "RETR ");\r
+                                                       DoSIZE(TrnSkt, Pos->RemoteFile, &Pos->Size);\r
+                                                       DoMDTM(TrnSkt, Pos->RemoteFile, &Pos->Time);\r
+                                                       strcpy(Pos->Cmd, "RETR ");\r
                                                }\r
 \r
                                                Down = YES;\r
 //                                             if(DoDownLoad(AskTrnCtrlSkt(), TransPacketBase, NO) == 429)\r
 //                                             {\r
-//                                                     if(ReConnectTrnSkt() == SUCCESS)\r
-                                                               DoDownLoad(AskTrnCtrlSkt(), TransPacketBase, NO, &Canceled);\r
+//                                                     if(ReConnectTrnSkt() == FFFTP_SUCCESS)\r
+//                                                             DoDownLoad(AskTrnCtrlSkt(), TransPacketBase, NO, &Canceled);\r
+                                                               DoDownLoad(TrnSkt, Pos, NO, &Canceled[Pos->ThreadCount]);\r
 //                                             }\r
                                        }\r
                                }\r
+                               // 一部TYPE、STOR(RETR)、PORT(PASV)を並列に処理できないホストがあるため\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83A\83b\83v\83\8d\81[\83h */\r
-                       else if(strncmp(TransPacketBase->Cmd, "STOR", 4) == 0)\r
+                       /* アップロード */\r
+//                     else if(strncmp(TransPacketBase->Cmd, "STOR", 4) == 0)\r
+                       else if(strncmp(Pos->Cmd, "STOR", 4) == 0)\r
                        {\r
-                               /* \83t\83\8b\83p\83X\82ð\8eg\82í\82È\82¢\82½\82ß\82Ì\8f\88\97\9d */\r
-                               if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == SUCCESS)\r
+                               // 一部TYPE、STOR(RETR)、PORT(PASV)を並列に処理できないホストがあるため\r
+//                             ReleaseMutex(hListAccMutex);\r
+                               /* フルパスを使わないための処理 */\r
+//                             if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == FFFTP_SUCCESS)\r
+                               if(MakeNonFullPath(Pos, CurDir, Tmp) == FFFTP_SUCCESS)\r
                                {\r
                                        Up = YES;\r
 //                                     if(DoUpLoad(AskTrnCtrlSkt(), TransPacketBase) == 429)\r
 //                                     {\r
-//                                             if(ReConnectTrnSkt() == SUCCESS)\r
-                                                       DoUpLoad(AskTrnCtrlSkt(), TransPacketBase);\r
+//                                             if(ReConnectTrnSkt() == FFFTP_SUCCESS)\r
+//                                                     DoUpLoad(AskTrnCtrlSkt(), TransPacketBase);\r
+                                                       DoUpLoad(TrnSkt, Pos);\r
 //                                     }\r
                                }\r
+                               // 一部TYPE、STOR(RETR)、PORT(PASV)を並列に処理できないホストがあるため\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83t\83H\83\8b\83_\8dì\90¬\81i\83\8d\81[\83J\83\8b\82Ü\82½\82Í\83z\83X\83g\81j */\r
-                       else if(strncmp(TransPacketBase->Cmd, "MKD", 3) == 0)\r
+                       /* フォルダ作成(ローカルまたはホスト) */\r
+//                     else if(strncmp(TransPacketBase->Cmd, "MKD", 3) == 0)\r
+                       else if(strncmp(Pos->Cmd, "MKD", 3) == 0)\r
                        {\r
-                               DispTransFileInfo(TransPacketBase, MSGJPN078, FALSE, YES);\r
+//                             DispTransFileInfo(TransPacketBase, MSGJPN078, FALSE, YES);\r
+                               DispTransFileInfo(Pos, MSGJPN078, FALSE, YES);\r
 \r
-                               if(strlen(TransPacketBase->RemoteFile) > 0)\r
+//                             if(strlen(TransPacketBase->RemoteFile) > 0)\r
+                               if(strlen(Pos->RemoteFile) > 0)\r
                                {\r
-                                       /* \83t\83\8b\83p\83X\82ð\8eg\82í\82È\82¢\82½\82ß\82Ì\8f\88\97\9d */\r
+                                       /* フルパスを使わないための処理 */\r
                                        CwdSts = FTP_COMPLETE;\r
 \r
-                                       strcpy(Tmp, TransPacketBase->RemoteFile);\r
-                                       if(ProcForNonFullpath(Tmp, CurDir, hWndTrans, 1) == FAIL)\r
+//                                     strcpy(Tmp, TransPacketBase->RemoteFile);\r
+                                       strcpy(Tmp, Pos->RemoteFile);\r
+//                                     if(ProcForNonFullpath(Tmp, CurDir, hWndTrans, 1) == FFFTP_FAIL)\r
+                                       if(ProcForNonFullpath(Tmp, CurDir, hWndTrans, (int)TrnSkt + 1) == FFFTP_FAIL)\r
                                        {\r
                                                ClearAll = YES;\r
                                                CwdSts = FTP_ERROR;\r
@@ -674,149 +834,215 @@ static ULONG WINAPI TransferThread(void *Dummy)
                                        if(CwdSts == FTP_COMPLETE)\r
                                        {\r
                                                Up = YES;\r
-                                               CommandProcTrn(NULL, "MKD %s", Tmp);\r
-                                               /* \82·\82Å\82É\83t\83H\83\8b\83_\82ª\82 \82é\8fê\8d\87\82à\82 \82é\82Ì\82Å\81A */\r
-                                               /* \82±\82±\82Å\82Í\83G\83\89\81[\83`\83F\83b\83N\82Í\82µ\82È\82¢ */\r
+//                                             CommandProcTrn(NULL, "MKD %s", Tmp);\r
+                                               CommandProcTrn(TrnSkt, NULL, "MKD %s", Tmp);\r
+                                               /* すでにフォルダがある場合もあるので、 */\r
+                                               /* ここではエラーチェックはしない */\r
 \r
                                        if(FolderAttr)\r
-                                               CommandProcTrn(NULL, "%s %03d %s", AskHostChmodCmd(), FolderAttrNum, Tmp);\r
+//                                             CommandProcTrn(NULL, "%s %03d %s", AskHostChmodCmd(), FolderAttrNum, Tmp);\r
+                                               CommandProcTrn(TrnSkt, NULL, "%s %03d %s", AskHostChmodCmd(), FolderAttrNum, Tmp);\r
                                        }\r
                                }\r
-                               else if(strlen(TransPacketBase->LocalFile) > 0)\r
+//                             else if(strlen(TransPacketBase->LocalFile) > 0)\r
+                               else if(strlen(Pos->LocalFile) > 0)\r
                                {\r
                                        Down = YES;\r
-                                       DoLocalMKD(TransPacketBase->LocalFile);\r
+//                                     DoLocalMKD(TransPacketBase->LocalFile);\r
+                                       DoLocalMKD(Pos->LocalFile);\r
                                }\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83f\83B\83\8c\83N\83g\83\8a\8dì\90¬\81i\8fí\82É\83z\83X\83g\91¤\81j */\r
-                       else if(strncmp(TransPacketBase->Cmd, "R-MKD", 5) == 0)\r
+                       /* ディレクトリ作成(常にホスト側) */\r
+//                     else if(strncmp(TransPacketBase->Cmd, "R-MKD", 5) == 0)\r
+                       else if(strncmp(Pos->Cmd, "R-MKD", 5) == 0)\r
                        {\r
-                               DispTransFileInfo(TransPacketBase, MSGJPN079, FALSE, YES);\r
+//                             DispTransFileInfo(TransPacketBase, MSGJPN079, FALSE, YES);\r
+                               DispTransFileInfo(Pos, MSGJPN079, FALSE, YES);\r
 \r
-                               /* \83t\83\8b\83p\83X\82ð\8eg\82í\82È\82¢\82½\82ß\82Ì\8f\88\97\9d */\r
-                               if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == SUCCESS)\r
+                               /* フルパスを使わないための処理 */\r
+//                             if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == FFFTP_SUCCESS)\r
+                               if(MakeNonFullPath(Pos, CurDir, Tmp) == FFFTP_SUCCESS)\r
                                {\r
                                        Up = YES;\r
-                                       CommandProcTrn(NULL, "%s%s", TransPacketBase->Cmd+2, TransPacketBase->RemoteFile);\r
+//                                     CommandProcTrn(NULL, "%s%s", TransPacketBase->Cmd+2, TransPacketBase->RemoteFile);\r
+                                       CommandProcTrn(TrnSkt, NULL, "%s%s", Pos->Cmd+2, Pos->RemoteFile);\r
 \r
                                        if(FolderAttr)\r
-                                               CommandProcTrn(NULL, "%s %03d %s", AskHostChmodCmd(), FolderAttrNum, TransPacketBase->RemoteFile);\r
+//                                             CommandProcTrn(NULL, "%s %03d %s", AskHostChmodCmd(), FolderAttrNum, TransPacketBase->RemoteFile);\r
+                                               CommandProcTrn(TrnSkt, NULL, "%s %03d %s", AskHostChmodCmd(), FolderAttrNum, Pos->RemoteFile);\r
                                }\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83f\83B\83\8c\83N\83g\83\8a\8dí\8f\9c\81i\8fí\82É\83z\83X\83g\91¤\81j */\r
-                       else if(strncmp(TransPacketBase->Cmd, "R-RMD", 5) == 0)\r
+                       /* ディレクトリ削除(常にホスト側) */\r
+//                     else if(strncmp(TransPacketBase->Cmd, "R-RMD", 5) == 0)\r
+                       else if(strncmp(Pos->Cmd, "R-RMD", 5) == 0)\r
                        {\r
-                               DispTransFileInfo(TransPacketBase, MSGJPN080, FALSE, YES);\r
+//                             DispTransFileInfo(TransPacketBase, MSGJPN080, FALSE, YES);\r
+                               DispTransFileInfo(Pos, MSGJPN080, FALSE, YES);\r
 \r
-                               DelNotify = MirrorDelNotify(WIN_REMOTE, DelNotify, TransPacketBase);\r
+//                             DelNotify = MirrorDelNotify(WIN_REMOTE, DelNotify, TransPacketBase);\r
+                               DelNotify = MirrorDelNotify(WIN_REMOTE, DelNotify, Pos);\r
                                if((DelNotify == YES) || (DelNotify == YES_ALL))\r
                                {\r
-                                       /* \83t\83\8b\83p\83X\82ð\8eg\82í\82È\82¢\82½\82ß\82Ì\8f\88\97\9d */\r
-                                       if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == SUCCESS)\r
+                                       /* フルパスを使わないための処理 */\r
+//                                     if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == FFFTP_SUCCESS)\r
+                                       if(MakeNonFullPath(Pos, CurDir, Tmp) == FFFTP_SUCCESS)\r
                                        {\r
                                                Up = YES;\r
-                                               CommandProcTrn(NULL, "%s%s", TransPacketBase->Cmd+2, TransPacketBase->RemoteFile);\r
+//                                             CommandProcTrn(NULL, "%s%s", TransPacketBase->Cmd+2, TransPacketBase->RemoteFile);\r
+                                               CommandProcTrn(TrnSkt, NULL, "%s%s", Pos->Cmd+2, Pos->RemoteFile);\r
                                        }\r
                                }\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83t\83@\83C\83\8b\8dí\8f\9c\81i\8fí\82É\83z\83X\83g\91¤\81j */\r
-                       else if(strncmp(TransPacketBase->Cmd, "R-DELE", 6) == 0)\r
+                       /* ファイル削除(常にホスト側) */\r
+//                     else if(strncmp(TransPacketBase->Cmd, "R-DELE", 6) == 0)\r
+                       else if(strncmp(Pos->Cmd, "R-DELE", 6) == 0)\r
                        {\r
-                               DispTransFileInfo(TransPacketBase, MSGJPN081, FALSE, YES);\r
+                               ReleaseMutex(hListAccMutex);\r
+//                             DispTransFileInfo(TransPacketBase, MSGJPN081, FALSE, YES);\r
+                               DispTransFileInfo(Pos, MSGJPN081, FALSE, YES);\r
 \r
-                               DelNotify = MirrorDelNotify(WIN_REMOTE, DelNotify, TransPacketBase);\r
+//                             DelNotify = MirrorDelNotify(WIN_REMOTE, DelNotify, TransPacketBase);\r
+                               DelNotify = MirrorDelNotify(WIN_REMOTE, DelNotify, Pos);\r
                                if((DelNotify == YES) || (DelNotify == YES_ALL))\r
                                {\r
-                                       /* \83t\83\8b\83p\83X\82ð\8eg\82í\82È\82¢\82½\82ß\82Ì\8f\88\97\9d */\r
-                                       if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == SUCCESS)\r
+                                       /* フルパスを使わないための処理 */\r
+//                                     if(MakeNonFullPath(TransPacketBase, CurDir, Tmp) == FFFTP_SUCCESS)\r
+                                       if(MakeNonFullPath(Pos, CurDir, Tmp) == FFFTP_SUCCESS)\r
                                        {\r
                                                Up = YES;\r
-                                               CommandProcTrn(NULL, "%s%s", TransPacketBase->Cmd+2, TransPacketBase->RemoteFile);\r
+//                                             CommandProcTrn(NULL, "%s%s", TransPacketBase->Cmd+2, TransPacketBase->RemoteFile);\r
+                                               CommandProcTrn(TrnSkt, NULL, "%s%s", Pos->Cmd+2, Pos->RemoteFile);\r
                                        }\r
                                }\r
                        }\r
-                       /* \83f\83B\83\8c\83N\83g\83\8a\8dì\90¬\81i\8fí\82É\83\8d\81[\83J\83\8b\91¤\81j */\r
-                       else if(strncmp(TransPacketBase->Cmd, "L-MKD", 5) == 0)\r
+                       /* ディレクトリ作成(常にローカル側) */\r
+//                     else if(strncmp(TransPacketBase->Cmd, "L-MKD", 5) == 0)\r
+                       else if(strncmp(Pos->Cmd, "L-MKD", 5) == 0)\r
                        {\r
-                               DispTransFileInfo(TransPacketBase, MSGJPN082, FALSE, YES);\r
+//                             DispTransFileInfo(TransPacketBase, MSGJPN082, FALSE, YES);\r
+                               DispTransFileInfo(Pos, MSGJPN082, FALSE, YES);\r
 \r
                                Down = YES;\r
-                               DoLocalMKD(TransPacketBase->LocalFile);\r
+//                             DoLocalMKD(TransPacketBase->LocalFile);\r
+                               DoLocalMKD(Pos->LocalFile);\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83f\83B\83\8c\83N\83g\83\8a\8dí\8f\9c\81i\8fí\82É\83\8d\81[\83J\83\8b\91¤\81j */\r
-                       else if(strncmp(TransPacketBase->Cmd, "L-RMD", 5) == 0)\r
+                       /* ディレクトリ削除(常にローカル側) */\r
+//                     else if(strncmp(TransPacketBase->Cmd, "L-RMD", 5) == 0)\r
+                       else if(strncmp(Pos->Cmd, "L-RMD", 5) == 0)\r
                        {\r
-                               DispTransFileInfo(TransPacketBase, MSGJPN083, FALSE, YES);\r
+//                             DispTransFileInfo(TransPacketBase, MSGJPN083, FALSE, YES);\r
+                               DispTransFileInfo(Pos, MSGJPN083, FALSE, YES);\r
 \r
-                               DelNotify = MirrorDelNotify(WIN_LOCAL, DelNotify, TransPacketBase);\r
+//                             DelNotify = MirrorDelNotify(WIN_LOCAL, DelNotify, TransPacketBase);\r
+                               DelNotify = MirrorDelNotify(WIN_LOCAL, DelNotify, Pos);\r
                                if((DelNotify == YES) || (DelNotify == YES_ALL))\r
                                {\r
                                        Down = YES;\r
-                                       DoLocalRMD(TransPacketBase->LocalFile);\r
+//                                     DoLocalRMD(TransPacketBase->LocalFile);\r
+                                       DoLocalRMD(Pos->LocalFile);\r
                                }\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83t\83@\83C\83\8b\8dí\8f\9c\81i\8fí\82É\83\8d\81[\83J\83\8b\91¤\81j */\r
-                       else if(strncmp(TransPacketBase->Cmd, "L-DELE", 6) == 0)\r
+                       /* ファイル削除(常にローカル側) */\r
+//                     else if(strncmp(TransPacketBase->Cmd, "L-DELE", 6) == 0)\r
+                       else if(strncmp(Pos->Cmd, "L-DELE", 6) == 0)\r
                        {\r
-                               DispTransFileInfo(TransPacketBase, MSGJPN084, FALSE, YES);\r
+//                             DispTransFileInfo(TransPacketBase, MSGJPN084, FALSE, YES);\r
+                               DispTransFileInfo(Pos, MSGJPN084, FALSE, YES);\r
 \r
-                               DelNotify = MirrorDelNotify(WIN_LOCAL, DelNotify, TransPacketBase);\r
+//                             DelNotify = MirrorDelNotify(WIN_LOCAL, DelNotify, TransPacketBase);\r
+                               DelNotify = MirrorDelNotify(WIN_LOCAL, DelNotify, Pos);\r
                                if((DelNotify == YES) || (DelNotify == YES_ALL))\r
                                {\r
                                        Down = YES;\r
-                                       DoLocalDELE(TransPacketBase->LocalFile);\r
+//                                     DoLocalDELE(TransPacketBase->LocalFile);\r
+                                       DoLocalDELE(Pos->LocalFile);\r
                                }\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83J\83\8c\83\93\83g\83f\83B\83\8c\83N\83g\83\8a\82ð\90Ý\92è */\r
-                       else if(strcmp(TransPacketBase->Cmd, "SETCUR") == 0)\r
+                       /* カレントディレクトリを設定 */\r
+//                     else if(strcmp(TransPacketBase->Cmd, "SETCUR") == 0)\r
+                       else if(strcmp(Pos->Cmd, "SETCUR") == 0)\r
                        {\r
                                if(AskShareProh() == YES)\r
                                {\r
-                                       if(strcmp(CurDir, TransPacketBase->RemoteFile) != 0)\r
+//                                     if(strcmp(CurDir, TransPacketBase->RemoteFile) != 0)\r
+                                       if(strcmp(CurDir, Pos->RemoteFile) != 0)\r
                                        {\r
-                                               if(CommandProcTrn(NULL, "CWD %s", TransPacketBase->RemoteFile)/100 != FTP_COMPLETE)\r
+//                                             if(CommandProcTrn(NULL, "CWD %s", TransPacketBase->RemoteFile)/100 != FTP_COMPLETE)\r
+                                               if(CommandProcTrn(TrnSkt, NULL, "CWD %s", Pos->RemoteFile)/100 != FTP_COMPLETE)\r
                                                {\r
                                                        DispCWDerror(hWndTrans);\r
                                                        ClearAll = YES;\r
                                                }\r
                                        }\r
                                }\r
-                               strcpy(CurDir, TransPacketBase->RemoteFile);\r
+//                             strcpy(CurDir, TransPacketBase->RemoteFile);\r
+                               strcpy(CurDir, Pos->RemoteFile);\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \83J\83\8c\83\93\83g\83f\83B\83\8c\83N\83g\83\8a\82ð\96ß\82· */\r
-                       else if(strcmp(TransPacketBase->Cmd, "BACKCUR") == 0)\r
+                       /* カレントディレクトリを戻す */\r
+//                     else if(strcmp(TransPacketBase->Cmd, "BACKCUR") == 0)\r
+                       else if(strcmp(Pos->Cmd, "BACKCUR") == 0)\r
                        {\r
                                if(AskShareProh() == NO)\r
                                {\r
-                                       if(strcmp(CurDir, TransPacketBase->RemoteFile) != 0)\r
-                                               CommandProcTrn(NULL, "CWD %s", TransPacketBase->RemoteFile);\r
-                                       strcpy(CurDir, TransPacketBase->RemoteFile);\r
+//                                     if(strcmp(CurDir, TransPacketBase->RemoteFile) != 0)\r
+//                                             CommandProcTrn(NULL, "CWD %s", TransPacketBase->RemoteFile);\r
+//                                     strcpy(CurDir, TransPacketBase->RemoteFile);\r
+                                       if(strcmp(CurDir, Pos->RemoteFile) != 0)\r
+                                               CommandProcTrn(TrnSkt, NULL, "CWD %s", Pos->RemoteFile);\r
+                                       strcpy(CurDir, Pos->RemoteFile);\r
                                }\r
+                               ReleaseMutex(hListAccMutex);\r
                        }\r
-                       /* \8e©\93®\8fI\97¹\82Ì\82½\82ß\82Ì\92Ê\92m */\r
-                       else if(strcmp(TransPacketBase->Cmd, "GOQUIT") == 0)\r
+                       /* 自動終了のための通知 */\r
+//                     else if(strcmp(TransPacketBase->Cmd, "GOQUIT") == 0)\r
+                       else if(strcmp(Pos->Cmd, "GOQUIT") == 0)\r
                        {\r
+                               ReleaseMutex(hListAccMutex);\r
                                GoExit = YES;\r
                        }\r
+                       else\r
+                               ReleaseMutex(hListAccMutex);\r
 \r
-                       /*===== \82P\82Â\82Ì\8f\88\97\9d\8fI\82í\82è =====*/\r
+                       /*===== 1つの処理終わり =====*/\r
 \r
                        if(ForceAbort == NO)\r
                        {\r
-                               WaitForSingleObject(hListAccMutex, INFINITE);\r
+//                             WaitForSingleObject(hListAccMutex, INFINITE);\r
+                               while(WaitForSingleObject(hListAccMutex, 0) == WAIT_TIMEOUT)\r
+                               {\r
+                                       BackgrndMessageProc();\r
+                                       Sleep(1);\r
+                               }\r
                                if(ClearAll == YES)\r
+//                                     EraseTransFileList();\r
+                               {\r
+                                       for(i = 0; i < MAX_DATA_CONNECTION; i++)\r
+                                               Canceled[i] = YES;\r
                                        EraseTransFileList();\r
+                                       Pos = NULL;\r
+                               }\r
                                else\r
                                {\r
-                                       if((strncmp(TransPacketBase->Cmd, "RETR", 4) == 0) ||\r
-                                          (strncmp(TransPacketBase->Cmd, "STOR", 4) == 0))\r
+//                                     if((strncmp(TransPacketBase->Cmd, "RETR", 4) == 0) ||\r
+//                                        (strncmp(TransPacketBase->Cmd, "STOR", 4) == 0))\r
+                                       if((strncmp(Pos->Cmd, "RETR", 4) == 0) ||\r
+                                          (strncmp(Pos->Cmd, "STOR", 4) == 0))\r
                                        {\r
-                                               TransFiles--;\r
+//                                             TransFiles--;\r
+                                               if(TransFiles > 0)\r
+                                                       TransFiles--;\r
                                                PostMessage(GetMainHwnd(), WM_CHANGE_COND, 0, 0);\r
                                        }\r
-                                       Pos = TransPacketBase;\r
-                                       TransPacketBase = TransPacketBase->Next;\r
-                                       free(Pos);\r
+//                                     Pos = TransPacketBase;\r
+//                                     TransPacketBase = TransPacketBase->Next;\r
+//                                     free(Pos);\r
                                }\r
                                ClearAll = NO;\r
                                ReleaseMutex(hListAccMutex);\r
@@ -828,8 +1054,13 @@ static ULONG WINAPI TransferThread(void *Dummy)
                                        ReleaseMutex(hListAccMutex);\r
                                }\r
                        }\r
+                       if(hWndTrans != NULL)\r
+                               SendMessage(hWndTrans, WM_SET_PACKET, 0, 0);\r
+                       if(Pos != NULL)\r
+                               strcpy(Pos->Cmd, "");\r
                }\r
-               else\r
+//             else\r
+               else if(TransPacketBase == NULL)\r
                {\r
                        DelNotify = NO;\r
 \r
@@ -841,57 +1072,83 @@ static ULONG WINAPI TransferThread(void *Dummy)
                                        DestroyWindow(hWndTrans);\r
                                        hWndTrans = NULL;\r
 \r
-                                       if(GoExit == YES)\r
-                                       {\r
-                                               SoundPlay(SND_TRANS);\r
-\r
-                                               if(AskAutoExit() == NO)\r
-                                               {\r
-                                                       if(Down == YES)\r
-                                                               PostMessage(GetMainHwnd(), WM_REFRESH_LOCAL_FLG, 0, 0);\r
-                                                       if(Up == YES)\r
-                                                               PostMessage(GetMainHwnd(), WM_REFRESH_REMOTE_FLG, 0, 0);\r
-                                               }\r
-                                               Down = NO;\r
-                                               Up = NO;\r
-                                       }\r
+//                                     if(GoExit == YES)\r
+//                                     {\r
+//                                             SoundPlay(SND_TRANS);\r
+//\r
+//                                             if(AskAutoExit() == NO)\r
+//                                             {\r
+//                                                     if(Down == YES)\r
+//                                                             PostMessage(GetMainHwnd(), WM_REFRESH_LOCAL_FLG, 0, 0);\r
+//                                                     if(Up == YES)\r
+//                                                             PostMessage(GetMainHwnd(), WM_REFRESH_REMOTE_FLG, 0, 0);\r
+//                                             }\r
+//                                             Down = NO;\r
+//                                             Up = NO;\r
+//                                     }\r
                                }\r
                        }\r
                        BackgrndMessageProc();\r
+                       Sleep(1);\r
 \r
                        if(GoExit == YES)\r
                        {\r
+                               SoundPlay(SND_TRANS);\r
+                               if(AskAutoExit() == NO)\r
+                               {\r
+                                       if(Down == YES)\r
+                                               PostMessage(GetMainHwnd(), WM_REFRESH_LOCAL_FLG, 0, 0);\r
+                                       if(Up == YES)\r
+                                               PostMessage(GetMainHwnd(), WM_REFRESH_REMOTE_FLG, 0, 0);\r
+                               }\r
+                               Down = NO;\r
+                               Up = NO;\r
                                PostMessage(GetMainHwnd(), WM_COMMAND, MAKEWPARAM(MENU_AUTO_EXIT, 0), 0);\r
                                GoExit = NO;\r
                        }\r
                }\r
+               else\r
+               {\r
+                       ReleaseMutex(hListAccMutex);\r
+                       if(hWndTrans != NULL)\r
+                       {\r
+                               DestroyWindow(hWndTrans);\r
+                               hWndTrans = NULL;\r
+                       }\r
+                       BackgrndMessageProc();\r
+                       Sleep(1);\r
+               }\r
        }\r
+       if(TrnSkt != INVALID_SOCKET)\r
+               DoClose(TrnSkt);\r
        return 0;\r
 }\r
 \r
 \r
-/*----- \83t\83\8b\83p\83X\82ð\8eg\82í\82È\82¢\83t\83@\83C\83\8b\83A\83N\83Z\83X\82Ì\8f\80\94õ ------------------------------\r
+/*----- フルパスを使わないファイルアクセスの準備 ------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83p\83P\83b\83g\r
-*              char *Cur : \83J\83\8c\83\93\83g\83f\83B\83\8c\83N\83g\83\8a\r
-*              char *Tmp : \8dì\8bÆ\97p\83G\83\8a\83A\r
+*              TRANSPACKET *Pkt : 転送パケット\r
+*              char *Cur : カレントディレクトリ\r
+*              char *Tmp : 作業用エリア\r
 *\r
 *      Return Value\r
-*              int \83X\83e\81[\83^\83X(SUCCESS/FAIL)\r
+*              int ステータス(FFFTP_SUCCESS/FFFTP_FAIL)\r
 *\r
 *      Note\r
-*              \83t\83\8b\83p\83X\82ð\8eg\82í\82È\82¢\8e\9e\82Í\81A\r
-*                      \82±\82Ì\83\82\83W\83\85\81[\83\8b\93à\82Å CWD \82ð\8ds\82È\82¢\81A\r
-*                      Pkt->RemoteFile \82É\83t\83@\83C\83\8b\96¼\82Ì\82Ý\8ec\82·\81B\81i\83p\83X\96¼\82Í\8fÁ\82·\81j\r
+*              フルパスを使わない時は、\r
+*                      このモジュール内で CWD を行ない、\r
+*                      Pkt->RemoteFile にファイル名のみ残す。(パス名は消す)\r
 *----------------------------------------------------------------------------*/\r
 \r
+// 同時接続対応\r
 static int MakeNonFullPath(TRANSPACKET *Pkt, char *Cur, char *Tmp)\r
 {\r
        int Sts;\r
 \r
-       Sts = ProcForNonFullpath(Pkt->RemoteFile, Cur, Pkt->hWndTrans, 1);\r
-       if(Sts == FAIL)\r
+//     Sts = ProcForNonFullpath(Pkt->RemoteFile, Cur, Pkt->hWndTrans, 1);\r
+       Sts = ProcForNonFullpath(Pkt->RemoteFile, Cur, Pkt->hWndTrans, (int)Pkt->ctrl_skt + 1);\r
+       if(Sts == FFFTP_FAIL)\r
                ClearAll = YES;\r
 \r
        return(Sts);\r
@@ -900,19 +1157,19 @@ static int MakeNonFullPath(TRANSPACKET *Pkt, char *Cur, char *Tmp)
 \r
 \r
 \r
-/*----- \83_\83E\83\93\83\8d\81[\83h\82ð\8ds\82È\82¤ --------------------------------------------------\r
+/*----- ダウンロードを行なう --------------------------------------------------\r
 *\r
 *      Parameter\r
-*              SOCKET cSkt : \83R\83\93\83g\83\8d\81[\83\8b\83\\83P\83b\83g\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              int DirList : \83f\83B\83\8c\83N\83g\83\8a\83\8a\83X\83g\82Ì\83_\83E\83\93\83\8d\81[\83h(YES/NO)\r
+*              SOCKET cSkt : コントロールソケット\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              int DirList : ディレクトリリストのダウンロード(YES/NO)\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *\r
 *      Note\r
-*              \82±\82Ì\83\82\83W\83\85\81[\83\8b\82Í\81A\83t\83@\83C\83\8b\88ê\97\97\82Ì\8eæ\93¾\82È\82Ç\82ð\8ds\82È\82¤\8dÛ\82É\83\81\83C\83\93\82Ì\83X\83\8c\83b\83h\r
-*              \82©\82ç\82à\8cÄ\82Î\82ê\82é\81B\83\81\83C\83\93\82Ì\83X\83\8c\83b\83h\82©\82ç\8cÄ\82Î\82ê\82é\8e\9e\82Í Pkt->hWndTrans == NULL\81B\r
+*              このモジュールは、ファイル一覧の取得などを行なう際にメインのスレッド\r
+*              からも呼ばれる。メインのスレッドから呼ばれる時は Pkt->hWndTrans == NULL。\r
 *----------------------------------------------------------------------------*/\r
 \r
 int DoDownLoad(SOCKET cSkt, TRANSPACKET *Pkt, int DirList, int *CancelCheckWork)\r
@@ -937,7 +1194,9 @@ int DoDownLoad(SOCKET cSkt, TRANSPACKET *Pkt, int DirList, int *CancelCheckWork)
                {\r
                        if(Pkt->hWndTrans != NULL)\r
                        {\r
-                               AllTransSizeNow = 0;\r
+                               // 同時接続対応\r
+//                             AllTransSizeNow = 0;\r
+                               AllTransSizeNow[Pkt->ThreadCount] = 0;\r
 \r
                                if(DirList == NO)\r
                                        DispTransFileInfo(Pkt, MSGJPN086, TRUE, YES);\r
@@ -968,13 +1227,13 @@ int DoDownLoad(SOCKET cSkt, TRANSPACKET *Pkt, int DirList, int *CancelCheckWork)
 }\r
 \r
 \r
-/*----- \92Ê\8fí\83\82\81[\83h\82Å\83t\83@\83C\83\8b\82ð\83_\83E\83\93\83\8d\81[\83h ------------------------------------\r
+/*----- 通常モードでファイルをダウンロード ------------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int DownLoadNonPassive(TRANSPACKET *Pkt, int *CancelCheckWork)\r
@@ -996,7 +1255,7 @@ static int DownLoadNonPassive(TRANSPACKET *Pkt, int *CancelCheckWork)
                        iRetCode = command(Pkt->ctrl_skt, Reply, CancelCheckWork, "%s", Buf);\r
                        if(iRetCode/100 == FTP_PRELIM)\r
                        {\r
-                               if(SocksGet2ndBindReply(listen_socket, &data_socket) == FAIL)\r
+                               if(SocksGet2ndBindReply(listen_socket, &data_socket) == FFFTP_FAIL)\r
                                {\r
                                        iLength = sizeof(saSockAddr1);\r
                                        data_socket = do_accept(listen_socket, (struct sockaddr *)&saSockAddr1, (int *)&iLength);\r
@@ -1017,7 +1276,19 @@ static int DownLoadNonPassive(TRANSPACKET *Pkt, int *CancelCheckWork)
 \r
                                if(data_socket != INVALID_SOCKET)\r
                                {\r
-                                       iRetCode = DownLoadFile(Pkt, data_socket, CreateMode, CancelCheckWork);\r
+                                       // 一部TYPE、STOR(RETR)、PORT(PASV)を並列に処理できないホストがあるため\r
+                                       ReleaseMutex(hListAccMutex);\r
+                                       // FTPS対応\r
+//                                     iRetCode = DownLoadFile(Pkt, data_socket, CreateMode, CancelCheckWork);\r
+                                       if(AskCryptMode() == CRYPT_FTPES || AskCryptMode() == CRYPT_FTPIS)\r
+                                       {\r
+                                               if(AttachSSL(data_socket))\r
+                                                       iRetCode = DownLoadFile(Pkt, data_socket, CreateMode, CancelCheckWork);\r
+                                               else\r
+                                                       iRetCode = FTP_ERROR;\r
+                                       }\r
+                                       else\r
+                                               iRetCode = DownLoadFile(Pkt, data_socket, CreateMode, CancelCheckWork);\r
 //                                     data_socket = DoClose(data_socket);\r
                                }\r
                        }\r
@@ -1043,13 +1314,13 @@ static int DownLoadNonPassive(TRANSPACKET *Pkt, int *CancelCheckWork)
 }\r
 \r
 \r
-/*----- Passive\83\82\81[\83h\82Å\83t\83@\83C\83\8b\82ð\83_\83E\83\93\83\8d\81[\83h ---------------------------------\r
+/*----- Passiveモードでファイルをダウンロード ---------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int DownLoadPassive(TRANSPACKET *Pkt, int *CancelCheckWork)\r
@@ -1066,10 +1337,12 @@ static int DownLoadPassive(TRANSPACKET *Pkt, int *CancelCheckWork)
        iRetCode = command(Pkt->ctrl_skt, Buf, CancelCheckWork, "PASV");\r
        if(iRetCode/100 == FTP_COMPLETE)\r
        {\r
-               if(GetAdrsAndPort(Buf, Adrs, &Port, 19) == SUCCESS)\r
+               if(GetAdrsAndPort(Buf, Adrs, &Port, 19) == FFFTP_SUCCESS)\r
                {\r
                        if((data_socket = connectsock(Adrs, Port, MSGJPN091, CancelCheckWork)) != INVALID_SOCKET)\r
                        {\r
+                               // 変数が未初期化のバグ修正\r
+                               Flg = 1;\r
                                if(setsockopt(data_socket, IPPROTO_TCP, TCP_NODELAY, (LPSTR)&Flg, sizeof(Flg)) == SOCKET_ERROR)\r
                                        ReportWSError("setsockopt", WSAGetLastError());\r
 \r
@@ -1079,7 +1352,19 @@ static int DownLoadPassive(TRANSPACKET *Pkt, int *CancelCheckWork)
                                        iRetCode = command(Pkt->ctrl_skt, Reply, CancelCheckWork, "%s", Buf);\r
                                        if(iRetCode/100 == FTP_PRELIM)\r
                                        {\r
-                                               iRetCode = DownLoadFile(Pkt, data_socket, CreateMode, CancelCheckWork);\r
+                                               // 一部TYPE、STOR(RETR)、PORT(PASV)を並列に処理できないホストがあるため\r
+                                               ReleaseMutex(hListAccMutex);\r
+                                               // FTPS対応\r
+//                                             iRetCode = DownLoadFile(Pkt, data_socket, CreateMode, CancelCheckWork);\r
+                                               if(AskCryptMode() == CRYPT_FTPES || AskCryptMode() == CRYPT_FTPIS)\r
+                                               {\r
+                                                       if(AttachSSL(data_socket))\r
+                                                               iRetCode = DownLoadFile(Pkt, data_socket, CreateMode, CancelCheckWork);\r
+                                                       else\r
+                                                               iRetCode = FTP_ERROR;\r
+                                               }\r
+                                               else\r
+                                                       iRetCode = DownLoadFile(Pkt, data_socket, CreateMode, CancelCheckWork);\r
 //                                             data_socket = DoClose(data_socket);\r
                                        }\r
                                        else\r
@@ -1112,20 +1397,20 @@ static int DownLoadPassive(TRANSPACKET *Pkt, int *CancelCheckWork)
 }\r
 \r
 \r
-/*----- \83_\83E\83\93\83\8d\81[\83h\82Ì\8eÀ\8ds ----------------------------------------------------\r
+/*----- ダウンロードの実行 ----------------------------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              SOCKET dSkt : \83f\81[\83^\83\\83P\83b\83g\r
-*              int CreateMode : \83t\83@\83C\83\8b\8dì\90¬\83\82\81[\83h (CREATE_ALWAYS/OPEN_ALWAYS)\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              SOCKET dSkt : データソケット\r
+*              int CreateMode : ファイル作成モード (CREATE_ALWAYS/OPEN_ALWAYS)\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *\r
 *      Note\r
-*              \93]\91\97\82Ì\8co\89ß\95\\8e¦\82Í\r
-*                      \83_\83C\83A\83\8d\83O\82ð\8fo\82·(Pkt->hWndTrans!=NULL)\8fê\8d\87\81A\83C\83\93\83^\81[\83o\83\8b\83^\83C\83}\82Å\8co\89ß\82ð\95\\8e¦\82·\82é\r
-*                      \83_\83C\83A\83\8d\83O\82ð\8fo\82³\82È\82¢\8fê\8d\87\81A\82±\82Ì\83\8b\81[\83`\83\93\82©\82çDispDownloadSize()\82ð\8cÄ\82Ô\r
+*              転送の経過表示は\r
+*                      ダイアログを出す(Pkt->hWndTrans!=NULL)場合、インターバルタイマで経過を表示する\r
+*                      ダイアログを出さない場合、このルーチンからDispDownloadSize()を呼ぶ\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *CancelCheckWork)\r
@@ -1155,8 +1440,8 @@ static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *Canc
 /* End */\r
 #endif\r
 \r
-#ifdef DISABLE_NETWORK_BUFFERS\r
-       // \94O\82Ì\82½\82ß\8eó\90M\83o\83b\83t\83@\82ð\96³\8cø\82É\82·\82é\81B\r
+       // 念のため受信バッファを無効にする\r
+#ifdef DISABLE_TRANSFER_NETWORK_BUFFERS\r
        int buf_size = 0;\r
        setsockopt(dSkt, SOL_SOCKET, SO_RCVBUF, (char *)&buf_size, sizeof(buf_size));\r
 #endif\r
@@ -1169,28 +1454,37 @@ static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *Canc
 \r
        dwFileAttributes = GetFileAttributes(Pkt->LocalFile);\r
        if (dwFileAttributes != INVALID_FILE_ATTRIBUTES && (dwFileAttributes & FILE_ATTRIBUTE_READONLY)) {\r
-               // \93Ç\82Ý\8eæ\82è\90ê\97p\r
+               // 読み取り専用\r
                if (MessageBox(GetMainHwnd(), MSGJPN296, MSGJPN086, MB_YESNO) == IDYES) {\r
-                       // \91®\90«\82ð\89ð\8f\9c\r
+                       // 属性を解除\r
                        SetFileAttributes(Pkt->LocalFile, dwFileAttributes ^ FILE_ATTRIBUTE_READONLY);\r
                }\r
        }\r
 \r
        if((iFileHandle = CreateFile(Pkt->LocalFile, GENERIC_READ | GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE, &Sec, CreateMode, FILE_ATTRIBUTE_NORMAL, NULL)) != INVALID_HANDLE_VALUE)\r
        {\r
+               // UTF-8対応\r
+               char Buf3[(BUFSIZE + 3) * 4];\r
+               CODECONVINFO cInfo2;\r
+               int ProcessedBOM = NO;\r
                if(CreateMode == OPEN_ALWAYS)\r
                        SetFilePointer(iFileHandle, 0, 0, FILE_END);\r
 \r
                if(Pkt->hWndTrans != NULL)\r
                {\r
-                       TimeStart = time(NULL);\r
+                       // 同時接続対応\r
+//                     TimeStart = time(NULL);\r
+                       TimeStart[Pkt->ThreadCount] = time(NULL);\r
                        SetTimer(Pkt->hWndTrans, TIMER_DISPLAY, DISPLAY_TIMING, NULL);\r
                }\r
 \r
                InitCodeConvInfo(&cInfo);\r
                cInfo.KanaCnv = Pkt->KanaCnv;\r
 \r
-               /*===== \83t\83@\83C\83\8b\82ð\8eó\90M\82·\82é\83\8b\81[\83v =====*/\r
+               InitCodeConvInfo(&cInfo2);\r
+               cInfo2.KanaCnv = Pkt->KanaCnv;\r
+\r
+               /*===== ファイルを受信するループ =====*/\r
                while((Pkt->Abort == ABORT_NONE) && (ForceAbort == NO))\r
                {\r
 //                     FD_ZERO(&ReadFds);\r
@@ -1237,7 +1531,7 @@ static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *Canc
                                break;\r
                        }\r
 \r
-                       /* \8a¿\8e\9a\83R\81[\83h\95Ï\8a· */\r
+                       /* 漢字コード変換 */\r
                        if(Pkt->KanjiCode != KANJI_NOCNV)\r
                        {\r
                                cInfo.Str = Buf;\r
@@ -1246,11 +1540,201 @@ static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *Canc
                                cInfo.BufSize = BUFSIZE+3;\r
                                do\r
                                {\r
-                                       if(Pkt->KanjiCode == KANJI_JIS)\r
-                                               Continue = ConvJIStoSJIS(&cInfo);\r
-                                       else\r
-                                               Continue = ConvEUCtoSJIS(&cInfo);\r
-                                       if(WriteFile(iFileHandle, Buf2, cInfo.OutLen, &Writed, NULL) == FALSE)\r
+                                       // ここで全てUTF-8へ変換する\r
+                                       // TODO: SJIS以外も直接UTF-8へ変換\r
+//                                     if(Pkt->KanjiCode == KANJI_JIS)\r
+//                                             Continue = ConvJIStoSJIS(&cInfo);\r
+//                                     else\r
+//                                             Continue = ConvEUCtoSJIS(&cInfo);\r
+                                       char Buf3[(BUFSIZE + 3) * 4];\r
+                                       CODECONVINFO cInfo2;\r
+                                       switch(Pkt->KanjiCode)\r
+                                       {\r
+                                       case KANJI_SJIS:\r
+                                               switch(Pkt->KanjiCodeDesired)\r
+                                               {\r
+                                               case KANJI_SJIS:\r
+//                                                     memcpy(Buf3, cInfo.Str, cInfo.StrLen);\r
+//                                                     cInfo2.OutLen = cInfo.StrLen;\r
+//                                                     Continue = NO;\r
+                                                       // カナ変換のため\r
+                                                       Continue = ConvSJIStoJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvJIStoSJIS(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_JIS:\r
+                                                       Continue = ConvSJIStoJIS(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_EUC:\r
+                                                       Continue = ConvSJIStoEUC(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_UTF8N:\r
+                                                       if(ProcessedBOM == NO)\r
+                                                       {\r
+                                                               memcpy(Buf3, "\xEF\xBB\xBF", 3);\r
+                                                               cInfo2.OutLen = 3;\r
+                                                               Continue = YES;\r
+                                                               ProcessedBOM = YES;\r
+                                                               break;\r
+                                                       }\r
+                                                       Continue = ConvSJIStoUTF8N(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               }\r
+                                               break;\r
+                                       case KANJI_JIS:\r
+                                               switch(Pkt->KanjiCodeDesired)\r
+                                               {\r
+                                               case KANJI_SJIS:\r
+                                                       Continue = ConvJIStoSJIS(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_JIS:\r
+//                                                     memcpy(Buf3, cInfo.Str, cInfo.StrLen);\r
+//                                                     cInfo2.OutLen = cInfo.StrLen;\r
+//                                                     Continue = NO;\r
+                                                       // カナ変換のため\r
+                                                       Continue = ConvJIStoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoJIS(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_EUC:\r
+                                                       Continue = ConvJIStoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoEUC(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_UTF8N:\r
+                                                       if(ProcessedBOM == NO)\r
+                                                       {\r
+                                                               memcpy(Buf3, "\xEF\xBB\xBF", 3);\r
+                                                               cInfo2.OutLen = 3;\r
+                                                               Continue = YES;\r
+                                                               ProcessedBOM = YES;\r
+                                                               break;\r
+                                                       }\r
+                                                       Continue = ConvJIStoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoUTF8N(&cInfo2);\r
+                                                       break;\r
+                                               }\r
+                                               break;\r
+                                       case KANJI_EUC:\r
+                                               switch(Pkt->KanjiCodeDesired)\r
+                                               {\r
+                                               case KANJI_SJIS:\r
+                                                       Continue = ConvEUCtoSJIS(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_JIS:\r
+                                                       Continue = ConvEUCtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoJIS(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_EUC:\r
+//                                                     memcpy(Buf3, cInfo.Str, cInfo.StrLen);\r
+//                                                     cInfo2.OutLen = cInfo.StrLen;\r
+//                                                     Continue = NO;\r
+                                                       // カナ変換のため\r
+                                                       Continue = ConvEUCtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoEUC(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_UTF8N:\r
+                                                       if(ProcessedBOM == NO)\r
+                                                       {\r
+                                                               memcpy(Buf3, "\xEF\xBB\xBF", 3);\r
+                                                               cInfo2.OutLen = 3;\r
+                                                               Continue = YES;\r
+                                                               ProcessedBOM = YES;\r
+                                                               break;\r
+                                                       }\r
+                                                       Continue = ConvEUCtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoUTF8N(&cInfo2);\r
+                                                       break;\r
+                                               }\r
+                                               break;\r
+                                       case KANJI_UTF8N:\r
+                                               if(ProcessedBOM == NO)\r
+                                               {\r
+                                                       if(memcmp(Buf, "\xEF\xBB\xBF", 3) == 0)\r
+                                                       {\r
+                                                               cInfo.Str += 3;\r
+                                                               cInfo.StrLen -= 3;\r
+                                                       }\r
+                                                       cInfo2.OutLen = 0;\r
+                                                       switch(Pkt->KanjiCodeDesired)\r
+                                                       {\r
+                                                       case KANJI_UTF8N:\r
+                                                               memcpy(Buf3, "\xEF\xBB\xBF", 3);\r
+                                                               cInfo2.OutLen = 3;\r
+                                                               break;\r
+                                                       }\r
+                                                       Continue = YES;\r
+                                                       ProcessedBOM = YES;\r
+                                                       break;\r
+                                               }\r
+                                               switch(Pkt->KanjiCodeDesired)\r
+                                               {\r
+                                               case KANJI_SJIS:\r
+                                                       Continue = ConvUTF8NtoSJIS(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_JIS:\r
+                                                       Continue = ConvUTF8NtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoJIS(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_EUC:\r
+                                                       Continue = ConvUTF8NtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoEUC(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_UTF8N:\r
+                                                       memcpy(Buf3, cInfo.Str, cInfo.StrLen);\r
+                                                       cInfo2.OutLen = cInfo.StrLen;\r
+                                                       Continue = NO;\r
+                                                       break;\r
+                                               }\r
+                                               break;\r
+                                       }\r
+//                                     if(WriteFile(iFileHandle, Buf2, cInfo.OutLen, &Writed, NULL) == FALSE)\r
+                                       if(WriteFile(iFileHandle, Buf3, cInfo2.OutLen, &Writed, NULL) == FALSE)\r
                                                Pkt->Abort = ABORT_DISKFULL;\r
                                }\r
                                while((Continue == YES) && (Pkt->Abort == ABORT_NONE));\r
@@ -1263,10 +1747,12 @@ static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *Canc
 \r
                        Pkt->ExistSize += iNumBytes;\r
                        if(Pkt->hWndTrans != NULL)\r
-                               AllTransSizeNow += iNumBytes;\r
+                               // 同時接続対応\r
+//                             AllTransSizeNow += iNumBytes;\r
+                               AllTransSizeNow[Pkt->ThreadCount] += iNumBytes;\r
                        else\r
                        {\r
-                               /* \93]\91\97\83_\83C\83A\83\8d\83O\82ð\8fo\82³\82È\82¢\8e\9e\82Ì\8co\89ß\95\\8e¦ */\r
+                               /* 転送ダイアログを出さない時の経過表示 */\r
                                DispDownloadSize(Pkt->ExistSize);\r
                        }\r
 \r
@@ -1274,30 +1760,155 @@ static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *Canc
                                ForceAbort = YES;\r
                }\r
 \r
-               /* \8f\91\82«\8ec\82µ\82½\83f\81[\83^\82ð\8f\91\82«\8d\9e\82Þ */\r
+               /* 書き残したデータを書き込む */\r
                if(Pkt->KanjiCode != KANJI_NOCNV)\r
                {\r
                        cInfo.Buf = Buf2;\r
                        cInfo.BufSize = BUFSIZE+3;\r
                        FlushRestData(&cInfo);\r
-                       if(WriteFile(iFileHandle, Buf2, cInfo.OutLen, &Writed, NULL) == FALSE)\r
+                       switch(Pkt->KanjiCode)\r
+                       {\r
+                       case KANJI_SJIS:\r
+                               switch(Pkt->KanjiCodeDesired)\r
+                               {\r
+                               case KANJI_SJIS:\r
+                                       // カナ変換のため\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvJIStoSJIS(&cInfo2);\r
+                                       break;\r
+                               case KANJI_JIS:\r
+                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                       break;\r
+                               case KANJI_EUC:\r
+                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                       break;\r
+                               case KANJI_UTF8N:\r
+                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                       break;\r
+                               }\r
+                               break;\r
+                       case KANJI_JIS:\r
+                               switch(Pkt->KanjiCodeDesired)\r
+                               {\r
+                               case KANJI_SJIS:\r
+                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                       break;\r
+                               case KANJI_JIS:\r
+                                       // カナ変換のため\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvSJIStoJIS(&cInfo2);\r
+                                       break;\r
+                               case KANJI_EUC:\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvSJIStoEUC(&cInfo2);\r
+                                       break;\r
+                               case KANJI_UTF8N:\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvSJIStoUTF8N(&cInfo2);\r
+                                       break;\r
+                               }\r
+                               break;\r
+                       case KANJI_EUC:\r
+                               switch(Pkt->KanjiCodeDesired)\r
+                               {\r
+                               case KANJI_SJIS:\r
+                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                       break;\r
+                               case KANJI_JIS:\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvSJIStoJIS(&cInfo2);\r
+                                       break;\r
+                               case KANJI_EUC:\r
+                                       // カナ変換のため\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvSJIStoEUC(&cInfo2);\r
+                                       break;\r
+                               case KANJI_UTF8N:\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvSJIStoUTF8N(&cInfo2);\r
+                                       break;\r
+                               }\r
+                               break;\r
+                       case KANJI_UTF8N:\r
+                               switch(Pkt->KanjiCodeDesired)\r
+                               {\r
+                               case KANJI_SJIS:\r
+                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                       break;\r
+                               case KANJI_JIS:\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvSJIStoJIS(&cInfo2);\r
+                                       break;\r
+                               case KANJI_EUC:\r
+                                       cInfo2.Str = cInfo.Buf;\r
+                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                       cInfo2.Buf = Buf3;\r
+                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                       ConvSJIStoEUC(&cInfo2);\r
+                                       break;\r
+                               case KANJI_UTF8N:\r
+                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                       break;\r
+                               }\r
+                               break;\r
+                       }\r
+//                     if(WriteFile(iFileHandle, Buf2, cInfo.OutLen, &Writed, NULL) == FALSE)\r
+                       if(WriteFile(iFileHandle, Buf3, cInfo2.OutLen, &Writed, NULL) == FALSE)\r
+                               Pkt->Abort = ABORT_DISKFULL;\r
+                       cInfo2.Buf = Buf3;\r
+                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                       FlushRestData(&cInfo2);\r
+                       if(WriteFile(iFileHandle, Buf3, cInfo2.OutLen, &Writed, NULL) == FALSE)\r
                                Pkt->Abort = ABORT_DISKFULL;\r
                }\r
 \r
-               /* \83O\83\89\83t\95\\8e¦\82ð\8dX\90V */\r
+               /* グラフ表示を更新 */\r
                if(Pkt->hWndTrans != NULL)\r
                {\r
                        KillTimer(Pkt->hWndTrans, TIMER_DISPLAY);\r
                        DispTransferStatus(Pkt->hWndTrans, YES, Pkt);\r
-                       TimeStart = time(NULL) - TimeStart + 1;\r
+                       // 同時接続対応\r
+//                     TimeStart = time(NULL) - TimeStart + 1;\r
+                       TimeStart[Pkt->ThreadCount] = time(NULL) - TimeStart[Pkt->ThreadCount] + 1;\r
                }\r
                else\r
                {\r
-                       /* \93]\91\97\83_\83C\83A\83\8d\83O\82ð\8fo\82³\82È\82¢\8e\9e\82Ì\8co\89ß\95\\8e¦\82ð\8fÁ\82· */\r
+                       /* 転送ダイアログを出さない時の経過表示を消す */\r
                        DispDownloadSize(-1);\r
                }\r
 \r
-               /* \83t\83@\83C\83\8b\82Ì\83^\83C\83\80\83X\83^\83\93\83v\82ð\8d\87\82í\82¹\82é */\r
+               /* ファイルのタイムスタンプを合わせる */\r
                if((SaveTimeStamp == YES) &&\r
                   ((Pkt->Time.dwLowDateTime != 0) || (Pkt->Time.dwHighDateTime != 0)))\r
                {\r
@@ -1324,10 +1935,10 @@ static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *Canc
 \r
        if(ForceAbort == NO)\r
        {\r
-               /* Abort\82ð\83z\83X\83g\82É\93`\82¦\82é */\r
+               /* Abortをホストに伝える */\r
                if(Pkt->Abort != ABORT_NONE && iFileHandle != INVALID_HANDLE_VALUE)\r
                {\r
-                       SendData(Pkt->ctrl_skt, "\xFF\xF4\xFF", 3, MSG_OOB, CancelCheckWork);   /* MSG_OOB\82É\92\8d\88Ó */\r
+                       SendData(Pkt->ctrl_skt, "\xFF\xF4\xFF", 3, MSG_OOB, CancelCheckWork);   /* MSG_OOBに注意 */\r
                        SendData(Pkt->ctrl_skt, "\xF2", 1, 0, CancelCheckWork);\r
                        command(Pkt->ctrl_skt, NULL, CancelCheckWork, "ABOR");\r
                }\r
@@ -1352,14 +1963,14 @@ static int DownLoadFile(TRANSPACKET *Pkt, SOCKET dSkt, int CreateMode, int *Canc
 }\r
 \r
 \r
-/*----- \83_\83E\83\93\83\8d\81[\83h\8fI\97¹\81^\92\86\8e~\8e\9e\82Ì\83\81\83b\83Z\81[\83W\82ð\95\\8e¦ ----------------------------\r
+/*----- ダウンロード終了/中止時のメッセージを表示 ----------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              int iRetCode : \89\9e\93\9a\83R\81[\83h\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              int iRetCode : 応答コード\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 static void DispDownloadFinishMsg(TRANSPACKET *Pkt, int iRetCode)\r
@@ -1373,8 +1984,8 @@ static void DispDownloadFinishMsg(TRANSPACKET *Pkt, int iRetCode)
                        strcpy(Fname, Pkt->RemoteFile);\r
 \r
 #if defined(HAVE_OPENVMS)\r
-                       /* OpenVMS\82Ì\8fê\8d\87\81A\8bó\83f\83B\83\8c\83N\83g\83\8a\82Ö\88Ú\93®\82·\82é\82Æ550 File not found\82É\82È\82Á\82Ä\r
-                        * \83G\83\89\81[\83_\83C\83A\83\8d\83O\82â\83G\83\89\81[\83\81\83b\83Z\81[\83W\82ª\8fo\82é\82Ì\82Å\89½\82à\82µ\82È\82¢ */\r
+                       /* OpenVMSの場合、空ディレクトリへ移動すると550 File not foundになって\r
+                        * エラーダイアログやエラーメッセージが出るので何もしない */\r
                        if (AskHostType() == HTYPE_VMS)\r
                                return;\r
 #endif\r
@@ -1384,14 +1995,19 @@ static void DispDownloadFinishMsg(TRANSPACKET *Pkt, int iRetCode)
                                SetTaskMsg(MSGJPN097);\r
                                strcpy(Fname, MSGJPN098);\r
                        }\r
-                       else if((Pkt->hWndTrans != NULL) && (TimeStart != 0))\r
-                               SetTaskMsg(MSGJPN099, TimeStart, Pkt->ExistSize/TimeStart);\r
+                       // 同時接続対応\r
+//                     else if((Pkt->hWndTrans != NULL) && (TimeStart != 0))\r
+//                             SetTaskMsg(MSGJPN099, TimeStart, Pkt->ExistSize/TimeStart);\r
+                       else if((Pkt->hWndTrans != NULL) && (TimeStart[Pkt->ThreadCount] != 0))\r
+                               SetTaskMsg(MSGJPN099, TimeStart[Pkt->ThreadCount], Pkt->ExistSize/TimeStart[Pkt->ThreadCount]);\r
                        else\r
                                SetTaskMsg(MSGJPN100);\r
 \r
                        if(Pkt->Abort != ABORT_USER)\r
                        {\r
-                               if(DispUpDownErrDialog(downerr_dlg, Pkt->hWndTrans, Fname) == NO)\r
+                               // 全て中止を選択後にダイアログが表示されるバグ対策\r
+//                             if(DispUpDownErrDialog(downerr_dlg, Pkt->hWndTrans, Fname) == NO)\r
+                               if(Canceled[Pkt->ThreadCount] == NO && ClearAll == NO && DispUpDownErrDialog(downerr_dlg, Pkt->hWndTrans, Fname) == NO)\r
                                        ClearAll = YES;\r
                        }\r
                }\r
@@ -1399,8 +2015,11 @@ static void DispDownloadFinishMsg(TRANSPACKET *Pkt, int iRetCode)
                {\r
                        if((strncmp(Pkt->Cmd, "NLST", 4) == 0) || (strncmp(Pkt->Cmd, "LIST", 4) == 0))\r
                                SetTaskMsg(MSGJPN101, Pkt->ExistSize);\r
-                       else if((Pkt->hWndTrans != NULL) && (TimeStart != 0))\r
-                               SetTaskMsg(MSGJPN102, TimeStart, Pkt->ExistSize/TimeStart);\r
+                       // 同時接続対応\r
+//                     else if((Pkt->hWndTrans != NULL) && (TimeStart != 0))\r
+//                             SetTaskMsg(MSGJPN102, TimeStart, Pkt->ExistSize/TimeStart);\r
+                       else if((Pkt->hWndTrans != NULL) && (TimeStart[Pkt->ThreadCount] != 0))\r
+                               SetTaskMsg(MSGJPN102, TimeStart[Pkt->ThreadCount], Pkt->ExistSize/TimeStart[Pkt->ThreadCount]);\r
                        else\r
                                SetTaskMsg(MSGJPN103, Pkt->ExistSize);\r
                }\r
@@ -1409,15 +2028,15 @@ static void DispDownloadFinishMsg(TRANSPACKET *Pkt, int iRetCode)
 }\r
 \r
 \r
-/*----- \83_\83E\83\93\83\8d\81[\83h\81^\83A\83b\83v\83\8d\81[\83h\83G\83\89\81[\82Ì\83_\83C\83A\83\8d\83O\82ð\95\\8e¦ --------------------\r
+/*----- ダウンロード/アップロードエラーのダイアログを表示 --------------------\r
 *\r
 *      Parameter\r
-*              int RedID : \83_\83C\83A\83\8d\83O\83{\83b\83N\83X\82Ì\83\8a\83\\81[\83XID\r
-*              HWND hWnd : \8f\91\82«\8d\9e\82Ý\92\86\83_\83C\83A\83\8d\83O\82Ì\83E\83C\83\93\83h\83E\r
-*              char *Fname : \83t\83@\83C\83\8b\96¼\r
+*              int RedID : ダイアログボックスのリソースID\r
+*              HWND hWnd : 書き込み中ダイアログのウインドウ\r
+*              char *Fname : ファイル名\r
 *\r
 *      Return Value\r
-*              int \83X\83e\81[\83^\83X (YES=\92\86\8e~/NO=\91S\82Ä\92\86\8e~)\r
+*              int ステータス (YES=中止/NO=全て中止)\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int DispUpDownErrDialog(int ResID, HWND hWnd, char *Fname)\r
@@ -1430,13 +2049,13 @@ static int DispUpDownErrDialog(int ResID, HWND hWnd, char *Fname)
 }\r
 \r
 \r
-/*----- \83_\83E\83\93\83\8d\81[\83h\83G\83\89\81[\81^\83A\83b\83v\83\8d\81[\83h\83G\83\89\81[\83_\83C\83A\83\8d\83O\82Ì\83R\81[\83\8b\83o\83b\83N --------\r
+/*----- ダウンロードエラー/アップロードエラーダイアログのコールバック --------\r
 *\r
 *      Parameter\r
-*              HWND hDlg : \83E\83C\83\93\83h\83E\83n\83\93\83h\83\8b\r
-*              UINT message : \83\81\83b\83Z\81[\83W\94Ô\8d\86\r
-*              WPARAM wParam : \83\81\83b\83Z\81[\83W\82Ì WPARAM \88ø\90\94\r
-*              LPARAM lParam : \83\81\83b\83Z\81[\83W\82Ì LPARAM \88ø\90\94\r
+*              HWND hDlg : ウインドウハンドル\r
+*              UINT message : メッセージ番号\r
+*              WPARAM wParam : メッセージの WPARAM 引数\r
+*              LPARAM lParam : メッセージの LPARAM 引数\r
 *\r
 *      Return Value\r
 *              BOOL TRUE/FALSE\r
@@ -1468,19 +2087,19 @@ static BOOL CALLBACK UpDownErrorDialogProc(HWND hDlg, UINT message, WPARAM wPara
 }\r
 \r
 \r
-/*----- \83_\83E\83\93\83\8d\81[\83h\82Ì\83\8a\83W\83\85\81[\83\80\82Ì\8f\80\94õ\82ð\8ds\82¤ ----------------------------------\r
+/*----- ダウンロードのリジュームの準備を行う ----------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              iont ProcMode : \8f\88\97\9d\83\82\81[\83h(EXIST_xxx)\r
-*              LONGLONG Size : \83\8d\81[\83h\8dÏ\82Ý\82Ì\83t\83@\83C\83\8b\82Ì\83T\83C\83Y\r
-*              int *Mode : \83t\83@\83C\83\8b\8dì\90¬\83\82\81[\83h (CREATE_xxxx)\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              iont ProcMode : 処理モード(EXIST_xxx)\r
+*              LONGLONG Size : ロード済みのファイルのサイズ\r
+*              int *Mode : ファイル作成モード (CREATE_xxxx)\r
 *\r
 *      Return Value\r
-*              int \93]\91\97\82ð\8ds\82¤\82©\82Ç\82¤\82©(YES/NO=\82±\82Ì\83t\83@\83C\83\8b\82ð\92\86\8e~/NO_ALL=\91S\82Ä\92\86\8e~)\r
+*              int 転送を行うかどうか(YES/NO=このファイルを中止/NO_ALL=全て中止)\r
 *\r
 *      Note\r
-*              Pkt->ExistSize\82Ì\83Z\83b\83g\82ð\8ds\82È\82¤\r
+*              Pkt->ExistSizeのセットを行なう\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int SetDownloadResume(TRANSPACKET *Pkt, int ProcMode, LONGLONG Size, int *Mode, int *CancelCheckWork)\r
@@ -1500,7 +2119,7 @@ static int SetDownloadResume(TRANSPACKET *Pkt, int ProcMode, LONGLONG Size, int
                iRetCode = command(Pkt->ctrl_skt, Reply, CancelCheckWork, "REST %s", MakeNumString(Size, Tmp, FALSE));\r
                if(iRetCode/100 < FTP_RETRY)\r
                {\r
-                       /* \83\8a\83W\83\85\81[\83\80 */\r
+                       /* リジューム */\r
                        if(Pkt->hWndTrans != NULL)\r
                                Pkt->ExistSize = Size;\r
                        *Mode = OPEN_ALWAYS;\r
@@ -1510,7 +2129,7 @@ static int SetDownloadResume(TRANSPACKET *Pkt, int ProcMode, LONGLONG Size, int
                        Com = DialogBox(GetFtpInst(), MAKEINTRESOURCE(noresume_dlg), Pkt->hWndTrans, NoResumeWndProc);\r
                        if(Com != YES)\r
                        {\r
-                               if(Com == NO_ALL)               /* \91S\82Ä\92\86\8e~ */\r
+                               if(Com == NO_ALL)               /* 全て中止 */\r
                                        ClearAll = YES;\r
                                Pkt->Abort = ABORT_USER;\r
                        }\r
@@ -1520,13 +2139,13 @@ static int SetDownloadResume(TRANSPACKET *Pkt, int ProcMode, LONGLONG Size, int
 }\r
 \r
 \r
-/*----- resume\83G\83\89\81[\83_\83C\83A\83\8d\83O\82Ì\83R\81[\83\8b\83o\83b\83N ----------------------------------\r
+/*----- resumeエラーダイアログのコールバック ----------------------------------\r
 *\r
 *      Parameter\r
-*              HWND hDlg : \83E\83C\83\93\83h\83E\83n\83\93\83h\83\8b\r
-*              UINT message : \83\81\83b\83Z\81[\83W\94Ô\8d\86\r
-*              WPARAM wParam : \83\81\83b\83Z\81[\83W\82Ì WPARAM \88ø\90\94\r
-*              LPARAM lParam : \83\81\83b\83Z\81[\83W\82Ì LPARAM \88ø\90\94\r
+*              HWND hDlg : ウインドウハンドル\r
+*              UINT message : メッセージ番号\r
+*              WPARAM wParam : メッセージの WPARAM 引数\r
+*              LPARAM lParam : メッセージの LPARAM 引数\r
 *\r
 *      Return Value\r
 *              BOOL TRUE/FALSE\r
@@ -1561,14 +2180,14 @@ static BOOL CALLBACK NoResumeWndProc(HWND hDlg, UINT iMessage, WPARAM wParam, LP
 \r
 \r
 \r
-/*----- \83A\83b\83v\83\8d\81[\83h\82ð\8ds\82È\82¤ --------------------------------------------------\r
+/*----- アップロードを行なう --------------------------------------------------\r
 *\r
 *      Parameter\r
-*              SOCKET cSkt : \83R\83\93\83g\83\8d\81[\83\8b\83\\83P\83b\83g\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
+*              SOCKET cSkt : コントロールソケット\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int DoUpLoad(SOCKET cSkt, TRANSPACKET *Pkt)\r
@@ -1580,12 +2199,14 @@ static int DoUpLoad(SOCKET cSkt, TRANSPACKET *Pkt)
 \r
        if(Pkt->Mode != EXIST_IGNORE)\r
        {\r
-               if(CheckFileReadable(Pkt->LocalFile) == SUCCESS)\r
+               if(CheckFileReadable(Pkt->LocalFile) == FFFTP_SUCCESS)\r
                {\r
                        if(Pkt->Type == TYPE_I)\r
                                Pkt->KanjiCode = KANJI_NOCNV;\r
 \r
-                       iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled, "TYPE %c", Pkt->Type);\r
+                       // 同時接続対応\r
+//                     iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled, "TYPE %c", Pkt->Type);\r
+                       iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled[Pkt->ThreadCount], "TYPE %c", Pkt->Type);\r
                        if(iRetCode/100 < FTP_RETRY)\r
                        {\r
                                if(Pkt->Mode == EXIST_UNIQUE)\r
@@ -1607,9 +2228,11 @@ static int DoUpLoad(SOCKET cSkt, TRANSPACKET *Pkt)
                        else\r
                                SetErrorMsg(Reply);\r
 \r
-                       /* \91®\90«\95Ï\8dX */\r
+                       /* 属性変更 */\r
                        if((Pkt->Attr != -1) && ((iRetCode/100) == FTP_COMPLETE))\r
-                               command(Pkt->ctrl_skt, Reply, &Canceled, "%s %03X %s", AskHostChmodCmd(), Pkt->Attr, Pkt->RemoteFile);\r
+                               // 同時接続対応\r
+//                             command(Pkt->ctrl_skt, Reply, &Canceled, "%s %03X %s", AskHostChmodCmd(), Pkt->Attr, Pkt->RemoteFile);\r
+                               command(Pkt->ctrl_skt, Reply, &Canceled[Pkt->ThreadCount], "%s %03X %s", AskHostChmodCmd(), Pkt->Attr, Pkt->RemoteFile);\r
                }\r
                else\r
                {\r
@@ -1630,13 +2253,13 @@ static int DoUpLoad(SOCKET cSkt, TRANSPACKET *Pkt)
 }\r
 \r
 \r
-/*----- \92Ê\8fí\83\82\81[\83h\82Å\83t\83@\83C\83\8b\82ð\83A\83b\83v\83\8d\81[\83h ------------------------------------\r
+/*----- 通常モードでファイルをアップロード ------------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int UpLoadNonPassive(TRANSPACKET *Pkt)\r
@@ -1650,7 +2273,9 @@ static int UpLoadNonPassive(TRANSPACKET *Pkt)
        int Resume;\r
        char Reply[ERR_MSG_LEN+7];\r
 \r
-       if((listen_socket = GetFTPListenSocket(Pkt->ctrl_skt, &Canceled)) != INVALID_SOCKET)\r
+       // 同時接続対応\r
+//     if((listen_socket = GetFTPListenSocket(Pkt->ctrl_skt, &Canceled)) != INVALID_SOCKET)\r
+       if((listen_socket = GetFTPListenSocket(Pkt->ctrl_skt, &Canceled[Pkt->ThreadCount])) != INVALID_SOCKET)\r
        {\r
                SetUploadResume(Pkt, Pkt->Mode, Pkt->ExistSize, &Resume);\r
                if(Resume == NO)\r
@@ -1658,10 +2283,12 @@ static int UpLoadNonPassive(TRANSPACKET *Pkt)
                else\r
                        sprintf(Buf, "%s%s", "APPE ", Pkt->RemoteFile);\r
 \r
-               iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled, "%s", Buf);\r
+               // 同時接続対応\r
+//             iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled, "%s", Buf);\r
+               iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled[Pkt->ThreadCount], "%s", Buf);\r
                if((iRetCode/100) == FTP_PRELIM)\r
                {\r
-                       if(SocksGet2ndBindReply(listen_socket, &data_socket) == FAIL)\r
+                       if(SocksGet2ndBindReply(listen_socket, &data_socket) == FFFTP_FAIL)\r
                        {\r
                                iLength=sizeof(saSockAddr1);\r
                                data_socket = do_accept(listen_socket,(struct sockaddr *)&saSockAddr1, (int *)&iLength);\r
@@ -1682,7 +2309,19 @@ static int UpLoadNonPassive(TRANSPACKET *Pkt)
 \r
                        if(data_socket != INVALID_SOCKET)\r
                        {\r
-                               iRetCode = UpLoadFile(Pkt, data_socket);\r
+                               // 一部TYPE、STOR(RETR)、PORT(PASV)を並列に処理できないホストがあるため\r
+                               ReleaseMutex(hListAccMutex);\r
+                               // FTPS対応\r
+//                             iRetCode = UpLoadFile(Pkt, data_socket);\r
+                               if(AskCryptMode() == CRYPT_FTPES || AskCryptMode() == CRYPT_FTPIS)\r
+                               {\r
+                                       if(AttachSSL(data_socket))\r
+                                               iRetCode = UpLoadFile(Pkt, data_socket);\r
+                                       else\r
+                                               iRetCode = FTP_ERROR;\r
+                               }\r
+                               else\r
+                                       iRetCode = UpLoadFile(Pkt, data_socket);\r
                                data_socket = DoClose(data_socket);\r
                        }\r
                }\r
@@ -1705,13 +2344,13 @@ static int UpLoadNonPassive(TRANSPACKET *Pkt)
 }\r
 \r
 \r
-/*----- Passive\83\82\81[\83h\82Å\83t\83@\83C\83\8b\82ð\83A\83b\83v\83\8d\81[\83h ---------------------------------\r
+/*----- Passiveモードでファイルをアップロード ---------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int UpLoadPassive(TRANSPACKET *Pkt)\r
@@ -1725,13 +2364,19 @@ static int UpLoadPassive(TRANSPACKET *Pkt)
        int Resume;\r
        char Reply[ERR_MSG_LEN+7];\r
 \r
-       iRetCode = command(Pkt->ctrl_skt, Buf, &Canceled, "PASV");\r
+       // 同時接続対応\r
+//     iRetCode = command(Pkt->ctrl_skt, Buf, &Canceled, "PASV");\r
+       iRetCode = command(Pkt->ctrl_skt, Buf, &Canceled[Pkt->ThreadCount], "PASV");\r
        if(iRetCode/100 == FTP_COMPLETE)\r
        {\r
-               if(GetAdrsAndPort(Buf, Adrs, &Port, 19) == SUCCESS)\r
+               if(GetAdrsAndPort(Buf, Adrs, &Port, 19) == FFFTP_SUCCESS)\r
                {\r
-                       if((data_socket = connectsock(Adrs, Port, MSGJPN109, &Canceled)) != INVALID_SOCKET)\r
+                       // 同時接続対応\r
+//                     if((data_socket = connectsock(Adrs, Port, MSGJPN109, &Canceled)) != INVALID_SOCKET)\r
+                       if((data_socket = connectsock(Adrs, Port, MSGJPN109, &Canceled[Pkt->ThreadCount])) != INVALID_SOCKET)\r
                        {\r
+                               // 変数が未初期化のバグ修正\r
+                               Flg = 1;\r
                                if(setsockopt(data_socket, IPPROTO_TCP, TCP_NODELAY, (LPSTR)&Flg, sizeof(Flg)) == SOCKET_ERROR)\r
                                        ReportWSError("setsockopt", WSAGetLastError());\r
 \r
@@ -1741,10 +2386,24 @@ static int UpLoadPassive(TRANSPACKET *Pkt)
                                else\r
                                        sprintf(Buf, "%s%s", "APPE ", Pkt->RemoteFile);\r
 \r
-                               iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled, "%s", Buf);\r
+                               // 同時接続対応\r
+//                             iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled, "%s", Buf);\r
+                               iRetCode = command(Pkt->ctrl_skt, Reply, &Canceled[Pkt->ThreadCount], "%s", Buf);\r
                                if(iRetCode/100 == FTP_PRELIM)\r
                                {\r
-                                       iRetCode = UpLoadFile(Pkt, data_socket);\r
+                                       // 一部TYPE、STOR(RETR)、PORT(PASV)を並列に処理できないホストがあるため\r
+                                       ReleaseMutex(hListAccMutex);\r
+                                       // FTPS対応\r
+//                                     iRetCode = UpLoadFile(Pkt, data_socket);\r
+                                       if(AskCryptMode() == CRYPT_FTPES || AskCryptMode() == CRYPT_FTPIS)\r
+                                       {\r
+                                               if(AttachSSL(data_socket))\r
+                                                       iRetCode = UpLoadFile(Pkt, data_socket);\r
+                                               else\r
+                                                       iRetCode = FTP_ERROR;\r
+                                       }\r
+                                       else\r
+                                               iRetCode = UpLoadFile(Pkt, data_socket);\r
 \r
                                        data_socket = DoClose(data_socket);\r
                                }\r
@@ -1778,18 +2437,18 @@ static int UpLoadPassive(TRANSPACKET *Pkt)
 }\r
 \r
 \r
-/*----- \83A\83b\83v\83\8d\81[\83h\82Ì\8eÀ\8ds ----------------------------------------------------\r
+/*----- アップロードの実行 ----------------------------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              SOCKET dSkt : \83f\81[\83^\83\\83P\83b\83g\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              SOCKET dSkt : データソケット\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *\r
 *      Note\r
-*              \93]\91\97\82Ì\8co\89ß\95\\8e¦\82Í\81A\83C\83\93\83^\81[\83o\83\8b\83^\83C\83}\82Å\8co\89ß\82ð\95\\8e¦\82·\82é\r
-*              \93]\91\97\83_\83C\83A\83\8d\83O\82ð\8fo\82³\82È\82¢\82Å\83A\83b\83v\83\8d\81[\83h\82·\82é\82±\82Æ\82Í\82È\82¢\r
+*              転送の経過表示は、インターバルタイマで経過を表示する\r
+*              転送ダイアログを出さないでアップロードすることはない\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)\r
@@ -1820,13 +2479,11 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
 /* End */\r
 #endif\r
 \r
-// Written by Suguru Kawamoto\r
-#ifdef DISABLE_NETWORK_BUFFERS\r
-       // \94O\82Ì\82½\82ß\91\97\90M\83o\83b\83t\83@\82ð\96³\8cø\82É\82·\82é\81B\r
+       // 念のため送信バッファを無効にする\r
+#ifdef DISABLE_TRANSFER_NETWORK_BUFFERS\r
        int buf_size = 0;\r
        setsockopt(dSkt, SOL_SOCKET, SO_SNDBUF, (char *)&buf_size, sizeof(buf_size));\r
 #endif\r
-// End Written by Suguru Kawamoto\r
 \r
        Pkt->Abort = ABORT_NONE;\r
 \r
@@ -1837,6 +2494,10 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
        if((iFileHandle = CreateFile(Pkt->LocalFile, GENERIC_READ,\r
                FILE_SHARE_READ|FILE_SHARE_WRITE, &Sec, OPEN_EXISTING, 0, NULL)) != INVALID_HANDLE_VALUE)\r
        {\r
+               // UTF-8対応\r
+               char Buf3[(BUFSIZE + 3) * 4];\r
+               CODECONVINFO cInfo2;\r
+               int ProcessedBOM = NO;\r
                if(Pkt->hWndTrans != NULL)\r
                {\r
                        Low = GetFileSize(iFileHandle, &High);\r
@@ -1846,8 +2507,11 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
                        Low = (DWORD)LOW32(Pkt->ExistSize);\r
                        SetFilePointer(iFileHandle, Low, &High, FILE_BEGIN);\r
 \r
-                       AllTransSizeNow = 0;\r
-                       TimeStart = time(NULL);\r
+                       // 同時接続対応\r
+//                     AllTransSizeNow = 0;\r
+//                     TimeStart = time(NULL);\r
+                       AllTransSizeNow[Pkt->ThreadCount] = 0;\r
+                       TimeStart[Pkt->ThreadCount] = time(NULL);\r
                        SetTimer(Pkt->hWndTrans, TIMER_DISPLAY, DISPLAY_TIMING, NULL);\r
                }\r
 \r
@@ -1855,7 +2519,10 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
                cInfo.KanaCnv = Pkt->KanaCnv;\r
                InitTermCodeConvInfo(&tInfo);\r
 \r
-               /*===== \83t\83@\83C\83\8b\82ð\91\97\90M\82·\82é\83\8b\81[\83v =====*/\r
+               InitCodeConvInfo(&cInfo2);\r
+               cInfo2.KanaCnv = Pkt->KanaCnv;\r
+\r
+               /*===== ファイルを送信するループ =====*/\r
                while((Pkt->Abort == ABORT_NONE) &&\r
                          (ForceAbort == NO) &&\r
                          (ReadFile(iFileHandle, Buf, BUFSIZE, &iNumBytes, NULL) == TRUE))\r
@@ -1863,7 +2530,7 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
                        if(iNumBytes == 0)\r
                                break;\r
 \r
-                       /* EOF\8f\9c\8b\8e */\r
+                       /* EOF除去 */\r
                        EofPos = NULL;\r
                        if((RmEOF == YES) && (Pkt->Type == TYPE_A))\r
                        {\r
@@ -1871,7 +2538,7 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
                                        iNumBytes = EofPos - Buf;\r
                        }\r
 \r
-                       /* \8a¿\8e\9a\83R\81[\83h\95Ï\8a· */\r
+                       /* 漢字コード変換 */\r
                        if(Pkt->KanjiCode != KANJI_NOCNV)\r
                        {\r
                                cInfo.Str = Buf;\r
@@ -1880,12 +2547,200 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
                                cInfo.BufSize = BUFSIZE+3;\r
                                do\r
                                {\r
-                                       if(Pkt->KanjiCode == KANJI_JIS)\r
-                                               Continue = ConvSJIStoJIS(&cInfo);\r
-                                       else\r
-                                               Continue = ConvSJIStoEUC(&cInfo);\r
+                                       // ここで全てUTF-8へ変換する\r
+                                       // TODO: SJIS以外も直接UTF-8へ変換\r
+//                                     if(Pkt->KanjiCode == KANJI_JIS)\r
+//                                             Continue = ConvSJIStoJIS(&cInfo);\r
+//                                     else\r
+//                                             Continue = ConvSJIStoEUC(&cInfo);\r
+                                       switch(Pkt->KanjiCodeDesired)\r
+                                       {\r
+                                       case KANJI_SJIS:\r
+                                               switch(Pkt->KanjiCode)\r
+                                               {\r
+                                               case KANJI_SJIS:\r
+//                                                     memcpy(Buf3, cInfo.Str, cInfo.StrLen);\r
+//                                                     cInfo2.OutLen = cInfo.StrLen;\r
+//                                                     Continue = NO;\r
+                                                       // カナ変換のため\r
+                                                       Continue = ConvSJIStoJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvJIStoSJIS(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_JIS:\r
+                                                       Continue = ConvSJIStoJIS(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_EUC:\r
+                                                       Continue = ConvSJIStoEUC(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_UTF8N:\r
+                                                       if(ProcessedBOM == NO)\r
+                                                       {\r
+                                                               memcpy(Buf3, "\xEF\xBB\xBF", 3);\r
+                                                               cInfo2.OutLen = 3;\r
+                                                               Continue = YES;\r
+                                                               ProcessedBOM = YES;\r
+                                                               break;\r
+                                                       }\r
+                                                       Continue = ConvSJIStoUTF8N(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               }\r
+                                               break;\r
+                                       case KANJI_JIS:\r
+                                               switch(Pkt->KanjiCode)\r
+                                               {\r
+                                               case KANJI_SJIS:\r
+                                                       Continue = ConvJIStoSJIS(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_JIS:\r
+//                                                     memcpy(Buf3, cInfo.Str, cInfo.StrLen);\r
+//                                                     cInfo2.OutLen = cInfo.StrLen;\r
+//                                                     Continue = NO;\r
+                                                       // カナ変換のため\r
+                                                       Continue = ConvJIStoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoJIS(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_EUC:\r
+                                                       Continue = ConvJIStoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoEUC(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_UTF8N:\r
+                                                       if(ProcessedBOM == NO)\r
+                                                       {\r
+                                                               memcpy(Buf3, "\xEF\xBB\xBF", 3);\r
+                                                               cInfo2.OutLen = 3;\r
+                                                               Continue = YES;\r
+                                                               ProcessedBOM = YES;\r
+                                                               break;\r
+                                                       }\r
+                                                       Continue = ConvJIStoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoUTF8N(&cInfo2);\r
+                                                       break;\r
+                                               }\r
+                                               break;\r
+                                       case KANJI_EUC:\r
+                                               switch(Pkt->KanjiCode)\r
+                                               {\r
+                                               case KANJI_SJIS:\r
+                                                       Continue = ConvEUCtoSJIS(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_JIS:\r
+                                                       Continue = ConvEUCtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoJIS(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_EUC:\r
+//                                                     memcpy(Buf3, cInfo.Str, cInfo.StrLen);\r
+//                                                     cInfo2.OutLen = cInfo.StrLen;\r
+//                                                     Continue = NO;\r
+                                                       // カナ変換のため\r
+                                                       Continue = ConvEUCtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoEUC(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_UTF8N:\r
+                                                       if(ProcessedBOM == NO)\r
+                                                       {\r
+                                                               memcpy(Buf3, "\xEF\xBB\xBF", 3);\r
+                                                               cInfo2.OutLen = 3;\r
+                                                               Continue = YES;\r
+                                                               ProcessedBOM = YES;\r
+                                                               break;\r
+                                                       }\r
+                                                       Continue = ConvEUCtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoUTF8N(&cInfo2);\r
+                                                       break;\r
+                                               }\r
+                                               break;\r
+                                       case KANJI_UTF8N:\r
+                                               if(ProcessedBOM == NO)\r
+                                               {\r
+                                                       if(memcmp(Buf, "\xEF\xBB\xBF", 3) == 0)\r
+                                                       {\r
+                                                               cInfo.Str += 3;\r
+                                                               cInfo.StrLen -= 3;\r
+                                                       }\r
+                                                       cInfo2.OutLen = 0;\r
+                                                       switch(Pkt->KanjiCode)\r
+                                                       {\r
+                                                       case KANJI_UTF8N:\r
+                                                               memcpy(Buf3, "\xEF\xBB\xBF", 3);\r
+                                                               cInfo2.OutLen = 3;\r
+                                                               break;\r
+                                                       }\r
+                                                       Continue = YES;\r
+                                                       ProcessedBOM = YES;\r
+                                                       break;\r
+                                               }\r
+                                               switch(Pkt->KanjiCode)\r
+                                               {\r
+                                               case KANJI_SJIS:\r
+                                                       Continue = ConvUTF8NtoSJIS(&cInfo);\r
+                                                       memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                                       cInfo2.OutLen = cInfo.OutLen;\r
+                                                       break;\r
+                                               case KANJI_JIS:\r
+                                                       Continue = ConvUTF8NtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoJIS(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_EUC:\r
+                                                       Continue = ConvUTF8NtoSJIS(&cInfo);\r
+                                                       cInfo2.Str = cInfo.Buf;\r
+                                                       cInfo2.StrLen = cInfo.OutLen;\r
+                                                       cInfo2.Buf = Buf3;\r
+                                                       cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                                       ConvSJIStoEUC(&cInfo2);\r
+                                                       break;\r
+                                               case KANJI_UTF8N:\r
+                                                       memcpy(Buf3, cInfo.Str, cInfo.StrLen);\r
+                                                       cInfo2.OutLen = cInfo.StrLen;\r
+                                                       Continue = NO;\r
+                                                       break;\r
+                                               }\r
+                                               break;\r
+                                       }\r
 \r
-                                       if(TermCodeConvAndSend(&tInfo, dSkt, Buf2, cInfo.OutLen, Pkt->Type) == FAIL)\r
+//                                     if(TermCodeConvAndSend(&tInfo, dSkt, Buf2, cInfo.OutLen, Pkt->Type) == FFFTP_FAIL)\r
+                                       if(TermCodeConvAndSend(Pkt->ThreadCount, &tInfo, dSkt, Buf3, cInfo2.OutLen, Pkt->Type) == FFFTP_FAIL)\r
                                        {\r
                                                Pkt->Abort = ABORT_ERROR;\r
                                                        break;\r
@@ -1895,13 +2750,17 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
                        }\r
                        else\r
                        {\r
-                               if(TermCodeConvAndSend(&tInfo, dSkt, Buf, iNumBytes, Pkt->Type) == FAIL)\r
+                               // 同時接続対応\r
+//                             if(TermCodeConvAndSend(&tInfo, dSkt, Buf, iNumBytes, Pkt->Type) == FFFTP_FAIL)\r
+                               if(TermCodeConvAndSend(Pkt->ThreadCount, &tInfo, dSkt, Buf, iNumBytes, Pkt->Type) == FFFTP_FAIL)\r
                                        Pkt->Abort = ABORT_ERROR;\r
                        }\r
 \r
                        Pkt->ExistSize += iNumBytes;\r
                        if(Pkt->hWndTrans != NULL)\r
-                               AllTransSizeNow += iNumBytes;\r
+                               // 同時接続対応\r
+//                             AllTransSizeNow += iNumBytes;\r
+                               AllTransSizeNow[Pkt->ThreadCount] += iNumBytes;\r
 \r
                        if(BackgrndMessageProc() == YES)\r
                                ForceAbort = YES;\r
@@ -1912,30 +2771,157 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
 \r
                if((ForceAbort == NO) && (Pkt->Abort == ABORT_NONE))\r
                {\r
-                       /* \91\97\82è\8ec\82µ\82½\83f\81[\83^\82ð\91\97\90M */\r
+                       /* 送り残したデータを送信 */\r
                        if(Pkt->KanjiCode != KANJI_NOCNV)\r
                        {\r
                                cInfo.Buf = Buf2;\r
                                cInfo.BufSize = BUFSIZE+3;\r
                                FlushRestData(&cInfo);\r
+                               switch(Pkt->KanjiCodeDesired)\r
+                               {\r
+                               case KANJI_SJIS:\r
+                                       switch(Pkt->KanjiCode)\r
+                                       {\r
+                                       case KANJI_SJIS:\r
+                                               // カナ変換のため\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvJIStoSJIS(&cInfo2);\r
+                                               break;\r
+                                       case KANJI_JIS:\r
+                                               memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                               cInfo2.OutLen = cInfo.OutLen;\r
+                                               break;\r
+                                       case KANJI_EUC:\r
+                                               memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                               cInfo2.OutLen = cInfo.OutLen;\r
+                                               break;\r
+                                       case KANJI_UTF8N:\r
+                                               memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                               cInfo2.OutLen = cInfo.OutLen;\r
+                                               break;\r
+                                       }\r
+                                       break;\r
+                               case KANJI_JIS:\r
+                                       switch(Pkt->KanjiCode)\r
+                                       {\r
+                                       case KANJI_SJIS:\r
+                                               memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                               cInfo2.OutLen = cInfo.OutLen;\r
+                                               break;\r
+                                       case KANJI_JIS:\r
+                                               // カナ変換のため\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvSJIStoJIS(&cInfo2);\r
+                                               break;\r
+                                       case KANJI_EUC:\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvSJIStoEUC(&cInfo2);\r
+                                               break;\r
+                                       case KANJI_UTF8N:\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvSJIStoUTF8N(&cInfo2);\r
+                                               break;\r
+                                       }\r
+                                       break;\r
+                               case KANJI_EUC:\r
+                                       switch(Pkt->KanjiCode)\r
+                                       {\r
+                                       case KANJI_SJIS:\r
+                                               memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                               cInfo2.OutLen = cInfo.OutLen;\r
+                                               break;\r
+                                       case KANJI_JIS:\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvSJIStoJIS(&cInfo2);\r
+                                               break;\r
+                                       case KANJI_EUC:\r
+                                               // カナ変換のため\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvSJIStoEUC(&cInfo2);\r
+                                               break;\r
+                                       case KANJI_UTF8N:\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvSJIStoUTF8N(&cInfo2);\r
+                                               break;\r
+                                       }\r
+                                       break;\r
+                               case KANJI_UTF8N:\r
+                                       switch(Pkt->KanjiCode)\r
+                                       {\r
+                                       case KANJI_SJIS:\r
+                                               memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                               cInfo2.OutLen = cInfo.OutLen;\r
+                                               break;\r
+                                       case KANJI_JIS:\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvSJIStoJIS(&cInfo2);\r
+                                               break;\r
+                                       case KANJI_EUC:\r
+                                               cInfo2.Str = cInfo.Buf;\r
+                                               cInfo2.StrLen = cInfo.OutLen;\r
+                                               cInfo2.Buf = Buf3;\r
+                                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                                               ConvSJIStoEUC(&cInfo2);\r
+                                               break;\r
+                                       case KANJI_UTF8N:\r
+                                               memcpy(Buf3, cInfo.Buf, cInfo.OutLen);\r
+                                               cInfo2.OutLen = cInfo.OutLen;\r
+                                               break;\r
+                                       }\r
+                                       break;\r
+                               }\r
 \r
-                               if(TermCodeConvAndSend(&tInfo, dSkt, Buf2, cInfo.OutLen, Pkt->Type) == FAIL)\r
+//                             if(TermCodeConvAndSend(&tInfo, dSkt, Buf2, cInfo.OutLen, Pkt->Type) == FFFTP_FAIL)\r
+                               if(TermCodeConvAndSend(Pkt->ThreadCount, &tInfo, dSkt, Buf3, cInfo2.OutLen, Pkt->Type) == FFFTP_FAIL)\r
+                                       Pkt->Abort = ABORT_ERROR;\r
+                               cInfo2.Buf = Buf3;\r
+                               cInfo2.BufSize = (BUFSIZE + 3) * 4;\r
+                               FlushRestData(&cInfo2);\r
+                               if(TermCodeConvAndSend(Pkt->ThreadCount, &tInfo, dSkt, Buf3, cInfo2.OutLen, Pkt->Type) == FFFTP_FAIL)\r
                                        Pkt->Abort = ABORT_ERROR;\r
                        }\r
 \r
                        tInfo.Buf = Buf2;\r
                        tInfo.BufSize = BUFSIZE+3;\r
                        FlushRestTermCodeConvData(&tInfo);\r
-                       if(SendData(dSkt, Buf2, tInfo.OutLen, 0, &Canceled) == FAIL)\r
+                       // 同時接続対応\r
+//                     if(SendData(dSkt, Buf2, tInfo.OutLen, 0, &Canceled) == FFFTP_FAIL)\r
+                       if(SendData(dSkt, Buf2, tInfo.OutLen, 0, &Canceled[Pkt->ThreadCount]) == FFFTP_FAIL)\r
                                Pkt->Abort = ABORT_ERROR;\r
                }\r
 \r
-               /* \83O\83\89\83t\95\\8e¦\82ð\8dX\90V */\r
+               /* グラフ表示を更新 */\r
                if(Pkt->hWndTrans != NULL)\r
                {\r
                        KillTimer(Pkt->hWndTrans, TIMER_DISPLAY);\r
                        DispTransferStatus(Pkt->hWndTrans, YES, Pkt);\r
-                       TimeStart = time(NULL) - TimeStart + 1;\r
+                       // 同時接続対応\r
+//                     TimeStart = time(NULL) - TimeStart + 1;\r
+                       TimeStart[Pkt->ThreadCount] = time(NULL) - TimeStart[Pkt->ThreadCount] + 1;\r
                }\r
                CloseHandle(iFileHandle);\r
        }\r
@@ -1955,7 +2941,9 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
                ;\r
 #endif\r
 \r
-       iRetCode = ReadReplyMessage(Pkt->ctrl_skt, Buf, 1024, &Canceled, TmpBuf);\r
+       // 同時接続対応\r
+//     iRetCode = ReadReplyMessage(Pkt->ctrl_skt, Buf, 1024, &Canceled, TmpBuf);\r
+       iRetCode = ReadReplyMessage(Pkt->ctrl_skt, Buf, 1024, &Canceled[Pkt->ThreadCount], TmpBuf);\r
 \r
 //#pragma aaa\r
 //DoPrintf("##UP REPLY : %s", Buf);\r
@@ -1970,28 +2958,30 @@ static int UpLoadFile(TRANSPACKET *Pkt, SOCKET dSkt)
 }\r
 \r
 \r
-/*----- \83o\83b\83t\83@\82Ì\93à\97e\82ð\89ü\8ds\83R\81[\83h\95Ï\8a·\82µ\82Ä\91\97\90M --------------------------------\r
+/*----- バッファの内容を改行コード変換して送信 --------------------------------\r
 *\r
 *      Parameter\r
-*              TERMCODECONVINFO *tInfo : \89ü\8ds\83R\81[\83h\95Ï\8a·\83p\83P\83b\83g\r
-*              SOCKET Skt : \83\\83P\83b\83g\r
-*              char *Data : \83f\81[\83^\r
-*              int Size : \83f\81[\83^\82Ì\83T\83C\83Y\r
-*              int Ascii : \83\82\81[\83h\81@\81@(TYPE_xx)\r
+*              TERMCODECONVINFO *tInfo : 改行コード変換パケット\r
+*              SOCKET Skt : ソケット\r
+*              char *Data : データ\r
+*              int Size : データのサイズ\r
+*              int Ascii : モード  (TYPE_xx)\r
 *\r
 *      Return Value\r
-*              int \89\9e\93\9a\83R\81[\83h\r
+*              int 応答コード\r
 *----------------------------------------------------------------------------*/\r
 \r
-static int TermCodeConvAndSend(TERMCODECONVINFO *tInfo, SOCKET Skt, char *Data, int Size, int Ascii)\r
+// 同時接続対応\r
+//static int TermCodeConvAndSend(TERMCODECONVINFO *tInfo, SOCKET Skt, char *Data, int Size, int Ascii)\r
+static int TermCodeConvAndSend(int ThreadCount, TERMCODECONVINFO *tInfo, SOCKET Skt, char *Data, int Size, int Ascii)\r
 {\r
        char Buf3[BUFSIZE*2];\r
        int Continue;\r
        int Ret;\r
 \r
-       Ret = SUCCESS;\r
+       Ret = FFFTP_SUCCESS;\r
 \r
-// CR-LF\88È\8aO\82Ì\89ü\8ds\83R\81[\83h\82ð\95Ï\8a·\82µ\82È\82¢\83\82\81[\83h\82Í\82±\82±\82Ö\92Ç\89Á\r
+// CR-LF以外の改行コードを変換しないモードはここへ追加\r
        if(Ascii == TYPE_A)\r
        {\r
                tInfo->Str = Data;\r
@@ -2001,26 +2991,30 @@ static int TermCodeConvAndSend(TERMCODECONVINFO *tInfo, SOCKET Skt, char *Data,
                do\r
                {\r
                        Continue = ConvTermCodeToCRLF(tInfo);\r
-                       if((Ret = SendData(Skt, Buf3, tInfo->OutLen, 0, &Canceled)) == FAIL)\r
+                       // 同時接続対応\r
+//                     if((Ret = SendData(Skt, Buf3, tInfo->OutLen, 0, &Canceled)) == FFFTP_FAIL)\r
+                       if((Ret = SendData(Skt, Buf3, tInfo->OutLen, 0, &Canceled[ThreadCount])) == FFFTP_FAIL)\r
                                break;\r
                }\r
                while(Continue == YES);\r
        }\r
        else\r
-               Ret = SendData(Skt, Data, Size, 0, &Canceled);\r
+               // 同時接続対応\r
+//             Ret = SendData(Skt, Data, Size, 0, &Canceled);\r
+               Ret = SendData(Skt, Data, Size, 0, &Canceled[ThreadCount]);\r
 \r
        return(Ret);\r
 }\r
 \r
 \r
-/*----- \83A\83b\83v\83\8d\81[\83h\8fI\97¹\81^\92\86\8e~\8e\9e\82Ì\83\81\83b\83Z\81[\83W\82ð\95\\8e¦ ----------------------------\r
+/*----- アップロード終了/中止時のメッセージを表示 ----------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              int iRetCode : \89\9e\93\9a\83R\81[\83h\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              int iRetCode : 応答コード\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 static void DispUploadFinishMsg(TRANSPACKET *Pkt, int iRetCode)\r
@@ -2029,21 +3023,32 @@ static void DispUploadFinishMsg(TRANSPACKET *Pkt, int iRetCode)
        {\r
                if((iRetCode/100) >= FTP_CONTINUE)\r
                {\r
-                       if((Pkt->hWndTrans != NULL) && (TimeStart != 0))\r
-                               SetTaskMsg(MSGJPN113, TimeStart, Pkt->ExistSize/TimeStart);\r
+                       // 同時接続対応\r
+//                     if((Pkt->hWndTrans != NULL) && (TimeStart != 0))\r
+//                             SetTaskMsg(MSGJPN113, TimeStart, Pkt->ExistSize/TimeStart);\r
+                       if((Pkt->hWndTrans != NULL) && (TimeStart[Pkt->ThreadCount] != 0))\r
+                               SetTaskMsg(MSGJPN113, TimeStart[Pkt->ThreadCount], Pkt->ExistSize/TimeStart[Pkt->ThreadCount]);\r
                        else\r
                                SetTaskMsg(MSGJPN114);\r
 \r
                        if(Pkt->Abort != ABORT_USER)\r
                        {\r
-                               if(DispUpDownErrDialog(uperr_dlg, Pkt->hWndTrans, Pkt->LocalFile) == NO)\r
+                               // 全て中止を選択後にダイアログが表示されるバグ対策\r
+//                             if(DispUpDownErrDialog(uperr_dlg, Pkt->hWndTrans, Pkt->LocalFile) == NO)\r
+                               if(Canceled[Pkt->ThreadCount] == NO && ClearAll == NO && DispUpDownErrDialog(uperr_dlg, Pkt->hWndTrans, Pkt->LocalFile) == NO)\r
                                        ClearAll = YES;\r
                        }\r
                }\r
                else\r
                {\r
-                       if((Pkt->hWndTrans != NULL) && (TimeStart != 0))\r
-                               SetTaskMsg(MSGJPN115, TimeStart, Pkt->ExistSize/TimeStart);\r
+                       // 同時接続対応\r
+//                     if((Pkt->hWndTrans != NULL) && (TimeStart != 0))\r
+//                             SetTaskMsg(MSGJPN115, TimeStart, Pkt->ExistSize/TimeStart);\r
+                       if((Pkt->hWndTrans != NULL) && (TimeStart[Pkt->ThreadCount] != 0))\r
+                               // "0 B/S"と表示されるバグを修正\r
+                               // 原因は%dにあたる部分に64ビット値が渡されているため\r
+//                             SetTaskMsg(MSGJPN115, TimeStart[Pkt->ThreadCount], Pkt->ExistSize/TimeStart[Pkt->ThreadCount]);\r
+                               SetTaskMsg(MSGJPN115, (LONG)TimeStart[Pkt->ThreadCount], (LONG)(Pkt->ExistSize/TimeStart[Pkt->ThreadCount]));\r
                        else\r
                                SetTaskMsg(MSGJPN116);\r
                }\r
@@ -2052,19 +3057,19 @@ static void DispUploadFinishMsg(TRANSPACKET *Pkt, int iRetCode)
 }\r
 \r
 \r
-/*----- \83A\83b\83v\83\8d\81[\83h\82Ì\83\8a\83W\83\85\81[\83\80\82Ì\8f\80\94õ\82ð\8ds\82¤ ----------------------------------\r
+/*----- アップロードのリジュームの準備を行う ----------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              iont ProcMode : \8f\88\97\9d\83\82\81[\83h(EXIST_xxx)\r
-*              LONGLONG Size : \83z\83X\83g\82É\82 \82é\83t\83@\83C\83\8b\82Ì\83T\83C\83Y\r
-*              int *Mode : \83\8a\83W\83\85\81[\83\80\82ð\8ds\82¤\82©\82Ç\82¤\82© (YES/NO)\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              iont ProcMode : 処理モード(EXIST_xxx)\r
+*              LONGLONG Size : ホストにあるファイルのサイズ\r
+*              int *Mode : リジュームを行うかどうか (YES/NO)\r
 *\r
 *      Return Value\r
-*              int \83X\83e\81[\83^\83X = YES\r
+*              int ステータス = YES\r
 *\r
 *      Note\r
-*              Pkt->ExistSize\82Ì\83Z\83b\83g\82ð\8ds\82È\82¤\r
+*              Pkt->ExistSizeのセットを行なう\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int SetUploadResume(TRANSPACKET *Pkt, int ProcMode, LONGLONG Size, int *Mode)\r
@@ -2083,13 +3088,13 @@ static int SetUploadResume(TRANSPACKET *Pkt, int ProcMode, LONGLONG Size, int *M
 }\r
 \r
 \r
-/*----- \93]\91\97\92\86\83_\83C\83A\83\8d\83O\83{\83b\83N\83X\82Ì\83R\81[\83\8b\83o\83b\83N --------------------------------\r
+/*----- 転送中ダイアログボックスのコールバック --------------------------------\r
 *\r
 *      Parameter\r
-*              HWND hDlg : \83E\83C\83\93\83h\83E\83n\83\93\83h\83\8b\r
-*              UINT message : \83\81\83b\83Z\81[\83W\94Ô\8d\86\r
-*              WPARAM wParam : \83\81\83b\83Z\81[\83W\82Ì WPARAM \88ø\90\94\r
-*              LPARAM lParam : \83\81\83b\83Z\81[\83W\82Ì LPARAM \88ø\90\94\r
+*              HWND hDlg : ウインドウハンドル\r
+*              UINT message : メッセージ番号\r
+*              WPARAM wParam : メッセージの WPARAM 引数\r
+*              LPARAM lParam : メッセージの LPARAM 引数\r
 *\r
 *      Return Value\r
 *              BOOL TRUE/FALSE\r
@@ -2100,7 +3105,10 @@ static LRESULT CALLBACK TransDlgProc(HWND hDlg, UINT Msg, WPARAM wParam, LPARAM
        RECT RectDlg;\r
        RECT RectPar;\r
        HMENU hMenu;\r
-       static TRANSPACKET *Pkt;\r
+       // 同時接続対応\r
+//     static TRANSPACKET *Pkt;\r
+       TRANSPACKET *Pkt;\r
+       int i;\r
 \r
        switch(Msg)\r
        {\r
@@ -2129,11 +3137,16 @@ static LRESULT CALLBACK TransDlgProc(HWND hDlg, UINT Msg, WPARAM wParam, LPARAM
 \r
                                case TRANS_STOP_ALL :\r
                                        ClearAll = YES;\r
-                                       /* \82±\82±\82É break \82Í\82È\82¢ */\r
+                                       for(i = 0; i < MAX_DATA_CONNECTION; i++)\r
+                                               Canceled[i] = YES;\r
+                                       /* ここに break はない */\r
 \r
                                case IDCANCEL :\r
+                                       if(!(Pkt = (TRANSPACKET*)GetWindowLong(hDlg, GWL_USERDATA)))\r
+                                               break;\r
                                        Pkt->Abort = ABORT_USER;\r
-                                       Canceled = YES;\r
+//                                     Canceled = YES;\r
+                                       Canceled[Pkt->ThreadCount] = YES;\r
                                        break;\r
                        }\r
                        break;\r
@@ -2145,27 +3158,32 @@ static LRESULT CALLBACK TransDlgProc(HWND hDlg, UINT Msg, WPARAM wParam, LPARAM
                                        SetForegroundWindow(hDlg);\r
                                MoveToForeground = NO;\r
                                KillTimer(hDlg, TIMER_DISPLAY);\r
+                               if(!(Pkt = (TRANSPACKET*)GetWindowLong(hDlg, GWL_USERDATA)))\r
+                                       break;\r
+                               if(Canceled[Pkt->ThreadCount] == YES)\r
+                                       Pkt->Abort = ABORT_USER;\r
                                DispTransferStatus(hDlg, NO, Pkt);\r
                                SetTimer(hDlg, TIMER_DISPLAY, DISPLAY_TIMING, NULL);\r
                        }\r
                        break;\r
 \r
                case WM_SET_PACKET :\r
-                       Pkt = (TRANSPACKET *)lParam;\r
+//                     Pkt = (TRANSPACKET *)lParam;\r
+                       SetWindowLong(hDlg, GWL_USERDATA, (LONG)lParam);\r
                        break;\r
        }\r
        return(FALSE);\r
 }\r
 \r
 \r
-/*----- \93]\91\97\83X\83e\81[\83^\83X\82ð\95\\8e¦ --------------------------------------------------\r
+/*----- 転送ステータスを表示 --------------------------------------------------\r
 *\r
 *      Parameter\r
-*              HWND hWnd : \83E\83C\83\93\83h\83E\83n\83\93\83h\83\8b\r
-*              int End : \93]\91\97\82ª\8a®\97¹\82µ\82½\82©\82Ç\82¤\82© (YES/NO)\r
+*              HWND hWnd : ウインドウハンドル\r
+*              int End : 転送が完了したかどうか (YES/NO)\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 static void DispTransferStatus(HWND hWnd, int End, TRANSPACKET *Pkt)\r
@@ -2194,11 +3212,15 @@ static void DispTransferStatus(HWND hWnd, int End, TRANSPACKET *Pkt)
                {\r
                        if(End == NO)\r
                        {\r
-                               TotalLap = time(NULL) - TimeStart + 1;\r
+                               // 同時接続対応\r
+//                             TotalLap = time(NULL) - TimeStart + 1;\r
+                               TotalLap = time(NULL) - TimeStart[Pkt->ThreadCount] + 1;\r
 \r
                                Bps = 0;\r
                                if(TotalLap != 0)\r
-                                       Bps = AllTransSizeNow / TotalLap;\r
+                                       // 同時接続対応\r
+//                                     Bps = AllTransSizeNow / TotalLap;\r
+                                       Bps = AllTransSizeNow[Pkt->ThreadCount] / TotalLap;\r
                                Transed = Pkt->Size - Pkt->ExistSize;\r
 \r
                                if(Pkt->Size <= 0)\r
@@ -2245,16 +3267,16 @@ static void DispTransferStatus(HWND hWnd, int End, TRANSPACKET *Pkt)
 }\r
 \r
 \r
-/*----- \93]\91\97\82·\82é\83t\83@\83C\83\8b\82Ì\8fî\95ñ\82ð\95\\8e¦ ------------------------------------------\r
+/*----- 転送するファイルの情報を表示 ------------------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *Pkt : \93]\91\97\83t\83@\83C\83\8b\8fî\95ñ\r
-*              char *Title : \83E\83C\83\93\83h\83E\82Ì\83^\83C\83g\83\8b\r
-*              int SkipButton : \81u\82±\82Ì\83t\83@\83C\83\8b\82ð\92\86\8e~\81v\83{\83^\83\93\82Ì\97L\96³ (TRUE/FALSE)\r
-*              int Info : \83t\83@\83C\83\8b\8fî\95ñ\82ð\95\\8e¦\82·\82é\82©\82Ç\82¤\82© (YES/NO)\r
+*              TRANSPACKET *Pkt : 転送ファイル情報\r
+*              char *Title : ウインドウのタイトル\r
+*              int SkipButton : 「このファイルを中止」ボタンの有無 (TRUE/FALSE)\r
+*              int Info : ファイル情報を表示するかどうか (YES/NO)\r
 *\r
 *      Return Value\r
-*              \82È\82µ\r
+*              なし\r
 *----------------------------------------------------------------------------*/\r
 \r
 static void DispTransFileInfo(TRANSPACKET *Pkt, char *Title, int SkipButton, int Info)\r
@@ -2283,12 +3305,17 @@ static void DispTransFileInfo(TRANSPACKET *Pkt, char *Title, int SkipButton, int
                        else if(Pkt->Type == TYPE_A)\r
                                SendDlgItemMessage(Pkt->hWndTrans, TRANS_MODE, WM_SETTEXT, 0, (LPARAM)MSGJPN120);\r
 \r
+                       // UTF-8対応\r
                        if(Pkt->KanjiCode == KANJI_NOCNV)\r
                                SendDlgItemMessage(Pkt->hWndTrans, TRANS_KANJI, WM_SETTEXT, 0, (LPARAM)MSGJPN121);\r
+                       else if(Pkt->KanjiCode == KANJI_SJIS)\r
+                               SendDlgItemMessage(Pkt->hWndTrans, TRANS_KANJI, WM_SETTEXT, 0, (LPARAM)MSGJPN305);\r
                        else if(Pkt->KanjiCode == KANJI_JIS)\r
                                SendDlgItemMessage(Pkt->hWndTrans, TRANS_KANJI, WM_SETTEXT, 0, (LPARAM)MSGJPN122);\r
                        else if(Pkt->KanjiCode == KANJI_EUC)\r
                                SendDlgItemMessage(Pkt->hWndTrans, TRANS_KANJI, WM_SETTEXT, 0, (LPARAM)MSGJPN123);\r
+                       else if(Pkt->KanjiCode == KANJI_UTF8N)\r
+                               SendDlgItemMessage(Pkt->hWndTrans, TRANS_KANJI, WM_SETTEXT, 0, (LPARAM)MSGJPN306);\r
                }\r
                else\r
                {\r
@@ -2302,17 +3329,17 @@ static void DispTransFileInfo(TRANSPACKET *Pkt, char *Title, int SkipButton, int
 }\r
 \r
 \r
-/*----- PASV\83R\83}\83\93\83h\82Ì\96ß\82è\92l\82©\82ç\83A\83h\83\8c\83X\82Æ\83|\81[\83g\94Ô\8d\86\82ð\92\8a\8fo --------------------\r
+/*----- PASVコマンドの戻り値からアドレスとポート番号を抽出 --------------------\r
 *\r
 *      Parameter\r
-*              char *Str : PASV\83R\83}\83\93\83h\82Ì\83\8a\83v\83\89\83C\r
-*              char *Adrs : \83A\83h\83\8c\83X\82Ì\83R\83s\81[\90æ ("www.xxx.yyy.zzz")\r
-*              int *Port : \83|\81[\83g\94Ô\8d\86\82ð\83Z\83b\83g\82·\82é\83\8f\81[\83N\r
-*              int Max : \83A\83h\83\8c\83X\95\8e\9a\97ñ\82Ì\8dÅ\91å\92·\r
+*              char *Str : PASVコマンドのリプライ\r
+*              char *Adrs : アドレスのコピー先 ("www.xxx.yyy.zzz")\r
+*              int *Port : ポート番号をセットするワーク\r
+*              int Max : ã\82¢ã\83\89ã\83¬ã\82¹æ\96\87å­\97å\88\97ã\81®æ\9c\80大é\95·\r
 *\r
 *      Return Value\r
-*              int \83X\83e\81[\83^\83X\r
-*                      SUCCESS/FAIL\r
+*              int ステータス\r
+*                      FFFTP_SUCCESS/FFFTP_FAIL\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int GetAdrsAndPort(char *Str, char *Adrs, int *Port, int Max)\r
@@ -2321,7 +3348,7 @@ static int GetAdrsAndPort(char *Str, char *Adrs, int *Port, int Max)
        char *Btm;\r
        int Sts;\r
 \r
-       Sts = FAIL;\r
+       Sts = FFFTP_FAIL;\r
 \r
        Pos = strchr(Str, '(');\r
        if(Pos != NULL)\r
@@ -2354,7 +3381,7 @@ static int GetAdrsAndPort(char *Str, char *Adrs, int *Port, int Max)
                                                        {\r
                                                                Btm++;\r
                                                                *Port = (atoi(Pos) * 0x100) + atoi(Btm);\r
-                                                               Sts = SUCCESS;\r
+                                                               Sts = FFFTP_SUCCESS;\r
                                                        }\r
                                                }\r
                                        }\r
@@ -2366,13 +3393,13 @@ static int GetAdrsAndPort(char *Str, char *Adrs, int *Port, int Max)
 }\r
 \r
 \r
-/*----- Windows\82Ì\83X\83y\83V\83\83\83\8b\83f\83o\83C\83X\82©\82Ç\82¤\82©\82ð\95Ô\82· -----------------------------\r
+/*----- Windowsのスペシャルデバイスかどうかを返す -----------------------------\r
 *\r
 *      Parameter\r
-*              char *Fname : \83t\83@\83C\83\8b\96¼\r
+*              char *Fname : ファイル名\r
 *\r
 *      Return Value\r
-*              int \83X\83e\81[\83^\83X (YES/NO)\r
+*              int ステータス (YES/NO)\r
 *----------------------------------------------------------------------------*/\r
 \r
 static int IsSpecialDevice(char *Fname)\r
@@ -2380,20 +3407,34 @@ static int IsSpecialDevice(char *Fname)
        int Sts;\r
 \r
        Sts = NO;\r
-       if((_stricmp(Fname, "CON") == 0) ||\r
-          (_stricmp(Fname, "PRN") == 0) ||\r
-          (_stricmp(Fname, "AUX") == 0) ||\r
-          (_strnicmp(Fname, "CON.", 4) == 0) ||\r
-          (_strnicmp(Fname, "PRN.", 4) == 0) ||\r
-          (_strnicmp(Fname, "AUX.", 4) == 0))\r
+       // 比較が不完全なバグ修正\r
+//     if((_stricmp(Fname, "CON") == 0) ||\r
+//        (_stricmp(Fname, "PRN") == 0) ||\r
+//        (_stricmp(Fname, "AUX") == 0) ||\r
+//        (_strnicmp(Fname, "CON.", 4) == 0) ||\r
+//        (_strnicmp(Fname, "PRN.", 4) == 0) ||\r
+//        (_strnicmp(Fname, "AUX.", 4) == 0))\r
+//     {\r
+//             Sts = YES;\r
+//     }\r
+       if(_strnicmp(Fname, "AUX", 3) == 0|| _strnicmp(Fname, "CON", 3) == 0 || _strnicmp(Fname, "NUL", 3) == 0 || _strnicmp(Fname, "PRN", 3) == 0)\r
        {\r
-               Sts = YES;\r
+               if(*(Fname + 3) == '\0' || *(Fname + 3) == '.')\r
+                       Sts = YES;\r
+       }\r
+       else if(_strnicmp(Fname, "COM", 3) == 0 || _strnicmp(Fname, "LPT", 3) == 0)\r
+       {\r
+               if(isdigit(*(Fname + 3)) != 0)\r
+               {\r
+                       if(*(Fname + 4) == '\0' || *(Fname + 4) == '.')\r
+                               Sts = YES;\r
+               }\r
        }\r
        return(Sts);\r
 }\r
 \r
 \r
-/*----- \83~\83\89\81[\83\8a\83\93\83O\82Å\82Ì\83t\83@\83C\83\8b\8dí\8f\9c\8am\94F --------------------------------------\r
+/*----- ミラーリングでのファイル削除確認 --------------------------------------\r
 *\r
 *      Parameter\r
 *              int Cur\r
@@ -2428,13 +3469,13 @@ static int MirrorDelNotify(int Cur, int Notify, TRANSPACKET *Pkt)
 }\r
 \r
 \r
-/*----- \83~\83\89\81[\83\8a\83\93\83O\82Å\82Ì\83t\83@\83C\83\8b\8dí\8f\9c\83_\83C\83A\83\8d\83O\82Ì\83R\81[\83\8b\83o\83b\83N ------------------\r
+/*----- ミラーリングでのファイル削除ダイアログのコールバック ------------------\r
 *\r
 *      Parameter\r
-*              HWND hDlg : \83E\83C\83\93\83h\83E\83n\83\93\83h\83\8b\r
-*              UINT message : \83\81\83b\83Z\81[\83W\94Ô\8d\86\r
-*              WPARAM wParam : \83\81\83b\83Z\81[\83W\82Ì WPARAM \88ø\90\94\r
-*              LPARAM lParam : \83\81\83b\83Z\81[\83W\82Ì LPARAM \88ø\90\94\r
+*              HWND hDlg : ウインドウハンドル\r
+*              UINT message : メッセージ番号\r
+*              WPARAM wParam : メッセージの WPARAM 引数\r
+*              LPARAM lParam : メッセージの LPARAM 引数\r
 *\r
 *      Return Value\r
 *              BOOL TRUE/FALSE\r
@@ -2507,13 +3548,13 @@ static void SetErrorMsg(char *fmt, ...)
 \r
 \r
 \r
-/*----- \83_\83E\83\93\83\8d\81[\83h\8e\9e\82Ì\95s\90³\82È\83p\83X\82ð\83`\83F\83b\83N ----------------------------------\r
+/*----- ダウンロード時の不正なパスをチェック ----------------------------------\r
 *\r
 *      Parameter\r
-*              TRANSPACKET *packet : \83_\83E\83\93\83\8d\81[\83h\8fî\95ñ\r
+*              TRANSPACKET *packet : ダウンロード情報\r
 *\r
 *      Return Value\r
-*              int YES=\95s\90³\82È\83p\83X/NO=\96â\91è\82È\82¢\83p\83X\r
+*              int YES=不正なパス/NO=問題ないパス\r
 *----------------------------------------------------------------------------*/\r
 int CheckPathViolation(TRANSPACKET *packet)\r
 {\r