* Copyright (c) 1989 The Regents of the University of California.
* %sccs.include.redist.c%
#if !defined(BUILTIN) && !defined(SHELL)
"@(#) Copyright (c) 1989 The Regents of the University of California.\n\
static char sccsid
[] = "@(#)printf.c 5.15 (Berkeley) %G%";
* This *has* to go away. TK.
#define warnx(a, b, c) { \
(void)sprintf(buf, sizeof(buf), a, b, c); \
#include "../../bin/sh/bltin/bltin.h"
(void)printf(f, fieldwidth, precision, func); \
(void)printf(f, fieldwidth, func); \
(void)printf(f, precision, func); \
static int asciicode
__P((void));
static void escape
__P((char *));
static int getchr
__P((void));
static double getdouble
__P((void));
static int getint
__P((int *));
static int getlong
__P((long *));
static char *getstr
__P((void));
static char *mklong
__P((char *, int));
static void usage
__P((void));
static char *skip1
, *skip2
;
int ch
, end
, fieldwidth
, precision
;
char convch
, nextch
, *format
, *fmt
, *start
;
while ((ch
= getopt(argc
, argv
, "")) != EOF
)
* Basic algorithm is to scan the format string for conversion
* specifications -- once one is found, find out if the field
* width or precision is a '*'; if it is, gather up value. Note,
* format strings are reused as necessary to use up the provided
* arguments, arguments of zero/null string are provided to use
escape(fmt
= format
= *argv
); /* backslash interpretation */
/* find next format specification */
next
: for (start
= fmt
;; ++fmt
) {
/* avoid infinite loop */
warnx("missing format character",
(void)printf("%s", start
);
(void)printf("%s", start
);
/* skip to field width */
for (; strchr(skip1
, *fmt
); ++fmt
);
/* skip to possible '.', get following precision */
for (; strchr(skip2
, *fmt
); ++fmt
);
/* skip to conversion char */
for (; strchr(skip2
, *fmt
); ++fmt
);
warnx("missing format character", NULL
, NULL
);
case 'd': case 'i': case 'o': case 'u': case 'x': case 'X': {
if ((f
= mklong(start
, convch
)) == NULL
)
case 'e': case 'E': case 'f': case 'g': case 'G': {
warnx("illegal format character", NULL
, NULL
);
memmove(copy
, str
, len
- 3);
for (store
= fmt
; c
= *fmt
; ++fmt
, ++store
) {
case '\0': /* EOS, user error */
case '\\': /* backslash */
case '\'': /* single quote */
case 'a': /* bell/alert */
case 'b': /* backspace */
case 'f': /* form-feed */
case 'r': /* carriage-return */
case 't': /* horizontal tab */
case 'v': /* vertical tab */
case '0': case '1': case '2': case '3':
case '4': case '5': case '6': case '7':
c
-- && *fmt
>= '0' && *fmt
<= '7'; ++fmt
) {
static char *Number
= "+-.0123456789";
warnx("%s", *gargv
, strerror(ERANGE
));
if (strchr(Number
, **gargv
)) {
val
= strtol(*gargv
, &ep
, 0);
warnx("%s: illegal number", *gargv
, NULL
);
warnx("%s", *gargv
, strerror(ERANGE
));
warnx("%s", *gargv
, strerror(ERANGE
));
if (strchr(Number
, **gargv
))
return ((double)asciicode());
if (ch
== '\'' || ch
== '"')
(void)fprintf(stderr
, "usage: printf format [arg ...]\n");