SS8_SET_LEN(3) Ssstr Manual SS8_SET_LEN(3)
NAME
ss8_set_len, ss8_grow_len, ss8_set_len_to_cstrlen - set length of ssstr
byte string
SYNOPSIS
#include <ss8str.h>
void ss8_set_len(ss8str *str, size_t newlen);
size_t ss8_grow_len(ss8str *str, size_t maxlen,
size_t maxdelta);
void ss8_set_len_to_cstrlen(ss8str *str);
DESCRIPTION
ss8_set_len() forcefully sets the length of the ss8str at str to
newlen. If newlen is less than the current length, the string is trun‐
cated. If newlen is greater than the current length, the new portion
of the string is filled with indeterminate bytes, except that the byte
after the former last byte is guaranteed to contain a null byte.
If the capacity of the ss8str is not sufficient to hold the new length,
it is increased to match the new length; otherwise, no memory alloca‐
tion or deallocation is performed.
ss8_grow_len() is like ss8_set_len(), but automatically chooses a new
length that is greater than the current length by a constant factor, or
equal to the current capacity, whichever is larger. Because the capac‐
ity is never zero, an appropriate length greater than zero is chosen if
the current length is zero.
The amount by which the lengh is increased is limited to no more than
maxdelta, and the final length is limited to no more than maxlen.
These two parameters can be set to SIZE_MAX to request the maximum al‐
lowed limits.
If the current length exceeds maxlen, no change is made (the caller
should avoid this case in typical usage).
ss8_set_len_to_cstrlen() truncates the ss8str at str to its length when
viewed as a null-terminated byte string. That is,
ss8_set_len_to_cstrlen(str);
is equivalent to
ss8_set_len(str, strlen(ss8_cstr(str));
No memory allocation or deallocation is performed.
These functions are intended for the purpose of using an ss8str as a
destination when calling functions that fill a caller-provided buffer
with a string. ss8_grow_len() is useful when it is necessary to retry
such a function call with successively larger buffers.
RETURN VALUE
ss8_grow_len() returns the amount (in bytes) by which the length of str
was increased. A zero return value indicates that the length of str
was already greater than or equal to maxlen, or that maxdelta was set
to zero.
EXAMPLES
To read at most 1024 bytes from the file fp:
#include <ss8str.h>
#include <stdio.h>
ss8str bytes;
ss8_init(&bytes);
ss8_set_len(&bytes, 1024);
size_t nread = fread(ss8_mutable_cstr(&bytes),
ss8_len(&bytes), 1, fp);
ss8_set_len(&bytes, nread);
// ...
ss8_destroy(&bytes);
To format the current local time:
#include <ss8str.h>
#include <stdint.h>
#include <time.h>
time_t now = time(NULL);
ss8str timestr;
ss8_init(×tr);
for (;;) {
ss8_grow_len(×tr, SIZE_MAX, SIZE_MAX);
// strftime() only returns zero (given "%c") if the buffer is
// too small to fit the result.
size_t n = strftime(ss8_mutable_cstr(×tr),
ss8_len(×tr) + 1,
"%c", localtime(&now));
if (n > 0) {
ss8_set_len(×tr, n);
break;
}
}
// ...
ss8_destroy(×tr);
To read a whole line from the file fp:
#include <ss8str.h>
#include <limits.h>
#include <stdint.h>
#include <stdio.h>
ss8str line;
ss8_init(&line);
size_t nread = 0;
do {
// fgets() takes an int count; limit buffer growth accordingly
int growth = (int)ss8_grow_len(&line, SIZE_MAX, INT_MAX - 1);
if (growth == 0) { // Reached limit
ss8_clear(&line);
break;
}
if (!fgets(ss8_mutable_cstr_suffix(&line, nread),
growth + 1, fp)) {
ss8_clear(&line);
break;
}
ss8_set_len_to_cstrlen(&line);
nread = ss8_len(&line);
} while (!ss8_ends_with_ch(&line, '\n'));
// ...
ss8_destroy(&line);
The last example is inteded for text input that does not contain null
bytes. If null bytes do occur, the read line will be silently cor‐
rupted but the program will not crash or leak memory. Other edge cases
occur if the line is longer than SIZE_MAX - 1 bytes or the input
reaches end-of-file before a newline.
SEE ALSO
ss8_len(3), ss8_mutable_cstr(3), ss8_reserve(3), ss8_shrink_to_fit(3),
ss8_substr_inplace(3), ssstr(7)
SSSTR 2023-12-30 SS8_SET_LEN(3)