mirror of
https://github.com/PDP-10/its.git
synced 2026-03-22 00:59:48 +00:00
246 lines
5.0 KiB
C
246 lines
5.0 KiB
C
/*
|
|
CPRINT - C Formatted Print Routine
|
|
Extendable Format Version:
|
|
Print Routines should expect the following
|
|
arguments (n specified when defined):
|
|
1 to n: n data arguments
|
|
n+1: file descriptor
|
|
n+2: field width (0 if none given)
|
|
n+3: pad character
|
|
|
|
Format options: (upper case treated identically)
|
|
%s string
|
|
%c character
|
|
%o octal
|
|
%d decimal
|
|
%z Like %c except repeat characters width times
|
|
If number preceeds format char (as in %4d) then number will be
|
|
minimum field width in which the argument appears.
|
|
A positive field width will right justify the arg.
|
|
A negative field width will left justify.
|
|
|
|
If a 0 immediately follows the %, then the pad character is
|
|
changed to 0 (instead of space). If the next character after the
|
|
0 is not a digit, then the pad character is changed to that character.
|
|
For example:
|
|
%09d -- zero pad, width nine. -- 000000312
|
|
%0*9d -- pad with *, width nine -- ******312
|
|
%-0*9d -- left justified -- 312******
|
|
Note that the 0 does NOT mean that the following number is octal.
|
|
*/
|
|
|
|
# define WORDMASK 077777777777
|
|
# define SMALLEST "-34359738368"
|
|
|
|
extern int cin, cout, cerr;
|
|
int prcf(), prdf(), prof(), prsf(), przf();
|
|
|
|
static int (*format_table[26]) () {
|
|
/* a */ 0, 0, prcf, prdf, 0, 0, 0, 0,
|
|
/* i */ 0, 0, 0, 0, 0, 0, prof, 0,
|
|
/* q */ 0, 0, prsf, 0, 0, 0, 0, 0,
|
|
/* y */ 0, przf};
|
|
|
|
static int format_nargs [26] {
|
|
/* a */ 0, 0, 1, 1, 0, 0, 0, 0,
|
|
/* i */ 0, 0, 0, 0, 0, 0, 1, 0,
|
|
/* q */ 0, 0, 1, 0, 0, 0, 0, 0,
|
|
/* y */ 0, 1};
|
|
|
|
fmtf (c, p, n)
|
|
int (*p)();
|
|
{
|
|
if (c >= 'A' && c <= 'Z')
|
|
c =+ ('a' - 'A');
|
|
if (c >= 'a' && c <= 'z')
|
|
{
|
|
if (n >= 0 && n <= 3)
|
|
{
|
|
format_table [c - 'a'] = p;
|
|
format_nargs [c - 'a'] = n;
|
|
}
|
|
else
|
|
cprint (cerr, "bad nargs to FMTF: %d\n", n);
|
|
}
|
|
else
|
|
cprint (cerr, "bad character to FMTF: %c\n", c);
|
|
}
|
|
|
|
|
|
cprint (a1,a2,a3,a4,a5,a6,a7,a8)
|
|
{
|
|
int *adx, c, width, rjust;
|
|
char *fmt, padc;
|
|
int fn, (*p)(), n;
|
|
|
|
if (cisfd(a1)) /* file descriptor */
|
|
{
|
|
fn = a1;
|
|
fmt = a2;
|
|
adx = &a3;
|
|
}
|
|
else
|
|
{
|
|
fn = cout;
|
|
fmt = a1;
|
|
adx = &a2;
|
|
}
|
|
|
|
while (c= *fmt++)
|
|
{
|
|
if (c!='%')
|
|
cputc (c,fn);
|
|
else
|
|
{
|
|
width = 0;
|
|
rjust = 0; /* right justify off */
|
|
padc = ' '; /* pad with a space */
|
|
if (*fmt == '-') /* then right justify */
|
|
{
|
|
rjust++;
|
|
fmt++;
|
|
}
|
|
if (*fmt == '0') /* then change pad character */
|
|
{
|
|
fmt++;
|
|
if (*fmt >= '0' && *fmt <= '9')
|
|
padc = '0';
|
|
else
|
|
padc = *fmt++;
|
|
}
|
|
while ((c = *fmt)>='0' && c<='9')
|
|
width = (width*10) + (*fmt++ - '0');
|
|
if (rjust)
|
|
width = -width;
|
|
c = *fmt++;
|
|
if (c >= 'A' && c <= 'Z')
|
|
c =+ ('a' - 'A');
|
|
if (c >= 'a' && c <= 'z')
|
|
{
|
|
p = format_table [c - 'a'];
|
|
n = format_nargs [c - 'a'];
|
|
if (p)
|
|
{
|
|
switch (n)
|
|
{
|
|
case 0:
|
|
(*p) (fn, width, padc);
|
|
break;
|
|
case 1:
|
|
(*p) (adx[0], fn, width, padc);
|
|
break;
|
|
case 2:
|
|
(*p) (adx[0], adx[1], fn, width, padc);
|
|
break;
|
|
case 3:
|
|
(*p) (adx[0], adx[1], adx[2], fn, width, padc);
|
|
break;
|
|
}
|
|
adx =+ n;
|
|
continue;
|
|
}
|
|
cputc (c, fn);
|
|
}
|
|
else
|
|
cputc (c, fn);
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
/*
|
|
* put out num many characters
|
|
*/
|
|
przf (chr, f, num, padc)
|
|
int num, f;
|
|
char chr;
|
|
{
|
|
while (--num >= 0)
|
|
cputc (chr, f);
|
|
}
|
|
|
|
/**********************************************************************
|
|
|
|
PROF - Print Octal Integer
|
|
|
|
**********************************************************************/
|
|
|
|
prof (i, f, w, padc)
|
|
{
|
|
int b[30], *p, nd;
|
|
|
|
p = b;
|
|
do {
|
|
*p++ = (i&07) + '0';
|
|
i = (i >> 3) & WORDMASK;
|
|
} while (i);
|
|
nd = p - b;
|
|
if (w > 0) przf (padc, f, w - nd, padc);
|
|
while (p > b) cputc (*--p, f);
|
|
if (w < 0) przf (padc, f, -w - nd, padc);
|
|
}
|
|
|
|
/**********************************************************************
|
|
|
|
PRDF - Print Decimal Integer
|
|
|
|
**********************************************************************/
|
|
|
|
prdf (i, f, w, padc)
|
|
{
|
|
int b[30], *p, flag, nd;
|
|
|
|
flag = 0;
|
|
p = b;
|
|
if (i < 0) {i = -i; flag = 1;}
|
|
if (i < 0)
|
|
{
|
|
stcpy (SMALLEST, b);
|
|
p = b+slen(b);
|
|
flag = 0;
|
|
}
|
|
else
|
|
{
|
|
do
|
|
{
|
|
*p++ = i%10 + '0';
|
|
i =/ 10;
|
|
} while (i);
|
|
}
|
|
if (flag) *p++ = '-';
|
|
nd = p - b;
|
|
if (w > 0) przf (padc, f, w - nd, padc);
|
|
while (p > b) cputc (*--p, f);
|
|
if (w < 0) przf (padc, f, -w - nd, padc);
|
|
}
|
|
|
|
/**********************************************************************
|
|
|
|
PRSF - Print String
|
|
|
|
**********************************************************************/
|
|
|
|
prsf (s, f, w, padc)
|
|
char *s;
|
|
{
|
|
int i, nd;
|
|
|
|
nd = slen (s);
|
|
if (w > 0) przf (padc, f, w - nd, padc);
|
|
while (i = *s++) cputc (i, f);
|
|
if (w < 0) przf (padc, f, -w - nd, padc);
|
|
}
|
|
|
|
/**********************************************************************
|
|
|
|
PRCF - Print Character
|
|
|
|
**********************************************************************/
|
|
|
|
prcf (c, f, w, padc)
|
|
{
|
|
if (w > 0) przf (padc, f, w - 1, padc);
|
|
cputc (c, f);
|
|
if (w < 0) przf (padc, f, -w - 1, padc);
|
|
}
|