Develop and Download Open Source Software

Browse Subversion Repository

Contents of /trunk/teraterm/ttpcmn/ttcmn.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 10009 - (show annotations) (download) (as text)
Thu Jun 23 23:59:07 2022 UTC (21 months, 2 weeks ago) by nmaya
File MIME type: text/x-csrc
File size: 36847 byte(s)
アイコンまわりを整理した

ディスプレイ拡大率にあったサイズのアイコンが使われるようにした
  各ウィンドウに動的にセットされるアイコン(タイトルバー・タスクバーなどで表示される)
  通知アイコン
通知アイコンにフルカラーのアイコンが使われるようにした
TTSSH から通知があったときには TTSSH のアイコンが使われるようにした
カスタム通知アイコンをセットする API を変更した

merge from branches/adjust_icon
ticket #43907, #44517
1 /*
2 * Copyright (C) 1994-1998 T. Teranishi
3 * (C) 2004- TeraTerm Project
4 * All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 *
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. The name of the author may not be used to endorse or promote products
16 * derived from this software without specific prior written permission.
17 *
18 * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
19 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21 * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT,
22 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 */
29
30 /* TTCMN.DLL, main */
31 #include <direct.h>
32 #include <string.h>
33 #include <stdio.h>
34 #include <windows.h>
35 #include <setupapi.h>
36 #include <htmlhelp.h>
37 #include <assert.h>
38 #include <crtdbg.h>
39 #include <time.h>
40
41 #define DllExport __declspec(dllexport)
42 #include "language.h"
43 #undef DllExport
44
45 #include "teraterm.h"
46 #include "tttypes.h"
47 #include "ttlib.h"
48 #include "tt_res.h"
49 #include "codeconv.h"
50 #include "compat_win.h"
51 #include "win32helper.h"
52 #include "asprintf.h"
53 #include "fileread.h"
54 #include "../teraterm/unicode.h"
55
56 #include "ttcmn_dup.h"
57
58 #define DllExport __declspec(dllexport)
59 #include "ttcommon.h"
60
61 /* shared memory */
62 typedef struct {
63 size_t size_tmap; /* sizeof TMap */
64 size_t size_tttset; /* sizeof TTTSet */
65 // Window list
66 int NWin;
67 HWND WinList[MAXNWIN];
68 /* COM port use flag
69 * bit 8 7 6 5 4 3 2 1
70 * char[0] : COM 8 7 6 5 4 3 2 1
71 * char[1] : COM16 15 14 13 12 11 10 9 ...
72 */
73 unsigned char ComFlag[(MAXCOMPORT-1)/CHAR_BIT+1];
74 /* Previous window rect (Tera Term 4.78 or later) */
75 WINDOWPLACEMENT WinPrevRect[MAXNWIN];
76 BOOL WinUndoFlag;
77 int WinUndoStyle;
78 // Duplicate Teraterm data
79 HANDLE DuplicateDataHandle;
80 DWORD DuplicateDataSizeLow;
81 } TMap;
82 typedef TMap *PMap;
83
84 // TMap ���i�[�����t�@�C���}�b�s���O�I�u�W�F�N�g(���L������)�����O
85 // TMap(�����������o)���X�V�������o�[�W�������������N���������������K�v��������
86 // �A�������o�[�W�����������g�����������X�������A���������������X�����K�v������
87 #define TT_FILEMAPNAME "ttset_memfilemap_" TT_VERSION_STR("_")
88
89 /* first instance flag */
90 static BOOL FirstInstance = TRUE;
91
92 static HINSTANCE hInst;
93
94 static PMap pm;
95
96 static HANDLE HMap = NULL;
97 #define VTCLASSNAME "VTWin32"
98 #define TEKCLASSNAME "TEKWin32"
99
100 enum window_style {
101 WIN_CASCADE,
102 WIN_STACKED,
103 WIN_SIDEBYSIDE,
104 };
105
106 static const char DupDataName[] = "dupdata";
107
108 void WINAPI CopyShmemToTTSet(PTTSet ts)
109 {
110 DWORD size = pm->DuplicateDataSizeLow;
111 HANDLE handle = CreateFileMappingA(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, size, DupDataName);
112 void *ptr = (void *)MapViewOfFile(handle, FILE_MAP_ALL_ACCESS, 0, 0, 0);
113 TTCMNUnserialize(ptr, (size_t)size, ts);
114 UnmapViewOfFile(ptr);
115 CloseHandle(handle);
116 pm->DuplicateDataSizeLow = 0;
117 }
118
119 void WINAPI CopyTTSetToShmem(PTTSet ts)
120 {
121 size_t size;
122 void *ptr = TTCMNSerialize(ts, &size);
123 if (ptr != NULL) {
124 HANDLE handle = CreateFileMappingA(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, (DWORD)size, DupDataName);
125 void *dest = (void *)MapViewOfFile(handle, FILE_MAP_ALL_ACCESS,0,0,0);
126 memcpy(dest, ptr, size);
127 UnmapViewOfFile(dest);
128 //CloseHandle(handle); do not close, �g�p����������������������������������
129
130 if (pm->DuplicateDataHandle != NULL) {
131 // 1���O����������������
132 CloseHandle(pm->DuplicateDataHandle);
133 }
134 pm->DuplicateDataHandle = handle;
135 pm->DuplicateDataSizeLow = (DWORD)size;
136 free(ptr);
137 }
138 }
139
140 static void CopyFiles(const wchar_t *file_list[], const wchar_t *src_dir, const wchar_t *dest_dir)
141 {
142 for (;;) {
143 wchar_t *dest;
144 size_t len;
145 const wchar_t *filename = *file_list;
146 file_list++;
147 if (filename == NULL) {
148 break;
149 }
150
151 dest = NULL;
152 awcscats(&dest, dest_dir, L"\\", filename, NULL);
153
154 len = wcslen(dest);
155 if (dest[len - 1] == '\\') {
156 // �t�H���_����
157 CreateDirectoryW(dest, NULL);
158 }
159 else {
160 wchar_t *src = NULL;
161 awcscats(&src, src_dir, L"\\", filename, NULL);
162 CopyFileW(src, dest, TRUE); // TRUE = do not copy if exists
163 free(src);
164 }
165 free(dest);
166 }
167 }
168
169 static void ConvertIniFiles(const wchar_t *filelist[], const wchar_t *dir, const wchar_t *date_str)
170 {
171 while(1) {
172 wchar_t *fname;
173 if (*filelist == NULL) {
174 break;
175 }
176
177 fname = NULL;
178 awcscats(&fname, dir, L"\\", *filelist, NULL);
179 ConvertIniFileCharCode(fname, date_str);
180 free(fname);
181 filelist++;
182 }
183 }
184
185 BOOL WINAPI StartTeraTerm(PTTSet ts)
186 {
187 if (FirstInstance) {
188 // init window list
189 pm->NWin = 0;
190 }
191 else {
192 /* only the first instance uses saved position */
193 ts->VTPos.x = CW_USEDEFAULT;
194 ts->VTPos.y = CW_USEDEFAULT;
195 ts->TEKPos.x = CW_USEDEFAULT;
196 ts->TEKPos.y = CW_USEDEFAULT;
197 }
198
199 // if (FirstInstance) { �������������� (2008.3.13 maya)
200 // �N���������A���L�������� HomeDir �� SetupFName ����������
201 /* Get home directory (ttermpro.exe���t�H���_) */
202 ts->ExeDirW = GetExeDirW(hInst);
203
204 // LogDir
205 ts->LogDirW = GetLogDirW(hInst);
206
207 // HomeDir
208 ts->HomeDirW = GetHomeDirW(hInst);
209 WideCharToACP_t(ts->HomeDirW, ts->HomeDir, _countof(ts->HomeDir));
210 SetCurrentDirectoryW(ts->HomeDirW); // TODO �K�v??
211
212 // TERATERM.INI ���t���p�X
213 ts->SetupFNameW = NULL;
214 awcscats(&ts->SetupFNameW, ts->HomeDirW, L"\\TERATERM.INI", NULL);
215 WideCharToACP_t(ts->SetupFNameW, ts->SetupFName, _countof(ts->SetupFName));
216
217 // KEYBOARD.CNF ���t���p�X
218 ts->KeyCnfFNW = NULL;
219 awcscats(&ts->KeyCnfFNW, ts->HomeDirW, L"\\KEYBOARD.CNF", NULL);
220 WideCharToACP_t(ts->KeyCnfFNW, ts->KeyCnfFN, _countof(ts->KeyCnfFN));
221
222 // �|�[�^�u�����[�h���������A
223 // ���l�����t�@�C���������t�H���_ HomeDirW �� TERATERM.INI ����������������
224 if (!IsPortableMode() &&
225 (GetFileAttributesW(ts->SetupFNameW) == INVALID_FILE_ATTRIBUTES)) {
226 // �����t�@�C�������l�t�H���_���R�s�[����
227 static const wchar_t *filelist[] = {
228 L"TERATERM.INI",
229 L"KEYBOARD.CNF",
230 L"cygterm.cfg",
231 L"ssh_known_hosts",
232 L"theme\\",
233 L"theme\\Advanced.sample",
234 L"theme\\ImageFile.INI",
235 L"theme\\scale\\",
236 L"theme\\scale\\23.jpg",
237 L"theme\\scale\\43.jpg",
238 L"theme\\Scale.INI",
239 L"theme\\tile\\",
240 L"theme\\tile\\03.jpg",
241 L"theme\\tile\\44.jpg",
242 L"theme\\Tile.INI",
243 NULL,
244 };
245 CopyFiles(filelist, ts->ExeDirW, ts->HomeDirW);
246 }
247
248 // ini�t�@�C���������R�[�h����������
249 {
250 static const wchar_t *filelist[] = {
251 L"TERATERM.INI",
252 L"KEYBOARD.CNF",
253 NULL,
254 };
255
256 // backup �t�@�C�������������t������
257 wchar_t *date_str = MakeISO8601Str(0);
258 awcscat(&date_str, L"_");
259
260 // ini�t�@�C������������
261 ConvertIniFiles(filelist, ts->HomeDirW, date_str);
262
263 free(date_str);
264 }
265
266 if (FirstInstance) {
267 FirstInstance = FALSE;
268 return TRUE;
269 }
270 else {
271 return FALSE;
272 }
273
274 ts->PluginVTIconInstance = NULL;
275 ts->PluginVTIconID = 0;
276 }
277
278 // �����t�@�C�����f�B�X�N���������ATera Term�{�������N�������B
279 // (2012.4.30 yutaka)
280 // �g����������?
281 void WINAPI RestartTeraTerm(HWND hwnd, PTTSet ts)
282 {
283 wchar_t *path;
284 int ret;
285
286 static const TTMessageBoxInfoW info = {
287 "Tera Term",
288 NULL, L"Tera Term: Configuration Warning",
289 "MSG_TT_TAKE_EFFECT",
290 L"This option takes effect the next time a session is started.\n"
291 L"Are you sure that you want to relaunch Tera Term?",
292 MB_YESNO | MB_ICONEXCLAMATION | MB_DEFBUTTON2
293 };
294 ret = TTMessageBoxA(hwnd, &info, ts->UILanguageFile);
295 if (ret != IDYES)
296 return;
297
298 SendMessage(hwnd, WM_COMMAND, ID_SETUP_SAVE, 0);
299 // ID_FILE_EXIT ���b�Z�[�W�����A�v�������������������������AWM_QUIT ���|�X�g�����B
300 //PostMessage(hwnd, WM_COMMAND, ID_FILE_EXIT, 0);
301 PostQuitMessage(0);
302
303 // ���v���Z�X�����N���B
304 if (hGetModuleFileNameW(NULL, &path) == 0) {
305 TTWinExec(path);
306 free(path);
307 }
308 }
309
310 void WINAPI SetCOMFlag(int Com)
311 {
312 pm->ComFlag[(Com-1)/CHAR_BIT] |= 1 << ((Com-1)%CHAR_BIT);
313 }
314
315 void WINAPI ClearCOMFlag(int Com)
316 {
317 pm->ComFlag[(Com-1)/CHAR_BIT] &= ~(1 << ((Com-1)%CHAR_BIT));
318 }
319
320 int WINAPI CheckCOMFlag(int Com)
321 {
322 return ((pm->ComFlag[(Com-1)/CHAR_BIT] & 1 << (Com-1)%CHAR_BIT) > 0);
323 }
324
325 int WINAPI RegWin(HWND HWinVT, HWND HWinTEK)
326 {
327 int i, j;
328
329 if (pm->NWin>=MAXNWIN)
330 return 0;
331 if (HWinVT==NULL)
332 return 0;
333 if (HWinTEK!=NULL) {
334 i = 0;
335 while ((i<pm->NWin) && (pm->WinList[i]!=HWinVT))
336 i++;
337 if (i>=pm->NWin)
338 return 0;
339 for (j=pm->NWin-1 ; j>i ; j--)
340 pm->WinList[j+1] = pm->WinList[j];
341 pm->WinList[i+1] = HWinTEK;
342 pm->NWin++;
343 return 0;
344 }
345 pm->WinList[pm->NWin++] = HWinVT;
346 memset(&pm->WinPrevRect[pm->NWin - 1], 0, sizeof(pm->WinPrevRect[pm->NWin - 1])); // RECT clear
347 if (pm->NWin==1) {
348 return 1;
349 }
350 else {
351 return (int)(SendMessage(pm->WinList[pm->NWin-2],
352 WM_USER_GETSERIALNO,0,0)+1);
353 }
354 }
355
356 void WINAPI UnregWin(HWND HWin)
357 {
358 int i, j;
359
360 i = 0;
361 while ((i<pm->NWin) && (pm->WinList[i]!=HWin)) {
362 i++;
363 }
364 if (pm->WinList[i]!=HWin) {
365 return;
366 }
367 for (j=i ; j<pm->NWin-1 ; j++) {
368 pm->WinList[j] = pm->WinList[j+1];
369 pm->WinPrevRect[j] = pm->WinPrevRect[j+1]; // RECT shift
370 }
371 if (pm->NWin>0) {
372 pm->NWin--;
373 }
374 }
375
376 char GetWindowTypeChar(HWND Hw, HWND HWin)
377 {
378 #if 0
379 if (HWin == Hw)
380 return '*';
381 else if (!IsWindowVisible(Hw))
382 #else
383 if (!IsWindowVisible(Hw))
384 #endif
385 return '#';
386 else if (IsIconic(Hw))
387 return '-';
388 else if (IsZoomed(Hw))
389 return '@';
390 else
391 return '+';
392 }
393
394 void WINAPI SetWinMenu(HMENU menu, PCHAR buf, int buflen, PCHAR langFile, int VTFlag)
395 {
396 int i;
397 char Temp[MAXPATHLEN];
398 HWND Hw;
399 wchar_t uimsg[MAX_UIMSG];
400
401 // delete all items in Window menu
402 i = GetMenuItemCount(menu);
403 if (i>0)
404 do {
405 i--;
406 RemoveMenu(menu,i,MF_BYPOSITION);
407 } while (i>0);
408
409 i = 0;
410 while (i<pm->NWin) {
411 Hw = pm->WinList[i]; // get window handle
412 if ((GetClassName(Hw,Temp,sizeof(Temp))>0) &&
413 ((strcmp(Temp,VTCLASSNAME)==0) ||
414 (strcmp(Temp,TEKCLASSNAME)==0))) {
415 Temp[0] = '&';
416 Temp[1] = (char)(0x31 + i);
417 Temp[2] = ' ';
418 Temp[3] = GetWindowTypeChar(Hw, NULL);
419 Temp[4] = ' ';
420 GetWindowText(Hw,&Temp[5],sizeof(Temp)-6);
421 AppendMenu(menu,MF_ENABLED | MF_STRING,ID_WINDOW_1+i,Temp);
422 i++;
423 if (i>8) {
424 i = pm->NWin;
425 }
426 }
427 else {
428 UnregWin(Hw);
429 }
430 }
431 if (VTFlag == 1) {
432 static const DlgTextInfo MenuTextInfo[] = {
433 { ID_WINDOW_WINDOW, "MENU_WINDOW_WINDOW" },
434 { ID_WINDOW_MINIMIZEALL, "MENU_WINDOW_MINIMIZEALL" },
435 { ID_WINDOW_RESTOREALL, "MENU_WINDOW_RESTOREALL" },
436 { ID_WINDOW_CASCADEALL, "MENU_WINDOW_CASCADE" },
437 { ID_WINDOW_STACKED, "MENU_WINDOW_STACKED" },
438 { ID_WINDOW_SIDEBYSIDE, "MENU_WINDOW_SIDEBYSIDE" },
439 };
440
441 AppendMenu(menu, MF_SEPARATOR, 0, NULL);
442 AppendMenu(menu, MF_ENABLED | MF_STRING, ID_WINDOW_WINDOW, "&Window");
443 AppendMenu(menu, MF_ENABLED | MF_STRING, ID_WINDOW_MINIMIZEALL, "&Minimize All");
444 AppendMenu(menu, MF_ENABLED | MF_STRING, ID_WINDOW_RESTOREALL, "&Restore All");
445 AppendMenu(menu, MF_ENABLED | MF_STRING, ID_WINDOW_CASCADEALL, "&Cascade");
446 AppendMenu(menu, MF_ENABLED | MF_STRING, ID_WINDOW_STACKED, "&Stacked");
447 AppendMenu(menu, MF_ENABLED | MF_STRING, ID_WINDOW_SIDEBYSIDE, "Side &by Side");
448
449 SetI18nMenuStrs("Tera Term", menu, MenuTextInfo, _countof(MenuTextInfo), langFile);
450
451 if (pm->WinUndoFlag) {
452 if (pm->WinUndoStyle == WIN_CASCADE)
453 get_lang_msgW("MENU_WINDOW_CASCADE_UNDO", uimsg, _countof(uimsg), L"&Undo - Cascade", langFile);
454 else if (pm->WinUndoStyle == WIN_STACKED)
455 get_lang_msgW("MENU_WINDOW_STACKED_UNDO", uimsg, _countof(uimsg), L"&Undo - Stacked", langFile);
456 else
457 get_lang_msgW("MENU_WINDOW_SIDEBYSIDE_UNDO", uimsg, _countof(uimsg), L"&Undo - Side by Side", langFile);
458 AppendMenuW(menu, MF_ENABLED | MF_STRING, ID_WINDOW_UNDO, uimsg); // TODO UNICODE
459 }
460
461 }
462 else {
463 get_lang_msgW("MENU_WINDOW_WINDOW", uimsg, _countof(uimsg), L"&Window", langFile);
464 AppendMenuW(menu,MF_ENABLED | MF_STRING,ID_TEKWINDOW_WINDOW, uimsg);
465 }
466 }
467
468 void WINAPI SetWinList(HWND HWin, HWND HDlg, int IList)
469 {
470 int i;
471 char Temp[MAXPATHLEN];
472 HWND Hw;
473
474 for (i=0; i<pm->NWin; i++) {
475 Hw = pm->WinList[i]; // get window handle
476 if ((GetClassName(Hw,Temp,sizeof(Temp))>0) &&
477 ((strcmp(Temp,VTCLASSNAME)==0) ||
478 (strcmp(Temp,TEKCLASSNAME)==0))) {
479 Temp[0] = GetWindowTypeChar(Hw, HWin);
480 Temp[1] = ' ';
481 GetWindowText(Hw,&Temp[2],sizeof(Temp)-3);
482 SendDlgItemMessage(HDlg, IList, LB_ADDSTRING,
483 0, (LPARAM)Temp);
484 if (Hw==HWin) {
485 SendDlgItemMessage(HDlg, IList, LB_SETCURSEL, i,0);
486 }
487 }
488 else {
489 UnregWin(Hw);
490 }
491 }
492 }
493
494 void WINAPI SelectWin(int WinId)
495 {
496 if ((WinId>=0) && (WinId<pm->NWin)) {
497 /* �E�B���h�E�����������������������������������A���������������������������A
498 * SW_SHOWNORMAL ���� SW_SHOW �����X�����B
499 * (2009.11.8 yutaka)
500 * �E�B���h�E�����������������������������T�C�Y������(SW_RESTORE)�����������B
501 * (2009.11.9 maya)
502 */
503 if (IsIconic(pm->WinList[WinId])) {
504 ShowWindow(pm->WinList[WinId],SW_RESTORE);
505 }
506 else {
507 ShowWindow(pm->WinList[WinId],SW_SHOW);
508 }
509 SetForegroundWindow(pm->WinList[WinId]);
510 }
511 }
512
513 void WINAPI SelectNextWin(HWND HWin, int Next, BOOL SkipIconic)
514 {
515 int i;
516
517 i = 0;
518 while ((i < pm->NWin) && (pm->WinList[i]!=HWin)) {
519 i++;
520 }
521 if (pm->WinList[i]!=HWin) {
522 return;
523 }
524
525 do {
526 i += Next;
527 if (i >= pm->NWin) {
528 i = 0;
529 }
530 else if (i < 0) {
531 i = pm->NWin-1;
532 }
533
534 if (pm->WinList[i] == HWin) {
535 break;
536 }
537 } while ((SkipIconic && IsIconic(pm->WinList[i])) || !IsWindowVisible(pm->WinList[i]));
538
539 SelectWin(i);
540 }
541
542 void WINAPI ShowAllWin(int stat) {
543 int i;
544
545 for (i=0; i < pm->NWin; i++) {
546 ShowWindow(pm->WinList[i], stat);
547 }
548 }
549
550 void WINAPI UndoAllWin(void) {
551 int i;
552 WINDOWPLACEMENT rc0;
553 RECT rc;
554 int stat = SW_RESTORE;
555 int multi_mon = 0;
556
557 if (HasMultiMonitorSupport()) {
558 multi_mon = 1;
559 }
560
561 // ���x�A�����������t���O���������B
562 pm->WinUndoFlag = FALSE;
563
564 memset(&rc0, 0, sizeof(rc0));
565
566 for (i=0; i < pm->NWin; i++) {
567 // �����w�����A�O�����������c���������������A�E�B���h�E�����������������B
568 if (stat == SW_RESTORE && memcmp(&pm->WinPrevRect[i], &rc0, sizeof(rc0)) != 0) {
569 rc = pm->WinPrevRect[i].rcNormalPosition;
570
571 // NT4.0, 95 ���}���`���j�^API��������
572 if (multi_mon) {
573 // �������j�^������������
574 HMONITOR hMonitor;
575 MONITORINFO mi;
576 hMonitor = pMonitorFromRect(&rc, MONITOR_DEFAULTTONEAREST);
577 mi.cbSize = sizeof(MONITORINFO);
578 pGetMonitorInfoA(hMonitor, &mi);
579
580 // ���u�����i�����O���������x���������������������������j
581 if (rc.right > mi.rcMonitor.right) {
582 rc.left -= rc.right - mi.rcMonitor.right;
583 rc.right = mi.rcMonitor.right;
584 }
585 if (rc.left < mi.rcMonitor.left) {
586 rc.right += mi.rcMonitor.left - rc.left;
587 rc.left = mi.rcMonitor.left;
588 }
589 if (rc.bottom > mi.rcMonitor.bottom) {
590 rc.top -= rc.bottom - mi.rcMonitor.bottom;
591 rc.bottom = mi.rcMonitor.bottom;
592 }
593 if (rc.top < mi.rcMonitor.top) {
594 rc.bottom += mi.rcMonitor.top - rc.top;
595 rc.top = mi.rcMonitor.top;
596 }
597 }
598
599 // �E�B���h�E���u����
600 SetWindowPos(
601 pm->WinList[i], NULL,
602 rc.left,
603 rc.top,
604 rc.right - rc.left,
605 rc.bottom - rc.top,
606 SWP_NOZORDER);
607
608 // �E�B���h�E����������
609 ShowWindow(pm->WinList[i], pm->WinPrevRect[i].showCmd);
610
611 } else {
612 ShowWindow(pm->WinList[i], stat);
613 }
614 }
615 }
616
617 HWND WINAPI GetNthWin(int n)
618 {
619 if (n<pm->NWin) {
620 return pm->WinList[n];
621 }
622 else {
623 return NULL;
624 }
625 }
626
627 int WINAPI GetRegisteredWindowCount(void)
628 {
629 return (pm->NWin);
630 }
631
632 // �L�����E�B���h�E���T���A�������u���L�������������B
633 static void get_valid_window_and_memorize_rect(HWND myhwnd, HWND hwnd[], int *num, int style)
634 {
635 int i, n;
636 WINDOWPLACEMENT wndPlace;
637
638 // ��������(Undo)���j���[�����x�����\���������B
639 if (pm->WinUndoFlag == FALSE) {
640 pm->WinUndoFlag = TRUE;
641 } else {
642 // ���������j���[���\�������������A�������O�������X�^�C�����I�����������A
643 // ���j���[�������B
644 // Windows8�����A�������A�����������X�^�C�����I�����������j���[�����������������A
645 // Tera Term�������j���[���\�������������A�������������B
646 if (pm->WinUndoStyle == style)
647 pm->WinUndoFlag = FALSE;
648 }
649 pm->WinUndoStyle = style;
650
651 n = 0;
652 for (i = 0 ; i < pm->NWin ; i++) {
653 // �������u���o���������B
654 wndPlace.length = sizeof(WINDOWPLACEMENT);
655 GetWindowPlacement(pm->WinList[i], &wndPlace);
656 pm->WinPrevRect[i] = wndPlace;
657
658 // �������g�������������B
659 if (pm->WinList[i] == myhwnd) {
660 hwnd[n] = hwnd[0];
661 hwnd[0] = myhwnd;
662 } else {
663 hwnd[n] = pm->WinList[i];
664 }
665 n++;
666 }
667 *num = n;
668 }
669
670 // �E�B���h�E�����E���������\������(Show Windows Side by Side)
671 void WINAPI ShowAllWinSidebySide(HWND myhwnd)
672 {
673 int n;
674 HWND hwnd[MAXNWIN];
675
676 get_valid_window_and_memorize_rect(myhwnd, hwnd, &n, WIN_SIDEBYSIDE);
677 TileWindows(NULL, MDITILE_VERTICAL, NULL, n, hwnd);
678 }
679
680 // �E�B���h�E���������������\������(Show Windows Stacked)
681 void WINAPI ShowAllWinStacked(HWND myhwnd)
682 {
683 int n;
684 HWND hwnd[MAXNWIN];
685
686 get_valid_window_and_memorize_rect(myhwnd, hwnd, &n, WIN_STACKED);
687 TileWindows(NULL, MDITILE_HORIZONTAL, NULL, n, hwnd);
688 }
689
690 // �E�B���h�E���d�����\������(Cascade)
691 void WINAPI ShowAllWinCascade(HWND myhwnd)
692 {
693 int n;
694 HWND hwnd[MAXNWIN];
695
696 get_valid_window_and_memorize_rect(myhwnd, hwnd, &n, WIN_CASCADE);
697 CascadeWindows(NULL, MDITILE_SKIPDISABLED, NULL, n, hwnd);
698 }
699
700 // �STera Term���I���w�����o���B
701 void WINAPI BroadcastClosingMessage(HWND myhwnd)
702 {
703 int i, max;
704 HWND hwnd[MAXNWIN];
705
706 // Tera Term���I�����������A���L���������������������A
707 // ���������o�b�t�@���R�s�[���������B
708 max = pm->NWin;
709 for (i = 0 ; i < pm->NWin ; i++) {
710 hwnd[i] = pm->WinList[i];
711 }
712
713 for (i = 0 ; i < max ; i++) {
714 // �������g�������������B
715 if (hwnd[i] == myhwnd)
716 continue;
717
718 PostMessage(hwnd[i], WM_USER_NONCONFIRM_CLOSE, 0, 0);
719 }
720 PostMessage(myhwnd, WM_USER_NONCONFIRM_CLOSE, 0, 0);
721 }
722
723
724 int WINAPI CommReadRawByte(PComVar cv, LPBYTE b)
725 {
726 if ( ! cv->Ready ) {
727 return 0;
728 }
729
730 if ( cv->InBuffCount>0 ) {
731 *b = cv->InBuff[cv->InPtr];
732 cv->InPtr++;
733 cv->InBuffCount--;
734 if ( cv->InBuffCount==0 ) {
735 cv->InPtr = 0;
736 }
737 return 1;
738 }
739 else {
740 cv->InPtr = 0;
741 return 0;
742 }
743 }
744
745 static void LogBinSkip(PComVar cv, int add)
746 {
747 if (cv->LogBinSkip != NULL) {
748 cv->LogBinSkip(add);
749 }
750 }
751
752 void WINAPI CommInsert1Byte(PComVar cv, BYTE b)
753 {
754 if ( ! cv->Ready ) {
755 return;
756 }
757
758 if (cv->InPtr == 0) {
759 memmove(&(cv->InBuff[1]),&(cv->InBuff[0]),cv->InBuffCount);
760 }
761 else {
762 cv->InPtr--;
763 }
764 cv->InBuff[cv->InPtr] = b;
765 cv->InBuffCount++;
766
767 LogBinSkip(cv, 1);
768 }
769
770 static void Log1Bin(PComVar cv, BYTE b)
771 {
772 if (cv->Log1Bin != NULL) {
773 cv->Log1Bin(b);
774 }
775 }
776
777 int WINAPI CommRead1Byte(PComVar cv, LPBYTE b)
778 {
779 int c;
780
781 if ( ! cv->Ready ) {
782 return 0;
783 }
784
785 if ( cv->TelMode ) {
786 c = 0;
787 }
788 else {
789 c = CommReadRawByte(cv,b);
790 }
791
792 if ((c==1) && cv->TelCRFlag) {
793 cv->TelCRFlag = FALSE;
794 if (*b==0) {
795 c = 0;
796 }
797 }
798
799 if ( c==1 ) {
800 if ( cv->IACFlag ) {
801 cv->IACFlag = FALSE;
802 if ( *b != 0xFF ) {
803 cv->TelMode = TRUE;
804 CommInsert1Byte(cv,*b);
805 LogBinSkip(cv, -1);
806 c = 0;
807 }
808 }
809 else if ((cv->PortType==IdTCPIP) && (*b==0xFF)) {
810 if (!cv->TelFlag && cv->TelAutoDetect) { /* TTPLUG */
811 cv->TelFlag = TRUE;
812 }
813 if (cv->TelFlag) {
814 cv->IACFlag = TRUE;
815 c = 0;
816 }
817 }
818 else if (cv->TelFlag && ! cv->TelBinRecv && (*b==0x0D)) {
819 cv->TelCRFlag = TRUE;
820 }
821 }
822
823 if (c == 1) {
824 Log1Bin(cv, *b);
825 }
826
827 return c;
828 }
829
830 int WINAPI CommRawOut(PComVar cv, /*const*/ PCHAR B, int C)
831 {
832 int a;
833
834 if ( ! cv->Ready ) {
835 return C;
836 }
837
838 if (C > OutBuffSize - cv->OutBuffCount) {
839 a = OutBuffSize - cv->OutBuffCount;
840 }
841 else {
842 a = C;
843 }
844 if ( cv->OutPtr > 0 ) {
845 memmove(&(cv->OutBuff[0]),&(cv->OutBuff[cv->OutPtr]),cv->OutBuffCount);
846 cv->OutPtr = 0;
847 }
848 memcpy(&(cv->OutBuff[cv->OutBuffCount]),B,a);
849 cv->OutBuffCount = cv->OutBuffCount + a;
850 return a;
851 }
852
853 int WINAPI CommBinaryOut(PComVar cv, PCHAR B, int C)
854 {
855 int a, i, Len;
856 char d[3];
857
858 if ( ! cv->Ready ) {
859 return C;
860 }
861
862 i = 0;
863 a = 1;
864 while ((a>0) && (i<C)) {
865 Len = 0;
866
867 d[Len] = B[i];
868 Len++;
869
870 if ( cv->TelFlag && (B[i]=='\x0d') && ! cv->TelBinSend ) {
871 d[Len++] = '\x00';
872 }
873 else if ( cv->TelFlag && (B[i]=='\xff') ) {
874 d[Len++] = '\xff';
875 }
876
877 if ( OutBuffSize - cv->OutBuffCount - Len >= 0 ) {
878 CommRawOut(cv, d, Len);
879 a = 1;
880 }
881 else {
882 a = 0;
883 }
884
885 i += a;
886 }
887 return i;
888 }
889
890 /**
891 * �f�[�^(������)���o���o�b�t�@����������
892 *
893 * �w���f�[�^��������������������������������������
894 * CommRawOut() ��������������������������
895 *
896 * @retval TRUE �o��������
897 * @retval FALSE �o��������������(buffer full)
898 */
899 static BOOL WriteOutBuff(PComVar cv, const char *TempStr, int TempLen)
900 {
901 BOOL output;
902
903 if (TempLen == 0) {
904 // ����0������������������������
905 return TRUE;
906 }
907
908 output = FALSE;
909 if (cv->TelLineMode) {
910 const BOOL Full = OutBuffSize - cv->LineModeBuffCount - TempLen < 0;
911 if (!Full) {
912 output = TRUE;
913 memcpy(&(cv->LineModeBuff[cv->LineModeBuffCount]), TempStr, TempLen);
914 cv->LineModeBuffCount += TempLen;
915 if (cv->Flush) {
916 cv->FlushLen = cv->LineModeBuffCount;
917 }
918 }
919 if (cv->FlushLen > 0) {
920 const int OutLen = CommRawOut(cv, cv->LineModeBuff, cv->FlushLen);
921 cv->FlushLen -= OutLen;
922 cv->LineModeBuffCount -= OutLen;
923 memmove(cv->LineModeBuff, &(cv->LineModeBuff[OutLen]), cv->LineModeBuffCount);
924 }
925 cv->Flush = FALSE;
926 }
927 else {
928 const BOOL Full = OutBuffSize-cv->OutBuffCount-TempLen < 0;
929 if (! Full) {
930 output = TRUE;
931 CommRawOut(cv, (char *)TempStr, TempLen);
932 }
933 }
934 return output;
935 }
936
937 /**
938 * �f�[�^(������)�������o�b�t�@����������
939 * �����o�b�t�@�������� -> �G�R�[������
940 *
941 * @retval TRUE �o��������
942 * @retval FALSE �o��������������(buffer full)
943 */
944 static BOOL WriteInBuff(PComVar cv, const char *TempStr, int TempLen)
945 {
946 BOOL Full;
947
948 if (TempLen == 0) {
949 return TRUE;
950 }
951
952 Full = InBuffSize-cv->InBuffCount-TempLen < 0;
953 if (! Full) {
954 memcpy(&(cv->InBuff[cv->InBuffCount]),TempStr,TempLen);
955 cv->InBuffCount = cv->InBuffCount + TempLen;
956 return TRUE;
957 }
958 return FALSE;
959 }
960
961 /**
962 * �����o�b�t�@�����������������������l����
963 */
964 static void PackInBuff(PComVar cv)
965 {
966 if ( (cv->InPtr>0) && (cv->InBuffCount>0) ) {
967 memmove(cv->InBuff,&(cv->InBuff[cv->InPtr]),cv->InBuffCount);
968 cv->InPtr = 0;
969 }
970 }
971
972 int WINAPI CommBinaryBuffOut(PComVar cv, PCHAR B, int C)
973 {
974 int a, i, Len;
975 char d[3];
976
977 if ( ! cv->Ready ) {
978 return C;
979 }
980
981 i = 0;
982 a = 1;
983 while ((a>0) && (i<C)) {
984 Len = 0;
985
986 d[Len] = B[i];
987 Len++;
988
989 if (B[i] == CR) {
990 if ( cv->TelFlag && ! cv->TelBinSend ) {
991 d[Len++] = '\x00';
992 }
993 if (cv->TelLineMode) {
994 cv->Flush = TRUE;
995 }
996 }
997 else if ( cv->TelFlag && (B[i]=='\xff') ) {
998 d[Len++] = '\xff';
999 }
1000
1001 if (WriteOutBuff(cv, d, Len)) {
1002 a = 1;
1003 i++;
1004 } else {
1005 a = 0;
1006 }
1007 }
1008 return i;
1009 }
1010
1011 /**
1012 * @retval true ���{�������p�J�^�J�i
1013 * @retval false ������
1014 */
1015 static BOOL IsHalfWidthKatakana(unsigned int u32)
1016 {
1017 // Halfwidth CJK punctuation (U+FF61�`FF64)
1018 // Halfwidth Katakana variants (U+FF65�`FF9F)
1019 return (0xff61 <= u32 && u32 <= 0xff9f);
1020 }
1021
1022 /**
1023 * �o���p�A TODO echo�p������
1024 * @param cv
1025 * @param u32 ��������
1026 * @param check_only TRUE���������s�����A
1027 * @param TempStr �o��������
1028 * @param StrLen TempStr�����o��������
1029 * @retval �������s����
1030 */
1031 static BOOL OutControl(PComVar cv, unsigned int u32, BOOL check_only, char *TempStr, size_t *StrLen)
1032 {
1033 const wchar_t d = u32;
1034 size_t TempLen = 0;
1035 BOOL retval = FALSE;
1036 if (check_only == TRUE) {
1037 /* �`�F�b�N���� */
1038 if (d == CR || d == BS || d == 0x15/*ctrl-u*/) {
1039 return TRUE;
1040 } else {
1041 return FALSE;
1042 }
1043 }
1044 if (d==CR) {
1045 TempStr[TempLen++] = 0x0d;
1046 if (cv->CRSend==IdCRLF) {
1047 TempStr[TempLen++] = 0x0a;
1048 }
1049 else if ((cv->CRSend ==IdCR) &&
1050 cv->TelFlag && ! cv->TelBinSend) {
1051 TempStr[TempLen++] = 0;
1052 }
1053 else if (cv->CRSend == IdLF) {
1054 TempStr[TempLen-1] = 0x0a;
1055 }
1056 if (cv->TelLineMode) {
1057 cv->Flush = TRUE;
1058 }
1059 retval = TRUE;
1060 }
1061 else if (d== BS) {
1062 if (cv->TelLineMode) {
1063 if (cv->FlushLen < cv->LineModeBuffCount) {
1064 cv->LineModeBuffCount--;
1065 }
1066 }
1067 else {
1068 TempStr[TempLen++] = BS;
1069 }
1070 retval = TRUE;
1071 }
1072 else if (d==0x15) { // ctrl-u
1073 if (cv->TelLineMode) {
1074 cv->LineModeBuffCount = cv->FlushLen;
1075 }
1076 else {
1077 TempStr[TempLen++] = 0x15;
1078 }
1079 retval = TRUE;
1080 }
1081 *StrLen = TempLen;
1082 return retval;
1083 }
1084 static BOOL ControlEcho(PComVar cv, unsigned int u32, BOOL check_only, char *TempStr, size_t *StrLen)
1085 {
1086 const wchar_t d = u32;
1087 size_t TempLen = 0;
1088 BOOL retval = FALSE;
1089 if (check_only == TRUE) {
1090 /* �`�F�b�N���� */
1091 if (d == CR || (d == 0x15/*ctrl-u*/ && cv->TelLineMode)) {
1092 return TRUE;
1093 } else {
1094 return FALSE;
1095 }
1096 }
1097 if (d==CR) {
1098 TempStr[TempLen++] = 0x0d;
1099 if (cv->CRSend==IdCRLF) {
1100 TempStr[TempLen++] = 0x0a;
1101 }
1102 else if ((cv->CRSend ==IdCR) && cv->TelFlag && ! cv->TelBinSend) {
1103 TempStr[TempLen++] = 0;
1104 }
1105 else if (cv->CRSend == IdLF) {
1106 TempStr[TempLen-1] = 0x0a;
1107 }
1108 retval = TRUE;
1109 }
1110 else if (d==0x15/*ctrl-u*/ && cv->TelLineMode) {
1111 // Move to top of line (CHA "\033[G") and erase line (EL "\033[K")
1112 memcpy(TempStr, "\033[G\033[K", 6);
1113 TempLen += 6;
1114 retval = TRUE;
1115 }
1116 *StrLen = TempLen;
1117 return retval;
1118 }
1119
1120 /**
1121 * �o���p����������������
1122 *
1123 * @retval ��������������
1124 */
1125 typedef struct {
1126 int KanjiCode; // [in]�o�������R�[�h(sjis,jis����)
1127 BOOL (*ControlOut)(PComVar cv, unsigned int u32, BOOL check_only, char *TempStr, size_t *StrLen);
1128 // state�����������K�v�����������R�[�h���g�p
1129 BOOL JIS7Katakana; // [in](Kanji JIS)kana
1130 int SendCode; // [in,out](Kanji JIS)���O�����M�R�[�h Ascii/Kana/Kanji
1131 BOOL KanjiFlag; // [in,out](MBCS)���O��1byte��������������?(2byte������������?)
1132 BYTE KanjiFirst; // [in,out](MBCS)���O��1byte
1133 } OutputCharState;
1134
1135 /**
1136 * unicode(UTF-16)����unicode(UTF-32)��1���������o����
1137 * �o���f�[�^(TempStr)����������
1138 */
1139 static size_t MakeOutputString(PComVar cv, OutputCharState *states,
1140 const wchar_t *B, int C,
1141 char *TempStr, int *TempLen_)
1142 {
1143 BOOL (*ControlOut)(PComVar cv, unsigned int u32, BOOL check_only, char *TempStr, size_t *StrLen)
1144 = states->ControlOut;
1145 //
1146 int TempLen = 0;
1147 size_t TempLen2;
1148 size_t output_char_count; // ��������������
1149
1150 // UTF-32 ��1���������o��
1151 unsigned int u32;
1152 size_t u16_len = UTF16ToUTF32(B, C, &u32);
1153 if (u16_len == 0) {
1154 // �f�R�[�h��������? ����������������?
1155 assert(FALSE);
1156 u32 = '?';
1157 u16_len = 1;
1158 }
1159 output_char_count = u16_len;
1160
1161 // �e���V�t�g����������������
1162 if (u32 < 0x100 || ControlOut(cv, u32, TRUE, NULL, NULL)) {
1163 if (cv->Language == IdJapanese && states->KanjiCode == IdJIS) {
1164 // �����������A���{��,JIS��������
1165 if (cv->SendCode == IdKanji) {
1166 // �����������������A����OUT
1167 TempStr[TempLen++] = 0x1B;
1168 TempStr[TempLen++] = '(';
1169 switch (cv->KanjiOut) {
1170 case IdKanjiOutJ:
1171 TempStr[TempLen++] = 'J';
1172 break;
1173 case IdKanjiOutH:
1174 TempStr[TempLen++] = 'H';
1175 break;
1176 default:
1177 TempStr[TempLen++] = 'B';
1178 }
1179 }
1180
1181 if (states->JIS7Katakana == 1) {
1182 if (cv->SendCode == IdKatakana) {
1183 TempStr[TempLen++] = SO;
1184 }
1185 }
1186
1187 states->SendCode = IdASCII;
1188 }
1189 }
1190
1191 // 1������������
1192 if (ControlOut(cv, u32, FALSE, TempStr, &TempLen2)) {
1193 // ��������������������
1194 TempLen += TempLen2;
1195 output_char_count = 1;
1196 } else if (cv->Language == IdUtf8 ||
1197 (cv->Language == IdJapanese && states->KanjiCode == IdUTF8) ||
1198 (cv->Language == IdKorean && states->KanjiCode == IdUTF8) ||
1199 (cv->Language == IdChinese && states->KanjiCode == IdUTF8))
1200 {
1201 // UTF-8 ���o��
1202 size_t utf8_len = sizeof(TempStr);
1203 utf8_len = UTF32ToUTF8(u32, TempStr, utf8_len);
1204 TempLen += utf8_len;
1205 } else if (cv->Language == IdJapanese) {
1206 // ���{��
1207 // ���� CP932(SJIS) ���������������o��
1208 char mb_char[2];
1209 size_t mb_len = sizeof(mb_char);
1210 mb_len = UTF32ToMBCP(u32, 932, mb_char, mb_len);
1211 if (mb_len == 0) {
1212 // SJIS��������������
1213 TempStr[TempLen++] = '?';
1214 } else {
1215 switch (states->KanjiCode) {
1216 case IdEUC:
1217 // TODO ���p�J�i
1218 if (mb_len == 1) {
1219 TempStr[TempLen++] = mb_char[0];
1220 } else {
1221 WORD K;
1222 K = (((WORD)(unsigned char)mb_char[0]) << 8) +
1223 (WORD)(unsigned char)mb_char[1];
1224 K = SJIS2EUC(K);
1225 TempStr[TempLen++] = HIBYTE(K);
1226 TempStr[TempLen++] = LOBYTE(K);
1227 }
1228 break;
1229 case IdJIS:
1230 if (u32 < 0x100) {
1231 // ASCII
1232 TempStr[TempLen++] = mb_char[0];
1233 states->SendCode = IdASCII;
1234 } else if (IsHalfWidthKatakana(u32)) {
1235 // ���p�J�^�J�i
1236 if (states->JIS7Katakana==1) {
1237 if (cv->SendCode != IdKatakana) {
1238 TempStr[TempLen++] = SI;
1239 }
1240 TempStr[TempLen++] = mb_char[0] & 0x7f;
1241 } else {
1242 TempStr[TempLen++] = mb_char[0];
1243 }
1244 states->SendCode = IdKatakana;
1245 } else {
1246 // ����
1247 WORD K;
1248 K = (((WORD)(unsigned char)mb_char[0]) << 8) +
1249 (WORD)(unsigned char)mb_char[1];
1250 K = SJIS2JIS(K);
1251 if (states->SendCode != IdKanji) {
1252 // ����IN
1253 TempStr[TempLen++] = 0x1B;
1254 TempStr[TempLen++] = '$';
1255 if (cv->KanjiIn == IdKanjiInB) {
1256 TempStr[TempLen++] = 'B';
1257 }
1258 else {
1259 TempStr[TempLen++] = '@';
1260 }
1261 states->SendCode = IdKanji;
1262 }
1263 TempStr[TempLen++] = HIBYTE(K);
1264 TempStr[TempLen++] = LOBYTE(K);
1265 }
1266 break;
1267 case IdSJIS:
1268 if (mb_len == 1) {
1269 TempStr[TempLen++] = mb_char[0];
1270 } else {
1271 TempStr[TempLen++] = mb_char[0];
1272 TempStr[TempLen++] = mb_char[1];
1273 }
1274 break;
1275 default:
1276 assert(FALSE);
1277 break;
1278 }
1279 }
1280 } else if (cv->Language == IdRussian) {
1281 /* ����CP1251�����������o�� */
1282 char mb_char[2];
1283 size_t mb_len = sizeof(mb_char);
1284 BYTE b;
1285 mb_len = UTF32ToMBCP(u32, 1251, mb_char, mb_len);
1286 if (mb_len != 1) {
1287 b = '?';
1288 } else {
1289 b = RussConv(IdWindows, states->KanjiCode, mb_char[0]);
1290 }
1291 TempStr[TempLen++] = b;
1292 } else if (cv->Language == IdKorean || cv->Language == IdChinese) {
1293 int code_page;
1294 char mb_char[2];
1295 size_t mb_len;
1296 if (cv->Language == IdKorean) {
1297 code_page = 51949;
1298 } else if (cv->Language == IdChinese) {
1299 switch (states->KanjiCode) {
1300 case IdCnGB2312:
1301 code_page = 936;
1302 break;
1303 case IdCnBig5:
1304 code_page = 950;
1305 break;
1306 default:
1307 assert(FALSE);
1308 code_page = 936;
1309 break;
1310 }
1311 }
1312 /* code_page �����������o�� */
1313 mb_len = sizeof(mb_char);
1314 mb_len = UTF32ToMBCP(u32, code_page, mb_char, mb_len);
1315 if (mb_len == 0) {
1316 TempStr[TempLen++] = '?';
1317 }
1318 else if (mb_len == 1) {
1319 TempStr[TempLen++] = mb_char[0];
1320 } else {
1321 TempStr[TempLen++] = mb_char[0];
1322 TempStr[TempLen++] = mb_char[1];
1323 }
1324 } else if (cv->Language == IdEnglish) {
1325 char byte;
1326 int part = KanjiCodeToISO8859Part(states->KanjiCode);
1327 int r = UnicodeToISO8859(part, u32, &byte);
1328 if (r == 0) {
1329 // �����������������R�[�h������
1330 byte = '?';
1331 }
1332 TempStr[TempLen++] = byte;
1333 } else {
1334 assert(FALSE);
1335 }
1336
1337 *TempLen_ = TempLen;
1338 return output_char_count;
1339 }
1340
1341
1342 /**
1343 * CommTextOut() �� wchar_t ��
1344 *
1345 * @retval �o��������(wchar_t�P��)
1346 */
1347 int WINAPI CommTextOutW(PComVar cv, const wchar_t *B, int C)
1348 {
1349 char TempStr[12];
1350 BOOL Full = FALSE;
1351 int i = 0;
1352 while (! Full && (i < C)) {
1353 // �o���p�f�[�^������
1354 int TempLen = 0;
1355 size_t output_char_count; // ��������������
1356 OutputCharState state;
1357 state.KanjiCode = cv->KanjiCodeSend;
1358 state.ControlOut = OutControl;
1359 state.SendCode = cv->SendCode;
1360 state.JIS7Katakana = cv->JIS7KatakanaSend;
1361 output_char_count = MakeOutputString(cv, &state, &B[i], C-i, TempStr, &TempLen);
1362
1363 // �f�[�^���o���o�b�t�@��
1364 if (WriteOutBuff(cv, TempStr, TempLen)) {
1365 i += output_char_count; // output_char_count ������ ��������
1366 // ��������������������
1367 cv->SendCode = state.SendCode;
1368 } else {
1369 Full = TRUE;
1370 }
1371 } // end of "while {}"
1372 _CrtCheckMemory();
1373 return i;
1374 }
1375
1376 /**
1377 * CommTextEcho() �� wchar_t ��
1378 *
1379 * @retval �o��������(wchar_t�P��)
1380 */
1381 int WINAPI CommTextEchoW(PComVar cv, const wchar_t *B, int C)
1382 {
1383 char TempStr[12];
1384 BOOL Full = FALSE;
1385 int i = 0;
1386 while (! Full && (i < C)) {
1387 // �o���p�f�[�^������
1388 int TempLen = 0;
1389 size_t output_char_count; // ��������������
1390 OutputCharState state;
1391 state.KanjiCode = cv->KanjiCodeEcho;
1392 state.ControlOut = ControlEcho;
1393 state.SendCode = cv->EchoCode;
1394 state.JIS7Katakana = cv->JIS7KatakanaEcho;
1395 output_char_count = MakeOutputString(cv, &state, &B[i], C-i, TempStr, &TempLen);
1396
1397 // �f�[�^���o���o�b�t�@��
1398 if (WriteInBuff(cv, TempStr, TempLen)) {
1399 i += output_char_count; // output_char_count ������ ��������
1400 // ��������������������
1401 cv->EchoCode = state.SendCode;
1402 } else {
1403 Full = TRUE;
1404 }
1405 } // end of "while {}"
1406 _CrtCheckMemory();
1407 return i;
1408 }
1409
1410 int WINAPI CommBinaryEcho(PComVar cv, PCHAR B, int C)
1411 {
1412 int a, i, Len;
1413 char d[3];
1414
1415 if ( ! cv->Ready )
1416 return C;
1417
1418 PackInBuff(cv);
1419
1420 i = 0;
1421 a = 1;
1422 while ((a>0) && (i<C)) {
1423 Len = 0;
1424
1425 d[Len] = B[i];
1426 Len++;
1427
1428 if ( cv->TelFlag && (B[i]=='\x0d') &&
1429 ! cv->TelBinSend ) {
1430 d[Len] = 0x00;
1431 Len++;
1432 }
1433
1434 if ( cv->TelFlag && (B[i]=='\xff') ) {
1435 d[Len] = '\xff';
1436 Len++;
1437 }
1438
1439 if (WriteInBuff(cv, d, Len)) {
1440 a = 1;
1441 i++;
1442 } else {
1443 a = 0;
1444 }
1445 }
1446 return i;
1447 }
1448
1449 /*
1450 * @return �G���[���L������ FALSE
1451 * @param[in] BOOL first_instance
1452 */
1453 static BOOL OpenSharedMemory(BOOL *first_instance_)
1454 {
1455 int i;
1456 HMap = NULL;
1457 pm = NULL;
1458 for (i = 0; i < 100; i++) {
1459 char tmp[32];
1460 HANDLE hMap;
1461 BOOL first_instance;
1462 TMap *map;
1463 _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, i == 0 ? "%s" : "%s_%d", TT_FILEMAPNAME, i);
1464 hMap = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE,
1465 0, sizeof(TMap), tmp);
1466 if (hMap == NULL) {
1467 return FALSE;
1468 }
1469
1470 first_instance = (GetLastError() != ERROR_ALREADY_EXISTS);
1471
1472 map = (TMap *)MapViewOfFile(hMap,FILE_MAP_WRITE,0,0,0);
1473 if (map == NULL) {
1474 return FALSE;
1475 }
1476
1477 if (first_instance ||
1478 (map->size_tmap == sizeof(TMap) &&
1479 map->size_tttset == sizeof(TTTSet)))
1480 {
1481 map->size_tmap = sizeof(TMap);
1482 map->size_tttset = sizeof(TTTSet);
1483 HMap = hMap;
1484 pm = map;
1485 *first_instance_ = first_instance;
1486 return TRUE;
1487 }
1488
1489 // next try
1490 UnmapViewOfFile(map);
1491 CloseHandle(hMap);
1492 }
1493 return FALSE;
1494 }
1495
1496 BOOL WINAPI DllMain(HANDLE hInstance,
1497 ULONG ul_reason_for_call,
1498 LPVOID lpReserved)
1499 {
1500 switch( ul_reason_for_call ) {
1501 case DLL_THREAD_ATTACH:
1502 /* do thread initialization */
1503 break;
1504 case DLL_THREAD_DETACH:
1505 /* do thread cleanup */
1506 break;
1507 case DLL_PROCESS_ATTACH:
1508 /* do process initialization */
1509 #ifdef _DEBUG
1510 _CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF);
1511 #endif
1512 hInst = hInstance;
1513 if (OpenSharedMemory(&FirstInstance) == FALSE) {
1514 // dll���[�h���s�Ateraterm���N��������
1515 return FALSE;
1516 }
1517 WinCompatInit();
1518 break;
1519 case DLL_PROCESS_DETACH:
1520 /* do process cleanup */
1521 UnmapViewOfFile(pm);
1522 CloseHandle(HMap);
1523 break;
1524 }
1525 return TRUE;
1526 }

Back to OSDN">Back to OSDN
ViewVC Help
Powered by ViewVC 1.1.26