diff options
Diffstat (limited to '410user/libstdio/printf.c')
| -rw-r--r-- | 410user/libstdio/printf.c | 97 |
1 files changed, 97 insertions, 0 deletions
diff --git a/410user/libstdio/printf.c b/410user/libstdio/printf.c new file mode 100644 index 0000000..0a4a4db --- /dev/null +++ b/410user/libstdio/printf.c @@ -0,0 +1,97 @@ +/* + * Mach Operating System + * Copyright (c) 1993-1989 Carnegie Mellon University. + * Copyright (c) 1994 The University of Utah and + * the Computer Systems Laboratory (CSL). + * All rights reserved. + * + * Permission to use, copy, modify and distribute this software and its + * documentation is hereby granted, provided that both the copyright + * notice and this permission notice appear in all copies of the + * software, derivative works or modified versions, and any portions + * thereof, and that both notices appear in supporting documentation. + * + * CARNEGIE MELLON, THE UNIVERSITY OF UTAH AND CSL ALLOW FREE USE OF + * THIS SOFTWARE IN ITS "AS IS" CONDITION, AND DISCLAIM ANY LIABILITY + * OF ANY KIND FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF + * THIS SOFTWARE. + * + * Carnegie Mellon requests users of this software to return to + * + * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU + * School of Computer Science + * Carnegie Mellon University + * Pittsburgh PA 15213-3890 + * + * any improvements or extensions that they make and grant Carnegie Mellon + * the rights to redistribute these changes. + */ + +#include <stdio.h> +#include <stdarg.h> +#include <syscall.h> +#include "doprnt.h" + +/* This version of printf is implemented in terms of putchar and puts. */ + +#define PRINTF_BUFMAX 128 + +struct printf_state { + char buf[PRINTF_BUFMAX]; + unsigned int index; +}; + +static void +flush(struct printf_state *state) +{ + print(state->index, state->buf); + state->index = 0; +} + +static void +printf_char(char *arg, int c) +{ + struct printf_state *state = (struct printf_state *) arg; + + if (state->index >= PRINTF_BUFMAX) { + flush(state); + } + + state->buf[state->index] = c; + state->index++; + if (c == '\n') { + flush(state); + } +} + +/* + * Printing (to console) + */ +int vprintf(const char *fmt, va_list args) +{ + struct printf_state state; + + state.index = 0; + _doprnt(fmt, args, 0, (void (*)())printf_char, (char *) &state); + + if (state.index != 0) + flush(&state); + + /* _doprnt currently doesn't pass back error codes, + so just assume nothing bad happened. */ + return 0; +} + +int +printf(const char *fmt, ...) +{ + va_list args; + int err; + + va_start(args, fmt); + err = vprintf(fmt, args); + va_end(args); + + return err; +} + |
