14d3c8f6aSBaptiste Daroussin /* $OpenBSD: misc.c,v 1.46 2015/12/07 14:12:46 espie Exp $ */ 2acc9d408SJuli Mallett /* $NetBSD: misc.c,v 1.6 1995/09/28 05:37:41 tls Exp $ */ 3acc9d408SJuli Mallett 4*8a16b7a1SPedro F. Giffuni /*- 5*8a16b7a1SPedro F. Giffuni * SPDX-License-Identifier: BSD-3-Clause 6*8a16b7a1SPedro F. Giffuni * 79b50d902SRodney W. Grimes * Copyright (c) 1989, 1993 89b50d902SRodney W. Grimes * The Regents of the University of California. All rights reserved. 99b50d902SRodney W. Grimes * 109b50d902SRodney W. Grimes * This code is derived from software contributed to Berkeley by 119b50d902SRodney W. Grimes * Ozan Yigit at York University. 129b50d902SRodney W. Grimes * 139b50d902SRodney W. Grimes * Redistribution and use in source and binary forms, with or without 149b50d902SRodney W. Grimes * modification, are permitted provided that the following conditions 159b50d902SRodney W. Grimes * are met: 169b50d902SRodney W. Grimes * 1. Redistributions of source code must retain the above copyright 179b50d902SRodney W. Grimes * notice, this list of conditions and the following disclaimer. 189b50d902SRodney W. Grimes * 2. Redistributions in binary form must reproduce the above copyright 199b50d902SRodney W. Grimes * notice, this list of conditions and the following disclaimer in the 209b50d902SRodney W. Grimes * documentation and/or other materials provided with the distribution. 21a841e1ebSBaptiste Daroussin * 3. Neither the name of the University nor the names of its contributors 229b50d902SRodney W. Grimes * may be used to endorse or promote products derived from this software 239b50d902SRodney W. Grimes * without specific prior written permission. 249b50d902SRodney W. Grimes * 259b50d902SRodney W. Grimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 269b50d902SRodney W. Grimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 279b50d902SRodney W. Grimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 289b50d902SRodney W. Grimes * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 299b50d902SRodney W. Grimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 309b50d902SRodney W. Grimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 319b50d902SRodney W. Grimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 329b50d902SRodney W. Grimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 339b50d902SRodney W. Grimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 349b50d902SRodney W. Grimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 359b50d902SRodney W. Grimes * SUCH DAMAGE. 369b50d902SRodney W. Grimes */ 3788497f0cSBaptiste Daroussin 38acc9d408SJuli Mallett #include <sys/cdefs.h> 39acc9d408SJuli Mallett __FBSDID("$FreeBSD$"); 409b50d902SRodney W. Grimes 419b50d902SRodney W. Grimes #include <sys/types.h> 42acc9d408SJuli Mallett #include <errno.h> 43acc9d408SJuli Mallett #include <unistd.h> 44a841e1ebSBaptiste Daroussin #include <stdarg.h> 459b50d902SRodney W. Grimes #include <stdio.h> 4688497f0cSBaptiste Daroussin #include <stdint.h> 479b50d902SRodney W. Grimes #include <stdlib.h> 48acc9d408SJuli Mallett #include <stddef.h> 499b50d902SRodney W. Grimes #include <string.h> 50acc9d408SJuli Mallett #include <err.h> 519b50d902SRodney W. Grimes #include "mdef.h" 529b50d902SRodney W. Grimes #include "stdd.h" 539b50d902SRodney W. Grimes #include "extern.h" 549b50d902SRodney W. Grimes #include "pathnames.h" 559b50d902SRodney W. Grimes 56acc9d408SJuli Mallett 57acc9d408SJuli Mallett char *ep; /* first free char in strspace */ 58acc9d408SJuli Mallett static char *strspace; /* string space for evaluation */ 59acc9d408SJuli Mallett char *endest; /* end of string space */ 60acc9d408SJuli Mallett static size_t strsize = STRSPMAX; 61acc9d408SJuli Mallett static size_t bufsize = BUFSIZE; 62acc9d408SJuli Mallett 63a841e1ebSBaptiste Daroussin unsigned char *buf; /* push-back buffer */ 64a841e1ebSBaptiste Daroussin unsigned char *bufbase; /* the base for current ilevel */ 65a841e1ebSBaptiste Daroussin unsigned char *bbase[MAXINP]; /* the base for each ilevel */ 66a841e1ebSBaptiste Daroussin unsigned char *bp; /* first available character */ 67a841e1ebSBaptiste Daroussin unsigned char *endpbb; /* end of push-back buffer */ 68acc9d408SJuli Mallett 6931129d4fSBaptiste Daroussin 709b50d902SRodney W. Grimes /* 719b50d902SRodney W. Grimes * find the index of second str in the first str. 729b50d902SRodney W. Grimes */ 73acc9d408SJuli Mallett ptrdiff_t 74bd2bfb58SJuli Mallett indx(const char *s1, const char *s2) 759b50d902SRodney W. Grimes { 76acc9d408SJuli Mallett char *t; 779b50d902SRodney W. Grimes 78acc9d408SJuli Mallett t = strstr(s1, s2); 79acc9d408SJuli Mallett if (t == NULL) 809b50d902SRodney W. Grimes return (-1); 81acc9d408SJuli Mallett else 82acc9d408SJuli Mallett return (t - s1); 839b50d902SRodney W. Grimes } 849b50d902SRodney W. Grimes /* 85a841e1ebSBaptiste Daroussin * pushback - push character back onto input 869b50d902SRodney W. Grimes */ 879b50d902SRodney W. Grimes void 88a841e1ebSBaptiste Daroussin pushback(int c) 899b50d902SRodney W. Grimes { 907c5eeb39SAndrey A. Chernov if (c == EOF) 91b63b4cdbSAndrey A. Chernov return; 92acc9d408SJuli Mallett if (bp >= endpbb) 93acc9d408SJuli Mallett enlarge_bufspace(); 949b50d902SRodney W. Grimes *bp++ = c; 959b50d902SRodney W. Grimes } 969b50d902SRodney W. Grimes 979b50d902SRodney W. Grimes /* 989b50d902SRodney W. Grimes * pbstr - push string back onto input 99a841e1ebSBaptiste Daroussin * pushback is replicated to improve 1009b50d902SRodney W. Grimes * performance. 1019b50d902SRodney W. Grimes */ 1029b50d902SRodney W. Grimes void 103bd2bfb58SJuli Mallett pbstr(const char *s) 1049b50d902SRodney W. Grimes { 105acc9d408SJuli Mallett size_t n; 1069b50d902SRodney W. Grimes 107acc9d408SJuli Mallett n = strlen(s); 108a841e1ebSBaptiste Daroussin while (endpbb - bp <= (long)n) 109acc9d408SJuli Mallett enlarge_bufspace(); 110acc9d408SJuli Mallett while (n > 0) 111acc9d408SJuli Mallett *bp++ = s[--n]; 1129b50d902SRodney W. Grimes } 1139b50d902SRodney W. Grimes 1149b50d902SRodney W. Grimes /* 1159b50d902SRodney W. Grimes * pbnum - convert number to string, push back on input. 1169b50d902SRodney W. Grimes */ 1179b50d902SRodney W. Grimes void 118bd2bfb58SJuli Mallett pbnum(int n) 1199b50d902SRodney W. Grimes { 120a841e1ebSBaptiste Daroussin pbnumbase(n, 10, 0); 121a841e1ebSBaptiste Daroussin } 122a841e1ebSBaptiste Daroussin 123a841e1ebSBaptiste Daroussin void 124a841e1ebSBaptiste Daroussin pbnumbase(int n, int base, int d) 125a841e1ebSBaptiste Daroussin { 126a841e1ebSBaptiste Daroussin static char digits[36] = "0123456789abcdefghijklmnopqrstuvwxyz"; 127acc9d408SJuli Mallett int num; 128a841e1ebSBaptiste Daroussin int printed = 0; 129a841e1ebSBaptiste Daroussin 130a841e1ebSBaptiste Daroussin if (base > 36) 131a841e1ebSBaptiste Daroussin m4errx(1, "base %d > 36: not supported.", base); 132a841e1ebSBaptiste Daroussin 133a841e1ebSBaptiste Daroussin if (base < 2) 134a841e1ebSBaptiste Daroussin m4errx(1, "bad base %d for conversion.", base); 1359b50d902SRodney W. Grimes 1369b50d902SRodney W. Grimes num = (n < 0) ? -n : n; 1379b50d902SRodney W. Grimes do { 138a841e1ebSBaptiste Daroussin pushback(digits[num % base]); 139a841e1ebSBaptiste Daroussin printed++; 1409b50d902SRodney W. Grimes } 141a841e1ebSBaptiste Daroussin while ((num /= base) > 0); 1429b50d902SRodney W. Grimes 1439b50d902SRodney W. Grimes if (n < 0) 144a841e1ebSBaptiste Daroussin printed++; 145a841e1ebSBaptiste Daroussin while (printed++ < d) 146a841e1ebSBaptiste Daroussin pushback('0'); 147a841e1ebSBaptiste Daroussin 148a841e1ebSBaptiste Daroussin if (n < 0) 149a841e1ebSBaptiste Daroussin pushback('-'); 1509b50d902SRodney W. Grimes } 1519b50d902SRodney W. Grimes 1529b50d902SRodney W. Grimes /* 153acc9d408SJuli Mallett * pbunsigned - convert unsigned long to string, push back on input. 154acc9d408SJuli Mallett */ 155acc9d408SJuli Mallett void 156bd2bfb58SJuli Mallett pbunsigned(unsigned long n) 157acc9d408SJuli Mallett { 158acc9d408SJuli Mallett do { 159a841e1ebSBaptiste Daroussin pushback(n % 10 + '0'); 160acc9d408SJuli Mallett } 161acc9d408SJuli Mallett while ((n /= 10) > 0); 162acc9d408SJuli Mallett } 163acc9d408SJuli Mallett 164acc9d408SJuli Mallett void 165d1fea89cSJuli Mallett initspaces(void) 166acc9d408SJuli Mallett { 167acc9d408SJuli Mallett int i; 168acc9d408SJuli Mallett 169a841e1ebSBaptiste Daroussin strspace = xalloc(strsize+1, NULL); 170acc9d408SJuli Mallett ep = strspace; 171acc9d408SJuli Mallett endest = strspace+strsize; 17288497f0cSBaptiste Daroussin buf = xalloc(bufsize, NULL); 173acc9d408SJuli Mallett bufbase = buf; 174acc9d408SJuli Mallett bp = buf; 175acc9d408SJuli Mallett endpbb = buf + bufsize; 176acc9d408SJuli Mallett for (i = 0; i < MAXINP; i++) 177acc9d408SJuli Mallett bbase[i] = buf; 178acc9d408SJuli Mallett } 179acc9d408SJuli Mallett 180acc9d408SJuli Mallett void 181d1fea89cSJuli Mallett enlarge_strspace(void) 182acc9d408SJuli Mallett { 183acc9d408SJuli Mallett char *newstrspace; 184acc9d408SJuli Mallett int i; 185acc9d408SJuli Mallett 186acc9d408SJuli Mallett strsize *= 2; 187acc9d408SJuli Mallett newstrspace = malloc(strsize + 1); 188acc9d408SJuli Mallett if (!newstrspace) 189acc9d408SJuli Mallett errx(1, "string space overflow"); 190acc9d408SJuli Mallett memcpy(newstrspace, strspace, strsize/2); 191acc9d408SJuli Mallett for (i = 0; i <= sp; i++) 19231129d4fSBaptiste Daroussin if (sstack[i] == STORAGE_STRSPACE) 193acc9d408SJuli Mallett mstack[i].sstr = (mstack[i].sstr - strspace) 194acc9d408SJuli Mallett + newstrspace; 195acc9d408SJuli Mallett ep = (ep-strspace) + newstrspace; 196acc9d408SJuli Mallett free(strspace); 197acc9d408SJuli Mallett strspace = newstrspace; 198acc9d408SJuli Mallett endest = strspace + strsize; 199acc9d408SJuli Mallett } 200acc9d408SJuli Mallett 201acc9d408SJuli Mallett void 202d1fea89cSJuli Mallett enlarge_bufspace(void) 203acc9d408SJuli Mallett { 204a841e1ebSBaptiste Daroussin unsigned char *newbuf; 205acc9d408SJuli Mallett int i; 206acc9d408SJuli Mallett 207a841e1ebSBaptiste Daroussin bufsize += bufsize/2; 208a841e1ebSBaptiste Daroussin newbuf = xrealloc(buf, bufsize, "too many characters pushed back"); 209acc9d408SJuli Mallett for (i = 0; i < MAXINP; i++) 210acc9d408SJuli Mallett bbase[i] = (bbase[i]-buf)+newbuf; 211acc9d408SJuli Mallett bp = (bp-buf)+newbuf; 212acc9d408SJuli Mallett bufbase = (bufbase-buf)+newbuf; 213acc9d408SJuli Mallett buf = newbuf; 214acc9d408SJuli Mallett endpbb = buf+bufsize; 215acc9d408SJuli Mallett } 216acc9d408SJuli Mallett 217acc9d408SJuli Mallett /* 2189b50d902SRodney W. Grimes * chrsave - put single char on string space 2199b50d902SRodney W. Grimes */ 2209b50d902SRodney W. Grimes void 221bd2bfb58SJuli Mallett chrsave(int c) 2229b50d902SRodney W. Grimes { 223acc9d408SJuli Mallett if (ep >= endest) 224acc9d408SJuli Mallett enlarge_strspace(); 2259b50d902SRodney W. Grimes *ep++ = c; 2269b50d902SRodney W. Grimes } 2279b50d902SRodney W. Grimes 2289b50d902SRodney W. Grimes /* 2299b50d902SRodney W. Grimes * read in a diversion file, and dispose it. 2309b50d902SRodney W. Grimes */ 2319b50d902SRodney W. Grimes void 232bd2bfb58SJuli Mallett getdiv(int n) 2339b50d902SRodney W. Grimes { 234acc9d408SJuli Mallett int c; 2359b50d902SRodney W. Grimes 2369b50d902SRodney W. Grimes if (active == outfile[n]) 237a841e1ebSBaptiste Daroussin m4errx(1, "undivert: diversion still active."); 238acc9d408SJuli Mallett rewind(outfile[n]); 239acc9d408SJuli Mallett while ((c = getc(outfile[n])) != EOF) 240acc9d408SJuli Mallett putc(c, active); 2419b50d902SRodney W. Grimes (void) fclose(outfile[n]); 2429b50d902SRodney W. Grimes outfile[n] = NULL; 2439b50d902SRodney W. Grimes } 2449b50d902SRodney W. Grimes 2459b50d902SRodney W. Grimes void 24688497f0cSBaptiste Daroussin onintr(int signo __unused) 2479b50d902SRodney W. Grimes { 248acc9d408SJuli Mallett #define intrmessage "m4: interrupted.\n" 249acc9d408SJuli Mallett write(STDERR_FILENO, intrmessage, sizeof(intrmessage)-1); 250acc9d408SJuli Mallett _exit(1); 2519b50d902SRodney W. Grimes } 2529b50d902SRodney W. Grimes 2539b50d902SRodney W. Grimes /* 2549b50d902SRodney W. Grimes * killdiv - get rid of the diversion files 2559b50d902SRodney W. Grimes */ 2569b50d902SRodney W. Grimes void 257d1fea89cSJuli Mallett killdiv(void) 2589b50d902SRodney W. Grimes { 259acc9d408SJuli Mallett int n; 2609b50d902SRodney W. Grimes 261acc9d408SJuli Mallett for (n = 0; n < maxout; n++) 2629b50d902SRodney W. Grimes if (outfile[n] != NULL) { 2639b50d902SRodney W. Grimes (void) fclose(outfile[n]); 2649b50d902SRodney W. Grimes } 2659b50d902SRodney W. Grimes } 2669b50d902SRodney W. Grimes 267a841e1ebSBaptiste Daroussin extern char *__progname; 268a841e1ebSBaptiste Daroussin 269a841e1ebSBaptiste Daroussin void 27031129d4fSBaptiste Daroussin m4errx(int eval, const char *fmt, ...) 271a841e1ebSBaptiste Daroussin { 272a841e1ebSBaptiste Daroussin fprintf(stderr, "%s: ", __progname); 273a841e1ebSBaptiste Daroussin fprintf(stderr, "%s at line %lu: ", CURRENT_NAME, CURRENT_LINE); 274a841e1ebSBaptiste Daroussin if (fmt != NULL) { 275a841e1ebSBaptiste Daroussin va_list ap; 276a841e1ebSBaptiste Daroussin 277a841e1ebSBaptiste Daroussin va_start(ap, fmt); 278a841e1ebSBaptiste Daroussin vfprintf(stderr, fmt, ap); 279a841e1ebSBaptiste Daroussin va_end(ap); 280a841e1ebSBaptiste Daroussin } 281a841e1ebSBaptiste Daroussin fprintf(stderr, "\n"); 28231129d4fSBaptiste Daroussin exit(eval); 283a841e1ebSBaptiste Daroussin } 284a841e1ebSBaptiste Daroussin 285acc9d408SJuli Mallett /* 286acc9d408SJuli Mallett * resizedivs: allocate more diversion files */ 2879b50d902SRodney W. Grimes void 288bd2bfb58SJuli Mallett resizedivs(int n) 289164c01f0SGregory Neil Shapiro { 290acc9d408SJuli Mallett int i; 291acc9d408SJuli Mallett 29288497f0cSBaptiste Daroussin outfile = xreallocarray(outfile, n, sizeof(FILE *), 293a841e1ebSBaptiste Daroussin "too many diverts %d", n); 294acc9d408SJuli Mallett for (i = maxout; i < n; i++) 295acc9d408SJuli Mallett outfile[i] = NULL; 296acc9d408SJuli Mallett maxout = n; 297164c01f0SGregory Neil Shapiro } 298acc9d408SJuli Mallett 299acc9d408SJuli Mallett void * 300a841e1ebSBaptiste Daroussin xalloc(size_t n, const char *fmt, ...) 301acc9d408SJuli Mallett { 302a841e1ebSBaptiste Daroussin void *p = malloc(n); 303acc9d408SJuli Mallett 304a841e1ebSBaptiste Daroussin if (p == NULL) { 305a841e1ebSBaptiste Daroussin if (fmt == NULL) 306acc9d408SJuli Mallett err(1, "malloc"); 307a841e1ebSBaptiste Daroussin else { 308a841e1ebSBaptiste Daroussin va_list va; 309a841e1ebSBaptiste Daroussin 310a841e1ebSBaptiste Daroussin va_start(va, fmt); 311a841e1ebSBaptiste Daroussin verr(1, fmt, va); 312a841e1ebSBaptiste Daroussin va_end(va); 313a841e1ebSBaptiste Daroussin } 314a841e1ebSBaptiste Daroussin } 315a841e1ebSBaptiste Daroussin return p; 316a841e1ebSBaptiste Daroussin } 317a841e1ebSBaptiste Daroussin 318a841e1ebSBaptiste Daroussin void * 31988497f0cSBaptiste Daroussin xcalloc(size_t n, size_t s, const char *fmt, ...) 32088497f0cSBaptiste Daroussin { 32188497f0cSBaptiste Daroussin void *p = calloc(n, s); 32288497f0cSBaptiste Daroussin 32388497f0cSBaptiste Daroussin if (p == NULL) { 32488497f0cSBaptiste Daroussin if (fmt == NULL) 32588497f0cSBaptiste Daroussin err(1, "calloc"); 32688497f0cSBaptiste Daroussin else { 32788497f0cSBaptiste Daroussin va_list va; 32888497f0cSBaptiste Daroussin 32988497f0cSBaptiste Daroussin va_start(va, fmt); 33088497f0cSBaptiste Daroussin verr(1, fmt, va); 33188497f0cSBaptiste Daroussin va_end(va); 33288497f0cSBaptiste Daroussin } 33388497f0cSBaptiste Daroussin } 33488497f0cSBaptiste Daroussin return p; 33588497f0cSBaptiste Daroussin } 33688497f0cSBaptiste Daroussin 33788497f0cSBaptiste Daroussin void * 338a841e1ebSBaptiste Daroussin xrealloc(void *old, size_t n, const char *fmt, ...) 339a841e1ebSBaptiste Daroussin { 340a841e1ebSBaptiste Daroussin char *p = realloc(old, n); 341a841e1ebSBaptiste Daroussin 342a841e1ebSBaptiste Daroussin if (p == NULL) { 343a841e1ebSBaptiste Daroussin free(old); 344a841e1ebSBaptiste Daroussin if (fmt == NULL) 345a841e1ebSBaptiste Daroussin err(1, "realloc"); 346a841e1ebSBaptiste Daroussin else { 347a841e1ebSBaptiste Daroussin va_list va; 348a841e1ebSBaptiste Daroussin 349a841e1ebSBaptiste Daroussin va_start(va, fmt); 350a841e1ebSBaptiste Daroussin verr(1, fmt, va); 351a841e1ebSBaptiste Daroussin va_end(va); 352a841e1ebSBaptiste Daroussin } 353a841e1ebSBaptiste Daroussin } 354acc9d408SJuli Mallett return p; 355acc9d408SJuli Mallett } 356acc9d408SJuli Mallett 35788497f0cSBaptiste Daroussin void * 35888497f0cSBaptiste Daroussin xreallocarray(void *old, size_t s1, size_t s2, const char *fmt, ...) 35988497f0cSBaptiste Daroussin { 36088497f0cSBaptiste Daroussin void *p = reallocarray(old, s1, s2); 36188497f0cSBaptiste Daroussin 36288497f0cSBaptiste Daroussin if (p == NULL) { 36388497f0cSBaptiste Daroussin free(old); 36488497f0cSBaptiste Daroussin if (fmt == NULL) 36588497f0cSBaptiste Daroussin err(1, "reallocarray"); 36688497f0cSBaptiste Daroussin else { 36788497f0cSBaptiste Daroussin va_list va; 36888497f0cSBaptiste Daroussin 36988497f0cSBaptiste Daroussin va_start(va, fmt); 37088497f0cSBaptiste Daroussin verr(1, fmt, va); 37188497f0cSBaptiste Daroussin va_end(va); 37288497f0cSBaptiste Daroussin } 37388497f0cSBaptiste Daroussin } 37488497f0cSBaptiste Daroussin return p; 37588497f0cSBaptiste Daroussin } 37688497f0cSBaptiste Daroussin 377acc9d408SJuli Mallett char * 378bd2bfb58SJuli Mallett xstrdup(const char *s) 379acc9d408SJuli Mallett { 380acc9d408SJuli Mallett char *p = strdup(s); 381acc9d408SJuli Mallett if (p == NULL) 382acc9d408SJuli Mallett err(1, "strdup"); 383acc9d408SJuli Mallett return p; 384164c01f0SGregory Neil Shapiro } 385164c01f0SGregory Neil Shapiro 386164c01f0SGregory Neil Shapiro void 387d1fea89cSJuli Mallett usage(void) 3889b50d902SRodney W. Grimes { 389a841e1ebSBaptiste Daroussin fprintf(stderr, "usage: m4 [-gPs] [-Dname[=value]] [-d flags] " 390a841e1ebSBaptiste Daroussin "[-I dirname] [-o filename]\n" 391a841e1ebSBaptiste Daroussin "\t[-t macro] [-Uname] [file ...]\n"); 3929b50d902SRodney W. Grimes exit(1); 3939b50d902SRodney W. Grimes } 394acc9d408SJuli Mallett 395acc9d408SJuli Mallett int 396bd2bfb58SJuli Mallett obtain_char(struct input_file *f) 397acc9d408SJuli Mallett { 398acc9d408SJuli Mallett if (f->c == EOF) 399acc9d408SJuli Mallett return EOF; 400acc9d408SJuli Mallett 401acc9d408SJuli Mallett f->c = fgetc(f->file); 402a841e1ebSBaptiste Daroussin if (f->c == '\n') 403a841e1ebSBaptiste Daroussin f->lineno++; 404a841e1ebSBaptiste Daroussin 405acc9d408SJuli Mallett return f->c; 406acc9d408SJuli Mallett } 407acc9d408SJuli Mallett 408acc9d408SJuli Mallett void 409bd2bfb58SJuli Mallett set_input(struct input_file *f, FILE *real, const char *name) 410acc9d408SJuli Mallett { 411acc9d408SJuli Mallett f->file = real; 412acc9d408SJuli Mallett f->lineno = 1; 413acc9d408SJuli Mallett f->c = 0; 414acc9d408SJuli Mallett f->name = xstrdup(name); 415a841e1ebSBaptiste Daroussin emit_synchline(); 416a841e1ebSBaptiste Daroussin } 417a841e1ebSBaptiste Daroussin 418a841e1ebSBaptiste Daroussin void 419a841e1ebSBaptiste Daroussin do_emit_synchline(void) 420a841e1ebSBaptiste Daroussin { 421a841e1ebSBaptiste Daroussin fprintf(active, "#line %lu \"%s\"\n", 422a841e1ebSBaptiste Daroussin infile[ilevel].lineno, infile[ilevel].name); 423a841e1ebSBaptiste Daroussin infile[ilevel].synch_lineno = infile[ilevel].lineno; 424acc9d408SJuli Mallett } 425acc9d408SJuli Mallett 426acc9d408SJuli Mallett void 427bd2bfb58SJuli Mallett release_input(struct input_file *f) 428acc9d408SJuli Mallett { 4294d3c8f6aSBaptiste Daroussin if (ferror(f->file)) 4304d3c8f6aSBaptiste Daroussin errx(1, "Fatal error reading from %s\n", f->name); 431acc9d408SJuli Mallett if (f->file != stdin) 432acc9d408SJuli Mallett fclose(f->file); 433acc9d408SJuli Mallett f->c = EOF; 434acc9d408SJuli Mallett /* 435acc9d408SJuli Mallett * XXX can't free filename, as there might still be 436acc9d408SJuli Mallett * error information pointing to it. 437acc9d408SJuli Mallett */ 438acc9d408SJuli Mallett } 439acc9d408SJuli Mallett 440acc9d408SJuli Mallett void 441bd2bfb58SJuli Mallett doprintlineno(struct input_file *f) 442acc9d408SJuli Mallett { 443acc9d408SJuli Mallett pbunsigned(f->lineno); 444acc9d408SJuli Mallett } 445acc9d408SJuli Mallett 446acc9d408SJuli Mallett void 447bd2bfb58SJuli Mallett doprintfilename(struct input_file *f) 448acc9d408SJuli Mallett { 449acc9d408SJuli Mallett pbstr(rquote); 450acc9d408SJuli Mallett pbstr(f->name); 451acc9d408SJuli Mallett pbstr(lquote); 452acc9d408SJuli Mallett } 453acc9d408SJuli Mallett 454acc9d408SJuli Mallett /* 455acc9d408SJuli Mallett * buffer_mark/dump_buffer: allows one to save a mark in a buffer, 456acc9d408SJuli Mallett * and later dump everything that was added since then to a file. 457acc9d408SJuli Mallett */ 458acc9d408SJuli Mallett size_t 459d1fea89cSJuli Mallett buffer_mark(void) 460acc9d408SJuli Mallett { 461acc9d408SJuli Mallett return bp - buf; 462acc9d408SJuli Mallett } 463acc9d408SJuli Mallett 464acc9d408SJuli Mallett 465acc9d408SJuli Mallett void 466bd2bfb58SJuli Mallett dump_buffer(FILE *f, size_t m) 467acc9d408SJuli Mallett { 468a841e1ebSBaptiste Daroussin unsigned char *s; 469acc9d408SJuli Mallett 470a841e1ebSBaptiste Daroussin for (s = bp; s-buf > (long)m;) 471acc9d408SJuli Mallett fputc(*--s, f); 472acc9d408SJuli Mallett } 473