diff --git a/TODO.txt b/TODO.txt index ecce73a..7aa951c 100644 --- a/TODO.txt +++ b/TODO.txt @@ -12,7 +12,7 @@ Milestone: v0.1.1 ----------------- [x] DbDelete() -[ ] UtilRandomString() +[x] UtilRandomString() [ ] Database version file [ ] User registration diff --git a/man/man3/Util.3 b/man/man3/Util.3 index f69df98..8f55715 100644 --- a/man/man3/Util.3 +++ b/man/man3/Util.3 @@ -1,4 +1,4 @@ -.Dd $Mdocdate: November 26 2022 $ +.Dd $Mdocdate: December 15 2022 $ .Dt UTIL 3 .Os Telodendria Project .Sh NAME @@ -26,6 +26,8 @@ .Fn UtilGetDelim "char **" "size_t *" "int" "FILE *" .Ft ssize_t .Fn UtilGetLine "char **" "size_t *" "FILE *" +.Ft char * +.Fn UtilRandomString "size_t" .Sh DESCRIPTION .Pp This header holds a number of random functions related to strings, @@ -98,6 +100,12 @@ work identically to the POSIX equivalents, documented in .Xr getdelim 3 , except it assumes pointers were allocated using the Memory API, and it uses the Memory API itself to reallocate necessary pointers. +.Pp +.Fn UtilRandomString +generates a random string of the given length. At the moment, it only +selects from uppercase and lowercase numbers, but the character set may +be expanded in the future, or a function may be added to specify an +arbitrary character set. .Sh RETURN VALUES .Pp .Fn UtilServerTs @@ -131,3 +139,7 @@ and .Fn UtilGetLine return the same value as their POSIX equivalents, documented in .Xr getdelim 3 . +.Pp +.Fn UtilRandomString +returns a string, allocated on the heap, of the given length, or NULL if there +was an error allocating memory. diff --git a/man/man7/telodendria-changelog.7 b/man/man7/telodendria-changelog.7 index cadae6f..e33cb8c 100644 --- a/man/man7/telodendria-changelog.7 +++ b/man/man7/telodendria-changelog.7 @@ -43,6 +43,12 @@ While the database is for persistent storage, there may be some ephemeral data that lives there only for a short while, so it will be necessary to remove that data when necessary. +.It +Added a thread-safe random string generator, which will +be used extensively for generating session tokens, device +IDs, access tokens, and more. This generator is seeded by +the current timestamp and the thread ID, so it should be +fairly random. .El .Pp Bug fixes: diff --git a/src/Routes/RouteRegister.c b/src/Routes/RouteRegister.c index c479173..43673d0 100644 --- a/src/Routes/RouteRegister.c +++ b/src/Routes/RouteRegister.c @@ -75,6 +75,7 @@ ROUTE_IMPL(RouteRegister, args) HashMapSet(response, "flows", JsonValueArray(flows)); HashMapSet(response, "params", JsonValueObject(HashMapCreate())); + HashMapSet(response, "session", JsonValueString(UtilRandomString(24))); } else { diff --git a/src/Util.c b/src/Util.c index dcb75af..2c1d733 100644 --- a/src/Util.c +++ b/src/Util.c @@ -36,6 +36,7 @@ #include #include #include +#include #ifndef PATH_MAX #define PATH_MAX 256 @@ -394,3 +395,34 @@ UtilGetLine(char **linePtr, size_t * n, FILE * stream) { return UtilGetDelim(linePtr, n, '\n', stream); } + +char * +UtilRandomString(size_t len) +{ + static const char charset[] = + "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"; + + char *str; + size_t i; + + unsigned int seed = UtilServerTs() * (unsigned long) pthread_self(); + + if (!len) + { + return NULL; + } + + str = Malloc(len + 1); + if (!str) + { + return NULL; + } + + for (i = 0; i < len; i++) + { + str[i] = charset[rand_r(&seed) % (sizeof(charset) - 1)]; + } + + str[len] = '\0'; + return str; +} diff --git a/src/include/Util.h b/src/include/Util.h index 4484991..e492afd 100644 --- a/src/include/Util.h +++ b/src/include/Util.h @@ -59,4 +59,7 @@ extern ssize_t extern ssize_t UtilGetLine(char **, size_t *, FILE *); +extern char * + UtilRandomString(size_t); + #endif /* TELODENDRIA_UTIL_H */