Skip to content

Commit

Permalink
Use custom basename(3) to avoid ptr reuse
Browse files Browse the repository at this point in the history
As http://man7.org/linux/man-pages/man3/basename.3.html says:

  These functions may return pointers to
  statically allocated memory which may be
  overwritten by subsequent calls.

So we just reimplement a safer one.

Fixes #253.
  • Loading branch information
davidmoreno committed Feb 4, 2020
1 parent 645da77 commit 2b3b230
Show file tree
Hide file tree
Showing 6 changed files with 47 additions and 16 deletions.
3 changes: 2 additions & 1 deletion src/onion/log.c
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
#include <stdlib.h>
#include <syslog.h>
#include <unistd.h>
#include "utils.h"

#ifdef HAVE_PTHREADS
#include <pthread.h>
Expand Down Expand Up @@ -135,7 +136,7 @@ void onion_log_stderr(onion_log_level level, const char *filename, int lineno,
}
}

filename = basename((char *)filename);
filename = onion_basename((char *)filename);

#ifdef __DEBUG__
if ((level == O_DEBUG0) && (!debug0 || !strstr(debug0, filename))) {
Expand Down
44 changes: 35 additions & 9 deletions src/onion/utils.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,16 +30,42 @@ extern "C" {
// In the HTTP RFC whitespace is always these characters
// and is not locale independent, we'll need this when
// parsing
static int __attribute__ ((unused)) is_space(char c) {
if (c == '\t' || c == '\n' || c == '\r' || c == ' ')
return 1;
return 0;
} static int __attribute__ ((unused)) is_alnum(char c) {
if ((c >= '0' && c <= '9') || (c >= 'A' && c <= 'Z')
|| (c >= 'a' && c <= 'z'))
return 1;
return 0;
static int __attribute__ ((unused)) is_space(char c) {
if (c == '\t' || c == '\n' || c == '\r' || c == ' ')
return 1;
return 0;
}
static int __attribute__ ((unused)) is_alnum(char c) {
if ((c >= '0' && c <= '9') || (c >= 'A' && c <= 'Z')
|| (c >= 'a' && c <= 'z'))
return 1;
return 0;
}

/**
* @short Reimplementation of basename(3)
*
* basename(3) has some problems on some platforms that reuse the returned pointer,
* this version always returns an pointer inside *path.
*
* As http://man7.org/linux/man-pages/man3/basename.3.html says: These functions
* may return pointers to statically allocated memory which may be overwritten
* by subsequent calls.
*
* This implementation does not return "." on NULL data, but NULL.
*/
static __attribute__ ((unused)) const char * onion_basename(const char *path){
if (!path)
return path;
const char *basename = path;
while (*path) {
if (*path == '/')
basename = path + 1; // Maybe last part? I keep it just in case.
path++;
}
return basename;
}


#ifdef __cplusplus
}
Expand Down
7 changes: 4 additions & 3 deletions tests/04-prerecorded/prerecorded.c
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@
#include <onion/log.h>
#include <onion/dict.h>
#include <onion/block.h>
#include <onion/utils.h>

#include "../ctest.h"
#include "../01-internal/buffer_listen_point.h"
Expand Down Expand Up @@ -93,7 +94,7 @@ onion_connection_status allinfo_handler(void *data, onion_request * req,

/**
* @short Performs regexec on each line of string.
*
*
* As regexec cant use ^$ to find the line limits, but the string limits, we split the string to make
* the find of ^ and $ on each line.
*/
Expand Down Expand Up @@ -131,7 +132,7 @@ void prerecorded(const char *oscript, int do_r) {
END_LOCAL();
return;
}
const char *script = basename((char *)oscript);
const char *script = onion_basename((char *)oscript);

onion_listen_point *listen_point = onion_get_listen_point(server, 0);
onion_request *req = onion_request_new(listen_point);
Expand Down Expand Up @@ -260,7 +261,7 @@ void prerecorded(const char *oscript, int do_r) {

/**
* @short Executes each script file passed as argument.
*
*
* Optionally a -r sets the new lines to \r\n. It takes care of not changing content types.
*/
int main(int argc, char **argv) {
Expand Down
3 changes: 2 additions & 1 deletion tools/opack/opack.c
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
#include <dirent.h>
#include <sys/stat.h>
#include <onion/mime.h>
#include <onion/utils.h>

#include "../common/updateassets.h"

Expand Down Expand Up @@ -91,7 +92,7 @@ int main(int argc, char **argv) {
struct stat st;
stat(argv[i], &st);
if (S_ISDIR(st.st_mode)) {
parse_directory(basename(argv[1]), argv[i], outfd, assets);
parse_directory(onion_basename(argv[1]), argv[i], outfd, assets);
} else {
parse_file("", argv[i], outfd, assets);
}
Expand Down
3 changes: 2 additions & 1 deletion tools/otemplate/otemplate.c
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@

#include "onion/log.h"
#include "onion/block.h"
#include "onion/utils.h"
#include "list.h"
#include "parser.h"
#include "tags.h"
Expand Down Expand Up @@ -181,7 +182,7 @@ int work(const char *infilename, const char *outfilename,
status.infilename = infilename;
char tmp2[256];
strncpy(tmp2, infilename, sizeof(tmp2) - 1);
const char *tname = basename(tmp2);
const char *tname = onion_basename(tmp2);
ONION_DEBUG("Create init function on top, tname %s", tname);
status.blocks_init = function_new(&status, "%s_blocks_init", tname);
status.blocks_init->signature = "onion_dict *context";
Expand Down
3 changes: 2 additions & 1 deletion tools/otemplate/tag_builtins.c
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
#include <onion/log.h>
#include <onion/codecs.h>
#include <onion/block.h>
#include <onion/utils.h>

#include "functions.h"
#include "parser.h"
Expand Down Expand Up @@ -211,7 +212,7 @@ void tag_block(parser_status * st, list * l) {
assert(strlen(st->infilename) < sizeof(tmp));
strncpy(tmp, st->infilename, sizeof(tmp) - 1);
function_data *d =
function_new(st, "%s__block_%s", basename(tmp), block_name);
function_new(st, "%s__block_%s", onion_basename(tmp), block_name);
function_add_code_f(st->blocks_init,
" if (!onion_dict_get(context, \"__block_%s__\"))\n"
" onion_dict_add(context, \"__block_%s__\", %s, 0);\n",
Expand Down

0 comments on commit 2b3b230

Please sign in to comment.