Skip to content

Commit

Permalink
[console] Allow usage to be defined independently for each console
Browse files Browse the repository at this point in the history
Add the concept of a "console usage", such as "standard output" or
"debug messages".  Allow usages to be associated with each console
independently.  For example, to send debugging output via the serial
port, while preventing it from appearing on the local console:

  #define CONSOLE_SERIAL CONSOLE_USAGE_ALL
  #define CONSOLE_PCBIOS ( CONSOLE_USAGE_ALL & ~CONSOLE_USAGE_DEBUG )

If no usages are explicitly specified, then a default set of usages
will be applied.  For example:

  #define CONSOLE_SERIAL

will have the same affect as

  #define CONSOLE_SERIAL CONSOLE_USAGE_ALL

Signed-off-by: Michael Brown <mcb30@ipxe.org>
  • Loading branch information
mcb30 committed Mar 26, 2012
1 parent b35d454 commit e024cd3
Show file tree
Hide file tree
Showing 11 changed files with 155 additions and 31 deletions.
9 changes: 9 additions & 0 deletions src/arch/i386/core/video_subr.c
Expand Up @@ -11,6 +11,14 @@
#include <ipxe/console.h>
#include <ipxe/init.h>
#include "vga.h"
#include <config/console.h>

/* Set default console usage if applicable */
#if ! ( defined ( CONSOLE_DIRECT_VGA ) && \
CONSOLE_EXPLICIT ( CONSOLE_DIRECT_VGA ) )
#undef CONSOLE_DIRECT_VGA
#define CONSOLE_DIRECT_VGA CONSOLE_USAGE_ALL
#endif

struct console_driver vga_console __console_driver;

Expand Down Expand Up @@ -97,6 +105,7 @@ static void vga_putc(int byte)
struct console_driver vga_console __console_driver = {
.putchar = vga_putc,
.disabled = 1,
.usage = CONSOLE_DIRECT_VGA,
};

struct init_fn video_init_fn __init_fn ( INIT_EARLY ) = {
Expand Down
8 changes: 8 additions & 0 deletions src/arch/i386/firmware/pcbios/bios_console.c
Expand Up @@ -23,6 +23,7 @@ FILE_LICENCE ( GPL2_OR_LATER );
#include <ipxe/console.h>
#include <ipxe/ansiesc.h>
#include <ipxe/keymap.h>
#include <config/console.h>

#define ATTR_BOLD 0x08

Expand All @@ -48,6 +49,12 @@ FILE_LICENCE ( GPL2_OR_LATER );

#define ATTR_DEFAULT ATTR_FCOL_WHITE

/* Set default console usage if applicable */
#if ! ( defined ( CONSOLE_PCBIOS ) && CONSOLE_EXPLICIT ( CONSOLE_PCBIOS ) )
#undef CONSOLE_PCBIOS
#define CONSOLE_PCBIOS CONSOLE_USAGE_ALL
#endif

/** Current character attribute */
static unsigned int bios_attr = ATTR_DEFAULT;

Expand Down Expand Up @@ -319,4 +326,5 @@ struct console_driver bios_console __console_driver = {
.putchar = bios_putchar,
.getchar = bios_getchar,
.iskey = bios_iskey,
.usage = CONSOLE_PCBIOS,
};
8 changes: 8 additions & 0 deletions src/arch/i386/interface/vmware/vmconsole.c
Expand Up @@ -29,10 +29,17 @@ FILE_LICENCE ( GPL2_OR_LATER );
#include <ipxe/lineconsole.h>
#include <ipxe/init.h>
#include <ipxe/guestrpc.h>
#include <config/console.h>

/** VMware logfile console buffer size */
#define VMCONSOLE_BUFSIZE 128

/* Set default console usage if applicable */
#if ! ( defined ( CONSOLE_VMWARE ) && CONSOLE_EXPLICIT ( CONSOLE_VMWARE ) )
#undef CONSOLE_VMWARE
#define CONSOLE_VMWARE CONSOLE_USAGE_ALL
#endif

/** VMware logfile console GuestRPC channel */
static int vmconsole_channel;

Expand Down Expand Up @@ -87,6 +94,7 @@ static void vmconsole_putchar ( int character ) {
struct console_driver vmconsole __console_driver = {
.putchar = vmconsole_putchar,
.disabled = 1,
.usage = CONSOLE_VMWARE,
};

/**
Expand Down
7 changes: 6 additions & 1 deletion src/core/console.c
Expand Up @@ -7,6 +7,9 @@

FILE_LICENCE ( GPL2_OR_LATER );

/** Current console usage */
int console_usage = CONSOLE_USAGE_STDOUT;

/**
* Write a single character to each console device.
*
Expand All @@ -26,7 +29,9 @@ void putchar ( int character ) {
putchar ( '\r' );

for_each_table_entry ( console, CONSOLES ) {
if ( ( ! console->disabled ) && console->putchar )
if ( ( ! console->disabled ) &&
( console_usage & console->usage ) &&
console->putchar )
console->putchar ( character );
}
}
Expand Down
54 changes: 38 additions & 16 deletions src/core/debug.c
Expand Up @@ -21,26 +21,48 @@ FILE_LICENCE ( GPL2_OR_LATER );
#include <stdio.h>
#include <stdint.h>
#include <stdarg.h>
#include <ipxe/io.h>
#include <ipxe/console.h>

/**
* Print debug message
*
* @v fmt Format string
* @v ... Arguments
*/
void dbg_printf ( const char *fmt, ... ) {
int saved_usage;
va_list args;

/* Mark console as in use for debugging messages */
saved_usage = console_set_usage ( CONSOLE_USAGE_DEBUG );

/* Print message */
va_start ( args, fmt );
vprintf ( fmt, args );
va_end ( args );

/* Restore console usage */
console_set_usage ( saved_usage );
}

/**
* Pause until a key is pressed
*
*/
void dbg_pause ( void ) {
printf ( "\nPress a key..." );
dbg_printf ( "\nPress a key..." );
getchar();
printf ( "\r \r" );
dbg_printf ( "\r \r" );
}

/**
* Indicate more data to follow and pause until a key is pressed
*
*/
void dbg_more ( void ) {
printf ( "---more---" );
dbg_printf ( "---more---" );
getchar();
printf ( "\r \r" );
dbg_printf ( "\r \r" );
}

/**
Expand All @@ -57,27 +79,27 @@ static void dbg_hex_dump_da_row ( unsigned long dispaddr, const void *data,
unsigned int i;
uint8_t byte;

printf ( "%08lx :", ( dispaddr + offset ) );
dbg_printf ( "%08lx :", ( dispaddr + offset ) );
for ( i = offset ; i < ( offset + 16 ) ; i++ ) {
if ( i >= len ) {
printf ( " " );
dbg_printf ( " " );
continue;
}
printf ( "%c%02x",
( ( ( i % 16 ) == 8 ) ? '-' : ' ' ), bytes[i] );
dbg_printf ( "%c%02x",
( ( ( i % 16 ) == 8 ) ? '-' : ' ' ), bytes[i] );
}
printf ( " : " );
dbg_printf ( " : " );
for ( i = offset ; i < ( offset + 16 ) ; i++ ) {
if ( i >= len ) {
printf ( " " );
dbg_printf ( " " );
continue;
}
byte = bytes[i];
if ( ( byte < 0x20 ) || ( byte >= 0x7f ) )
byte = '.';
printf ( "%c", byte );
dbg_printf ( "%c", byte );
}
printf ( "\n" );
dbg_printf ( "\n" );
}

/**
Expand Down Expand Up @@ -157,14 +179,14 @@ static int dbg_autocolour ( unsigned long stream ) {
* @v stream Message stream ID
*/
void dbg_autocolourise ( unsigned long stream ) {
printf ( "\033[%dm",
( stream ? ( 31 + dbg_autocolour ( stream ) ) : 0 ) );
dbg_printf ( "\033[%dm",
( stream ? ( 31 + dbg_autocolour ( stream ) ) : 0 ) );
}

/**
* Revert to normal colour
*
*/
void dbg_decolourise ( void ) {
printf ( "\033[0m" );
dbg_printf ( "\033[0m" );
}
8 changes: 8 additions & 0 deletions src/core/serial_console.c
@@ -1,13 +1,20 @@
#include <ipxe/init.h>
#include <ipxe/serial.h>
#include <ipxe/console.h>
#include <config/console.h>

/** @file
*
* Serial console
*
*/

/* Set default console usage if applicable */
#if ! ( defined ( CONSOLE_SERIAL ) && CONSOLE_EXPLICIT ( CONSOLE_SERIAL ) )
#undef CONSOLE_SERIAL
#define CONSOLE_SERIAL CONSOLE_USAGE_ALL
#endif

struct console_driver serial_console __console_driver;

static void serial_console_init ( void ) {
Expand All @@ -21,6 +28,7 @@ struct console_driver serial_console __console_driver = {
.getchar = serial_getc,
.iskey = serial_ischar,
.disabled = 1,
.usage = CONSOLE_SERIAL,
};

/**
Expand Down
16 changes: 3 additions & 13 deletions src/include/compiler.h
Expand Up @@ -260,19 +260,9 @@ REQUEST_EXPANDED ( CONFIG_SYMBOL );

#ifndef ASSEMBLY

/** printf() for debugging
*
* This function exists so that the DBG() macros can expand to
* printf() calls without dragging the printf() prototype into scope.
*
* As far as the compiler is concerned, dbg_printf() and printf() are
* completely unrelated calls; it's only at the assembly stage that
* references to the dbg_printf symbol are collapsed into references
* to the printf symbol.
*/
extern int __attribute__ (( format ( printf, 1, 2 ) ))
dbg_printf ( const char *fmt, ... ) asm ( "printf" );

/** printf() for debugging */
extern void __attribute__ (( format ( printf, 1, 2 ) ))
dbg_printf ( const char *fmt, ... );
extern void dbg_autocolourise ( unsigned long id );
extern void dbg_decolourise ( void );
extern void dbg_hex_dump_da ( unsigned long dispaddr,
Expand Down
51 changes: 50 additions & 1 deletion src/include/ipxe/console.h
Expand Up @@ -75,6 +75,13 @@ struct console_driver {
*
*/
int ( *iskey ) ( void );

/** Console usage bitmask
*
* This is the bitwise OR of zero or more @c CONSOLE_USAGE_XXX
* values.
*/
int usage;
};

/** Console driver table */
Expand All @@ -99,7 +106,49 @@ struct console_driver {
*/
#define __console_driver __table_entry ( CONSOLES, 01 )

/* Function prototypes */
/**
* @defgroup consoleusage Console usages
* @{
*/

/** Standard output */
#define CONSOLE_USAGE_STDOUT 0x0001

/** Debug messages */
#define CONSOLE_USAGE_DEBUG 0x0002

/** All console usages */
#define CONSOLE_USAGE_ALL ( CONSOLE_USAGE_STDOUT | CONSOLE_USAGE_DEBUG )

/** @} */

/**
* Test to see if console has an explicit usage
*
* @v console Console definition (e.g. CONSOLE_PCBIOS)
* @ret explicit Console has an explicit usage
*
* This relies upon the trick that the expression ( 2 * N + 1 ) will
* be valid even if N is defined to be empty, since it will then
* evaluate to give ( 2 * + 1 ) == ( 2 * +1 ) == 2.
*/
#define CONSOLE_EXPLICIT( console ) ( ( 2 * console + 1 ) != 2 )

extern int console_usage;

/**
* Set console usage
*
* @v usage New console usage
* @ret old_usage Previous console usage
*/
static inline __attribute__ (( always_inline )) int
console_set_usage ( int usage ) {
int old_usage = console_usage;

console_usage = usage;
return old_usage;
}

extern int iskey ( void );
extern int getkey ( unsigned long timeout );
Expand Down
8 changes: 8 additions & 0 deletions src/interface/efi/efi_console.c
Expand Up @@ -23,6 +23,7 @@ FILE_LICENCE ( GPL2_OR_LATER );
#include <ipxe/efi/efi.h>
#include <ipxe/ansiesc.h>
#include <ipxe/console.h>
#include <config/console.h>

#define ATTR_BOLD 0x08

Expand All @@ -48,6 +49,12 @@ FILE_LICENCE ( GPL2_OR_LATER );

#define ATTR_DEFAULT ATTR_FCOL_WHITE

/* Set default console usage if applicable */
#if ! ( defined ( CONSOLE_EFI ) && CONSOLE_EXPLICIT ( CONSOLE_EFI ) )
#undef CONSOLE_EFI
#define CONSOLE_EFI CONSOLE_USAGE_ALL
#endif

/** Current character attribute */
static unsigned int efi_attr = ATTR_DEFAULT;

Expand Down Expand Up @@ -273,4 +280,5 @@ struct console_driver efi_console __console_driver = {
.putchar = efi_putchar,
.getchar = efi_getchar,
.iskey = efi_iskey,
.usage = CONSOLE_EFI,
};
9 changes: 9 additions & 0 deletions src/interface/linux/linux_console.c
Expand Up @@ -33,6 +33,14 @@ FILE_LICENCE(GPL2_OR_LATER);
#include <linux/termios.h>
#include <asm/errno.h>

#include <config/console.h>

/* Set default console usage if applicable */
#if ! ( defined ( CONSOLE_LINUX ) && CONSOLE_EXPLICIT ( CONSOLE_LINUX ) )
#undef CONSOLE_LINUX
#define CONSOLE_LINUX CONSOLE_USAGE_ALL
#endif

static void linux_console_putchar(int c)
{
/* write to stdout */
Expand Down Expand Up @@ -79,6 +87,7 @@ struct console_driver linux_console __console_driver = {
.putchar = linux_console_putchar,
.getchar = linux_console_getchar,
.iskey = linux_console_iskey,
.usage = CONSOLE_LINUX,
};

static int linux_tcgetattr(int fd, struct termios *termios_p)
Expand Down
8 changes: 8 additions & 0 deletions src/net/udp/syslog.c
Expand Up @@ -34,6 +34,13 @@ FILE_LICENCE ( GPL2_OR_LATER );
#include <ipxe/console.h>
#include <ipxe/lineconsole.h>
#include <ipxe/syslog.h>
#include <config/console.h>

/* Set default console usage if applicable */
#if ! ( defined ( CONSOLE_SYSLOG ) && CONSOLE_EXPLICIT ( CONSOLE_SYSLOG ) )
#undef CONSOLE_SYSLOG
#define CONSOLE_SYSLOG CONSOLE_USAGE_ALL
#endif

/** The syslog server */
static struct sockaddr_tcpip logserver = {
Expand Down Expand Up @@ -106,6 +113,7 @@ static void syslog_putchar ( int character ) {
struct console_driver syslog_console __console_driver = {
.putchar = syslog_putchar,
.disabled = 1,
.usage = CONSOLE_SYSLOG,
};

/******************************************************************************
Expand Down

0 comments on commit e024cd3

Please sign in to comment.