Annotation of src/usr.bin/less/ttyin.c, Revision 1.6
1.1 etheisen 1: /*
1.6 ! shadchin 2: * Copyright (C) 1984-2012 Mark Nudelman
1.1 etheisen 3: *
1.3 millert 4: * You may distribute under the terms of either the GNU General Public
5: * License or the Less License, as specified in the README file.
1.1 etheisen 6: *
1.6 ! shadchin 7: * For more information, see the README file.
1.1 etheisen 8: */
9:
10:
11: /*
12: * Routines dealing with getting input from the keyboard (i.e. from the user).
13: */
14:
15: #include "less.h"
1.3 millert 16: #if OS2
17: #include "cmd.h"
18: #include "pckeys.h"
19: #endif
20: #if MSDOS_COMPILER==WIN32C
21: #include "windows.h"
22: extern char WIN32getch();
23: static DWORD console_mode;
24: #endif
1.1 etheisen 25:
1.3 millert 26: public int tty;
1.5 millert 27: extern volatile sig_atomic_t sigs;
1.4 shadchin 28: extern int utf_mode;
1.1 etheisen 29:
30: /*
31: * Open keyboard for input.
32: */
33: public void
34: open_getchr()
35: {
1.3 millert 36: #if MSDOS_COMPILER==WIN32C
37: /* Need this to let child processes inherit our console handle */
38: SECURITY_ATTRIBUTES sa;
39: memset(&sa, 0, sizeof(SECURITY_ATTRIBUTES));
40: sa.nLength = sizeof(SECURITY_ATTRIBUTES);
41: sa.bInheritHandle = TRUE;
42: tty = (int) CreateFile("CONIN$", GENERIC_READ,
43: FILE_SHARE_READ, &sa,
44: OPEN_EXISTING, 0L, NULL);
45: GetConsoleMode((HANDLE)tty, &console_mode);
46: /* Make sure we get Ctrl+C events. */
47: SetConsoleMode((HANDLE)tty, ENABLE_PROCESSED_INPUT);
48: #else
49: #if MSDOS_COMPILER
1.1 etheisen 50: extern int fd0;
51: /*
52: * Open a new handle to CON: in binary mode
53: * for unbuffered keyboard read.
54: */
55: fd0 = dup(0);
56: close(0);
1.3 millert 57: tty = open("CON", OPEN_READ);
58: #if MSDOS_COMPILER==DJGPPC
59: /*
60: * Setting stdin to binary causes Ctrl-C to not
61: * raise SIGINT. We must undo that side-effect.
62: */
63: (void) __djgpp_set_ctrl_c(1);
64: #endif
1.1 etheisen 65: #else
66: /*
67: * Try /dev/tty.
68: * If that doesn't work, use file descriptor 2,
69: * which in Unix is usually attached to the screen,
70: * but also usually lets you read from the keyboard.
71: */
1.3 millert 72: #if OS2
73: /* The __open() system call translates "/dev/tty" to "con". */
74: tty = __open("/dev/tty", OPEN_READ);
75: #else
76: tty = open("/dev/tty", OPEN_READ);
77: #endif
1.1 etheisen 78: if (tty < 0)
79: tty = 2;
80: #endif
1.3 millert 81: #endif
82: }
83:
84: /*
85: * Close the keyboard.
86: */
87: public void
88: close_getchr()
89: {
90: #if MSDOS_COMPILER==WIN32C
91: SetConsoleMode((HANDLE)tty, console_mode);
92: CloseHandle((HANDLE)tty);
93: #endif
1.1 etheisen 94: }
95:
96: /*
97: * Get a character from the keyboard.
98: */
99: public int
100: getchr()
101: {
102: char c;
103: int result;
104:
105: do
106: {
1.3 millert 107: #if MSDOS_COMPILER && MSDOS_COMPILER != DJGPPC
1.1 etheisen 108: /*
109: * In raw read, we don't see ^C so look here for it.
110: */
111: flush();
1.3 millert 112: #if MSDOS_COMPILER==WIN32C
113: if (ABORT_SIGS())
114: return (READ_INTR);
115: c = WIN32getch(tty);
116: #else
1.1 etheisen 117: c = getch();
1.3 millert 118: #endif
1.1 etheisen 119: result = 1;
120: if (c == '\003')
121: return (READ_INTR);
122: #else
123: result = iread(tty, &c, sizeof(char));
124: if (result == READ_INTR)
125: return (READ_INTR);
126: if (result < 0)
127: {
128: /*
129: * Don't call error() here,
130: * because error calls getchr!
131: */
132: quit(QUIT_ERROR);
133: }
134: #endif
1.4 shadchin 135: #if 0 /* allow entering arbitrary hex chars for testing */
136: /* ctrl-A followed by two hex chars makes a byte */
137: {
138: int hex_in = 0;
139: int hex_value = 0;
140: if (c == CONTROL('A'))
141: {
142: hex_in = 2;
143: result = 0;
144: continue;
145: }
146: if (hex_in > 0)
147: {
148: int v;
149: if (c >= '0' && c <= '9')
150: v = c - '0';
151: else if (c >= 'a' && c <= 'f')
152: v = c - 'a' + 10;
153: else if (c >= 'A' && c <= 'F')
154: v = c - 'A' + 10;
155: else
156: hex_in = 0;
157: hex_value = (hex_value << 4) | v;
158: if (--hex_in > 0)
159: {
160: result = 0;
161: continue;
162: }
163: c = hex_value;
164: }
165: }
166: #endif
1.1 etheisen 167: /*
168: * Various parts of the program cannot handle
169: * an input character of '\0'.
170: * If a '\0' was actually typed, convert it to '\340' here.
171: */
172: if (c == '\0')
173: c = '\340';
174: } while (result != 1);
175:
1.4 shadchin 176: return (c & 0xFF);
1.1 etheisen 177: }