rs.c revision 98003
11590Srgrimes/*- 21590Srgrimes * Copyright (c) 1993 31590Srgrimes * The Regents of the University of California. All rights reserved. 41590Srgrimes * 51590Srgrimes * Redistribution and use in source and binary forms, with or without 61590Srgrimes * modification, are permitted provided that the following conditions 71590Srgrimes * are met: 81590Srgrimes * 1. Redistributions of source code must retain the above copyright 91590Srgrimes * notice, this list of conditions and the following disclaimer. 101590Srgrimes * 2. Redistributions in binary form must reproduce the above copyright 111590Srgrimes * notice, this list of conditions and the following disclaimer in the 121590Srgrimes * documentation and/or other materials provided with the distribution. 131590Srgrimes * 3. All advertising materials mentioning features or use of this software 141590Srgrimes * must display the following acknowledgement: 151590Srgrimes * This product includes software developed by the University of 161590Srgrimes * California, Berkeley and its contributors. 171590Srgrimes * 4. Neither the name of the University nor the names of its contributors 181590Srgrimes * may be used to endorse or promote products derived from this software 191590Srgrimes * without specific prior written permission. 201590Srgrimes * 211590Srgrimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 221590Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 231590Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 241590Srgrimes * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 251590Srgrimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 261590Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 271590Srgrimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 281590Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 291590Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 301590Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 311590Srgrimes * SUCH DAMAGE. 321590Srgrimes */ 331590Srgrimes 341590Srgrimes#ifndef lint 3527953Scharnierstatic const char copyright[] = 361590Srgrimes"@(#) Copyright (c) 1993\n\ 371590Srgrimes The Regents of the University of California. All rights reserved.\n"; 381590Srgrimes#endif /* not lint */ 391590Srgrimes 401590Srgrimes#ifndef lint 4195618Smarkmstatic const char sccsid[] = "@(#)rs.c 8.1 (Berkeley) 6/6/93"; 421590Srgrimes#endif /* not lint */ 431590Srgrimes 441590Srgrimes/* 451590Srgrimes * rs - reshape a data array 461590Srgrimes * Author: John Kunze, Office of Comp. Affairs, UCB 471590Srgrimes * BEWARE: lots of unfinished edges 481590Srgrimes */ 491590Srgrimes 5095618Smarkm#include <sys/cdefs.h> 5195618Smarkm__FBSDID("$FreeBSD: head/usr.bin/rs/rs.c 98003 2002-06-07 07:08:06Z tjr $"); 5295618Smarkm 5327953Scharnier#include <err.h> 541590Srgrimes#include <ctype.h> 551590Srgrimes#include <stdio.h> 561590Srgrimes#include <stdlib.h> 5733648Sjb#include <string.h> 581590Srgrimes 591590Srgrimeslong flags; 601590Srgrimes#define TRANSPOSE 000001 611590Srgrimes#define MTRANSPOSE 000002 621590Srgrimes#define ONEPERLINE 000004 631590Srgrimes#define ONEISEPONLY 000010 641590Srgrimes#define ONEOSEPONLY 000020 651590Srgrimes#define NOTRIMENDCOL 000040 661590Srgrimes#define SQUEEZE 000100 671590Srgrimes#define SHAPEONLY 000200 681590Srgrimes#define DETAILSHAPE 000400 691590Srgrimes#define RIGHTADJUST 001000 701590Srgrimes#define NULLPAD 002000 711590Srgrimes#define RECYCLE 004000 721590Srgrimes#define SKIPPRINT 010000 731590Srgrimes#define ICOLBOUNDS 020000 741590Srgrimes#define OCOLBOUNDS 040000 751590Srgrimes#define ONEPERCHAR 0100000 761590Srgrimes#define NOARGS 0200000 771590Srgrimes 781590Srgrimesshort *colwidths; 791590Srgrimesshort *cord; 801590Srgrimesshort *icbd; 811590Srgrimesshort *ocbd; 821590Srgrimesint nelem; 831590Srgrimeschar **elem; 841590Srgrimeschar **endelem; 851590Srgrimeschar *curline; 861590Srgrimesint allocsize = BUFSIZ; 871590Srgrimesint curlen; 881590Srgrimesint irows, icols; 891590Srgrimesint orows, ocols; 901590Srgrimesint maxlen; 911590Srgrimesint skip; 921590Srgrimesint propgutter; 931590Srgrimeschar isep = ' ', osep = ' '; 9495618Smarkmchar blank[] = ""; 951590Srgrimesint owidth = 80, gutter = 2; 961590Srgrimes 9792921Simpvoid getargs(int, char *[]); 9892921Simpvoid getfile(void); 9992921Simpint getline(void); 10092921Simpchar *getlist(short **, char *); 10192921Simpchar *getnum(int *, char *, int); 10292921Simpchar **getptrs(char **); 10392921Simpvoid prepfile(void); 10492921Simpvoid prints(char *, int); 10592921Simpvoid putfile(void); 10692921Simpstatic void usage(void); 1071590Srgrimes 10883303Sru#define INCR(ep) do { \ 10983303Sru if (++ep >= endelem) \ 11083303Sru ep = getptrs(ep); \ 11183303Sru} while(0) 11283303Sru 1131590Srgrimesint 11495618Smarkmmain(int argc, char *argv[]) 1151590Srgrimes{ 1161590Srgrimes getargs(argc, argv); 1171590Srgrimes getfile(); 1181590Srgrimes if (flags & SHAPEONLY) { 1191590Srgrimes printf("%d %d\n", irows, icols); 1201590Srgrimes exit(0); 1211590Srgrimes } 1221590Srgrimes prepfile(); 1231590Srgrimes putfile(); 1241590Srgrimes exit(0); 1251590Srgrimes} 1261590Srgrimes 1271590Srgrimesvoid 12895618Smarkmgetfile(void) 1291590Srgrimes{ 13095618Smarkm char *p; 13195618Smarkm char *endp; 13283303Sru char **ep; 1331590Srgrimes int multisep = (flags & ONEISEPONLY ? 0 : 1); 1341590Srgrimes int nullpad = flags & NULLPAD; 1351590Srgrimes char **padto; 1361590Srgrimes 1371590Srgrimes while (skip--) { 1381590Srgrimes getline(); 1391590Srgrimes if (flags & SKIPPRINT) 1401590Srgrimes puts(curline); 1411590Srgrimes } 1421590Srgrimes getline(); 1431590Srgrimes if (flags & NOARGS && curlen < owidth) 1441590Srgrimes flags |= ONEPERLINE; 1451590Srgrimes if (flags & ONEPERLINE) 1461590Srgrimes icols = 1; 1471590Srgrimes else /* count cols on first line */ 1481590Srgrimes for (p = curline, endp = curline + curlen; p < endp; p++) { 1491590Srgrimes if (*p == isep && multisep) 1501590Srgrimes continue; 1511590Srgrimes icols++; 1521590Srgrimes while (*p && *p != isep) 1531590Srgrimes p++; 1541590Srgrimes } 1551590Srgrimes ep = getptrs(elem); 1561590Srgrimes p = curline; 1571590Srgrimes do { 1581590Srgrimes if (flags & ONEPERLINE) { 15983303Sru *ep = curline; 16083303Sru INCR(ep); /* prepare for next entry */ 1611590Srgrimes if (maxlen < curlen) 1621590Srgrimes maxlen = curlen; 1631590Srgrimes irows++; 1641590Srgrimes continue; 1651590Srgrimes } 1661590Srgrimes for (p = curline, endp = curline + curlen; p < endp; p++) { 1671590Srgrimes if (*p == isep && multisep) 1681590Srgrimes continue; /* eat up column separators */ 1691590Srgrimes if (*p == isep) /* must be an empty column */ 17095618Smarkm *ep = blank; 1711590Srgrimes else /* store column entry */ 1721590Srgrimes *ep = p; 1731590Srgrimes while (p < endp && *p != isep) 1741590Srgrimes p++; /* find end of entry */ 1751590Srgrimes *p = '\0'; /* mark end of entry */ 1761590Srgrimes if (maxlen < p - *ep) /* update maxlen */ 1771590Srgrimes maxlen = p - *ep; 17883303Sru INCR(ep); /* prepare for next entry */ 1791590Srgrimes } 1801590Srgrimes irows++; /* update row count */ 1811590Srgrimes if (nullpad) { /* pad missing entries */ 1821590Srgrimes padto = elem + irows * icols; 18383303Sru while (ep < padto) { 18495618Smarkm *ep = blank; 18583303Sru INCR(ep); 18683303Sru } 1871590Srgrimes } 1881590Srgrimes } while (getline() != EOF); 1891590Srgrimes *ep = 0; /* mark end of pointers */ 1901590Srgrimes nelem = ep - elem; 1911590Srgrimes} 1921590Srgrimes 1931590Srgrimesvoid 19495618Smarkmputfile(void) 1951590Srgrimes{ 19695618Smarkm char **ep; 19795618Smarkm int i, j, k; 1981590Srgrimes 1991590Srgrimes ep = elem; 2001590Srgrimes if (flags & TRANSPOSE) 2011590Srgrimes for (i = 0; i < orows; i++) { 2021590Srgrimes for (j = i; j < nelem; j += orows) 2031590Srgrimes prints(ep[j], (j - i) / orows); 2041590Srgrimes putchar('\n'); 2051590Srgrimes } 2061590Srgrimes else 20715909Sjoerg for (i = k = 0; i < orows; i++) { 20815909Sjoerg for (j = 0; j < ocols; j++, k++) 20915909Sjoerg if (k < nelem) 21015909Sjoerg prints(ep[k], j); 2111590Srgrimes putchar('\n'); 2121590Srgrimes } 2131590Srgrimes} 2141590Srgrimes 2151590Srgrimesvoid 21695618Smarkmprints(char *s, int col) 2171590Srgrimes{ 21895618Smarkm int n; 21995618Smarkm char *p = s; 2201590Srgrimes 2211590Srgrimes while (*p) 2221590Srgrimes p++; 2231590Srgrimes n = (flags & ONEOSEPONLY ? 1 : colwidths[col] - (p - s)); 2241590Srgrimes if (flags & RIGHTADJUST) 2251590Srgrimes while (n-- > 0) 2261590Srgrimes putchar(osep); 2271590Srgrimes for (p = s; *p; p++) 2281590Srgrimes putchar(*p); 2291590Srgrimes while (n-- > 0) 2301590Srgrimes putchar(osep); 2311590Srgrimes} 2321590Srgrimes 23327953Scharnierstatic void 23495618Smarkmusage(void) 2351590Srgrimes{ 2361590Srgrimes fprintf(stderr, 23727953Scharnier "usage: rs [-[csCS][x][kKgGw][N]tTeEnyjhHmz] [rows [cols]]\n"); 2381590Srgrimes exit(1); 2391590Srgrimes} 2401590Srgrimes 2411590Srgrimesvoid 24295618Smarkmprepfile(void) 2431590Srgrimes{ 24495618Smarkm char **ep; 24595618Smarkm int i; 24695618Smarkm int j; 2471590Srgrimes char **lp; 2481590Srgrimes int colw; 24983296Sru int max; 2501590Srgrimes int n; 2511590Srgrimes 2521590Srgrimes if (!nelem) 2531590Srgrimes exit(0); 2541590Srgrimes gutter += maxlen * propgutter / 100.0; 2551590Srgrimes colw = maxlen + gutter; 2561590Srgrimes if (flags & MTRANSPOSE) { 2571590Srgrimes orows = icols; 2581590Srgrimes ocols = irows; 2591590Srgrimes } 2601590Srgrimes else if (orows == 0 && ocols == 0) { /* decide rows and cols */ 2611590Srgrimes ocols = owidth / colw; 26283298Sru if (ocols == 0) { 26327953Scharnier warnx("display width %d is less than column width %d", 26427953Scharnier owidth, colw); 26583298Sru ocols = 1; 26683298Sru } 2671590Srgrimes if (ocols > nelem) 2681590Srgrimes ocols = nelem; 2691590Srgrimes orows = nelem / ocols + (nelem % ocols ? 1 : 0); 2701590Srgrimes } 2711590Srgrimes else if (orows == 0) /* decide on rows */ 2721590Srgrimes orows = nelem / ocols + (nelem % ocols ? 1 : 0); 2731590Srgrimes else if (ocols == 0) /* decide on cols */ 2741590Srgrimes ocols = nelem / orows + (nelem % orows ? 1 : 0); 2751590Srgrimes lp = elem + orows * ocols; 2761590Srgrimes while (lp > endelem) { 2771590Srgrimes getptrs(elem + nelem); 2781590Srgrimes lp = elem + orows * ocols; 2791590Srgrimes } 2801590Srgrimes if (flags & RECYCLE) { 2811590Srgrimes for (ep = elem + nelem; ep < lp; ep++) 2821590Srgrimes *ep = *(ep - nelem); 2831590Srgrimes nelem = lp - elem; 2841590Srgrimes } 2851590Srgrimes if (!(colwidths = (short *) malloc(ocols * sizeof(short)))) 28627953Scharnier errx(1, "malloc"); 2871590Srgrimes if (flags & SQUEEZE) { 28883296Sru ep = elem; 2891590Srgrimes if (flags & TRANSPOSE) 29083296Sru for (i = 0; i < ocols; i++) { 29183296Sru max = 0; 29283296Sru for (j = 0; *ep != NULL && j < orows; j++) 2931590Srgrimes if ((n = strlen(*ep++)) > max) 2941590Srgrimes max = n; 2951590Srgrimes colwidths[i] = max + gutter; 2961590Srgrimes } 2971590Srgrimes else 2981590Srgrimes for (i = 0; i < ocols; i++) { 29983296Sru max = 0; 3001590Srgrimes for (j = i; j < nelem; j += ocols) 3011590Srgrimes if ((n = strlen(ep[j])) > max) 3021590Srgrimes max = n; 3031590Srgrimes colwidths[i] = max + gutter; 3041590Srgrimes } 3051590Srgrimes } 3061590Srgrimes /* for (i = 0; i < orows; i++) { 3071590Srgrimes for (j = i; j < nelem; j += orows) 3081590Srgrimes prints(ep[j], (j - i) / orows); 3091590Srgrimes putchar('\n'); 3101590Srgrimes } 3111590Srgrimes else 3121590Srgrimes for (i = 0; i < orows; i++) { 3131590Srgrimes for (j = 0; j < ocols; j++) 3141590Srgrimes prints(*ep++, j); 3151590Srgrimes putchar('\n'); 3161590Srgrimes }*/ 3171590Srgrimes else 3181590Srgrimes for (i = 0; i < ocols; i++) 3191590Srgrimes colwidths[i] = colw; 3201590Srgrimes if (!(flags & NOTRIMENDCOL)) { 3211590Srgrimes if (flags & RIGHTADJUST) 3221590Srgrimes colwidths[0] -= gutter; 3231590Srgrimes else 3241590Srgrimes colwidths[ocols - 1] = 0; 3251590Srgrimes } 3261590Srgrimes n = orows * ocols; 3271590Srgrimes if (n > nelem && (flags & RECYCLE)) 3281590Srgrimes nelem = n; 3291590Srgrimes /*for (i = 0; i < ocols; i++) 33027953Scharnier warnx("%d is colwidths, nelem %d", colwidths[i], nelem);*/ 3311590Srgrimes} 3321590Srgrimes 3331590Srgrimes#define BSIZE 2048 3341590Srgrimeschar ibuf[BSIZE]; /* two screenfuls should do */ 3351590Srgrimes 3361590Srgrimesint 33795618Smarkmgetline(void) /* get line; maintain curline, curlen; manage storage */ 3381590Srgrimes{ 3391590Srgrimes static int putlength; 3401590Srgrimes static char *endblock = ibuf + BSIZE; 34195618Smarkm char *p; 34295618Smarkm int c, i; 3431590Srgrimes 3441590Srgrimes if (!irows) { 3451590Srgrimes curline = ibuf; 3461590Srgrimes putlength = flags & DETAILSHAPE; 3471590Srgrimes } 3481590Srgrimes else if (skip <= 0) { /* don't waste storage */ 3491590Srgrimes curline += curlen + 1; 35098003Stjr if (putlength) { /* print length, recycle storage */ 3511590Srgrimes printf(" %d line %d\n", curlen, irows); 35298003Stjr curline = ibuf; 35398003Stjr } 3541590Srgrimes } 3551590Srgrimes if (!putlength && endblock - curline < BUFSIZ) { /* need storage */ 3561590Srgrimes /*ww = endblock-curline; tt += ww;*/ 3571590Srgrimes /*printf("#wasted %d total %d\n",ww,tt);*/ 3581590Srgrimes if (!(curline = (char *) malloc(BSIZE))) 35927953Scharnier errx(1, "file too large"); 3601590Srgrimes endblock = curline + BSIZE; 3611590Srgrimes /*printf("#endb %d curline %d\n",endblock,curline);*/ 3621590Srgrimes } 3631590Srgrimes for (p = curline, i = 1; i < BUFSIZ; *p++ = c, i++) 3641590Srgrimes if ((c = getchar()) == EOF || c == '\n') 3651590Srgrimes break; 3661590Srgrimes *p = '\0'; 3671590Srgrimes curlen = i - 1; 3681590Srgrimes return(c); 3691590Srgrimes} 3701590Srgrimes 3711590Srgrimeschar ** 37295618Smarkmgetptrs(char **sp) 3731590Srgrimes{ 37483303Sru char **p; 3751590Srgrimes 37683303Sru allocsize += allocsize; 37783303Sru p = (char **)realloc(elem, allocsize * sizeof(char *)); 37883303Sru if (p == NULL) 37983303Sru err(1, "no memory"); 38083303Sru 38183303Sru sp += (p - elem); 38283303Sru endelem = (elem = p) + allocsize; 38383303Sru return(sp); 3841590Srgrimes} 3851590Srgrimes 3861590Srgrimesvoid 38795618Smarkmgetargs(int ac, char *av[]) 3881590Srgrimes{ 38995618Smarkm char *p; 3901590Srgrimes 3911590Srgrimes if (ac == 1) { 3921590Srgrimes flags |= NOARGS | TRANSPOSE; 3931590Srgrimes } 3941590Srgrimes while (--ac && **++av == '-') 3951590Srgrimes for (p = *av+1; *p; p++) 3961590Srgrimes switch (*p) { 3971590Srgrimes case 'T': 3981590Srgrimes flags |= MTRANSPOSE; 3991590Srgrimes case 't': 4001590Srgrimes flags |= TRANSPOSE; 4011590Srgrimes break; 4021590Srgrimes case 'c': /* input col. separator */ 4031590Srgrimes flags |= ONEISEPONLY; 4041590Srgrimes case 's': /* one or more allowed */ 4051590Srgrimes if (p[1]) 4061590Srgrimes isep = *++p; 4071590Srgrimes else 4081590Srgrimes isep = '\t'; /* default is ^I */ 4091590Srgrimes break; 4101590Srgrimes case 'C': 4111590Srgrimes flags |= ONEOSEPONLY; 4121590Srgrimes case 'S': 4131590Srgrimes if (p[1]) 4141590Srgrimes osep = *++p; 4151590Srgrimes else 4161590Srgrimes osep = '\t'; /* default is ^I */ 4171590Srgrimes break; 4181590Srgrimes case 'w': /* window width, default 80 */ 4191590Srgrimes p = getnum(&owidth, p, 0); 4201590Srgrimes if (owidth <= 0) 42127953Scharnier errx(1, "width must be a positive integer"); 4221590Srgrimes break; 4231590Srgrimes case 'K': /* skip N lines */ 4241590Srgrimes flags |= SKIPPRINT; 4251590Srgrimes case 'k': /* skip, do not print */ 4261590Srgrimes p = getnum(&skip, p, 0); 4271590Srgrimes if (!skip) 4281590Srgrimes skip = 1; 4291590Srgrimes break; 4301590Srgrimes case 'm': 4311590Srgrimes flags |= NOTRIMENDCOL; 4321590Srgrimes break; 4331590Srgrimes case 'g': /* gutter space */ 4341590Srgrimes p = getnum(&gutter, p, 0); 4351590Srgrimes break; 4361590Srgrimes case 'G': 4371590Srgrimes p = getnum(&propgutter, p, 0); 4381590Srgrimes break; 4391590Srgrimes case 'e': /* each line is an entry */ 4401590Srgrimes flags |= ONEPERLINE; 4411590Srgrimes break; 4421590Srgrimes case 'E': 4431590Srgrimes flags |= ONEPERCHAR; 4441590Srgrimes break; 4451590Srgrimes case 'j': /* right adjust */ 4461590Srgrimes flags |= RIGHTADJUST; 4471590Srgrimes break; 4481590Srgrimes case 'n': /* null padding for missing values */ 4491590Srgrimes flags |= NULLPAD; 4501590Srgrimes break; 4511590Srgrimes case 'y': 4521590Srgrimes flags |= RECYCLE; 4531590Srgrimes break; 4541590Srgrimes case 'H': /* print shape only */ 4551590Srgrimes flags |= DETAILSHAPE; 4561590Srgrimes case 'h': 4571590Srgrimes flags |= SHAPEONLY; 4581590Srgrimes break; 4591590Srgrimes case 'z': /* squeeze col width */ 4601590Srgrimes flags |= SQUEEZE; 4611590Srgrimes break; 4621590Srgrimes /*case 'p': 4631590Srgrimes ipagespace = atoi(++p); (default is 1) 4641590Srgrimes break;*/ 4651590Srgrimes case 'o': /* col order */ 4661590Srgrimes p = getlist(&cord, p); 4671590Srgrimes break; 4681590Srgrimes case 'b': 4691590Srgrimes flags |= ICOLBOUNDS; 4701590Srgrimes p = getlist(&icbd, p); 4711590Srgrimes break; 4721590Srgrimes case 'B': 4731590Srgrimes flags |= OCOLBOUNDS; 4741590Srgrimes p = getlist(&ocbd, p); 4751590Srgrimes break; 4761590Srgrimes default: 47727953Scharnier usage(); 4781590Srgrimes } 4791590Srgrimes /*if (!osep) 4801590Srgrimes osep = isep;*/ 4811590Srgrimes switch (ac) { 4821590Srgrimes /*case 3: 4831590Srgrimes opages = atoi(av[2]);*/ 4841590Srgrimes case 2: 4851590Srgrimes ocols = atoi(av[1]); 4861590Srgrimes case 1: 4871590Srgrimes orows = atoi(av[0]); 4881590Srgrimes case 0: 4891590Srgrimes break; 4901590Srgrimes default: 49127953Scharnier errx(1, "too many arguments"); 4921590Srgrimes } 4931590Srgrimes} 4941590Srgrimes 4951590Srgrimeschar * 49695618Smarkmgetlist(short **list, char *p) 4971590Srgrimes{ 49895618Smarkm int count = 1; 49995618Smarkm char *t; 5001590Srgrimes 5011590Srgrimes for (t = p + 1; *t; t++) { 5021590Srgrimes if (!isdigit(*t)) 50327953Scharnier errx(1, 50427953Scharnier "option %.1s requires a list of unsigned numbers separated by commas", t); 5051590Srgrimes count++; 5061590Srgrimes while (*t && isdigit(*t)) 5071590Srgrimes t++; 5081590Srgrimes if (*t != ',') 5091590Srgrimes break; 5101590Srgrimes } 5111590Srgrimes if (!(*list = (short *) malloc(count * sizeof(short)))) 51227953Scharnier errx(1, "no list space"); 5131590Srgrimes count = 0; 5141590Srgrimes for (t = p + 1; *t; t++) { 5151590Srgrimes (*list)[count++] = atoi(t); 5161590Srgrimes printf("++ %d ", (*list)[count-1]); 5171590Srgrimes fflush(stdout); 5181590Srgrimes while (*t && isdigit(*t)) 5191590Srgrimes t++; 5201590Srgrimes if (*t != ',') 5211590Srgrimes break; 5221590Srgrimes } 5231590Srgrimes (*list)[count] = 0; 5241590Srgrimes return(t - 1); 5251590Srgrimes} 5261590Srgrimes 52795618Smarkm/* 52895618Smarkm * num = number p points to; if (strict) complain 52995618Smarkm * returns pointer to end of num 53095618Smarkm */ 5311590Srgrimeschar * 53295618Smarkmgetnum(int *num, char *p, int strict) 5331590Srgrimes{ 53495618Smarkm char *t = p; 5351590Srgrimes 5361590Srgrimes if (!isdigit(*++t)) { 5371590Srgrimes if (strict || *t == '-' || *t == '+') 53827953Scharnier errx(1, "option %.1s requires an unsigned integer", p); 5391590Srgrimes *num = 0; 5401590Srgrimes return(p); 5411590Srgrimes } 5421590Srgrimes *num = atoi(t); 5431590Srgrimes while (*++t) 5441590Srgrimes if (!isdigit(*t)) 5451590Srgrimes break; 5461590Srgrimes return(--t); 5471590Srgrimes} 548