Code Comments
Programming Forum and web based access to our favorite programming groups.I'm trying to write a c/c++ program that will find all files matching *.txt from a specific directory downwards... I've done this on dos/windows before with findfirst/findnext but can't find the equivalent function calls on unix. (MAC OS X) (thanks to google) I've found glob but that just seems to give me a list of directories and the parameters are not well explained, nor its recursive use. I've found some postings on opendir/readdir/closedir but I'm not sure they are giving me anything more that what glob is giving me... Seems I still need extra code to match filenames to wild cards like *.txt etc... I'm concerned with following links and getting stuck in loops... Surely I'm not the first person to have done this... Does any one have some code to do this, or a pointer to some? Perhaps I'm just missing that elusive function call whose name I don't yet know... TIA JSG.
Post Follow-up to this messageJustSomeGuy wrote: > I'm trying to write a c/c++ program that will find all files matching > *.txt from a specific directory downwards... > I've done this on dos/windows before with findfirst/findnext but can't > find the equivalent function calls on unix. (MAC OS X) > > (thanks to google) > I've found glob but that just seems to give me a list of directories and > the parameters are not well explained, nor its recursive use. > I've found some postings on opendir/readdir/closedir but I'm not sure > they are giving me anything more that what > glob is giving me... Seems I still need extra code to match filenames > to wild cards like *.txt etc... > > I'm concerned with following links and getting stuck in loops... > > Surely I'm not the first person to have done this... Does any one have > some code to do this, or a pointer to some? > Perhaps I'm just missing that elusive function call whose name I don't > yet know... > > TIA > JSG. > > man opendir man readdir man closedir man stat
Post Follow-up to this messageJustSomeGuy <NoOne@ucalgary.ca> writes: > I'm trying to write a c/c++ program that will find all files matching > *.txt from a specific directory downwards... > I've done this on dos/windows before with findfirst/findnext but can't > find the equivalent function calls on unix. (MAC OS X) > > (thanks to google) > I've found glob but that just seems to give me a list of directories and > the parameters are not well explained, nor its recursive use. > I've found some postings on opendir/readdir/closedir but I'm not sure > they are giving me anything more that what > glob is giving me... Seems I still need extra code to match filenames > to wild cards like *.txt etc... > > I'm concerned with following links and getting stuck in loops... > > Surely I'm not the first person to have done this... Does any one have > some code to do this, or a pointer to some? > Perhaps I'm just missing that elusive function call whose name I don't > yet know... ftw, nftw -- Måns Rullgård mru@inprovide.com
Post Follow-up to this messageMåns Rullgård wrote: > JustSomeGuy <NoOne@ucalgary.ca> writes: > > > ftw, nftw > Yes that is a great looking function, unfortunantly its not supported by MAC OS X. The hunt goes on...
Post Follow-up to this messageJustSomeGuy wrote: > Måns Rullgård wrote: > > > Yes that is a great looking function, unfortunantly its not supported > by MAC OS X. > > The hunt goes on... I did now find fts.h and its functions fts_open etc... Any one have a working example?
Post Follow-up to this messageOn Tue, 26 Oct 2004 14:19:07 -0600, JustSomeGuy <NoOne@ucalgary.ca> wrote: > > I'm concerned with following links and getting stuck in loops... > > Surely I'm not the first person to have done this... Does any one have > some code to do this, or a pointer to some? > Perhaps I'm just missing that elusive function call whose name I don't > yet know... > Use the find source code, or use popen() and the find command. -- "aptitude is also Y2K-compliant, non-fattening, naturally cleansing, and housebroken."
Post Follow-up to this messageJustSomeGuy wrote:
> I'm trying to write a c/c++ program that will find all files matching
> *.txt from a specific directory downwards...
This works on Linux (and is not thoroughly tested):
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <limits.h>
#include <fnmatch.h>
#include <sys/types.h>
#include <unistd.h>
#include <dirent.h>
#define FILENAME_FILTER "*.txt"
int scandirectory(const char *dirname)
{
DIR *dir;
struct dirent *entry;
char path[PATH_MAX];
if (path == NULL) {
fprintf(stderr, "Out of memory error\n");
return 0;
}
dir = opendir(dirname);
if (dir == NULL) {
perror("Error opendir()");
return 0;
}
while ((entry = readdir(dir)) != NULL) {
if (entry->d_type == DT_DIR) {
if (strcmp(entry->d_name, ".")
&& strcmp(entry->d_name, "..")) {
snprintf(path, (size_t) PATH_MAX, "%s/%s", dirname,
entry->d_name);
scandirectory(path);
}
} else if (entry->d_type == DT_REG) {
if (!fnmatch(FILENAME_FILTER, entry->d_name, 0)) {
/*
* This is the place where a file matching the filter is
* found. Do file processing here. Now just
* printing its path.
*/
printf("%s/%s\n", dirname, entry->d_name);
}
}
}
closedir(dir);
return 1;
}
int main(int argc, char *argv[])
{
if (argc != 2) {
fprintf(stderr, "Usage:\t%s <directory>\n", *argv);
return 1;
}
return !scandirectory(argv[1]);
}
/* EOF */
Heiko
Post Follow-up to this messageSmall fix: Please remove the part below from the code I posted.
/* <wrong part> */
if (path == NULL) {
fprintf(stderr, "Out of memory error\n");
return 0;
}
/* </wrong part> */
Heiko
Post Follow-up to this messageJustSomeGuy <NoOne@ucalgary.ca> writes:
> JustSomeGuy wrote:
>
>
> I did now find fts.h and its functions fts_open etc...
> Any one have a working example?
Try this:
========================================
==========================
#include <sys/types.h>
#include <sys/stat.h>
#include <fts.h>
#include <stdio.h>
#include <string.h>
int compar(const FTSENT **f1, const FTSENT **f2)
{
return strcmp( (*f1)->fts_name, (*f2)->fts_name);
}
int is_dot_txt(FTSENT *f)
{
return f->fts_info == FTS_F
&& f->fts_namelen > 4
&& strcmp(f->fts_name + f->fts_namelen - 4, ".txt") == 0;
}
int main(void)
{
FTS *fts;
FTSENT *ftsent;
char * const path[] = { ".", 0};
fts = fts_open(path, FTS_PHYSICAL, compar);
while ( (ftsent = fts_read(fts)) != NULL) {
if ( is_dot_txt(ftsent) ) {
printf("%s\n", ftsent->fts_path);
}
}
fts_close(fts);
return 0;
}
========================================
======================
This should get you going, but you should read the man page and check
the fts_read() return values. If you want to follow links, but check
for loops, you need to use FTS_LOGICAL rather than FTS_PHYSICAL, and
pay attention to fts_cycle.
Post Follow-up to this message
Show a Printable Version
Email This Page to Someone!
Receive updates to this thread
Powered by vBulletin
Copyright 2000-2006 Jelsoft Enterprises Limited.