snac2

Fork of https://codeberg.org/grunfink/snac2
git clone https://git.inz.fi/snac2
Log | Files | Refs | README | LICENSE

xs_io.h (1513B)


      1 /* copyright (c) 2022 - 2025 grunfink et al. / MIT license */
      2 
      3 #ifndef _XS_IO_H
      4 
      5 #define _XS_IO_H
      6 
      7 xs_str *xs_readline(FILE *f);
      8 xs_val *xs_read(FILE *f, int *size);
      9 xs_val *xs_readall(FILE *f);
     10 
     11 
     12 #ifdef XS_IMPLEMENTATION
     13 
     14 xs_str *xs_readline(FILE *f)
     15 /* reads a line from a file */
     16 {
     17     size_t sz = 128;
     18     size_t i = 0;
     19     char *s = xs_realloc(NULL, sz);
     20     int c;
     21 
     22     errno = 0;
     23 
     24     /* don't even try on eof */
     25     while ((c = fgetc(f)) != EOF && c != '\n') {
     26         if (!xs_is_string(&(char){ c }))
     27             continue;
     28         if (i == sz - 1)
     29             s = xs_realloc(s, sz *= 2);
     30         s[i++] = c;
     31     }
     32     s[i] = '\0';
     33 
     34     return s;
     35 }
     36 
     37 
     38 xs_val *xs_read(FILE *f, int *sz)
     39 /* reads up to size bytes from f */
     40 {
     41     xs_val *s  = NULL;
     42     int size   = *sz;
     43     int rdsz   = 0;
     44 
     45     errno = 0;
     46 
     47     while (size > 0 && !feof(f)) {
     48         char tmp[4096];
     49         int n, r;
     50 
     51         if ((n = sizeof(tmp)) > size)
     52             n = size;
     53 
     54         r = fread(tmp, 1, n, f);
     55 
     56         /* open room */
     57         s = xs_realloc(s, rdsz + r);
     58 
     59         /* copy read data */
     60         memcpy(s + rdsz, tmp, r);
     61 
     62         rdsz += r;
     63         size -= r;
     64     }
     65 
     66     /* null terminate, just in case it's treated as a string */
     67     s = xs_realloc(s, _xs_blk_size(rdsz + 1));
     68     s[rdsz] = '\0';
     69 
     70     *sz = rdsz;
     71 
     72     return s;
     73 }
     74 
     75 
     76 xs_val *xs_readall(FILE *f)
     77 /* reads the rest of the file into a string */
     78 {
     79     int size = XS_ALL;
     80 
     81     return xs_read(f, &size);
     82 }
     83 
     84 
     85 #endif /* XS_IMPLEMENTATION */
     86 
     87 #endif /* _XS_IO_H */