aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPascal Bellard <pascal.bellard@ads-lu.com>2010-06-23 20:25:00 +0200
committerDenys Vlasenko <vda.linux@googlemail.com>2010-06-23 20:25:00 +0200
commit1b8e2b0e7620c5f80d93f4b7a5a225afe76c65da (patch)
treeddaf5994b778be19a57e69a5879611e138ec3208
parent64606c6d01f5b86b62541b12dd4f475635d47270 (diff)
downloadbusybox-w32-1b8e2b0e7620c5f80d93f4b7a5a225afe76c65da.tar.gz
busybox-w32-1b8e2b0e7620c5f80d93f4b7a5a225afe76c65da.tar.bz2
busybox-w32-1b8e2b0e7620c5f80d93f4b7a5a225afe76c65da.zip
conspy: code shrink ~200 bytes
Signed-off-by: Pascal Bellard <pascal.bellard@ads-lu.com> Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
-rw-r--r--miscutils/conspy.c87
1 files changed, 42 insertions, 45 deletions
diff --git a/miscutils/conspy.c b/miscutils/conspy.c
index ae471a3fa..0a5fdccad 100644
--- a/miscutils/conspy.c
+++ b/miscutils/conspy.c
@@ -63,6 +63,12 @@ struct globals {
63 unsigned width; 63 unsigned width;
64 unsigned height; 64 unsigned height;
65 char last_attr; 65 char last_attr;
66 int ioerror_count;
67 int key_count;
68 int escape_count;
69 int nokeys;
70 int current;
71 int vcsa_fd;
66 struct screen_info info; 72 struct screen_info info;
67 struct termios term_orig; 73 struct termios term_orig;
68}; 74};
@@ -83,11 +89,12 @@ enum {
83#define FLAG(x) (1 << FLAG_##x) 89#define FLAG(x) (1 << FLAG_##x)
84#define BW (option_mask32 & FLAG(n)) 90#define BW (option_mask32 & FLAG(n))
85 91
86static void screen_read_close(int fd, char *data) 92static void screen_read_close(void)
87{ 93{
88 unsigned i, j; 94 unsigned i, j;
95 char *data = G.data + G.current;
89 96
90 xread(fd, data, G.size); 97 xread(G.vcsa_fd, data, G.size);
91 G.last_attr = 0; 98 G.last_attr = 0;
92 for (i = 0; i < G.info.lines; i++) { 99 for (i = 0; i < G.info.lines; i++) {
93 for (j = 0; j < G.info.rows; j++, NEXT(data)) { 100 for (j = 0; j < G.info.rows; j++, NEXT(data)) {
@@ -100,7 +107,7 @@ static void screen_read_close(int fd, char *data)
100 DATA(data) = 0; 107 DATA(data) = 0;
101 } 108 }
102 } 109 }
103 close(fd); 110 close(G.vcsa_fd);
104} 111}
105 112
106static void screen_char(char *data) 113static void screen_char(char *data)
@@ -131,13 +138,13 @@ static void gotoxy(int row, int line)
131 printf("\033[%u;%uH", line + 1, row + 1); 138 printf("\033[%u;%uH", line + 1, row + 1);
132} 139}
133 140
134static void screen_dump(char *data) 141static void screen_dump(void)
135{ 142{
136 int linefeed_cnt; 143 int linefeed_cnt;
137 int line, row; 144 int line, row;
138 int linecnt = G.info.lines - G.y; 145 int linecnt = G.info.lines - G.y;
146 char *data = G.data + G.current + (2 * G.y * G.info.rows);
139 147
140 data += 2 * G.y * G.info.rows;
141 linefeed_cnt = 0; 148 linefeed_cnt = 0;
142 for (line = 0; line < linecnt && line < G.height; line++) { 149 for (line = 0; line < linecnt && line < G.height; line++) {
143 int space_cnt = 0; 150 int space_cnt = 0;
@@ -197,12 +204,12 @@ static void cleanup(int code)
197static void get_initial_data(const char* vcsa_name) 204static void get_initial_data(const char* vcsa_name)
198{ 205{
199 int size; 206 int size;
200 int fd = xopen(vcsa_name, O_RDONLY); 207 G.vcsa_fd = xopen(vcsa_name, O_RDONLY);
201 xread(fd, &G.info, 4); 208 xread(G.vcsa_fd, &G.info, 4);
202 G.size = size = G.info.rows * G.info.lines * 2; 209 G.size = size = G.info.rows * G.info.lines * 2;
203 G.width = G.height = UINT_MAX; 210 G.width = G.height = UINT_MAX;
204 G.data = xzalloc(2 * size); 211 G.data = xzalloc(2 * size);
205 screen_read_close(fd, G.data); 212 screen_read_close();
206} 213}
207 214
208static void create_cdev_if_doesnt_exist(const char* name, dev_t dev) 215static void create_cdev_if_doesnt_exist(const char* name, dev_t dev)
@@ -250,7 +257,6 @@ static NOINLINE void start_shell_in_child(const char* tty_name)
250int conspy_main(int argc UNUSED_PARAM, char **argv) MAIN_EXTERNALLY_VISIBLE; 257int conspy_main(int argc UNUSED_PARAM, char **argv) MAIN_EXTERNALLY_VISIBLE;
251int conspy_main(int argc UNUSED_PARAM, char **argv) 258int conspy_main(int argc UNUSED_PARAM, char **argv)
252{ 259{
253 char *buffer[2];
254 char vcsa_name[sizeof("/dev/vcsa") + 2]; 260 char vcsa_name[sizeof("/dev/vcsa") + 2];
255 char tty_name[sizeof("/dev/tty") + 2]; 261 char tty_name[sizeof("/dev/tty") + 2];
256#define keybuf bb_common_bufsiz1 262#define keybuf bb_common_bufsiz1
@@ -258,11 +264,6 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
258 unsigned opts; 264 unsigned opts;
259 unsigned ttynum; 265 unsigned ttynum;
260 int poll_timeout_ms; 266 int poll_timeout_ms;
261 int current;
262 int ioerror_count;
263 int key_count;
264 int escape_count;
265 int nokeys;
266#if ENABLE_LONG_OPTS 267#if ENABLE_LONG_OPTS
267 static const char getopt_longopts[] ALIGN1 = 268 static const char getopt_longopts[] ALIGN1 =
268 "viewonly\0" No_argument "v" 269 "viewonly\0" No_argument "v"
@@ -276,7 +277,6 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
276 applet_long_options = getopt_longopts; 277 applet_long_options = getopt_longopts;
277#endif 278#endif
278 INIT_G(); 279 INIT_G();
279 strcpy(vcsa_name, "/dev/vcsa");
280 280
281 opt_complementary = "x+:y+"; // numeric params 281 opt_complementary = "x+:y+"; // numeric params
282 opts = getopt32(argv, "vcsndfx:y:", &G.x, &G.y); 282 opts = getopt32(argv, "vcsndfx:y:", &G.x, &G.y);
@@ -284,8 +284,8 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
284 ttynum = 0; 284 ttynum = 0;
285 if (argv[0]) { 285 if (argv[0]) {
286 ttynum = xatou_range(argv[0], 0, 63); 286 ttynum = xatou_range(argv[0], 0, 63);
287 sprintf(vcsa_name + sizeof("/dev/vcsa")-1, "%u", ttynum);
288 } 287 }
288 sprintf(vcsa_name, "/dev/vcsa%u", ttynum);
289 sprintf(tty_name, "%s%u", "/dev/tty", ttynum); 289 sprintf(tty_name, "%s%u", "/dev/tty", ttynum);
290 if (opts & FLAG(c)) { 290 if (opts & FLAG(c)) {
291 if ((opts & (FLAG(s)|FLAG(v))) != FLAG(v)) 291 if ((opts & (FLAG(s)|FLAG(v))) != FLAG(v))
@@ -299,7 +299,7 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
299 get_initial_data(vcsa_name); 299 get_initial_data(vcsa_name);
300 G.kbd_fd = xopen(CURRENT_TTY, O_RDONLY); 300 G.kbd_fd = xopen(CURRENT_TTY, O_RDONLY);
301 if (opts & FLAG(d)) { 301 if (opts & FLAG(d)) {
302 screen_dump(G.data); 302 screen_dump();
303 bb_putchar('\n'); 303 bb_putchar('\n');
304 if (ENABLE_FEATURE_CLEAN_UP) { 304 if (ENABLE_FEATURE_CLEAN_UP) {
305 free(ptr_to_globals); 305 free(ptr_to_globals);
@@ -318,23 +318,21 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
318 termbuf.c_cc[VMIN] = 1; 318 termbuf.c_cc[VMIN] = 1;
319 termbuf.c_cc[VTIME] = 0; 319 termbuf.c_cc[VTIME] = 0;
320 tcsetattr(G.kbd_fd, TCSANOW, &termbuf); 320 tcsetattr(G.kbd_fd, TCSANOW, &termbuf);
321 buffer[0] = G.data;
322 buffer[1] = G.data + G.size;
323 poll_timeout_ms = 250; 321 poll_timeout_ms = 250;
324 ioerror_count = key_count = escape_count = nokeys = current = 0;
325 while (1) { 322 while (1) {
326 struct pollfd pfd; 323 struct pollfd pfd;
327 int vcsa_handle;
328 int bytes_read; 324 int bytes_read;
329 int i, j; 325 int i, j;
330 int next = 1 - current; 326 char *data, *old;
331 char *data = buffer[next];
332 char *old = buffer[current];
333 327
328 old = G.data + G.current;
329 G.current = G.size - G.current;
330 data = G.data + G.current;
331
334 // Close & re-open vcsa in case they have 332 // Close & re-open vcsa in case they have
335 // swapped virtual consoles 333 // swapped virtual consoles
336 vcsa_handle = xopen(vcsa_name, O_RDONLY); 334 G.vcsa_fd = xopen(vcsa_name, O_RDONLY);
337 xread(vcsa_handle, &G.info, 4); 335 xread(G.vcsa_fd, &G.info, 4);
338 if (G.size != (G.info.rows * G.info.lines * 2)) { 336 if (G.size != (G.info.rows * G.info.lines * 2)) {
339 cleanup(1); 337 cleanup(1);
340 } 338 }
@@ -364,10 +362,10 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
364 } 362 }
365 363
366 // Scan console data and redraw our tty where needed 364 // Scan console data and redraw our tty where needed
367 screen_read_close(vcsa_handle, data); 365 screen_read_close();
368 if (i != G.width || j != G.height) { 366 if (i != G.width || j != G.height) {
369 clrscr(); 367 clrscr();
370 screen_dump(data); 368 screen_dump();
371 } 369 }
372 else for (i = 0; i < G.info.lines; i++) { 370 else for (i = 0; i < G.info.lines; i++) {
373 char *last = last; 371 char *last = last;
@@ -399,7 +397,6 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
399 for (; first < last; NEXT(first)) 397 for (; first < last; NEXT(first))
400 screen_char(first); 398 screen_char(first);
401 } 399 }
402 current = next;
403 curmove(); 400 curmove();
404 401
405 // Wait for local user keypresses 402 // Wait for local user keypresses
@@ -407,26 +404,26 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
407 pfd.events = POLLIN; 404 pfd.events = POLLIN;
408 bytes_read = 0; 405 bytes_read = 0;
409 switch (poll(&pfd, 1, poll_timeout_ms)) { 406 switch (poll(&pfd, 1, poll_timeout_ms)) {
407 char *k;
410 case -1: 408 case -1:
411 if (errno != EINTR) 409 if (errno != EINTR)
412 cleanup(1); 410 cleanup(1);
413 break; 411 break;
414 case 0: 412 case 0:
415 if (++nokeys >= 4) 413 if (++G.nokeys >= 4)
416 nokeys = escape_count = 0; 414 G.nokeys = G.escape_count = 0;
417 break; 415 break;
418 default: 416 default:
419 // Read the keys pressed 417 // Read the keys pressed
420 bytes_read = read(G.kbd_fd, keybuf + key_count, 418 k = keybuf + G.key_count;
421 sizeof(keybuf) - key_count); 419 bytes_read = read(G.kbd_fd, k, sizeof(keybuf) - G.key_count);
422 if (bytes_read < 0) 420 if (bytes_read < 0)
423 cleanup(1); 421 cleanup(1);
424 422
425 // Do exit processing 423 // Do exit processing
426 for (i = 0; i < bytes_read; i++) { 424 for (i = 0; i < bytes_read; i++) {
427 if (keybuf[key_count + i] != '\033') 425 if (k[i] != '\033') G.escape_count = 0;
428 escape_count = 0; 426 else if (++G.escape_count >= 3)
429 else if (++escape_count >= 3)
430 cleanup(0); 427 cleanup(0);
431 } 428 }
432 } 429 }
@@ -436,23 +433,23 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
436 // buffer. Don't do this if the virtual console is in scan 433 // buffer. Don't do this if the virtual console is in scan
437 // code mode - giving ASCII characters to a program expecting 434 // code mode - giving ASCII characters to a program expecting
438 // scan codes will confuse it. 435 // scan codes will confuse it.
439 if (!(option_mask32 & FLAG(v)) && escape_count == 0) { 436 if (!(option_mask32 & FLAG(v)) && G.escape_count == 0) {
440 int handle, result; 437 int handle, result;
441 long kbd_mode; 438 long kbd_mode;
442 439
443 key_count += bytes_read; 440 G.key_count += bytes_read;
444 handle = xopen(tty_name, O_WRONLY); 441 handle = xopen(tty_name, O_WRONLY);
445 result = ioctl(handle, KDGKBMODE, &kbd_mode); 442 result = ioctl(handle, KDGKBMODE, &kbd_mode);
446 if (result == -1) 443 if (result == -1)
447 /* nothing */; 444 /* nothing */;
448 else if (kbd_mode != K_XLATE && kbd_mode != K_UNICODE) 445 else if (kbd_mode != K_XLATE && kbd_mode != K_UNICODE)
449 key_count = 0; // scan code mode 446 G.key_count = 0; // scan code mode
450 else { 447 else {
451 for (i = 0; i < key_count && result != -1; i++) 448 for (i = 0; i < G.key_count && result != -1; i++)
452 result = ioctl(handle, TIOCSTI, keybuf + i); 449 result = ioctl(handle, TIOCSTI, keybuf + i);
453 key_count -= i; 450 G.key_count -= i;
454 if (key_count) 451 if (G.key_count)
455 memmove(keybuf, keybuf + i, key_count); 452 memmove(keybuf, keybuf + i, G.key_count);
456 // If there is an application on console which reacts 453 // If there is an application on console which reacts
457 // to keypresses, we need to make our first sleep 454 // to keypresses, we need to make our first sleep
458 // shorter to quickly redraw whatever it printed there. 455 // shorter to quickly redraw whatever it printed there.
@@ -465,8 +462,8 @@ int conspy_main(int argc UNUSED_PARAM, char **argv)
465 // We sometimes get spurious IO errors on the TTY 462 // We sometimes get spurious IO errors on the TTY
466 // as programs close and re-open it 463 // as programs close and re-open it
467 if (result != -1) 464 if (result != -1)
468 ioerror_count = 0; 465 G.ioerror_count = 0;
469 else if (errno != EIO || ++ioerror_count > 4) 466 else if (errno != EIO || ++G.ioerror_count > 4)
470 cleanup(1); 467 cleanup(1);
471 } 468 }
472 } 469 }