Merge pull request #12 from cryb-to/cryb-core

String function improvements.
This commit is contained in:
Dag-Erling Smørgrav 2017-05-02 13:07:01 +02:00 committed by GitHub
commit 04783e88af
9 changed files with 104 additions and 36 deletions

View file

@ -302,7 +302,7 @@ string_printf(string *str, const char_t *fmt, ...)
ssize_t ssize_t
string_vprintf(string *str, const char_t *fmt, va_list ap) string_vprintf(string *str, const char_t *fmt, va_list ap)
{ {
va_list ap2; va_list apc;
ssize_t res, ret; ssize_t res, ret;
int len; int len;
@ -312,9 +312,9 @@ string_vprintf(string *str, const char_t *fmt, va_list ap)
*/ */
for (;;) { for (;;) {
res = str->size / sizeof(char_t) - str->len; res = str->size / sizeof(char_t) - str->len;
va_copy(ap2, ap); va_copy(apc, ap);
len = vsnprintf(str->buf + str->len, res, fmt, ap); len = vsnprintf(str->buf + str->len, res, fmt, apc);
va_end(ap2); va_end(apc);
if (len < res) if (len < res)
break; break;
str->buf[str->len] = 0; str->buf[str->len] = 0;

View file

@ -1,6 +1,6 @@
.\"- .\"-
.\" Copyright (c) 2015 The University of Oslo .\" Copyright (c) 2015 The University of Oslo
.\" Copyright (c) 2016 Dag-Erling Smørgrav .\" Copyright (c) 2016-2017 Dag-Erling Smørgrav
.\" All rights reserved. .\" All rights reserved.
.\" .\"
.\" Redistribution and use in source and binary forms, with or without .\" Redistribution and use in source and binary forms, with or without
@ -27,7 +27,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE. .\" SUCH DAMAGE.
.\" .\"
.Dd Septmber 17, 2016 .Dd May 2, 2017
.Dt cryb_strlcat 3 .Dt cryb_strlcat 3
.Os .Os
.Sh NAME .Sh NAME
@ -54,14 +54,25 @@ occupied by the existing string and space for the terminating NUL
character. character.
If the sum of the lengths of both strings exceeds the available space, If the sum of the lengths of both strings exceeds the available space,
the result is truncated. the result is truncated.
In all cases, the destination buffer is properly NUL-terminated. In either case, the destination buffer is properly NUL-terminated.
.Pp
If the buffer pointed to by
.Va dst
does not contain a NUL character within the first
.Va size
bytes,
.Nm
behaves as if the length of
.Va dst
is
.Va size .
.Sh RETURN VALUES .Sh RETURN VALUES
The The
.Fn cryb_strlcat .Fn cryb_strlcat
function returns the sum of the lengths of the original strings. function returns the sum of the lengths of the original strings.
If this number is equal to or greater than the value of the If this number is equal to or greater than the value of
.Va size .Va size ,
argument, the string was too long to fit in the buffer. the string was too long to fit in the buffer.
.Sh IMPLEMENTATION NOTES .Sh IMPLEMENTATION NOTES
If the If the
.Dv HAVE_STRLCAT .Dv HAVE_STRLCAT

View file

@ -1,5 +1,5 @@
/*- /*-
* Copyright (c) 2011-2014 Dag-Erling Smørgrav * Copyright (c) 2011-2017 Dag-Erling Smørgrav
* All rights reserved. * All rights reserved.
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
@ -33,7 +33,13 @@
#include <cryb/strlcat.h> #include <cryb/strlcat.h>
/* like strcat(3), but always NUL-terminates; returns strlen(src) */ /*
* Like strcat(3), but always NUL-terminates.
*
* Returns strlen(dst) + strlen(src), regardless of how much was copied,
* if dst was properly terminated. Returns size + strlen(src) otherwise.
*/
size_t size_t
cryb_strlcat(char *dst, const char *src, size_t size) cryb_strlcat(char *dst, const char *src, size_t size)
{ {

View file

@ -1,6 +1,6 @@
.\"- .\"-
.\" Copyright (c) 2015 The University of Oslo .\" Copyright (c) 2015 The University of Oslo
.\" Copyright (c) 2016 Dag-Erling Smørgrav .\" Copyright (c) 2016-2017 Dag-Erling Smørgrav
.\" All rights reserved. .\" All rights reserved.
.\" .\"
.\" Redistribution and use in source and binary forms, with or without .\" Redistribution and use in source and binary forms, with or without
@ -27,7 +27,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE. .\" SUCH DAMAGE.
.\" .\"
.Dd September 17, 2016 .Dd May 2, 2017
.Dt cryb_strlcpy 3 .Dt cryb_strlcpy 3
.Os .Os
.Sh NAME .Sh NAME
@ -53,14 +53,14 @@ argument specifies the total size of the buffer, including the space
required for the terminating NUL character. required for the terminating NUL character.
If the length of the string exceeds the available space, the result is If the length of the string exceeds the available space, the result is
truncated. truncated.
In all cases, the destination buffer is properly NUL-terminated. In either case, the destination buffer is properly NUL-terminated.
.Sh RETURN VALUES .Sh RETURN VALUES
The The
.Fn cryb_strlcpy .Fn cryb_strlcpy
function returns the length of the original string. function returns the length of the original string.
If this number is equal to or greater than the value of the If this number is equal to or greater than the value of
.Va size .Va size ,
argument, the string was too long to fit in the buffer. the string was too long to fit in the buffer.
.Sh IMPLEMENTATION NOTES .Sh IMPLEMENTATION NOTES
If the If the
.Dv HAVE_STRLCPY .Dv HAVE_STRLCPY

View file

@ -1,5 +1,5 @@
/*- /*-
* Copyright (c) 2011-2014 Dag-Erling Smørgrav * Copyright (c) 2011-2017 Dag-Erling Smørgrav
* All rights reserved. * All rights reserved.
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
@ -33,7 +33,12 @@
#include <cryb/strlcpy.h> #include <cryb/strlcpy.h>
/* like strcpy(3), but always NUL-terminates; returns strlen(src) */ /*
* Like strcpy(3), but always NUL-terminates.
*
* Returns strlen(src), regardless of how much was copied.
*/
size_t size_t
cryb_strlcpy(char *dst, const char *src, size_t size) cryb_strlcpy(char *dst, const char *src, size_t size)
{ {

View file

@ -29,10 +29,9 @@
#include "cryb/impl.h" #include "cryb/impl.h"
#include <sys/types.h>
#include <stddef.h> #include <stddef.h>
#include <stdint.h> #include <stdint.h>
#include <unistd.h>
#include <cryb/string.h> #include <cryb/string.h>

View file

@ -1,5 +1,5 @@
/*- /*-
* Copyright (c) 2014-2016 Dag-Erling Smørgrav * Copyright (c) 2014-2017 Dag-Erling Smørgrav
* All rights reserved. * All rights reserved.
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
@ -35,11 +35,12 @@
#include <string.h> #include <string.h>
#include <unistd.h> #include <unistd.h>
#undef HAVE_STRLCAT
#include <cryb/strlcat.h> #include <cryb/strlcat.h>
#include <cryb/test.h> #include <cryb/test.h>
typedef size_t (*strlcat_f)(char *, const char *, size_t);
#define T_MAGIC_STR "squeamish ossifrage" #define T_MAGIC_STR "squeamish ossifrage"
#define T_MAGIC_LEN (sizeof(T_MAGIC_STR) - 1) #define T_MAGIC_LEN (sizeof(T_MAGIC_STR) - 1)
#define T_BUFSIZE (T_MAGIC_LEN + 1 + T_MAGIC_LEN + 1) #define T_BUFSIZE (T_MAGIC_LEN + 1 + T_MAGIC_LEN + 1)
@ -126,16 +127,15 @@ static struct t_case t_cases[] = {
* Test function * Test function
*/ */
static int static int
t_strlcat(char **desc CRYB_UNUSED, void *arg) t_strlcat(strlcat_f func, const struct t_case *t)
{ {
struct t_case *t = arg;
char buf[T_BUFSIZE + 1]; char buf[T_BUFSIZE + 1];
size_t sz; size_t sz;
int ret; int ret;
memcpy(buf, t->buf, sizeof t->buf); memcpy(buf, t->buf, sizeof t->buf);
buf[T_BUFSIZE] = T_CANARY; buf[T_BUFSIZE] = T_CANARY;
sz = strlcat(buf, t->in, T_BUFSIZE); sz = func(buf, t->in, T_BUFSIZE);
if (buf[T_BUFSIZE] != T_CANARY) { if (buf[T_BUFSIZE] != T_CANARY) {
t_printv("buffer overflow\n"); t_printv("buffer overflow\n");
return (0); return (0);
@ -146,6 +146,24 @@ t_strlcat(char **desc CRYB_UNUSED, void *arg)
return (ret); return (ret);
} }
static int
t_cryb_strlcat(char **desc CRYB_UNUSED, void *arg)
{
const struct t_case *t = arg;
return (t_strlcat(cryb_strlcat, t));
}
#if HAVE_STRLCAT
static int
t_libc_strlcat(char **desc CRYB_UNUSED, void *arg)
{
const struct t_case *t = arg;
return (t_strlcat(strlcat, t));
}
#endif
/*************************************************************************** /***************************************************************************
* Boilerplate * Boilerplate
@ -160,7 +178,13 @@ t_prepare(int argc, char *argv[])
(void)argv; (void)argv;
n = sizeof t_cases / sizeof t_cases[0]; n = sizeof t_cases / sizeof t_cases[0];
for (i = 0; i < n; ++i) for (i = 0; i < n; ++i)
t_add_test(t_strlcat, &t_cases[i], "%s", t_cases[i].desc); t_add_test(t_cryb_strlcat, &t_cases[i],
"%s (cryb)", t_cases[i].desc);
#if HAVE_STRLCAT
for (i = 0; i < n; ++i)
t_add_test(t_libc_strlcat, &t_cases[i],
"%s (libc)", t_cases[i].desc);
#endif
return (0); return (0);
} }

View file

@ -1,5 +1,5 @@
/*- /*-
* Copyright (c) 2014-2016 Dag-Erling Smørgrav * Copyright (c) 2014-2017 Dag-Erling Smørgrav
* All rights reserved. * All rights reserved.
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
@ -35,11 +35,12 @@
#include <string.h> #include <string.h>
#include <unistd.h> #include <unistd.h>
#undef HAVE_STRLCPY
#include <cryb/strlcpy.h> #include <cryb/strlcpy.h>
#include <cryb/test.h> #include <cryb/test.h>
typedef size_t (*strlcpy_f)(char *, const char *, size_t);
#define T_MAGIC_STR "squeamish ossifrage" #define T_MAGIC_STR "squeamish ossifrage"
#define T_MAGIC_LEN (sizeof(T_MAGIC_STR) - 1) #define T_MAGIC_LEN (sizeof(T_MAGIC_STR) - 1)
#define T_BUFSIZE (T_MAGIC_LEN + 1 + T_MAGIC_LEN + 1) #define T_BUFSIZE (T_MAGIC_LEN + 1 + T_MAGIC_LEN + 1)
@ -86,14 +87,13 @@ static struct t_case t_cases[] = {
* Test function * Test function
*/ */
static int static int
t_strlcpy(char **desc CRYB_UNUSED, void *arg) t_strlcpy(strlcpy_f func, const struct t_case *t)
{ {
struct t_case *t = arg;
char buf[T_BUFSIZE + 1]; char buf[T_BUFSIZE + 1];
size_t sz; size_t sz;
memset(buf, T_CANARY, sizeof buf); memset(buf, T_CANARY, sizeof buf);
sz = strlcpy(buf, t->in, T_BUFSIZE); sz = func(buf, t->in, T_BUFSIZE);
if (buf[T_BUFSIZE] != T_CANARY) { if (buf[T_BUFSIZE] != T_CANARY) {
t_printv("buffer overflow\n"); t_printv("buffer overflow\n");
return (0); return (0);
@ -101,6 +101,24 @@ t_strlcpy(char **desc CRYB_UNUSED, void *arg)
return (t_compare_sz(t->sz, sz) & t_compare_str(t->out, buf)); return (t_compare_sz(t->sz, sz) & t_compare_str(t->out, buf));
} }
static int
t_cryb_strlcpy(char **desc CRYB_UNUSED, void *arg)
{
const struct t_case *t = arg;
return (t_strlcpy(cryb_strlcpy, t));
}
#if HAVE_STRLCPY
static int
t_libc_strlcpy(char **desc CRYB_UNUSED, void *arg)
{
const struct t_case *t = arg;
return (t_strlcpy(strlcpy, t));
}
#endif
/*************************************************************************** /***************************************************************************
* Boilerplate * Boilerplate
@ -115,7 +133,13 @@ t_prepare(int argc, char *argv[])
(void)argv; (void)argv;
n = sizeof t_cases / sizeof t_cases[0]; n = sizeof t_cases / sizeof t_cases[0];
for (i = 0; i < n; ++i) for (i = 0; i < n; ++i)
t_add_test(t_strlcpy, &t_cases[i], "%s", t_cases[i].desc); t_add_test(t_cryb_strlcpy, &t_cases[i],
"%s (cryb)", t_cases[i].desc);
#if HAVE_STRLCPY
for (i = 0; i < n; ++i)
t_add_test(t_libc_strlcpy, &t_cases[i],
"%s (libc)", t_cases[i].desc);
#endif
return (0); return (0);
} }

View file

@ -29,10 +29,9 @@
#include "cryb/impl.h" #include "cryb/impl.h"
#include <sys/types.h>
#include <stddef.h> #include <stddef.h>
#include <stdint.h> #include <stdint.h>
#include <unistd.h>
#include <wchar.h> #include <wchar.h>
#include <cryb/wstring.h> #include <cryb/wstring.h>