Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Should I free strdup pointer after basename/dirname in C?

I want to use POSIX's basename function (as opposed to GNU's).

From the man page:

Both dirname() and basename() may modify the contents of path, so it may be desirable to pass a copy when calling one of these functions.

These functions may return pointers to statically allocated memory which may be overwritten by subsequent calls. Alternatively, they may return a pointer to some part of path, so that the string referred to by path should not be modified or freed until the pointer returned by the function is no longer required.

It also says:

RETURN VALUE
Both dirname() and basename() return pointers to null-terminated strings. (Do not pass these pointers to free(3).)

So the example suggests something like:

EXAMPLE

       char *dirc, *basec, *bname, *dname;
       char *path = "/etc/passwd";

       dirc = strdup(path);
       basec = strdup(path);
       dname = dirname(dirc);
       bname = basename(basec);
       printf("dirname=%s, basename=%s\n", dname, bname);

The strdup(strndup) man page says:

Memory for the new string is obtained with malloc(3), and can be freed with free(3).

So the question is: Should I free dirc and basec (as per strdup) or not (as per basename)?

like image 561
pakman Avatar asked Sep 30 '14 00:09

pakman


People also ask

What does basename do in C?

The basename() function takes the pathname pointed to by path and returns a pointer to the final component of the pathname, deleting any trailing '/' characters. If the string consists entirely of the '/' character, basename() returns a pointer to the string “/”.

What is Dirname and basename?

The functions dirname() and basename() break a null-terminated pathname string into directory and filename components. In the usual case, dirname() returns the string up to, but not including, the final '/', and basename() returns the component following the final '/'.


1 Answers

dname and bname could be using parts of dirc and basec respectively, so it's not safe to free dirc or basec.

I'd do an strdup of the results from the dirname and basename calls. Then it is safe to freedirc and basec, and you KNOW you have to free your copies.

(yes it's messy, but I think it's cleaner than remembering you can't free dirc yet because dname may or may not be using it...)

like image 60
John3136 Avatar answered Oct 07 '22 22:10

John3136