OSDN Git Service

Add emulation for an old conversion method between UTF-8 and UTF-16.
[ffftp/ffftp.git] / filelist.c
1 /*=============================================================================\r
2 *\r
3 *                                                               ファイル一覧\r
4 *\r
5 ===============================================================================\r
6 / Copyright (C) 1997-2007 Sota. All rights reserved.\r
7 /\r
8 / Redistribution and use in source and binary forms, with or without \r
9 / modification, are permitted provided that the following conditions \r
10 / are met:\r
11 /\r
12 /  1. Redistributions of source code must retain the above copyright \r
13 /     notice, this list of conditions and the following disclaimer.\r
14 /  2. Redistributions in binary form must reproduce the above copyright \r
15 /     notice, this list of conditions and the following disclaimer in the \r
16 /     documentation and/or other materials provided with the distribution.\r
17 /\r
18 / THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR \r
19 / IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES \r
20 / OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. \r
21 / IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, \r
22 / INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, \r
23 / BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF \r
24 / USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON \r
25 / ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT \r
26 / (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF \r
27 / THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\r
28 /============================================================================*/\r
29 \r
30 // UTF-8対応\r
31 //#define _WIN32_WINNT  0x400\r
32 \r
33 #define STRICT\r
34 // IPv6対応\r
35 #include <winsock2.h>\r
36 #include <windows.h>\r
37 #include <stdio.h>\r
38 #include <stdlib.h>\r
39 #include <string.h>\r
40 #include <ctype.h>\r
41 #include <time.h>\r
42 #include <mbstring.h>\r
43 #include <malloc.h>\r
44 #include <windowsx.h>\r
45 #include <commctrl.h>\r
46 #include <sys/types.h>\r
47 #include <sys/stat.h>\r
48 #include <direct.h>\r
49 \r
50 #include "common.h"\r
51 #include "resource.h"\r
52 \r
53 #include <htmlhelp.h>\r
54 #include "helpid.h"\r
55 \r
56 #include <shlobj.h>\r
57 #include "OleDragDrop.h"\r
58 #include "common.h"\r
59 \r
60 // UTF-8対応\r
61 #undef __MBSWRAPPER_H__\r
62 #include "mbswrapper.h"\r
63 \r
64 #define BUF_SIZE                256\r
65 #define CF_CNT 2\r
66 #define WM_DRAGDROP             (WM_APP + 100)\r
67 #define WM_GETDATA              (WM_APP + 101)\r
68 #define WM_DRAGOVER             (WM_APP + 102)\r
69 \r
70 \r
71 /*===== ファイルリストのリスト用ストラクチャ =====*/\r
72 \r
73 typedef struct {\r
74         FILELIST *Top;                  /* ファイルリストの先頭 */\r
75         int Files;                              /* ファイルの数 */\r
76 } FLISTANCHOR;\r
77 \r
78 /*===== プロトタイプ =====*/\r
79 \r
80 static LRESULT CALLBACK LocalWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);\r
81 static LRESULT CALLBACK RemoteWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);\r
82 static LRESULT FileListCommonWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);\r
83 static void AddDispFileList(FLISTANCHOR *Anchor, char *Name, FILETIME *Time, LONGLONG Size, int Attr, int Type, int Link, char *Owner, int InfoExist, int Win);\r
84 static void EraseDispFileList(FLISTANCHOR *Anchor);\r
85 static void DispFileList2View(HWND hWnd, FLISTANCHOR *Anchor);\r
86 // ファイルアイコン表示対応\r
87 //static void AddListView(HWND hWnd, int Pos, char *Name, int Type, LONGLONG Size, FILETIME *Time, int Attr, char *Owner, int Link, int InfoExist);\r
88 static void AddListView(HWND hWnd, int Pos, char *Name, int Type, LONGLONG Size, FILETIME *Time, int Attr, char *Owner, int Link, int InfoExist, int ImageId);\r
89 // 64ビット対応\r
90 //static BOOL CALLBACK SelectDialogCallBack(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam);\r
91 static INT_PTR CALLBACK SelectDialogCallBack(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam);\r
92 static void DispListList(FILELIST *Pos, char *Title);\r
93 static void MakeRemoteTree1(char *Path, char *Cur, FILELIST **Base, int *CancelCheckWork);\r
94 static void MakeRemoteTree2(char *Path, char *Cur, FILELIST **Base, int *CancelCheckWork);\r
95 static void CopyTmpListToFileList(FILELIST **Base, FILELIST *List);\r
96 static int GetListOneLine(char *Buf, int Max, FILE *Fd);\r
97 static int MakeDirPath(char *Str, int ListType, char *Path, char *Dir);\r
98 static void MakeLocalTree(char *Path, FILELIST **Base);\r
99 static void AddFileList(FILELIST *Pkt, FILELIST **Base);\r
100 static int AnalizeFileInfo(char *Str);\r
101 static int CheckUnixType(char *Str, char *Tmp, int Add1, int Add2, int Day);\r
102 static int CheckHHMMformat(char *Str);\r
103 static int CheckYYMMDDformat(char *Str, char Sym, int Dig3);\r
104 static int CheckYYYYMMDDformat(char *Str, char Sym);\r
105 static int ResolvFileInfo(char *Str, int ListType, char *Fname, LONGLONG *Size, FILETIME *Time, int *Attr, char *Owner, int *Link, int *InfoExist);\r
106 static int FindField(char *Str, char *Buf, int Num, int ToLast);\r
107 // MLSD対応\r
108 static int FindField2(char *Str, char *Buf, char Separator, int Num, int ToLast);\r
109 static void GetMonth(char *Str, WORD *Month, WORD *Day);\r
110 static int GetYearMonthDay(char *Str, WORD *Year, WORD *Month, WORD *Day);\r
111 static int GetHourAndMinute(char *Str, WORD *Hour, WORD *Minute);\r
112 static int GetVMSdate(char *Str, WORD *Year, WORD *Month, WORD *Day);\r
113 static int CheckSpecialDirName(char *Fname);\r
114 static int AskFilterStr(char *Fname, int Type);\r
115 // 64ビット対応\r
116 //static BOOL CALLBACK FilterWndProc(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam);\r
117 static INT_PTR CALLBACK FilterWndProc(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam);\r
118 static int atoi_n(const char *Str, int Len);\r
119 \r
120 /*===== 外部参照 =====*/\r
121 \r
122 extern int SepaWidth;\r
123 extern int RemoteWidth;\r
124 extern int ListHeight;\r
125 extern char FilterStr[FILTER_EXT_LEN+1];\r
126 extern HWND hHelpWin;\r
127 \r
128 /* 設定値 */\r
129 extern int LocalWidth;\r
130 extern int LocalTabWidth[4];\r
131 extern int RemoteTabWidth[6];\r
132 extern char UserMailAdrs[USER_MAIL_LEN+1];\r
133 extern HFONT ListFont;\r
134 extern int ListType;\r
135 extern int FindMode;\r
136 extern int DotFile;\r
137 extern int DispIgnoreHide;\r
138 extern int DispDrives;\r
139 extern int MoveMode;\r
140 \r
141 /*===== ローカルなワーク =====*/\r
142 \r
143 static HWND hWndListLocal = NULL;\r
144 static HWND hWndListRemote = NULL;\r
145 \r
146 static WNDPROC LocalProcPtr;\r
147 static WNDPROC RemoteProcPtr;\r
148 \r
149 static HIMAGELIST ListImg = NULL;\r
150 // ファイルアイコン表示対応\r
151 static HIMAGELIST ListImgFileIcon = NULL;\r
152 \r
153 static char FindStr[40+1] = { "*" };            /* 検索文字列 */\r
154 static int IgnoreNew = NO;\r
155 static int IgnoreOld = NO;\r
156 static int IgnoreExist = NO;\r
157 \r
158 static int Dragging = NO;\r
159 \r
160 static int StratusMode;                 /* 0=ファイル, 1=ディレクトリ, 2=リンク */\r
161 \r
162 \r
163 // リモートファイルリスト (2007.9.3 yutaka)\r
164 static FILELIST *remoteFileListBase;\r
165 static FILELIST *remoteFileListBaseNoExpand;\r
166 static char remoteFileDir[FMAX_PATH + 1];\r
167 \r
168 \r
169 /*----- ファイルリストウインドウを作成する ------------------------------------\r
170 *\r
171 *       Parameter\r
172 *               HWND hWnd : 親ウインドウのウインドウハンドル\r
173 *               HINSTANCE hInst : インスタンスハンドル\r
174 *\r
175 *       Return Value\r
176 *               int ステータス\r
177 *                       FFFTP_SUCCESS/FFFTP_FAIL\r
178 *----------------------------------------------------------------------------*/\r
179 \r
180 int MakeListWin(HWND hWnd, HINSTANCE hInst)\r
181 {\r
182         int Sts;\r
183         LV_COLUMN LvCol;\r
184         long Tmp;\r
185 \r
186         // 変数が未初期化のバグ修正\r
187         memset(&LvCol, 0, sizeof(LV_COLUMN));\r
188 \r
189         /*===== ローカル側のリストビュー =====*/\r
190 \r
191         hWndListLocal = CreateWindowEx(/*WS_EX_STATICEDGE*/WS_EX_CLIENTEDGE,\r
192                         WC_LISTVIEWA, NULL,\r
193                         WS_CHILD | /*WS_BORDER | */LVS_REPORT | LVS_SHOWSELALWAYS,\r
194                         0, TOOLWIN_HEIGHT*2, LocalWidth, ListHeight,\r
195                         GetMainHwnd(), (HMENU)1500, hInst, NULL);\r
196 \r
197         if(hWndListLocal != NULL)\r
198         {\r
199                 // 64ビット対応\r
200 //              LocalProcPtr = (WNDPROC)SetWindowLong(hWndListLocal, GWL_WNDPROC, (LONG)LocalWndProc);\r
201                 LocalProcPtr = (WNDPROC)SetWindowLongPtr(hWndListLocal, GWLP_WNDPROC, (LONG_PTR)LocalWndProc);\r
202 \r
203             Tmp = SendMessage(hWndListLocal, LVM_GETEXTENDEDLISTVIEWSTYLE, 0, 0);\r
204             Tmp |= LVS_EX_FULLROWSELECT;\r
205             SendMessage(hWndListLocal, LVM_SETEXTENDEDLISTVIEWSTYLE, 0, (LPARAM)Tmp);\r
206 \r
207                 if(ListFont != NULL)\r
208                         SendMessage(hWndListLocal, WM_SETFONT, (WPARAM)ListFont, MAKELPARAM(TRUE, 0));\r
209 \r
210                 ListImg = ImageList_LoadBitmap(hInst, MAKEINTRESOURCE(dirattr_bmp), 16, 9, RGB(255,0,0));\r
211                 SendMessage(hWndListLocal, LVM_SETIMAGELIST, LVSIL_SMALL, (LPARAM)ListImg);\r
212                 ShowWindow(hWndListLocal, SW_SHOW);\r
213 \r
214                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;\r
215                 LvCol.cx = LocalTabWidth[0];\r
216                 LvCol.pszText = MSGJPN038;\r
217                 LvCol.iSubItem = 0;\r
218                 SendMessage(hWndListLocal, LVM_INSERTCOLUMN, 0, (LPARAM)&LvCol);\r
219 \r
220                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;\r
221                 LvCol.cx = LocalTabWidth[1];\r
222                 LvCol.pszText = MSGJPN039;\r
223                 LvCol.iSubItem = 1;\r
224                 SendMessage(hWndListLocal, LVM_INSERTCOLUMN, 1, (LPARAM)&LvCol);\r
225 \r
226                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM | LVCF_FMT;\r
227                 LvCol.fmt = LVCFMT_RIGHT;\r
228                 LvCol.cx = LocalTabWidth[2];\r
229                 LvCol.pszText = MSGJPN040;\r
230                 LvCol.iSubItem = 2;\r
231                 SendMessage(hWndListLocal, LVM_INSERTCOLUMN, 2, (LPARAM)&LvCol);\r
232 \r
233                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;\r
234                 LvCol.cx = LocalTabWidth[3];\r
235                 LvCol.pszText = MSGJPN041;\r
236                 LvCol.iSubItem = 3;\r
237                 SendMessage(hWndListLocal, LVM_INSERTCOLUMN, 3, (LPARAM)&LvCol);\r
238         }\r
239 \r
240         /*===== ホスト側のリストビュー =====*/\r
241 \r
242         hWndListRemote = CreateWindowEx(/*WS_EX_STATICEDGE*/WS_EX_CLIENTEDGE,\r
243                         WC_LISTVIEWA, NULL,\r
244                         WS_CHILD | /*WS_BORDER | */LVS_REPORT | LVS_SHOWSELALWAYS,\r
245                         LocalWidth + SepaWidth, TOOLWIN_HEIGHT*2, RemoteWidth, ListHeight,\r
246                         GetMainHwnd(), (HMENU)1500, hInst, NULL);\r
247 \r
248         if(hWndListRemote != NULL)\r
249         {\r
250                 // 64ビット対応\r
251 //              RemoteProcPtr = (WNDPROC)SetWindowLong(hWndListRemote, GWL_WNDPROC, (LONG)RemoteWndProc);\r
252                 RemoteProcPtr = (WNDPROC)SetWindowLongPtr(hWndListRemote, GWLP_WNDPROC, (LONG_PTR)RemoteWndProc);\r
253 \r
254             Tmp = SendMessage(hWndListRemote, LVM_GETEXTENDEDLISTVIEWSTYLE, 0, 0);\r
255             Tmp |= LVS_EX_FULLROWSELECT;\r
256             SendMessage(hWndListRemote, LVM_SETEXTENDEDLISTVIEWSTYLE, 0, (LPARAM)Tmp);\r
257 \r
258                 if(ListFont != NULL)\r
259                         SendMessage(hWndListRemote, WM_SETFONT, (WPARAM)ListFont, MAKELPARAM(TRUE, 0));\r
260 \r
261                 SendMessage(hWndListRemote, LVM_SETIMAGELIST, LVSIL_SMALL, (LPARAM)ListImg);\r
262                 ShowWindow(hWndListRemote, SW_SHOW);\r
263 \r
264                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;\r
265                 LvCol.cx = RemoteTabWidth[0];\r
266                 LvCol.pszText = MSGJPN042;\r
267                 LvCol.iSubItem = 0;\r
268                 SendMessage(hWndListRemote, LVM_INSERTCOLUMN, 0, (LPARAM)&LvCol);\r
269 \r
270                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;\r
271                 LvCol.cx = RemoteTabWidth[1];\r
272                 LvCol.pszText = MSGJPN043;\r
273                 LvCol.iSubItem = 1;\r
274                 SendMessage(hWndListRemote, LVM_INSERTCOLUMN, 1, (LPARAM)&LvCol);\r
275 \r
276                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM | LVCF_FMT;\r
277                 LvCol.fmt = LVCFMT_RIGHT;\r
278                 LvCol.cx = RemoteTabWidth[2];\r
279                 LvCol.pszText = MSGJPN044;\r
280                 LvCol.iSubItem = 2;\r
281                 SendMessage(hWndListRemote, LVM_INSERTCOLUMN, 2, (LPARAM)&LvCol);\r
282 \r
283                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;\r
284                 LvCol.cx = RemoteTabWidth[3];\r
285                 LvCol.pszText = MSGJPN045;\r
286                 LvCol.iSubItem = 3;\r
287                 SendMessage(hWndListRemote, LVM_INSERTCOLUMN, 3, (LPARAM)&LvCol);\r
288 \r
289                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;\r
290                 LvCol.cx = RemoteTabWidth[4];\r
291                 LvCol.pszText = MSGJPN046;\r
292                 LvCol.iSubItem = 4;\r
293                 SendMessage(hWndListRemote, LVM_INSERTCOLUMN, 4, (LPARAM)&LvCol);\r
294 \r
295                 LvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;\r
296                 LvCol.cx = RemoteTabWidth[5];\r
297                 LvCol.pszText = MSGJPN047;\r
298                 LvCol.iSubItem = 5;\r
299                 SendMessage(hWndListRemote, LVM_INSERTCOLUMN, 5, (LPARAM)&LvCol);\r
300         }\r
301 \r
302         Sts = FFFTP_SUCCESS;\r
303         if((hWndListLocal == NULL) ||\r
304            (hWndListRemote == NULL))\r
305         {\r
306                 Sts = FFFTP_FAIL;\r
307         }\r
308         return(Sts);\r
309 }\r
310 \r
311 \r
312 /*----- ファイルリストウインドウを削除 ----------------------------------------\r
313 *\r
314 *       Parameter\r
315 *               なし\r
316 *\r
317 *       Return Value\r
318 *               なし\r
319 *----------------------------------------------------------------------------*/\r
320 \r
321 void DeleteListWin(void)\r
322 {\r
323 //      if(ListImg != NULL)\r
324 //              ImageList_Destroy(ListImg);\r
325         if(hWndListLocal != NULL)\r
326                 DestroyWindow(hWndListLocal);\r
327         if(hWndListRemote != NULL)\r
328                 DestroyWindow(hWndListRemote);\r
329         return;\r
330 }\r
331 \r
332 \r
333 /*----- ローカル側のファイルリストのウインドウハンドルを返す ------------------\r
334 *\r
335 *       Parameter\r
336 *               なし\r
337 *\r
338 *       Return Value\r
339 *               HWND ウインドウハンドル\r
340 *----------------------------------------------------------------------------*/\r
341 \r
342 HWND GetLocalHwnd(void)\r
343 {\r
344         return(hWndListLocal);\r
345 }\r
346 \r
347 \r
348 /*----- ホスト側のファイルリストのウインドウハンドルを返す --------------------\r
349 *\r
350 *       Parameter\r
351 *               なし\r
352 *\r
353 *       Return Value\r
354 *               HWND ウインドウハンドル\r
355 *----------------------------------------------------------------------------*/\r
356 \r
357 HWND GetRemoteHwnd(void)\r
358 {\r
359         return(hWndListRemote);\r
360 }\r
361 \r
362 \r
363 /*----- ローカル側のファイルリストウインドウのメッセージ処理 ------------------\r
364 *\r
365 *       Parameter\r
366 *               HWND hWnd : ウインドウハンドル\r
367 *               UINT message  : メッセージ番号\r
368 *               WPARAM wParam : メッセージの WPARAM 引数\r
369 *               LPARAM lParam : メッセージの LPARAM 引数\r
370 *\r
371 *       Return Value\r
372 *               メッセージに対応する戻り値\r
373 *----------------------------------------------------------------------------*/\r
374 \r
375 static LRESULT CALLBACK LocalWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)\r
376 {\r
377         return(FileListCommonWndProc(hWnd, message, wParam, lParam));\r
378 }\r
379 \r
380 \r
381 /*----- ホスト側のファイルリストウインドウのメッセージ処理 --------------------\r
382 *\r
383 *       Parameter\r
384 *               HWND hWnd : ウインドウハンドル\r
385 *               UINT message  : メッセージ番号\r
386 *               WPARAM wParam : メッセージの WPARAM 引数\r
387 *               LPARAM lParam : メッセージの LPARAM 引数\r
388 *\r
389 *       Return Value\r
390 *               メッセージに対応する戻り値\r
391 *----------------------------------------------------------------------------*/\r
392 \r
393 static LRESULT CALLBACK RemoteWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)\r
394 {\r
395         return(FileListCommonWndProc(hWnd, message, wParam, lParam));\r
396 }\r
397 \r
398 \r
399 // ダイアログプロシージャ\r
400 static BOOL CALLBACK doOleDlgProc(HWND hDlg, UINT msg, WPARAM wp, LPARAM lp)\r
401 {\r
402 #define TIMER_ID     (100)      // 作成するタイマの識別ID\r
403 #define TIMER_ELAPSE (100)       // WM_TIMERの発生間隔\r
404         MSG message;\r
405 \r
406         switch( msg ){\r
407         case WM_INITDIALOG:  // ダイアログボックスが作成されたとき\r
408                 SetTimer( hDlg, TIMER_ID, 0, NULL);\r
409                 return TRUE;\r
410 \r
411         case WM_TIMER:\r
412                 ShowWindow(hDlg, SW_HIDE);  // ダイアログは隠す\r
413 \r
414                 if (wp != TIMER_ID)\r
415                         break;\r
416 \r
417                 if (PeekMessage(&message, NULL, 0, 0, PM_REMOVE)) {\r
418                                 TranslateMessage(&message);\r
419                                 DispatchMessage(&message);\r
420 \r
421                 } else {\r
422                         if (AskTransferNow() == NO) {\r
423                                 EndDialog( hDlg, 0 );\r
424                                 return TRUE;\r
425                         }\r
426                 }\r
427 \r
428                 SetTimer( hDlg, TIMER_ID, TIMER_ELAPSE, NULL );\r
429                 return TRUE;\r
430 \r
431         case WM_COMMAND:     // ダイアログボックス内の何かが選択されたとき\r
432                 switch( LOWORD( wp ) ){\r
433 //              case IDOK:       // 「OK」ボタンが選択された\r
434                 case IDCANCEL:   // 「キャンセル」ボタンが選択された\r
435                         // ダイアログボックスを消す\r
436                         EndDialog( hDlg, 0 );\r
437                         break;\r
438                 }\r
439                 return TRUE;\r
440         }\r
441 \r
442         return FALSE;  // DefWindowProc()ではなく、FALSEを返すこと!\r
443 #undef TIMER_ID     \r
444 #undef TIMER_ELAPSE \r
445 }\r
446 \r
447 \r
448 static void doTransferRemoteFile(void)\r
449 {\r
450         FILELIST *FileListBase, *FileListBaseNoExpand, *pf;\r
451         int CancelFlg = NO;\r
452         char LocDir[FMAX_PATH+1];\r
453         char TmpDir[FMAX_PATH+1];\r
454         // 環境依存の不具合対策\r
455 //      char buf[32];\r
456         int i;\r
457         // 環境依存の不具合対策\r
458 //      DWORD pid;\r
459 \r
460         // すでにリモートから転送済みなら何もしない。(2007.9.3 yutaka)\r
461         if (remoteFileListBase != NULL)\r
462                 return;\r
463 \r
464         FileListBase = NULL;\r
465         MakeSelectedFileList(WIN_REMOTE, YES, NO, &FileListBase, &CancelFlg);\r
466         FileListBaseNoExpand = NULL;\r
467         MakeSelectedFileList(WIN_REMOTE, NO, NO, &FileListBaseNoExpand, &CancelFlg);\r
468 \r
469         // set temporary folder\r
470         AskLocalCurDir(LocDir, FMAX_PATH);\r
471 \r
472         // アプリを多重起動してもコンフリクトしないように、テンポラリフォルダ名にプロセスID\r
473         // を付加する。(2007.9.13 yutaka)\r
474         // 環境依存の不具合対策\r
475 //      GetTempPath(sizeof(TmpDir), TmpDir);\r
476 //      pid = GetCurrentProcessId();\r
477 //      _snprintf_s(buf, sizeof(buf), _TRUNCATE, "ffftp%d", pid);\r
478 //      strncat_s(TmpDir, sizeof(TmpDir), buf, _TRUNCATE);\r
479         GetAppTempPath(TmpDir);\r
480         _mkdir(TmpDir);\r
481         SetYenTail(TmpDir);\r
482         strcat(TmpDir, "file");\r
483         _mkdir(TmpDir);\r
484 #if 0\r
485         if (TmpDir[strlen(TmpDir) - 1] == '\\') {\r
486                 TmpDir[strlen(TmpDir) - 1] = '\0';\r
487         }\r
488 #endif\r
489 \r
490         // 既存のファイルを削除する\r
491         for (pf = FileListBase ; pf ; pf = pf->Next) {\r
492                 char fn[FMAX_PATH+1];\r
493 \r
494                 strncpy_s(fn, sizeof(fn), TmpDir, _TRUNCATE);\r
495                 strncat_s(fn, sizeof(fn), "\\", _TRUNCATE);\r
496                 strncat_s(fn, sizeof(fn), pf->File, _TRUNCATE);\r
497 \r
498                 remove(fn);\r
499         }\r
500 \r
501         // ダウンロード先をテンポラリに設定\r
502         SetLocalDirHist(TmpDir);\r
503 \r
504         // FFFTPにダウンロード要求を出し、ダウンロードの完了を待つ。\r
505         PostMessage(GetMainHwnd(), WM_COMMAND, MAKEWPARAM(MENU_DOWNLOAD, 0), 0);\r
506 \r
507         for (i = 0 ; i < 10 ; i++) {\r
508                 MSG msg;\r
509 \r
510                 if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE)) {\r
511                         TranslateMessage(&msg);\r
512                         DispatchMessage(&msg);\r
513 \r
514                 } else {\r
515                         // 転送スレッドが動き出したら抜ける。\r
516                         if (AskTransferNow() == YES)\r
517                                 break;\r
518                 }\r
519 \r
520                 Sleep(10);\r
521         }\r
522 \r
523         // OLE D&D中にメインウィンドウをユーザに操作させると、おかしくなるので、\r
524         // 隠しモーダルダイアログを作る。\r
525         // (2007.9.11 yutaka)\r
526         DialogBox(GetFtpInst(), MAKEINTRESOURCE(IDD_OLEDRAG), GetMainHwnd(), (DLGPROC)doOleDlgProc);\r
527 \r
528         // ダウンロード先を元に戻す\r
529         SetLocalDirHist(LocDir);\r
530         SetCurrentDirAsDirHist();\r
531 \r
532         remoteFileListBase = FileListBase;  // あとでフリーすること\r
533         remoteFileListBaseNoExpand = FileListBaseNoExpand;  // あとでフリーすること\r
534         strncpy_s(remoteFileDir, sizeof(remoteFileDir), TmpDir, _TRUNCATE);\r
535 \r
536 #if 0\r
537         // add temporary list\r
538         if (remoteFileListBase != NULL) {\r
539                 FILELIST *pf = remoteFileListBase;\r
540                 char fn[FMAX_PATH + 1];\r
541                 while (pf) {\r
542                         strncpy_s(fn, sizeof(fn), remoteFileDir, _TRUNCATE);\r
543                         strncat_s(fn, sizeof(fn), "\\", _TRUNCATE);\r
544                         strncat_s(fn, sizeof(fn), pf->File, _TRUNCATE);\r
545                         AddTempFileList(fn);\r
546                         pf = pf->Next;\r
547                 }\r
548         }\r
549 #endif\r
550 }\r
551 \r
552 \r
553 int isDirectory(char *fn)\r
554 {\r
555         struct _stat buf;\r
556 \r
557         if (_stat(fn, &buf) == 0) {\r
558                 if (buf.st_mode & _S_IFDIR) { // is directory\r
559                         return 1;\r
560                 }\r
561         }\r
562         return 0;\r
563 }\r
564 \r
565 // テンポラリのファイルおよびフォルダを削除する。\r
566 void doDeleteRemoteFile(void)\r
567 {\r
568         if (remoteFileListBase != NULL) {\r
569 #if 0\r
570                 int dirs = 0;\r
571                 int i, count;\r
572                 FILELIST *pf = remoteFileListBase;\r
573                 char fn[FMAX_PATH + 1];\r
574                 while (pf) {\r
575                         strncpy_s(fn, sizeof(fn), remoteFileDir, _TRUNCATE);\r
576                         strncat_s(fn, sizeof(fn), "\\", _TRUNCATE);\r
577                         strncat_s(fn, sizeof(fn), pf->File, _TRUNCATE);\r
578                         if (isDirectory(fn)) {\r
579                                 dirs++;\r
580                         } else {\r
581                                 remove(fn);\r
582                         }\r
583                         pf = pf->Next;\r
584                 }\r
585 \r
586                 count = 0;\r
587                 for (i = 0 ; i < 1000 ; i++) {\r
588                         pf = remoteFileListBase;\r
589                         while (pf) {\r
590                                 strncpy_s(fn, sizeof(fn), remoteFileDir, _TRUNCATE);\r
591                                 strncat_s(fn, sizeof(fn), "\\", _TRUNCATE);\r
592                                 strncat_s(fn, sizeof(fn), pf->File, _TRUNCATE);\r
593                                 if (isDirectory(fn)) {\r
594                                         if (_rmdir(fn) == 0) { // ディレクトリを消せたらカウントアップ\r
595                                                 count++;\r
596                                                 if (count >= dirs)  // すべて消せたら終わり\r
597                                                         goto skip;\r
598                                         }\r
599                                 }\r
600                                 pf = pf->Next;\r
601                         }\r
602                 }\r
603 skip:\r
604                 _rmdir(remoteFileDir);  // 自分で作ったディレクトリも消す\r
605 #else\r
606                 SHFILEOPSTRUCT FileOp = { NULL, FO_DELETE, remoteFileDir, NULL, \r
607                         FOF_SILENT | FOF_NOCONFIRMATION | FOF_NOERRORUI, \r
608                         FALSE, NULL, NULL };    \r
609                 SHFileOperation(&FileOp);\r
610 #endif\r
611 \r
612                 DeleteFileList(&remoteFileListBase);\r
613                 remoteFileListBase = NULL;\r
614         }\r
615 \r
616         if (remoteFileListBaseNoExpand != NULL) {\r
617                 DeleteFileList(&remoteFileListBaseNoExpand);\r
618                 remoteFileListBaseNoExpand = NULL;\r
619         }\r
620 }\r
621 \r
622 \r
623 // yutaka\r
624 // cf. http://www.nakka.com/lib/\r
625 /* ドロップファイルの作成 */\r
626 static HDROP APIPRIVATE CreateDropFileMem(char **FileName,int cnt,BOOL fWide)\r
627 {\r
628         HDROP hDrop;\r
629         LPDROPFILES lpDropFile;\r
630         wchar_t wbuf[BUF_SIZE];\r
631         int flen = 0;\r
632         int i;\r
633         \r
634         if(fWide == TRUE){\r
635                 /* ワイドキャラ */\r
636                 for(i = 0;i < cnt;i++){\r
637                         // UTF-8対応\r
638 //                      MultiByteToWideChar(CP_ACP,0,FileName[i],-1,wbuf,BUF_SIZE);\r
639 //                      flen += (wcslen(wbuf) + 1) * sizeof(wchar_t);\r
640                         flen += sizeof(wchar_t) * MtoW(NULL, 0, FileName[i], -1);\r
641                 }\r
642                 flen++;\r
643         }else{\r
644                 /* マルチバイト */\r
645                 for(i = 0;i < cnt;i++){\r
646                         // UTF-8対応\r
647 //                      flen += lstrlen(FileName[i]) + 1;\r
648                         MtoW(wbuf, BUF_SIZE, FileName[i], -1);\r
649                         flen += sizeof(char) * WtoA(NULL, 0, wbuf, -1);\r
650                 }\r
651         }\r
652 \r
653         hDrop = (HDROP)GlobalAlloc(GHND,sizeof(DROPFILES) + flen + 1);\r
654         if (hDrop == NULL){\r
655                 return NULL;\r
656         }\r
657 \r
658         lpDropFile = (LPDROPFILES) GlobalLock(hDrop);\r
659         lpDropFile->pFiles = sizeof(DROPFILES);         /* ファイル名のリストまでのオフセット */\r
660         lpDropFile->pt.x = 0;\r
661         lpDropFile->pt.y = 0;\r
662         lpDropFile->fNC = FALSE;\r
663         lpDropFile->fWide = fWide;                                      /* ワイドキャラの場合は TRUE */\r
664 \r
665         /* 構造体の後ろにファイル名のリストをコピーする。(ファイル名\0ファイル名\0ファイル名\0\0) */\r
666         if(fWide == TRUE){\r
667                 /* ワイドキャラ */\r
668                 wchar_t *buf;\r
669 \r
670                 buf = (wchar_t *)(&lpDropFile[1]);\r
671                 for(i = 0;i < cnt;i++){\r
672                         // UTF-8対応\r
673 //                      MultiByteToWideChar(CP_ACP,0,FileName[i],-1,wbuf,BUF_SIZE);\r
674 //                      wcscpy(buf,wbuf);\r
675 //                      buf += wcslen(wbuf) + 1;\r
676                         buf += MtoW(buf, BUF_SIZE, FileName[i], -1);\r
677                 }\r
678         }else{\r
679                 /* マルチバイト */\r
680                 char *buf;\r
681 \r
682                 buf = (char *)(&lpDropFile[1]);\r
683                 for(i = 0;i < cnt;i++){\r
684                         // UTF-8対応\r
685 //                      lstrcpy(buf,FileName[i]);\r
686 //                      buf += lstrlen(FileName[i]) + 1;\r
687                         MtoW(wbuf, BUF_SIZE, FileName[i], -1);\r
688                         buf += WtoA(buf, BUF_SIZE, wbuf, -1);\r
689                 }\r
690         }\r
691 \r
692         GlobalUnlock(hDrop);\r
693         return(hDrop);\r
694 }\r
695 \r
696 \r
697 // OLE D&Dを開始する \r
698 // (2007.8.30 yutaka)\r
699 static void doDragDrop(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)\r
700 {\r
701         UINT cf[CF_CNT];\r
702         POINT pt;\r
703         int ret;\r
704 \r
705         // テンポラリをきれいにする (2007.9.3 yutaka)\r
706         doDeleteRemoteFile();\r
707 \r
708         /* ドラッグ&ドロップの開始 */\r
709         cf[0] = CF_HDROP;\r
710         cf[1] = CF_HDROP;       /* ファイル */\r
711         if((ret = OLE_IDropSource_Start(hWnd,WM_GETDATA, WM_DRAGOVER, cf,1,DROPEFFECT_COPY | DROPEFFECT_MOVE | DROPEFFECT_LINK)) == DROPEFFECT_MOVE){\r
712         }\r
713 \r
714         // ドロップ先のアプリに WM_LBUTTONUP を飛ばす。\r
715         GetCursorPos(&pt);\r
716         ScreenToClient(hWnd, &pt);\r
717         PostMessage(hWnd,WM_LBUTTONUP,0,MAKELPARAM(pt.x,pt.y));\r
718 }\r
719 \r
720 \r
721 \r
722 /*----- ファイル一覧ウインドウの共通メッセージ処理 ----------------------------\r
723 *\r
724 *       Parameter\r
725 *               HWND hWnd : ウインドウハンドル\r
726 *               UINT message  : メッセージ番号\r
727 *               WPARAM wParam : メッセージの WPARAM 引数\r
728 *               LPARAM lParam : メッセージの LPARAM 引数\r
729 *\r
730 *       Return Value\r
731 *               メッセージに対応する戻り値\r
732 *----------------------------------------------------------------------------*/\r
733 \r
734 static LRESULT FileListCommonWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)\r
735 {\r
736         POINT Point;\r
737         HWND hWndPnt;\r
738         HWND hWndParent;\r
739         static HCURSOR hCsrDrg;\r
740         static HCURSOR hCsrNoDrg;\r
741         static POINT DragPoint;\r
742         static HWND hWndDragStart;\r
743         static int RemoteDropFileIndex = -1;\r
744         int Win;\r
745         HWND hWndDst;\r
746         WNDPROC ProcPtr;\r
747         HWND hWndHistEdit;\r
748 \r
749         Win = WIN_LOCAL;\r
750         hWndDst = hWndListRemote;\r
751         ProcPtr = LocalProcPtr;\r
752         hWndHistEdit = GetLocalHistEditHwnd();\r
753         if(hWnd == hWndListRemote)\r
754         {\r
755                 Win = WIN_REMOTE;\r
756                 hWndDst = hWndListLocal;\r
757                 ProcPtr = RemoteProcPtr;\r
758                 hWndHistEdit = GetRemoteHistEditHwnd();\r
759         }\r
760 \r
761         switch (message)\r
762         {\r
763         case WM_SYSKEYDOWN:\r
764                         if (wParam == 'D') {    // Alt+D\r
765                                 SetFocus(hWndHistEdit);\r
766                                 break;\r
767                         }\r
768                         EraseListViewTips();\r
769                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
770 \r
771         case WM_KEYDOWN:\r
772                         if(wParam == 0x09)\r
773                         {\r
774                                 SetFocus(hWndDst);\r
775                                 break;\r
776                         }\r
777                         EraseListViewTips();\r
778                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
779 \r
780                 case WM_SETFOCUS :\r
781                         SetFocusHwnd(hWnd);\r
782                         MakeButtonsFocus();\r
783                         DispCurrentWindow(Win);\r
784                         DispSelectedSpace();\r
785                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
786 \r
787                 case WM_KILLFOCUS :\r
788                         EraseListViewTips();\r
789                         MakeButtonsFocus();\r
790                         DispCurrentWindow(-1);\r
791                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
792 \r
793                 case WM_DROPFILES :\r
794                         // 同時接続対応\r
795                         if(AskUserOpeDisabled() == YES)\r
796                                 break;\r
797                         // ドラッグ中は処理しない。ドラッグ後にWM_LBUTTONDOWNが飛んでくるため、そこで処理する。\r
798                         if (Dragging == YES) \r
799                                 return (FALSE);\r
800 \r
801                         if(hWnd == hWndListRemote)\r
802                         {\r
803                                 if(AskConnecting() == YES)\r
804                                         UploadDragProc(wParam);\r
805                         }\r
806                         else if(hWnd == hWndListLocal)\r
807                         {\r
808                                 ChangeDirDropFileProc(wParam);\r
809                         }\r
810                         break;\r
811 \r
812                 case WM_LBUTTONDOWN :\r
813                         EraseListViewTips();\r
814                         SetFocus(hWnd);\r
815                         DragPoint.x = LOWORD(lParam);\r
816                         DragPoint.y = HIWORD(lParam);\r
817                         hWndDragStart = hWnd;\r
818                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
819                         break;\r
820 \r
821                 case WM_LBUTTONUP :\r
822                         if(Dragging == YES)\r
823                         {\r
824                                 Dragging = NO;\r
825                                 ReleaseCapture();\r
826                                 hCsrDrg = LoadCursor(NULL, IDC_ARROW);\r
827                                 SetCursor(hCsrDrg);\r
828 \r
829                                 // 同時接続対応\r
830                                 if(AskUserOpeDisabled() == YES)\r
831                                         break;\r
832                                 Point.x = (long)(short)LOWORD(lParam);\r
833                                 Point.y = (long)(short)HIWORD(lParam);\r
834                                 ClientToScreen(hWnd, &Point);\r
835                                 hWndPnt = WindowFromPoint(Point);\r
836                                 if(hWndPnt == hWndDst)  // local <-> remote \r
837                                 {\r
838                                         if(hWndPnt == hWndListRemote) {\r
839                                                 PostMessage(GetMainHwnd(), WM_COMMAND, MAKEWPARAM(MENU_UPLOAD, 0), 0);\r
840                                         } else if(hWndPnt == hWndListLocal) {\r
841                                                 PostMessage(GetMainHwnd(), WM_COMMAND, MAKEWPARAM(MENU_DOWNLOAD, 0), 0);\r
842                                         }\r
843                                 } else { // 同一ウィンドウ内の場合 (yutaka)\r
844                                         if (hWndDragStart == hWndListRemote && hWndPnt == hWndListRemote) {\r
845                                                 // remote <-> remoteの場合は、サーバでのファイルの移動を行う。(2007.9.5 yutaka)\r
846                                                 if (RemoteDropFileIndex != -1) {\r
847                                                         ListView_SetItemState(hWnd, RemoteDropFileIndex, 0, LVIS_DROPHILITED);\r
848                                                         MoveRemoteFileProc(RemoteDropFileIndex);\r
849                                                 }\r
850 \r
851                                         }\r
852 \r
853                                 }\r
854                         }\r
855                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
856 \r
857                 case WM_DRAGDROP:  \r
858                         // OLE D&Dを開始する (yutaka)\r
859                         doDragDrop(hWnd, message, wParam, lParam);\r
860                         return (TRUE);\r
861                         break;\r
862  \r
863                 case WM_GETDATA:  // ファイルのパスをD&D先のアプリへ返す (yutaka)\r
864                         switch(wParam)\r
865                         {\r
866                         case CF_HDROP:          /* ファイル */\r
867                                 {\r
868                                         OSVERSIONINFO os_info;\r
869                                         BOOL NTFlag = FALSE;\r
870                                         char **FileNameList;\r
871                                         int filelen;\r
872                                         int i, j, filenum = 0;\r
873  \r
874                                         FILELIST *FileListBase, *FileListBaseNoExpand, *pf;\r
875                                         int CancelFlg = NO;\r
876                                         char LocDir[FMAX_PATH+1];\r
877                                         char *PathDir;\r
878  \r
879                                         // 変数が未初期化のバグ修正\r
880                                         FileListBaseNoExpand = NULL;\r
881                                         // ローカル側で選ばれているファイルをFileListBaseに登録\r
882                                         if (hWndDragStart == hWndListLocal) {\r
883                                                 AskLocalCurDir(LocDir, FMAX_PATH);\r
884                                                 PathDir = LocDir;\r
885  \r
886                                                 FileListBase = NULL;\r
887                                                 // ローカル側からアプリケーションにD&Dできないバグ修正\r
888 //                                              MakeSelectedFileList(WIN_LOCAL, YES, NO, &FileListBase, &CancelFlg);                    \r
889                                                 MakeSelectedFileList(WIN_LOCAL, NO, NO, &FileListBase, &CancelFlg);                     \r
890                                                 FileListBaseNoExpand = FileListBase;\r
891  \r
892                                         } else if (hWndDragStart == hWndListRemote) {\r
893                                                 GetCursorPos(&Point);\r
894                                                 hWndPnt = WindowFromPoint(Point);\r
895                                                 hWndParent = GetParent(hWndPnt);\r
896                                                 if (hWndPnt == hWndListRemote || hWndPnt == hWndListLocal ||\r
897                                                         hWndParent == hWndListRemote || hWndParent == hWndListLocal) {\r
898                                                         FileListBase = NULL;\r
899  \r
900                                                 } else {\r
901                                                         // 選択されているリモートファイルのリストアップ\r
902                                                         // このタイミングでリモートからローカルの一時フォルダへダウンロードする\r
903                                                         // (2007.8.31 yutaka)\r
904                                                         doTransferRemoteFile();\r
905                                                         PathDir = remoteFileDir;\r
906                                                         FileListBase = remoteFileListBase;\r
907                                                         FileListBaseNoExpand = remoteFileListBaseNoExpand;\r
908                                                 }\r
909  \r
910                                         } \r
911  \r
912 #if defined(HAVE_TANDEM)\r
913                                         if(FileListBaseNoExpand == NULL)\r
914                                                 pf = FileListBase;\r
915                                         else\r
916 #endif\r
917                                         pf = FileListBaseNoExpand;\r
918                                         for (filenum = 0; pf ; filenum++) {\r
919                                                 pf = pf->Next;\r
920                                         }\r
921                                         // ファイルが未選択の場合は何もしない。(yutaka)\r
922                                         if (filenum <= 0) {\r
923                                                 *((HANDLE *)lParam) = NULL;\r
924                                                 return (FALSE);\r
925                                         }\r
926                                         \r
927                                         /* ファイル名の配列を作成する */\r
928                                         // TODO: GlobalAllocが返すのはメモリポインタではなくハンドルだが実際は同じ値\r
929                                         FileNameList = (char **)GlobalAlloc(GPTR,sizeof(char *) * filenum);\r
930                                         if(FileNameList == NULL){\r
931                                                 abort();\r
932                                         }\r
933                                         pf = FileListBaseNoExpand;\r
934                                         for (j = 0; pf ; j++) {\r
935                                                 filelen = strlen(PathDir) + 1 + strlen(pf->File) + 1;\r
936                                                 FileNameList[j] = (char *)GlobalAlloc(GPTR, filelen);\r
937                                                 strncpy_s(FileNameList[j], filelen, PathDir, _TRUNCATE);\r
938                                                 strncat_s(FileNameList[j], filelen, "\\", _TRUNCATE);\r
939                                                 strncat_s(FileNameList[j], filelen, pf->File, _TRUNCATE);\r
940                                                 pf = pf->Next;\r
941 #if 0\r
942                                                 if (FileListBase->Node == NODE_DIR) { \r
943                                                         // フォルダを掴んだ場合はそれ以降展開しない\r
944                                                         filenum = 1;\r
945                                                         break;\r
946                                                 }\r
947 #endif\r
948                                         }\r
949                                         \r
950                                         os_info.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);\r
951                                         GetVersionEx(&os_info);\r
952                                         if(os_info.dwPlatformId == VER_PLATFORM_WIN32_NT){\r
953                                                 NTFlag = TRUE;\r
954                                         }\r
955  \r
956                                         /* ドロップファイルリストの作成 */\r
957                                         /* NTの場合はUNICODEになるようにする */\r
958                                         *((HANDLE *)lParam) = CreateDropFileMem(FileNameList, filenum, NTFlag);\r
959  \r
960                                         /* ファイル名の配列を解放する */\r
961                                         for (i = 0; i < filenum ; i++) {\r
962                                                 GlobalFree(FileNameList[i]);\r
963                                         }\r
964                                         GlobalFree(FileNameList);\r
965  \r
966                                         if (hWndDragStart == hWndListLocal) {\r
967                                                 DeleteFileList(&FileListBase);\r
968                                         } else {\r
969                                                 // あとでファイル削除してフリーする\r
970                                         }\r
971  \r
972                                         return (TRUE);\r
973                                 }\r
974                                 break;\r
975  \r
976                         default:\r
977                                 *((HANDLE *)lParam) = NULL;\r
978                                 break;\r
979                         }\r
980  \r
981                         break;\r
982 \r
983                 case WM_DRAGOVER:\r
984                         {\r
985                                 LVHITTESTINFO hi;\r
986                                 int Node, index;\r
987                                 static int prev_index = -1;\r
988 \r
989                                 // 同一ウィンドウ内でのD&Dはリモート側のみ\r
990                                 if (Win != WIN_REMOTE)\r
991                                         break;\r
992 \r
993                                 if(MoveMode == MOVE_DISABLE)\r
994                                         break;\r
995 \r
996                                 memset(&hi, 0, sizeof(hi));\r
997 \r
998                                 GetCursorPos(&Point);\r
999                                 hWndPnt = WindowFromPoint(Point);\r
1000                                 ScreenToClient(hWnd, &Point);\r
1001 \r
1002                                 hi.pt = Point;\r
1003 \r
1004                                 // 以前の選択を消す\r
1005                                 ListView_SetItemState(hWnd, prev_index, 0, LVIS_DROPHILITED);\r
1006                                 RemoteDropFileIndex = -1;\r
1007 \r
1008                                 if ((hWndPnt == hWndListRemote) && (ListView_HitTest(hWnd, &hi) != -1)) {\r
1009                                         if (hi.flags == LVHT_ONITEMLABEL) { // The position is over a list-view item's text.\r
1010                                         \r
1011                                                 index = hi.iItem;\r
1012                                                 prev_index = index;\r
1013                                                 Node = GetNodeType(Win, index);\r
1014                                                 if (Node == NODE_DIR) {\r
1015                                                         ListView_SetItemState(hWnd, index, LVIS_DROPHILITED, LVIS_DROPHILITED);\r
1016                                                         RemoteDropFileIndex = index;\r
1017                                                 }\r
1018                                         }\r
1019                                 } \r
1020 \r
1021                         }\r
1022                         break;\r
1023 \r
1024                 case WM_RBUTTONDOWN :\r
1025                         /* ここでファイルを選ぶ */\r
1026                         CallWindowProc(ProcPtr, hWnd, message, wParam, lParam);\r
1027 \r
1028                         EraseListViewTips();\r
1029                         SetFocus(hWnd);\r
1030                         if(hWnd == hWndListRemote)\r
1031                                 RemoteRbuttonMenu(0);\r
1032                         else if(hWnd == hWndListLocal)\r
1033                                 LocalRbuttonMenu(0);\r
1034                         break;\r
1035 \r
1036                 case WM_LBUTTONDBLCLK :\r
1037                         DoubleClickProc(Win, NO, -1);\r
1038                         break;\r
1039 \r
1040                 case WM_MOUSEMOVE :\r
1041                         if(wParam == MK_LBUTTON)\r
1042                         {\r
1043                                 if((Dragging == NO) && \r
1044                                    (hWnd == hWndDragStart) &&\r
1045                                    (AskConnecting() == YES) &&\r
1046                                    (SendMessage(hWnd, LVM_GETSELECTEDCOUNT, 0, 0) > 0) &&\r
1047                                    ((abs((short)LOWORD(lParam) - DragPoint.x) > 5) ||\r
1048                                         (abs((short)HIWORD(lParam) - DragPoint.y) > 5)))\r
1049                                 {\r
1050                                         SetCapture(hWnd);\r
1051                                         Dragging = YES;\r
1052                                         hCsrDrg = LoadCursor(GetFtpInst(), MAKEINTRESOURCE(drag_csr));\r
1053                                         hCsrNoDrg = LoadCursor(GetFtpInst(), MAKEINTRESOURCE(nodrop_csr));\r
1054                                         SetCursor(hCsrDrg);\r
1055                                 }\r
1056                                 else if(Dragging == YES)\r
1057                                 {\r
1058                                         Point.x = (long)(short)LOWORD(lParam);\r
1059                                         Point.y = (long)(short)HIWORD(lParam);\r
1060                                         ClientToScreen(hWnd, &Point);\r
1061                                         hWndPnt = WindowFromPoint(Point);\r
1062                                         if((hWndPnt == hWndListRemote) || (hWndPnt == hWndListLocal))\r
1063                                                 SetCursor(hCsrDrg);\r
1064                                         else {\r
1065                                                 // マウスポインタの×表示をやめる (yutaka)\r
1066 #if 0\r
1067                                                 SetCursor(hCsrNoDrg);\r
1068 #endif\r
1069                                         }\r
1070 \r
1071                                         // OLE D&Dの開始を指示する\r
1072                                         PostMessage(hWnd, WM_DRAGDROP, MAKEWPARAM(wParam, lParam), 0);\r
1073 \r
1074                                 }\r
1075                                 else\r
1076                                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
1077                         }\r
1078                         else\r
1079                         {\r
1080                                 CheckTipsDisplay(hWnd, lParam);\r
1081                                 return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
1082                         }\r
1083                         break;\r
1084 \r
1085                 case WM_MOUSEWHEEL :\r
1086                         if(Dragging == NO)\r
1087                         {\r
1088                 short zDelta = (short)HIWORD(wParam);\r
1089 \r
1090                                 EraseListViewTips();\r
1091                                 Point.x = (short)LOWORD(lParam);\r
1092                                 Point.y = (short)HIWORD(lParam);\r
1093                                 hWndPnt = WindowFromPoint(Point);\r
1094 \r
1095                                 if((wParam & MAKEWPARAM(MK_SHIFT, 0)) && \r
1096                                    ((hWndPnt == hWndListRemote) ||\r
1097                                         (hWndPnt == hWndListLocal) || \r
1098                                         (hWndPnt == GetTaskWnd())))\r
1099                                 {\r
1100                                         PostMessage(hWndPnt, WM_VSCROLL, zDelta > 0 ? MAKEWPARAM(SB_PAGEUP, 0) : MAKEWPARAM(SB_PAGEDOWN, 0), 0);\r
1101 //                                      PostMessage(hWndPnt, WM_VSCROLL, MAKEWPARAM(SB_ENDSCROLL, 0), 0);\r
1102                                 }\r
1103                                 else if(hWndPnt == hWnd)\r
1104                                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
1105                                 else if((hWndPnt == hWndDst) || (hWndPnt == GetTaskWnd()))\r
1106                                         PostMessage(hWndPnt, message, wParam, lParam);\r
1107                         }\r
1108                         break;\r
1109 \r
1110                 default :\r
1111                         return(CallWindowProc(ProcPtr, hWnd, message, wParam, lParam));\r
1112         }\r
1113     return(0L);\r
1114 }\r
1115 \r
1116 \r
1117 /*----- ファイルリストのタブ幅を取得する --------------------------------------\r
1118 *\r
1119 *       Parameter\r
1120 *               なし\r
1121 *\r
1122 *       Return Value\r
1123 *               なし\r
1124 *----------------------------------------------------------------------------*/\r
1125 \r
1126 void GetListTabWidth(void)\r
1127 {\r
1128         LV_COLUMN LvCol;\r
1129         int i;\r
1130 \r
1131         // 変数が未初期化のバグ修正\r
1132         memset(&LvCol, 0, sizeof(LV_COLUMN));\r
1133 \r
1134         for(i = 0; i <= 3; i++)\r
1135         {\r
1136                 LvCol.mask = LVCF_WIDTH;\r
1137                 if(SendMessage(hWndListLocal, LVM_GETCOLUMN, i, (LPARAM)&LvCol) == TRUE)\r
1138                         LocalTabWidth[i] = LvCol.cx;\r
1139         }\r
1140 \r
1141         for(i = 0; i <= 5; i++)\r
1142         {\r
1143                 LvCol.mask = LVCF_WIDTH;\r
1144                 if(SendMessage(hWndListRemote, LVM_GETCOLUMN, i, (LPARAM)&LvCol) == TRUE)\r
1145                         RemoteTabWidth[i] = LvCol.cx;\r
1146         }\r
1147         return;\r
1148 }\r
1149 \r
1150 \r
1151 /*----- ファイル一覧方法にしたがってリストビューを設定する --------------------\r
1152 *\r
1153 *       Parameter\r
1154 *               なし\r
1155 *\r
1156 *       Return Value\r
1157 *               なし\r
1158 *----------------------------------------------------------------------------*/\r
1159 \r
1160 void SetListViewType(void)\r
1161 {\r
1162         // 64ビット対応\r
1163 //      long lStyle;\r
1164         LONG_PTR lStyle;\r
1165 \r
1166         switch(ListType)\r
1167         {\r
1168                 case LVS_LIST :\r
1169                         // 64ビット対応\r
1170 //                      lStyle = GetWindowLong(GetLocalHwnd(), GWL_STYLE);\r
1171                         lStyle = GetWindowLongPtr(GetLocalHwnd(), GWL_STYLE);\r
1172                         lStyle &= ~(LVS_REPORT | LVS_LIST);\r
1173                         lStyle |= LVS_LIST;\r
1174                         // 64ビット対応\r
1175 //                      SetWindowLong(GetLocalHwnd(), GWL_STYLE, lStyle);\r
1176                         SetWindowLongPtr(GetLocalHwnd(), GWL_STYLE, lStyle);\r
1177 \r
1178                         // 64ビット対応\r
1179 //                      lStyle = GetWindowLong(GetRemoteHwnd(), GWL_STYLE);\r
1180                         lStyle = GetWindowLongPtr(GetRemoteHwnd(), GWL_STYLE);\r
1181                         lStyle &= ~(LVS_REPORT | LVS_LIST);\r
1182                         lStyle |= LVS_LIST;\r
1183                         // 64ビット対応\r
1184 //                      SetWindowLong(GetRemoteHwnd(), GWL_STYLE, lStyle);\r
1185                         SetWindowLongPtr(GetRemoteHwnd(), GWL_STYLE, lStyle);\r
1186                         break;\r
1187 \r
1188                 default :\r
1189                         // 64ビット対応\r
1190 //                      lStyle = GetWindowLong(GetLocalHwnd(), GWL_STYLE);\r
1191                         lStyle = GetWindowLongPtr(GetLocalHwnd(), GWL_STYLE);\r
1192                         lStyle &= ~(LVS_REPORT | LVS_LIST);\r
1193                         lStyle |= LVS_REPORT;\r
1194                         // 64ビット対応\r
1195 //                      SetWindowLong(GetLocalHwnd(), GWL_STYLE, lStyle);\r
1196                         SetWindowLongPtr(GetLocalHwnd(), GWL_STYLE, lStyle);\r
1197 \r
1198                         // 64ビット対応\r
1199 //                      lStyle = GetWindowLong(GetRemoteHwnd(), GWL_STYLE);\r
1200                         lStyle = GetWindowLongPtr(GetRemoteHwnd(), GWL_STYLE);\r
1201                         lStyle &= ~(LVS_REPORT | LVS_LIST);\r
1202                         lStyle |= LVS_REPORT;\r
1203                         // 64ビット対応\r
1204 //                      SetWindowLong(GetRemoteHwnd(), GWL_STYLE, lStyle);\r
1205                         SetWindowLongPtr(GetRemoteHwnd(), GWL_STYLE, lStyle);\r
1206                         break;\r
1207         }\r
1208         return;\r
1209 }\r
1210 \r
1211 \r
1212 /*----- ホスト側のファイル一覧ウインドウにファイル名をセット ------------------\r
1213 *\r
1214 *       Parameter\r
1215 *               int Mode : キャッシュモード (CACHE_xxx)\r
1216 *\r
1217 *       Return Value\r
1218 *               なし\r
1219 *----------------------------------------------------------------------------*/\r
1220 \r
1221 void GetRemoteDirForWnd(int Mode, int *CancelCheckWork)\r
1222 {\r
1223         FILE *fd;\r
1224         LONGLONG Size;\r
1225         char Str[FMAX_PATH+1];\r
1226         char Buf[FMAX_PATH+1];\r
1227         FILETIME Time;\r
1228         int Attr;\r
1229         int Type;\r
1230         int ListType;\r
1231         int Num;\r
1232         FLISTANCHOR Anchor;\r
1233         char Owner[OWNER_NAME_LEN+1];\r
1234         int Link;\r
1235         int InfoExist;\r
1236 \r
1237 //#pragma aaa\r
1238 //DoPrintf("===== GetRemoteDirForWnd");\r
1239 \r
1240         Anchor.Top = NULL;\r
1241         Anchor.Files = 0;\r
1242 \r
1243         if(AskConnecting() == YES)\r
1244         {\r
1245 //              SetCursor(LoadCursor(NULL, IDC_WAIT));\r
1246                 DisableUserOpe();\r
1247 \r
1248                 AskRemoteCurDir(Buf, FMAX_PATH);\r
1249                 SetRemoteDirHist(Buf);\r
1250 \r
1251                 Type = FTP_COMPLETE;\r
1252                 if(Mode != CACHE_LASTREAD)\r
1253                 {\r
1254 \r
1255                         if((Num = AskCached(Buf)) == -1)\r
1256                         {\r
1257                                 Num = AskFreeCache();\r
1258                                 Mode = CACHE_REFRESH;\r
1259                         }\r
1260 \r
1261                         if(Mode == CACHE_REFRESH)\r
1262                         {\r
1263                                 if((Type = DoDirListCmdSkt("", "", Num, CancelCheckWork)) == FTP_COMPLETE)\r
1264                                         SetCache(Num, Buf);\r
1265                                 else\r
1266                                         ClearCache(Num);\r
1267                         }\r
1268                 }\r
1269                 else\r
1270                         Num = AskCurrentFileListNum();\r
1271 \r
1272                 if(Type == FTP_COMPLETE)\r
1273                 {\r
1274                         SetCurrentFileListNum(Num);\r
1275                         MakeCacheFileName(Num, Buf);\r
1276                         if((fd = fopen(Buf, "rb"))!=NULL)\r
1277                         {\r
1278                                 ListType = LIST_UNKNOWN;\r
1279 \r
1280                                 while(GetListOneLine(Str, FMAX_PATH, fd) == FFFTP_SUCCESS)\r
1281                                 {\r
1282                                         if((ListType = AnalizeFileInfo(Str)) != LIST_UNKNOWN)\r
1283                                         {\r
1284                                                 if((Type = ResolvFileInfo(Str, ListType, Buf, &Size, &Time, &Attr, Owner, &Link, &InfoExist)) != NODE_NONE)\r
1285                                                 {\r
1286                                                         if(AskFilterStr(Buf, Type) == YES)\r
1287                                                         {\r
1288                                                                 if((DotFile == YES) || (Buf[0] != '.'))\r
1289                                                                 {\r
1290                                                                         AddDispFileList(&Anchor, Buf, &Time, Size, Attr, Type, Link, Owner, InfoExist, WIN_REMOTE);\r
1291                                                                 }\r
1292                                                         }\r
1293                                                 }\r
1294                                         }\r
1295                                 }\r
1296                                 fclose(fd);\r
1297 \r
1298                                 DispFileList2View(GetRemoteHwnd(), &Anchor);\r
1299                                 EraseDispFileList(&Anchor);\r
1300 \r
1301                                 // 先頭のアイテムを選択\r
1302                                 ListView_SetItemState(GetRemoteHwnd(), 0, LVIS_FOCUSED, LVIS_FOCUSED);\r
1303                         }\r
1304                         else\r
1305                         {\r
1306                                 SetTaskMsg(MSGJPN048);\r
1307                                 SendMessage(GetRemoteHwnd(), LVM_DELETEALLITEMS, 0, 0);\r
1308                         }\r
1309                 }\r
1310                 else\r
1311                 {\r
1312 #if defined(HAVE_OPENVMS)\r
1313                         /* OpenVMSの場合空ディレクトリ移動の時に出るので、メッセージだけ出さない\r
1314                          * ようにする(VIEWはクリアして良い) */\r
1315                         if (AskHostType() != HTYPE_VMS)\r
1316 #endif\r
1317                         SetTaskMsg(MSGJPN049);\r
1318                         SendMessage(GetRemoteHwnd(), LVM_DELETEALLITEMS, 0, 0);\r
1319                 }\r
1320 \r
1321 //              SetCursor(LoadCursor(NULL, IDC_ARROW));\r
1322                 EnableUserOpe();\r
1323 \r
1324         }\r
1325 \r
1326 //#pragma aaa\r
1327 //DoPrintf("===== GetRemoteDirForWnd Done");\r
1328 \r
1329         return;\r
1330 }\r
1331 \r
1332 \r
1333 /*----- ローカル側のファイル一覧ウインドウにファイル名をセット ----------------\r
1334 *\r
1335 *       Parameter\r
1336 *               なし\r
1337 *\r
1338 *       Return Value\r
1339 *               なし\r
1340 *----------------------------------------------------------------------------*/\r
1341 \r
1342 // ファイルアイコン表示対応\r
1343 void RefreshIconImageList(FLISTANCHOR *Anchor)\r
1344 {\r
1345         HBITMAP hBitmap;\r
1346         int ImageId;\r
1347         FILELIST *Pos;\r
1348         int i;\r
1349         char Cur[FMAX_PATH+1];\r
1350         SHFILEINFO FileInfo;\r
1351         if(AskDispFileIcon() == YES)\r
1352         {\r
1353                 SendMessage(hWndListLocal, LVM_SETIMAGELIST, LVSIL_SMALL, (LPARAM)NULL);\r
1354                 ShowWindow(hWndListLocal, SW_SHOW);\r
1355                 SendMessage(hWndListRemote, LVM_SETIMAGELIST, LVSIL_SMALL, (LPARAM)NULL);\r
1356                 ShowWindow(hWndListRemote, SW_SHOW);\r
1357                 ImageList_Destroy(ListImgFileIcon);\r
1358                 ListImgFileIcon = ImageList_Create(16, 16, ILC_MASK | ILC_COLOR32, 0, 1);\r
1359                 hBitmap = LoadBitmap(GetFtpInst(), MAKEINTRESOURCE(dirattr16_bmp));\r
1360                 ImageList_AddMasked(ListImgFileIcon, hBitmap, RGB(255, 0, 0));\r
1361                 DeleteObject(hBitmap);\r
1362                 ImageId = 0;\r
1363                 Pos = Anchor->Top;\r
1364                 for(i = 0; i < Anchor->Files; i++)\r
1365                 {\r
1366                         Pos->ImageId = -1;\r
1367                         if(Pos->Node == NODE_DRIVE)\r
1368                                 strcpy(Cur, Pos->File);\r
1369                         else\r
1370                         {\r
1371                                 AskLocalCurDir(Cur, FMAX_PATH);\r
1372                                 SetYenTail(Cur);\r
1373                                 strcat(Cur, Pos->File);\r
1374                         }\r
1375                         if(SHGetFileInfoM(Cur, 0, &FileInfo, sizeof(SHFILEINFO), SHGFI_SMALLICON | SHGFI_ICON) != 0)\r
1376                         {\r
1377                                 if(ImageList_AddIcon(ListImgFileIcon, FileInfo.hIcon) >= 0)\r
1378                                 {\r
1379                                         Pos->ImageId = ImageId;\r
1380                                         ImageId++;\r
1381                                 }\r
1382                                 DestroyIcon(FileInfo.hIcon);\r
1383                         }\r
1384                         Pos = Pos->Next;\r
1385                 }\r
1386                 SendMessage(hWndListLocal, LVM_SETIMAGELIST, LVSIL_SMALL, (LPARAM)ListImgFileIcon);\r
1387                 ShowWindow(hWndListLocal, SW_SHOW);\r
1388                 SendMessage(hWndListRemote, LVM_SETIMAGELIST, LVSIL_SMALL, (LPARAM)ListImgFileIcon);\r
1389                 ShowWindow(hWndListRemote, SW_SHOW);\r
1390         }\r
1391         else\r
1392         {\r
1393                 SendMessage(hWndListLocal, LVM_SETIMAGELIST, LVSIL_SMALL, (LPARAM)ListImg);\r
1394                 ShowWindow(hWndListLocal, SW_SHOW);\r
1395                 SendMessage(hWndListRemote, LVM_SETIMAGELIST, LVSIL_SMALL, (LPARAM)ListImg);\r
1396                 ShowWindow(hWndListRemote, SW_SHOW);\r
1397         }\r
1398 }\r
1399 \r
1400 void GetLocalDirForWnd(void)\r
1401 {\r
1402         HANDLE fHnd;\r
1403         WIN32_FIND_DATA Find;\r
1404         char Scan[FMAX_PATH+1];\r
1405         char *Pos;\r
1406         char Buf[10];\r
1407         FILETIME Time;\r
1408         FLISTANCHOR Anchor;\r
1409         DWORD NoDrives;\r
1410         int Tmp;\r
1411 \r
1412         Anchor.Top = NULL;\r
1413         Anchor.Files = 0;\r
1414 \r
1415         DoLocalPWD(Scan);\r
1416         SetLocalDirHist(Scan);\r
1417         DispLocalFreeSpace(Scan);\r
1418 \r
1419         /* ディレクトリ/ファイル */\r
1420 \r
1421         SetYenTail(Scan);\r
1422         strcat(Scan, "*");\r
1423         if((fHnd = FindFirstFileAttr(Scan, &Find, DispIgnoreHide)) != INVALID_HANDLE_VALUE)\r
1424         {\r
1425                 do\r
1426                 {\r
1427                         if((strcmp(Find.cFileName, ".") != 0) &&\r
1428                            (strcmp(Find.cFileName, "..") != 0))\r
1429                         {\r
1430                                 if((DotFile == YES) || (Find.cFileName[0] != '.'))\r
1431                                 {\r
1432                                         if(Find.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)\r
1433                                                 AddDispFileList(&Anchor, Find.cFileName, &Find.ftLastWriteTime, MakeLongLong(Find.nFileSizeHigh, Find.nFileSizeLow), 0, NODE_DIR, NO, "", FINFO_ALL, WIN_LOCAL);\r
1434                                         else\r
1435                                         {\r
1436                                                 if(AskFilterStr(Find.cFileName, NODE_FILE) == YES)\r
1437                                                 {\r
1438                                                         AddDispFileList(&Anchor, Find.cFileName, &Find.ftLastWriteTime, MakeLongLong(Find.nFileSizeHigh, Find.nFileSizeLow), 0, NODE_FILE, NO, "", FINFO_ALL, WIN_LOCAL);\r
1439                                                 }\r
1440                                         }\r
1441                                 }\r
1442                         }\r
1443                 }\r
1444                 while(FindNextFileAttr(fHnd, &Find, DispIgnoreHide) == TRUE);\r
1445                 FindClose(fHnd);\r
1446         }\r
1447 \r
1448         /* ドライブ */\r
1449         if(DispDrives)\r
1450         {\r
1451                 GetLogicalDriveStrings(FMAX_PATH, Scan);\r
1452                 NoDrives = LoadHideDriveListRegistry();\r
1453 \r
1454                 Pos = Scan;\r
1455                 while(*Pos != NUL)\r
1456                 {\r
1457                         Tmp = toupper(*Pos) - 'A';\r
1458                         if((NoDrives & (0x00000001 << Tmp)) == 0)\r
1459                         {\r
1460                                 sprintf(Buf, "%s", Pos);\r
1461                                 memset(&Time, 0, sizeof(FILETIME));\r
1462                                 AddDispFileList(&Anchor, Buf, &Time, 0, 0, NODE_DRIVE, NO, "", FINFO_ALL, WIN_LOCAL);\r
1463                         }\r
1464                         Pos = strchr(Pos, NUL) + 1;\r
1465                 }\r
1466         }\r
1467 \r
1468         // ファイルアイコン表示対応\r
1469         RefreshIconImageList(&Anchor);\r
1470         DispFileList2View(GetLocalHwnd(), &Anchor);\r
1471         EraseDispFileList(&Anchor);\r
1472 \r
1473         // 先頭のアイテムを選択\r
1474         ListView_SetItemState(GetLocalHwnd(), 0, LVIS_FOCUSED, LVIS_FOCUSED);\r
1475 \r
1476         return;\r
1477 }\r
1478 \r
1479 \r
1480 /*----- ファイル情報をファイル一覧用リストに登録する --------------------------\r
1481 *\r
1482 *       Parameter\r
1483 *               FLISTANCHOR *Anchor : ファイルリストの先頭\r
1484 *               char *Name : ファイル名\r
1485 *               FILETIME *Time : 日付\r
1486 *               LONGLONG Size : サイズ\r
1487 *               int Attr : 属性\r
1488 *               int Type : タイプ (NODE_xxxx)\r
1489 *               int Link : リンクかどうか (YES/NO)\r
1490 *               char *Owner : オーナ名\r
1491 *               int InfoExist : 情報があるかどうか (FINFO_xxx)\r
1492 *               int Win : ウィンドウ番号 (WIN_xxxx)\r
1493 *\r
1494 *       Return Value\r
1495 *               なし\r
1496 *----------------------------------------------------------------------------*/\r
1497 \r
1498 static void AddDispFileList(FLISTANCHOR *Anchor, char *Name, FILETIME *Time, LONGLONG Size, int Attr, int Type, int Link, char *Owner, int InfoExist, int Win)\r
1499 {\r
1500         int i;\r
1501         FILELIST *Pos;\r
1502         FILELIST *Prev;\r
1503         FILELIST *New;\r
1504         int FileSort;\r
1505         int DirSort;\r
1506         int Sort;\r
1507         LONGLONG Cmp;\r
1508 \r
1509         FileSort = AskSortType(ITEM_LFILE);\r
1510         DirSort = AskSortType(ITEM_LDIR);\r
1511         if(Win == WIN_REMOTE)\r
1512         {\r
1513                 FileSort = AskSortType(ITEM_RFILE);\r
1514                 DirSort = AskSortType(ITEM_RDIR);\r
1515         }\r
1516 \r
1517         Pos = Anchor->Top;\r
1518         for(i = 0; i < Anchor->Files; i++)\r
1519         {\r
1520                 if((Type == NODE_DIR) && (Pos->Node == NODE_FILE))\r
1521                         break;\r
1522                 if((Type == NODE_FILE) && (Pos->Node == NODE_DRIVE))\r
1523                         break;\r
1524 \r
1525                 if(Type == Pos->Node)\r
1526                 {\r
1527                         if(Type == NODE_DIR)\r
1528                                 Sort = DirSort;\r
1529                         else\r
1530                                 Sort = FileSort;\r
1531 \r
1532                         if((Sort & SORT_GET_ORD) == SORT_ASCENT)\r
1533                         {\r
1534                                 // 読みにくいのでリファクタリング\r
1535 //                              if((((Sort & SORT_MASK_ORD) == SORT_EXT) &&\r
1536 //                                      ((Cmp = _mbsicmp(GetFileExt(Name), GetFileExt(Pos->File))) < 0)) ||\r
1537 //#if defined(HAVE_TANDEM)\r
1538 //                                 ((AskHostType() == HTYPE_TANDEM) &&\r
1539 //                                  ((Sort & SORT_MASK_ORD) == SORT_EXT) &&\r
1540 //                                      ((Cmp = Attr - Pos->Attr) < 0)) ||\r
1541 //#endif\r
1542 //                                 (((Sort & SORT_MASK_ORD) == SORT_SIZE) &&\r
1543 //                                      ((Cmp = Size - Pos->Size) < 0)) ||\r
1544 //                                 (((Sort & SORT_MASK_ORD) == SORT_DATE) &&\r
1545 //                                      ((Cmp = CompareFileTime(Time, &Pos->Time)) < 0)))\r
1546 //                              {\r
1547 //                                      break;\r
1548 //                              }\r
1549                                 if(((Sort & SORT_MASK_ORD) == SORT_EXT) &&\r
1550                                         ((Cmp = _mbsicmp(GetFileExt(Name), GetFileExt(Pos->File))) < 0))\r
1551                                         break;\r
1552 #if defined(HAVE_TANDEM)\r
1553                                 if((AskHostType() == HTYPE_TANDEM) &&\r
1554                                         ((Sort & SORT_MASK_ORD) == SORT_EXT) &&\r
1555                                         ((Cmp = Attr - Pos->Attr) < 0))\r
1556                                         break;\r
1557 #endif\r
1558                                 if(((Sort & SORT_MASK_ORD) == SORT_SIZE) &&\r
1559                                         ((Cmp = Size - Pos->Size) < 0))\r
1560                                         break;\r
1561                                 if(((Sort & SORT_MASK_ORD) == SORT_DATE) &&\r
1562                                         ((Cmp = CompareFileTime(Time, &Pos->Time)) < 0))\r
1563                                         break;\r
1564 \r
1565                                 if(((Sort & SORT_MASK_ORD) == SORT_NAME) || (Cmp == 0))\r
1566                                 {\r
1567                                         if(_mbsicmp(Name, Pos->File) < 0)\r
1568                                                 break;\r
1569                                 }\r
1570                         }\r
1571                         else\r
1572                         {\r
1573                                 if((((Sort & SORT_MASK_ORD) == SORT_EXT) &&\r
1574                                         ((Cmp = _mbsicmp(GetFileExt(Name), GetFileExt(Pos->File))) > 0)) ||\r
1575 #if defined(HAVE_TANDEM)\r
1576                                    ((AskHostType() == HTYPE_TANDEM) &&\r
1577                                     ((Sort & SORT_MASK_ORD) == SORT_EXT) &&\r
1578                                         ((Cmp = Attr - Pos->Attr) > 0)) ||\r
1579 #endif\r
1580                                    (((Sort & SORT_MASK_ORD) == SORT_SIZE) &&\r
1581                                         ((Cmp = Size - Pos->Size) > 0)) ||\r
1582                                    (((Sort & SORT_MASK_ORD) == SORT_DATE) &&\r
1583                                         ((Cmp = CompareFileTime(Time, &Pos->Time)) > 0)))\r
1584                                 {\r
1585                                         break;\r
1586                                 }\r
1587 \r
1588                                 if(((Sort & SORT_MASK_ORD) == SORT_NAME) || (Cmp == 0))\r
1589                                 {\r
1590                                         if(_mbsicmp(Name, Pos->File) > 0)\r
1591                                                 break;\r
1592                                 }\r
1593                         }\r
1594                 }\r
1595                 Prev = Pos;\r
1596                 Pos = Pos->Next;\r
1597         }\r
1598 \r
1599         if((New = malloc(sizeof(FILELIST))) != NULL)\r
1600         {\r
1601                 strcpy(New->File, Name);\r
1602                 New->Node = Type;\r
1603                 New->Link = Link;\r
1604                 New->Size = Size;\r
1605                 New->Attr = Attr;\r
1606                 New->Time = *Time;\r
1607                 strcpy(New->Owner, Owner);\r
1608                 New->InfoExist = InfoExist;\r
1609 \r
1610                 if(Pos == Anchor->Top)\r
1611                 {\r
1612                         New->Next = Anchor->Top;\r
1613                         Anchor->Top = New;\r
1614                 }\r
1615                 else\r
1616                 {\r
1617                         New->Next = Prev->Next;\r
1618                         Prev->Next = New;\r
1619                 }\r
1620                 Anchor->Files += 1;\r
1621         }\r
1622         return;\r
1623 }\r
1624 \r
1625 \r
1626 /*----- ファイル一覧用リストをクリアする --------------------------------------\r
1627 *\r
1628 *       Parameter\r
1629 *               FLISTANCHOR *Anchor : ファイルリストの先頭\r
1630 *\r
1631 *       Return Value\r
1632 *               なし\r
1633 *----------------------------------------------------------------------------*/\r
1634 \r
1635 static void EraseDispFileList(FLISTANCHOR *Anchor)\r
1636 {\r
1637         FILELIST *Pos;\r
1638         FILELIST *Next;\r
1639         int i;\r
1640 \r
1641         Pos = Anchor->Top;\r
1642         for(i = 0; i < Anchor->Files; i++)\r
1643         {\r
1644                 Next = Pos->Next;\r
1645                 free(Pos);\r
1646                 Pos = Next;\r
1647         }\r
1648         Anchor->Files = 0;\r
1649         Anchor->Top = NULL;\r
1650         return;\r
1651 }\r
1652 \r
1653 \r
1654 /*----- ファイル一覧用リストの内容をファイル一覧ウインドウにセット ------------\r
1655 *\r
1656 *       Parameter\r
1657 *               HWND hWnd : ウインドウハンドル\r
1658 *               FLISTANCHOR *Anchor : ファイルリストの先頭\r
1659 *\r
1660 *       Return Value\r
1661 *               なし\r
1662 *----------------------------------------------------------------------------*/\r
1663 \r
1664 static void DispFileList2View(HWND hWnd, FLISTANCHOR *Anchor)\r
1665 {\r
1666         int i;\r
1667         FILELIST *Pos;\r
1668 \r
1669         SendMessage(hWnd, WM_SETREDRAW, (WPARAM)FALSE, 0);\r
1670         SendMessage(hWnd, LVM_DELETEALLITEMS, 0, 0);\r
1671 \r
1672         Pos = Anchor->Top;\r
1673         for(i = 0; i < Anchor->Files; i++)\r
1674         {\r
1675                 // ファイルアイコン表示対応\r
1676 //              AddListView(hWnd, -1, Pos->File, Pos->Node, Pos->Size, &Pos->Time, Pos->Attr, Pos->Owner, Pos->Link, Pos->InfoExist);\r
1677                 AddListView(hWnd, -1, Pos->File, Pos->Node, Pos->Size, &Pos->Time, Pos->Attr, Pos->Owner, Pos->Link, Pos->InfoExist, Pos->ImageId);\r
1678                 Pos = Pos->Next;\r
1679         }\r
1680 \r
1681         SendMessage(hWnd, WM_SETREDRAW, (WPARAM)TRUE, 0);\r
1682         UpdateWindow(hWnd);\r
1683 \r
1684         DispSelectedSpace();\r
1685         return;\r
1686 }\r
1687 \r
1688 \r
1689 /*----- ファイル一覧ウインドウ(リストビュー)に追加 --------------------------\r
1690 *\r
1691 *       Parameter\r
1692 *               HWND hWnd : ウインドウハンドル\r
1693 *               int Pos : 挿入位置\r
1694 *               char *Name : 名前\r
1695 *               int Type : タイプ (NIDE_xxxx)\r
1696 *               LONGLONG Size : サイズ\r
1697 *               FILETIME *Time : 日付\r
1698 *               int Attr : 属性\r
1699 *               char Owner : オーナ名\r
1700 *               int Link : リンクかどうか\r
1701 *               int InfoExist : 情報があるかどうか (FINFO_xxx)\r
1702 *\r
1703 *       Return Value\r
1704 *               なし\r
1705 *----------------------------------------------------------------------------*/\r
1706 \r
1707 // ファイルアイコン表示対応\r
1708 //static void AddListView(HWND hWnd, int Pos, char *Name, int Type, LONGLONG Size, FILETIME *Time, int Attr, char *Owner, int Link, int InfoExist)\r
1709 static void AddListView(HWND hWnd, int Pos, char *Name, int Type, LONGLONG Size, FILETIME *Time, int Attr, char *Owner, int Link, int InfoExist, int ImageId)\r
1710 {\r
1711         LV_ITEM LvItem;\r
1712         char Tmp[20];\r
1713 \r
1714         if(Pos == -1)\r
1715                 Pos = SendMessage(hWnd, LVM_GETITEMCOUNT, 0, 0);\r
1716 \r
1717         // 変数が未初期化のバグ修正\r
1718         memset(&LvItem, 0, sizeof(LV_ITEM));\r
1719         /* アイコン/ファイル名 */\r
1720         LvItem.mask = LVIF_TEXT | LVIF_IMAGE;\r
1721         LvItem.iItem = Pos;\r
1722         LvItem.iSubItem = 0;\r
1723         LvItem.pszText = Name;\r
1724         if((Type == NODE_FILE) && (AskTransferTypeAssoc(Name, TYPE_X) == TYPE_I))\r
1725                 Type = 3;\r
1726         if(Link == NO)\r
1727                 LvItem.iImage = Type;\r
1728         else\r
1729                 LvItem.iImage = 4;\r
1730         // ファイルアイコン表示対応\r
1731         if(AskDispFileIcon() == YES && hWnd == GetLocalHwnd())\r
1732                 LvItem.iImage = ImageId + 5;\r
1733         LvItem.iItem = SendMessage(hWnd, LVM_INSERTITEM, 0, (LPARAM)&LvItem);\r
1734 \r
1735         /* 日付/時刻 */\r
1736         FileTime2TimeString(Time, Tmp, DISPFORM_LEGACY, InfoExist);\r
1737         LvItem.mask = LVIF_TEXT;\r
1738         LvItem.iItem = Pos;\r
1739         LvItem.iSubItem = 1;\r
1740         LvItem.pszText = Tmp;\r
1741         LvItem.iItem = SendMessage(hWnd, LVM_SETITEM, 0, (LPARAM)&LvItem);\r
1742 \r
1743         /* サイズ */\r
1744         if(Type == NODE_DIR)\r
1745                 strcpy(Tmp, "<DIR>");\r
1746         else if(Type == NODE_DRIVE)\r
1747                 strcpy(Tmp, "<DRIVE>");\r
1748         else if(Size >= 0)\r
1749                 MakeNumString(Size, Tmp, TRUE);\r
1750         else\r
1751                 strcpy(Tmp, "");\r
1752         LvItem.mask = LVIF_TEXT;\r
1753         LvItem.iItem = Pos;\r
1754         LvItem.iSubItem = 2;\r
1755         LvItem.pszText = Tmp;\r
1756         LvItem.iItem = SendMessage(hWnd, LVM_SETITEM, 0, (LPARAM)&LvItem);\r
1757 \r
1758         /* 拡張子 */\r
1759         LvItem.mask = LVIF_TEXT;\r
1760         LvItem.iItem = Pos;\r
1761         LvItem.iSubItem = 3;\r
1762 #if defined(HAVE_TANDEM)\r
1763         if (AskHostType() == HTYPE_TANDEM) {\r
1764                 _itoa_s(Attr, Tmp, sizeof(Tmp), 10);\r
1765                 LvItem.pszText = Tmp;\r
1766         } else\r
1767 #endif\r
1768         LvItem.pszText = GetFileExt(Name);\r
1769         LvItem.iItem = SendMessage(hWnd, LVM_SETITEM, 0, (LPARAM)&LvItem);\r
1770 \r
1771         if(hWnd == GetRemoteHwnd())\r
1772         {\r
1773                 /* 属性 */\r
1774                 strcpy(Tmp, "");\r
1775 #if defined(HAVE_TANDEM)\r
1776                 if((InfoExist & FINFO_ATTR) && (AskHostType() != HTYPE_TANDEM))\r
1777 #else\r
1778                 if(InfoExist & FINFO_ATTR)\r
1779 #endif\r
1780                         AttrValue2String(Attr, Tmp);\r
1781                 LvItem.mask = LVIF_TEXT;\r
1782                 LvItem.iItem = Pos;\r
1783                 LvItem.iSubItem = 4;\r
1784                 LvItem.pszText = Tmp;\r
1785                 LvItem.iItem = SendMessage(hWnd, LVM_SETITEM, 0, (LPARAM)&LvItem);\r
1786 \r
1787                 /* オーナ名 */\r
1788                 LvItem.mask = LVIF_TEXT;\r
1789                 LvItem.iItem = Pos;\r
1790                 LvItem.iSubItem = 5;\r
1791                 LvItem.pszText = Owner;\r
1792                 LvItem.iItem = SendMessage(hWnd, LVM_SETITEM, 0, (LPARAM)&LvItem);\r
1793         }\r
1794         return;\r
1795 }\r
1796 \r
1797 \r
1798 /*----- ファイル名一覧ウインドウをソートし直す --------------------------------\r
1799 *\r
1800 *       Parameter\r
1801 *               int Win : ウィンドウ番号 (WIN_xxxx)\r
1802 *\r
1803 *       Return Value\r
1804 *               なし\r
1805 *----------------------------------------------------------------------------*/\r
1806 \r
1807 void ReSortDispList(int Win, int *CancelCheckWork)\r
1808 {\r
1809         if(Win == WIN_REMOTE)\r
1810                 GetRemoteDirForWnd(CACHE_LASTREAD, CancelCheckWork);\r
1811         else\r
1812                 GetLocalDirForWnd();\r
1813         return;\r
1814 }\r
1815 \r
1816 \r
1817 /*----- ファイル一覧ウインドウのファイルを選択する ----------------------------\r
1818 *\r
1819 *       Parameter\r
1820 *               HWND hWnd : ウインドウハンドル\r
1821 *               int Type : 選択方法 (SELECT_xxx)\r
1822 *\r
1823 *       Return Value\r
1824 *               なし\r
1825 *----------------------------------------------------------------------------*/\r
1826 \r
1827 void SelectFileInList(HWND hWnd, int Type)\r
1828 {\r
1829         int Win;\r
1830         int WinDst;\r
1831         int i;\r
1832         int Num;\r
1833         char RegExp[FMAX_PATH+1];\r
1834         char Name[FMAX_PATH+1];\r
1835         LV_ITEM LvItem;\r
1836         int CsrPos;\r
1837         FILETIME Time1;\r
1838         FILETIME Time2;\r
1839         int Find;\r
1840 \r
1841         // 変数が未初期化のバグ修正\r
1842         memset(&LvItem, 0, sizeof(LV_ITEM));\r
1843         Win = WIN_LOCAL;\r
1844         WinDst = WIN_REMOTE;\r
1845         if(hWnd == GetRemoteHwnd())\r
1846         {\r
1847                 Win = WIN_REMOTE;\r
1848                 WinDst = WIN_LOCAL;\r
1849         }\r
1850 \r
1851         Num = GetItemCount(Win);\r
1852         switch(Type)\r
1853         {\r
1854                 case SELECT_ALL :\r
1855                         LvItem.state = 0;\r
1856                         if(GetSelectedCount(Win) <= 1)\r
1857                                 LvItem.state = LVIS_SELECTED;\r
1858                         for(i = 0; i < Num; i++)\r
1859                         {\r
1860                                 if(GetNodeType(Win, i) != NODE_DRIVE)\r
1861                                 {\r
1862                                         LvItem.mask = LVIF_STATE;\r
1863                                         LvItem.iItem = i;\r
1864                                         LvItem.stateMask = LVIS_SELECTED;\r
1865                                         LvItem.iSubItem = 0;\r
1866                                         SendMessage(hWnd, LVM_SETITEMSTATE, i, (LPARAM)&LvItem);\r
1867                                 }\r
1868                         }\r
1869                         break;\r
1870 \r
1871                 case SELECT_REGEXP :\r
1872                         if(((Win == WIN_LOCAL) &&\r
1873                                 (DialogBox(GetFtpInst(), MAKEINTRESOURCE(sel_local_dlg), hWnd, SelectDialogCallBack) == YES)) ||\r
1874                            ((Win == WIN_REMOTE) &&\r
1875                                 (DialogBox(GetFtpInst(), MAKEINTRESOURCE(sel_remote_dlg), hWnd, SelectDialogCallBack) == YES)))\r
1876                         {\r
1877                                 strcpy(RegExp, FindStr);\r
1878 //                              if(FindMode == 0)\r
1879 //                                      WildCard2RegExp(RegExp);\r
1880 \r
1881                                 _mbslwr(RegExp);\r
1882                                 if((FindMode == 0) || (JreCompileStr(RegExp) == TRUE))\r
1883                                 {\r
1884                                         CsrPos = -1;\r
1885                                         for(i = 0; i < Num; i++)\r
1886                                         {\r
1887                                                 GetNodeName(Win, i, Name, FMAX_PATH);\r
1888                                                 Find = FindNameNode(WinDst, Name);\r
1889 \r
1890                                                 _mbslwr(Name);\r
1891                                                 LvItem.state = 0;\r
1892                                                 if(GetNodeType(Win, i) != NODE_DRIVE)\r
1893                                                 {\r
1894                                                         if(((FindMode == 0) && (CheckFname(Name, RegExp) == FFFTP_SUCCESS)) ||\r
1895                                                            ((FindMode != 0) && (JreGetStrMatchInfo(Name, 0) != NULL)))\r
1896                                                         {\r
1897                                                                 LvItem.state = LVIS_SELECTED;\r
1898 \r
1899                                                                 if(Find >= 0)\r
1900                                                                 {\r
1901                                                                         if(IgnoreExist == YES)\r
1902                                                                                 LvItem.state = 0;\r
1903 \r
1904                                                                         if((LvItem.state != 0) && (IgnoreNew == YES))\r
1905                                                                         {\r
1906                                                                                 GetNodeTime(Win, i, &Time1);\r
1907                                                                                 GetNodeTime(WinDst, Find, &Time2);\r
1908                                                                                 if(CompareFileTime(&Time1, &Time2) > 0)\r
1909                                                                                         LvItem.state = 0;\r
1910                                                                         }\r
1911 \r
1912                                                                         if((LvItem.state != 0) && (IgnoreOld == YES))\r
1913                                                                         {\r
1914                                                                                 GetNodeTime(Win, i, &Time1);\r
1915                                                                                 GetNodeTime(WinDst, Find, &Time2);\r
1916                                                                                 if(CompareFileTime(&Time1, &Time2) < 0)\r
1917                                                                                         LvItem.state = 0;\r
1918                                                                         }\r
1919                                                                 }\r
1920                                                         }\r
1921                                                 }\r
1922 \r
1923                                                 if((LvItem.state != 0) && (CsrPos == -1))\r
1924                                                         CsrPos = i;\r
1925 \r
1926                                                 LvItem.mask = LVIF_STATE;\r
1927                                                 LvItem.iItem = i;\r
1928                                                 LvItem.stateMask = LVIS_SELECTED;\r
1929                                                 LvItem.iSubItem = 0;\r
1930                                                 SendMessage(hWnd, LVM_SETITEMSTATE, i, (LPARAM)&LvItem);\r
1931                                         }\r
1932                                         if(CsrPos != -1)\r
1933                                         {\r
1934                                                 LvItem.mask = LVIF_STATE;\r
1935                                                 LvItem.iItem = CsrPos;\r
1936                                                 LvItem.state = LVIS_FOCUSED;\r
1937                                                 LvItem.stateMask = LVIS_FOCUSED;\r
1938                                                 LvItem.iSubItem = 0;\r
1939                                                 SendMessage(hWnd, LVM_SETITEMSTATE, CsrPos, (LPARAM)&LvItem);\r
1940                                                 SendMessage(hWnd, LVM_ENSUREVISIBLE, CsrPos, (LPARAM)TRUE);\r
1941                                         }\r
1942                                 }\r
1943                         }\r
1944                         break;\r
1945         }\r
1946         return;\r
1947 }\r
1948 \r
1949 \r
1950 /*----- 選択ダイアログのコールバック ------------------------------------------\r
1951 *\r
1952 *       Parameter\r
1953 *               HWND hDlg : ウインドウハンドル\r
1954 *               UINT message : メッセージ番号\r
1955 *               WPARAM wParam : メッセージの WPARAM 引数\r
1956 *               LPARAM lParam : メッセージの LPARAM 引数\r
1957 *\r
1958 *       Return Value\r
1959 *               BOOL TRUE/FALSE\r
1960 *----------------------------------------------------------------------------*/\r
1961 \r
1962 // 64ビット対応\r
1963 //static BOOL CALLBACK SelectDialogCallBack(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam)\r
1964 static INT_PTR CALLBACK SelectDialogCallBack(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam)\r
1965 {\r
1966         switch (iMessage)\r
1967         {\r
1968                 case WM_INITDIALOG :\r
1969                         SendDlgItemMessage(hDlg, SEL_FNAME, EM_LIMITTEXT, 40, 0);\r
1970                         SendDlgItemMessage(hDlg, SEL_FNAME, WM_SETTEXT, 0, (LPARAM)FindStr);\r
1971                         SendDlgItemMessage(hDlg, SEL_REGEXP, BM_SETCHECK, FindMode, 0);\r
1972                         SendDlgItemMessage(hDlg, SEL_NOOLD, BM_SETCHECK, IgnoreOld, 0);\r
1973                         SendDlgItemMessage(hDlg, SEL_NONEW, BM_SETCHECK, IgnoreNew, 0);\r
1974                         SendDlgItemMessage(hDlg, SEL_NOEXIST, BM_SETCHECK, IgnoreExist, 0);\r
1975                         return(TRUE);\r
1976 \r
1977                 case WM_COMMAND :\r
1978                         switch(GET_WM_COMMAND_ID(wParam, lParam))\r
1979                         {\r
1980                                 case IDOK :\r
1981                                         SendDlgItemMessage(hDlg, SEL_FNAME, WM_GETTEXT, 40+1, (LPARAM)FindStr);\r
1982                                         FindMode = SendDlgItemMessage(hDlg, SEL_REGEXP, BM_GETCHECK, 0, 0);\r
1983                                         IgnoreOld = SendDlgItemMessage(hDlg, SEL_NOOLD, BM_GETCHECK, 0, 0);\r
1984                                         IgnoreNew = SendDlgItemMessage(hDlg, SEL_NONEW, BM_GETCHECK, 0, 0);\r
1985                                         IgnoreExist = SendDlgItemMessage(hDlg, SEL_NOEXIST, BM_GETCHECK, 0, 0);\r
1986                                         EndDialog(hDlg, YES);\r
1987                                         break;\r
1988 \r
1989                                 case IDCANCEL :\r
1990                                         EndDialog(hDlg, NO);\r
1991                                         break;\r
1992 \r
1993                                 case IDHELP :\r
1994                                         hHelpWin = HtmlHelp(NULL, AskHelpFilePath(), HH_HELP_CONTEXT, IDH_HELP_TOPIC_0000061);\r
1995                                         break;\r
1996                         }\r
1997             return(TRUE);\r
1998         }\r
1999         return(FALSE);\r
2000 }\r
2001 \r
2002 \r
2003 /*----- ファイル一覧ウインドウのファイルを検索する ----------------------------\r
2004 *\r
2005 *       Parameter\r
2006 *               HWND hWnd : ウインドウハンドル\r
2007 *               int Type : 検索方法 (FIND_xxx)\r
2008 *\r
2009 *       Return Value\r
2010 *               なし\r
2011 *----------------------------------------------------------------------------*/\r
2012 \r
2013 void FindFileInList(HWND hWnd, int Type)\r
2014 {\r
2015         int Win;\r
2016         int i;\r
2017         int Num;\r
2018         static char RegExp[FMAX_PATH+1] = { "" };\r
2019         char Name[FMAX_PATH+1];\r
2020         LV_ITEM LvItem;\r
2021         char *Title;\r
2022 \r
2023         // 変数が未初期化のバグ修正\r
2024         memset(&LvItem, 0, sizeof(LV_ITEM));\r
2025         Win = WIN_LOCAL;\r
2026         Title = MSGJPN050;\r
2027         if(hWnd == GetRemoteHwnd())\r
2028         {\r
2029                 Win = WIN_REMOTE;\r
2030                 Title = MSGJPN051;\r
2031         }\r
2032 \r
2033         Num = GetItemCount(Win);\r
2034         switch(Type)\r
2035         {\r
2036                 case FIND_FIRST :\r
2037                         if(InputDialogBox(find_dlg, hWnd, Title, FindStr, 40+1, &FindMode, IDH_HELP_TOPIC_0000001) == YES)\r
2038                         {\r
2039                                 strcpy(RegExp, FindStr);\r
2040 //                              if(FindMode == 0)\r
2041 //                                      WildCard2RegExp(RegExp);\r
2042 \r
2043                                 _mbslwr(RegExp);\r
2044                                 if((FindMode == 0) || (JreCompileStr(RegExp) == TRUE))\r
2045                                 {\r
2046                                         for(i = GetCurrentItem(Win)+1; i < Num; i++)\r
2047                                         {\r
2048                                                 GetNodeName(Win, i, Name, FMAX_PATH);\r
2049                                                 _mbslwr(Name);\r
2050 \r
2051                                                 LvItem.state = 0;\r
2052                                                 if(((FindMode == 0) && (CheckFname(Name, RegExp) == FFFTP_SUCCESS)) ||\r
2053                                                    ((FindMode != 0) && (JreGetStrMatchInfo(Name, 0) != NULL)))\r
2054                                                 {\r
2055                                                         LvItem.mask = LVIF_STATE;\r
2056                                                         LvItem.iItem = i;\r
2057                                                         LvItem.state = LVIS_FOCUSED;\r
2058                                                         LvItem.stateMask = LVIS_FOCUSED;\r
2059                                                         LvItem.iSubItem = 0;\r
2060                                                         SendMessage(hWnd, LVM_SETITEMSTATE, i, (LPARAM)&LvItem);\r
2061                                                         SendMessage(hWnd, LVM_ENSUREVISIBLE, i, (LPARAM)TRUE);\r
2062                                                         break;\r
2063                                                 }\r
2064                                         }\r
2065                                 }\r
2066                         }\r
2067                         break;\r
2068 \r
2069                 case FIND_NEXT :\r
2070                         for(i = GetCurrentItem(Win)+1; i < Num; i++)\r
2071                         {\r
2072                                 GetNodeName(Win, i, Name, FMAX_PATH);\r
2073                                 _mbslwr(Name);\r
2074 \r
2075                                 LvItem.state = 0;\r
2076                                 if(((FindMode == 0) && (CheckFname(Name, RegExp) == FFFTP_SUCCESS)) ||\r
2077                                    ((FindMode != 0) && (JreGetStrMatchInfo(Name, 0) != NULL)))\r
2078                                 {\r
2079                                         LvItem.mask = LVIF_STATE;\r
2080                                         LvItem.iItem = i;\r
2081                                         LvItem.state = LVIS_FOCUSED;\r
2082                                         LvItem.stateMask = LVIS_FOCUSED;\r
2083                                         LvItem.iSubItem = 0;\r
2084                                         SendMessage(hWnd, LVM_SETITEMSTATE, i, (LPARAM)&LvItem);\r
2085                                         SendMessage(hWnd, LVM_ENSUREVISIBLE, i, (LPARAM)TRUE);\r
2086                                         break;\r
2087                                 }\r
2088                         }\r
2089                         break;\r
2090         }\r
2091         return;\r
2092 }\r
2093 \r
2094 \r
2095 #if 0\r
2096 /*----- ワイルドカードを正規表現に変換する ------------------------------------\r
2097 *\r
2098 *       Parameter\r
2099 *               char *Str : 文字列\r
2100 *\r
2101 *       Return Value\r
2102 *               なし\r
2103 *----------------------------------------------------------------------------*/\r
2104 \r
2105 void WildCard2RegExp(char *Str)\r
2106 {\r
2107         char Tmp[FMAX_PATH+1];\r
2108         char *Org;\r
2109         char *Pos;\r
2110         UINT Ch;\r
2111 \r
2112         Org = Str;\r
2113         Pos = Tmp;\r
2114 \r
2115         *Pos++ = '^';\r
2116         *Pos++ = '(';\r
2117         while(*Str != NUL)\r
2118         {\r
2119                 if(Pos >= Tmp + FMAX_PATH - 3)\r
2120                         break;\r
2121 \r
2122                 Ch = _mbsnextc(Str);\r
2123                 Str = _mbsinc(Str);\r
2124 \r
2125                 if(Ch <= 0x7F)\r
2126                 {\r
2127                         if(strchr("[]()^$.+", Ch) != NULL)\r
2128                         {\r
2129                                 *Pos++ = '\\';\r
2130                                 *Pos++ = Ch;\r
2131                         }\r
2132                         else if(Ch == '*')\r
2133                         {\r
2134                                 *Pos++ = '.';\r
2135                                 *Pos++ = '*';\r
2136                         }\r
2137                         else if(Ch == '?')\r
2138                                 *Pos++ = '.';\r
2139                         else if(Ch == '|')\r
2140                         {\r
2141                                 *Pos++ = '|';\r
2142                         }\r
2143                         else\r
2144                                 *Pos++ = Ch;\r
2145                 }\r
2146                 else\r
2147                 {\r
2148                         _mbsnset(Pos, Ch, 1);\r
2149                         Pos = _mbsinc(Pos);\r
2150                 }\r
2151         }\r
2152         *Pos++ = ')';\r
2153         *Pos++ = '$';\r
2154         *Pos = NUL;\r
2155         strcpy(Org, Tmp);\r
2156 \r
2157         return;\r
2158 }\r
2159 #endif\r
2160 \r
2161 \r
2162 /*----- カーソル位置のアイテム番号を返す --------------------------------------\r
2163 *\r
2164 *       Parameter\r
2165 *               int Win : ウィンドウ番号 (WIN_xxxx)\r
2166 *\r
2167 *       Return Value\r
2168 *               int アイテム番号\r
2169 *----------------------------------------------------------------------------*/\r
2170 \r
2171 int GetCurrentItem(int Win)\r
2172 {\r
2173         HWND hWnd;\r
2174         int Ret;\r
2175 \r
2176         hWnd = GetLocalHwnd();\r
2177         if(Win == WIN_REMOTE)\r
2178                 hWnd = GetRemoteHwnd();\r
2179 \r
2180         if((Ret = SendMessage(hWnd, LVM_GETNEXTITEM, -1, MAKELPARAM(LVNI_ALL | LVNI_FOCUSED, 0))) == -1)\r
2181                 Ret = 0;\r
2182 \r
2183         return(Ret);\r
2184 }\r
2185 \r
2186 \r
2187 /*----- アイテム数を返す ------------------------------------------------------\r
2188 *\r
2189 *       Parameter\r
2190 *               int Win : ウィンドウ番号 (WIN_xxxx)\r
2191 *\r
2192 *       Return Value\r
2193 *               int アイテム数\r
2194 *----------------------------------------------------------------------------*/\r
2195 \r
2196 int GetItemCount(int Win)\r
2197 {\r
2198         HWND hWnd;\r
2199 \r
2200         hWnd = GetLocalHwnd();\r
2201         if(Win == WIN_REMOTE)\r
2202                 hWnd = GetRemoteHwnd();\r
2203 \r
2204         return(SendMessage(hWnd, LVM_GETITEMCOUNT, 0, 0));\r
2205 }\r
2206 \r
2207 \r
2208 /*----- 選択されているアイテム数を返す ----------------------------------------\r
2209 *\r
2210 *       Parameter\r
2211 *               int Win : ウィンドウ番号 (WIN_xxxx)\r
2212 *\r
2213 *       Return Value\r
2214 *               int 選択されているアイテム数\r
2215 *----------------------------------------------------------------------------*/\r
2216 \r
2217 int GetSelectedCount(int Win)\r
2218 {\r
2219         HWND hWnd;\r
2220 \r
2221         hWnd = GetLocalHwnd();\r
2222         if(Win == WIN_REMOTE)\r
2223                 hWnd = GetRemoteHwnd();\r
2224 \r
2225         return(SendMessage(hWnd, LVM_GETSELECTEDCOUNT, 0, 0));\r
2226 }\r
2227 \r
2228 \r
2229 /*----- 選択されている最初のアイテム番号を返す --------------------------------\r
2230 *\r
2231 *       Parameter\r
2232 *               int Win : ウィンドウ番号 (WIN_xxxx)\r
2233 *               int All : 選ばれていないものを含める\r
2234 *\r
2235 *       Return Value\r
2236 *               int アイテム番号\r
2237 *                       -1 = 選択されていない\r
2238 *----------------------------------------------------------------------------*/\r
2239 \r
2240 int GetFirstSelected(int Win, int All)\r
2241 {\r
2242         HWND hWnd;\r
2243         int Ope;\r
2244 \r
2245         hWnd = GetLocalHwnd();\r
2246         if(Win == WIN_REMOTE)\r
2247                 hWnd = GetRemoteHwnd();\r
2248 \r
2249         Ope = LVNI_SELECTED;\r
2250         if(All == YES)\r
2251                 Ope = LVNI_ALL;\r
2252 \r
2253         return(SendMessage(hWnd, LVM_GETNEXTITEM, (WPARAM)-1, (LPARAM)MAKELPARAM(Ope, 0)));\r
2254 }\r
2255 \r
2256 \r
2257 /*----- 選択されている次のアイテム番号を返す ----------------------------------\r
2258 *\r
2259 *       Parameter\r
2260 *               int Win : ウィンドウ番号 (WIN_xxxx)\r
2261 *               int Pos : 今のアイテム番号\r
2262 *               int All : 選ばれていないものも含める\r
2263 *\r
2264 *       Return Value\r
2265 *               int アイテム番号\r
2266 *                       -1 = 選択されていない\r
2267 *----------------------------------------------------------------------------*/\r
2268 \r
2269 int GetNextSelected(int Win, int Pos, int All)\r
2270 {\r
2271         HWND hWnd;\r
2272         int Ope;\r
2273 \r
2274         hWnd = GetLocalHwnd();\r
2275         if(Win == WIN_REMOTE)\r
2276                 hWnd = GetRemoteHwnd();\r
2277 \r
2278         Ope = LVNI_SELECTED;\r
2279         if(All == YES)\r
2280                 Ope = LVNI_ALL;\r
2281 \r
2282         return(SendMessage(hWnd, LVM_GETNEXTITEM, (WPARAM)Pos, (LPARAM)MAKELPARAM(Ope, 0)));\r
2283 }\r
2284 \r
2285 \r
2286 /*----- 指定された名前のアイテムを探す ----------------------------------------\r
2287 *\r
2288 *       Parameter\r
2289 *               int Win : ウインドウ番号 (WIN_xxx)\r
2290 *               char *Name : 名前\r
2291 *\r
2292 *       Return Value\r
2293 *               int アイテム番号\r
2294 *                       -1=見つからなかった\r
2295 *----------------------------------------------------------------------------*/\r
2296 \r
2297 int FindNameNode(int Win, char *Name)\r
2298 {\r
2299         LV_FINDINFO FindInfo;\r
2300         HWND hWnd;\r
2301 \r
2302         hWnd = GetLocalHwnd();\r
2303         if(Win == WIN_REMOTE)\r
2304                 hWnd = GetRemoteHwnd();\r
2305 \r
2306         // 変数が未初期化のバグ修正\r
2307         memset(&FindInfo, 0, sizeof(LV_FINDINFO));\r
2308         FindInfo.flags = LVFI_STRING;\r
2309         FindInfo.psz = Name;\r
2310         return(SendMessage(hWnd, LVM_FINDITEM, -1, (LPARAM)&FindInfo));\r
2311 }\r
2312 \r
2313 \r
2314 /*----- 指定位置のアイテムの名前を返す ----------------------------------------\r
2315 *\r
2316 *       Parameter\r
2317 *               int Win : ウインドウ番号 (WIN_xxx)\r
2318 *               int Pos : 位置\r
2319 *               char *Buf : 名前を返すバッファ\r
2320 *               int Max : バッファのサイズ\r
2321 *\r
2322 *       Return Value\r
2323 *               なし\r
2324 *----------------------------------------------------------------------------*/\r
2325 \r
2326 void GetNodeName(int Win, int Pos, char *Buf, int Max)\r
2327 {\r
2328         HWND hWnd;\r
2329         LV_ITEM LvItem;\r
2330 \r
2331         hWnd = GetLocalHwnd();\r
2332         if(Win == WIN_REMOTE)\r
2333                 hWnd = GetRemoteHwnd();\r
2334 \r
2335         // 変数が未初期化のバグ修正\r
2336         memset(&LvItem, 0, sizeof(LV_ITEM));\r
2337         LvItem.mask = LVIF_TEXT;\r
2338         LvItem.iItem = Pos;\r
2339         LvItem.iSubItem = 0;\r
2340         LvItem.pszText = Buf;\r
2341         LvItem.cchTextMax = Max;\r
2342         SendMessage(hWnd, LVM_GETITEM, 0, (LPARAM)&LvItem);\r
2343         return;\r
2344 }\r
2345 \r
2346 \r
2347 /*----- 指定位置のアイテムの日付を返す ----------------------------------------\r
2348 *\r
2349 *       Parameter\r
2350 *               int Win : ウインドウ番号 (WIN_xxx)\r
2351 *               int Pos : 位置\r
2352 *               FILETIME *Buf : 日付を返すバッファ\r
2353 *\r
2354 *       Return Value\r
2355 *               int ステータス\r
2356 *                       YES/NO=日付情報がなかった\r
2357 *----------------------------------------------------------------------------*/\r
2358 \r
2359 int GetNodeTime(int Win, int Pos, FILETIME *Buf)\r
2360 {\r
2361         HWND hWnd;\r
2362         LV_ITEM LvItem;\r
2363         char Tmp[20];\r
2364         int Ret;\r
2365 \r
2366         hWnd = GetLocalHwnd();\r
2367         if(Win == WIN_REMOTE)\r
2368                 hWnd = GetRemoteHwnd();\r
2369 \r
2370         // 変数が未初期化のバグ修正\r
2371         memset(&LvItem, 0, sizeof(LV_ITEM));\r
2372         LvItem.mask = LVIF_TEXT;\r
2373         LvItem.iItem = Pos;\r
2374         LvItem.iSubItem = 1;\r
2375         LvItem.pszText = Tmp;\r
2376         LvItem.cchTextMax = 20;\r
2377         SendMessage(hWnd, LVM_GETITEM, 0, (LPARAM)&LvItem);\r
2378         Ret = TimeString2FileTime(Tmp, Buf);\r
2379         return(Ret);\r
2380 }\r
2381 \r
2382 \r
2383 /*----- 指定位置のアイテムのサイズを返す --------------------------------------\r
2384 *\r
2385 *       Parameter\r
2386 *               int Win : ウインドウ番号 (WIN_xxx)\r
2387 *               int Pos : 位置\r
2388 *               int *Buf : サイズを返すワーク\r
2389 *\r
2390 *       Return Value\r
2391 *               int ステータス\r
2392 *                       YES/NO=サイズ情報がなかった\r
2393 *----------------------------------------------------------------------------*/\r
2394 \r
2395 int GetNodeSize(int Win, int Pos, LONGLONG *Buf)\r
2396 {\r
2397         HWND hWnd;\r
2398         LV_ITEM LvItem;\r
2399         char Tmp[40];\r
2400         int Ret;\r
2401 \r
2402         hWnd = GetLocalHwnd();\r
2403         if(Win == WIN_REMOTE)\r
2404                 hWnd = GetRemoteHwnd();\r
2405 \r
2406         // 変数が未初期化のバグ修正\r
2407         memset(&LvItem, 0, sizeof(LV_ITEM));\r
2408         LvItem.mask = LVIF_TEXT;\r
2409         LvItem.iItem = Pos;\r
2410         LvItem.iSubItem = 2;\r
2411         LvItem.pszText = Tmp;\r
2412         LvItem.cchTextMax = 20;\r
2413         SendMessage(hWnd, LVM_GETITEM, 0, (LPARAM)&LvItem);\r
2414         *Buf = -1;\r
2415         Ret = NO;\r
2416 #if defined(HAVE_TANDEM)\r
2417         if(AskHostType() == HTYPE_TANDEM) {\r
2418                 RemoveComma(Tmp);\r
2419                 *Buf = _atoi64(Tmp);\r
2420                 Ret = YES;\r
2421         } else\r
2422 #endif\r
2423         if(strlen(Tmp) > 0)\r
2424         {\r
2425                 RemoveComma(Tmp);\r
2426                 *Buf = _atoi64(Tmp);\r
2427                 Ret = YES;\r
2428         }\r
2429         return(Ret);\r
2430 }\r
2431 \r
2432 \r
2433 /*----- 指定位置のアイテムの属性を返す ----------------------------------------\r
2434 *\r
2435 *       Parameter\r
2436 *               int Win : ウインドウ番号 (WIN_xxx)\r
2437 *               int Pos : 位置\r
2438 *               int *Buf : 属性を返すワーク\r
2439 *\r
2440 *       Return Value\r
2441 *               int ステータス\r
2442 *                       YES/NO=サイズ情報がなかった\r
2443 *----------------------------------------------------------------------------*/\r
2444 \r
2445 int GetNodeAttr(int Win, int Pos, int *Buf)\r
2446 {\r
2447         LV_ITEM LvItem;\r
2448         char Tmp[20];\r
2449         int Ret;\r
2450 \r
2451         *Buf = 0;\r
2452         Ret = NO;\r
2453         if(Win == WIN_REMOTE)\r
2454         {\r
2455                 // 変数が未初期化のバグ修正\r
2456                 memset(&LvItem, 0, sizeof(LV_ITEM));\r
2457                 LvItem.mask = LVIF_TEXT;\r
2458                 LvItem.iItem = Pos;\r
2459 #if defined(HAVE_TANDEM)\r
2460                 if(AskHostType() == HTYPE_TANDEM)\r
2461                         LvItem.iSubItem = 3;\r
2462                 else\r
2463 #endif\r
2464                 LvItem.iSubItem = 4;\r
2465                 LvItem.pszText = Tmp;\r
2466                 LvItem.cchTextMax = 20;\r
2467                 SendMessage(GetRemoteHwnd(), LVM_GETITEM, 0, (LPARAM)&LvItem);\r
2468                 if(strlen(Tmp) > 0)\r
2469                 {\r
2470 #if defined(HAVE_TANDEM)\r
2471                         if(AskHostType() == HTYPE_TANDEM)\r
2472                                 *Buf = atoi(Tmp);\r
2473                         else\r
2474 #endif\r
2475                         *Buf = AttrString2Value(Tmp);\r
2476                         Ret = YES;\r
2477                 }\r
2478         }\r
2479         return(Ret);\r
2480 }\r
2481 \r
2482 \r
2483 /*----- 指定位置のアイテムのタイプを返す --------------------------------------\r
2484 *\r
2485 *       Parameter\r
2486 *               int Win : ウインドウ番号 (WIN_xxx)\r
2487 *               int Pos : 位置\r
2488 *\r
2489 *       Return Value\r
2490 *               int タイプ (NODE_xxx)\r
2491 *----------------------------------------------------------------------------*/\r
2492 \r
2493 int GetNodeType(int Win, int Pos)\r
2494 {\r
2495         char Tmp[20];\r
2496         LV_ITEM LvItem;\r
2497         int Ret;\r
2498         HWND hWnd;\r
2499 \r
2500         hWnd = GetLocalHwnd();\r
2501         if(Win == WIN_REMOTE)\r
2502                 hWnd = GetRemoteHwnd();\r
2503 \r
2504         // 変数が未初期化のバグ修正\r
2505         memset(&LvItem, 0, sizeof(LV_ITEM));\r
2506         LvItem.mask = LVIF_TEXT;\r
2507         LvItem.iItem = Pos;\r
2508         LvItem.iSubItem = 2;\r
2509         LvItem.pszText = Tmp;\r
2510         LvItem.cchTextMax = 20;\r
2511         SendMessage(hWnd, LVM_GETITEM, 0, (LPARAM)&LvItem);\r
2512 \r
2513         if(strcmp(Tmp, "<DIR>") == 0)\r
2514                 Ret = NODE_DIR;\r
2515         else if(strcmp(Tmp, "<DRIVE>") == 0)\r
2516                 Ret = NODE_DRIVE;\r
2517         else\r
2518                 Ret = NODE_FILE;\r
2519 \r
2520         return(Ret);\r
2521 }\r
2522 \r
2523 \r
2524 /*----- 指定位置のアイテムのオーナ名を返す ------------------------------------\r
2525 *\r
2526 *       Parameter\r
2527 *               int Win : ウインドウ番号 (WIN_xxx)\r
2528 *               int Pos : 位置\r
2529 *               char *Buf : オーナ名を返すバッファ\r
2530 *               int Max : バッファのサイズ\r
2531 *\r
2532 *       Return Value\r
2533 *               なし\r
2534 *----------------------------------------------------------------------------*/\r
2535 \r
2536 void GetNodeOwner(int Win, int Pos, char *Buf, int Max)\r
2537 {\r
2538         LV_ITEM LvItem;\r
2539 \r
2540         strcpy(Buf, "");\r
2541         if(Win == WIN_REMOTE)\r
2542         {\r
2543                 // 変数が未初期化のバグ修正\r
2544                 memset(&LvItem, 0, sizeof(LV_ITEM));\r
2545                 LvItem.mask = LVIF_TEXT;\r
2546                 LvItem.iItem = Pos;\r
2547                 LvItem.iSubItem = 5;\r
2548                 LvItem.pszText = Buf;\r
2549                 LvItem.cchTextMax = Max;\r
2550                 SendMessage(GetRemoteHwnd(), LVM_GETITEM, 0, (LPARAM)&LvItem);\r
2551         }\r
2552         return;\r
2553 }\r
2554 \r
2555 \r
2556 /*----- ホスト側のファイル一覧ウインドウをクリア ------------------------------\r
2557 *\r
2558 *       Parameter\r
2559 *               なし\r
2560 *\r
2561 *       Return Value\r
2562 *               なし\r
2563 *----------------------------------------------------------------------------*/\r
2564 \r
2565 void EraseRemoteDirForWnd(void)\r
2566 {\r
2567         SendMessage(GetRemoteHwnd(), LVM_DELETEALLITEMS, 0, 0);\r
2568         SendMessage(GetRemoteHistHwnd(), CB_RESETCONTENT, 0, 0);\r
2569         return;\r
2570 }\r
2571 \r
2572 \r
2573 /*----- 選択されているファイルの総サイズを返す --------------------------------\r
2574 *\r
2575 *       Parameter\r
2576 *               int Win : ウインドウ番号 (WIN_xxx)\r
2577 *\r
2578 *       Return Value\r
2579 *               double サイズ\r
2580 *----------------------------------------------------------------------------*/\r
2581 \r
2582 double GetSelectedTotalSize(int Win)\r
2583 {\r
2584         double Ret;\r
2585         LONGLONG Size;\r
2586         int Pos;\r
2587 \r
2588         Ret = 0;\r
2589         if(GetSelectedCount(Win) > 0)\r
2590         {\r
2591                 Pos = GetFirstSelected(Win, NO);\r
2592                 while(Pos != -1)\r
2593                 {\r
2594                         GetNodeSize(Win, Pos, &Size);\r
2595                         if(Size >= 0)\r
2596                                 Ret += Size;\r
2597                         Pos = GetNextSelected(Win, Pos, NO);\r
2598                 }\r
2599         }\r
2600         return(Ret);\r
2601 }\r
2602 \r
2603 \r
2604 \r
2605 /*===================================================================\r
2606 \r
2607 ===================================================================*/\r
2608 \r
2609 \r
2610 \r
2611 /*----- ファイル一覧で選ばれているファイルをリストに登録する ------------------\r
2612 *\r
2613 *       Parameter\r
2614 *               int Win : ウインドウ番号 (WIN_xxx)\r
2615 *               int Expand : サブディレクトリを展開する (YES/NO)\r
2616 *               int All : 選ばれていないものもすべて登録する (YES/NO)\r
2617 *               FILELIST **Base : ファイルリストの先頭\r
2618 *\r
2619 *       Return Value\r
2620 *               なし\r
2621 *----------------------------------------------------------------------------*/\r
2622 \r
2623 void MakeSelectedFileList(int Win, int Expand, int All, FILELIST **Base, int *CancelCheckWork)\r
2624 {\r
2625         int Pos;\r
2626         char Name[FMAX_PATH+1];\r
2627         char Cur[FMAX_PATH+1];\r
2628         FILELIST Pkt;\r
2629         int Node;\r
2630         DWORD Attr;\r
2631         int Ignore;\r
2632 \r
2633         if((All == YES) || (GetSelectedCount(Win) > 0))\r
2634         {\r
2635                 /*===== カレントディレクトリのファイル =====*/\r
2636 \r
2637                 Pos = GetFirstSelected(Win, All);\r
2638                 while(Pos != -1)\r
2639                 {\r
2640                         Node = GetNodeType(Win, Pos);\r
2641                         if((Node == NODE_FILE) ||\r
2642                            ((Expand == NO) && (Node == NODE_DIR)))\r
2643                         {\r
2644                                 Pkt.InfoExist = 0;\r
2645                                 GetNodeName(Win, Pos, Pkt.File, FMAX_PATH);\r
2646                                 if(GetNodeSize(Win, Pos, &Pkt.Size) == YES)\r
2647                                         Pkt.InfoExist |= FINFO_SIZE;\r
2648                                 if(GetNodeAttr(Win, Pos, &Pkt.Attr) == YES)\r
2649                                         Pkt.InfoExist |= FINFO_ATTR;\r
2650                                 if(GetNodeTime(Win, Pos, &Pkt.Time) == YES)\r
2651                                         Pkt.InfoExist |= (FINFO_TIME | FINFO_DATE);\r
2652                                 Pkt.Node = Node;\r
2653 \r
2654                                 Ignore = NO;\r
2655                                 if((DispIgnoreHide == YES) && (Win == WIN_LOCAL))\r
2656                                 {\r
2657                                         AskLocalCurDir(Cur, FMAX_PATH);\r
2658                                         SetYenTail(Cur);\r
2659                                         strcat(Cur, Pkt.File);\r
2660                                         Attr = GetFileAttributes(Cur);\r
2661                                         if((Attr != 0xFFFFFFFF) && (Attr & FILE_ATTRIBUTE_HIDDEN))\r
2662                                                 Ignore = YES;\r
2663                                 }\r
2664 \r
2665                                 if(Ignore == NO)\r
2666                                         AddFileList(&Pkt, Base);\r
2667                         }\r
2668                         Pos = GetNextSelected(Win, Pos, All);\r
2669                 }\r
2670 \r
2671                 if(Expand == YES)\r
2672                 {\r
2673                         /*===== ディレクトリツリー =====*/\r
2674 \r
2675                         Pos = GetFirstSelected(Win, All);\r
2676                         while(Pos != -1)\r
2677                         {\r
2678                                 if(GetNodeType(Win, Pos) == NODE_DIR)\r
2679                                 {\r
2680                                         GetNodeName(Win, Pos, Name, FMAX_PATH);\r
2681                                         strcpy(Pkt.File, Name);\r
2682                                         ReplaceAll(Pkt.File, '\\', '/');\r
2683 //8/26\r
2684 \r
2685                                         Ignore = NO;\r
2686                                         if((DispIgnoreHide == YES) && (Win == WIN_LOCAL))\r
2687                                         {\r
2688                                                 AskLocalCurDir(Cur, FMAX_PATH);\r
2689                                                 SetYenTail(Cur);\r
2690                                                 strcat(Cur, Pkt.File);\r
2691                                                 ReplaceAll(Cur, '/', '\\');\r
2692                                                 Attr = GetFileAttributes(Cur);\r
2693                                                 if((Attr != 0xFFFFFFFF) && (Attr & FILE_ATTRIBUTE_HIDDEN))\r
2694                                                         Ignore = YES;\r
2695                                         }\r
2696 \r
2697                                         if(Ignore == NO)\r
2698                                         {\r
2699                                                 Pkt.Node = NODE_DIR;\r
2700                                                 Pkt.Attr = 0;\r
2701                                                 Pkt.Size = 0;\r
2702                                                 memset(&Pkt.Time, 0, sizeof(FILETIME));\r
2703                                                 AddFileList(&Pkt, Base);\r
2704 \r
2705                                                 if(Win == WIN_LOCAL)\r
2706                                                         MakeLocalTree(Name, Base);\r
2707                                                 else\r
2708                                                 {\r
2709                                                         AskRemoteCurDir(Cur, FMAX_PATH);\r
2710 \r
2711                                                         if((AskListCmdMode() == NO) &&\r
2712                                                            (AskUseNLST_R() == YES))\r
2713                                                                 MakeRemoteTree1(Name, Cur, Base, CancelCheckWork);\r
2714                                                         else\r
2715                                                                 MakeRemoteTree2(Name, Cur, Base, CancelCheckWork);\r
2716 \r
2717 //DispListList(*Base, "LIST");\r
2718 \r
2719                                                 }\r
2720                                         }\r
2721                                 }\r
2722                                 Pos = GetNextSelected(Win, Pos, All);\r
2723                         }\r
2724                 }\r
2725         }\r
2726         return;\r
2727 }\r
2728 \r
2729 \r
2730 /* デバッグ用 */\r
2731 /* ファイルリストの内容を表示 */\r
2732 static void DispListList(FILELIST *Pos, char *Title)\r
2733 {\r
2734         DoPrintf("############ %s ############", Title);\r
2735         while(Pos != NULL)\r
2736         {\r
2737                 DoPrintf("%d %s", Pos->Node, Pos->File);\r
2738                 Pos = Pos->Next;\r
2739         }\r
2740         DoPrintf("############ END ############");\r
2741         return;\r
2742 }\r
2743 \r
2744 \r
2745 /*----- Drag&Dropされたファイルをリストに登録する -----------------------------\r
2746 *\r
2747 *       Parameter\r
2748 *               WPARAM wParam : ドロップされたファイルの情報\r
2749 *               char *Cur : カレントディレクトリを返すバッファ\r
2750 *               FILELIST **Base : ファイルリストの先頭\r
2751 *\r
2752 *       Return Value\r
2753 *               なし\r
2754 *----------------------------------------------------------------------------*/\r
2755 \r
2756 void MakeDroppedFileList(WPARAM wParam, char *Cur, FILELIST **Base)\r
2757 {\r
2758         int Max;\r
2759         int i;\r
2760         char Name[FMAX_PATH+1];\r
2761         char Tmp[FMAX_PATH+1];\r
2762         FILELIST Pkt;\r
2763         HANDLE fHnd;\r
2764         WIN32_FIND_DATA Find;\r
2765 \r
2766         Max = DragQueryFile((HDROP)wParam, 0xFFFFFFFF, NULL, 0);\r
2767 \r
2768         DragQueryFile((HDROP)wParam, 0, Cur, FMAX_PATH);\r
2769         GetUpperDir(Cur);\r
2770 \r
2771         for(i = 0; i < Max; i++)\r
2772         {\r
2773                 DragQueryFile((HDROP)wParam, i, Name, FMAX_PATH);\r
2774 \r
2775                 if((GetFileAttributes(Name) & FILE_ATTRIBUTE_DIRECTORY) == 0)\r
2776                 {\r
2777                         Pkt.Node = NODE_FILE;\r
2778                         strcpy(Pkt.File, GetFileName(Name));\r
2779 \r
2780                         memset(&Pkt.Time, 0, sizeof(FILETIME));\r
2781 #if defined(HAVE_TANDEM)\r
2782                         /* Guardian スペースへのアップロードのためにサイズが必要 */\r
2783                         Pkt.Size = 0;\r
2784                         Pkt.InfoExist = 0;\r
2785 #endif\r
2786                         if((fHnd = FindFirstFile(Name, &Find)) != INVALID_HANDLE_VALUE)\r
2787                         {\r
2788                                 FindClose(fHnd);\r
2789                                 Pkt.Time = Find.ftLastWriteTime;\r
2790 #if defined(HAVE_TANDEM)\r
2791                                 Pkt.Size = MakeLongLong(Find.nFileSizeHigh, Find.nFileSizeLow);\r
2792                                 Pkt.InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE);\r
2793 #endif\r
2794                         }\r
2795                         AddFileList(&Pkt, Base);\r
2796                 }\r
2797         }\r
2798 \r
2799         GetCurrentDirectory(FMAX_PATH, Tmp);\r
2800         SetCurrentDirectory(Cur);\r
2801         for(i = 0; i < Max; i++)\r
2802         {\r
2803                 DragQueryFile((HDROP)wParam, i, Name, FMAX_PATH);\r
2804 \r
2805                 if(GetFileAttributes(Name) & FILE_ATTRIBUTE_DIRECTORY)\r
2806                 {\r
2807                         Pkt.Node = NODE_DIR;\r
2808                         strcpy(Pkt.File, GetFileName(Name));\r
2809                         AddFileList(&Pkt, Base);\r
2810 \r
2811                         MakeLocalTree(Pkt.File, Base);\r
2812                 }\r
2813         }\r
2814         SetCurrentDirectory(Tmp);\r
2815 \r
2816         DragFinish((HDROP)wParam);\r
2817 \r
2818         return;\r
2819 }\r
2820 \r
2821 \r
2822 /*----- Drag&Dropされたファイルがあるフォルダを取得する -----------------------\r
2823 *\r
2824 *       Parameter\r
2825 *               WPARAM wParam : ドロップされたファイルの情報\r
2826 *               char *Cur : カレントディレクトリを返すバッファ\r
2827 *\r
2828 *       Return Value\r
2829 *               なし\r
2830 *----------------------------------------------------------------------------*/\r
2831 \r
2832 void MakeDroppedDir(WPARAM wParam, char *Cur)\r
2833 {\r
2834         int Max;\r
2835 \r
2836         Max = DragQueryFile((HDROP)wParam, 0xFFFFFFFF, NULL, 0);\r
2837         DragQueryFile((HDROP)wParam, 0, Cur, FMAX_PATH);\r
2838         GetUpperDir(Cur);\r
2839         DragFinish((HDROP)wParam);\r
2840 \r
2841         return;\r
2842 }\r
2843 \r
2844 \r
2845 /*----- ホスト側のサブディレクトリ以下のファイルをリストに登録する(1)-------\r
2846 *\r
2847 *       Parameter\r
2848 *               char *Path : パス名\r
2849 *               char *Cur : カレントディレクトリ\r
2850 *               FILELIST **Base : ファイルリストの先頭\r
2851 *\r
2852 *       Return Value\r
2853 *               なし\r
2854 *\r
2855 *       Note\r
2856 *               NLST -alLR を使う\r
2857 *----------------------------------------------------------------------------*/\r
2858 \r
2859 static void MakeRemoteTree1(char *Path, char *Cur, FILELIST **Base, int *CancelCheckWork)\r
2860 {\r
2861         int Sts;\r
2862 \r
2863         if(DoCWD(Path, NO, NO, NO) == FTP_COMPLETE)\r
2864         {\r
2865                 /* サブフォルダも含めたリストを取得 */\r
2866                 Sts = DoDirListCmdSkt("R", "", 999, CancelCheckWork);   /* NLST -alLR*/\r
2867                 DoCWD(Cur, NO, NO, NO);\r
2868 \r
2869                 if(Sts == FTP_COMPLETE)\r
2870                         AddRemoteTreeToFileList(999, Path, RDIR_NLST, Base);\r
2871         }\r
2872         return;\r
2873 }\r
2874 \r
2875 \r
2876 /*----- ホスト側のサブディレクトリ以下のファイルをリストに登録する(2)-------\r
2877 *\r
2878 *       Parameter\r
2879 *               char *Path : パス名\r
2880 *               char *Cur : カレントディレクトリ\r
2881 *               FILELIST **Base : ファイルリストの先頭\r
2882 *\r
2883 *       Return Value\r
2884 *               なし\r
2885 *\r
2886 *       Note\r
2887 *               各フォルダに移動してリストを取得\r
2888 *----------------------------------------------------------------------------*/\r
2889 \r
2890 static void MakeRemoteTree2(char *Path, char *Cur, FILELIST **Base, int *CancelCheckWork)\r
2891 {\r
2892         int Sts;\r
2893         FILELIST *CurList;\r
2894         FILELIST *Pos;\r
2895         FILELIST Pkt;\r
2896 \r
2897         /* VAX VMS は CWD xxx/yyy という指定ができないので */\r
2898         /* CWD xxx, Cwd yyy と複数に分ける                                       */\r
2899         if(AskHostType() != HTYPE_VMS)\r
2900                 Sts = DoCWD(Path, NO, NO, NO);\r
2901         else\r
2902         {\r
2903 #if defined(HAVE_OPENVMS)\r
2904                 /* OpenVMSの場合、ディレクトリ移動時は"HOGE.DIR;1"を"HOGE"にする */\r
2905                 ReformVMSDirName(Path, TRUE);\r
2906 #endif\r
2907                 Sts = DoCWDStepByStep(Path, Cur);\r
2908         }\r
2909 \r
2910         if(Sts == FTP_COMPLETE)\r
2911         {\r
2912                 Sts = DoDirListCmdSkt("", "", 999, CancelCheckWork);            /* NLST -alL*/\r
2913                 DoCWD(Cur, NO, NO, NO);\r
2914 \r
2915                 if(Sts == FTP_COMPLETE)\r
2916                 {\r
2917                         CurList = NULL;\r
2918                         AddRemoteTreeToFileList(999, Path, RDIR_CWD, &CurList);\r
2919                         CopyTmpListToFileList(Base, CurList);\r
2920 \r
2921                         Pos = CurList;\r
2922                         while(Pos != NULL)\r
2923                         {\r
2924                                 if(Pos->Node == NODE_DIR)\r
2925                                 {\r
2926                                         /* まずディレクトリ名をセット */\r
2927                                         strcpy(Pkt.File, Pos->File);\r
2928                                         Pkt.Node = NODE_DIR;\r
2929                                         Pkt.Size = 0;\r
2930                                         Pkt.Attr = 0;\r
2931                                         memset(&Pkt.Time, 0, sizeof(FILETIME));\r
2932                                         AddFileList(&Pkt, Base);\r
2933 \r
2934                                         /* そのディレクトリの中を検索 */\r
2935                                         MakeRemoteTree2(Pos->File, Cur, Base, CancelCheckWork);\r
2936                                 }\r
2937                                 Pos = Pos->Next;\r
2938                         }\r
2939                         DeleteFileList(&CurList);\r
2940                 }\r
2941         }\r
2942         return;\r
2943 }\r
2944 \r
2945 \r
2946 /*----- ファイルリストの内容を別のファイルリストにコピー ----------------------\r
2947 *\r
2948 *       Parameter\r
2949 *               FILELIST **Base : コピー先\r
2950 *               FILELIST *List : コピー元\r
2951 *\r
2952 *       Return Value\r
2953 *               なし\r
2954 *\r
2955 *       Note\r
2956 *               コピーするのはファイルの情報だけ\r
2957 *               ディレクトリの情報はコピーしない\r
2958 *----------------------------------------------------------------------------*/\r
2959 \r
2960 static void CopyTmpListToFileList(FILELIST **Base, FILELIST *List)\r
2961 {\r
2962         while(List != NULL)\r
2963         {\r
2964                 if(List->Node == NODE_FILE)\r
2965                         AddFileList(List, Base);\r
2966 \r
2967                 List = List->Next;\r
2968         }\r
2969         return;\r
2970 }\r
2971 \r
2972 \r
2973 /*----- ホスト側のファイル情報をファイルリストに登録 --------------------------\r
2974 *\r
2975 *       Parameter\r
2976 *               int Num : テンポラリファイルのファイル名番号 (_ffftp.???)\r
2977 *               char *Path : パス名\r
2978 *               int IncDir : 再帰検索の方法 (RDIR_xxx)\r
2979 *               FILELIST **Base : ファイルリストの先頭\r
2980 *\r
2981 *       Return Value\r
2982 *               なし\r
2983 *----------------------------------------------------------------------------*/\r
2984 \r
2985 void AddRemoteTreeToFileList(int Num, char *Path, int IncDir, FILELIST **Base)\r
2986 {\r
2987         char Str[FMAX_PATH+1];\r
2988         char Dir[FMAX_PATH+1];\r
2989         char Name[FMAX_PATH+1];\r
2990         LONGLONG Size;\r
2991         FILETIME Time;\r
2992         int Attr;\r
2993         FILELIST Pkt;\r
2994         FILE *fd;\r
2995         int Node;\r
2996         int ListType;\r
2997         char Owner[OWNER_NAME_LEN+1];\r
2998         int Link;\r
2999         int InfoExist;\r
3000 \r
3001         MakeCacheFileName(Num, Str);\r
3002         if((fd = fopen(Str, "rb")) != NULL)\r
3003         {\r
3004                 strcpy(Dir, Path);\r
3005 \r
3006                 ListType = LIST_UNKNOWN;\r
3007 \r
3008                 while(GetListOneLine(Str, FMAX_PATH, fd) == FFFTP_SUCCESS)\r
3009                 {\r
3010                         if((ListType = AnalizeFileInfo(Str)) == LIST_UNKNOWN)\r
3011                         {\r
3012                                 if(MakeDirPath(Str, ListType, Path, Dir) == FFFTP_SUCCESS)\r
3013                                 {\r
3014                                         if(IncDir == RDIR_NLST)\r
3015                                         {\r
3016                                                 strcpy(Pkt.File, Dir);\r
3017                                                 Pkt.Node = NODE_DIR;\r
3018                                                 Pkt.Size = 0;\r
3019                                                 Pkt.Attr = 0;\r
3020                                                 memset(&Pkt.Time, 0, sizeof(FILETIME));\r
3021                                                 AddFileList(&Pkt, Base);\r
3022                                         }\r
3023                                 }\r
3024                         }\r
3025                         else\r
3026                         {\r
3027                                 Node = ResolvFileInfo(Str, ListType, Name, &Size, &Time, &Attr, Owner, &Link, &InfoExist);\r
3028 \r
3029                                 if(AskFilterStr(Name, Node) == YES)\r
3030                                 {\r
3031                                         if((Node == NODE_FILE) ||\r
3032                                            ((IncDir == RDIR_CWD) && (Node == NODE_DIR)))\r
3033                                         {\r
3034                                                 strcpy(Pkt.File, Dir);\r
3035                                                 if(strlen(Pkt.File) > 0)\r
3036                                                         SetSlashTail(Pkt.File);\r
3037                                                 strcat(Pkt.File, Name);\r
3038                                                 Pkt.Node = Node;\r
3039                                                 Pkt.Link = Link;\r
3040                                                 Pkt.Size = Size;\r
3041                                                 Pkt.Attr = Attr;\r
3042                                                 Pkt.Time = Time;\r
3043                                                 Pkt.InfoExist = InfoExist;\r
3044                                                 AddFileList(&Pkt, Base);\r
3045                                         }\r
3046                                 }\r
3047                         }\r
3048                 }\r
3049                 fclose(fd);\r
3050         }\r
3051         return;\r
3052 }\r
3053 \r
3054 \r
3055 /*----- ファイル一覧情報の1行を取得 ------------------------------------------\r
3056 *\r
3057 *       Parameter\r
3058 *               char *Buf : 1行の情報をセットするバッファ\r
3059 *               int Max : 最大文字数\r
3060 *               FILE *Fd : ストリーム\r
3061 *\r
3062 *       Return Value\r
3063 *               int ステータス (FFFTP_SUCCESS/FFFTP_FAIL)\r
3064 *\r
3065 *       Note\r
3066 *               VAX VMS以外の時は fgets(Buf, Max, Fd) と同じ\r
3067 *               Vax VMSの時は、複数行のファイル情報を1行にまとめる\r
3068 *----------------------------------------------------------------------------*/\r
3069 \r
3070 static int GetListOneLine(char *Buf, int Max, FILE *Fd)\r
3071 {\r
3072         char Tmp[FMAX_PATH+1];\r
3073         int Sts;\r
3074 \r
3075         Sts = FFFTP_FAIL;\r
3076         while((Sts == FFFTP_FAIL) && (fgets(Buf, Max, Fd) != NULL))\r
3077         {\r
3078                 Sts = FFFTP_SUCCESS;\r
3079                 RemoveReturnCode(Buf);\r
3080                 ReplaceAll(Buf, '\x08', ' ');\r
3081 \r
3082                 /* VAX VMSではファイル情報が複数行にわかれている     */\r
3083                 /* それを1行にまとめる                                                               */\r
3084                 if(AskHostType() == HTYPE_VMS)\r
3085                 {\r
3086                         if(strchr(Buf, ';') == NULL)    /* ファイル名以外の行 */\r
3087                                 Sts = FFFTP_FAIL;\r
3088                         else\r
3089                         {\r
3090                                 Max -= strlen(Buf);\r
3091                                 while(strchr(Buf, ')') == NULL)\r
3092                                 {\r
3093                                         if(fgets(Tmp, FMAX_PATH, Fd) != NULL)\r
3094                                         {\r
3095                                                 RemoveReturnCode(Tmp);\r
3096                                                 ReplaceAll(Buf, '\x08', ' ');\r
3097                                                 if((int)strlen(Tmp) > Max)\r
3098                                                         Tmp[Max] = NUL;\r
3099                                                 Max -= strlen(Tmp);\r
3100                                                 strcat(Buf, Tmp);\r
3101                                         }\r
3102                                         else\r
3103                                                 break;\r
3104                                 }\r
3105                         }\r
3106                 }\r
3107         }\r
3108 \r
3109 //      DoPrintf("List : %s", Buf);\r
3110 \r
3111         return(Sts);\r
3112 }\r
3113 \r
3114 \r
3115 /*----- サブディレクトリ情報の解析 --------------------------------------------\r
3116 *\r
3117 *       Parameter\r
3118 *               char *Str : ファイル情報(1行)\r
3119 *               int ListType : リストのタイプ\r
3120 *               char *Path : 先頭からのパス名\r
3121 *               char *Dir : ディレクトリ名\r
3122 *\r
3123 *       Return Value\r
3124 *               int ステータス\r
3125 *                       FFFTP_SUCCESS/FFFTP_FAIL=ディレクトリ情報でない\r
3126 *----------------------------------------------------------------------------*/\r
3127 \r
3128 static int MakeDirPath(char *Str, int ListType, char *Path, char *Dir)\r
3129 {\r
3130         int Sts;\r
3131 \r
3132         Sts = FFFTP_FAIL;\r
3133         switch(ListType)\r
3134         {\r
3135                 case LIST_ACOS :\r
3136                 case LIST_ACOS_4 :\r
3137                         break;\r
3138 \r
3139                 default:\r
3140                         if(*(Str + strlen(Str) - 1) == ':')             /* 最後が : ならサブディレクトリ */\r
3141                         {\r
3142                                 if(strcmp(Str, ".:") != 0)\r
3143                                 {\r
3144                                         if((strncmp(Str, "./", 2) == 0) ||\r
3145                                            (strncmp(Str, ".\\", 2) == 0))\r
3146                                         {\r
3147                                                 Str += 2;\r
3148                                         }\r
3149 \r
3150                                         if(strlen(Str) > 1)\r
3151                                         {\r
3152                                                 strcpy(Dir, Path);\r
3153                                                 SetSlashTail(Dir);\r
3154                                                 strcat(Dir, Str);\r
3155                                                 *(Dir + strlen(Dir) - 1) = NUL;\r
3156 \r
3157                                                 ChangeFnameRemote2Local(Dir, FMAX_PATH);\r
3158 \r
3159                                                 ReplaceAll(Dir, '\\', '/');\r
3160                                         }\r
3161                                 }\r
3162                                 Sts = FFFTP_SUCCESS;\r
3163                         }\r
3164                         break;\r
3165         }\r
3166         return(Sts);\r
3167 }\r
3168 \r
3169 \r
3170 /*----- ローカル側のサブディレクトリ以下のファイルをリストに登録する ----------\r
3171 *\r
3172 *       Parameter\r
3173 *               char *Path : パス名\r
3174 *               FILELIST **Base : ファイルリストの先頭\r
3175 *\r
3176 *       Return Value\r
3177 *               なし\r
3178 *----------------------------------------------------------------------------*/\r
3179 \r
3180 static void MakeLocalTree(char *Path, FILELIST **Base)\r
3181 {\r
3182         char Src[FMAX_PATH+1];\r
3183         HANDLE fHnd;\r
3184         WIN32_FIND_DATA FindBuf;\r
3185         FILELIST Pkt;\r
3186         SYSTEMTIME TmpStime;\r
3187 \r
3188         strcpy(Src, Path);\r
3189         SetYenTail(Src);\r
3190         strcat(Src, "*");\r
3191         ReplaceAll(Src, '/', '\\');\r
3192 \r
3193         if((fHnd = FindFirstFileAttr(Src, &FindBuf, DispIgnoreHide)) != INVALID_HANDLE_VALUE)\r
3194         {\r
3195                 do\r
3196                 {\r
3197                         if((FindBuf.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) == 0)\r
3198                         {\r
3199                                 if(AskFilterStr(FindBuf.cFileName, NODE_FILE) == YES)\r
3200                                 {\r
3201                                         strcpy(Pkt.File, Path);\r
3202                                         SetSlashTail(Pkt.File);\r
3203                                         strcat(Pkt.File, FindBuf.cFileName);\r
3204                                         ReplaceAll(Pkt.File, '\\', '/');\r
3205                                         Pkt.Node = NODE_FILE;\r
3206                                         Pkt.Size = MakeLongLong(FindBuf.nFileSizeHigh, FindBuf.nFileSizeLow);\r
3207                                         Pkt.Attr = 0;\r
3208                                         Pkt.Time = FindBuf.ftLastWriteTime;\r
3209                                         FileTimeToSystemTime(&Pkt.Time, &TmpStime);\r
3210                                         TmpStime.wSecond = 0;\r
3211                                         TmpStime.wMilliseconds = 0;\r
3212                                         SystemTimeToFileTime(&TmpStime, &Pkt.Time);\r
3213                                         AddFileList(&Pkt, Base);\r
3214                                 }\r
3215                         }\r
3216                 }\r
3217                 while(FindNextFileAttr(fHnd, &FindBuf, DispIgnoreHide) == TRUE);\r
3218                 FindClose(fHnd);\r
3219         }\r
3220 \r
3221         if((fHnd = FindFirstFileAttr(Src, &FindBuf, DispIgnoreHide)) != INVALID_HANDLE_VALUE)\r
3222         {\r
3223                 do\r
3224                 {\r
3225                         if((FindBuf.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) &&\r
3226                            (strcmp(FindBuf.cFileName, ".") != 0) &&\r
3227                            (strcmp(FindBuf.cFileName, "..") != 0))\r
3228                         {\r
3229                                 strcpy(Src, Path);\r
3230                                 SetYenTail(Src);\r
3231                                 strcat(Src, FindBuf.cFileName);\r
3232                                 strcpy(Pkt.File, Src);\r
3233                                 ReplaceAll(Pkt.File, '\\', '/');\r
3234                                 Pkt.Node = NODE_DIR;\r
3235                                 Pkt.Size = 0;\r
3236                                 Pkt.Attr = 0;\r
3237                                 memset(&Pkt.Time, 0, sizeof(FILETIME));\r
3238                                 AddFileList(&Pkt, Base);\r
3239 \r
3240                                 MakeLocalTree(Src, Base);\r
3241                         }\r
3242                 }\r
3243                 while(FindNextFileAttr(fHnd, &FindBuf, DispIgnoreHide) == TRUE);\r
3244                 FindClose(fHnd);\r
3245         }\r
3246         return;\r
3247 }\r
3248 \r
3249 \r
3250 /*----- ファイルリストに情報を登録する ----------------------------------------\r
3251 *\r
3252 *       Parameter\r
3253 *               FILELIST *Pkt : 登録するファイル情報\r
3254 *               FILELIST **Base : ファイルリストの先頭\r
3255 *\r
3256 *       Return Value\r
3257 *               なし\r
3258 *----------------------------------------------------------------------------*/\r
3259 \r
3260 static void AddFileList(FILELIST *Pkt, FILELIST **Base)\r
3261 {\r
3262         FILELIST *Pos;\r
3263         FILELIST *Prev;\r
3264 \r
3265         DoPrintf("FileList : NODE=%d : %s", Pkt->Node, Pkt->File);\r
3266 \r
3267         /* リストの重複を取り除く */\r
3268         Pos = *Base;\r
3269         while(Pos != NULL)\r
3270         {\r
3271                 if(strcmp(Pkt->File, Pos->File) == 0)\r
3272                 {\r
3273                         DoPrintf(" --> Duplicate!!");\r
3274                         break;\r
3275                 }\r
3276                 Prev = Pos;\r
3277                 Pos = Pos->Next;\r
3278         }\r
3279 \r
3280         if(Pos == NULL)         /* 重複していないので登録する */\r
3281         {\r
3282                 if((Pos = malloc(sizeof(FILELIST))) != NULL)\r
3283                 {\r
3284                         memcpy(Pos, Pkt, sizeof(FILELIST));\r
3285                         Pos->Next = NULL;\r
3286 \r
3287                         if(*Base == NULL)\r
3288                                 *Base = Pos;\r
3289                         else\r
3290                                 Prev->Next = Pos;\r
3291                 }\r
3292         }\r
3293         return;\r
3294 }\r
3295 \r
3296 \r
3297 /*----- ファイルリストをクリアする --------------------------------------------\r
3298 *\r
3299 *       Parameter\r
3300 *               FILELIST **Base : ファイルリストの先頭\r
3301 *\r
3302 *       Return Value\r
3303 *               なし\r
3304 *----------------------------------------------------------------------------*/\r
3305 \r
3306 void DeleteFileList(FILELIST **Base)\r
3307 {\r
3308         FILELIST *New;\r
3309         FILELIST *Next;\r
3310 \r
3311         New = *Base;\r
3312         while(New != NULL)\r
3313         {\r
3314                 Next = New->Next;\r
3315                 free(New);\r
3316                 New = Next;\r
3317         }\r
3318         *Base = NULL;\r
3319         return;\r
3320 }\r
3321 \r
3322 \r
3323 /*----- ファイルリストに指定のファイルがあるかチェック ------------------------\r
3324 *\r
3325 *       Parameter\r
3326 *               char *Fname : ファイル名\r
3327 *               FILELIST *Base : ファイルリストの先頭\r
3328 *               int Caps : 大文字/小文字の区別モード (COMP_xxx)\r
3329 *\r
3330 *       Return Value\r
3331 *               FILELIST *見つかったファイルリストのデータ\r
3332 *                       NULL=見つからない\r
3333 *----------------------------------------------------------------------------*/\r
3334 \r
3335 FILELIST *SearchFileList(char *Fname, FILELIST *Base, int Caps)\r
3336 {\r
3337         char Tmp[FMAX_PATH+1];\r
3338 \r
3339         while(Base != NULL)\r
3340         {\r
3341                 if(Caps == COMP_STRICT)\r
3342                 {\r
3343                         if(_mbscmp(Fname, Base->File) == 0)\r
3344                                 break;\r
3345                 }\r
3346                 else\r
3347                 {\r
3348                         if(_mbsicmp(Fname, Base->File) == 0)\r
3349                         {\r
3350                                 if(Caps == COMP_IGNORE)\r
3351                                         break;\r
3352                                 else\r
3353                                 {\r
3354                                         strcpy(Tmp, Base->File);\r
3355                                         _mbslwr(Tmp);\r
3356                                         if(_mbscmp(Tmp, Base->File) == 0)\r
3357                                                 break;\r
3358                                 }\r
3359                         }\r
3360                 }\r
3361                 Base = Base->Next;\r
3362         }\r
3363         return(Base);\r
3364 }\r
3365 \r
3366 \r
3367 /*----- ファイル情報からリストタイプを求める ----------------------------------\r
3368 *\r
3369 *       Parameter\r
3370 *               char *Str : ファイル情報(1行)\r
3371 *\r
3372 *       Return Value\r
3373 *               int リストタイプ (LIST_xxx)\r
3374 *----------------------------------------------------------------------------*/\r
3375 \r
3376 static int AnalizeFileInfo(char *Str)\r
3377 {\r
3378         int Ret;\r
3379         char Tmp[FMAX_PATH+1];\r
3380         int Add1;\r
3381         int TmpInt;\r
3382         int Flag1;\r
3383         WORD Month;\r
3384         WORD Day;\r
3385 \r
3386 //DoPrintf("LIST : %s", Str);\r
3387 \r
3388         Ret = LIST_UNKNOWN;\r
3389         Flag1 = AskHostType();\r
3390         if(Flag1 == HTYPE_ACOS)\r
3391                 Ret = LIST_ACOS;\r
3392         else if(Flag1 == HTYPE_ACOS_4)\r
3393                 Ret = LIST_ACOS_4;\r
3394         else if(Flag1 == HTYPE_VMS)\r
3395                 Ret = LIST_VMS;\r
3396         else if(Flag1 == HTYPE_IRMX)\r
3397                 Ret = LIST_IRMX;\r
3398         else if(Flag1 == HTYPE_STRATUS)\r
3399                 Ret = LIST_STRATUS;\r
3400         else if(Flag1 == HTYPE_AGILENT)\r
3401                 Ret = LIST_AGILENT;\r
3402         else if(Flag1 == HTYPE_SHIBASOKU)\r
3403                 Ret = LIST_SHIBASOKU;\r
3404         else\r
3405         {\r
3406                 /* 以下のフォーマットをチェック */\r
3407                 /* LIST_UNIX_10, LIST_UNIX_20, LIST_UNIX_12, LIST_UNIX_22, LIST_UNIX_50, LIST_UNIX_60 */\r
3408                 /* MELCOM80 */\r
3409 \r
3410                 if(FindField(Str, Tmp, 0, NO) == FFFTP_SUCCESS)\r
3411                 {\r
3412                         /* MELCOM80は "d rwxrwxrwx" のようにスペースが空いている */\r
3413                         Flag1 = NO;\r
3414                         if((strlen(Tmp) == 1) && (strchr("-dDlL", Tmp[0]) != NULL))\r
3415                         {\r
3416                                 if(FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS)\r
3417                                 {\r
3418                                         if((strlen(Tmp) == 9) ||\r
3419                                            ((strlen(Tmp) > 9) && (IsDigit(Tmp[9]) != 0)))\r
3420                                         {\r
3421                                                 memmove(Str+1, Str+2, strlen(Str+2)+1);\r
3422                                                 FindField(Str, Tmp, 0, NO);\r
3423                                                 Flag1 = YES;\r
3424                                         }\r
3425                                 }\r
3426                         }\r
3427 \r
3428                         if(strlen(Tmp) >= 10)\r
3429                         {\r
3430                                 Add1 = 0;\r
3431                                 if((strlen(Tmp) > 10) && (IsDigit(Tmp[10]) != 0))\r
3432                                 {\r
3433                                         /* こういう時 */\r
3434                                         /*   drwxr-xr-x1234  owner group  1024  Nov 6 14:21 Linux/    */\r
3435                                         Add1 = -1;\r
3436                                 }\r
3437 \r
3438 ////////////\r
3439 // LIST_UNIX_60 support\r
3440                                 if(FindField(Str, Tmp, 7+Add1, NO) == FFFTP_SUCCESS)\r
3441                                 {\r
3442                                         GetMonth(Tmp, &Month, &Day);\r
3443                                         if(Month != 0)\r
3444                                         {\r
3445                                                 Ret = CheckUnixType(Str, Tmp, Add1, 2, Day);\r
3446                                         }\r
3447                                 }\r
3448 ///////////\r
3449 \r
3450 ////////////\r
3451 // LIST_UNIX_12 support\r
3452                                 if((Ret == LIST_UNKNOWN) &&\r
3453                                    (FindField(Str, Tmp, 6+Add1, NO) == FFFTP_SUCCESS))\r
3454                                 {\r
3455                                         GetMonth(Tmp, &Month, &Day);\r
3456                                         if(Month != 0)\r
3457                                         {\r
3458                                                 Ret = CheckUnixType(Str, Tmp, Add1, 0, Day);\r
3459                                         }\r
3460                                 }\r
3461 //////////////////\r
3462 \r
3463 ////////////\r
3464 // LIST_UNIX_70 support\r
3465                                 if((Ret == LIST_UNKNOWN) &&\r
3466                                    (FindField(Str, Tmp, 6+Add1, NO) == FFFTP_SUCCESS))\r
3467                                 {\r
3468                                         GetMonth(Tmp, &Month, &Day);\r
3469                                         if(Month != 0)\r
3470                                         {\r
3471                                                 Ret = CheckUnixType(Str, Tmp, Add1, 1, Day);\r
3472                                         }\r
3473                                 }\r
3474 ///////////\r
3475 \r
3476                                 if((Ret == LIST_UNKNOWN) &&\r
3477                                    (FindField(Str, Tmp, 5+Add1, NO) == FFFTP_SUCCESS))\r
3478                                 {\r
3479                                         GetMonth(Tmp, &Month, &Day);\r
3480                                         if(Month != 0)\r
3481                                         {\r
3482                                                 Ret = CheckUnixType(Str, Tmp, Add1, 0, Day);\r
3483                                         }\r
3484                                 }\r
3485 \r
3486                                 if((Ret == LIST_UNKNOWN) &&\r
3487                                    (FindField(Str, Tmp, 4+Add1, NO) == FFFTP_SUCCESS))\r
3488                                 {\r
3489                                         GetMonth(Tmp, &Month, &Day);\r
3490                                         if(Month != 0)\r
3491                                         {\r
3492                                                 Ret = CheckUnixType(Str, Tmp, Add1, -1, Day);\r
3493                                         }\r
3494                                 }\r
3495 \r
3496                                 if((Ret == LIST_UNKNOWN) &&\r
3497                                    (FindField(Str, Tmp, 3+Add1, NO) == FFFTP_SUCCESS))\r
3498                                 {\r
3499                                         GetMonth(Tmp, &Month, &Day);\r
3500                                         if(Month != 0)\r
3501                                         {\r
3502                                                 Ret = CheckUnixType(Str, Tmp, Add1, -2, Day);\r
3503                                         }\r
3504                                 }\r
3505 \r
3506                                 // linux-ftpd\r
3507                                 if((Ret == LIST_UNKNOWN) &&\r
3508                                    (FindField(Str, Tmp, 7+Add1, NO) == FFFTP_SUCCESS))\r
3509                                 {\r
3510                                         if((FindField(Str, Tmp, 5, NO) == FFFTP_SUCCESS) &&\r
3511                                            (CheckYYYYMMDDformat(Tmp, NUL) != 0))\r
3512                                         {\r
3513                                                 if((FindField(Str, Tmp, 6, NO) == FFFTP_SUCCESS) &&\r
3514                                                    (CheckHHMMformat(Tmp) == YES))\r
3515                                                 {\r
3516                                                         Ret = LIST_UNIX_16;\r
3517                                                 }\r
3518                                         }\r
3519                                 }\r
3520 \r
3521                                 if((Ret != LIST_UNKNOWN) && (Flag1 == YES))\r
3522                                         Ret |= LIST_MELCOM;\r
3523                         }\r
3524                 }\r
3525 \r
3526                 /* 以下のフォーマットをチェック */\r
3527                 /* LIST_AS400 */\r
3528 \r
3529                 if(Ret == LIST_UNKNOWN)\r
3530                 {\r
3531                         if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3532                            (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3533                         {\r
3534                                 if((FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS) &&\r
3535                                    (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3536                                 {\r
3537                                         if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) &&\r
3538                                            (IsDigit(Tmp[0]) != 0))\r
3539                                         {\r
3540                                                 if(FindField(Str, Tmp, 5, NO) == FFFTP_SUCCESS)\r
3541                                                 {\r
3542                                                         Ret = LIST_AS400;\r
3543                                                 }\r
3544                                         }\r
3545                                 }\r
3546                         }\r
3547                 }\r
3548 \r
3549                 /* 以下のフォーマットをチェック */\r
3550                 /* LIST_M1800 */\r
3551 \r
3552                 if(Ret == LIST_UNKNOWN)\r
3553                 {\r
3554                         if((FindField(Str, Tmp, 5, NO) == FFFTP_SUCCESS) &&\r
3555                            (CheckYYMMDDformat(Tmp, '*', NO) != 0))\r
3556                         {\r
3557                                 if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3558                                    ((IsDigit(Tmp[0]) != 0) || (StrAllSameChar(Tmp, '*') == YES)))\r
3559                                 {\r
3560                                         if((FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS) &&\r
3561                                            ((IsDigit(Tmp[0]) != 0) || (StrAllSameChar(Tmp, '*') == YES)))\r
3562                                         {\r
3563                                                 if((FindField(Str, Tmp, 0, NO) == FFFTP_SUCCESS) &&\r
3564                                                    (strlen(Tmp) == 4))\r
3565                                                 {\r
3566                                                         if(FindField(Str, Tmp, 6, NO) == FFFTP_SUCCESS)\r
3567                                                         {\r
3568                                                                 Ret = LIST_M1800;\r
3569                                                         }\r
3570                                                 }\r
3571                                         }\r
3572                                 }\r
3573                         }\r
3574                 }\r
3575 \r
3576                 /* 以下のフォーマットをチェック */\r
3577                 /* LIST_GP6000 */\r
3578 \r
3579                 if(Ret == LIST_UNKNOWN)\r
3580                 {\r
3581                         if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) &&\r
3582                            (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3583                         {\r
3584                                 if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3585                                    (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3586                                 {\r
3587                                         if((FindField(Str, Tmp, 5, NO) == FFFTP_SUCCESS) &&\r
3588                                            (IsDigit(Tmp[0]) != 0))\r
3589                                         {\r
3590                                                 if(FindField(Str, Tmp, 6, NO) == FFFTP_SUCCESS)\r
3591                                                 {\r
3592                                                         Ret = LIST_GP6000;\r
3593                                                 }\r
3594                                         }\r
3595                                 }\r
3596                         }\r
3597                 }\r
3598 \r
3599                 /* 以下のフォーマットをチェック */\r
3600                 /* LIST_DOS_1, LIST_DOS_2 */\r
3601 \r
3602                 if(Ret == LIST_UNKNOWN)\r
3603                 {\r
3604                         if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) &&\r
3605                            (CheckHHMMformat(Tmp) == YES))\r
3606                         {\r
3607                                 if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3608                                    ((Tmp[0] == '<') || (IsDigit(Tmp[0]) != 0)))\r
3609                                 {\r
3610                                         if(FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS)\r
3611                                         {\r
3612                                                 if((FindField(Str, Tmp, 0, NO) == FFFTP_SUCCESS) &&\r
3613                                                    (CheckYYMMDDformat(Tmp, NUL, YES) != 0))\r
3614                                                 {\r
3615                                                         TmpInt = atoi(Tmp);\r
3616                                                         if((TmpInt >= 1) && (TmpInt <= 12))\r
3617                                                                 Ret = LIST_DOS_2;\r
3618                                                         else\r
3619                                                                 Ret = LIST_DOS_1;\r
3620                                                 }\r
3621                                         }\r
3622                                 }\r
3623                         }\r
3624                 }\r
3625 \r
3626                 /* 以下のフォーマットをチェック */\r
3627                 /* LIST_DOS_3 */\r
3628 \r
3629                 if(Ret == LIST_UNKNOWN)\r
3630                 {\r
3631                         if((FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS) &&\r
3632                            (CheckHHMMformat(Tmp) == YES))\r
3633                         {\r
3634                                 if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) &&\r
3635                                    ((Tmp[0] == '<') || (IsDigit(Tmp[0]) != 0)))\r
3636                                 {\r
3637                                         if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3638                                            (CheckYYMMDDformat(Tmp, NUL, YES) != 0))\r
3639                                         {\r
3640                                                 Ret = LIST_DOS_3;\r
3641                                         }\r
3642                                 }\r
3643                         }\r
3644                 }\r
3645 \r
3646                 /* 以下のフォーマットをチェック */\r
3647                 /* LIST_DOS_4 */\r
3648 \r
3649                 if(Ret == LIST_UNKNOWN)\r
3650                 {\r
3651                         if((FindField(Str, Tmp, 0, NO) == FFFTP_SUCCESS) &&\r
3652                            (CheckYYYYMMDDformat(Tmp, NUL) == YES))\r
3653                         {\r
3654                                 if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) &&\r
3655                                    (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3656                                 {\r
3657                                         if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3658                                            ((Tmp[0] == '<') || (IsDigit(Tmp[0]) != 0)))\r
3659                                         {\r
3660                                                 if(FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS)\r
3661                                                 {\r
3662                                                         Ret = LIST_DOS_4;\r
3663                                                 }\r
3664                                         }\r
3665                                 }\r
3666                         }\r
3667                 }\r
3668 \r
3669                 /* 以下のフォーマットをチェック */\r
3670                 /* LIST_CHAMELEON */\r
3671 \r
3672                 if(Ret == LIST_UNKNOWN)\r
3673                 {\r
3674                         if(FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS)\r
3675                         {\r
3676                                 GetMonth(Tmp, &Month, &Day);\r
3677                                 if((Month != 0) && (Day == 0))\r
3678                                 {\r
3679                                         if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) &&\r
3680                                            ((Tmp[0] == '<') || (IsDigit(Tmp[0]) != 0)))\r
3681                                         {\r
3682                                                 if((FindField(Str, Tmp, 5, NO) == FFFTP_SUCCESS) &&\r
3683                                                    (CheckHHMMformat(Tmp) == YES))\r
3684                                                 {\r
3685                                                         Ret = LIST_CHAMELEON;\r
3686                                                 }\r
3687                                         }\r
3688                                 }\r
3689                         }\r
3690                 }\r
3691 \r
3692                 /* 以下のフォーマットをチェック */\r
3693                 /* LIST_OS2 */\r
3694 \r
3695                 if(Ret == LIST_UNKNOWN)\r
3696                 {\r
3697                         if((FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS) &&\r
3698                            (CheckHHMMformat(Tmp) == YES))\r
3699                         {\r
3700                                 if((FindField(Str, Tmp, 0, NO) == FFFTP_SUCCESS) &&\r
3701                                    (IsDigit(Tmp[0]) != 0))\r
3702                                 {\r
3703                                         if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3704                                            (CheckYYMMDDformat(Tmp, NUL, YES) != 0))\r
3705                                         {\r
3706                                                 if(FindField(Str, Tmp, 4, NO) == FFFTP_SUCCESS)\r
3707                                                 {\r
3708                                                         Ret = LIST_OS2;\r
3709                                                 }\r
3710                                         }\r
3711                                 }\r
3712                         }\r
3713                 }\r
3714 \r
3715                 /* 以下のフォーマットをチェック */\r
3716                 /* LIST_OS7 */\r
3717 \r
3718                 if(Ret == LIST_UNKNOWN)\r
3719                 {\r
3720                         if((FindField(Str, Tmp, 0, NO) == FFFTP_SUCCESS) &&\r
3721                            (strlen(Tmp) == 10))\r
3722                         {\r
3723                                 if((FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS) &&\r
3724                                    (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3725                                 {\r
3726                                         if((FindField(Str, Tmp, 4, NO) == FFFTP_SUCCESS) &&\r
3727                                            (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3728                                         {\r
3729                                                 if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3730                                                    (IsDigit(Tmp[0]) != 0))\r
3731                                                 {\r
3732                                                         if(FindField(Str, Tmp, 5, NO) == FFFTP_SUCCESS)\r
3733                                                         {\r
3734                                                                 Ret = LIST_OS7_2;\r
3735                                                         }\r
3736                                                 }\r
3737                                         }\r
3738                                 }\r
3739                                 else if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) &&\r
3740                                                 (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3741                                 {\r
3742                                         if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3743                                            (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3744                                         {\r
3745                                                 if(FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS)\r
3746                                                 {\r
3747                                                         Ret = LIST_OS7_1;\r
3748                                                 }\r
3749                                         }\r
3750                                 }\r
3751                         }\r
3752                 }\r
3753 \r
3754                 /* 以下のフォーマットをチェック */\r
3755                 /* LIST_ALLIED */\r
3756 \r
3757                 if(Ret == LIST_UNKNOWN)\r
3758                 {\r
3759                         if((FindField(Str, Tmp, 0, NO) == FFFTP_SUCCESS) &&\r
3760                            ((Tmp[0] == '<') || (IsDigit(Tmp[0]) != 0)))\r
3761                         {\r
3762                                 if((FindField(Str, Tmp, 5, NO) == FFFTP_SUCCESS) &&\r
3763                                    (CheckHHMMformat(Tmp) == YES))\r
3764                                 {\r
3765                                         if(FindField(Str, Tmp, 3, NO) == FFFTP_SUCCESS)\r
3766                                         {\r
3767                                                 GetMonth(Tmp, &Month, &Day);\r
3768                                                 if(Month != 0)\r
3769                                                 {\r
3770                                                         if((FindField(Str, Tmp, 6, NO) == FFFTP_SUCCESS) &&\r
3771                                                            (IsDigit(Tmp[0]) != 0))\r
3772                                                         {\r
3773                                                                 Ret = LIST_ALLIED;\r
3774                                                         }\r
3775                                                 }\r
3776                                         }\r
3777                                 }\r
3778                         }\r
3779                 }\r
3780 \r
3781                 /* 以下のフォーマットをチェック */\r
3782                 /* LIST_OS9 */\r
3783 \r
3784                 if(Ret == LIST_UNKNOWN)\r
3785                 {\r
3786                         if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) &&\r
3787                            (CheckYYMMDDformat(Tmp, NUL, NO) != 0))\r
3788                         {\r
3789                                 if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3790                                    (IsDigit(Tmp[0]) != 0) && (strlen(Tmp) == 4))\r
3791                                 {\r
3792                                         if((FindField(Str, Tmp, 5, NO) == FFFTP_SUCCESS) &&\r
3793                                            (IsDigit(Tmp[0]) != 0))\r
3794                                         {\r
3795                                                 if(FindField(Str, Tmp, 6, NO) == FFFTP_SUCCESS)\r
3796                                                 {\r
3797                                                         Ret = LIST_OS9;\r
3798                                                 }\r
3799                                         }\r
3800                                 }\r
3801                         }\r
3802                 }\r
3803 \r
3804                 /* 以下のフォーマットをチェック */\r
3805                 /* LIST_IBM */\r
3806 \r
3807                 if(Ret == LIST_UNKNOWN)\r
3808                 {\r
3809                         if((FindField(Str, Tmp, 2, NO) == FFFTP_SUCCESS) &&\r
3810                            (CheckYYYYMMDDformat(Tmp, NUL) == YES))\r
3811                         {\r
3812                                 if((FindField(Str, Tmp, 1, NO) == FFFTP_SUCCESS) && IsDigit(Tmp[0]))\r
3813                                 {\r
3814                                         if((FindField(Str, Tmp, 7, NO) == FFFTP_SUCCESS) && IsDigit(Tmp[0]))\r
3815                                         {\r
3816                                                 if(FindField(Str, Tmp, 9, NO) == FFFTP_SUCCESS)\r
3817                                                 {\r
3818                                                         Ret = LIST_IBM;\r
3819                                                 }\r
3820                                         }\r
3821                                 }\r
3822                         }\r
3823                 }\r
3824 #if defined(HAVE_TANDEM)\r
3825                 /* 以下のフォーマットをチェック */\r
3826                 /* LIST_TANDEM */\r
3827 \r
3828                 /* OSS の場合は自動判別可能のため Ret == LIST_UNKNOWN のチェックは後 */\r
3829                 if(AskRealHostType() == HTYPE_TANDEM) {\r
3830                         if(Ret == LIST_UNKNOWN) {\r
3831                                 SetOSS(NO);\r
3832                                 Ret = LIST_TANDEM;\r
3833                         } else {\r
3834                                 SetOSS(YES);\r
3835                         }\r
3836                 }\r
3837 #endif\r
3838 \r
3839                 // MLSD対応\r
3840                 if(Ret == LIST_UNKNOWN)\r
3841                 {\r
3842                         if(FindField2(Str, Tmp, ';', 1, NO) == FFFTP_SUCCESS && FindField2(Str, Tmp, '=', 1, NO) == FFFTP_SUCCESS)\r
3843                         {\r
3844                                 Ret = LIST_MLSD;\r
3845                         }\r
3846                 }\r
3847         }\r
3848 \r
3849 DoPrintf("ListType=%d", Ret);\r
3850 \r
3851         return(Ret);\r
3852 }\r
3853 \r
3854 \r
3855 /*----- UNIX系リストタイプのチェックを行なう ----------------------------------\r
3856 *\r
3857 *       Parameter\r
3858 *               char *Str : ファイル情報(1行)\r
3859 *               char *Tmp : 一時ワーク\r
3860 *               int Add1 : 加算パラメータ1\r
3861 *               int Add2 : 加算パラメータ2\r
3862 *               int Day : 日 (0=ここで取得する)\r
3863 *\r
3864 *       Return Value\r
3865 *               int リストタイプ (LIST_xxx)\r
3866 *----------------------------------------------------------------------------*/\r
3867 \r
3868 static int CheckUnixType(char *Str, char *Tmp, int Add1, int Add2, int Day)\r
3869 {\r
3870         int Ret;\r
3871         int Add3;\r
3872         WORD Hour;\r
3873         WORD Minute;\r
3874         int Flag;\r
3875 \r
3876         Flag = 0;\r
3877         Ret = LIST_UNKNOWN;\r
3878 \r
3879 //DayによってAdd3を変える\r
3880 \r
3881         Add3 = 0;\r
3882         if(Day != 0)\r
3883                 Add3 = -1;\r
3884 \r
3885         // unix系チェック\r
3886         if((Day != 0) ||\r
3887            ((FindField(Str, Tmp, 6+Add1+Add2+Add3, NO) == FFFTP_SUCCESS) &&\r
3888                 ((atoi(Tmp) >= 1) && (atoi(Tmp) <= 31))))\r
3889         {\r
3890                 if((FindField(Str, Tmp, 7+Add1+Add2+Add3, NO) == FFFTP_SUCCESS) &&\r
3891                    ((atoi(Tmp) >= 1900) || (GetHourAndMinute(Tmp, &Hour, &Minute) == FFFTP_SUCCESS)))\r
3892                 {\r
3893                         if(FindField(Str, Tmp, 8+Add1+Add2+Add3, NO) == FFFTP_SUCCESS)\r
3894                         {\r
3895                                 Flag = 1;\r
3896                         }\r
3897                 }\r
3898         }\r
3899 \r
3900         // 中国語Solaris専用\r
3901         if(Flag == 0)\r
3902         {\r
3903            if((FindField(Str, Tmp, 7+Add1+Add2+Add3, NO) == FFFTP_SUCCESS) &&\r
3904                   ((atoi(Tmp) >= 1) && (atoi(Tmp) <= 31)))\r
3905                 {\r
3906                         if((FindField(Str, Tmp, 5+Add1+Add2+Add3, NO) == FFFTP_SUCCESS) &&\r
3907                            (atoi(Tmp) >= 1900))\r
3908                         {\r
3909                                 if((FindField(Str, Tmp, 6+Add1+Add2+Add3, NO) == FFFTP_SUCCESS) &&\r
3910                                    (((atoi(Tmp) >= 1) && (atoi(Tmp) <= 9) && \r
3911                                          ((unsigned char)Tmp[1] == 0xD4) &&\r
3912                                          ((unsigned char)Tmp[2] == 0xC2)) ||\r
3913                                     ((atoi(Tmp) >= 10) && (atoi(Tmp) <= 12) && \r
3914                                          ((unsigned char)Tmp[2] == 0xD4) && \r
3915                                          ((unsigned char)Tmp[3] == 0xC2))))\r
3916                                 {\r
3917                                         if(FindField(Str, Tmp, 8+Add1+Add2+Add3, NO) == FFFTP_SUCCESS)\r
3918                                         {\r
3919                                                 Flag = 2;\r
3920                                         }\r
3921                                 }\r
3922                         }\r
3923                 }\r
3924         }\r
3925 \r
3926         if(Flag != 0)\r
3927         {\r
3928                 if(Add2 == 2)\r
3929                 {\r
3930                         Ret = LIST_UNIX_60;\r
3931                         if(Flag == 2)\r
3932                                 Ret = LIST_UNIX_64;\r
3933                         if(Day != 0)\r
3934                                 Ret = LIST_UNIX_61;\r
3935 \r
3936                         if(Add1 == -1)\r
3937                         {\r
3938                                 Ret = LIST_UNIX_62;\r
3939                                 if(Flag == 2)\r
3940                                         Ret = LIST_UNIX_65;\r
3941                                 if(Day != 0)\r
3942                                         Ret = LIST_UNIX_63;\r
3943                         }\r
3944                 }\r
3945                 else if(Add2 == 1)\r
3946                 {\r
3947                         Ret = LIST_UNIX_70;\r
3948                         if(Flag == 2)\r
3949                                 Ret = LIST_UNIX_74;\r
3950                         if(Day != 0)\r
3951                                 Ret = LIST_UNIX_71;\r
3952 \r
3953                         if(Add1 == -1)\r
3954                         {\r
3955                                 Ret = LIST_UNIX_72;\r
3956                                 if(Flag == 2)\r
3957                                         Ret = LIST_UNIX_75;\r
3958                                 if(Day != 0)\r
3959                                         Ret = LIST_UNIX_73;\r
3960                         }\r
3961                 }\r
3962                 else if(Add2 == 0)\r
3963                 {\r
3964                         Ret = LIST_UNIX_10;\r
3965                         if(Flag == 2)\r
3966                                 Ret = LIST_UNIX_14;\r
3967                         if(Day != 0)\r
3968                                 Ret = LIST_UNIX_11;\r
3969 \r
3970                         if(Add1 == -1)\r
3971                         {\r
3972                                 Ret = LIST_UNIX_12;\r
3973                                 if(Flag == 2)\r
3974                                         Ret = LIST_UNIX_15;\r
3975                                 if(Day != 0)\r
3976                                         Ret = LIST_UNIX_13;\r
3977                         }\r
3978                 }\r
3979                 else if(Add2 == -1)\r
3980                 {\r
3981                         Ret = LIST_UNIX_20;\r
3982                         if(Flag == 2)\r
3983                                 Ret = LIST_UNIX_24;\r
3984                         if(Day != 0)\r
3985                                 Ret = LIST_UNIX_21;\r
3986 \r
3987                         if(Add1 == -1)\r
3988                         {\r
3989                                 Ret = LIST_UNIX_22;\r
3990                                 if(Flag == 2)\r
3991                                         Ret = LIST_UNIX_25;\r
3992                                 if(Day != 0)\r
3993                                         Ret = LIST_UNIX_23;\r
3994                         }\r
3995                 }\r
3996                 else\r
3997                 {\r
3998                         Ret = LIST_UNIX_50;\r
3999                         if(Flag == 2)\r
4000                                 Ret = LIST_UNIX_54;\r
4001                         if(Day != 0)\r
4002                                 Ret = LIST_UNIX_51;\r
4003                 }\r
4004         }\r
4005         return(Ret);\r
4006 }\r
4007 \r
4008 \r
4009 /*----- HH:MM 形式の文字列かどうかをチェック ----------------------------------\r
4010 *\r
4011 *       Parameter\r
4012 *               char *Str : 文字列\r
4013 *\r
4014 *       Return Value\r
4015 *               int ステータス (YES/NO)\r
4016 *\r
4017 *       Note\r
4018 *               区切り文字は何でもよい\r
4019 *               時分でなくてもよい\r
4020 *               後ろに余分な文字が付いていてもよい\r
4021 *----------------------------------------------------------------------------*/\r
4022 \r
4023 static int CheckHHMMformat(char *Str)\r
4024 {\r
4025         int Ret;\r
4026 \r
4027         Ret = NO;\r
4028         if((strlen(Str) >= 3) &&\r
4029            (IsDigit(Str[0]) != 0))\r
4030         {\r
4031                 if((Str = strchr(Str, ':')) != NULL)\r
4032                 {\r
4033                         if(IsDigit(*(Str+1)) != 0)\r
4034                                 Ret = YES;\r
4035                 }\r
4036         }\r
4037         return(Ret);\r
4038 }\r
4039 \r
4040 \r
4041 /*----- YY/MM/DD 形式の文字列かどうかをチェック -------------------------------\r
4042 *\r
4043 *       Parameter\r
4044 *               char *Str : 文字列\r
4045 *               char Sym : 数字の代わりに使える記号 (NUL=数字以外使えない)\r
4046 *               int Dig3 : 3桁の年を許可\r
4047 *\r
4048 *       Return Value\r
4049 *               int ステータス\r
4050 *                       0 = 該当しない\r
4051 *                       1 = ??/??/??, ??/??/???\r
4052 *                       2 = ???/??/??\r
4053 *\r
4054 *       Note\r
4055 *               区切り文字は何でもよい\r
4056 *               年月日でなくてもよい\r
4057 *----------------------------------------------------------------------------*/\r
4058 \r
4059 static int CheckYYMMDDformat(char *Str, char Sym, int Dig3)\r
4060 {\r
4061         int Ret;\r
4062 \r
4063         Ret = 0;\r
4064         if((strlen(Str) == 8) &&\r
4065            (IsDigitSym(Str[0], Sym) != 0) && (IsDigitSym(Str[1], Sym) != 0) &&\r
4066            (IsDigit(Str[2]) == 0) &&\r
4067            (IsDigitSym(Str[3], Sym) != 0) && (IsDigitSym(Str[4], Sym) != 0) &&\r
4068            (IsDigit(Str[5]) == 0) &&\r
4069            (IsDigitSym(Str[6], Sym) != 0) && (IsDigitSym(Str[7], Sym) != 0))\r
4070         {\r
4071                 Ret = 1; \r
4072         }\r
4073         if(Dig3 == YES)\r
4074         {\r
4075                 if((strlen(Str) == 9) &&\r
4076                    (IsDigitSym(Str[0], Sym) != 0) && (IsDigitSym(Str[1], Sym) != 0) && (IsDigitSym(Str[2], Sym) != 0) &&\r
4077                    (IsDigit(Str[3]) == 0) &&\r
4078                    (IsDigitSym(Str[4], Sym) != 0) && (IsDigitSym(Str[5], Sym) != 0) &&\r
4079                    (IsDigit(Str[6]) == 0) &&\r
4080                    (IsDigitSym(Str[7], Sym) != 0) && (IsDigitSym(Str[8], Sym) != 0))\r
4081                 {\r
4082                         Ret = 2; \r
4083                 }\r
4084                 else if((strlen(Str) == 9) &&\r
4085                                 (IsDigitSym(Str[0], Sym) != 0) && (IsDigitSym(Str[1], Sym) != 0) &&\r
4086                                 (IsDigit(Str[2]) == 0) &&\r
4087                                 (IsDigitSym(Str[3], Sym) != 0) && (IsDigitSym(Str[4], Sym) != 0) &&\r
4088                                 (IsDigit(Str[5]) == 0) &&\r
4089                                 (IsDigitSym(Str[6], Sym) != 0) && (IsDigitSym(Str[7], Sym) != 0) && (IsDigitSym(Str[8], Sym) != 0))\r
4090                 {\r
4091                         Ret = 1; \r
4092                 }\r
4093         }\r
4094         return(Ret);\r
4095 }\r
4096 \r
4097 \r
4098 /*----- YYYY/MM/DD 形式の文字列かどうかをチェック -----------------------------\r
4099 *\r
4100 *       Parameter\r
4101 *               char *Str : 文字列\r
4102 *               char Sym : 数字の代わりに使える記号 (NUL=数字以外使えない)\r
4103 *\r
4104 *       Return Value\r
4105 *               int ステータス (YES/NO)\r
4106 *\r
4107 *       Note\r
4108 *               区切り文字は何でもよい\r
4109 *               年月日でなくてもよい\r
4110 *----------------------------------------------------------------------------*/\r
4111 \r
4112 static int CheckYYYYMMDDformat(char *Str, char Sym)\r
4113 {\r
4114         int Ret;\r
4115 \r
4116         Ret = NO;\r
4117         if((strlen(Str) == 10) &&\r
4118            (IsDigitSym(Str[0], Sym) != 0) && (IsDigitSym(Str[1], Sym) != 0) &&\r
4119            (IsDigitSym(Str[2], Sym) != 0) && (IsDigitSym(Str[3], Sym) != 0) &&\r
4120            (IsDigit(Str[4]) == 0) &&\r
4121            (IsDigitSym(Str[5], Sym) != 0) && (IsDigitSym(Str[6], Sym) != 0) &&\r
4122            (IsDigit(Str[7]) == 0) &&\r
4123            (IsDigitSym(Str[8], Sym) != 0) && (IsDigitSym(Str[9], Sym) != 0))\r
4124         {\r
4125                 Ret = YES; \r
4126         }\r
4127         return(Ret);\r
4128 }\r
4129 \r
4130 \r
4131 /*----- ファイル情報からファイル名、サイズなどを取り出す ----------------------\r
4132 *\r
4133 *       Parameter\r
4134 *               char *Str : ファイル情報(1行)\r
4135 *               int ListType : リストのタイプ\r
4136 *               char *Name : ファイル名のコピー先\r
4137 *               LONGLONG *Size : サイズのコピー先\r
4138 *               FILETIME *Time : 日付のコピー先\r
4139 *               int *Attr : 属性のコピー先\r
4140 *               char *Owner : オーナ名\r
4141 *               int *Link : リンクかどうか (YES/NO)\r
4142 *               int *InfoExist : 時刻の情報があったかどうか (YES/NO)\r
4143 *\r
4144 *       Return Value\r
4145 *               int 種類 (NODE_xxxx)\r
4146 *----------------------------------------------------------------------------*/\r
4147 \r
4148 static int ResolvFileInfo(char *Str, int ListType, char *Fname, LONGLONG *Size, FILETIME *Time, int *Attr, char *Owner, int *Link, int *InfoExist)\r
4149 {\r
4150         SYSTEMTIME sTime;\r
4151         SYSTEMTIME sTimeNow;\r
4152         char Buf[FMAX_PATH+1];\r
4153         char *Pos;\r
4154         char Flag;\r
4155         int Ret;\r
4156         int offs;\r
4157         int offs2;\r
4158         int offs3;\r
4159         int OrgListType;\r
4160         int err;\r
4161         int Flag2;\r
4162 \r
4163         static const int DosPos[3][4] = { { 1, 0, 2, 3 }, { 1, 0, 2, 3 }, { 3, 2, 1, 0 } };\r
4164         static const int DosDate[3][3][2] = { { {0, 0}, {3, 4}, {6, 7} }, { {6, 7}, {0, 0}, {3, 4} }, { {6, 7}, {0, 0}, {3, 4} } };\r
4165         static const int DosLongFname[3] = { YES, YES, NO };\r
4166 \r
4167         /* まずクリアしておく */\r
4168         Ret = NODE_NONE;\r
4169         // バグ対策\r
4170         memset(Fname, NUL, FMAX_PATH+1);\r
4171         *Size = -1;\r
4172         *Attr = 0;\r
4173         *Link = NO;\r
4174         memset(Owner, NUL, OWNER_NAME_LEN+1);\r
4175         Time->dwLowDateTime = 0;\r
4176         Time->dwHighDateTime = 0;\r
4177         *InfoExist = 0;\r
4178         offs = 0;\r
4179         offs2 = 0;\r
4180         offs3 = 0;\r
4181 \r
4182         OrgListType = ListType;\r
4183         ListType &= LIST_MASKFLG;\r
4184         switch(ListType)\r
4185         {\r
4186                 case LIST_DOS_1 :\r
4187                 case LIST_DOS_2 :\r
4188                 case LIST_DOS_3 :\r
4189                         if(ListType == LIST_DOS_1)\r
4190                                 offs = 0;\r
4191                         else if(ListType == LIST_DOS_2)\r
4192                                 offs = 1;\r
4193                         else\r
4194                                 offs = 2;\r
4195 \r
4196                         *InfoExist |= (FINFO_DATE | FINFO_SIZE);\r
4197 \r
4198                         /* 時刻 */\r
4199                         FindField(Str, Buf, DosPos[offs][0], NO);\r
4200                         if((Pos = strchr(Buf, ':')) != NULL)\r
4201                         {\r
4202                                 *InfoExist |= FINFO_TIME;\r
4203                                 sTime.wHour = atoi(Buf);\r
4204                                 sTime.wMinute = atoi(Pos+1);\r
4205                                 sTime.wSecond = 0;\r
4206                                 sTime.wMilliseconds = 0;\r
4207 \r
4208                                 if(strlen(Pos) >= 4)\r
4209                                 {\r
4210                                         if(tolower(Pos[3]) == 'a')\r
4211                                         {\r
4212                                                 if(sTime.wHour == 12)\r
4213                                                         sTime.wHour = 0;\r
4214                                         }\r
4215                                         else if(tolower(Pos[3]) == 'p')\r
4216                                         {\r
4217                                                 if(sTime.wHour != 12)\r
4218                                                         sTime.wHour += 12;\r
4219                                         }\r
4220                                 }\r
4221                         }\r
4222 \r
4223                         /* 日付 */\r
4224                         FindField(Str, Buf, DosPos[offs][1], NO);\r
4225                         if((offs2 = CheckYYMMDDformat(Buf, NUL, YES)) == 0)\r
4226                                 break;\r
4227                         offs2--;\r
4228                         sTime.wYear = Assume1900or2000(atoi(Buf + DosDate[offs][0][offs2]));\r
4229                         sTime.wMonth = atoi(Buf + DosDate[offs][1][offs2]);\r
4230                         sTime.wDay = atoi(Buf + DosDate[offs][2][offs2]);\r
4231                         SystemTimeToFileTime(&sTime, Time);\r
4232                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4233 \r
4234                         /* サイズ */\r
4235                         FindField(Str, Buf, DosPos[offs][2], NO);\r
4236                         *Size = _atoi64(Buf);\r
4237 \r
4238                         /* 名前 */\r
4239                         if(FindField(Str, Fname, DosPos[offs][3], DosLongFname[offs]) == FFFTP_SUCCESS)\r
4240                         {\r
4241                                 Ret = NODE_FILE;\r
4242                                 if(Buf[0] == '<')\r
4243                                         Ret = NODE_DIR;\r
4244                         }\r
4245                         break;\r
4246 \r
4247                 case LIST_DOS_4 :\r
4248                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE);\r
4249 \r
4250                         /* 日付 */\r
4251                         FindField(Str, Buf, 0, NO);\r
4252                         sTime.wYear = atoi(Buf);\r
4253                         sTime.wMonth = atoi(Buf+5);\r
4254                         sTime.wDay = atoi(Buf+8);\r
4255 \r
4256                         /* 時刻 */\r
4257                         *InfoExist |= FINFO_TIME;\r
4258                         FindField(Str, Buf, 1, NO);\r
4259                         sTime.wHour = atoi(Buf);\r
4260                         sTime.wMinute = atoi(Buf+3);\r
4261                         sTime.wSecond = 0;                              // atoi(Buf+6);\r
4262                         sTime.wMilliseconds = 0;\r
4263                         SystemTimeToFileTime(&sTime, Time);\r
4264                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4265 \r
4266                         /* サイズ */\r
4267                         FindField(Str, Buf, 2, NO);\r
4268                         *Size = _atoi64(Buf);\r
4269 \r
4270                         /* 名前 */\r
4271                         if(FindField(Str, Fname, 3, YES) == FFFTP_SUCCESS)\r
4272                         {\r
4273                                 Ret = NODE_FILE;\r
4274                                 if(Buf[0] == '<')\r
4275                                         Ret = NODE_DIR;\r
4276                         }\r
4277                         break;\r
4278 \r
4279                 case LIST_OS2 :\r
4280                         *InfoExist |= (FINFO_DATE | FINFO_SIZE);\r
4281 \r
4282                         /* 時刻 */\r
4283                         FindField(Str, Buf, 3, NO);\r
4284                         if((Pos = strchr(Buf, ':')) != NULL)\r
4285                         {\r
4286                                 *InfoExist |= FINFO_TIME;\r
4287                                 sTime.wHour = atoi(Buf);\r
4288                                 sTime.wMinute = atoi(Pos+1);\r
4289                                 sTime.wSecond = 0;\r
4290                                 sTime.wMilliseconds = 0;\r
4291                         }\r
4292 \r
4293                         /* 日付 */\r
4294                         FindField(Str, Buf, 2, NO);\r
4295                         sTime.wYear = Assume1900or2000(atoi(Buf+6));\r
4296                         sTime.wMonth = atoi(Buf+0);\r
4297                         sTime.wDay = atoi(Buf+3);\r
4298                         SystemTimeToFileTime(&sTime, Time);\r
4299                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4300 \r
4301                         /* サイズ */\r
4302                         FindField(Str, Buf, 0, NO);\r
4303                         *Size = _atoi64(Buf);\r
4304 \r
4305                         /* 名前 */\r
4306                         if(FindField(Str, Fname, 4, YES) == FFFTP_SUCCESS)\r
4307                         {\r
4308                                 FindField(Str, Buf, 1, NO);\r
4309                                 Ret = NODE_FILE;\r
4310                                 if(strstr(Buf, "DIR") != NULL)\r
4311                                         Ret = NODE_DIR;\r
4312                         }\r
4313                         break;\r
4314 \r
4315                 case LIST_CHAMELEON :\r
4316                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE | FINFO_ATTR);\r
4317 \r
4318                         /* 属性 */\r
4319                         FindField(Str, Buf, 6, NO);\r
4320                         strcat(Buf, "------");\r
4321                         *Attr = AttrString2Value(Buf+1);\r
4322 \r
4323                         /* 日付 */\r
4324                         FindField(Str, Buf, 2, NO);\r
4325                         GetMonth(Buf, &sTime.wMonth, &sTime.wDay);      /* wDayは常に0 */\r
4326                         FindField(Str, Buf, 3, NO);\r
4327                         sTime.wDay = atoi(Buf);\r
4328                         FindField(Str, Buf, 4, NO);\r
4329                         sTime.wYear = atoi(Buf);\r
4330 \r
4331                         /* 時刻 */\r
4332                         FindField(Str, Buf, 5, NO);\r
4333                         sTime.wHour = atoi(Buf);\r
4334                         sTime.wMinute = atoi(Buf+3);\r
4335                         sTime.wSecond = 0;\r
4336                         sTime.wMilliseconds = 0;\r
4337                         SystemTimeToFileTime(&sTime, Time);\r
4338                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4339 \r
4340                         /* サイズ */\r
4341                         FindField(Str, Buf, 1, NO);\r
4342                         *Size = _atoi64(Buf);\r
4343 \r
4344                         /* 名前 */\r
4345                         if(FindField(Str, Fname, 0, NO) == FFFTP_SUCCESS)\r
4346                         {\r
4347                                 Ret = NODE_FILE;\r
4348                                 if(Buf[0] == '<')\r
4349                                         Ret = NODE_DIR;\r
4350                         }\r
4351                         break;\r
4352 \r
4353                 case LIST_AS400 :\r
4354                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE);\r
4355 \r
4356                         /* オーナ名 */\r
4357                         FindField(Str, Buf, 0, NO);\r
4358                         strncpy(Owner, Buf, OWNER_NAME_LEN);\r
4359 \r
4360                         /* 時刻 */\r
4361                         FindField(Str, Buf, 3, NO);\r
4362                         sTime.wHour = atoi(Buf);\r
4363                         sTime.wMinute = atoi(Buf+3);\r
4364                         sTime.wSecond = 0;\r
4365                         sTime.wMilliseconds = 0;\r
4366 \r
4367                         /* 日付 */\r
4368                         FindField(Str, Buf, 2, NO);\r
4369                         sTime.wYear = Assume1900or2000(atoi(Buf));\r
4370                         sTime.wMonth = atoi(Buf + 3);\r
4371                         sTime.wDay = atoi(Buf + 6);\r
4372                         SystemTimeToFileTime(&sTime, Time);\r
4373                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4374 \r
4375                         /* サイズ */\r
4376                         FindField(Str, Buf, 1, NO);\r
4377                         *Size = _atoi64(Buf);\r
4378 \r
4379                         /* 名前 */\r
4380                         if(FindField(Str, Fname, 5, YES) == FFFTP_SUCCESS)\r
4381                         {\r
4382                                 Ret = NODE_FILE;\r
4383                                 if((Pos = strchr(Fname, '/')) != NULL)\r
4384                                 {\r
4385                                         Ret = NODE_DIR;\r
4386                                         *Pos = NUL;\r
4387                                 }\r
4388                         }\r
4389                         break;\r
4390 \r
4391                 case LIST_M1800 :\r
4392                         *InfoExist |= FINFO_ATTR;\r
4393 \r
4394                         /* 属性 */\r
4395                         FindField(Str, Buf, 0, NO);\r
4396                         strcat(Buf, "------");\r
4397                         *Attr = AttrString2Value(Buf+1);\r
4398 \r
4399                         /* 日付 */\r
4400                         Time->dwLowDateTime = 0;\r
4401                         Time->dwHighDateTime = 0;\r
4402                         FindField(Str, Buf, 5, NO);\r
4403                         if(Buf[0] != '*')\r
4404                         {\r
4405                                 *InfoExist |= FINFO_DATE;\r
4406                                 sTime.wHour = 0;\r
4407                                 sTime.wMinute = 0;\r
4408                                 sTime.wSecond = 0;\r
4409                                 sTime.wMilliseconds = 0;\r
4410 \r
4411                                 sTime.wYear = Assume1900or2000(atoi(Buf));\r
4412                                 sTime.wMonth = atoi(Buf + 3);\r
4413                                 sTime.wDay = atoi(Buf + 6);\r
4414                                 SystemTimeToFileTime(&sTime, Time);\r
4415                                 SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4416                         }\r
4417 \r
4418                         /* 名前 */\r
4419                         if(FindField(Str, Fname, 6, YES) == FFFTP_SUCCESS)\r
4420                         {\r
4421                                 RemoveTailingSpaces(Fname);\r
4422                                 Ret = NODE_FILE;\r
4423                                 if((Pos = strchr(Fname, '/')) != NULL)\r
4424                                 {\r
4425                                         Ret = NODE_DIR;\r
4426                                         *Pos = NUL;\r
4427                                 }\r
4428                         }\r
4429                         break;\r
4430 \r
4431                 case LIST_GP6000 :\r
4432                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE | FINFO_ATTR);\r
4433 \r
4434                         /* オーナ名 */\r
4435                         FindField(Str, Buf, 3, NO);\r
4436                         strncpy(Owner, Buf, OWNER_NAME_LEN);\r
4437 \r
4438                         /* 時刻 */\r
4439                         FindField(Str, Buf, 2, NO);\r
4440                         sTime.wHour = atoi(Buf);\r
4441                         sTime.wMinute = atoi(Buf+3);\r
4442                         sTime.wSecond = 0;\r
4443                         sTime.wMilliseconds = 0;\r
4444 \r
4445                         /* 日付 */\r
4446                         FindField(Str, Buf, 1, NO);\r
4447                         sTime.wYear = Assume1900or2000(atoi(Buf));\r
4448                         sTime.wMonth = atoi(Buf + 3);\r
4449                         sTime.wDay = atoi(Buf + 6);\r
4450                         SystemTimeToFileTime(&sTime, Time);\r
4451                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4452 \r
4453                         /* サイズ */\r
4454                         FindField(Str, Buf, 5, NO);\r
4455                         *Size = _atoi64(Buf);\r
4456 \r
4457                         /* 属性 */\r
4458                         FindField(Str, Buf, 0, NO);\r
4459                         *Attr = AttrString2Value(Buf+1);\r
4460 \r
4461                         /* 名前 */\r
4462                         if(FindField(Str, Fname, 6, YES) == FFFTP_SUCCESS)\r
4463                         {\r
4464                                 Ret = NODE_FILE;\r
4465                                 if(strchr("dl", Buf[0]) != NULL)\r
4466                                         Ret = NODE_DIR;\r
4467                         }\r
4468                         break;\r
4469 \r
4470                 case LIST_ACOS :\r
4471                 case LIST_ACOS_4 :\r
4472                         /* 名前 */\r
4473                         FindField(Str, Fname, 0, NO);\r
4474                         Ret = NODE_FILE;\r
4475                         break;\r
4476 \r
4477                 case LIST_VMS :\r
4478                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE);\r
4479 \r
4480                         /* サイズ */\r
4481                         FindField(Str, Buf, 1, NO);\r
4482                         *Size = _atoi64(Buf) * BLOCK_SIZE;\r
4483 \r
4484                         /* 時刻/日付 */\r
4485                         FindField(Str, Buf, 2, NO);\r
4486                         GetVMSdate(Buf, &sTime.wYear, &sTime.wMonth, &sTime.wDay);\r
4487 \r
4488                         FindField(Str, Buf, 3, NO);\r
4489                         GetHourAndMinute(Buf, &sTime.wHour, &sTime.wMinute);\r
4490 \r
4491                         sTime.wSecond = 0;\r
4492                         sTime.wMilliseconds = 0;\r
4493                         SystemTimeToFileTime(&sTime, Time);\r
4494                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4495 \r
4496                         /* 名前 */\r
4497                         FindField(Str, Fname, 0, NO);\r
4498 \r
4499                         Ret = NODE_FILE;\r
4500                         if((Pos = strchr(Fname, '.')) != NULL)\r
4501                         {\r
4502                                 if(_strnicmp(Pos, ".DIR;", 5) == 0)\r
4503                                 {\r
4504                                         /* OpenVMSの場合、ファイル/ディレクトリ削除時には".DIR;?"までないと\r
4505                                          * 削除できないので、ここではつぶさない */\r
4506 #if !defined(HAVE_OPENVMS)\r
4507                                         *Pos = NUL;\r
4508 #endif\r
4509                                         Ret = NODE_DIR;\r
4510                                 }\r
4511                         }\r
4512                         break;\r
4513 \r
4514                 case LIST_OS7_2 :\r
4515                         *InfoExist |= FINFO_SIZE;\r
4516                         offs = 2;\r
4517 \r
4518                         /* サイズ */\r
4519                         FindField(Str, Buf, 2, NO);\r
4520                         *Size = _atoi64(Buf);\r
4521                         /* ここにbreakはない */\r
4522 \r
4523                 case LIST_OS7_1 :\r
4524                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_ATTR);\r
4525 \r
4526                         /* 日付 */\r
4527                         FindField(Str, Buf, 1+offs, NO);\r
4528                         sTime.wYear = Assume1900or2000(atoi(Buf));\r
4529                         sTime.wMonth = atoi(Buf + 3);\r
4530                         sTime.wDay = atoi(Buf + 6);\r
4531 \r
4532                         /* 時刻 */\r
4533                         FindField(Str, Buf, 2+offs, NO);\r
4534                         sTime.wHour = atoi(Buf);\r
4535                         sTime.wMinute = atoi(Buf+3);\r
4536                         sTime.wSecond = 0;\r
4537                         sTime.wMilliseconds = 0;\r
4538                         SystemTimeToFileTime(&sTime, Time);\r
4539                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4540 \r
4541                         /* 属性 */\r
4542                         FindField(Str, Buf, 0, NO);\r
4543                         *Attr = AttrString2Value(Buf+1);\r
4544 \r
4545                         /* 名前 */\r
4546                         if(FindField(Str, Fname, 3+offs, YES) == FFFTP_SUCCESS)\r
4547                         {\r
4548                                 RemoveTailingSpaces(Fname);\r
4549                                 Ret = NODE_FILE;\r
4550                                 if(strchr("dl", Buf[0]) != NULL)\r
4551                                         Ret = NODE_DIR;\r
4552                         }\r
4553                         break;\r
4554 \r
4555                 case LIST_STRATUS :\r
4556                         if(FindField(Str, Buf, 0, NO) != FFFTP_SUCCESS)\r
4557                                 break;\r
4558                         if(_strnicmp(Buf, "Files:", 6) == 0)\r
4559                                 StratusMode = 0;\r
4560                         else if(_strnicmp(Buf, "Dirs:", 5) == 0)\r
4561                                 StratusMode = 1;\r
4562                         else if(_strnicmp(Buf, "Links:", 6) == 0)\r
4563                                 StratusMode = 2;\r
4564                         else\r
4565                         {\r
4566                                 if(StratusMode == 0)\r
4567                                         offs = 1;\r
4568                                 else if(StratusMode == 1)\r
4569                                         offs = 0;\r
4570                                 else\r
4571                                         break;\r
4572 \r
4573                                 *InfoExist |= (FINFO_TIME | FINFO_DATE);\r
4574 \r
4575                                 /* 日付 */\r
4576                                 if(FindField(Str, Buf, 2+offs, NO) != FFFTP_SUCCESS)\r
4577                                         break;\r
4578                                 sTime.wYear = Assume1900or2000(atoi(Buf));\r
4579                                 sTime.wMonth = atoi(Buf + 3);\r
4580                                 sTime.wDay = atoi(Buf + 6);\r
4581 \r
4582                                 /* 時刻 */\r
4583                                 if(FindField(Str, Buf, 3+offs, NO) != FFFTP_SUCCESS)\r
4584                                         break;\r
4585                                 sTime.wHour = atoi(Buf);\r
4586                                 sTime.wMinute = atoi(Buf+3);\r
4587                                 sTime.wSecond = 0;\r
4588                                 sTime.wMilliseconds = 0;\r
4589                                 SystemTimeToFileTime(&sTime, Time);\r
4590                                 SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4591 \r
4592                                 /* 名前 */\r
4593                                 if(FindField(Str, Fname, 4+offs, YES) != FFFTP_SUCCESS)\r
4594                                         break;\r
4595 \r
4596                                 if(StratusMode == 0)\r
4597                                 {\r
4598                                         *InfoExist |= FINFO_SIZE;\r
4599 \r
4600                                         /* サイズ */\r
4601                                         if(FindField(Str, Buf, 1, NO) != FFFTP_SUCCESS)\r
4602                                                 break;\r
4603                                         *Size = _atoi64(Buf) * 4096;\r
4604 \r
4605                                         /* 種類(オーナ名のフィールドにいれる) */\r
4606                                         if(FindField(Str, Buf, 2, NO) != FFFTP_SUCCESS)\r
4607                                                 break;\r
4608                                         strncpy(Owner, Buf, OWNER_NAME_LEN);\r
4609 \r
4610                                         Ret = NODE_FILE;\r
4611                                 }\r
4612                                 else\r
4613                                         Ret = NODE_DIR;\r
4614                         }\r
4615                         break;\r
4616 \r
4617                 case LIST_IRMX :\r
4618                         *InfoExist |= (FINFO_DATE | FINFO_SIZE);\r
4619 \r
4620                         /* 日付 */\r
4621                         for(offs = 11; offs > 7; offs--)\r
4622                         {\r
4623                                 if((err = FindField(Str, Buf, offs, NO)) == FFFTP_SUCCESS)\r
4624                                         break;\r
4625                         }\r
4626                         if(err != FFFTP_SUCCESS)\r
4627                                 break;\r
4628                         if(IsDigit(*Buf) == 0)\r
4629                                 break;\r
4630                         sTime.wYear = Assume1900or2000(atoi(Buf));\r
4631                         if(FindField(Str, Buf, --offs, NO) != FFFTP_SUCCESS)\r
4632                                 break;\r
4633                         GetMonth(Buf, &sTime.wMonth, &sTime.wDay);\r
4634                         if(FindField(Str, Buf, --offs, NO) != FFFTP_SUCCESS)\r
4635                                 break;\r
4636                         if(IsDigit(*Buf) == 0)\r
4637                                 break;\r
4638                         sTime.wDay = atoi(Buf);\r
4639                         sTime.wHour = 0;\r
4640                         sTime.wMinute = 0;\r
4641                         sTime.wSecond = 0;\r
4642                         sTime.wMilliseconds = 0;\r
4643                         SystemTimeToFileTime(&sTime, Time);\r
4644                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4645 \r
4646                         /* オーナ名 */\r
4647                         if(FindField(Str, Buf, --offs, NO) != FFFTP_SUCCESS)\r
4648                                 break;\r
4649                         strncpy(Owner, Buf, OWNER_NAME_LEN);\r
4650 \r
4651                         /* サイズ */\r
4652                         do\r
4653                         {\r
4654                                 if((err = FindField(Str, Buf, --offs, NO)) != FFFTP_SUCCESS)\r
4655                                         break;\r
4656                         }\r
4657                         while(IsDigit(*Buf) == 0);\r
4658                         --offs;\r
4659                         if((err = FindField(Str, Buf, --offs, NO)) != FFFTP_SUCCESS)\r
4660                                 break;\r
4661                         RemoveComma(Buf);\r
4662                         *Size = _atoi64(Buf);\r
4663                         if((err = FindField(Str, Buf, --offs, NO)) != FFFTP_SUCCESS)\r
4664                                 break;\r
4665                         if(IsDigit(*Buf) == 0)\r
4666                                 break;\r
4667                         /* 名前 */\r
4668                         if(FindField(Str, Fname, 0, NO) != FFFTP_SUCCESS)\r
4669                                 break;\r
4670                         /* 種類 */\r
4671                         if(offs == 0)\r
4672                                 Ret = NODE_FILE;\r
4673                         else\r
4674                         {\r
4675                                 if((FindField(Str, Buf, 1, NO) == FFFTP_SUCCESS) &&\r
4676                                    (strcmp(Buf, "DR") == 0))\r
4677                                         Ret = NODE_DIR;\r
4678                                 else\r
4679                                         Ret = NODE_FILE;\r
4680                         }\r
4681                         break;\r
4682 \r
4683                 case LIST_ALLIED :\r
4684                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE);\r
4685 \r
4686                         /* 日付 */\r
4687                         FindField(Str, Buf, 3, NO);\r
4688                         GetMonth(Buf, &sTime.wMonth, &sTime.wDay);      /* wDayは常に0 */\r
4689                         FindField(Str, Buf, 4, NO);\r
4690                         sTime.wDay = atoi(Buf);\r
4691                         FindField(Str, Buf, 6, NO);\r
4692                         sTime.wYear = atoi(Buf);\r
4693 \r
4694                         /* 時刻 */\r
4695                         FindField(Str, Buf, 5, NO);\r
4696                         sTime.wHour = atoi(Buf);\r
4697                         sTime.wMinute = atoi(Buf+3);\r
4698                         sTime.wSecond = 0;\r
4699                         sTime.wMilliseconds = 0;\r
4700                         SystemTimeToFileTime(&sTime, Time);\r
4701                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4702 \r
4703                         /* サイズ */\r
4704                         FindField(Str, Buf, 0, NO);\r
4705                         *Size = _atoi64(Buf);\r
4706 \r
4707                         /* 名前 */\r
4708                         if(FindField(Str, Fname, 1, NO) == FFFTP_SUCCESS)\r
4709                         {\r
4710                                 Ret = NODE_FILE;\r
4711                                 if(Buf[0] == '<')\r
4712                                         Ret = NODE_DIR;\r
4713                         }\r
4714                         break;\r
4715 \r
4716                 case LIST_OS9 :\r
4717                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE);\r
4718 \r
4719                         /* 日付 */\r
4720                         FindField(Str, Buf, 1, NO);\r
4721                         sTime.wYear = Assume1900or2000(atoi(Buf));\r
4722                         sTime.wMonth = atoi(Buf + 3);\r
4723                         sTime.wDay = atoi(Buf + 6);\r
4724                         SystemTimeToFileTime(&sTime, Time);\r
4725                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4726 \r
4727                         /* 時刻 */\r
4728                         FindField(Str, Buf, 2, NO);\r
4729                         sTime.wHour = atoi_n(Buf, 2);\r
4730                         sTime.wMinute = atoi(Buf+2);\r
4731                         sTime.wSecond = 0;\r
4732                         sTime.wMilliseconds = 0;\r
4733                         SystemTimeToFileTime(&sTime, Time);\r
4734                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4735 \r
4736                         /* サイズ */\r
4737                         FindField(Str, Buf, 5, NO);\r
4738                         *Size = _atoi64(Buf);\r
4739 \r
4740                         /* オーナ名 */\r
4741                         FindField(Str, Buf, 0, NO);\r
4742                         strncpy(Owner, Buf, OWNER_NAME_LEN);\r
4743 \r
4744                         /* オーナ名 */\r
4745                         FindField(Str, Buf, 3, NO);\r
4746 \r
4747                         /* 名前 */\r
4748                         if(FindField(Str, Fname, 6, NO) == FFFTP_SUCCESS)\r
4749                         {\r
4750                                 if((Buf[0] == 'd') || (Buf[0] == 'D'))\r
4751                                         Ret = NODE_DIR;\r
4752                                 else\r
4753                                         Ret = NODE_FILE;\r
4754                         }\r
4755                         break;\r
4756 \r
4757                 case LIST_IBM :\r
4758                         *InfoExist |= FINFO_DATE;\r
4759 \r
4760 \r
4761                         /* 日付 */\r
4762                         FindField(Str, Buf, 2, NO);\r
4763                         sTime.wYear = atoi(Buf);\r
4764                         sTime.wMonth = atoi(Buf + 5);\r
4765                         sTime.wDay = atoi(Buf + 8);\r
4766                         sTime.wHour = 0;\r
4767                         sTime.wMinute = 0;\r
4768                         sTime.wSecond = 0;\r
4769                         sTime.wMilliseconds = 0;\r
4770                         SystemTimeToFileTime(&sTime, Time);\r
4771                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4772 \r
4773                         /* 名前 */\r
4774                         FindField(Str, Buf, 8, NO);\r
4775                         if(FindField(Str, Fname, 9, NO) == FFFTP_SUCCESS)\r
4776                         {\r
4777                                 if(strcmp(Buf, "PO") == 0)\r
4778                                         Ret = NODE_DIR;\r
4779                                 else if(strcmp(Buf, "PS") == 0)\r
4780                                         Ret = NODE_FILE;\r
4781                         }\r
4782                         break;\r
4783 \r
4784                 case LIST_AGILENT :\r
4785                         *InfoExist |= (FINFO_SIZE | FINFO_ATTR);\r
4786 \r
4787                         /* オーナ名 */\r
4788                         FindField(Str, Buf, 2, NO);\r
4789                         strncpy(Owner, Buf, OWNER_NAME_LEN);\r
4790 \r
4791                         /* サイズ */\r
4792                         FindField(Str, Buf, 4, NO);\r
4793                         *Size = _atoi64(Buf);\r
4794 \r
4795                         /* 属性 */\r
4796                         FindField(Str, Buf, 0, NO);\r
4797                         *Attr = AttrString2Value(Buf+1);\r
4798 \r
4799                         /* 名前 */\r
4800                         if(FindField(Str, Fname, 5, YES) == FFFTP_SUCCESS)\r
4801                         {\r
4802                                 Ret = NODE_FILE;\r
4803                                 if(strchr("dl", Buf[0]) != NULL)\r
4804                                         Ret = NODE_DIR;\r
4805                         }\r
4806                         break;\r
4807 \r
4808                 case LIST_SHIBASOKU :\r
4809                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE);\r
4810 \r
4811                         /* サイズ */\r
4812                         FindField(Str, Buf, 0, NO);\r
4813                         if(IsDigit(Buf[0]))\r
4814                         {\r
4815                                 *Size = _atoi64(Buf);\r
4816 \r
4817                                 /* 日付 */\r
4818                                 FindField(Str, Buf, 1, NO);\r
4819                                 Buf[3] = '\0';\r
4820                                 GetMonth(Buf, &sTime.wMonth, &sTime.wDay);\r
4821                                 sTime.wDay = atoi(Buf+4);\r
4822                                 sTime.wYear = atoi(Buf+7);\r
4823 \r
4824                                 /* 時刻 */\r
4825                                 FindField(Str, Buf, 2, NO);\r
4826                                 sTime.wHour = atoi(Buf);\r
4827                                 sTime.wMinute = atoi(Buf+3);\r
4828                                 sTime.wSecond = 0;\r
4829                                 sTime.wMilliseconds = 0;\r
4830                                 SystemTimeToFileTime(&sTime, Time);\r
4831                                 SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4832 \r
4833                                 /* 名前 */\r
4834                                 FindField(Str, Fname, 3, NO);\r
4835 \r
4836                                 /* 種類 */\r
4837                                 Ret = NODE_FILE;\r
4838                                 if(FindField(Str, Buf, 4, NO) == FFFTP_SUCCESS)\r
4839                                 {\r
4840                                         if(strcmp(Buf, "<DIR>") == 0)\r
4841                                                 Ret = NODE_DIR;\r
4842                                 }\r
4843                         }\r
4844                         break;\r
4845 \r
4846 #if defined(HAVE_TANDEM)\r
4847                 case LIST_TANDEM :\r
4848                         *InfoExist |= (FINFO_TIME | FINFO_DATE | FINFO_SIZE | FINFO_ATTR);\r
4849                         /* Open 中だったらずらす */\r
4850                         if(FindField(Str, Buf, 1, NO) != FFFTP_SUCCESS)\r
4851                                 break;\r
4852                         if (!strncmp(Buf, "O", 1)) {\r
4853                                 offs = 1;\r
4854                         }\r
4855                         /* 日付 */\r
4856                         if(FindField(Str, Buf, 3 + offs, NO) != FFFTP_SUCCESS)\r
4857                                 break;\r
4858                         if (Buf[1] == '-') {  /* 日付が 1桁 */\r
4859                                 sTime.wYear = Assume1900or2000(atoi(Buf + 6));\r
4860                                 Buf[5] = 0;\r
4861                                 GetMonth(Buf+2, &sTime.wMonth, &sTime.wDay);    /* wDayは常に0 */\r
4862                                 sTime.wDay = atoi(Buf);\r
4863                                 sTime.wDayOfWeek = 0;\r
4864                         } else {\r
4865                                 sTime.wYear = Assume1900or2000(atoi(Buf + 7));\r
4866                                 Buf[6] = 0;\r
4867                                 GetMonth(Buf+3, &sTime.wMonth, &sTime.wDay);    /* wDayは常に0 */\r
4868                                 sTime.wDay = atoi(Buf);\r
4869                                 sTime.wDayOfWeek = 0;\r
4870                         }\r
4871                         /* 時刻 */\r
4872                         FindField(Str, Buf, 4 + offs, NO);\r
4873                         sTime.wHour = atoi(Buf);\r
4874                         sTime.wMinute = atoi(Buf+3);\r
4875                         sTime.wSecond = atoi(Buf+6);\r
4876                         sTime.wMilliseconds = 0;\r
4877                         SystemTimeToFileTime(&sTime, Time);\r
4878                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4879 \r
4880                         /* 属性 セキュリティではなく FileCode を保存する */\r
4881                         FindField(Str, Buf, 1 + offs, NO);\r
4882                         *Attr = atoi(Buf);\r
4883                         /* サイズ */\r
4884                         FindField(Str, Buf, 2 + offs, NO);\r
4885                         *Size = _atoi64(Buf);\r
4886                         /* オーナ名 */\r
4887                         if(FindField(Str, Buf, 5 + offs, NO) == FFFTP_SUCCESS) {\r
4888                                 if(strncmp(Buf, "Owner", sizeof("Owner"))) {\r
4889                                         memset(Owner, NUL, OWNER_NAME_LEN+1);\r
4890                                         strncpy(Owner, Buf, OWNER_NAME_LEN);\r
4891                                         /* 通常は 255,255 だが、20, 33 などにも対応する */\r
4892                                         /* 最後の文字が , だったら後ろとつなげる */\r
4893                                         if (Buf[strlen(Buf)-1] == ',') {\r
4894                                                 FindField(Str, Buf, 6 + offs, NO);\r
4895                                                 strncat(Owner, Buf, OWNER_NAME_LEN - strlen(Buf));\r
4896                                         }\r
4897                                         /* ファイル名 */\r
4898                                         if(FindField(Str, Fname, 0, NO) == FFFTP_SUCCESS) {\r
4899                                                 Ret = NODE_FILE;\r
4900                                         }\r
4901                                 }\r
4902                         }\r
4903                         break;\r
4904 #endif\r
4905 \r
4906                         // MLSD対応\r
4907                         // 以下の形式に対応\r
4908                         // fact1=value1;fact2=value2;fact3=value3; filename\r\n\r
4909                         // 不完全な実装のホストが存在するため以下の形式も許容\r
4910                         // fact1=value1;fact2=value2;fact3=value3 filename\r\n\r
4911                         // fact1=value1;fact2=value2;fact3=value3;filename\r\n\r
4912                 case LIST_MLSD:\r
4913                         {\r
4914                                 int i = 0;\r
4915                                 char StrBuf[(FMAX_PATH * 2) + 1];\r
4916                                 char Fact[FMAX_PATH + 1];\r
4917                                 char Name[FMAX_PATH + 1];\r
4918                                 char Value[FMAX_PATH + 1];\r
4919                                 char* pFileName;\r
4920                                 strncpy(StrBuf, Str, FMAX_PATH * 2);\r
4921                                 StrBuf[FMAX_PATH * 2] = '\0';\r
4922                                 if((pFileName = strstr(StrBuf, "; ")) != NULL)\r
4923                                 {\r
4924                                         *pFileName = '\0';\r
4925                                         pFileName += 2;\r
4926                                 }\r
4927                                 else if((pFileName = strchr(StrBuf, ' ')) != NULL)\r
4928                                 {\r
4929                                         *pFileName = '\0';\r
4930                                         pFileName++;\r
4931                                 }\r
4932                                 else if((pFileName = strrchr(StrBuf, ';')) != NULL)\r
4933                                 {\r
4934                                         *pFileName = '\0';\r
4935                                         pFileName++;\r
4936                                 }\r
4937                                 if(pFileName != NULL)\r
4938                                         strcpy(Fname, pFileName);\r
4939                                 while(FindField2(StrBuf, Fact, ';', i, NO) == FFFTP_SUCCESS)\r
4940                                 {\r
4941                                         if(FindField2(Fact, Name, '=', 0, NO) == FFFTP_SUCCESS && FindField2(Fact, Value, '=', 1, NO) == FFFTP_SUCCESS)\r
4942                                         {\r
4943                                                 if(_stricmp(Name, "type") == 0)\r
4944                                                 {\r
4945                                                         if(_stricmp(Value, "dir") == 0)\r
4946                                                                 Ret = NODE_DIR;\r
4947                                                         else if(_stricmp(Value, "file") == 0)\r
4948                                                                 Ret = NODE_FILE;\r
4949                                                 }\r
4950                                                 else if(_stricmp(Name, "size") == 0)\r
4951                                                 {\r
4952                                                         *Size = _atoi64(Value);\r
4953                                                         *InfoExist |= FINFO_SIZE;\r
4954                                                 }\r
4955                                                 else if(_stricmp(Name, "modify") == 0)\r
4956                                                 {\r
4957                                                         sTime.wYear = atoi_n(Value, 4);\r
4958                                                         sTime.wMonth = atoi_n(Value + 4, 2);\r
4959                                                         sTime.wDay = atoi_n(Value + 6, 2);\r
4960                                                         sTime.wHour = atoi_n(Value + 8, 2);\r
4961                                                         sTime.wMinute = atoi_n(Value + 10, 2);\r
4962                                                         sTime.wSecond = atoi_n(Value + 12, 2);\r
4963                                                         sTime.wMilliseconds = 0;\r
4964                                                         SystemTimeToFileTime(&sTime, Time);\r
4965                                                         // 時刻はGMT\r
4966 //                                                      SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
4967                                                         *InfoExist |= FINFO_DATE | FINFO_TIME;\r
4968                                                 }\r
4969                                                 else if(_stricmp(Name, "UNIX.mode") == 0)\r
4970                                                 {\r
4971                                                         *Attr = strtol(Value, NULL, 16);\r
4972                                                         *InfoExist |= FINFO_ATTR;\r
4973                                                 }\r
4974                                                 else if(_stricmp(Name, "UNIX.owner") == 0)\r
4975                                                         strcpy(Owner, Value);\r
4976                                         }\r
4977                                         i++;\r
4978                                 }\r
4979                         }\r
4980                         break;\r
4981 \r
4982                 case LIST_UNIX_10 :\r
4983                 case LIST_UNIX_11 :\r
4984                 case LIST_UNIX_12 :\r
4985                 case LIST_UNIX_13 :\r
4986                 case LIST_UNIX_14 :\r
4987                 case LIST_UNIX_15 :\r
4988                 case LIST_UNIX_20 :\r
4989                 case LIST_UNIX_21 :\r
4990                 case LIST_UNIX_22 :\r
4991                 case LIST_UNIX_23 :\r
4992                 case LIST_UNIX_24 :\r
4993                 case LIST_UNIX_25 :\r
4994                 case LIST_UNIX_50 :\r
4995                 case LIST_UNIX_51 :\r
4996                 case LIST_UNIX_54 :\r
4997                 case LIST_UNIX_60 :\r
4998                 case LIST_UNIX_61 :\r
4999                 case LIST_UNIX_62 :\r
5000                 case LIST_UNIX_63 :\r
5001                 case LIST_UNIX_64 :\r
5002                 case LIST_UNIX_65 :\r
5003                 case LIST_UNIX_70 :\r
5004                 case LIST_UNIX_71 :\r
5005                 case LIST_UNIX_72 :\r
5006                 case LIST_UNIX_73 :\r
5007                 case LIST_UNIX_74 :\r
5008                 case LIST_UNIX_75 :\r
5009 // MELCOMはビットフラグになっている\r
5010 //              case LIST_MELCOM :\r
5011                 // linux-ftpd\r
5012                 case LIST_UNIX_16 :\r
5013                 default:\r
5014                         /* offsはサイズの位置, offs=0はカラム4 */\r
5015                         offs = 0;\r
5016                         if((ListType == LIST_UNIX_12) ||\r
5017                            (ListType == LIST_UNIX_13) ||\r
5018                            (ListType == LIST_UNIX_15) ||\r
5019                            (ListType == LIST_UNIX_20) ||\r
5020                            (ListType == LIST_UNIX_21) ||\r
5021                            (ListType == LIST_UNIX_24))\r
5022                                 offs = -1;\r
5023 \r
5024                         if((ListType == LIST_UNIX_22) ||\r
5025                            (ListType == LIST_UNIX_23) ||\r
5026                            (ListType == LIST_UNIX_25) ||\r
5027                            (ListType == LIST_UNIX_50) ||\r
5028                            (ListType == LIST_UNIX_51) ||\r
5029                            (ListType == LIST_UNIX_54))\r
5030                                 offs = -2;\r
5031 \r
5032                         if((ListType == LIST_UNIX_60) ||\r
5033                            (ListType == LIST_UNIX_61) ||\r
5034                            (ListType == LIST_UNIX_64))\r
5035                                 offs = 2;\r
5036 \r
5037                         if((ListType == LIST_UNIX_62) ||\r
5038                            (ListType == LIST_UNIX_63) ||\r
5039                            (ListType == LIST_UNIX_65) ||\r
5040                            (ListType == LIST_UNIX_70) ||\r
5041                            (ListType == LIST_UNIX_71) ||\r
5042                            (ListType == LIST_UNIX_74))\r
5043                                 offs = 1;\r
5044 \r
5045                         /* offs2は時間(もしくは年)の位置 */\r
5046                         offs2 = 0;\r
5047                         // linux-ftpd\r
5048 //                      if((ListType == LIST_UNIX_11) ||\r
5049 //                         (ListType == LIST_UNIX_13) ||\r
5050 //                         (ListType == LIST_UNIX_21) ||\r
5051 //                         (ListType == LIST_UNIX_23) ||\r
5052 //                         (ListType == LIST_UNIX_51) ||\r
5053 //                         (ListType == LIST_UNIX_61) ||\r
5054 //                         (ListType == LIST_UNIX_63) ||\r
5055 //                         (ListType == LIST_UNIX_71) ||\r
5056 //                         (ListType == LIST_UNIX_73))\r
5057                         if((ListType == LIST_UNIX_11) ||\r
5058                            (ListType == LIST_UNIX_13) ||\r
5059                            (ListType == LIST_UNIX_21) ||\r
5060                            (ListType == LIST_UNIX_23) ||\r
5061                            (ListType == LIST_UNIX_51) ||\r
5062                            (ListType == LIST_UNIX_61) ||\r
5063                            (ListType == LIST_UNIX_63) ||\r
5064                            (ListType == LIST_UNIX_71) ||\r
5065                            (ListType == LIST_UNIX_73) ||\r
5066                            (ListType == LIST_UNIX_16))\r
5067                                 offs2 = -1;\r
5068 \r
5069                         /* offs3はオーナ名の位置 */\r
5070                         offs3 = 0;\r
5071                         if((ListType == LIST_UNIX_12) ||\r
5072                            (ListType == LIST_UNIX_13) ||\r
5073                            (ListType == LIST_UNIX_15) ||\r
5074                            (ListType == LIST_UNIX_22) ||\r
5075                            (ListType == LIST_UNIX_23) ||\r
5076                            (ListType == LIST_UNIX_25) ||\r
5077                            (ListType == LIST_UNIX_50) ||\r
5078                            (ListType == LIST_UNIX_51) ||\r
5079                            (ListType == LIST_UNIX_62) ||\r
5080                            (ListType == LIST_UNIX_63) ||\r
5081                            (ListType == LIST_UNIX_65) ||\r
5082                            (ListType == LIST_UNIX_72) ||\r
5083                            (ListType == LIST_UNIX_73) ||\r
5084                            (ListType == LIST_UNIX_75))\r
5085                                 offs3 = -1;\r
5086 \r
5087                         Flag2 = 0;\r
5088                         if((ListType == LIST_UNIX_14) ||\r
5089                            (ListType == LIST_UNIX_15) ||\r
5090                            (ListType == LIST_UNIX_24) ||\r
5091                            (ListType == LIST_UNIX_25) ||\r
5092                            (ListType == LIST_UNIX_54) ||\r
5093                            (ListType == LIST_UNIX_64) ||\r
5094                            (ListType == LIST_UNIX_65) ||\r
5095                            (ListType == LIST_UNIX_74) ||\r
5096                            (ListType == LIST_UNIX_75))\r
5097                                 Flag2 = 1;\r
5098 \r
5099                         *InfoExist |= (FINFO_DATE | FINFO_SIZE | FINFO_ATTR);\r
5100 \r
5101                         /* 属性 */\r
5102                         FindField(Str, Buf, 0, NO);\r
5103                         *Attr = AttrString2Value(Buf+1);\r
5104 \r
5105                         /* オーナ名 */\r
5106                         FindField(Str, Buf, 2+offs3, NO);\r
5107                         strncpy(Owner, Buf, OWNER_NAME_LEN);\r
5108 \r
5109                         /* サイズ */\r
5110                         FindField(Str, Buf, 4+offs, NO);\r
5111                         Pos = Buf;\r
5112                         if((*Pos != NUL) && (IsDigit(*Pos) == 0))\r
5113                         {\r
5114                                 Pos = strchr(Pos, NUL) - 1;\r
5115                                 for(; Pos > Buf; Pos--)\r
5116                                 {\r
5117                                         if(IsDigit(*Pos) == 0)\r
5118                                         {\r
5119                                                 Pos++;\r
5120                                                 break;\r
5121                                         }\r
5122                                 }\r
5123                         }\r
5124                         *Size = _atoi64(Pos);\r
5125 \r
5126                         if(Flag2 == 0)\r
5127                         {\r
5128                                 /* 時刻/日付 */\r
5129                                 GetLocalTime(&sTime);\r
5130                                 memcpy(&sTimeNow, &sTime, sizeof(SYSTEMTIME));\r
5131                                 sTime.wSecond = 0;\r
5132                                 sTime.wMilliseconds = 0;\r
5133 \r
5134                                 FindField(Str, Buf, 5+offs, NO);\r
5135                                 /* 日付が yy/mm/dd の場合に対応 */\r
5136                                 if(GetYearMonthDay(Buf, &sTime.wYear, &sTime.wMonth, &sTime.wDay) == FFFTP_SUCCESS)\r
5137                                 {\r
5138                                         sTime.wYear = Assume1900or2000(sTime.wYear);\r
5139 \r
5140                                         FindField(Str, Buf, 7+offs+offs2, NO);\r
5141                                         if(GetHourAndMinute(Buf, &sTime.wHour, &sTime.wMinute) == FFFTP_SUCCESS)\r
5142                                                 *InfoExist |= FINFO_TIME;\r
5143                                 }\r
5144                                 // linux-ftpd\r
5145                                 else if(CheckYYYYMMDDformat(Buf, NUL) != 0)\r
5146                                 {\r
5147                                         sTime.wYear = atoi(Buf);\r
5148                                         sTime.wMonth = atoi(Buf+5);\r
5149                                         sTime.wDay = atoi(Buf+8);\r
5150                                         FindField(Str, Buf, 7+offs+offs2, NO);\r
5151                                         if(GetHourAndMinute(Buf, &sTime.wHour, &sTime.wMinute) == FFFTP_SUCCESS)\r
5152                                                 *InfoExist |= FINFO_TIME;\r
5153                                 }\r
5154                                 else\r
5155                                 {\r
5156                                         GetMonth(Buf, &sTime.wMonth, &sTime.wDay);\r
5157                                         if(offs2 == 0)\r
5158                                         {\r
5159                                                 FindField(Str, Buf, 6+offs, NO);\r
5160                                                 sTime.wDay = atoi(Buf);\r
5161                                         }\r
5162 \r
5163                                         FindField(Str, Buf, 7+offs+offs2, NO);\r
5164                                         if(GetHourAndMinute(Buf, &sTime.wHour, &sTime.wMinute) == FFFTP_FAIL)\r
5165                                         {\r
5166                                                 sTime.wYear = atoi(Buf);\r
5167                                         }\r
5168                                         else\r
5169                                         {\r
5170                                                 *InfoExist |= FINFO_TIME;\r
5171 \r
5172                                                 /* 年がない */\r
5173                                                 /* 現在の日付から推定 */\r
5174                                                 // 恐らくホストとローカルの時刻が異なる場合の対処のようだがとりあえず無効にする\r
5175 //                                              if((sTimeNow.wMonth == 12) && (sTime.wMonth == 1))\r
5176 //                                                      sTime.wYear++;\r
5177 //                                              else if(sTimeNow.wMonth+1 == sTime.wMonth)\r
5178                                                 if(sTimeNow.wMonth+1 == sTime.wMonth)\r
5179                                                         /* nothing */;\r
5180                                                 else if(sTimeNow.wMonth < sTime.wMonth)\r
5181                                                         sTime.wYear--;\r
5182 \r
5183 \r
5184 //#################\r
5185                                                 /* 今年の今日以降のファイルは、実は去年のファイル */\r
5186                                                 if((sTime.wYear == sTimeNow.wYear) &&\r
5187                                                    ((sTime.wMonth > sTimeNow.wMonth) ||\r
5188                                                         ((sTime.wMonth == sTimeNow.wMonth) && (sTime.wDay > sTimeNow.wDay))))\r
5189                                                 {\r
5190                                                         sTime.wYear--;\r
5191                                                 }\r
5192                                         }\r
5193                                 }\r
5194                         }\r
5195                         else\r
5196                         {\r
5197                                 /* LIST_UNIX_?4, LIST_UNIX_?5 の時 */\r
5198                                 FindField(Str, Buf, 5+offs, NO);\r
5199                                 sTime.wYear = atoi(Buf);\r
5200                                 FindField(Str, Buf, 6+offs, NO);\r
5201                                 sTime.wMonth = atoi(Buf);\r
5202                                 FindField(Str, Buf, 7+offs, NO);\r
5203                                 sTime.wDay = atoi(Buf);\r
5204                                 sTime.wHour = 0;\r
5205                                 sTime.wMinute = 0;\r
5206                                 sTime.wSecond = 0;\r
5207                                 sTime.wMilliseconds = 0;\r
5208                         }\r
5209                         SystemTimeToFileTime(&sTime, Time);\r
5210                         SpecificLocalFileTime2FileTime(Time, AskHostTimeZone());\r
5211 \r
5212                         /* 名前 */\r
5213                         if(FindField(Str, Fname, 8+offs+offs2, YES) == FFFTP_SUCCESS)\r
5214                         {\r
5215                                 Flag = 'B';\r
5216                                 if(OrgListType & LIST_MELCOM)\r
5217                                 {\r
5218                                         Flag = Fname[14];\r
5219                                         Fname[14] = NUL;\r
5220                                         RemoveTailingSpaces(Fname);\r
5221                                 }\r
5222                                 else\r
5223                                 {\r
5224                                         if((Pos = strstr(Fname, " -> ")) != NULL)\r
5225                                                 *Pos = NUL;\r
5226                                 }\r
5227 \r
5228                                 if(strchr("dl", *Str) != NULL)\r
5229                                 {\r
5230                                         // 0x5Cが含まれる文字列を扱えないバグ修正\r
5231 //                                      if((_mbscmp(_mbsninc(Fname, _mbslen(Fname) - 1), "/") == 0) ||\r
5232 //                                         (_mbscmp(_mbsninc(Fname, _mbslen(Fname) - 1), "\\") == 0))\r
5233 //                                      {\r
5234 //                                              *(Fname + strlen(Fname) - 1) = NUL;\r
5235 //                                      }\r
5236                                         Ret = NODE_DIR;\r
5237                                         if(*Str == 'l')\r
5238                                                 *Link = YES;\r
5239                                 }\r
5240                                 else if(strchr("-+f", *Str) != NULL)\r
5241                                         Ret = NODE_FILE;\r
5242 \r
5243                                 if((Ret == NODE_FILE) && (Flag != 'B'))\r
5244                                         Ret = NODE_NONE;\r
5245                         }\r
5246                         break;\r
5247         }\r
5248 \r
5249         // UTF-8対応\r
5250 //      if((Ret != NODE_NONE) && (strlen(Fname) > 0))\r
5251         if(!(OrgListType & LIST_RAW_NAME) && (Ret != NODE_NONE) && (strlen(Fname) > 0))\r
5252         {\r
5253                 // UTF-8対応\r
5254 //              if(CheckSpecialDirName(Fname) == YES)\r
5255 //                      Ret = NODE_NONE;\r
5256 //              else\r
5257 //                      ChangeFnameRemote2Local(Fname, FMAX_PATH);\r
5258                 ChangeFnameRemote2Local(Fname, FMAX_PATH);\r
5259                 // UTF-8の冗長表現によるディレクトリトラバーサル対策\r
5260                 FixStringM(Fname, Fname);\r
5261                 // 0x5Cが含まれる文字列を扱えないバグ修正\r
5262                 if((_mbscmp(_mbsninc(Fname, _mbslen(Fname) - 1), "/") == 0)\r
5263                         || (_mbscmp(_mbsninc(Fname, _mbslen(Fname) - 1), "\\") == 0))\r
5264                         *(Fname + strlen(Fname) - 1) = NUL;\r
5265                 if(CheckSpecialDirName(Fname) == YES)\r
5266                         Ret = NODE_NONE;\r
5267                 // 文字コードが正しくないために長さが0になったファイル名は表示しない\r
5268                 if(strlen(Fname) == 0)\r
5269                         Ret = NODE_NONE;\r
5270         }\r
5271         return(Ret);\r
5272 }\r
5273 \r
5274 \r
5275 /*----- 指定の番号のフィールドを求める ----------------------------------------\r
5276 *\r
5277 *       Parameter\r
5278 *               char *Str : 文字列\r
5279 *               char *Buf : 文字列のコピー先\r
5280 *               int Num : フィールド番号\r
5281 *               int ToLast : 文字列の最後までコピー (YES/NO)\r
5282 *\r
5283 *       Return Value\r
5284 *               int ステータス\r
5285 *                       FFFTP_SUCCESS/FFFTP_FAIL\r
5286 *----------------------------------------------------------------------------*/\r
5287 \r
5288 static int FindField(char *Str, char *Buf, int Num, int ToLast)\r
5289 {\r
5290         char *Pos;\r
5291         int Sts;\r
5292 \r
5293         Sts = FFFTP_FAIL;\r
5294         *Buf = NUL;\r
5295         if(Num >= 0)\r
5296         {\r
5297                 while(*Str == ' ')\r
5298                         Str++;\r
5299 \r
5300                 for(; Num > 0; Num--)\r
5301                 {\r
5302                         if((Str = strchr(Str, ' ')) != NULL)\r
5303                         {\r
5304                                 while(*Str == ' ')\r
5305                                 {\r
5306                                         if(*Str == NUL)\r
5307                                         {\r
5308                                                 Str = NULL;\r
5309                                                 break;\r
5310                                         }\r
5311                                         Str++;\r
5312                                 }\r
5313                         }\r
5314                         else\r
5315                                 break;\r
5316                 }\r
5317         }\r
5318 \r
5319         if(Str != NULL)\r
5320         {\r
5321                 if((ToLast == YES) || ((Pos = strchr(Str, ' ')) == NULL))\r
5322                         strcpy(Buf, Str);\r
5323                 else\r
5324                 {\r
5325                         strncpy(Buf, Str, Pos - Str);\r
5326                         *(Buf + (Pos - Str)) = NUL;\r
5327                 }\r
5328                 Sts = FFFTP_SUCCESS;\r
5329         }\r
5330         return(Sts);\r
5331 }\r
5332 \r
5333 \r
5334 // MLSD対応\r
5335 static int FindField2(char *Str, char *Buf, char Separator, int Num, int ToLast)\r
5336 {\r
5337         char *Pos;\r
5338         int Sts;\r
5339 \r
5340         Sts = FFFTP_FAIL;\r
5341         *Buf = NUL;\r
5342         if(Num >= 0)\r
5343         {\r
5344                 while(*Str == Separator)\r
5345                         Str++;\r
5346 \r
5347                 for(; Num > 0; Num--)\r
5348                 {\r
5349                         if((Str = strchr(Str, Separator)) != NULL)\r
5350                         {\r
5351                                 while(*Str == Separator)\r
5352                                 {\r
5353                                         if(*Str == NUL)\r
5354                                         {\r
5355                                                 Str = NULL;\r
5356                                                 break;\r
5357                                         }\r
5358                                         Str++;\r
5359                                 }\r
5360                         }\r
5361                         else\r
5362                                 break;\r
5363                 }\r
5364         }\r
5365 \r
5366         if(Str != NULL)\r
5367         {\r
5368                 if((ToLast == YES) || ((Pos = strchr(Str, Separator)) == NULL))\r
5369                         strcpy(Buf, Str);\r
5370                 else\r
5371                 {\r
5372                         strncpy(Buf, Str, Pos - Str);\r
5373                         *(Buf + (Pos - Str)) = NUL;\r
5374                 }\r
5375                 Sts = FFFTP_SUCCESS;\r
5376         }\r
5377         return(Sts);\r
5378 }\r
5379 \r
5380 \r
5381 /*----- 文字列から月を求める --------------------------------------------------\r
5382 *\r
5383 *       Parameter\r
5384 *               char *Str : 文字列\r
5385 *               WORD *Month : 月 (0=月を表す文字列ではない)\r
5386 *               WORD *Day : 日 (0=日は含まれていない)\r
5387 *\r
5388 *       Return Value\r
5389 *               なし\r
5390 *----------------------------------------------------------------------------*/\r
5391 \r
5392 static void GetMonth(char *Str, WORD *Month, WORD *Day)\r
5393 {\r
5394         static const char DateStr[] = { "JanFebMarAprMayJunJulAugSepOctNovDec" };\r
5395         char *Pos;\r
5396 \r
5397         *Month = 0;\r
5398         *Day = 0;\r
5399 \r
5400         if(IsDigit(*Str) == 0)\r
5401         {\r
5402                 _strlwr(Str);\r
5403                 *Str = toupper(*Str);\r
5404                 if((Pos = strstr(DateStr, Str)) != NULL)\r
5405                         *Month = ((Pos - DateStr) / 3) + 1;\r
5406         }\r
5407         else\r
5408         {\r
5409                 /* 「10月」のような日付を返すものがある */\r
5410                 /* 漢字がJISの時のみSJISに変換 */\r
5411                 ConvAutoToSJIS(Str, KANJI_NOCNV);\r
5412 \r
5413                 Pos = Str;\r
5414                 while(*Pos != NUL)\r
5415                 {\r
5416                         if(!IsDigit(*Pos))\r
5417                         {\r
5418                                 // UTF-8対応\r
5419 //                              if((_mbsncmp(Pos, "月", 1) == 0) ||\r
5420 //                                 (memcmp(Pos, "\xB7\xEE", 2) == 0) || /* EUCの「月」 */\r
5421 //                                 (memcmp(Pos, "\xD4\xC2", 2) == 0))   /* GBコードの「月」 */\r
5422                                 if(memcmp(Pos, "\xE6\x9C\x88", 3) == 0 || memcmp(Pos, "\x8C\x8E", 2) == 0 || memcmp(Pos, "\xB7\xEE", 2) == 0 || memcmp(Pos, "\xD4\xC2", 2) == 0)\r
5423                                 {\r
5424                                         Pos += 2;\r
5425                                         *Month = atoi(Str);\r
5426                                         if((*Month < 1) || (*Month > 12))\r
5427                                                 *Month = 0;\r
5428                                         else\r
5429                                         {\r
5430                                                 /* 「10月11日」のように日がくっついている事がある */\r
5431                                                 if(*Pos != NUL)\r
5432                                                 {\r
5433                                                         *Day = atoi(Pos);\r
5434                                                         if((*Day < 1) || (*Day > 31))\r
5435                                                                 *Day = 0;\r
5436                                                 }\r
5437                                         }\r
5438                                 }\r
5439                                 else if(_mbsncmp(Pos, "/", 1) == 0)\r
5440                                 {\r
5441                                         /* 「10/」のような日付を返すものがある */\r
5442                                         Pos += 1;\r
5443                                         *Month = atoi(Str);\r
5444                                         if((*Month < 1) || (*Month > 12))\r
5445                                                 *Month = 0;\r
5446                                         else\r
5447                                         {\r
5448                                                 /* 「10/11」のように日がくっついている事がある */\r
5449                                                 if(*Pos != NUL)\r
5450                                                 {\r
5451                                                         *Day = atoi(Pos);\r
5452                                                         if((*Day < 1) || (*Day > 31))\r
5453                                                                 *Day = 0;\r
5454                                                 }\r
5455                                         }\r
5456                                 }\r
5457                                 break;\r
5458                         }\r
5459                         Pos++;\r
5460                 }\r
5461         }\r
5462         return;\r
5463 }\r
5464 \r
5465 \r
5466 /*----- 文字列から年月日を求める ----------------------------------------------\r
5467 *\r
5468 *       Parameter\r
5469 *               char *Str : 文字列\r
5470 *               WORD *Year : 年\r
5471 *               WORD *Month : 月\r
5472 *               WORD *Day : 日\r
5473 *\r
5474 *       Return Value\r
5475 *               int ステータス (FFFTP_SUCCESS/FFFTP_FAIL=日付を表す文字ではない)\r
5476 *\r
5477 *       Note\r
5478 *               以下の形式をサポート\r
5479 *                       01/07/25\r
5480 *               FFFTP_FAILを返す時は *Year = 0; *Month = 0; *Day = 0\r
5481 *----------------------------------------------------------------------------*/\r
5482 static int GetYearMonthDay(char *Str, WORD *Year, WORD *Month, WORD *Day)\r
5483 {\r
5484         int Sts;\r
5485 \r
5486         Sts = FFFTP_FAIL;\r
5487         if(strlen(Str) == 8)\r
5488         {\r
5489                 if(IsDigit(Str[0]) && IsDigit(Str[1]) && !IsDigit(Str[2]) &&\r
5490                    IsDigit(Str[3]) && IsDigit(Str[4]) && !IsDigit(Str[5]) &&\r
5491                    IsDigit(Str[6]) && IsDigit(Str[7]))\r
5492                 {\r
5493                         *Year = atoi(&Str[0]);\r
5494                         *Month = atoi(&Str[3]);\r
5495                         *Day = atoi(&Str[6]);\r
5496                         Sts = FFFTP_SUCCESS;\r
5497                 }\r
5498         }\r
5499         return(Sts);\r
5500 }\r
5501 \r
5502 \r
5503 /*----- 文字列から時刻を取り出す ----------------------------------------------\r
5504 *\r
5505 *       Parameter\r
5506 *               char *Str : 文字列\r
5507 *               WORD *Hour : 時\r
5508 *               WORD *Minute : 分\r
5509 *\r
5510 *       Return Value\r
5511 *               int ステータス (FFFTP_SUCCESS/FFFTP_FAIL=時刻を表す文字ではない)\r
5512 *\r
5513 *       Note\r
5514 *               以下の形式をサポート\r
5515 *                       HH:MM\r
5516 *                       HH時MM分\r
5517 *               FFFTP_FAILを返す時は *Hour = 0; *Minute = 0\r
5518 *----------------------------------------------------------------------------*/\r
5519 \r
5520 static int GetHourAndMinute(char *Str, WORD *Hour, WORD *Minute)\r
5521 {\r
5522         int Ret;\r
5523         char *Pos;\r
5524 \r
5525         Ret = FFFTP_FAIL;\r
5526         if((_mbslen(Str) >= 3) && (isdigit(Str[0]) != 0))\r
5527         {\r
5528                 *Hour = atoi(Str);\r
5529                 if(*Hour <= 24)\r
5530                 {\r
5531                         if((Pos = _mbschr(Str, ':')) != NULL)\r
5532                         {\r
5533                                 Pos++;\r
5534                                 if(IsDigit(*Pos) != 0)\r
5535                                 {\r
5536                                         *Minute = atoi(Pos);\r
5537                                         if(*Minute < 60)\r
5538                                                 Ret = FFFTP_SUCCESS;\r
5539                                 }\r
5540                         }\r
5541                         else\r
5542                         {\r
5543                                 /* 漢字がJISの時のみSJISに変換 */\r
5544                                 ConvAutoToSJIS(Str, KANJI_NOCNV);\r
5545 \r
5546                                 Pos = Str;\r
5547                                 while(*Pos != NUL)\r
5548                                 {\r
5549                                         if(IsDigit(*Pos) == 0)\r
5550                                         {\r
5551                                                 // UTF-8対応\r
5552 //                                              if((_mbsncmp(Pos, "時", 1) == 0) ||\r
5553 //                                                 (memcmp(Pos, "\xBB\xFE", 2) == 0))   /* EUCの「時」 */\r
5554                                                 if(memcmp(Pos, "\xE6\x99\x82", 3) == 0 || memcmp(Pos, "\x8E\x9E", 2) == 0 || memcmp(Pos, "\xBB\xFE", 2) == 0)\r
5555                                                 {\r
5556                                                         Pos += 2;\r
5557                                                         if(*Pos != NUL)\r
5558                                                         {\r
5559                                                                 *Minute = atoi(Pos);\r
5560                                                                 if(*Minute < 60)\r
5561                                                                         Ret = FFFTP_SUCCESS;\r
5562                                                         }\r
5563                                                 }\r
5564                                                 break;\r
5565                                         }\r
5566                                         Pos++;\r
5567                                 }\r
5568                         }\r
5569                 }\r
5570         }\r
5571         else if((_stricmp(Str, "a:m") == 0) || (_stricmp(Str, "p:m") == 0))\r
5572         {\r
5573                 *Hour = 0;\r
5574                 *Minute = 0;\r
5575                 Ret = FFFTP_SUCCESS;\r
5576         }\r
5577 \r
5578         if(Ret == FFFTP_FAIL)\r
5579         {\r
5580                 *Hour = 0;\r
5581                 *Minute = 0;\r
5582         }\r
5583         return(Ret);\r
5584 }\r
5585 \r
5586 \r
5587 /*----- VAX VMSの日付文字列から日付を取り出す ---------------------------------\r
5588 *\r
5589 *       Parameter\r
5590 *               char *Str : 文字列\r
5591 *               WORD *Year : 年\r
5592 *               WORD *Month : 月\r
5593 *               WORD *Day : 日\r
5594 *\r
5595 *       Return Value\r
5596 *               int ステータス (FFFTP_SUCCESS/FFFTP_FAIL=日付を表す文字ではない)\r
5597 *\r
5598 *       Note\r
5599 *               以下の形式をサポート\r
5600 *                       18-SEP-1998\r
5601 *               FFFTP_FAILを返す時は *Year = 0; *Month = 0; *Day = 0\r
5602 *----------------------------------------------------------------------------*/\r
5603 \r
5604 static int GetVMSdate(char *Str, WORD *Year, WORD *Month, WORD *Day)\r
5605 {\r
5606         char *Pos;\r
5607         int Ret;\r
5608         WORD Tmp;\r
5609         char Buf[4];\r
5610 \r
5611         Ret = FFFTP_FAIL;\r
5612         *Day = atoi(Str);\r
5613         if((Pos = strchr(Str, '-')) != NULL)\r
5614         {\r
5615                 Pos++;\r
5616                 strncpy(Buf, Pos, 3);\r
5617                 Buf[3] = NUL;\r
5618                 GetMonth(Buf, Month, &Tmp);\r
5619                 if((Pos = strchr(Pos, '-')) != NULL)\r
5620                 {\r
5621                         Pos++;\r
5622                         *Year = atoi(Pos);\r
5623                         Ret = FFFTP_SUCCESS;\r
5624                 }\r
5625         }\r
5626 \r
5627         if(Ret == FFFTP_FAIL)\r
5628         {\r
5629                 *Year = 0;\r
5630                 *Month = 0;\r
5631                 *Day = 0;\r
5632         }\r
5633         return(Ret);\r
5634 }\r
5635 \r
5636 \r
5637 /*----- 1900年代か2000年代かを決める ------------------------------------------\r
5638 *\r
5639 *       Parameter\r
5640 *               int Year : 年(2桁)\r
5641 *\r
5642 *       Return Value\r
5643 *               int 年\r
5644 *----------------------------------------------------------------------------*/\r
5645 \r
5646 int Assume1900or2000(int Year)\r
5647 {\r
5648         if(Year >= 60)\r
5649                 Year += 1900;\r
5650         else\r
5651                 Year += 2000;\r
5652         return(Year);\r
5653 }\r
5654 \r
5655 \r
5656 \r
5657 /*----- "."や".."かどうかを返す -----------------------------------------------\r
5658 *\r
5659 *       Parameter\r
5660 *               char *Fname : ファイル名\r
5661 *\r
5662 *       Return Value\r
5663 *               int ステータス (YES="."か".."のどちらか/NO)\r
5664 *----------------------------------------------------------------------------*/\r
5665 \r
5666 static int CheckSpecialDirName(char *Fname)\r
5667 {\r
5668         int Sts;\r
5669 \r
5670         Sts = NO;\r
5671         if((strcmp(Fname, ".") == 0) || (strcmp(Fname, "..") == 0))\r
5672                 Sts = YES;\r
5673 \r
5674         return(Sts);\r
5675 }\r
5676 \r
5677 \r
5678 /*----- フィルタに指定されたファイル名かどうかを返す --------------------------\r
5679 *\r
5680 *       Parameter\r
5681 *               char Fname : ファイル名\r
5682 *               int Type : ファイルのタイプ (NODE_xxx)\r
5683 *\r
5684 *       Return Value\r
5685 *               int ステータス\r
5686 *                       YES/NO=表示しない\r
5687 *\r
5688 *       Note\r
5689 *               フィルタ文字列は以下の形式\r
5690 *                       *.txt;*.log\r
5691 *----------------------------------------------------------------------------*/\r
5692 \r
5693 static int AskFilterStr(char *Fname, int Type)\r
5694 {\r
5695         int Ret;\r
5696         char *Tbl;\r
5697         char *Pos;\r
5698         char Tmp[FILTER_EXT_LEN+1];\r
5699 \r
5700         Tbl = FilterStr;\r
5701         Ret = YES;\r
5702         if((strlen(Tbl) > 0) && (Type == NODE_FILE))\r
5703         {\r
5704                 Ret = NO;\r
5705                 while((Tbl != NULL) && (*Tbl != NUL))\r
5706                 {\r
5707                         while(*Tbl == ';')\r
5708                                 Tbl++;\r
5709                         if(*Tbl == NUL)\r
5710                                 break;\r
5711 \r
5712                         strcpy(Tmp, Tbl);\r
5713                         if((Pos = strchr(Tmp, ';')) != NULL)\r
5714                                 *Pos = NUL;\r
5715 \r
5716                         if(CheckFname(Fname, Tmp) == FFFTP_SUCCESS)\r
5717                         {\r
5718                                 Ret = YES;\r
5719                                 break;\r
5720                         }\r
5721 \r
5722                         Tbl = strchr(Tbl, ';');\r
5723                 }\r
5724         }\r
5725         return(Ret);\r
5726 }\r
5727 \r
5728 \r
5729 /*----- フィルタを設定する ----------------------------------------------------\r
5730 *\r
5731 *       Parameter\r
5732 *               なし\r
5733 *\r
5734 *       Return Value\r
5735 *               なし\r
5736 *----------------------------------------------------------------------------*/\r
5737 \r
5738 void SetFilter(int *CancelCheckWork)\r
5739 {\r
5740         if(DialogBox(GetFtpInst(), MAKEINTRESOURCE(filter_dlg), GetMainHwnd(), FilterWndProc) == YES)\r
5741         {\r
5742                 DispWindowTitle();\r
5743                 GetLocalDirForWnd();\r
5744                 GetRemoteDirForWnd(CACHE_LASTREAD, CancelCheckWork);\r
5745         }\r
5746         return;\r
5747 }\r
5748 \r
5749 \r
5750 /*----- フィルタ入力ダイアログのコールバック ----------------------------------\r
5751 *\r
5752 *       Parameter\r
5753 *               HWND hDlg : ウインドウハンドル\r
5754 *               UINT message : メッセージ番号\r
5755 *               WPARAM wParam : メッセージの WPARAM 引数\r
5756 *               LPARAM lParam : メッセージの LPARAM 引数\r
5757 *\r
5758 *       Return Value\r
5759 *               BOOL TRUE/FALSE\r
5760 *----------------------------------------------------------------------------*/\r
5761 \r
5762 // 64ビット対応\r
5763 //static BOOL CALLBACK FilterWndProc(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam)\r
5764 static INT_PTR CALLBACK FilterWndProc(HWND hDlg, UINT iMessage, WPARAM wParam, LPARAM lParam)\r
5765 {\r
5766         switch (iMessage)\r
5767         {\r
5768                 case WM_INITDIALOG :\r
5769                         SendDlgItemMessage(hDlg, FILTER_STR, EM_LIMITTEXT, FILTER_EXT_LEN+1, 0);\r
5770                         SendDlgItemMessage(hDlg, FILTER_STR, WM_SETTEXT, 0, (LPARAM)FilterStr);\r
5771                         return(TRUE);\r
5772 \r
5773                 case WM_COMMAND :\r
5774                         switch(GET_WM_COMMAND_ID(wParam, lParam))\r
5775                         {\r
5776                                 case IDOK :\r
5777                                         SendDlgItemMessage(hDlg, FILTER_STR, WM_GETTEXT, FILTER_EXT_LEN, (LPARAM)FilterStr);\r
5778                                         EndDialog(hDlg, YES);\r
5779                                         break;\r
5780 \r
5781                                 case IDCANCEL :\r
5782                                         EndDialog(hDlg, NO);\r
5783                                         break;\r
5784 \r
5785                                 case FILTER_NOR :\r
5786                                         strcpy(FilterStr, "*");\r
5787                                         EndDialog(hDlg, YES);\r
5788                                         break;\r
5789 \r
5790                                 case IDHELP :\r
5791                                         hHelpWin = HtmlHelp(NULL, AskHelpFilePath(), HH_HELP_CONTEXT, IDH_HELP_TOPIC_0000021);\r
5792                                         break;\r
5793                         }\r
5794             return(TRUE);\r
5795         }\r
5796         return(FALSE);\r
5797 }\r
5798 \r
5799 \r
5800 \r
5801 \r
5802 \r
5803 static int atoi_n(const char *Str, int Len)\r
5804 {\r
5805         char *Tmp;\r
5806         int Ret;\r
5807 \r
5808         Ret = 0;\r
5809         if((Tmp = malloc(Len+1)) != NULL)\r
5810         {\r
5811                 memset(Tmp, 0, Len+1);\r
5812                 strncpy(Tmp, Str, Len);\r
5813                 Ret = atoi(Tmp);\r
5814                 free(Tmp);\r
5815         }\r
5816         return(Ret);\r
5817 }\r
5818 \r
5819 \r
5820 \r
5821 \r
5822 // UTF-8対応\r
5823 // ファイル一覧から漢字コードを推測\r
5824 // 優先度はUTF-8、Shift_JIS、EUC、JISの順\r
5825 int AnalyzeNameKanjiCode(int Num)\r
5826 {\r
5827         char Str[FMAX_PATH+1];\r
5828         char Name[FMAX_PATH+1];\r
5829         LONGLONG Size;\r
5830         FILETIME Time;\r
5831         int Attr;\r
5832         FILE *fd;\r
5833         int Node;\r
5834         int ListType;\r
5835         char Owner[OWNER_NAME_LEN+1];\r
5836         int Link;\r
5837         int InfoExist;\r
5838         int NameKanjiCode;\r
5839         int Point;\r
5840         int PointSJIS;\r
5841         int PointJIS;\r
5842         int PointEUC;\r
5843         int PointUTF8N;\r
5844         char* p;\r
5845 \r
5846         NameKanjiCode = KANJI_AUTO;\r
5847         Point = 0;\r
5848         PointSJIS = 0;\r
5849         PointJIS = 0;\r
5850         PointEUC = 0;\r
5851         PointUTF8N = 0;\r
5852         MakeCacheFileName(Num, Str);\r
5853         if((fd = fopen(Str, "rb")) != NULL)\r
5854         {\r
5855                 while(GetListOneLine(Str, FMAX_PATH, fd) == FFFTP_SUCCESS)\r
5856                 {\r
5857                         if((ListType = AnalizeFileInfo(Str)) != LIST_UNKNOWN)\r
5858                         {\r
5859                                 strcpy(Name, "");\r
5860                                 Node = ResolvFileInfo(Str, ListType | LIST_RAW_NAME, Name, &Size, &Time, &Attr, Owner, &Link, &InfoExist);\r
5861                                 p = Name;\r
5862                                 while(*p != '\0')\r
5863                                 {\r
5864                                         if(*p & 0x80)\r
5865                                         {\r
5866                                                 p = NULL;\r
5867                                                 break;\r
5868                                         }\r
5869                                         p++;\r
5870                                 }\r
5871                                 if(!p)\r
5872                                 {\r
5873                                         if(!CheckStringM(Name))\r
5874                                                 PointUTF8N++;\r
5875                                         else\r
5876                                         {\r
5877                                                 switch(CheckKanjiCode(Name, strlen(Name), KANJI_SJIS))\r
5878                                                 {\r
5879                                                 case KANJI_SJIS:\r
5880                                                         PointSJIS++;\r
5881                                                         break;\r
5882                                                 case KANJI_JIS:\r
5883                                                         PointJIS++;\r
5884                                                         break;\r
5885                                                 case KANJI_EUC:\r
5886                                                         PointEUC++;\r
5887                                                         break;\r
5888                                                 }\r
5889                                         }\r
5890                                 }\r
5891                         }\r
5892                 }\r
5893                 fclose(fd);\r
5894         }\r
5895         if(PointJIS >= Point)\r
5896         {\r
5897                 NameKanjiCode = KANJI_JIS;\r
5898                 Point = PointJIS;\r
5899         }\r
5900         if(PointEUC >= Point)\r
5901         {\r
5902                 NameKanjiCode = KANJI_EUC;\r
5903                 Point = PointEUC;\r
5904         }\r
5905         if(PointSJIS >= Point)\r
5906         {\r
5907                 NameKanjiCode = KANJI_SJIS;\r
5908                 Point = PointSJIS;\r
5909         }\r
5910         if(PointUTF8N >= Point)\r
5911         {\r
5912                 NameKanjiCode = KANJI_UTF8N;\r
5913                 Point = PointUTF8N;\r
5914         }\r
5915         return NameKanjiCode;\r
5916 }\r
5917 \r