1 /* $OpenBSD: shf.c,v 1.16 2013/04/19 17:36:09 millert Exp $ */ 2 3 /*- 4 * Copyright (c) 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2011, 5 * 2012, 2013, 2015, 2016, 2017, 2018 6 * mirabilos <m (at) mirbsd.org> 7 * Copyright (c) 2015 8 * Daniel Richard G. <skunk (at) iSKUNK.ORG> 9 * 10 * Provided that these terms and disclaimer and all copyright notices 11 * are retained or reproduced in an accompanying document, permission 12 * is granted to deal in this work without restriction, including un- 13 * limited rights to use, publicly perform, distribute, sell, modify, 14 * merge, give away, or sublicence. 15 * 16 * This work is provided "AS IS" and WITHOUT WARRANTY of any kind, to 17 * the utmost extent permitted by applicable law, neither express nor 18 * implied; without malicious intent or gross negligence. In no event 19 * may a licensor, author or contributor be held liable for indirect, 20 * direct, other damage, loss, or other issues arising in any way out 21 * of dealing in the work, even if advised of the possibility of such 22 * damage or existence of a defect, except proven that it results out 23 * of said person's immediate fault when using the work as intended. 24 *- 25 * Use %zX instead of %p and floating point isn't supported at all. 26 */ 27 28 #include "sh.h" 29 30 __RCSID("$MirOS: src/bin/mksh/shf.c,v 1.98 2018/08/10 02:53:39 tg Exp $"); 31 32 /* flags to shf_emptybuf() */ 33 #define EB_READSW 0x01 /* about to switch to reading */ 34 #define EB_GROW 0x02 /* grow buffer if necessary (STRING+DYNAMIC) */ 35 36 /* 37 * Replacement stdio routines. Stdio is too flakey on too many machines 38 * to be useful when you have multiple processes using the same underlying 39 * file descriptors. 40 */ 41 42 static int shf_fillbuf(struct shf *); 43 static int shf_emptybuf(struct shf *, int); 44 45 /* 46 * Open a file. First three args are for open(), last arg is flags for 47 * this package. Returns NULL if file could not be opened, or if a dup 48 * fails. 49 */ 50 struct shf * 51 shf_open(const char *name, int oflags, int mode, int sflags) 52 { 53 struct shf *shf; 54 ssize_t bsize = 55 /* at most 512 */ 56 sflags & SHF_UNBUF ? (sflags & SHF_RD ? 1 : 0) : SHF_BSIZE; 57 int fd, eno; 58 59 /* Done before open so if alloca fails, fd won't be lost. */ 60 shf = alloc(sizeof(struct shf) + bsize, ATEMP); 61 shf->areap = ATEMP; 62 shf->buf = (unsigned char *)&shf[1]; 63 shf->bsize = bsize; 64 shf->flags = SHF_ALLOCS; 65 /* Rest filled in by reopen. */ 66 67 fd = binopen3(name, oflags, mode); 68 if (fd < 0) { 69 eno = errno; 70 afree(shf, shf->areap); 71 errno = eno; 72 return (NULL); 73 } 74 if ((sflags & SHF_MAPHI) && fd < FDBASE) { 75 int nfd; 76 77 nfd = fcntl(fd, F_DUPFD, FDBASE); 78 eno = errno; 79 close(fd); 80 if (nfd < 0) { 81 afree(shf, shf->areap); 82 errno = eno; 83 return (NULL); 84 } 85 fd = nfd; 86 } 87 sflags &= ~SHF_ACCMODE; 88 sflags |= (oflags & O_ACCMODE) == O_RDONLY ? SHF_RD : 89 ((oflags & O_ACCMODE) == O_WRONLY ? SHF_WR : SHF_RDWR); 90 91 return (shf_reopen(fd, sflags, shf)); 92 } 93 94 /* helper function for shf_fdopen and shf_reopen */ 95 static void 96 shf_open_hlp(int fd, int *sflagsp, const char *where) 97 { 98 int sflags = *sflagsp; 99 100 /* use fcntl() to figure out correct read/write flags */ 101 if (sflags & SHF_GETFL) { 102 int flags = fcntl(fd, F_GETFL, 0); 103 104 if (flags < 0) 105 /* will get an error on first read/write */ 106 sflags |= SHF_RDWR; 107 else { 108 switch (flags & O_ACCMODE) { 109 case O_RDONLY: 110 sflags |= SHF_RD; 111 break; 112 case O_WRONLY: 113 sflags |= SHF_WR; 114 break; 115 case O_RDWR: 116 sflags |= SHF_RDWR; 117 break; 118 } 119 } 120 *sflagsp = sflags; 121 } 122 123 if (!(sflags & (SHF_RD | SHF_WR))) 124 internal_errorf(Tf_sD_s, where, "missing read/write"); 125 } 126 127 /* Set up the shf structure for a file descriptor. Doesn't fail. */ 128 struct shf * 129 shf_fdopen(int fd, int sflags, struct shf *shf) 130 { 131 ssize_t bsize = 132 /* at most 512 */ 133 sflags & SHF_UNBUF ? (sflags & SHF_RD ? 1 : 0) : SHF_BSIZE; 134 135 shf_open_hlp(fd, &sflags, "shf_fdopen"); 136 if (shf) { 137 if (bsize) { 138 shf->buf = alloc(bsize, ATEMP); 139 sflags |= SHF_ALLOCB; 140 } else 141 shf->buf = NULL; 142 } else { 143 shf = alloc(sizeof(struct shf) + bsize, ATEMP); 144 shf->buf = (unsigned char *)&shf[1]; 145 sflags |= SHF_ALLOCS; 146 } 147 shf->areap = ATEMP; 148 shf->fd = fd; 149 shf->rp = shf->wp = shf->buf; 150 shf->rnleft = 0; 151 shf->rbsize = bsize; 152 shf->wnleft = 0; /* force call to shf_emptybuf() */ 153 shf->wbsize = sflags & SHF_UNBUF ? 0 : bsize; 154 shf->flags = sflags; 155 shf->errnosv = 0; 156 shf->bsize = bsize; 157 if (sflags & SHF_CLEXEC) 158 fcntl(fd, F_SETFD, FD_CLOEXEC); 159 return (shf); 160 } 161 162 /* Set up an existing shf (and buffer) to use the given fd */ 163 struct shf * 164 shf_reopen(int fd, int sflags, struct shf *shf) 165 { 166 ssize_t bsize = 167 /* at most 512 */ 168 sflags & SHF_UNBUF ? (sflags & SHF_RD ? 1 : 0) : SHF_BSIZE; 169 170 shf_open_hlp(fd, &sflags, "shf_reopen"); 171 if (!shf || !shf->buf || shf->bsize < bsize) 172 internal_errorf(Tf_sD_s, "shf_reopen", Tbad_bsize); 173 174 /* assumes shf->buf and shf->bsize already set up */ 175 shf->fd = fd; 176 shf->rp = shf->wp = shf->buf; 177 shf->rnleft = 0; 178 shf->rbsize = bsize; 179 shf->wnleft = 0; /* force call to shf_emptybuf() */ 180 shf->wbsize = sflags & SHF_UNBUF ? 0 : bsize; 181 shf->flags = (shf->flags & (SHF_ALLOCS | SHF_ALLOCB)) | sflags; 182 shf->errnosv = 0; 183 if (sflags & SHF_CLEXEC) 184 fcntl(fd, F_SETFD, FD_CLOEXEC); 185 return (shf); 186 } 187 188 /* 189 * Open a string for reading or writing. If reading, bsize is the number 190 * of bytes that can be read. If writing, bsize is the maximum number of 191 * bytes that can be written. If shf is not NULL, it is filled in and 192 * returned, if it is NULL, shf is allocated. If writing and buf is NULL 193 * and SHF_DYNAMIC is set, the buffer is allocated (if bsize > 0, it is 194 * used for the initial size). Doesn't fail. 195 * When writing, a byte is reserved for a trailing NUL - see shf_sclose(). 196 */ 197 struct shf * 198 shf_sopen(char *buf, ssize_t bsize, int sflags, struct shf *shf) 199 { 200 /* can't have a read+write string */ 201 if (!(!(sflags & SHF_RD) ^ !(sflags & SHF_WR))) 202 internal_errorf(Tf_flags, "shf_sopen", 203 (unsigned int)sflags); 204 205 if (!shf) { 206 shf = alloc(sizeof(struct shf), ATEMP); 207 sflags |= SHF_ALLOCS; 208 } 209 shf->areap = ATEMP; 210 if (!buf && (sflags & SHF_WR) && (sflags & SHF_DYNAMIC)) { 211 if (bsize <= 0) 212 bsize = 64; 213 sflags |= SHF_ALLOCB; 214 buf = alloc(bsize, shf->areap); 215 } 216 shf->fd = -1; 217 shf->buf = shf->rp = shf->wp = (unsigned char *)buf; 218 shf->rnleft = bsize; 219 shf->rbsize = bsize; 220 shf->wnleft = bsize - 1; /* space for a '\0' */ 221 shf->wbsize = bsize; 222 shf->flags = sflags | SHF_STRING; 223 shf->errnosv = 0; 224 shf->bsize = bsize; 225 226 return (shf); 227 } 228 229 /* Flush and close file descriptor, free the shf structure */ 230 int 231 shf_close(struct shf *shf) 232 { 233 int ret = 0; 234 235 if (shf->fd >= 0) { 236 ret = shf_flush(shf); 237 if (close(shf->fd) < 0) 238 ret = -1; 239 } 240 if (shf->flags & SHF_ALLOCS) 241 afree(shf, shf->areap); 242 else if (shf->flags & SHF_ALLOCB) 243 afree(shf->buf, shf->areap); 244 245 return (ret); 246 } 247 248 /* Flush and close file descriptor, don't free file structure */ 249 int 250 shf_fdclose(struct shf *shf) 251 { 252 int ret = 0; 253 254 if (shf->fd >= 0) { 255 ret = shf_flush(shf); 256 if (close(shf->fd) < 0) 257 ret = -1; 258 shf->rnleft = 0; 259 shf->rp = shf->buf; 260 shf->wnleft = 0; 261 shf->fd = -1; 262 } 263 264 return (ret); 265 } 266 267 /* 268 * Close a string - if it was opened for writing, it is NUL terminated; 269 * returns a pointer to the string and frees shf if it was allocated 270 * (does not free string if it was allocated). 271 */ 272 char * 273 shf_sclose(struct shf *shf) 274 { 275 unsigned char *s = shf->buf; 276 277 /* NUL terminate */ 278 if (shf->flags & SHF_WR) { 279 shf->wnleft++; 280 shf_putc('\0', shf); 281 } 282 if (shf->flags & SHF_ALLOCS) 283 afree(shf, shf->areap); 284 return ((char *)s); 285 } 286 287 /* 288 * Un-read what has been read but not examined, or write what has been 289 * buffered. Returns 0 for success, -1 for (write) error. 290 */ 291 int 292 shf_flush(struct shf *shf) 293 { 294 int rv = 0; 295 296 if (shf->flags & SHF_STRING) 297 rv = (shf->flags & SHF_WR) ? -1 : 0; 298 else if (shf->fd < 0) 299 internal_errorf(Tf_sD_s, "shf_flush", "no fd"); 300 else if (shf->flags & SHF_ERROR) { 301 errno = shf->errnosv; 302 rv = -1; 303 } else if (shf->flags & SHF_READING) { 304 shf->flags &= ~(SHF_EOF | SHF_READING); 305 if (shf->rnleft > 0) { 306 if (lseek(shf->fd, (off_t)-shf->rnleft, 307 SEEK_CUR) == -1) { 308 shf->flags |= SHF_ERROR; 309 shf->errnosv = errno; 310 rv = -1; 311 } 312 shf->rnleft = 0; 313 shf->rp = shf->buf; 314 } 315 } else if (shf->flags & SHF_WRITING) 316 rv = shf_emptybuf(shf, 0); 317 318 return (rv); 319 } 320 321 /* 322 * Write out any buffered data. If currently reading, flushes the read 323 * buffer. Returns 0 for success, -1 for (write) error. 324 */ 325 static int 326 shf_emptybuf(struct shf *shf, int flags) 327 { 328 int ret = 0; 329 330 if (!(shf->flags & SHF_STRING) && shf->fd < 0) 331 internal_errorf(Tf_sD_s, "shf_emptybuf", "no fd"); 332 333 if (shf->flags & SHF_ERROR) { 334 errno = shf->errnosv; 335 return (-1); 336 } 337 338 if (shf->flags & SHF_READING) { 339 if (flags & EB_READSW) 340 /* doesn't happen */ 341 return (0); 342 ret = shf_flush(shf); 343 shf->flags &= ~SHF_READING; 344 } 345 if (shf->flags & SHF_STRING) { 346 unsigned char *nbuf; 347 348 /* 349 * Note that we assume SHF_ALLOCS is not set if 350 * SHF_ALLOCB is set... (changing the shf pointer could 351 * cause problems) 352 */ 353 if (!(flags & EB_GROW) || !(shf->flags & SHF_DYNAMIC) || 354 !(shf->flags & SHF_ALLOCB)) 355 return (-1); 356 /* allocate more space for buffer */ 357 nbuf = aresize2(shf->buf, 2, shf->wbsize, shf->areap); 358 shf->rp = nbuf + (shf->rp - shf->buf); 359 shf->wp = nbuf + (shf->wp - shf->buf); 360 shf->rbsize += shf->wbsize; 361 shf->wnleft += shf->wbsize; 362 shf->wbsize <<= 1; 363 shf->buf = nbuf; 364 } else { 365 if (shf->flags & SHF_WRITING) { 366 ssize_t n, ntowrite = shf->wp - shf->buf; 367 unsigned char *buf = shf->buf; 368 369 while (ntowrite > 0) { 370 n = write(shf->fd, buf, ntowrite); 371 if (n < 0) { 372 if (errno == EINTR && 373 !(shf->flags & SHF_INTERRUPT)) 374 continue; 375 shf->flags |= SHF_ERROR; 376 shf->errnosv = errno; 377 shf->wnleft = 0; 378 if (buf != shf->buf) { 379 /* 380 * allow a second flush 381 * to work 382 */ 383 memmove(shf->buf, buf, 384 ntowrite); 385 shf->wp = shf->buf + ntowrite; 386 } 387 return (-1); 388 } 389 buf += n; 390 ntowrite -= n; 391 } 392 if (flags & EB_READSW) { 393 shf->wp = shf->buf; 394 shf->wnleft = 0; 395 shf->flags &= ~SHF_WRITING; 396 return (0); 397 } 398 } 399 shf->wp = shf->buf; 400 shf->wnleft = shf->wbsize; 401 } 402 shf->flags |= SHF_WRITING; 403 404 return (ret); 405 } 406 407 /* Fill up a read buffer. Returns -1 for a read error, 0 otherwise. */ 408 static int 409 shf_fillbuf(struct shf *shf) 410 { 411 ssize_t n; 412 413 if (shf->flags & SHF_STRING) 414 return (0); 415 416 if (shf->fd < 0) 417 internal_errorf(Tf_sD_s, "shf_fillbuf", "no fd"); 418 419 if (shf->flags & (SHF_EOF | SHF_ERROR)) { 420 if (shf->flags & SHF_ERROR) 421 errno = shf->errnosv; 422 return (-1); 423 } 424 425 if ((shf->flags & SHF_WRITING) && shf_emptybuf(shf, EB_READSW) == -1) 426 return (-1); 427 428 shf->flags |= SHF_READING; 429 430 shf->rp = shf->buf; 431 while (/* CONSTCOND */ 1) { 432 n = blocking_read(shf->fd, (char *)shf->buf, shf->rbsize); 433 if (n < 0 && errno == EINTR && !(shf->flags & SHF_INTERRUPT)) 434 continue; 435 break; 436 } 437 if (n < 0) { 438 shf->flags |= SHF_ERROR; 439 shf->errnosv = errno; 440 shf->rnleft = 0; 441 shf->rp = shf->buf; 442 return (-1); 443 } 444 if ((shf->rnleft = n) == 0) 445 shf->flags |= SHF_EOF; 446 return (0); 447 } 448 449 /* 450 * Read a buffer from shf. Returns the number of bytes read into buf, if 451 * no bytes were read, returns 0 if end of file was seen, -1 if a read 452 * error occurred. 453 */ 454 ssize_t 455 shf_read(char *buf, ssize_t bsize, struct shf *shf) 456 { 457 ssize_t ncopy, orig_bsize = bsize; 458 459 if (!(shf->flags & SHF_RD)) 460 internal_errorf(Tf_flags, Tshf_read, 461 (unsigned int)shf->flags); 462 463 if (bsize <= 0) 464 internal_errorf(Tf_szs, Tshf_read, bsize, Tbsize); 465 466 while (bsize > 0) { 467 if (shf->rnleft == 0 && 468 (shf_fillbuf(shf) == -1 || shf->rnleft == 0)) 469 break; 470 ncopy = shf->rnleft; 471 if (ncopy > bsize) 472 ncopy = bsize; 473 memcpy(buf, shf->rp, ncopy); 474 buf += ncopy; 475 bsize -= ncopy; 476 shf->rp += ncopy; 477 shf->rnleft -= ncopy; 478 } 479 /* Note: fread(3S) returns 0 for errors - this doesn't */ 480 return (orig_bsize == bsize ? (shf_error(shf) ? -1 : 0) : 481 orig_bsize - bsize); 482 } 483 484 /* 485 * Read up to a newline or -1. The newline is put in buf; buf is always 486 * NUL terminated. Returns NULL on read error or if nothing was read 487 * before end of file, returns a pointer to the NUL byte in buf 488 * otherwise. 489 */ 490 char * 491 shf_getse(char *buf, ssize_t bsize, struct shf *shf) 492 { 493 unsigned char *end; 494 ssize_t ncopy; 495 char *orig_buf = buf; 496 497 if (!(shf->flags & SHF_RD)) 498 internal_errorf(Tf_flags, "shf_getse", 499 (unsigned int)shf->flags); 500 501 if (bsize <= 0) 502 return (NULL); 503 504 /* save room for NUL */ 505 --bsize; 506 do { 507 if (shf->rnleft == 0) { 508 if (shf_fillbuf(shf) == -1) 509 return (NULL); 510 if (shf->rnleft == 0) { 511 *buf = '\0'; 512 return (buf == orig_buf ? NULL : buf); 513 } 514 } 515 end = (unsigned char *)memchr((char *)shf->rp, '\n', 516 shf->rnleft); 517 ncopy = end ? end - shf->rp + 1 : shf->rnleft; 518 if (ncopy > bsize) 519 ncopy = bsize; 520 memcpy(buf, (char *) shf->rp, ncopy); 521 shf->rp += ncopy; 522 shf->rnleft -= ncopy; 523 buf += ncopy; 524 bsize -= ncopy; 525 #ifdef MKSH_WITH_TEXTMODE 526 if (end && buf > orig_buf + 1 && buf[-2] == '\r') { 527 buf--; 528 bsize++; 529 buf[-1] = '\n'; 530 } 531 #endif 532 } while (!end && bsize); 533 #ifdef MKSH_WITH_TEXTMODE 534 if (!bsize && buf[-1] == '\r') { 535 int c = shf_getc(shf); 536 if (c == '\n') 537 buf[-1] = '\n'; 538 else if (c != -1) 539 shf_ungetc(c, shf); 540 } 541 #endif 542 *buf = '\0'; 543 return (buf); 544 } 545 546 /* Returns the char read. Returns -1 for error and end of file. */ 547 int 548 shf_getchar(struct shf *shf) 549 { 550 if (!(shf->flags & SHF_RD)) 551 internal_errorf(Tf_flags, "shf_getchar", 552 (unsigned int)shf->flags); 553 554 if (shf->rnleft == 0 && (shf_fillbuf(shf) == -1 || shf->rnleft == 0)) 555 return (-1); 556 --shf->rnleft; 557 return (ord(*shf->rp++)); 558 } 559 560 /* 561 * Put a character back in the input stream. Returns the character if 562 * successful, -1 if there is no room. 563 */ 564 int 565 shf_ungetc(int c, struct shf *shf) 566 { 567 if (!(shf->flags & SHF_RD)) 568 internal_errorf(Tf_flags, "shf_ungetc", 569 (unsigned int)shf->flags); 570 571 if ((shf->flags & SHF_ERROR) || c == -1 || 572 (shf->rp == shf->buf && shf->rnleft)) 573 return (-1); 574 575 if ((shf->flags & SHF_WRITING) && shf_emptybuf(shf, EB_READSW) == -1) 576 return (-1); 577 578 if (shf->rp == shf->buf) 579 shf->rp = shf->buf + shf->rbsize; 580 if (shf->flags & SHF_STRING) { 581 /* 582 * Can unget what was read, but not something different; 583 * we don't want to modify a string. 584 */ 585 if ((int)(shf->rp[-1]) != c) 586 return (-1); 587 shf->flags &= ~SHF_EOF; 588 shf->rp--; 589 shf->rnleft++; 590 return (c); 591 } 592 shf->flags &= ~SHF_EOF; 593 *--(shf->rp) = c; 594 shf->rnleft++; 595 return (c); 596 } 597 598 /* 599 * Write a character. Returns the character if successful, -1 if the 600 * char could not be written. 601 */ 602 int 603 shf_putchar(int c, struct shf *shf) 604 { 605 if (!(shf->flags & SHF_WR)) 606 internal_errorf(Tf_flags, "shf_putchar", 607 (unsigned int)shf->flags); 608 609 if (c == -1) 610 return (-1); 611 612 if (shf->flags & SHF_UNBUF) { 613 unsigned char cc = (unsigned char)c; 614 ssize_t n; 615 616 if (shf->fd < 0) 617 internal_errorf(Tf_sD_s, "shf_putchar", "no fd"); 618 if (shf->flags & SHF_ERROR) { 619 errno = shf->errnosv; 620 return (-1); 621 } 622 while ((n = write(shf->fd, &cc, 1)) != 1) 623 if (n < 0) { 624 if (errno == EINTR && 625 !(shf->flags & SHF_INTERRUPT)) 626 continue; 627 shf->flags |= SHF_ERROR; 628 shf->errnosv = errno; 629 return (-1); 630 } 631 } else { 632 /* Flush deals with strings and sticky errors */ 633 if (shf->wnleft == 0 && shf_emptybuf(shf, EB_GROW) == -1) 634 return (-1); 635 shf->wnleft--; 636 *shf->wp++ = c; 637 } 638 639 return (c); 640 } 641 642 /* 643 * Write a string. Returns the length of the string if successful, -1 644 * if the string could not be written. 645 */ 646 ssize_t 647 shf_puts(const char *s, struct shf *shf) 648 { 649 if (!s) 650 return (-1); 651 652 return (shf_write(s, strlen(s), shf)); 653 } 654 655 /* Write a buffer. Returns nbytes if successful, -1 if there is an error. */ 656 ssize_t 657 shf_write(const char *buf, ssize_t nbytes, struct shf *shf) 658 { 659 ssize_t n, ncopy, orig_nbytes = nbytes; 660 661 if (!(shf->flags & SHF_WR)) 662 internal_errorf(Tf_flags, Tshf_write, 663 (unsigned int)shf->flags); 664 665 if (nbytes < 0) 666 internal_errorf(Tf_szs, Tshf_write, nbytes, Tbytes); 667 668 /* Don't buffer if buffer is empty and we're writting a large amount. */ 669 if ((ncopy = shf->wnleft) && 670 (shf->wp != shf->buf || nbytes < shf->wnleft)) { 671 if (ncopy > nbytes) 672 ncopy = nbytes; 673 memcpy(shf->wp, buf, ncopy); 674 nbytes -= ncopy; 675 buf += ncopy; 676 shf->wp += ncopy; 677 shf->wnleft -= ncopy; 678 } 679 if (nbytes > 0) { 680 if (shf->flags & SHF_STRING) { 681 /* resize buffer until there's enough space left */ 682 while (nbytes > shf->wnleft) 683 if (shf_emptybuf(shf, EB_GROW) == -1) 684 return (-1); 685 /* then write everything into the buffer */ 686 } else { 687 /* flush deals with sticky errors */ 688 if (shf_emptybuf(shf, EB_GROW) == -1) 689 return (-1); 690 /* write chunks larger than window size directly */ 691 if (nbytes > shf->wbsize) { 692 ncopy = nbytes; 693 if (shf->wbsize) 694 ncopy -= nbytes % shf->wbsize; 695 nbytes -= ncopy; 696 while (ncopy > 0) { 697 n = write(shf->fd, buf, ncopy); 698 if (n < 0) { 699 if (errno == EINTR && 700 !(shf->flags & SHF_INTERRUPT)) 701 continue; 702 shf->flags |= SHF_ERROR; 703 shf->errnosv = errno; 704 shf->wnleft = 0; 705 /* 706 * Note: fwrite(3) returns 0 707 * for errors - this doesn't 708 */ 709 return (-1); 710 } 711 buf += n; 712 ncopy -= n; 713 } 714 } 715 /* ... and buffer the rest */ 716 } 717 if (nbytes > 0) { 718 /* write remaining bytes to buffer */ 719 memcpy(shf->wp, buf, nbytes); 720 shf->wp += nbytes; 721 shf->wnleft -= nbytes; 722 } 723 } 724 725 return (orig_nbytes); 726 } 727 728 ssize_t 729 shf_fprintf(struct shf *shf, const char *fmt, ...) 730 { 731 va_list args; 732 ssize_t n; 733 734 va_start(args, fmt); 735 n = shf_vfprintf(shf, fmt, args); 736 va_end(args); 737 738 return (n); 739 } 740 741 ssize_t 742 shf_snprintf(char *buf, ssize_t bsize, const char *fmt, ...) 743 { 744 struct shf shf; 745 va_list args; 746 ssize_t n; 747 748 if (!buf || bsize <= 0) 749 internal_errorf("shf_snprintf: buf %zX, bsize %zd", 750 (size_t)buf, bsize); 751 752 shf_sopen(buf, bsize, SHF_WR, &shf); 753 va_start(args, fmt); 754 n = shf_vfprintf(&shf, fmt, args); 755 va_end(args); 756 /* NUL terminates */ 757 shf_sclose(&shf); 758 return (n); 759 } 760 761 char * 762 shf_smprintf(const char *fmt, ...) 763 { 764 struct shf shf; 765 va_list args; 766 767 shf_sopen(NULL, 0, SHF_WR|SHF_DYNAMIC, &shf); 768 va_start(args, fmt); 769 shf_vfprintf(&shf, fmt, args); 770 va_end(args); 771 /* NUL terminates */ 772 return (shf_sclose(&shf)); 773 } 774 775 #define FL_HASH 0x001 /* '#' seen */ 776 #define FL_PLUS 0x002 /* '+' seen */ 777 #define FL_RIGHT 0x004 /* '-' seen */ 778 #define FL_BLANK 0x008 /* ' ' seen */ 779 #define FL_SHORT 0x010 /* 'h' seen */ 780 #define FL_LONG 0x020 /* 'l' seen */ 781 #define FL_ZERO 0x040 /* '0' seen */ 782 #define FL_DOT 0x080 /* '.' seen */ 783 #define FL_UPPER 0x100 /* format character was uppercase */ 784 #define FL_NUMBER 0x200 /* a number was formated %[douxefg] */ 785 #define FL_SIZET 0x400 /* 'z' seen */ 786 #define FM_SIZES 0x430 /* h/l/z mask */ 787 788 ssize_t 789 shf_vfprintf(struct shf *shf, const char *fmt, va_list args) 790 { 791 const char *s; 792 char c, *cp; 793 int tmp = 0, flags; 794 size_t field, precision, len; 795 unsigned long lnum; 796 /* %#o produces the longest output */ 797 char numbuf[(8 * sizeof(long) + 2) / 3 + 1 + /* NUL */ 1]; 798 /* this stuff for dealing with the buffer */ 799 ssize_t nwritten = 0; 800 801 #define VA(type) va_arg(args, type) 802 803 if (!fmt) 804 return (0); 805 806 while ((c = *fmt++)) { 807 if (c != '%') { 808 shf_putc(c, shf); 809 nwritten++; 810 continue; 811 } 812 /* 813 * This will accept flags/fields in any order - not just 814 * the order specified in printf(3), but this is the way 815 * _doprnt() seems to work (on BSD and SYSV). The only 816 * restriction is that the format character must come 817 * last :-). 818 */ 819 flags = 0; 820 field = precision = 0; 821 while ((c = *fmt++)) { 822 switch (c) { 823 case '#': 824 flags |= FL_HASH; 825 continue; 826 827 case '+': 828 flags |= FL_PLUS; 829 continue; 830 831 case '-': 832 flags |= FL_RIGHT; 833 continue; 834 835 case ' ': 836 flags |= FL_BLANK; 837 continue; 838 839 case '0': 840 if (!(flags & FL_DOT)) 841 flags |= FL_ZERO; 842 continue; 843 844 case '.': 845 flags |= FL_DOT; 846 precision = 0; 847 continue; 848 849 case '*': 850 tmp = VA(int); 851 if (tmp < 0) { 852 if (flags & FL_DOT) 853 precision = 0; 854 else { 855 field = (unsigned int)-tmp; 856 flags |= FL_RIGHT; 857 } 858 } else if (flags & FL_DOT) 859 precision = (unsigned int)tmp; 860 else 861 field = (unsigned int)tmp; 862 continue; 863 864 case 'l': 865 flags &= ~FM_SIZES; 866 flags |= FL_LONG; 867 continue; 868 869 case 'h': 870 flags &= ~FM_SIZES; 871 flags |= FL_SHORT; 872 continue; 873 874 case 'z': 875 flags &= ~FM_SIZES; 876 flags |= FL_SIZET; 877 continue; 878 } 879 if (ctype(c, C_DIGIT)) { 880 bool overflowed = false; 881 882 tmp = ksh_numdig(c); 883 while (ctype((c = *fmt++), C_DIGIT)) 884 if (notok2mul(2147483647, tmp, 10)) 885 overflowed = true; 886 else 887 tmp = tmp * 10 + ksh_numdig(c); 888 --fmt; 889 if (overflowed) 890 tmp = 0; 891 if (flags & FL_DOT) 892 precision = (unsigned int)tmp; 893 else 894 field = (unsigned int)tmp; 895 continue; 896 } 897 break; 898 } 899 900 if (!c) 901 /* nasty format */ 902 break; 903 904 if (ctype(c, C_UPPER)) { 905 flags |= FL_UPPER; 906 c = ksh_tolower(c); 907 } 908 909 switch (c) { 910 case 'd': 911 case 'i': 912 if (flags & FL_SIZET) 913 lnum = (long)VA(ssize_t); 914 else if (flags & FL_LONG) 915 lnum = VA(long); 916 else if (flags & FL_SHORT) 917 lnum = (long)(short)VA(int); 918 else 919 lnum = (long)VA(int); 920 goto integral; 921 922 case 'o': 923 case 'u': 924 case 'x': 925 if (flags & FL_SIZET) 926 lnum = VA(size_t); 927 else if (flags & FL_LONG) 928 lnum = VA(unsigned long); 929 else if (flags & FL_SHORT) 930 lnum = (unsigned long)(unsigned short)VA(int); 931 else 932 lnum = (unsigned long)VA(unsigned int); 933 934 integral: 935 flags |= FL_NUMBER; 936 cp = numbuf + sizeof(numbuf); 937 *--cp = '\0'; 938 939 switch (c) { 940 case 'd': 941 case 'i': 942 if (0 > (long)lnum) { 943 lnum = -(long)lnum; 944 tmp = 1; 945 } else 946 tmp = 0; 947 /* FALLTHROUGH */ 948 case 'u': 949 do { 950 *--cp = digits_lc[lnum % 10]; 951 lnum /= 10; 952 } while (lnum); 953 954 if (c != 'u') { 955 if (tmp) 956 *--cp = '-'; 957 else if (flags & FL_PLUS) 958 *--cp = '+'; 959 else if (flags & FL_BLANK) 960 *--cp = ' '; 961 } 962 break; 963 964 case 'o': 965 do { 966 *--cp = digits_lc[lnum & 0x7]; 967 lnum >>= 3; 968 } while (lnum); 969 970 if ((flags & FL_HASH) && *cp != '0') 971 *--cp = '0'; 972 break; 973 974 case 'x': { 975 const char *digits = (flags & FL_UPPER) ? 976 digits_uc : digits_lc; 977 do { 978 *--cp = digits[lnum & 0xF]; 979 lnum >>= 4; 980 } while (lnum); 981 982 if (flags & FL_HASH) { 983 *--cp = (flags & FL_UPPER) ? 'X' : 'x'; 984 *--cp = '0'; 985 } 986 } 987 } 988 len = numbuf + sizeof(numbuf) - 1 - (s = cp); 989 if (flags & FL_DOT) { 990 if (precision > len) { 991 field = precision; 992 flags |= FL_ZERO; 993 } else 994 /* no loss */ 995 precision = len; 996 } 997 break; 998 999 case 's': 1000 if ((s = VA(const char *)) == NULL) 1001 s = "(null)"; 1002 else if (flags & FL_HASH) { 1003 print_value_quoted(shf, s); 1004 continue; 1005 } 1006 len = utf_mbswidth(s); 1007 break; 1008 1009 case 'c': 1010 flags &= ~FL_DOT; 1011 c = (char)(VA(int)); 1012 /* FALLTHROUGH */ 1013 1014 case '%': 1015 default: 1016 numbuf[0] = c; 1017 numbuf[1] = 0; 1018 s = numbuf; 1019 len = 1; 1020 break; 1021 } 1022 1023 /* 1024 * At this point s should point to a string that is to be 1025 * formatted, and len should be the length of the string. 1026 */ 1027 if (!(flags & FL_DOT) || len < precision) 1028 precision = len; 1029 if (field > precision) { 1030 field -= precision; 1031 if (!(flags & FL_RIGHT)) { 1032 /* skip past sign or 0x when padding with 0 */ 1033 if ((flags & FL_ZERO) && (flags & FL_NUMBER)) { 1034 if (ctype(*s, C_SPC | C_PLUS | C_MINUS)) { 1035 shf_putc(*s, shf); 1036 s++; 1037 precision--; 1038 nwritten++; 1039 } else if (*s == '0') { 1040 shf_putc(*s, shf); 1041 s++; 1042 nwritten++; 1043 if (--precision && 1044 ksh_eq(*s, 'X', 'x')) { 1045 shf_putc(*s, shf); 1046 s++; 1047 precision--; 1048 nwritten++; 1049 } 1050 } 1051 c = '0'; 1052 } else 1053 c = flags & FL_ZERO ? '0' : ' '; 1054 nwritten += field; 1055 while (field--) 1056 shf_putc(c, shf); 1057 field = 0; 1058 } else 1059 c = ' '; 1060 } else 1061 field = 0; 1062 1063 nwritten += precision; 1064 precision = utf_skipcols(s, precision, &tmp) - s; 1065 while (precision--) 1066 shf_putc(*s++, shf); 1067 1068 nwritten += field; 1069 while (field--) 1070 shf_putc(c, shf); 1071 } 1072 1073 return (shf_error(shf) ? -1 : nwritten); 1074 } 1075 1076 #if defined(MKSH_SMALL) && !defined(MKSH_SMALL_BUT_FAST) 1077 int 1078 shf_getc(struct shf *shf) 1079 { 1080 return (shf_getc_i(shf)); 1081 } 1082 1083 int 1084 shf_putc(int c, struct shf *shf) 1085 { 1086 return (shf_putc_i(c, shf)); 1087 } 1088 #endif 1089 1090 #ifdef DEBUG 1091 const char * 1092 cstrerror(int errnum) 1093 { 1094 #undef strerror 1095 return (strerror(errnum)); 1096 #define strerror dontuse_strerror /* poisoned */ 1097 } 1098 #elif !HAVE_STRERROR 1099 1100 #if HAVE_SYS_ERRLIST 1101 #if !HAVE_SYS_ERRLIST_DECL 1102 extern const int sys_nerr; 1103 extern const char * const sys_errlist[]; 1104 #endif 1105 #endif 1106 1107 const char * 1108 cstrerror(int errnum) 1109 { 1110 /* "Unknown error: " + sign + rough estimate + NUL */ 1111 static char errbuf[15 + 1 + (8 * sizeof(int) + 2) / 3 + 1]; 1112 1113 #if HAVE_SYS_ERRLIST 1114 if (errnum > 0 && errnum < sys_nerr && sys_errlist[errnum]) 1115 return (sys_errlist[errnum]); 1116 #endif 1117 1118 switch (errnum) { 1119 case 0: 1120 return ("Undefined error: 0"); 1121 case EPERM: 1122 return ("Operation not permitted"); 1123 case ENOENT: 1124 return ("No such file or directory"); 1125 #ifdef ESRCH 1126 case ESRCH: 1127 return ("No such process"); 1128 #endif 1129 #ifdef E2BIG 1130 case E2BIG: 1131 return ("Argument list too long"); 1132 #endif 1133 case ENOEXEC: 1134 return ("Exec format error"); 1135 case EBADF: 1136 return ("Bad file descriptor"); 1137 #ifdef ENOMEM 1138 case ENOMEM: 1139 return ("Cannot allocate memory"); 1140 #endif 1141 case EACCES: 1142 return ("Permission denied"); 1143 case EEXIST: 1144 return ("File exists"); 1145 case ENOTDIR: 1146 return ("Not a directory"); 1147 #ifdef EINVAL 1148 case EINVAL: 1149 return ("Invalid argument"); 1150 #endif 1151 #ifdef ELOOP 1152 case ELOOP: 1153 return ("Too many levels of symbolic links"); 1154 #endif 1155 default: 1156 shf_snprintf(errbuf, sizeof(errbuf), 1157 "Unknown error: %d", errnum); 1158 return (errbuf); 1159 } 1160 } 1161 #endif 1162 1163 /* fast character classes */ 1164 const uint32_t tpl_ctypes[128] = { 1165 /* 0x00 */ 1166 CiNUL, CiCNTRL, CiCNTRL, CiCNTRL, 1167 CiCNTRL, CiCNTRL, CiCNTRL, CiCNTRL, 1168 CiCNTRL, CiTAB, CiNL, CiSPX, 1169 CiSPX, CiCR, CiCNTRL, CiCNTRL, 1170 /* 0x10 */ 1171 CiCNTRL, CiCNTRL, CiCNTRL, CiCNTRL, 1172 CiCNTRL, CiCNTRL, CiCNTRL, CiCNTRL, 1173 CiCNTRL, CiCNTRL, CiCNTRL, CiCNTRL, 1174 CiCNTRL, CiCNTRL, CiCNTRL, CiCNTRL, 1175 /* 0x20 */ 1176 CiSP, CiALIAS | CiVAR1, CiQC, CiHASH, 1177 CiSS, CiPERCT, CiQCL, CiQC, 1178 CiQCL, CiQCL, CiQCX | CiVAR1, CiPLUS, 1179 CiALIAS, CiMINUS, CiALIAS, CiQCM, 1180 /* 0x30 */ 1181 CiOCTAL, CiOCTAL, CiOCTAL, CiOCTAL, 1182 CiOCTAL, CiOCTAL, CiOCTAL, CiOCTAL, 1183 CiDIGIT, CiDIGIT, CiCOLON, CiQCL, 1184 CiANGLE, CiEQUAL, CiANGLE, CiQUEST, 1185 /* 0x40 */ 1186 CiALIAS | CiVAR1, CiUPPER | CiHEXLT, 1187 CiUPPER | CiHEXLT, CiUPPER | CiHEXLT, 1188 CiUPPER | CiHEXLT, CiUPPER | CiHEXLT, 1189 CiUPPER | CiHEXLT, CiUPPER, 1190 CiUPPER, CiUPPER, CiUPPER, CiUPPER, 1191 CiUPPER, CiUPPER, CiUPPER, CiUPPER, 1192 /* 0x50 */ 1193 CiUPPER, CiUPPER, CiUPPER, CiUPPER, 1194 CiUPPER, CiUPPER, CiUPPER, CiUPPER, 1195 CiUPPER, CiUPPER, CiUPPER, CiQCX | CiBRACK, 1196 CiQCX, CiBRACK, CiQCM, CiUNDER, 1197 /* 0x60 */ 1198 CiGRAVE, CiLOWER | CiHEXLT, 1199 CiLOWER | CiHEXLT, CiLOWER | CiHEXLT, 1200 CiLOWER | CiHEXLT, CiLOWER | CiHEXLT, 1201 CiLOWER | CiHEXLT, CiLOWER, 1202 CiLOWER, CiLOWER, CiLOWER, CiLOWER, 1203 CiLOWER, CiLOWER, CiLOWER, CiLOWER, 1204 /* 0x70 */ 1205 CiLOWER, CiLOWER, CiLOWER, CiLOWER, 1206 CiLOWER, CiLOWER, CiLOWER, CiLOWER, 1207 CiLOWER, CiLOWER, CiLOWER, CiCURLY, 1208 CiQCL, CiCURLY, CiQCM, CiCNTRL 1209 }; 1210 1211 void 1212 set_ifs(const char *s) 1213 { 1214 #if defined(MKSH_EBCDIC) || defined(MKSH_FAUX_EBCDIC) 1215 int i = 256; 1216 1217 memset(ksh_ctypes, 0, sizeof(ksh_ctypes)); 1218 while (i--) 1219 if (ebcdic_map[i] < 0x80U) 1220 ksh_ctypes[i] = tpl_ctypes[ebcdic_map[i]]; 1221 #else 1222 memcpy(ksh_ctypes, tpl_ctypes, sizeof(tpl_ctypes)); 1223 memset((char *)ksh_ctypes + sizeof(tpl_ctypes), '\0', 1224 sizeof(ksh_ctypes) - sizeof(tpl_ctypes)); 1225 #endif 1226 ifs0 = *s; 1227 while (*s) 1228 ksh_ctypes[ord(*s++)] |= CiIFS; 1229 } 1230 1231 #if defined(MKSH_EBCDIC) || defined(MKSH_FAUX_EBCDIC) 1232 #include <locale.h> 1233 1234 /* 1235 * Many headaches with EBCDIC: 1236 * 1. There are numerous EBCDIC variants, and it is not feasible for us 1237 * to support them all. But we can support the EBCDIC code pages that 1238 * contain all (most?) of the characters in ASCII, and these 1239 * usually tend to agree on the code points assigned to the ASCII 1240 * subset. If you need a representative example, look at EBCDIC 1047, 1241 * which is first among equals in the IBM MVS development 1242 * environment: https://en.wikipedia.org/wiki/EBCDIC_1047 1243 * Unfortunately, the square brackets are not consistently mapped, 1244 * and for certain reasons, we need an unambiguous bijective 1245 * mapping between EBCDIC and "extended ASCII". 1246 * 2. Character ranges that are contiguous in ASCII, like the letters 1247 * in [A-Z], are broken up into segments (i.e. [A-IJ-RS-Z]), so we 1248 * can't implement e.g. islower() as { return c >= 'a' && c <= 'z'; } 1249 * because it will also return true for a handful of extraneous 1250 * characters (like the plus-minus sign at 0x8F in EBCDIC 1047, a 1251 * little after 'i'). But at least '_' is not one of these. 1252 * 3. The normal [0-9A-Za-z] characters are at codepoints beyond 0x80. 1253 * Not only do they require all 8 bits instead of 7, if chars are 1254 * signed, they will have negative integer values! Something like 1255 * (c - 'A') could actually become (c + 63)! Use the ord() macro to 1256 * ensure you're getting a value in [0, 255] (ORD for constants). 1257 * 4. '\n' is actually NL (0x15, U+0085) instead of LF (0x25, U+000A). 1258 * EBCDIC has a proper newline character instead of "emulating" one 1259 * with line feeds, although this is mapped to LF for our purposes. 1260 * 5. Note that it is possible to compile programs in ASCII mode on IBM 1261 * mainframe systems, using the -qascii option to the XL C compiler. 1262 * We can determine the build mode by looking at __CHARSET_LIB: 1263 * 0 == EBCDIC, 1 == ASCII 1264 */ 1265 1266 void 1267 ebcdic_init(void) 1268 { 1269 int i = 256; 1270 unsigned char t; 1271 bool mapcache[256]; 1272 1273 while (i--) 1274 ebcdic_rtt_toascii[i] = i; 1275 memset(ebcdic_rtt_fromascii, 0xFF, sizeof(ebcdic_rtt_fromascii)); 1276 setlocale(LC_ALL, ""); 1277 #ifdef MKSH_EBCDIC 1278 if (__etoa_l(ebcdic_rtt_toascii, 256) != 256) { 1279 write(2, "mksh: could not map EBCDIC to ASCII\n", 36); 1280 exit(255); 1281 } 1282 #endif 1283 1284 memset(mapcache, 0, sizeof(mapcache)); 1285 i = 256; 1286 while (i--) { 1287 t = ebcdic_rtt_toascii[i]; 1288 /* ensure unique round-trip capable mapping */ 1289 if (mapcache[t]) { 1290 write(2, "mksh: duplicate EBCDIC to ASCII mapping\n", 40); 1291 exit(255); 1292 } 1293 /* 1294 * since there are 256 input octets, this also ensures 1295 * the other mapping direction is completely filled 1296 */ 1297 mapcache[t] = true; 1298 /* fill the complete round-trip map */ 1299 ebcdic_rtt_fromascii[t] = i; 1300 /* 1301 * Only use the converted value if it's in the range 1302 * [0x00; 0x7F], which I checked; the "extended ASCII" 1303 * characters can be any encoding, not just Latin1, 1304 * and the C1 control characters other than NEL are 1305 * hopeless, but we map EBCDIC NEL to ASCII LF so we 1306 * cannot even use C1 NEL. 1307 * If ever we map to UCS, bump the table width to 1308 * an unsigned int, and or the raw unconverted EBCDIC 1309 * values with 0x01000000 instead. 1310 */ 1311 if (t < 0x80U) 1312 ebcdic_map[i] = (unsigned short)ord(t); 1313 else 1314 ebcdic_map[i] = (unsigned short)(0x100U | ord(i)); 1315 } 1316 if (ebcdic_rtt_toascii[0] || ebcdic_rtt_fromascii[0] || ebcdic_map[0]) { 1317 write(2, "mksh: NUL not at position 0\n", 28); 1318 exit(255); 1319 } 1320 } 1321 #endif 1322