aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--st.c76
1 files changed, 56 insertions, 20 deletions
diff --git a/st.c b/st.c
index 8b18607..8bf9337 100644
--- a/st.c
+++ b/st.c
@@ -110,17 +110,18 @@ enum glyph_state {
110}; 110};
111 111
112enum term_mode { 112enum term_mode {
113 MODE_WRAP = 1, 113 MODE_WRAP = 1,
114 MODE_INSERT = 2, 114 MODE_INSERT = 2,
115 MODE_APPKEYPAD = 4, 115 MODE_APPKEYPAD = 4,
116 MODE_ALTSCREEN = 8, 116 MODE_ALTSCREEN = 8,
117 MODE_CRLF = 16, 117 MODE_CRLF = 16,
118 MODE_MOUSEBTN = 32, 118 MODE_MOUSEBTN = 32,
119 MODE_MOUSEMOTION = 64, 119 MODE_MOUSEMOTION = 64,
120 MODE_MOUSE = 32|64, 120 MODE_MOUSE = 32|64,
121 MODE_REVERSE = 128, 121 MODE_REVERSE = 128,
122 MODE_KBDLOCK = 256, 122 MODE_KBDLOCK = 256,
123 MODE_HIDE = 512 123 MODE_HIDE = 512,
124 MODE_ECHO = 1024
124}; 125};
125 126
126enum escape_state { 127enum escape_state {
@@ -320,6 +321,7 @@ static void tswapscreen(void);
320static void tsetdirt(int, int); 321static void tsetdirt(int, int);
321static void tsetmode(bool, bool, int *, int); 322static void tsetmode(bool, bool, int *, int);
322static void tfulldirt(void); 323static void tfulldirt(void);
324static void techo(char *, int);
323 325
324static void ttynew(void); 326static void ttynew(void);
325static void ttyread(void); 327static void ttyread(void);
@@ -1534,7 +1536,8 @@ tsetmode(bool priv, bool set, int *args, int narg) {
1534 case 4: /* IRM -- Insertion-replacement */ 1536 case 4: /* IRM -- Insertion-replacement */
1535 MODBIT(term.mode, set, MODE_INSERT); 1537 MODBIT(term.mode, set, MODE_INSERT);
1536 break; 1538 break;
1537 case 12: /* XXX: SRM -- Send/Receive */ 1539 case 12: /* SRM -- Send/Receive */
1540 MODBIT(term.mode, !set, MODE_ECHO);
1538 break; 1541 break;
1539 case 20: /* LNM -- Linefeed/new line */ 1542 case 20: /* LNM -- Linefeed/new line */
1540 MODBIT(term.mode, set, MODE_CRLF); 1543 MODBIT(term.mode, set, MODE_CRLF);
@@ -1849,6 +1852,28 @@ tputtab(bool forward) {
1849} 1852}
1850 1853
1851void 1854void
1855techo(char *buf, int len) {
1856 for(; len > 0; buf++, len--) {
1857 char c = *buf;
1858
1859 if(c == '\033') { /* escape */
1860 tputc("^", 1);
1861 tputc("[", 1);
1862 } else if (c < '\x20') { /* control code */
1863 if(c != '\n' && c != '\r' && c != '\t') {
1864 c |= '\x40';
1865 tputc("^", 1);
1866 }
1867 tputc(&c, 1);
1868 } else {
1869 break;
1870 }
1871 }
1872 if (len)
1873 tputc(buf, len);
1874}
1875
1876void
1852tputc(char *c, int len) { 1877tputc(char *c, int len) {
1853 uchar ascii = *c; 1878 uchar ascii = *c;
1854 bool control = ascii < '\x20' || ascii == 0177; 1879 bool control = ascii < '\x20' || ascii == 0177;
@@ -2679,7 +2704,7 @@ void
2679kpress(XEvent *ev) { 2704kpress(XEvent *ev) {
2680 XKeyEvent *e = &ev->xkey; 2705 XKeyEvent *e = &ev->xkey;
2681 KeySym ksym; 2706 KeySym ksym;
2682 char buf[32], *customkey; 2707 char xstr[31], buf[32], *customkey, *cp = buf;
2683 int len, meta, shift, i; 2708 int len, meta, shift, i;
2684 Status status; 2709 Status status;
2685 2710
@@ -2688,7 +2713,7 @@ kpress(XEvent *ev) {
2688 2713
2689 meta = e->state & Mod1Mask; 2714 meta = e->state & Mod1Mask;
2690 shift = e->state & ShiftMask; 2715 shift = e->state & ShiftMask;
2691 len = XmbLookupString(xw.xic, e, buf, sizeof(buf), &ksym, &status); 2716 len = XmbLookupString(xw.xic, e, xstr, sizeof(xstr), &ksym, &status);
2692 2717
2693 /* 1. shortcuts */ 2718 /* 1. shortcuts */
2694 for(i = 0; i < LEN(shortcuts); i++) { 2719 for(i = 0; i < LEN(shortcuts); i++) {
@@ -2702,7 +2727,8 @@ kpress(XEvent *ev) {
2702 2727
2703 /* 2. custom keys from config.h */ 2728 /* 2. custom keys from config.h */
2704 if((customkey = kmap(ksym, e->state))) { 2729 if((customkey = kmap(ksym, e->state))) {
2705 ttywrite(customkey, strlen(customkey)); 2730 len = strlen(customkey);
2731 memcpy(buf, customkey, len);
2706 /* 2. hardcoded (overrides X lookup) */ 2732 /* 2. hardcoded (overrides X lookup) */
2707 } else { 2733 } else {
2708 switch(ksym) { 2734 switch(ksym) {
@@ -2714,34 +2740,44 @@ kpress(XEvent *ev) {
2714 sprintf(buf, "\033%c%c", 2740 sprintf(buf, "\033%c%c",
2715 IS_SET(MODE_APPKEYPAD) ? 'O' : '[', 2741 IS_SET(MODE_APPKEYPAD) ? 'O' : '[',
2716 (shift ? "dacb":"DACB")[ksym - XK_Left]); 2742 (shift ? "dacb":"DACB")[ksym - XK_Left]);
2717 ttywrite(buf, 3); 2743 len = 3;
2718 break; 2744 break;
2719 case XK_Insert: 2745 case XK_Insert:
2720 if(shift) 2746 if(shift) {
2721 selpaste(); 2747 selpaste();
2748 return;
2749 }
2750 memcpy(buf, xstr, len);
2722 break; 2751 break;
2723 case XK_Return: 2752 case XK_Return:
2753 len = 0;
2724 if(meta) 2754 if(meta)
2725 ttywrite("\033", 1); 2755 *cp++ = '\033', len++;
2726 2756
2727 if(IS_SET(MODE_CRLF)) { 2757 *cp++ = '\r', len++;
2728 ttywrite("\r\n", 2); 2758
2729 } else { 2759 if(IS_SET(MODE_CRLF))
2730 ttywrite("\r", 1); 2760 *cp = '\n', len++;
2731 }
2732 break; 2761 break;
2733 /* 3. X lookup */ 2762 /* 3. X lookup */
2734 default: 2763 default:
2735 if(len > 0) { 2764 if(len == 0)
2736 if(meta && len == 1) 2765 return;
2737 ttywrite("\033", 1); 2766
2738 ttywrite(buf, len); 2767 if (len == 1 && meta)
2739 } 2768 *cp++ = '\033';
2769
2770 memcpy(cp, xstr, len);
2771 len = cp - buf + len;
2740 break; 2772 break;
2741 } 2773 }
2742 } 2774 }
2775 ttywrite(buf, len);
2776 if(IS_SET(MODE_ECHO))
2777 techo(buf, len);
2743} 2778}
2744 2779
2780
2745void 2781void
2746cmessage(XEvent *e) { 2782cmessage(XEvent *e) {
2747 /* See xembed specs 2783 /* See xembed specs