Develop and Download Open Source Software

Browse Subversion Repository

Annotation of /trunk/teraterm/teraterm/vtterm.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 7978 - (hide annotations) (download) (as text)
Sat Aug 17 04:54:13 2019 UTC (4 years, 7 months ago) by yutakapon
File MIME type: text/x-csrc
File size: 139651 byte(s)
英語版WindowsでTera Termの起動時にアプリケーションフォルトとなることがある問題を修正した。
英語版Windows95/NT4.0でsetlocaleがNULLを返すことで、NULLポインタアクセスで落ちる。
ただし、英語版Windows95でもstrrchrにNULLを渡しているにも関わらず、落ちない場合もある。

1 doda 6806 /*
2     * Copyright (C) 1994-1998 T. Teranishi
3 zmatsuo 7398 * (C) 2004-2019 TeraTerm Project
4 doda 6806 * All rights reserved.
5     *
6 doda 6841 * Redistribution and use in source and binary forms, with or without
7     * modification, are permitted provided that the following conditions
8     * are met:
9 doda 6806 *
10 doda 6841 * 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 doda 6806 *
18 doda 6841 * 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 doda 6806 */
29 maya 3227
30     /* TERATERM.EXE, VT terminal emulation */
31     #include "teraterm.h"
32     #include "tttypes.h"
33     #include <stdio.h>
34     #include <string.h>
35     #include <stdlib.h>
36     #include <mbstring.h>
37     #include <locale.h>
38 doda 4225 #include <ctype.h>
39 zmatsuo 7405 #include <crtdbg.h>
40     #include <tchar.h>
41 maya 3227
42     #include "buffer.h"
43     #include "ttwinman.h"
44     #include "ttcommon.h"
45     #include "commlib.h"
46     #include "vtdisp.h"
47     #include "keyboard.h"
48     #include "ttlib.h"
49     #include "ttftypes.h"
50     #include "filesys.h"
51     #include "teraprn.h"
52     #include "telnet.h"
53 doda 4278 #include "ttime.h"
54 doda 4769 #include "clipboar.h"
55 zmatsuo 7462 #include "codeconv.h"
56 maya 3227
57     #include "vtterm.h"
58    
59 zmatsuo 7405 #ifdef _DEBUG
60     #define malloc(l) _malloc_dbg((l), _NORMAL_BLOCK, __FILE__, __LINE__)
61     #define realloc(p, l) _realloc_dbg((p), (l), _NORMAL_BLOCK, __FILE__, __LINE__)
62     #define free(p) _free_dbg((p), _NORMAL_BLOCK)
63     #define strdup(s) _strdup_dbg((s), _NORMAL_BLOCK, __FILE__, __LINE__)
64     #define _strdup(s) _strdup_dbg((s), _NORMAL_BLOCK, __FILE__, __LINE__)
65     #endif
66    
67 doda 4256 void ParseFirst(BYTE b);
68    
69 doda 3443 #define MAPSIZE(x) (sizeof(x)/sizeof((x)[0]))
70 doda 4246 #define Accept8BitCtrl ((VTlevel >= 2) && (ts.TermFlag & TF_ACCEPT8BITCTRL))
71 doda 3443
72 maya 3227 /* Parsing modes */
73     #define ModeFirst 0
74     #define ModeESC 1
75     #define ModeDCS 2
76     #define ModeDCUserKey 3
77     #define ModeSOS 4
78     #define ModeCSI 5
79     #define ModeXS 6
80     #define ModeDLE 7
81     #define ModeCAN 8
82 doda 5911 #define ModeIgnore 9
83 maya 3227
84 doda 5073 #define NParamMax 16
85     #define NSParamMax 16
86     #define IntCharMax 5
87 maya 3227
88 doda 3997 /* DEC Locator Flag */
89     #define DecLocatorOneShot 1
90     #define DecLocatorPixel 2
91     #define DecLocatorButtonDown 4
92     #define DecLocatorButtonUp 8
93     #define DecLocatorFiltered 16
94    
95 doda 5316 void RingBell(int type);
96 maya 3227 void VisualBell();
97 doda 3999 BOOL DecLocatorReport(int Event, int Button);
98 maya 3227
99     /* character attribute */
100     static TCharAttr CharAttr;
101    
102     /* various modes of VT emulation */
103     static BOOL RelativeOrgMode;
104     static BOOL InsertMode;
105     static BOOL LFMode;
106 doda 5564 static BOOL ClearThenHome;
107 maya 3227 static BOOL AutoWrapMode;
108     static BOOL FocusReportMode;
109 doda 3743 static BOOL AltScr;
110 doda 5324 static BOOL LRMarginMode;
111 doda 7086 static BOOL RectangleMode;
112 doda 7140 static BOOL BracketedPaste;
113 maya 3227
114 doda 7140 char BracketStart[] = "\033[200~";
115     char BracketEnd[] = "\033[201~";
116     int BracketStartLen = (sizeof(BracketStart)-1);
117     int BracketEndLen = (sizeof(BracketEnd)-1);
118    
119 doda 4246 static int VTlevel;
120    
121 doda 4293 BOOL AcceptWheelToCursor;
122    
123 maya 3227 // save/restore cursor
124     typedef struct {
125 doda 6802 int CursorX, CursorY;
126     TCharAttr Attr;
127     int Glr[2], Gn[4]; // G0-G3, GL & GR
128     BOOL AutoWrapMode;
129     BOOL RelativeOrgMode;
130 maya 3227 } TStatusBuff;
131     typedef TStatusBuff *PStatusBuff;
132    
133 maya 4893 // currently only used for AUTO CR/LF receive mode
134     BYTE PrevCharacter;
135     BOOL PrevCRorLFGeneratedCRLF; // indicates that previous CR or LF really generated a CR+LF
136    
137 maya 3227 // status buffer for main screen & status line
138 doda 3797 static TStatusBuff SBuff1, SBuff2, SBuff3;
139 maya 3227
140     static BOOL ESCFlag, JustAfterESC;
141     static BOOL KanjiIn;
142     static BOOL EUCkanaIn, EUCsupIn;
143     static int EUCcount;
144     static BOOL Special;
145    
146     static int Param[NParamMax+1];
147 doda 5073 static int SubParam[NParamMax+1][NSParamMax+1];
148     static int NParam, NSParam[NParamMax+1];
149 maya 3227 static BOOL FirstPrm;
150     static BYTE IntChar[IntCharMax+1];
151     static int ICount;
152     static BYTE Prv;
153 doda 4291 static int ParseMode;
154 maya 3227 static int ChangeEmu;
155    
156 doda 5096 typedef struct tstack {
157 doda 6802 char *title;
158     struct tstack *next;
159 doda 5096 } TStack;
160     typedef TStack *PTStack;
161     PTStack TitleStack = NULL;
162    
163 maya 3227 /* user defined keys */
164     static BOOL WaitKeyId, WaitHi;
165    
166     /* GL, GR code group */
167     static int Glr[2];
168     /* G0, G1, G2, G3 code group */
169     static int Gn[4];
170     /* GL for single shift 2/3 */
171     static int GLtmp;
172     /* single shift 2/3 flag */
173     static BOOL SSflag;
174     /* JIS -> SJIS conversion flag */
175     static BOOL ConvJIS;
176     static WORD Kanji;
177 doda 6602 static BOOL Fallbacked;
178 maya 3227
179     // variables for status line mode
180     static int StatusX=0;
181     static BOOL StatusWrap=FALSE;
182     static BOOL StatusCursor=TRUE;
183     static int MainX, MainY; //cursor registers
184     static int MainTop, MainBottom; // scroll region registers
185     static BOOL MainWrap;
186     static BOOL MainCursor=TRUE;
187    
188     /* status for printer escape sequences */
189 doda 6802 static BOOL PrintEX = TRUE; // printing extent
190 maya 3227 // (TRUE: screen, FALSE: scroll region)
191     static BOOL AutoPrintMode = FALSE;
192     static BOOL PrinterMode = FALSE;
193     static BOOL DirectPrn = FALSE;
194    
195     /* User key */
196     static BYTE NewKeyStr[FuncKeyStrMax];
197     static int NewKeyId, NewKeyLen;
198    
199 doda 3997 /* Mouse Report */
200 zmatsuo 7434 static int MouseReportMode;
201     static int MouseReportExtMode;
202     static unsigned int DecLocatorFlag;
203     static int LastX, LastY;
204     static int ButtonStat;
205     static int FilterTop, FilterBottom, FilterLeft, FilterRight;
206 doda 3997
207 doda 5316 /* Beep over-used */
208     static DWORD BeepStartTime = 0;
209     static DWORD BeepSuppressTime = 0;
210     static DWORD BeepOverUsedCount = 0;
211    
212 doda 3450 static _locale_t CLocale = NULL;
213 maya 3227
214 doda 5073 void ClearParams()
215     {
216 doda 6802 ICount = 0;
217     NParam = 1;
218     NSParam[1] = 0;
219     Param[1] = 0;
220     Prv = 0;
221 doda 5073 }
222    
223 doda 3916 void ResetSBuffer(PStatusBuff sbuff)
224 maya 3227 {
225 doda 6802 sbuff->CursorX = 0;
226     sbuff->CursorY = 0;
227     sbuff->Attr = DefCharAttr;
228     if (ts.Language==IdJapanese) {
229     sbuff->Gn[0] = IdASCII;
230     sbuff->Gn[1] = IdKatakana;
231     sbuff->Gn[2] = IdKatakana;
232     sbuff->Gn[3] = IdKanji;
233     sbuff->Glr[0] = 0;
234     if ((ts.KanjiCode==IdJIS) && (ts.JIS7Katakana==0))
235     sbuff->Glr[1] = 2; // 8-bit katakana
236     else
237     sbuff->Glr[1] = 3;
238     }
239     else {
240     sbuff->Gn[0] = IdASCII;
241     sbuff->Gn[1] = IdSpecial;
242     sbuff->Gn[2] = IdASCII;
243     sbuff->Gn[3] = IdASCII;
244     sbuff->Glr[0] = 0;
245     sbuff->Glr[1] = 0;
246     }
247     sbuff->AutoWrapMode = TRUE;
248     sbuff->RelativeOrgMode = FALSE;
249 doda 3916 }
250    
251     void ResetAllSBuffers()
252     {
253 doda 6802 ResetSBuffer(&SBuff1);
254     // copy SBuff1 to SBuff2
255     SBuff2 = SBuff1;
256     SBuff3 = SBuff1;
257 maya 3227 }
258    
259 doda 3916 void ResetCurSBuffer()
260     {
261 doda 6802 PStatusBuff Buff;
262 doda 3916
263 doda 6802 if (AltScr) {
264     Buff = &SBuff3; // Alternate screen buffer
265     }
266     else {
267     Buff = &SBuff1; // Normal screen buffer
268     }
269     ResetSBuffer(Buff);
270     SBuff2 = *Buff;
271 doda 3916 }
272    
273 maya 3227 void ResetTerminal() /*reset variables but don't update screen */
274     {
275 doda 6802 DispReset();
276     BuffReset();
277 maya 3227
278 doda 6802 /* Attribute */
279     CharAttr = DefCharAttr;
280     Special = FALSE;
281     BuffSetCurCharAttr(CharAttr);
282 maya 3227
283 doda 6802 /* Various modes */
284     InsertMode = FALSE;
285     LFMode = (ts.CRSend == IdCRLF);
286     AutoWrapMode = TRUE;
287     AppliKeyMode = FALSE;
288     AppliCursorMode = FALSE;
289     AppliEscapeMode = FALSE;
290     AcceptWheelToCursor = ts.TranslateWheelToCursor;
291     RelativeOrgMode = FALSE;
292     ts.ColorFlag &= ~CF_REVERSEVIDEO;
293     AutoRepeatMode = TRUE;
294     FocusReportMode = FALSE;
295     MouseReportMode = IdMouseTrackNone;
296     MouseReportExtMode = IdMouseTrackExtNone;
297     DecLocatorFlag = 0;
298     ClearThenHome = FALSE;
299 doda 7086 RectangleMode = FALSE;
300 maya 3227
301 doda 6802 ChangeTerminalID();
302 doda 4246
303 doda 6802 LastX = 0;
304     LastY = 0;
305     ButtonStat = 0;
306 doda 3997
307 doda 6802 if (CLocale == NULL) {
308     CLocale = _create_locale(LC_ALL, "C");
309     }
310 maya 3227
311 doda 6802 /* Character sets */
312     ResetCharSet();
313 maya 3227
314 doda 6802 /* ESC flag for device control sequence */
315     ESCFlag = FALSE;
316     /* for TEK sequence */
317     JustAfterESC = FALSE;
318 maya 3227
319 doda 6802 /* Parse mode */
320     ParseMode = ModeFirst;
321 maya 3227
322 doda 6802 /* Clear printer mode */
323     PrinterMode = FALSE;
324 maya 3227
325 doda 6802 // status buffers
326     ResetAllSBuffers();
327 doda 3745
328 doda 6802 // Alternate Screen Buffer
329     AltScr = FALSE;
330 doda 3872
331 doda 6802 // Left/Right Margin Mode
332     LRMarginMode = FALSE;
333 doda 5324
334 doda 6802 // Bracketed Paste Mode
335     BracketedPaste = FALSE;
336 doda 4278
337 doda 6802 // Saved IME Status
338     IMEstat = FALSE;
339 maya 4893
340 doda 6802 // previous received character
341     PrevCharacter = -1; // none
342     PrevCRorLFGeneratedCRLF = FALSE;
343 doda 5316
344 doda 6802 // Beep over-used
345     BeepStartTime = GetTickCount();
346     BeepSuppressTime = BeepStartTime - ts.BeepSuppressTime * 1000;
347     BeepStartTime -= (ts.BeepOverUsedTime * 1000);
348     BeepOverUsedCount = ts.BeepOverUsedCount;
349 maya 3227 }
350    
351     void ResetCharSet()
352     {
353 zmatsuo 7405 char *result;
354 doda 6802 if (ts.Language==IdJapanese) {
355     Gn[0] = IdASCII;
356     Gn[1] = IdKatakana;
357     Gn[2] = IdKatakana;
358     Gn[3] = IdKanji;
359     Glr[0] = 0;
360     if ((ts.KanjiCode==IdJIS) && (ts.JIS7Katakana==0))
361     Glr[1] = 2; // 8-bit katakana
362     else
363     Glr[1] = 3;
364     }
365     else {
366     Gn[0] = IdASCII;
367     Gn[1] = IdSpecial;
368     Gn[2] = IdASCII;
369     Gn[3] = IdASCII;
370     Glr[0] = 0;
371     Glr[1] = 0;
372     cv.SendCode = IdASCII;
373     cv.SendKanjiFlag = FALSE;
374     cv.EchoCode = IdASCII;
375     cv.EchoKanjiFlag = FALSE;
376     }
377     /* Kanji flag */
378     KanjiIn = FALSE;
379     EUCkanaIn = FALSE;
380     EUCsupIn = FALSE;
381     SSflag = FALSE;
382     ConvJIS = FALSE;
383     Fallbacked = FALSE;
384 maya 3227
385 doda 6802 cv.Language = ts.Language;
386     cv.CRSend = ts.CRSend;
387     cv.KanjiCodeEcho = ts.KanjiCode;
388     cv.JIS7KatakanaEcho = ts.JIS7Katakana;
389     cv.KanjiCodeSend = ts.KanjiCodeSend;
390     cv.JIS7KatakanaSend = ts.JIS7KatakanaSend;
391     cv.KanjiIn = ts.KanjiIn;
392     cv.KanjiOut = ts.KanjiOut;
393 doda 7402
394 zmatsuo 7405 // ���P�[��������
395     // wctomb ������
396     result = setlocale(LC_ALL, ts.Locale);
397     if (result == NULL) {
398     // ��������Locale���������Z�b�g����������?
399     // default���Z�b�g��������
400     strcpy(ts.Locale, DEFAULT_LOCALE);
401     result = setlocale(LC_ALL, ts.Locale);
402     }
403 yutakapon 7978 // �p����Windows95/NT4.0�����Ats.Locale���f�t�H���g��"japanese"�����������A
404     // setlocale�� NULL �����������ATera Term���N�����������������������B
405     // setlocale �����������������A�R�[�h�y�[�W�����������B
406     if (result)
407     ts.CodePage = atoi(strrchr(result, '.')+1);
408 maya 3227 }
409    
410     void ResetKeypadMode(BOOL DisabledModeOnly)
411     {
412 doda 6802 if (!DisabledModeOnly || ts.DisableAppKeypad)
413     AppliKeyMode = FALSE;
414     if (!DisabledModeOnly || ts.DisableAppCursor)
415     AppliCursorMode = FALSE;
416 maya 3227 }
417    
418     void MoveToMainScreen()
419     {
420 doda 6802 StatusX = CursorX;
421     StatusWrap = Wrap;
422     StatusCursor = IsCaretEnabled();
423 maya 3227
424 doda 6802 CursorTop = MainTop;
425     CursorBottom = MainBottom;
426     Wrap = MainWrap;
427     DispEnableCaret(MainCursor);
428     MoveCursor(MainX, MainY); // move to main screen
429 maya 3227 }
430    
431     void MoveToStatusLine()
432     {
433 doda 6802 MainX = CursorX;
434     MainY = CursorY;
435     MainTop = CursorTop;
436     MainBottom = CursorBottom;
437     MainWrap = Wrap;
438     MainCursor = IsCaretEnabled();
439 maya 3227
440 doda 6802 DispEnableCaret(StatusCursor);
441     MoveCursor(StatusX, NumOfLines-1); // move to status line
442     CursorTop = NumOfLines-1;
443     CursorBottom = CursorTop;
444     Wrap = StatusWrap;
445 maya 3227 }
446    
447     void HideStatusLine()
448     {
449 doda 6802 if (isCursorOnStatusLine)
450     MoveToMainScreen();
451     StatusX = 0;
452     StatusWrap = FALSE;
453     StatusCursor = TRUE;
454     ShowStatusLine(0); //hide
455 maya 3227 }
456    
457     void ChangeTerminalSize(int Nx, int Ny)
458     {
459 doda 6802 BuffChangeTerminalSize(Nx, Ny);
460     StatusX = 0;
461     MainX = 0;
462     MainY = 0;
463     MainTop = 0;
464 doda 7045 MainBottom = NumOfLines-StatusLine-1;
465 maya 3227 }
466    
467 doda 3471 void SendCSIstr(char *str, int len) {
468 doda 4024 int l;
469    
470     if (str == NULL || len < 0)
471 doda 3471 return;
472    
473 doda 4024 if (len == 0) {
474     l = strlen(str);
475     }
476     else {
477     l = len;
478     }
479    
480 doda 3471 if (Send8BitMode)
481     CommBinaryOut(&cv,"\233", 1);
482     else
483     CommBinaryOut(&cv,"\033[", 2);
484    
485 doda 4024 CommBinaryOut(&cv, str, l);
486 doda 3471 }
487    
488 doda 5911 void SendOSCstr(char *str, int len, char TermChar) {
489 doda 4024 int l;
490    
491 doda 4104 if (str == NULL || len < 0)
492 doda 3471 return;
493    
494 doda 4024 if (len == 0) {
495     l = strlen(str);
496     }
497     else {
498     l = len;
499     }
500    
501 doda 5911 if (TermChar == BEL) {
502     CommBinaryOut(&cv,"\033]", 2);
503     CommBinaryOut(&cv, str, l);
504     CommBinaryOut(&cv,"\007", 1);
505     }
506     else if (Send8BitMode) {
507 doda 3471 CommBinaryOut(&cv,"\235", 1);
508 doda 4024 CommBinaryOut(&cv, str, l);
509 doda 3486 CommBinaryOut(&cv,"\234", 1);
510     }
511     else {
512 doda 3471 CommBinaryOut(&cv,"\033]", 2);
513 doda 4024 CommBinaryOut(&cv, str, l);
514 doda 3486 CommBinaryOut(&cv,"\033\\", 2);
515     }
516 doda 3471
517     }
518    
519 doda 4162 void SendDCSstr(char *str, int len) {
520     int l;
521    
522     if (str == NULL || len < 0)
523     return;
524    
525     if (len == 0) {
526     l = strlen(str);
527     }
528     else {
529     l = len;
530     }
531    
532     if (Send8BitMode) {
533     CommBinaryOut(&cv,"\220", 1);
534     CommBinaryOut(&cv, str, l);
535     CommBinaryOut(&cv,"\234", 1);
536     }
537     else {
538     CommBinaryOut(&cv,"\033P", 2);
539     CommBinaryOut(&cv, str, l);
540     CommBinaryOut(&cv,"\033\\", 2);
541     }
542    
543     }
544    
545 maya 3227 void BackSpace()
546     {
547 doda 5324 if (CursorX == CursorLeftM || CursorX == 0) {
548     if (CursorY > 0 && (ts.TermFlag & TF_BACKWRAP)) {
549     MoveCursor(CursorRightM, CursorY-1);
550     if (cv.HLogBuf!=0 && !ts.LogTypePlainText) Log1Byte(BS);
551     }
552     }
553     else if (CursorX > 0) {
554     MoveCursor(CursorX-1, CursorY);
555     if (cv.HLogBuf!=0 && !ts.LogTypePlainText) Log1Byte(BS);
556     }
557 maya 3227 }
558    
559     void CarriageReturn(BOOL logFlag)
560     {
561     if (!ts.EnableContinuedLineCopy || logFlag)
562 doda 6803 if (cv.HLogBuf!=0) Log1Byte(CR);
563 maya 3227
564 doda 5324 if (RelativeOrgMode || CursorX > CursorLeftM)
565     MoveCursor(CursorLeftM, CursorY);
566     else if (CursorX < CursorLeftM)
567     MoveCursor(0, CursorY);
568 doda 6602
569     Fallbacked = FALSE;
570 maya 3227 }
571    
572     void LineFeed(BYTE b, BOOL logFlag)
573     {
574     /* for auto print mode */
575     if ((AutoPrintMode) &&
576     (b>=LF) && (b<=FF))
577     BuffDumpCurrentLine(b);
578    
579     if (!ts.EnableContinuedLineCopy || logFlag)
580 doda 6803 if (cv.HLogBuf!=0) Log1Byte(LF);
581 maya 3227
582     if (CursorY < CursorBottom)
583     MoveCursor(CursorX,CursorY+1);
584     else if (CursorY == CursorBottom) BuffScrollNLines(1);
585     else if (CursorY < NumOfLines-StatusLine-1)
586     MoveCursor(CursorX,CursorY+1);
587    
588 doda 3312 ClearLineContinued();
589    
590 maya 3227 if (LFMode) CarriageReturn(logFlag);
591 doda 6602
592     Fallbacked = FALSE;
593 maya 3227 }
594    
595     void Tab()
596     {
597 doda 6802 if (Wrap && !ts.VTCompatTab) {
598     CarriageReturn(FALSE);
599     LineFeed(LF,FALSE);
600     if (ts.EnableContinuedLineCopy) {
601     SetLineContinued();
602     }
603     Wrap = FALSE;
604     }
605     CursorForwardTab(1, AutoWrapMode);
606     if (cv.HLogBuf!=0) Log1Byte(HT);
607 maya 3227 }
608    
609     void PutChar(BYTE b)
610     {
611 doda 6802 BOOL SpecialNew;
612     TCharAttr CharAttrTmp;
613 maya 3227
614 doda 6802 CharAttrTmp = CharAttr;
615 maya 3227
616 doda 6802 if (PrinterMode) { // printer mode
617     WriteToPrnFile(b,TRUE);
618     return;
619     }
620 maya 3227
621 doda 6802 if (Wrap) {
622     CarriageReturn(FALSE);
623     LineFeed(LF,FALSE);
624     CharAttrTmp.Attr |= ts.EnableContinuedLineCopy ? AttrLineContinued : 0;
625     }
626 maya 3227
627 zmatsuo 7427 if (cv.HLogBuf !=0) {
628     // (2005.2.20 yutaka)
629     if (ts.LogTypePlainText) {
630     if (__isascii(b) && !isprint(b)) {
631     // ASCII�������A���\�������������O�����������B
632     } else {
633     Log1Byte(b);
634     }
635 doda 6802 } else {
636 zmatsuo 7427 Log1Byte(b);
637 doda 6802 }
638     }
639 maya 3227
640 doda 6802 Wrap = FALSE;
641 maya 3227
642 doda 6802 SpecialNew = FALSE;
643     if ((b>0x5F) && (b<0x80)) {
644     if (SSflag)
645     SpecialNew = (Gn[GLtmp]==IdSpecial);
646     else
647     SpecialNew = (Gn[Glr[0]]==IdSpecial);
648     }
649     else if (b>0xDF) {
650     if (SSflag)
651     SpecialNew = (Gn[GLtmp]==IdSpecial);
652     else
653     SpecialNew = (Gn[Glr[1]]==IdSpecial);
654     }
655 maya 3227
656 doda 6802 if (SpecialNew != Special) {
657     UpdateStr();
658     Special = SpecialNew;
659     }
660 maya 3227
661 doda 6802 if (Special) {
662     b = b & 0x7F;
663     CharAttrTmp.Attr |= AttrSpecial;
664     }
665     else
666     CharAttrTmp.Attr |= CharAttr.Attr;
667 maya 3227
668 doda 6802 BuffPutChar(b, CharAttrTmp, InsertMode);
669 maya 3227
670 doda 6802 if (CursorX == CursorRightM || CursorX >= NumOfColumns-1) {
671     UpdateStr();
672     Wrap = AutoWrapMode;
673     }
674     else {
675     MoveRight();
676     }
677 maya 3227 }
678    
679     void PutDecSp(BYTE b)
680     {
681 doda 6802 TCharAttr CharAttrTmp;
682 maya 3227
683 doda 6802 CharAttrTmp = CharAttr;
684 maya 3227
685 doda 6802 if (PrinterMode) { // printer mode
686     WriteToPrnFile(b, TRUE);
687     return;
688     }
689 maya 3227
690 doda 6802 if (Wrap) {
691     CarriageReturn(FALSE);
692     LineFeed(LF, FALSE);
693     CharAttrTmp.Attr |= ts.EnableContinuedLineCopy ? AttrLineContinued : 0;
694     }
695 maya 3227
696 doda 6802 if (cv.HLogBuf!=0) Log1Byte(b);
697 maya 3227 /*
698 doda 6802 if (ts.LogTypePlainText && __isascii(b) && !isprint(b)) {
699     // ASCII�������A���\�������������O�����������B
700     } else {
701     if (cv.HLogBuf!=0) Log1Byte(b);
702     }
703 maya 3227 */
704    
705 doda 6802 Wrap = FALSE;
706 maya 3227
707 doda 6802 if (!Special) {
708     UpdateStr();
709     Special = TRUE;
710     }
711 maya 3227
712 doda 6802 CharAttrTmp.Attr |= AttrSpecial;
713     BuffPutChar(b, CharAttrTmp, InsertMode);
714 maya 3227
715 doda 6802 if (CursorX == CursorRightM || CursorX >= NumOfColumns-1) {
716     UpdateStr();
717     Wrap = AutoWrapMode;
718     }
719     else {
720     MoveRight();
721     }
722 maya 3227 }
723    
724     void PutKanji(BYTE b)
725     {
726 doda 6802 int LineEnd;
727     TCharAttr CharAttrTmp;
728 doda 6803 CharAttrTmp = CharAttr;
729 maya 3227
730 doda 6802 Kanji = Kanji + b;
731 maya 3227
732 doda 6802 if (PrinterMode && DirectPrn) {
733     WriteToPrnFile(HIBYTE(Kanji),FALSE);
734     WriteToPrnFile(LOBYTE(Kanji),TRUE);
735     return;
736     }
737 maya 3227
738 doda 6802 if (ConvJIS)
739     Kanji = JIS2SJIS((WORD)(Kanji & 0x7f7f));
740 maya 3227
741 doda 6802 if (PrinterMode) { // printer mode
742     WriteToPrnFile(HIBYTE(Kanji),FALSE);
743     WriteToPrnFile(LOBYTE(Kanji),TRUE);
744     return;
745     }
746 maya 3227
747 doda 6802 if (CursorX > CursorRightM)
748     LineEnd = NumOfColumns - 1;
749     else
750     LineEnd = CursorRightM;
751 doda 5324
752 doda 6802 if (Wrap) {
753     CarriageReturn(FALSE);
754     LineFeed(LF,FALSE);
755     if (ts.EnableContinuedLineCopy)
756     CharAttrTmp.Attr |= AttrLineContinued;
757     }
758     else if (CursorX > LineEnd - 1) {
759     if (AutoWrapMode) {
760     if (ts.EnableContinuedLineCopy) {
761     CharAttrTmp.Attr |= AttrLineContinued;
762     if (CursorX == LineEnd)
763     BuffPutChar(0x20, CharAttr, FALSE);
764     }
765     CarriageReturn(FALSE);
766     LineFeed(LF,FALSE);
767     }
768     else {
769     return;
770     }
771     }
772 maya 3227
773 doda 6802 Wrap = FALSE;
774 maya 3227
775 doda 6802 if (cv.HLogBuf!=0) {
776     Log1Byte(HIBYTE(Kanji));
777     Log1Byte(LOBYTE(Kanji));
778     }
779 maya 3227
780 doda 6802 if (Special) {
781     UpdateStr();
782     Special = FALSE;
783     }
784 maya 3227
785 doda 6802 BuffPutKanji(Kanji, CharAttrTmp, InsertMode);
786 maya 3227
787 doda 6802 if (CursorX < LineEnd - 1) {
788     MoveRight();
789     MoveRight();
790     }
791     else {
792     UpdateStr();
793     Wrap = AutoWrapMode;
794     }
795 maya 3227 }
796    
797     void PutDebugChar(BYTE b)
798     {
799 yutakapon 3637 static BYTE buff[3];
800 doda 5589 int i;
801     BOOL svInsertMode, svAutoWrapMode;
802     BYTE svCharAttr;
803 yutakapon 3637
804 doda 5589 if (DebugFlag!=DEBUG_FLAG_NOUT) {
805     svInsertMode = InsertMode;
806     svAutoWrapMode = AutoWrapMode;
807 doda 5588 InsertMode = FALSE;
808     AutoWrapMode = TRUE;
809 maya 3227
810 doda 5589 svCharAttr = CharAttr.Attr;
811     if (CharAttr.Attr != AttrDefault) {
812     UpdateStr();
813     CharAttr.Attr = AttrDefault;
814     }
815    
816 doda 5588 if (DebugFlag==DEBUG_FLAG_HEXD) {
817     _snprintf(buff, 3, "%02X", (unsigned int) b);
818 yutakapon 3637
819 doda 5589 for (i=0; i<2; i++)
820 doda 5588 PutChar(buff[i]);
821     PutChar(' ');
822     }
823     else if (DebugFlag==DEBUG_FLAG_NORM) {
824 yutakapon 3637
825 doda 5588 if ((b & 0x80) == 0x80) {
826     UpdateStr();
827     CharAttr.Attr = AttrReverse;
828     b = b & 0x7f;
829     }
830 maya 3227
831 doda 5588 if (b<=US) {
832     PutChar('^');
833     PutChar((char)(b+0x40));
834     }
835     else if (b==DEL) {
836     PutChar('<');
837     PutChar('D');
838     PutChar('E');
839     PutChar('L');
840     PutChar('>');
841     }
842     else
843     PutChar(b);
844     }
845 maya 3227
846 doda 5589 if (CharAttr.Attr != svCharAttr) {
847 doda 5588 UpdateStr();
848 doda 5589 CharAttr.Attr = svCharAttr;
849 doda 5588 }
850 doda 5589 InsertMode = svInsertMode;
851     AutoWrapMode = svAutoWrapMode;
852 yutakapon 3637 }
853 maya 3227 }
854    
855     void PrnParseControl(BYTE b) // printer mode
856     {
857 doda 6802 switch (b) {
858     case NUL:
859     return;
860     case SO:
861 doda 6913 if ((ts.ISO2022Flag & ISO2022_SO) && ! DirectPrn) {
862 doda 6802 if ((ts.Language==IdJapanese) &&
863     (ts.KanjiCode==IdJIS) &&
864     (ts.JIS7Katakana==1) &&
865     ((ts.TermFlag & TF_FIXEDJIS)!=0))
866     {
867     Gn[1] = IdKatakana;
868     }
869     Glr[0] = 1; /* LS1 */
870     return;
871     }
872     break;
873     case SI:
874 doda 6913 if ((ts.ISO2022Flag & ISO2022_SI) && ! DirectPrn) {
875 doda 6802 Glr[0] = 0; /* LS0 */
876     return;
877     }
878     break;
879     case DC1:
880     case DC3:
881     return;
882     case ESC:
883     ICount = 0;
884     JustAfterESC = TRUE;
885     ParseMode = ModeESC;
886     WriteToPrnFile(0, TRUE); // flush prn buff
887     return;
888     case CSI:
889     if (! Accept8BitCtrl) {
890     PutChar(b); /* Disp C1 char in VT100 mode */
891     return;
892     }
893     ClearParams();
894     FirstPrm = TRUE;
895     ParseMode = ModeCSI;
896     WriteToPrnFile(0, TRUE); // flush prn buff
897     WriteToPrnFile(b, FALSE);
898     return;
899     }
900     /* send the uninterpreted character to printer */
901     WriteToPrnFile(b, TRUE);
902 maya 3227 }
903    
904     void ParseControl(BYTE b)
905     {
906 doda 6802 if (PrinterMode) { // printer mode
907     PrnParseControl(b);
908     return;
909     }
910 maya 3227
911 doda 6802 if (b>=0x80) { /* C1 char */
912     if (ts.Language==IdEnglish) { /* English mode */
913     if (!Accept8BitCtrl) {
914     PutChar(b); /* Disp C1 char in VT100 mode */
915     return;
916     }
917     }
918     else { /* Japanese mode */
919     if ((ts.TermFlag & TF_ACCEPT8BITCTRL)==0) {
920     return; /* ignore C1 char */
921     }
922     /* C1 chars are interpreted as C0 chars in VT100 mode */
923     if (VTlevel < 2) {
924     b = b & 0x7F;
925     }
926     }
927     }
928     switch (b) {
929     /* C0 group */
930     case ENQ:
931     CommBinaryOut(&cv, &(ts.Answerback[0]), ts.AnswerbackLen);
932     break;
933     case BEL:
934     if (ts.Beep != IdBeepOff)
935     RingBell(ts.Beep);
936     break;
937     case BS:
938     BackSpace();
939     break;
940     case HT:
941     Tab();
942     break;
943     case LF:
944 maya 3227 if (ts.CRReceive == IdLF) {
945 maya 4893 // ���M�������s�R�[�h�� LF ���������A�T�[�o���� LF ���������������������������A
946     // CR+LF���������������������B
947     // cf. http://www.neocom.ca/forum/viewtopic.php?t=216
948     // (2007.1.21 yutaka)
949 maya 3227 CarriageReturn(TRUE);
950     LineFeed(b, TRUE);
951     break;
952     }
953 maya 4893 else if (ts.CRReceive == IdAUTO) {
954     // 9th Apr 2012: AUTO CR/LF mode (tentner)
955     // a CR or LF will generated a CR+LF, if the next character is the opposite, it will be ignored
956     if(PrevCharacter != CR || !PrevCRorLFGeneratedCRLF) {
957     CarriageReturn(TRUE);
958     LineFeed(b, TRUE);
959     PrevCRorLFGeneratedCRLF = TRUE;
960     }
961     else {
962     PrevCRorLFGeneratedCRLF = FALSE;
963     }
964     break;
965     }
966 maya 3227
967 doda 6802 case VT:
968     LineFeed(b, TRUE);
969     break;
970 maya 3227
971 doda 6802 case FF:
972     if ((ts.AutoWinSwitch>0) && JustAfterESC) {
973     CommInsert1Byte(&cv, b);
974     CommInsert1Byte(&cv, ESC);
975     ChangeEmu = IdTEK; /* Enter TEK Mode */
976     }
977     else
978     LineFeed(b, TRUE);
979     break;
980     case CR:
981     if (ts.CRReceive == IdAUTO) {
982     // 9th Apr 2012: AUTO CR/LF mode (tentner)
983     // a CR or LF will generated a CR+LF, if the next character is the opposite, it will be ignored
984     if(PrevCharacter != LF || !PrevCRorLFGeneratedCRLF) {
985     CarriageReturn(TRUE);
986     LineFeed(b, TRUE);
987     PrevCRorLFGeneratedCRLF = TRUE;
988     }
989     else {
990     PrevCRorLFGeneratedCRLF = FALSE;
991     }
992     }
993     else {
994     CarriageReturn(TRUE);
995     if (ts.CRReceive==IdCRLF) {
996     CommInsert1Byte(&cv, LF);
997     }
998     }
999     break;
1000     case SO: /* LS1 */
1001 doda 6913 if (ts.ISO2022Flag & ISO2022_SO) {
1002 doda 6804 if ((ts.Language==IdJapanese) &&
1003     (ts.KanjiCode==IdJIS) &&
1004     (ts.JIS7Katakana==1) &&
1005     ((ts.TermFlag & TF_FIXEDJIS)!=0))
1006     {
1007     Gn[1] = IdKatakana;
1008     }
1009 maya 3227
1010 doda 6804 Glr[0] = 1;
1011     }
1012 doda 6802 break;
1013     case SI: /* LS0 */
1014 doda 6913 if (ts.ISO2022Flag & ISO2022_SI) {
1015 doda 6804 Glr[0] = 0;
1016     }
1017 doda 6802 break;
1018     case DLE:
1019     if ((ts.FTFlag & FT_BPAUTO)!=0)
1020     ParseMode = ModeDLE; /* Auto B-Plus activation */
1021     break;
1022     case CAN:
1023     if ((ts.FTFlag & FT_ZAUTO)!=0)
1024     ParseMode = ModeCAN; /* Auto ZMODEM activation */
1025     // else if (ts.AutoWinSwitch>0)
1026     // ChangeEmu = IdTEK; /* Enter TEK Mode */
1027     else
1028     ParseMode = ModeFirst;
1029     break;
1030     case SUB:
1031     ParseMode = ModeFirst;
1032     break;
1033     case ESC:
1034     ICount = 0;
1035     JustAfterESC = TRUE;
1036     ParseMode = ModeESC;
1037     break;
1038     case FS:
1039     case GS:
1040     case RS:
1041     case US:
1042     if (ts.AutoWinSwitch>0) {
1043     CommInsert1Byte(&cv, b);
1044     ChangeEmu = IdTEK; /* Enter TEK Mode */
1045     }
1046     break;
1047 maya 3227
1048 doda 6802 /* C1 char */
1049     case IND:
1050     LineFeed(0, TRUE);
1051     break;
1052     case NEL:
1053     LineFeed(0, TRUE);
1054     CarriageReturn(TRUE);
1055     break;
1056     case HTS:
1057     if (ts.TabStopFlag & TABF_HTS8)
1058     SetTabStop();
1059     break;
1060     case RI:
1061     CursorUpWithScroll();
1062     break;
1063     case SS2:
1064 doda 6913 if (ts.ISO2022Flag & ISO2022_SS2) {
1065     GLtmp = 2;
1066     SSflag = TRUE;
1067     }
1068 doda 6802 break;
1069     case SS3:
1070 doda 6913 if (ts.ISO2022Flag & ISO2022_SS3) {
1071     GLtmp = 3;
1072     SSflag = TRUE;
1073     }
1074 doda 6802 break;
1075     case DCS:
1076     ClearParams();
1077     ESCFlag = FALSE;
1078     ParseMode = ModeDCS;
1079     break;
1080     case SOS:
1081     ESCFlag = FALSE;
1082     ParseMode = ModeIgnore;
1083     break;
1084     case CSI:
1085     ClearParams();
1086     FirstPrm = TRUE;
1087     ParseMode = ModeCSI;
1088     break;
1089     case OSC:
1090     ClearParams();
1091     ParseMode = ModeXS;
1092     break;
1093     case PM:
1094     case APC:
1095     ESCFlag = FALSE;
1096     ParseMode = ModeIgnore;
1097     break;
1098     }
1099 maya 3227 }
1100    
1101     void SaveCursor()
1102     {
1103 doda 6802 int i;
1104     PStatusBuff Buff;
1105 maya 3227
1106 doda 6802 if (isCursorOnStatusLine)
1107     Buff = &SBuff2; // for status line
1108     else if (AltScr)
1109     Buff = &SBuff3; // for alternate screen
1110     else
1111     Buff = &SBuff1; // for main screen
1112 maya 3227
1113 doda 6802 Buff->CursorX = CursorX;
1114     Buff->CursorY = CursorY;
1115     Buff->Attr = CharAttr;
1116    
1117     Buff->Glr[0] = Glr[0];
1118     Buff->Glr[1] = Glr[1];
1119     for (i=0 ; i<=3; i++)
1120     Buff->Gn[i] = Gn[i];
1121    
1122     Buff->AutoWrapMode = AutoWrapMode;
1123     Buff->RelativeOrgMode = RelativeOrgMode;
1124 maya 3227 }
1125    
1126 doda 6802 void RestoreCursor()
1127 maya 3227 {
1128 doda 6802 int i;
1129     PStatusBuff Buff;
1130 maya 3227
1131 doda 6802 UpdateStr();
1132 maya 3227
1133 doda 6802 if (isCursorOnStatusLine)
1134     Buff = &SBuff2; // for status line
1135     else if (AltScr)
1136     Buff = &SBuff3; // for alternate screen
1137     else
1138     Buff = &SBuff1; // for main screen
1139    
1140     if (Buff->CursorX > NumOfColumns-1)
1141     Buff->CursorX = NumOfColumns-1;
1142     if (Buff->CursorY > NumOfLines-1-StatusLine)
1143     Buff->CursorY = NumOfLines-1-StatusLine;
1144     MoveCursor(Buff->CursorX, Buff->CursorY);
1145    
1146     CharAttr = Buff->Attr;
1147     BuffSetCurCharAttr(CharAttr);
1148    
1149     Glr[0] = Buff->Glr[0];
1150     Glr[1] = Buff->Glr[1];
1151     for (i=0 ; i<=3; i++)
1152     Gn[i] = Buff->Gn[i];
1153    
1154     AutoWrapMode = Buff->AutoWrapMode;
1155     RelativeOrgMode = Buff->RelativeOrgMode;
1156 maya 3227 }
1157    
1158     void AnswerTerminalType()
1159     {
1160 doda 6802 char Tmp[50];
1161 maya 3227
1162 doda 6802 if (ts.TerminalID<IdVT320 || !Send8BitMode)
1163     strncpy_s(Tmp, sizeof(Tmp),"\033[?", _TRUNCATE);
1164     else
1165     strncpy_s(Tmp, sizeof(Tmp),"\233?", _TRUNCATE);
1166 maya 3227
1167 doda 6802 switch (ts.TerminalID) {
1168     case IdVT100:
1169     strncat_s(Tmp,sizeof(Tmp),"1;2",_TRUNCATE);
1170     break;
1171     case IdVT100J:
1172     strncat_s(Tmp,sizeof(Tmp),"5;2",_TRUNCATE);
1173     break;
1174     case IdVT101:
1175     strncat_s(Tmp,sizeof(Tmp),"1;0",_TRUNCATE);
1176     break;
1177     case IdVT102:
1178     strncat_s(Tmp,sizeof(Tmp),"6",_TRUNCATE);
1179     break;
1180     case IdVT102J:
1181     strncat_s(Tmp,sizeof(Tmp),"15",_TRUNCATE);
1182     break;
1183     case IdVT220J:
1184     strncat_s(Tmp,sizeof(Tmp),"62;1;2;5;6;7;8",_TRUNCATE);
1185     break;
1186     case IdVT282:
1187     strncat_s(Tmp,sizeof(Tmp),"62;1;2;4;5;6;7;8;10;11",_TRUNCATE);
1188     break;
1189     case IdVT320:
1190     strncat_s(Tmp,sizeof(Tmp),"63;1;2;6;7;8",_TRUNCATE);
1191     break;
1192     case IdVT382:
1193     strncat_s(Tmp,sizeof(Tmp),"63;1;2;4;5;6;7;8;10;15",_TRUNCATE);
1194     break;
1195     case IdVT420:
1196     strncat_s(Tmp,sizeof(Tmp),"64;1;2;7;8;9;15;18;21",_TRUNCATE);
1197     break;
1198     case IdVT520:
1199     strncat_s(Tmp,sizeof(Tmp),"65;1;2;7;8;9;12;18;19;21;23;24;42;44;45;46",_TRUNCATE);
1200     break;
1201     case IdVT525:
1202     strncat_s(Tmp,sizeof(Tmp),"65;1;2;7;9;12;18;19;21;22;23;24;42;44;45;46",_TRUNCATE);
1203     break;
1204     }
1205     strncat_s(Tmp,sizeof(Tmp),"c",_TRUNCATE);
1206 maya 3227
1207 doda 6802 CommBinaryOut(&cv,Tmp,strlen(Tmp)); /* Report terminal ID */
1208 maya 3227 }
1209    
1210     void ESCSpace(BYTE b)
1211     {
1212 doda 6802 switch (b) {
1213     case 'F': // S7C1T
1214     Send8BitMode = FALSE;
1215     break;
1216     case 'G': // S8C1T
1217     if (VTlevel >= 2) {
1218     Send8BitMode = TRUE;
1219     }
1220     break;
1221     }
1222 maya 3227 }
1223    
1224     void ESCSharp(BYTE b)
1225     {
1226 doda 6802 switch (b) {
1227     case '8': /* Fill screen with "E" (DECALN) */
1228     BuffUpdateScroll();
1229     BuffFillWithE();
1230     CursorTop = 0;
1231     CursorBottom = NumOfLines-1-StatusLine;
1232     CursorLeftM = 0;
1233     CursorRightM = NumOfColumns - 1;
1234     MoveCursor(0, 0);
1235     ParseMode = ModeFirst;
1236     break;
1237     }
1238 maya 3227 }
1239    
1240     /* select double byte code set */
1241     void ESCDBCSSelect(BYTE b)
1242     {
1243 doda 6802 int Dist;
1244 maya 3227
1245 doda 6802 if (ts.Language!=IdJapanese) return;
1246 maya 3227
1247 doda 6802 switch (ICount) {
1248     case 1:
1249     if ((b=='@') || (b=='B'))
1250     {
1251     Gn[0] = IdKanji; /* Kanji -> G0 */
1252     if ((ts.TermFlag & TF_AUTOINVOKE)!=0)
1253     Glr[0] = 0; /* G0->GL */
1254     }
1255     break;
1256     case 2:
1257     /* Second intermediate char must be
1258     '(' or ')' or '*' or '+'. */
1259     Dist = (IntChar[2]-'(') & 3; /* G0 - G3 */
1260     if ((b=='1') || (b=='3') ||
1261     (b=='@') || (b=='B'))
1262     {
1263     Gn[Dist] = IdKanji; /* Kanji -> G0-3 */
1264     if (((ts.TermFlag & TF_AUTOINVOKE)!=0) &&
1265     (Dist==0))
1266     Glr[0] = 0; /* G0->GL */
1267     }
1268     break;
1269     }
1270 maya 3227 }
1271    
1272     void ESCSelectCode(BYTE b)
1273     {
1274 doda 6802 switch (b) {
1275     case '0':
1276     if (ts.AutoWinSwitch>0)
1277     ChangeEmu = IdTEK; /* enter TEK mode */
1278     break;
1279     }
1280 maya 3227 }
1281    
1282 doda 6802 /* select single byte code set */
1283 maya 3227 void ESCSBCSSelect(BYTE b)
1284     {
1285 doda 6802 int Dist;
1286 maya 3227
1287 doda 6802 /* Intermediate char must be '(' or ')' or '*' or '+'. */
1288     Dist = (IntChar[1]-'(') & 3; /* G0 - G3 */
1289 maya 3227
1290 doda 6802 switch (b) {
1291     case '0': Gn[Dist] = IdSpecial; break;
1292     case '<': Gn[Dist] = IdASCII; break;
1293     case '>': Gn[Dist] = IdASCII; break;
1294     case 'A': Gn[Dist] = IdASCII; break;
1295     case 'B': Gn[Dist] = IdASCII; break;
1296     case 'H': Gn[Dist] = IdASCII; break;
1297     case 'I':
1298     if (ts.Language==IdJapanese)
1299     Gn[Dist] = IdKatakana;
1300     break;
1301     case 'J': Gn[Dist] = IdASCII; break;
1302     }
1303 maya 3227
1304 doda 6802 if (((ts.TermFlag & TF_AUTOINVOKE)!=0) && (Dist==0))
1305     Glr[0] = 0; /* G0->GL */
1306 maya 3227 }
1307    
1308     void PrnParseEscape(BYTE b) // printer mode
1309     {
1310 doda 6802 int i;
1311 maya 3227
1312 doda 6802 ParseMode = ModeFirst;
1313     switch (ICount) {
1314     /* no intermediate char */
1315     case 0:
1316     switch (b) {
1317     case '[': /* CSI */
1318     ClearParams();
1319     FirstPrm = TRUE;
1320     WriteToPrnFile(ESC,FALSE);
1321     WriteToPrnFile('[',FALSE);
1322     ParseMode = ModeCSI;
1323     return;
1324     } /* end of case Icount=0 */
1325     break;
1326     /* one intermediate char */
1327     case 1:
1328     switch (IntChar[1]) {
1329     case '$':
1330     if (! DirectPrn) {
1331     ESCDBCSSelect(b);
1332     return;
1333     }
1334     break;
1335     case '(':
1336     case ')':
1337     case '*':
1338     case '+':
1339     if (! DirectPrn) {
1340     ESCSBCSSelect(b);
1341     return;
1342     }
1343     break;
1344     }
1345     break;
1346     /* two intermediate char */
1347     case 2:
1348     if ((! DirectPrn) &&
1349     (IntChar[1]=='$') &&
1350     ('('<=IntChar[2]) &&
1351     (IntChar[2]<='+'))
1352     {
1353     ESCDBCSSelect(b);
1354     return;
1355     }
1356     break;
1357     }
1358     // send the uninterpreted sequence to printer
1359     WriteToPrnFile(ESC,FALSE);
1360     for (i=1; i<=ICount; i++)
1361     WriteToPrnFile(IntChar[i],FALSE);
1362     WriteToPrnFile(b,TRUE);
1363 maya 3227 }
1364    
1365     void ParseEscape(BYTE b) /* b is the final char */
1366     {
1367 doda 6802 if (PrinterMode) { // printer mode
1368     PrnParseEscape(b);
1369     return;
1370     }
1371 maya 3227
1372 doda 6802 switch (ICount) {
1373     case 0: /* no intermediate char */
1374     switch (b) {
1375     case '6': // DECBI
1376     if (CursorY >= CursorTop && CursorY <= CursorBottom &&
1377     CursorX >= CursorLeftM && CursorX <= CursorRightM) {
1378     if (CursorX == CursorLeftM)
1379     BuffScrollRight(1);
1380     else
1381     MoveCursor(CursorX-1, CursorY);
1382     }
1383     break;
1384     case '7': SaveCursor(); break;
1385     case '8': RestoreCursor(); break;
1386     case '9': // DECFI
1387     if (CursorY >= CursorTop && CursorY <= CursorBottom &&
1388     CursorX >= CursorLeftM && CursorX <= CursorRightM) {
1389     if (CursorX == CursorRightM)
1390     BuffScrollLeft(1);
1391     else
1392     MoveCursor(CursorX+1, CursorY);
1393     }
1394     break;
1395     case '=': AppliKeyMode = TRUE; break;
1396     case '>': AppliKeyMode = FALSE; break;
1397     case 'D': /* IND */
1398     LineFeed(0,TRUE);
1399     break;
1400     case 'E': /* NEL */
1401     MoveCursor(0,CursorY);
1402     LineFeed(0,TRUE);
1403     break;
1404     case 'H': /* HTS */
1405     if (ts.TabStopFlag & TABF_HTS7)
1406     SetTabStop();
1407     break;
1408     case 'M': /* RI */
1409     CursorUpWithScroll();
1410     break;
1411     case 'N': /* SS2 */
1412 doda 6913 if (ts.ISO2022Flag & ISO2022_SS2) {
1413     GLtmp = 2;
1414     SSflag = TRUE;
1415     }
1416 doda 6802 break;
1417     case 'O': /* SS3 */
1418 doda 6913 if (ts.ISO2022Flag & ISO2022_SS3) {
1419     GLtmp = 3;
1420     SSflag = TRUE;
1421     }
1422 doda 6802 break;
1423     case 'P': /* DCS */
1424     ClearParams();
1425     ESCFlag = FALSE;
1426     ParseMode = ModeDCS;
1427     return;
1428     case 'X': /* SOS */
1429     case '^': /* APC */
1430     case '_': /* PM */
1431     ESCFlag = FALSE;
1432     ParseMode = ModeIgnore;
1433     return;
1434     case 'Z': /* DECID */
1435     AnswerTerminalType();
1436     break;
1437     case '[': /* CSI */
1438     ClearParams();
1439     FirstPrm = TRUE;
1440     ParseMode = ModeCSI;
1441     return;
1442     case '\\': break; /* ST */
1443     case ']': /* XTERM sequence (OSC) */
1444     ClearParams();
1445     ParseMode = ModeXS;
1446     return;
1447     case 'c': /* Hardware reset */
1448     HideStatusLine();
1449     ResetTerminal();
1450     ClearUserKey();
1451     ClearBuffer();
1452     if (ts.PortType==IdSerial) // reset serial port
1453     CommResetSerial(&ts, &cv, TRUE);
1454     break;
1455     case 'g': /* Visual Bell (screen original?) */
1456     RingBell(IdBeepVisual);
1457     break;
1458 doda 6913 case 'n': /* LS2 */
1459     if (ts.ISO2022Flag & ISO2022_LS2) {
1460     Glr[0] = 2;
1461     }
1462     break;
1463     case 'o': /* LS3 */
1464     if (ts.ISO2022Flag & ISO2022_LS3) {
1465     Glr[0] = 3;
1466     }
1467     break;
1468     case '|': /* LS3R */
1469     if (ts.ISO2022Flag & ISO2022_LS3R) {
1470     Glr[1] = 3;
1471     }
1472     break;
1473     case '}': /* LS2R */
1474     if (ts.ISO2022Flag & ISO2022_LS2R) {
1475     Glr[1] = 2;
1476     }
1477     break;
1478     case '~': /* LS1R */
1479     if (ts.ISO2022Flag & ISO2022_LS1R) {
1480     Glr[1] = 1;
1481     }
1482     break;
1483 doda 6802 }
1484     break;
1485     /* end of case Icount=0 */
1486    
1487     case 1: /* one intermediate char */
1488     switch (IntChar[1]) {
1489     case ' ': ESCSpace(b); break;
1490     case '#': ESCSharp(b); break;
1491     case '$': ESCDBCSSelect(b); break;
1492     case '%': break;
1493     case '(':
1494     case ')':
1495     case '*':
1496     case '+':
1497     ESCSBCSSelect(b);
1498     break;
1499     }
1500     break;
1501    
1502     case 2: /* two intermediate char */
1503     if ((IntChar[1]=='$') && ('('<=IntChar[2]) && (IntChar[2]<='+'))
1504     ESCDBCSSelect(b);
1505     else if ((IntChar[1]=='%') && (IntChar[2]=='!'))
1506     ESCSelectCode(b);
1507     break;
1508     }
1509     ParseMode = ModeFirst;
1510 maya 3227 }
1511    
1512     void EscapeSequence(BYTE b)
1513     {
1514 doda 6173 if (b<=US)
1515     ParseControl(b);
1516     else if ((b>=0x20) && (b<=0x2F)) {
1517 doda 6174 // TODO: ICount �� IntCharMax ���B�������A������ IntChar ���u����������������?
1518 doda 6173 if (ICount<IntCharMax)
1519     ICount++;
1520     IntChar[ICount] = b;
1521     }
1522     else if ((b>=0x30) && (b<=0x7E))
1523     ParseEscape(b);
1524     else if ((b>=0x80) && (b<=0x9F))
1525     ParseControl(b);
1526     else if (b>=0xA0) {
1527     ParseMode=ModeFirst;
1528     ParseFirst(b);
1529     }
1530 maya 3227
1531 doda 6173 JustAfterESC = FALSE;
1532 maya 3227 }
1533    
1534 doda 6174 #define CheckParamVal(p,m) \
1535     if ((p) == 0) { \
1536     (p) = 1; \
1537     } \
1538     else if ((p) > (m) || p < 0) { \
1539     (p) = (m); \
1540     }
1541    
1542     #define CheckParamValMax(p,m) \
1543     if ((p) > (m) || p <= 0) { \
1544     (p) = (m); \
1545     }
1546    
1547     #define RequiredParams(n) \
1548     if ((n) > 1) { \
1549     while (NParam < n) { \
1550     NParam++; \
1551     Param[NParam] = 0; \
1552     NSParam[NParam] = 0; \
1553     } \
1554     }
1555    
1556 doda 6173 void CSInsertCharacter() // ICH
1557     {
1558     // Insert space characters at cursor
1559 doda 6174 CheckParamVal(Param[1], NumOfColumns);
1560 maya 3227
1561 doda 6173 BuffUpdateScroll();
1562 doda 6174 BuffInsertSpace(Param[1]);
1563 doda 6173 }
1564 maya 3227
1565 doda 5429 void CSCursorUp(BOOL AffectMargin) // CUU / VPB
1566     {
1567     int topMargin, NewY;
1568 maya 3227
1569 doda 6174 CheckParamVal(Param[1], CursorY);
1570 maya 3227
1571 doda 5429 if (AffectMargin && CursorY >= CursorTop)
1572     topMargin = CursorTop;
1573     else
1574     topMargin = 0;
1575 maya 3227
1576 doda 5429 NewY = CursorY - Param[1];
1577     if (NewY < topMargin)
1578     NewY = topMargin;
1579 maya 3227
1580 doda 5429 MoveCursor(CursorX, NewY);
1581     }
1582 maya 3227
1583 doda 5429 void CSCursorUp1() // CPL
1584     {
1585     MoveCursor(CursorLeftM, CursorY);
1586     CSCursorUp(TRUE);
1587     }
1588 maya 3227
1589 doda 5429 void CSCursorDown(BOOL AffectMargin) // CUD / VPR
1590     {
1591     int bottomMargin, NewY;
1592    
1593     if (AffectMargin && CursorY <= CursorBottom)
1594     bottomMargin = CursorBottom;
1595     else
1596     bottomMargin = NumOfLines-StatusLine-1;
1597    
1598 doda 6174 CheckParamVal(Param[1], bottomMargin);
1599    
1600 doda 5429 NewY = CursorY + Param[1];
1601     if (NewY > bottomMargin)
1602     NewY = bottomMargin;
1603    
1604     MoveCursor(CursorX, NewY);
1605     }
1606    
1607     void CSCursorDown1() // CNL
1608     {
1609     MoveCursor(CursorLeftM, CursorY);
1610     CSCursorDown(TRUE);
1611     }
1612    
1613 maya 3227 void CSScreenErase()
1614     {
1615     BuffUpdateScroll();
1616     switch (Param[1]) {
1617 doda 6173 case 0:
1618 maya 3227 // <ESC>[H(Cursor in left upper corner)�������J�[�\�������������w�������������A
1619     // <ESC>[J��<ESC>[2J�����������������A�����������A���s�o�b�t�@���X�N���[���A�E�g
1620     // �����������������B(2005.5.29 yutaka)
1621     // �R���t�B�O���[�V�������������������������������B(2008.5.3 yutaka)
1622 doda 6435 if (ts.ScrollWindowClearScreen &&
1623 maya 3227 (CursorX == 0 && CursorY == 0)) {
1624 doda 6173 // Erase screen (scroll out)
1625 maya 3227 BuffClearScreen();
1626     UpdateWindow(HVTWin);
1627    
1628     } else {
1629 doda 6173 // Erase characters from cursor to the end of screen
1630 maya 3227 BuffEraseCurToEnd();
1631     }
1632     break;
1633    
1634 doda 6173 case 1:
1635     // Erase characters from home to cursor
1636 maya 3227 BuffEraseHomeToCur();
1637     break;
1638    
1639 doda 6173 case 2:
1640     // Erase screen (scroll out)
1641 maya 3227 BuffClearScreen();
1642     UpdateWindow(HVTWin);
1643 doda 5564 if (ClearThenHome && !isCursorOnStatusLine) {
1644     if (RelativeOrgMode) {
1645     MoveCursor(0, 0);
1646     }
1647     else {
1648     MoveCursor(CursorLeftM, CursorTop);
1649     }
1650     }
1651 maya 3227 break;
1652     }
1653     }
1654    
1655 doda 4070 void CSQSelScreenErase()
1656     {
1657     BuffUpdateScroll();
1658     switch (Param[1]) {
1659 doda 6173 case 0:
1660     // Erase characters from cursor to end
1661 doda 4070 BuffSelectedEraseCurToEnd();
1662     break;
1663    
1664 doda 6173 case 1:
1665     // Erase characters from home to cursor
1666 doda 4070 BuffSelectedEraseHomeToCur();
1667     break;
1668    
1669 doda 6173 case 2:
1670     // Erase entire screen
1671 doda 4070 BuffSelectedEraseScreen();
1672     break;
1673     }
1674     }
1675    
1676 doda 6173 void CSInsertLine()
1677     {
1678     // Insert lines at current position
1679     int Count, YEnd;
1680 maya 3227
1681 doda 6174 if (CursorY < CursorTop || CursorY > CursorBottom) {
1682 doda 6173 return;
1683 doda 6174 }
1684 maya 3227
1685 doda 6174 CheckParamVal(Param[1], NumOfLines);
1686    
1687 doda 6173 Count = Param[1];
1688 maya 3227
1689 doda 6173 YEnd = CursorBottom;
1690     if (CursorY > YEnd)
1691     YEnd = NumOfLines-1-StatusLine;
1692 doda 6174
1693 doda 6173 if (Count > YEnd+1 - CursorY)
1694     Count = YEnd+1 - CursorY;
1695 maya 3227
1696 doda 6173 BuffInsertLines(Count,YEnd);
1697     }
1698 maya 3227
1699 doda 6173 void CSLineErase()
1700     {
1701     BuffUpdateScroll();
1702     switch (Param[1]) {
1703     case 0: /* erase char from cursor to end of line */
1704     BuffEraseCharsInLine(CursorX,NumOfColumns-CursorX);
1705     break;
1706 doda 4070
1707 doda 6173 case 1: /* erase char from start of line to cursor */
1708     BuffEraseCharsInLine(0,CursorX+1);
1709     break;
1710 maya 3227
1711 doda 6173 case 2: /* erase entire line */
1712     BuffEraseCharsInLine(0,NumOfColumns);
1713     break;
1714     }
1715     }
1716 maya 3227
1717 doda 6173 void CSQSelLineErase()
1718     {
1719     BuffUpdateScroll();
1720     switch (Param[1]) {
1721     case 0: /* erase char from cursor to end of line */
1722     BuffSelectedEraseCharsInLine(CursorX,NumOfColumns-CursorX);
1723     break;
1724 maya 3227
1725 doda 6173 case 1: /* erase char from start of line to cursor */
1726     BuffSelectedEraseCharsInLine(0,CursorX+1);
1727     break;
1728 maya 3227
1729 doda 6173 case 2: /* erase entire line */
1730     BuffSelectedEraseCharsInLine(0,NumOfColumns);
1731     break;
1732     }
1733     }
1734 maya 3227
1735 doda 6173 void CSDeleteNLines()
1736     // Delete lines from current line
1737     {
1738     int Count, YEnd;
1739 maya 3227
1740 doda 6174 if (CursorY < CursorTop || CursorY > CursorBottom) {
1741 doda 6173 return;
1742 doda 6174 }
1743    
1744     CheckParamVal(Param[1], NumOfLines);
1745 doda 6173 Count = Param[1];
1746 maya 3227
1747 doda 6173 YEnd = CursorBottom;
1748     if (CursorY > YEnd)
1749     YEnd = NumOfLines-1-StatusLine;
1750 doda 6174
1751 doda 6173 if (Count > YEnd+1-CursorY)
1752     Count = YEnd+1-CursorY;
1753 doda 6174
1754 doda 6173 BuffDeleteLines(Count,YEnd);
1755     }
1756 maya 3227
1757 doda 6173 void CSDeleteCharacter() // DCH
1758     {
1759     // Delete characters in current line from cursor
1760 doda 6174 CheckParamVal(Param[1], NumOfColumns);
1761 maya 3227
1762 doda 6173 BuffUpdateScroll();
1763     BuffDeleteChars(Param[1]);
1764     }
1765 maya 3227
1766 doda 6173 void CSEraseCharacter() // ECH
1767     {
1768 doda 6174 CheckParamVal(Param[1], NumOfColumns);
1769    
1770 doda 6173 BuffUpdateScroll();
1771     BuffEraseChars(Param[1]);
1772     }
1773    
1774     void CSScrollUp()
1775     {
1776 doda 6174 // TODO: �X�N���[���������l���[���s�����������������v����
1777     CheckParamVal(Param[1], INT_MAX);
1778    
1779 doda 6173 BuffUpdateScroll();
1780     BuffRegionScrollUpNLines(Param[1]);
1781     }
1782    
1783     void CSScrollDown()
1784     {
1785 doda 6174 CheckParamVal(Param[1], NumOfLines);
1786    
1787 doda 6173 BuffUpdateScroll();
1788     BuffRegionScrollDownNLines(Param[1]);
1789     }
1790    
1791     void CSForwardTab()
1792     {
1793 doda 6174 CheckParamVal(Param[1], NumOfColumns);
1794 doda 6173 CursorForwardTab(Param[1], AutoWrapMode);
1795     }
1796    
1797     void CSBackwardTab()
1798     {
1799 doda 6174 CheckParamVal(Param[1], NumOfColumns);
1800 doda 6173 CursorBackwardTab(Param[1]);
1801     }
1802    
1803 doda 5324 void CSMoveToColumnN() // CHA / HPA
1804     {
1805 doda 6174 CheckParamVal(Param[1], NumOfColumns);
1806 maya 3227
1807 doda 5324 Param[1]--;
1808 maya 3227
1809 doda 5324 if (RelativeOrgMode) {
1810     if (CursorLeftM + Param[1] > CursorRightM )
1811     MoveCursor(CursorRightM, CursorY);
1812     else
1813     MoveCursor(CursorLeftM + Param[1], CursorY);
1814     }
1815     else {
1816     MoveCursor(Param[1], CursorY);
1817     }
1818     }
1819 maya 3227
1820 doda 5429 void CSCursorRight(BOOL AffectMargin) // CUF / HPR
1821 doda 5324 {
1822 doda 5429 int NewX, rightMargin;
1823 doda 5324
1824 doda 6174 CheckParamVal(Param[1], NumOfColumns);
1825 doda 5324
1826 doda 6174 if (AffectMargin && CursorX <= CursorRightM) {
1827 doda 5429 rightMargin = CursorRightM;
1828 doda 6174 }
1829     else {
1830 doda 5429 rightMargin = NumOfColumns-1;
1831 doda 6174 }
1832 doda 5429
1833 doda 5324 NewX = CursorX + Param[1];
1834 doda 5429 if (NewX > rightMargin)
1835     NewX = rightMargin;
1836 doda 5324
1837     MoveCursor(NewX, CursorY);
1838     }
1839    
1840 doda 5429 void CSCursorLeft(BOOL AffectMargin) // CUB / HPB
1841 doda 5324 {
1842 doda 5429 int NewX, leftMargin;
1843 doda 5324
1844 doda 6174 CheckParamVal(Param[1], NumOfColumns);
1845 doda 5324
1846 doda 6174 if (AffectMargin && CursorX >= CursorLeftM) {
1847 doda 5429 leftMargin = CursorLeftM;
1848 doda 6174 }
1849     else {
1850 doda 5429 leftMargin = 0;
1851 doda 6174 }
1852 doda 5324
1853 doda 5429 NewX = CursorX - Param[1];
1854 doda 6174 if (NewX < leftMargin) {
1855 doda 5429 NewX = leftMargin;
1856 doda 6174 }
1857 doda 5324
1858     MoveCursor(NewX, CursorY);
1859     }
1860    
1861 doda 6174 void CSMoveToLineN() // VPA
1862 doda 6173 {
1863 doda 6174 CheckParamVal(Param[1], NumOfLines-StatusLine);
1864    
1865 doda 6173 if (RelativeOrgMode) {
1866     if (CursorTop+Param[1]-1 > CursorBottom)
1867     MoveCursor(CursorX,CursorBottom);
1868     else
1869     MoveCursor(CursorX,CursorTop+Param[1]-1);
1870     }
1871     else {
1872     if (Param[1] > NumOfLines-StatusLine)
1873     MoveCursor(CursorX,NumOfLines-1-StatusLine);
1874     else
1875     MoveCursor(CursorX,Param[1]-1);
1876     }
1877 doda 6602 Fallbacked = FALSE;
1878 doda 6173 }
1879 maya 3227
1880 doda 5324 void CSMoveToXY() // CUP / HVP
1881     {
1882     int NewX, NewY;
1883 maya 3227
1884 doda 6174 RequiredParams(2);
1885     CheckParamVal(Param[1], NumOfLines-StatusLine);
1886     CheckParamVal(Param[2], NumOfColumns);
1887 maya 3227
1888 doda 5324 NewY = Param[1] - 1;
1889     NewX = Param[2] - 1;
1890    
1891     if (isCursorOnStatusLine)
1892     NewY = CursorY;
1893     else if (RelativeOrgMode) {
1894     NewX += CursorLeftM;
1895     if (NewX > CursorRightM)
1896     NewX = CursorRightM;
1897    
1898     NewY += CursorTop;
1899     if (NewY > CursorBottom)
1900     NewY = CursorBottom;
1901     }
1902     else {
1903     if (NewY > NumOfLines-1-StatusLine)
1904     NewY = NumOfLines-1-StatusLine;
1905     }
1906    
1907     MoveCursor(NewX, NewY);
1908 doda 6602 Fallbacked = FALSE;
1909 doda 5324 }
1910    
1911 doda 6173 void CSDeleteTabStop()
1912     {
1913     ClearTabStop(Param[1]);
1914     }
1915 maya 3227
1916 doda 6173 void CS_h_Mode() // SM
1917     {
1918     switch (Param[1]) {
1919     case 2: // KAM
1920     KeybEnabled = FALSE; break;
1921     case 4: // IRM
1922     InsertMode = TRUE; break;
1923     case 12: // SRM
1924     ts.LocalEcho = 0;
1925     if (cv.Ready && cv.TelFlag && (ts.TelEcho>0))
1926     TelChangeEcho();
1927     break;
1928     case 20: // LF/NL
1929     LFMode = TRUE;
1930     ts.CRSend = IdCRLF;
1931     cv.CRSend = IdCRLF;
1932     break;
1933     case 33: // WYSTCURM
1934     if (ts.WindowFlag & WF_CURSORCHANGE) {
1935     ts.NonblinkingCursor = TRUE;
1936     ChangeCaret();
1937     }
1938     break;
1939     case 34: // WYULCURM
1940     if (ts.WindowFlag & WF_CURSORCHANGE) {
1941     ts.CursorShape = IdHCur;
1942     ChangeCaret();
1943     }
1944     break;
1945     }
1946     }
1947 maya 3227
1948 doda 6173 void CS_i_Mode() // MC
1949     {
1950     switch (Param[1]) {
1951     /* print screen */
1952     // PrintEX -- TRUE: print screen
1953     // FALSE: scroll region
1954     case 0:
1955     if (ts.TermFlag&TF_PRINTERCTRL) {
1956     BuffPrint(! PrintEX);
1957     }
1958     break;
1959     /* printer controller mode off */
1960     case 4: break; /* See PrnParseCS() */
1961     /* printer controller mode on */
1962     case 5:
1963     if (ts.TermFlag&TF_PRINTERCTRL) {
1964     if (! AutoPrintMode)
1965     OpenPrnFile();
1966     DirectPrn = (ts.PrnDev[0]!=0);
1967     PrinterMode = TRUE;
1968     }
1969     break;
1970 doda 4397 }
1971 doda 6173 }
1972    
1973     void CS_l_Mode() // RM
1974     {
1975     switch (Param[1]) {
1976     case 2: // KAM
1977     KeybEnabled = TRUE; break;
1978     case 4: // IRM
1979     InsertMode = FALSE; break;
1980     case 12: // SRM
1981     ts.LocalEcho = 1;
1982     if (cv.Ready && cv.TelFlag && (ts.TelEcho>0))
1983     TelChangeEcho();
1984     break;
1985     case 20: // LF/NL
1986     LFMode = FALSE;
1987     ts.CRSend = IdCR;
1988     cv.CRSend = IdCR;
1989     break;
1990     case 33: // WYSTCURM
1991     if (ts.WindowFlag & WF_CURSORCHANGE) {
1992     ts.NonblinkingCursor = FALSE;
1993     ChangeCaret();
1994     }
1995     break;
1996     case 34: // WYULCURM
1997     if (ts.WindowFlag & WF_CURSORCHANGE) {
1998     ts.CursorShape = IdBlkCur;
1999     ChangeCaret();
2000     }
2001     break;
2002 doda 4397 }
2003 doda 6173 }
2004 maya 3227
2005 doda 6173 void CS_n_Mode() // DSR
2006     {
2007     char Report[16];
2008     int X, Y, len;
2009 maya 3227
2010 doda 6173 switch (Param[1]) {
2011     case 5:
2012     /* Device Status Report -> Ready */
2013     SendCSIstr("0n", 0);
2014     break;
2015     case 6:
2016     /* Cursor Position Report */
2017     if (isCursorOnStatusLine) {
2018     X = CursorX + 1;
2019     Y = 1;
2020     }
2021     else if (RelativeOrgMode) {
2022     X = CursorX - CursorLeftM + 1;
2023     Y = CursorY - CursorTop + 1;
2024     }
2025     else {
2026     X = CursorX + 1;
2027     Y = CursorY+1;
2028     }
2029     len = _snprintf_s_l(Report, sizeof(Report), _TRUNCATE, "%u;%uR", CLocale, Y, X);
2030     SendCSIstr(Report, len);
2031     break;
2032 doda 5336 }
2033 doda 6173 }
2034 maya 3227
2035 doda 5095 void ParseSGRParams(PCharAttr attr, PCharAttr mask, int start)
2036 maya 3227 {
2037 doda 5073 int i, j, P, r, g, b, color;
2038 doda 5095 TCharAttr dummy;
2039 maya 3227
2040 doda 5095 if (mask == NULL) {
2041     mask = &dummy;
2042     }
2043    
2044 doda 6173 for (i=start ; i<=NParam ; i++) {
2045 maya 3227 P = Param[i];
2046     switch (P) {
2047 doda 6173 case 0: /* Clear all */
2048 doda 5095 attr->Attr = DefCharAttr.Attr;
2049     attr->Attr2 = DefCharAttr.Attr2 | (attr->Attr2&Attr2Protect);
2050     attr->Fore = DefCharAttr.Fore;
2051     attr->Back = DefCharAttr.Back;
2052     mask->Attr = AttrSgrMask;
2053     mask->Attr2 = Attr2ColorMask;
2054 maya 3227 break;
2055    
2056 doda 6173 case 1: /* Bold */
2057 doda 5095 attr->Attr |= AttrBold;
2058     mask->Attr |= AttrBold;
2059 maya 3227 break;
2060    
2061 doda 6173 case 4: /* Under line */
2062 doda 5095 attr->Attr |= AttrUnder;
2063     mask->Attr |= AttrUnder;
2064 maya 3227 break;
2065    
2066 doda 6173 case 5: /* Blink */
2067 doda 5095 attr->Attr |= AttrBlink;
2068     mask->Attr |= AttrBlink;
2069 maya 3227 break;
2070    
2071 doda 6173 case 7: /* Reverse */
2072 doda 5095 attr->Attr |= AttrReverse;
2073     mask->Attr |= AttrReverse;
2074 maya 3227 break;
2075    
2076 doda 6173 case 22: /* Bold off */
2077 doda 5095 attr->Attr &= ~ AttrBold;
2078     mask->Attr |= AttrBold;
2079 maya 3227 break;
2080    
2081 doda 6173 case 24: /* Under line off */
2082 doda 5095 attr->Attr &= ~ AttrUnder;
2083     mask->Attr |= AttrUnder;
2084 maya 3227 break;
2085    
2086 doda 6173 case 25: /* Blink off */
2087 doda 5095 attr->Attr &= ~ AttrBlink;
2088     mask->Attr |= AttrBlink;
2089 maya 3227 break;
2090    
2091 doda 6173 case 27: /* Reverse off */
2092 doda 5095 attr->Attr &= ~ AttrReverse;
2093     mask->Attr |= AttrReverse;
2094 maya 3227 break;
2095    
2096 doda 6173 case 30:
2097     case 31:
2098     case 32:
2099     case 33:
2100     case 34:
2101     case 35:
2102     case 36:
2103     case 37: /* text color */
2104 doda 5095 attr->Attr2 |= Attr2Fore;
2105     mask->Attr2 |= Attr2Fore;
2106     attr->Fore = P - 30;
2107 maya 3227 break;
2108    
2109 doda 6173 case 38: /* text color (256color mode) */
2110 doda 5073 if (ts.ColorFlag & CF_XTERM256) {
2111     /*
2112     * Change foreground color. accept following formats.
2113     *
2114     * 38 ; 2 ; r ; g ; b
2115     * 38 ; 2 : r : g : b
2116     * 38 : 2 : r : g : b
2117     * 38 ; 5 ; idx
2118     * 38 ; 5 : idx
2119     * 38 : 5 : idx
2120     *
2121     */
2122     color = -1;
2123     j = 0;
2124     if (NSParam[i] > 0) {
2125     P = SubParam[i][1];
2126     j++;
2127     }
2128     else if (i < NParam) {
2129     P = Param[i+1];
2130     if (P == 2 || P == 5) {
2131     i++;
2132     }
2133     }
2134     switch (P) {
2135 doda 6173 case 2:
2136 doda 5073 r = g = b = 0;
2137     if (NSParam[i] > 0) {
2138     if (j < NSParam[i]) {
2139     r = SubParam[i][++j];
2140     if (j < NSParam[i]) {
2141     g = SubParam[i][++j];
2142     }
2143     if (j < NSParam[i]) {
2144     b = SubParam[i][++j];
2145     }
2146     color = DispFindClosestColor(r, g, b);
2147     }
2148     }
2149     else if (i < NParam && NSParam[i+1] > 0) {
2150     r = Param[++i];
2151     g = SubParam[i][1];
2152     if (NSParam[i] > 1) {
2153     b = SubParam[i][2];
2154     }
2155     color = DispFindClosestColor(r, g, b);
2156     }
2157     else if (i+2 < NParam) {
2158     r = Param[++i];
2159     g = Param[++i];
2160     b = Param[++i];
2161     color = DispFindClosestColor(r, g, b);
2162     }
2163     break;
2164 doda 6173 case 5:
2165 doda 5073 if (NSParam[i] > 0) {
2166     if (j < NSParam[i]) {
2167     color = SubParam[i][++j];
2168     }
2169     }
2170     else if (i < NParam) {
2171     color = Param[++i];
2172     }
2173     break;
2174     }
2175 doda 5077 if (color >= 0 && color < 256) {
2176 doda 5095 attr->Attr2 |= Attr2Fore;
2177     mask->Attr2 |= Attr2Fore;
2178     attr->Fore = color;
2179 maya 3227 }
2180     }
2181     break;
2182    
2183 doda 6173 case 39: /* Reset text color */
2184 doda 5095 attr->Attr2 &= ~ Attr2Fore;
2185     mask->Attr2 |= Attr2Fore;
2186     attr->Fore = AttrDefaultFG;
2187 maya 3227 break;
2188    
2189 doda 6173 case 40:
2190     case 41:
2191     case 42:
2192     case 43:
2193     case 44:
2194     case 45:
2195     case 46:
2196     case 47: /* Back color */
2197 doda 5095 attr->Attr2 |= Attr2Back;
2198     mask->Attr2 |= Attr2Back;
2199     attr->Back = P - 40;
2200 maya 3227 break;
2201    
2202 doda 6173 case 48: /* Back color (256color mode) */
2203 doda 5073 if (ts.ColorFlag & CF_XTERM256) {
2204     color = -1;
2205     j = 0;
2206     if (NSParam[i] > 0) {
2207     P = SubParam[i][1];
2208     j++;
2209     }
2210     else if (i < NParam) {
2211     P = Param[i+1];
2212     if (P == 2 || P == 5) {
2213     i++;
2214     }
2215     }
2216     switch (P) {
2217 doda 6173 case 2:
2218 doda 5073 r = g = b = 0;
2219     if (NSParam[i] > 0) {
2220     if (j < NSParam[i]) {
2221     r = SubParam[i][++j];
2222     if (j < NSParam[i]) {
2223     g = SubParam[i][++j];
2224     }
2225     if (j < NSParam[i]) {
2226     b = SubParam[i][++j];
2227     }
2228     color = DispFindClosestColor(r, g, b);
2229     }
2230     }
2231     else if (i < NParam && NSParam[i+1] > 0) {
2232     r = Param[++i];
2233     g = SubParam[i][1];
2234     if (NSParam[i] > 1) {
2235     b = SubParam[i][2];
2236     }
2237     color = DispFindClosestColor(r, g, b);
2238     }
2239     else if (i+2 < NParam) {
2240     r = Param[++i];
2241     g = Param[++i];
2242     b = Param[++i];
2243     color = DispFindClosestColor(r, g, b);
2244     }
2245     break;
2246 doda 6173 case 5:
2247 doda 5073 if (NSParam[i] > 0) {
2248     if (j < NSParam[i]) {
2249     color = SubParam[i][++j];
2250     }
2251     }
2252     else if (i < NParam) {
2253     color = Param[++i];
2254     }
2255     break;
2256     }
2257 doda 5077 if (color >= 0 && color < 256) {
2258 doda 5095 attr->Attr2 |= Attr2Back;
2259     mask->Attr2 |= Attr2Back;
2260     attr->Back = color;
2261 maya 3227 }
2262     }
2263     break;
2264    
2265 doda 6173 case 49: /* Reset back color */
2266 doda 5095 attr->Attr2 &= ~ Attr2Back;
2267     mask->Attr2 |= Attr2Back;
2268     attr->Back = AttrDefaultBG;
2269 maya 3227 break;
2270    
2271 doda 6173 case 90:
2272     case 91:
2273     case 92:
2274     case 93:
2275     case 94:
2276     case 95:
2277     case 96:
2278     case 97: /* aixterm style text color */
2279 maya 3227 if (ts.ColorFlag & CF_AIXTERM16) {
2280 doda 5095 attr->Attr2 |= Attr2Fore;
2281     mask->Attr2 |= Attr2Fore;
2282     attr->Fore = P - 90 + 8;
2283 maya 3227 }
2284     break;
2285    
2286 doda 6173 case 100:
2287 maya 3227 if (! (ts.ColorFlag & CF_AIXTERM16)) {
2288     /* Reset text and back color */
2289 doda 5095 attr->Attr2 &= ~ (Attr2Fore | Attr2Back);
2290     mask->Attr2 |= Attr2ColorMask;
2291     attr->Fore = AttrDefaultFG;
2292     attr->Back = AttrDefaultBG;
2293 maya 3227 break;
2294     }
2295     /* fall through to aixterm style back color */
2296    
2297 doda 6173 case 101:
2298     case 102:
2299     case 103:
2300     case 104:
2301     case 105:
2302     case 106:
2303     case 107: /* aixterm style back color */
2304 maya 3227 if (ts.ColorFlag & CF_AIXTERM16) {
2305 doda 5095 attr->Attr2 |= Attr2Back;
2306     mask->Attr2 |= Attr2Back;
2307     attr->Back = P - 100 + 8;
2308 maya 3227 }
2309     break;
2310     }
2311     }
2312     }
2313    
2314 doda 5095 void CSSetAttr() // SGR
2315     {
2316     UpdateStr();
2317     ParseSGRParams(&CharAttr, NULL, 1);
2318     BuffSetCurCharAttr(CharAttr);
2319     }
2320    
2321 doda 6173 void CSSetScrollRegion() // DECSTBM
2322     {
2323     if (isCursorOnStatusLine) {
2324     MoveCursor(0,CursorY);
2325     return;
2326     }
2327 doda 6174
2328     RequiredParams(2);
2329     CheckParamVal(Param[1], NumOfLines-StatusLine);
2330     CheckParamValMax(Param[2], NumOfLines-StatusLine);
2331    
2332     if (Param[1] >= Param[2])
2333     return;
2334    
2335     CursorTop = Param[1] - 1;
2336     CursorBottom = Param[2] - 1;
2337    
2338     if (RelativeOrgMode)
2339     // TODO: ���}�[�W���������������B�v���@�m�F�B
2340     MoveCursor(0, CursorTop);
2341     else
2342     MoveCursor(0, 0);
2343 doda 6173 }
2344 maya 3227
2345 doda 5502 void CSSetLRScrollRegion() // DECSLRM
2346 doda 5324 {
2347 doda 6174 // TODO: �X�e�[�^�X���C�������������m�F�B
2348 doda 5324 // if (isCursorOnStatusLine) {
2349     // MoveCursor(0,CursorY);
2350     // return;
2351     // }
2352    
2353 doda 6174 RequiredParams(2);
2354     CheckParamVal(Param[1], NumOfColumns);
2355     CheckParamValMax(Param[2], NumOfColumns);
2356 doda 5324
2357     if (Param[1] >= Param[2])
2358     return;
2359    
2360 doda 6174 CursorLeftM = Param[1] - 1;
2361     CursorRightM = Param[2] - 1;
2362 doda 5324
2363     if (RelativeOrgMode)
2364     MoveCursor(CursorLeftM, CursorTop);
2365     else
2366     MoveCursor(0, 0);
2367     }
2368    
2369 doda 6173 void CSSunSequence() /* Sun terminal private sequences */
2370     {
2371     int x, y, len;
2372     char Report[TitleBuffSize*2+10];
2373     PTStack t;
2374 maya 3227
2375 doda 6173 switch (Param[1]) {
2376     case 1: // De-iconify window
2377     if (ts.WindowFlag & WF_WINDOWCHANGE)
2378     DispShowWindow(WINDOW_RESTORE);
2379     break;
2380 doda 6174
2381 doda 6173 case 2: // Iconify window
2382     if (ts.WindowFlag & WF_WINDOWCHANGE)
2383     DispShowWindow(WINDOW_MINIMIZE);
2384     break;
2385 doda 6174
2386 doda 6173 case 3: // set window position
2387     if (ts.WindowFlag & WF_WINDOWCHANGE) {
2388 doda 6174 RequiredParams(3);
2389 doda 6173 DispMoveWindow(Param[2], Param[3]);
2390     }
2391     break;
2392 doda 6174
2393 doda 6173 case 4: // set window size
2394     if (ts.WindowFlag & WF_WINDOWCHANGE) {
2395 doda 6174 RequiredParams(3);
2396 doda 6173 DispResizeWin(Param[3], Param[2]);
2397     }
2398     break;
2399 doda 6174
2400 doda 6173 case 5: // Raise window
2401     if (ts.WindowFlag & WF_WINDOWCHANGE)
2402     DispShowWindow(WINDOW_RAISE);
2403     break;
2404 doda 6174
2405 doda 6173 case 6: // Lower window
2406     if (ts.WindowFlag & WF_WINDOWCHANGE)
2407     DispShowWindow(WINDOW_LOWER);
2408     break;
2409 doda 6174
2410 doda 6173 case 7: // Refresh window
2411     if (ts.WindowFlag & WF_WINDOWCHANGE)
2412     DispShowWindow(WINDOW_REFRESH);
2413     break;
2414 doda 6174
2415 doda 6173 case 8: /* set terminal size */
2416     if (ts.WindowFlag & WF_WINDOWCHANGE) {
2417 doda 6174 RequiredParams(3);
2418     if (Param[2] <= 1) Param[2] = 24;
2419     if (Param[3] <= 1) Param[3] = 80;
2420     ChangeTerminalSize(Param[3], Param[2]);
2421 doda 6173 }
2422     break;
2423 doda 6174
2424 doda 6173 case 9: // Maximize/Restore window
2425     if (ts.WindowFlag & WF_WINDOWCHANGE) {
2426 doda 6174 RequiredParams(2);
2427     if (Param[2] == 0) {
2428 doda 6173 DispShowWindow(WINDOW_RESTORE);
2429     }
2430     else if (Param[2] == 1) {
2431     DispShowWindow(WINDOW_MAXIMIZE);
2432     }
2433     }
2434     break;
2435 doda 6174
2436 doda 7274 case 10: // Full-screen
2437     /*
2438     * �{�������� PuTTY ���������t���X�N���[�����[�h�������������������A
2439     * �������������������������������p����
2440     */
2441     if (ts.WindowFlag & WF_WINDOWCHANGE) {
2442     RequiredParams(2);
2443     switch (Param[2]) {
2444     case 0:
2445     DispShowWindow(WINDOW_RESTORE);
2446     break;
2447     case 1:
2448     DispShowWindow(WINDOW_MAXIMIZE);
2449     break;
2450     case 2:
2451     DispShowWindow(WINDOW_TOGGLE_MAXIMIZE);
2452     break;
2453     }
2454     }
2455     break;
2456    
2457 doda 6173 case 11: // Report window state
2458     if (ts.WindowFlag & WF_WINDOWREPORT) {
2459     len = _snprintf_s_l(Report, sizeof(Report), _TRUNCATE, "%dt", CLocale, DispWindowIconified()?2:1);
2460     SendCSIstr(Report, len);
2461     }
2462     break;
2463 doda 6174
2464 doda 6173 case 13: // Report window position
2465     if (ts.WindowFlag & WF_WINDOWREPORT) {
2466 doda 7271 RequiredParams(2);
2467     switch (Param[2]) {
2468     case 0:
2469     case 1:
2470     DispGetWindowPos(&x, &y, FALSE);
2471     break;
2472     case 2:
2473     DispGetWindowPos(&x, &y, TRUE);
2474     break;
2475