1 /* 2 * Copyright (C) 2006 Michael Brown <mbrown@fensystems.co.uk>. 3 * 4 * This program is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU General Public License as 6 * published by the Free Software Foundation; either version 2 of the 7 * License, or any later version. 8 * 9 * This program is distributed in the hope that it will be useful, but 10 * WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 * General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program; if not, write to the Free Software 16 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 17 */ 18 19 FILE_LICENCE ( GPL2_OR_LATER ); 20 21 #include <ctype.h> 22 #include <console.h> 23 #include <gpxe/process.h> 24 #include <gpxe/keys.h> 25 #include <gpxe/timer.h> 26 27 /** @file 28 * 29 * Special key interpretation 30 * 31 */ 32 33 #define GETKEY_TIMEOUT ( TICKS_PER_SEC / 4 ) 34 35 /** 36 * Read character from console if available within timeout period 37 * 38 * @v timeout Timeout period, in ticks 39 * @ret character Character read from console 40 */ 41 static int getchar_timeout ( unsigned long timeout ) { 42 unsigned long expiry = ( currticks() + timeout ); 43 44 while ( currticks() < expiry ) { 45 step(); 46 if ( iskey() ) 47 return getchar(); 48 } 49 50 return -1; 51 } 52 53 /** 54 * Get single keypress 55 * 56 * @ret key Key pressed 57 * 58 * The returned key will be an ASCII value or a KEY_XXX special 59 * constant. This function differs from getchar() in that getchar() 60 * will return "special" keys (e.g. cursor keys) as a series of 61 * characters forming an ANSI escape sequence. 62 */ 63 int getkey ( void ) { 64 int character; 65 unsigned int n = 0; 66 67 character = getchar(); 68 if ( character != ESC ) 69 return character; 70 71 while ( ( character = getchar_timeout ( GETKEY_TIMEOUT ) ) >= 0 ) { 72 if ( character == '[' ) 73 continue; 74 if ( isdigit ( character ) ) { 75 n = ( ( n * 10 ) + ( character - '0' ) ); 76 continue; 77 } 78 if ( character >= 0x40 ) 79 return KEY_ANSI ( n, character ); 80 } 81 82 return ESC; 83 } 84