Go to the first, previous, next, last section, table of contents.


Scanning the Content of a Directory

A higher-level interface to the directory handling functions is the scandir function. With its help one can select a subset of the entries in a directory, possibly sort them and get as the result a list of names.

Function: int scandir (const char *dir, struct dirent ***namelist, int (*selector) (const struct dirent *), int (*cmp) (const void *, const void *))

The scandir function scans the contents of the directory selected by dir. The result in namelist is an array of pointers to structure of type struct dirent which describe all selected directory entries and which is allocated using malloc. Instead of always getting all directory entries returned, the user supplied function selector can be used to decide which entries are in the result. Only the entries for which selector returns a nonzero value are selected.

Finally the entries in the namelist are sorted using the user supplied function cmp. The arguments of the cmp function are of type struct dirent **. I.e., one cannot directly use the strcmp or strcoll function; see the functions alphasort and versionsort below.

The return value of the function gives the number of entries placed in namelist. If it is -1 an error occurred (either the directory could not be opened for reading or the malloc call failed) and the global variable errno contains more information on the error.

As said above the fourth argument to the scandir function must be a pointer to a sorting function. For the convenience of the programmer the GNU C library contains implementations of functions which are very helpful for this purpose.

Function: int alphasort (const void *a, const void *b)
The alphasort function behaves like the strcoll function (see section String/Array Comparison). The difference is that the arguments are not string pointers but instead they are of type struct dirent **.

Return value of alphasort is less than, equal to, or greater than zero depending on the order of the two entries a and b.

Function: int versionsort (const void *a, const void *b)
The versionsort function is like alphasort, excepted that it uses the strverscmp function internally.

If the filesystem supports large files we cannot use the scandir anymore since the dirent structure might not able to contain all the information. The LFS provides the new type struct dirent64. To use this we need a new function.

Function: int scandir64 (const char *dir, struct dirent64 ***namelist, int (*selector) (const struct dirent64 *), int (*cmp) (const void *, const void *))
The scandir64 function works like the scandir function only that the directory entries it returns are described by elements of type struct dirent64. The function pointed to by selector is again used to select the wanted entries only that selector now must point to a function which takes a struct dirent64 * parameter.

The cmp now must be a function which expects its two arguments to be of type struct dirent64 **.

As just said the function expected as the fourth is different from the function expected in scandir. Therefore we cannot use the alphasort and versionsort functions anymore. Instead we have two similar functions available.

Function: int alphasort64 (const void *a, const void *b)
The alphasort64 function behaves like the strcoll function (see section String/Array Comparison). The difference is that the arguments are not string pointers but instead they are of type struct dirent64 **.

Return value of alphasort64 is less than, equal to, or greater than zero depending on the order of the two entries a and b.

Function: int versionsort64 (const void *a, const void *b)
The versionsort64 function is like alphasort64, excepted that it uses the strverscmp function internally.

It is important not to mix the use of scandir and the 64 bits comparison functions or vice versa. There are systems on which this works but on others it will fail miserably.


Go to the first, previous, next, last section, table of contents.