• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 423
  • Last Modified:

Questions on codes

There're several questions i would like to ask for the following codes:
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <limits.h>

#include <sys/types.h>
#include <sys/stat.h>
#include <dirent.h>
#include <unistd.h>


unsigned process_directory( char *theDir )
{
    	DIR *dir = NULL;
    	struct dirent entry;
    	struct dirent *entryPtr = NULL;
    	int retval = 0;
    	unsigned count = 0;
	char pathName[PATH_MAX + 1];

    	/* Open the given directory, if you can. */  
    	dir = opendir( theDir );
    	if( dir == NULL ) 
	{
        	printf( "Error opening %s: %s", theDir, strerror( errno ) );
        	return 0;
    	}
	
	retval = readdir_r( dir, &entry, &entryPtr );
    	while( entryPtr != NULL ) 
	{
        	struct stat entryInfo;
        
        	if( ( strncmp( entry.d_name, ".", PATH_MAX ) == 0 ) || ( strncmp( entry.d_name, "..", PATH_MAX ) == 0 ) ) 
		{
            		/* Short-circuit the . and .. entries. */
            		retval = readdir_r( dir, &entry, &entryPtr );
            		continue;
        	}
		(void)strncpy( pathName, theDir, PATH_MAX );
        	(void)strncat( pathName, "/", PATH_MAX );
        	(void)strncat( pathName, entry.d_name, PATH_MAX );
        
        	if( lstat( pathName, &entryInfo ) == 0 ) 
		{
            		count++;
                        // to check whether it is a directory
            		if( S_ISDIR( entryInfo.st_mode ) ) 
			{            
				/* directory */
                		printf( "processing %s/\n", pathName );
                		count += process_directory( pathName );
            		} 
                        // to check whether it is a file
			else if( S_ISREG( entryInfo.st_mode ) ) 
			{ 
				/* regular file */
                		printf( "\t%s has %lld bytes\n", pathName, (long long)entryInfo.st_size );
            		} 
                        // to check whether it is a symbolic link
			else if( S_ISLNK( entryInfo.st_mode ) ) 
			{ 
				/* symbolic link */
                		char targetName[PATH_MAX + 1];
                		if( readlink( pathName, targetName, PATH_MAX ) != -1 ) 
				{
                    			printf( "\t%s -> %s\n", pathName, targetName );
                		} 
				else 
				{
                    			printf( "\t%s -> (invalid symbolic link!)\n", pathName );
                		}
            		}
        	} 
		else 
		{
            		printf( "Error statting %s: %s\n", pathName, strerror( errno ) );
        	}
 		retval = readdir_r( dir, &entry, &entryPtr );
    	}
    
    	/* Close the directory and return the number of entries. */
    	(void)closedir( dir );
    	return count;
}

/* readdir_demo main()
 * 
 * Run through the specified directories, and pass them
 * to process_directory().
 */
int main( int argc, char **argv )
{
    int idx = 0;
    unsigned count = 0;
    
    for( idx = 1; idx < argc; idx++ ) {
        count += process_directory( argv[idx] );
    }
    
    return EXIT_SUCCESS;
}

Open in new window


1) I got some errors while compiling this code, not too sure what are these

as3.c: In function `process_directory':
as3.c:30: error: too many arguments to function `readdir_r'
as3.c:30: warning: assignment makes integer from pointer without a cast
as3.c:38: error: too many arguments to function `readdir_r'
as3.c:38: warning: assignment makes integer from pointer without a cast
as3.c:79: error: too many arguments to function `readdir_r'
as3.c:79: warning: assignment makes integer from pointer without a cast

2) Is that possible for me to use chdir in this prog? Let's say if i remove the following line and replace with the chdir func (like chdir (entry.d_name) and chdir (".."))?
             retval = readdir_r( dir, &entry, &entryPtr );

3) what does this return >> EXIT_SUCCESS at the end of the main func what is the difference than the usual?

4) Is there any difference of using void and without void in some of these lines, what do they meant to be here?
                (void)strncpy( pathName, theDir, PATH_MAX );
              (void)strncat( pathName, "/", PATH_MAX );
              (void)strncat( pathName, entry.d_name, PATH_MAX );

5) Is there any possibility for me getting a NULL when reading a directory?

Any help will be greatly appreciated:)
0
crazy4s
Asked:
crazy4s
  • 37
  • 32
  • 3
2 Solutions
 
ssnkumarCommented:
1. I compiled your code on CentOS and didn't get any warnings or errors.
So, it should compile without problems, if you are using Linux and gcc.
Anyway, check the manpages on your computer for readdir_r and see if it has different arguments.
Or check the header file /usr/include/dirent.h and search for readdir_h. Check if it has same arguments that you are using.

2. I think, that should be possible.

3. In the header file stdlib.h, EXIT_STATUS is defined as:
#define   EXIT_SUCCESS    0
So, when your program ends, you can check the exit status.
You can have different exit values depending on the place where you are exiting.
For error 1, you can exit with -1.
For error 2, you can exit with -2.
For success, you can exit with 0.
Now, after your code terminates, how do you know, whether your code completed successfully or with error.
In Linux/Unix, you can do "echo $?" and this will give the exit value of your program (provided you execute "echo $?" immediately after you execute your program).

4. From programming point of view, there is no difference.
But, there are some compilers, which might give lint errors/warning if you are not using the return values (if the function is returning some value). To overcome this, you can prefix the function with (void).
But, if a function is returning value, it is better to use that value.

5. Yes. If the directory is not there or in case of errors you might get NULL.
But, before reading the values in dirent structure, you have to check the return value of readdir().
If it is successful, then only you should attempt to check the dirent structure.
Even then, it is better to check for NULL and then dereference it.
0
 
Infinity08Commented:
>> 1) I got some errors while compiling this code, not too sure what are these

Check the dirent.h header file on your platform to see if it includes a declaration for the readdir_r function, and whether it matches the standard signature :

        int readdir_r(DIR *restrict dirp, struct dirent *restrict entry, struct dirent **restrict result);

Your platform might not have this function.


>> 2) Is that possible for me to use chdir in this prog? Let's say if i remove the following line and replace with the chdir func (like chdir (entry.d_name) and chdir (".."))?
>>              retval = readdir_r( dir, &entry, &entryPtr );

chdir doesn't do the same thing as readdir, so I'm not sure what you mean.


>> 3) what does this return >> EXIT_SUCCESS at the end of the main func what is the difference than the usual?

EXIT_SUCCESS is an integer value that indicates success. Commonly that will be the value 0, but it depends on the platform.


>> 4) Is there any difference of using void and without void in some of these lines, what do they meant to be here?
>>                 (void)strncpy( pathName, theDir, PATH_MAX );

It doesn't relly matter whether you put it or not.
It just documents the intent of the programmer that he doesn't use the return value.


>> 5) Is there any possibility for me getting a NULL when reading a directory?

Sure. There always is the potential that a function call fails, so you always have to check for error cases. Check the manual pages for the function to know more about what could go wrong.
0
 
Infinity08Commented:
Heh, sorry for repeating you, ssnkumar :)
0
Free Tool: Site Down Detector

Helpful to verify reports of your own downtime, or to double check a downed website you are trying to access.

One of a set of tools we are providing to everyone as a way of saying thank you for being a part of the community.

 
crazy4sAuthor Commented:
i checked the man page for readdir_r, all the headers seems to have included in my prog but i'm still not sure why there're still error for readdir_r

given in the man page: (it looks a bit different from the readdir_r in my prog?)

     #include <sys/types.h>
     #include <dirent.h>

     struct dirent *readdir(DIR *dirp);

     struct dirent *readdir_r(DIR *dirp, struct dirent *entry);

cpfoo@csa02 as3$ gcc as3.c <- is it correct to compile like this?
as3.c: In function `process_directory':
as3.c:30: error: too many arguments to function `readdir_r'
as3.c:30: warning: assignment makes integer from pointer without a cast
as3.c:38: error: too many arguments to function `readdir_r'
as3.c:38: warning: assignment makes integer from pointer without a cast
as3.c:79: error: too many arguments to function `readdir_r'
as3.c:79: warning: assignment makes integer from pointer without a cast

2.

the chdir func that i've to use in this prog is used to go back to the parent directory?
can somebody lead me to use this func in this prog? i'm not sure how should i use this?

3.
so can i say return EXIT_SUCCESS; = return 0;?

5.
if let's say you've no permission to access the directory will you get a NULL for that too or error?
0
 
Infinity08Commented:
>>      struct dirent *readdir_r(DIR *dirp, struct dirent *entry);

That one doesn't have three arguments like the standard one :

        int readdir_r(DIR *restrict dirp, struct dirent *restrict entry, struct dirent **restrict result);

So, you'll need to change every call to readdir_r to have only two arguments.


>> the chdir func that i've to use in this prog is used to go back to the parent directory?

chdir changes the working directory. Check the man page for more information ;)


>> so can i say return EXIT_SUCCESS; = return 0;?

That depends on the platform you're working on. On most platforms, yes.


>> if let's say you've no permission to access the directory will you get a NULL for that too or error?

opendir will generate an error if there is a permission issue with the directory.
You can check the man pages for all these functions to see what they do in all error cases.
0
 
crazy4sAuthor Commented:
when i changed to retval = readdir_r( dir, &entry);
i have these errors:

as3.c: In function `process_directory':
as3.c:29: warning: assignment makes integer from pointer without a cast
as3.c:37: warning: assignment makes integer from pointer without a cast
as3.c:78: warning: assignment makes integer from pointer without a cast

somehow i know i've to do smt like that but i'm not sure correct or not?
chdir (entry.d_name) <-- this will be right before the while loop
and
chdir ("..") <-- this will be somewhere near the end of while loop

one more question does this above code have a recursive func in it?
just like the tree that've posted by one of the expert in the related question.
IF yes, is it the while loop that causes the recursive?
0
 
Infinity08Commented:
your readdir_r returns a struct dirent *, not an int. You'll have to adapt your code accordingly.

You wrote your code with another implementation of the readdir_r function in mind, so you have to change it to suit the actual implementation on your platform.
0
 
crazy4sAuthor Commented:
so do you meant that i should change int retval to struct dirent *retval?
0
 
crazy4sAuthor Commented:
i changed it to struct dirent *retval = 0;
compiled with no error but the output is something like that
CS224 is a directory where it has subdirectories and files; as3 is the subdir that has files in it.
the path is smt like /home/ugrad/cpfoo/CS224/as3

cpfoo@csa02 as3$ gcc as3.c -o MY
cpfoo@csa02 as3$ MY CS224
Error opening CS224: No such file or directorycpfoo@csa02 as3$
0
 
Infinity08Commented:
You cannot just change code without understanding it ... That rarely leads to good results :)

You first have to know what you want the readdir_r function to do for you, and then you figure out how you make it do that.

What do you want the readdir_r function to do for you ?
0
 
crazy4sAuthor Commented:
to get the information of the particular directory (theDir)?
0
 
Infinity08Commented:
Ok, now have a look at the man page for the function. How does it explain to do that ? It takes two arguments, and returns one. What are the arguments it takes ? And what does it return ?
0
 
crazy4sAuthor Commented:
The readdir_r() function will not return  directory  entries
     containing  empty  names.  It is unspecified whether entries
     are returned for . (dot) or .. (dot-dot).

     If a file is removed from or added to  the  directory  after
     the  most recent call to opendir() or rewinddir(), whether a
     subsequent call to readdir_r() returns  an  entry  for  that
     file is unspecified.

     The  readdir_r()  function  can  buffer  several   directory
     entries  per  actual read operation. It marks for update the
     st_atime field of the directory each time the  directory  is
     actually read.

     The standard-conforming version (see  standards(5))  of  the
     readdir_r()  function  performs all of the actions described
     above and sets the pointer pointed to by result. If a direc-
     tory  entry is returned, the pointer will be set to the same
     value as the entry argument; otherwise, it will  be  set  to
     NULL.

RETURN VALUES
     Upon  successful  completion,  readdir()  and  the   default
     readdir_r()  return  a  pointer  to an object of type struct
0
 
crazy4sAuthor Commented:
but now my prob seems to appear in opendir rather than readdir_r because i got this after compiling
cpfoo@csa02 as3$ gcc as3.c -o MY
cpfoo@csa02 as3$ MY CS224
Error opening CS224: No such file or directorycpfoo@csa02 as3$
0
 
Infinity08Commented:
That's part of the man page, yes. So, what do you have to pass it as argument, and what do you do with the returned pointer ?
0
 
Infinity08Commented:
>> Error opening CS224: No such file or directory

Then maybe the error message isn't lying ;)
0
 
crazy4sAuthor Commented:
the address of entry (which is a struct dirent)?
0
 
crazy4sAuthor Commented:
hmm what you meant by this? but i do have the CS224 directory as i tried using pwd i got this
/home/ugrad/cpfoo/CS224/as3

>> Error opening CS224: No such file or directory

Then maybe the error message isn't lying ;)
0
 
Infinity08Commented:
>> the address of entry (which is a struct dirent)?

Where you want the next entry to be stored, yes.

When you call the function, check the returned pointer to see if there was an error, and if not, you can use the entry.


>> hmm what you meant by this? but i do have the CS224 directory as i tried using pwd i got this

which means that the directory CS224 is NOT in the current directory, but two levels up.
0
 
crazy4sAuthor Commented:
and can someone lead me in doing the chdir? I really got no idea on how and where should i put in my prog but so far i know that i should've put something like this
chdir (entry.d_name) <-- this will be right before the while loop
                                         to change it to the subdir and check whether there're files or directories in it
chdir ("..") <-- this will be somewhere near the end of while loop
                       back to the parent directory and go to another subdir if there're a few of subdir in the dir?
i'm not sure what i understand is it correct, but pls do correct me if i'm wrong?
0
 
crazy4sAuthor Commented:
hmm in a struct form?
but even if i use  as3 it still give me the same error...as3 is my current working directory

cpfoo@csa02 as3$ gcc as3.c -o MY
cpfoo@csa02 as3$ MY as3
Error opening as3: No such file or directorycpfoo@csa02 as3$
0
 
Infinity08Commented:
>> as3 is my current working directory

as3 is not IN the current working directory though.
0
 
crazy4sAuthor Commented:
when i tried pwd it gives me
/home/ugrad/cpfoo/CS224/as3
hmm a current working directory should be in a path or just the name?
0
 
Infinity08Commented:
The current working directory is the directory you are currently in.

Everything shown by the command ls are the files and directories that are in the current working directory.

A directory can be specified with an absolute path (starting with a /, so from the root), or a relative path (starting from the current directory). If you specify "CS224", then it will look for that in the current working directory.
0
 
crazy4sAuthor Commented:
yeah i understand that but why it appears error opening and stated there no such file or directory?
0
 
Infinity08Commented:
>> yeah i understand that but why it appears error opening and stated there no such file or directory?

Because there is no such directory in the current working directory.
0
 
crazy4sAuthor Commented:
/home/ugrad/cpfoo/CS224/as3
so u meant that i've to compile this file let's say in cpfoo (currently in as3), and so they'll have the directory that i specified (CS224)?
hmm is that possible to look up into that directory even i'm in the sub directory(current working directory)?
0
 
crazy4sAuthor Commented:
is that possible to use chdir so that i can change my current working directory?
0
 
Infinity08Commented:
>> so u meant that i've to compile this file let's say in cpfoo (currently in as3), and so they'll have the directory that i specified (CS224)?

If you would run the executable from the /home/ugrad/cpfoo directory, then it would have access to CS224, yes.
0
 
Infinity08Commented:
>> is that possible to use chdir so that i can change my current working directory?

Yes. But that's probably not what you want to do.

Instead, make use of absolute or relative paths to specify the directory you need.

        http://www.linux-tutorial.info/modules.php?name=MContent&pageid=17
0
 
crazy4sAuthor Commented:
but in this assignment i was asked to use the chdir func to locate the directory and also back to the parent directory?
0
 
Infinity08Commented:
>> but in this assignment i was asked to use the chdir func to locate the directory and also back to the parent directory?

If it's your assignment, then I guess you'll have to do it ;)
0
 
crazy4sAuthor Commented:
so how or where should i start from? i totally got no idea on this, hope you can lead me? thank you.
but so far i know that i should've put something like this
chdir (entry.d_name) <-- this will be right before the while loop
                                         to change it to the subdir and check whether there're files or directories in it
chdir ("..") <-- this will be somewhere near the end of while loop
                       back to the parent directory and go to another subdir if there're a few of subdir in the dir?
i'm not sure what i understand is it correct, but pls do correct me if i'm wrong?
0
 
Infinity08Commented:
That sounds good, yes.
0
 
crazy4sAuthor Commented:
this is the latest code but i still got the same output:(
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <limits.h>

#include <sys/types.h>
#include <sys/stat.h>
#include <dirent.h>
#include <unistd.h>

unsigned process_directory( char *theDir )
{
    	DIR *dir = NULL;
    	struct dirent entry;
    	struct dirent *entryPtr = NULL;
    	struct dirent *retval = 0;
    	unsigned count = 0;
	char pathName[PATH_MAX + 1];

    	/* Open the given directory, if you can. */  
    	dir = opendir( theDir );
    	if( dir == NULL ) 
	{
        	printf( "Error opening %s: %s", theDir, strerror( errno ) );
        	return 0;
    	}
	
	retval = readdir_r( dir, &entry);
	// Change to new directory
	chdir(entry.d_name);
    	while( entryPtr != NULL ) 
	{
        	struct stat entryInfo;
        
        	if( ( strncmp( entry.d_name, ".", PATH_MAX ) == 0 ) || ( strncmp( entry.d_name, "..", PATH_MAX ) == 0 ) ) 
		{
            		/* Short-circuit the . and .. entries. */
            		retval = readdir_r( dir, &entry);
            		continue;
        	}
		(void)strncpy( pathName, theDir, PATH_MAX );
        	(void)strncat( pathName, "/", PATH_MAX );
        	(void)strncat( pathName, entry.d_name, PATH_MAX );
        
        	if( lstat( pathName, &entryInfo ) == 0 ) 
		{
            		/* stat() succeeded, let's party */
            		count++;
            
            		if( S_ISDIR( entryInfo.st_mode ) ) 
			{            
				/* directory */
                		printf( "processing %s/\n", pathName );
                		count += process_directory( pathName );
            		} 
			else if( S_ISREG( entryInfo.st_mode ) ) 
			{ 
				/* regular file */
                		printf( "\t%s has %lld bytes\n", pathName, (long long)entryInfo.st_size );
            		} 
			else if( S_ISLNK( entryInfo.st_mode ) ) 
			{ 
				/* symbolic link */
                		char targetName[PATH_MAX + 1];
                		if( readlink( pathName, targetName, PATH_MAX ) != -1 ) 
				{
                    			printf( "\t%s -> %s\n", pathName, targetName );
                		} 
				else 
				{
                    			printf( "\t%s -> (invalid symbolic link!)\n", pathName );
                		}
            		}
        	} 
		else 
		{
            		printf( "Error statting %s: %s\n", pathName, strerror( errno ) );
        	}
 		retval = readdir_r( dir, &entry);
		/* Switch up to parent directory
		   Now that all directories at this level have been processed*/
		chdir(".."); 
    	}
    
    	/* Close the directory and return the number of entries. */
    	(void)closedir( dir );
    	return count;
}

/* readdir_demo main()
 * 
 * Run through the specified directories, and pass them
 * to process_directory().
 */
int main( int argc, char **argv )
{
    int idx = 0;
    unsigned count = 0;
    
    for( idx = 1; idx < argc; idx++ ) {
        count += process_directory( argv[idx] );
    }
    
    return EXIT_SUCCESS;
}

Open in new window



cpfoo@csa02 as3$ gcc as3.c -o MY
cpfoo@csa02 as3$ MY CS224
Error opening CS224: No such file or directorycpfoo@csa02 as3$
0
 
Infinity08Commented:
Well, you can't expect the result to be different if you don't change anything ;)

You're still running the code from a directory where there is NO CS224 directory.
0
 
crazy4sAuthor Commented:
hmm but i thought we can use the chdir to change the working directory, do we still need to shift?
anyway i've shifted my as3.c to cpfoo but when i compile i got these error:

cpfoo@csa02 ~$ gcc as3.c -o MY
as3.c: In function `process_directory':
as3.c:77: error: missing terminating " character
as3.c:78: error: syntax error before '!' token
as3.c:78: error: stray '\' in program
as3.c:78: error: missing terminating " character

it seems the error appears at the error statting line?
0
 
Infinity08Commented:
>> hmm but i thought we can use the chdir to change the working directory, do we still need to shift?

You can use chdir to change the working directory, yes. But you still need to change it to a valid working directory, and you need to change it at the right time.


>> anyway i've shifted my as3.c to cpfoo but when i compile i got these error:

The error messages are pretty clear. Just go to the indicated line for the first error, and look for the missing ".
0
 
crazy4sAuthor Commented:
so how should i check this error? using gdb? but because i've to input a dir at the command line i got no idea how to check? can you lead me?
0
 
Infinity08Commented:
This is a compilation error, so you cannot use gdb.

Just look at the source code, at the indicated line, and look for the missing "
0
 
crazy4sAuthor Commented:
but i don't see any error in these few lines?
else
            {
                        printf( "Error statting %s: %s\n", pathName, strerror( errno ) );
              }
0
 
Infinity08Commented:
Then maybe you're not compiling the file you think you are.
0
 
crazy4sAuthor Commented:
ah yeah you're right i'm still using the old ones=P
but i got nothing output

cpfoo@csa02 ~$ gcc as3.c -o MY
cpfoo@csa02 ~$ MY CS224
cpfoo@csa02 ~$
0
 
Infinity08Commented:
>> but i got nothing output

Have a closer look at what your code is doing.

Hint : you never actually get into the while loop.
0
 
crazy4sAuthor Commented:
hoh yeah because of the changes that i've made in readdir, the entryPtr seems to be no more functioning is it?
can i change it into something like this while (retval != NULL) as in referring to struct dirent *retval?
0
 
crazy4sAuthor Commented:
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <limits.h>

#include <sys/types.h>
#include <sys/stat.h>
#include <dirent.h>
#include <unistd.h>

unsigned process_directory( char *theDir )
{
    	DIR *dir = NULL;
    	struct dirent entry;
    	struct dirent *retval = 0;
    	unsigned count = 0;
	char pathName[PATH_MAX + 1];

    	/* Open the given directory, if you can. */  
    	dir = opendir( theDir );
    	if( dir == NULL ) 
	{
        	printf( "Error opening %s: %s", theDir, strerror( errno ) );
        	return 0;
    	}
	
	retval = readdir_r( dir, &entry);
	// Change to new directory
	chdir(entry.d_name);
    	while( retval != NULL ) 
	{
        	struct stat entryInfo;
        
        	if( ( strncmp( entry.d_name, ".", PATH_MAX ) == 0 ) || ( strncmp( entry.d_name, "..", PATH_MAX ) == 0 ) ) 
		{
            		/* Short-circuit the . and .. entries. */
            		retval = readdir_r( dir, &entry);
            		continue;
        	}
		(void)strncpy( pathName, theDir, PATH_MAX );
        	(void)strncat( pathName, "/", PATH_MAX );
        	(void)strncat( pathName, entry.d_name, PATH_MAX );
        
        	if( lstat( pathName, &entryInfo ) == 0 ) 
		{
            		/* stat() succeeded, let's party */
            		count++;
            
            		if( S_ISDIR( entryInfo.st_mode ) ) 
			{            
				/* directory */
                		printf( "processing %s/\n", pathName );
                		count += process_directory( pathName );
            		} 
			else if( S_ISREG( entryInfo.st_mode ) ) 
			{ 
				/* regular file */
                		printf( "\t%s has %lld bytes\n", pathName, (long long)entryInfo.st_size );
            		} 
			else if( S_ISLNK( entryInfo.st_mode ) ) 
			{ 
				/* symbolic link */
                		char targetName[PATH_MAX + 1];
                		if( readlink( pathName, targetName, PATH_MAX ) != -1 ) 
				{
                    			printf( "\t%s -> %s\n", pathName, targetName );
                		} 
				else 
				{
                    			printf( "\t%s -> (invalid symbolic link!)\n", pathName );
                		}
            		}
        	} 
		else 
		{
            		printf( "Error statting %s: %s\n", pathName, strerror( errno ) );
        	}
 		retval = readdir_r( dir, &entry);
		/* Switch up to parent directory
		   Now that all directories at this level have been processed*/
		chdir(".."); 
    	}
    
    	/* Close the directory and return the number of entries. */
    	(void)closedir( dir );
    	return count;
}

/* readdir_demo main()
 * 
 * Run through the specified directories, and pass them
 * to process_directory().
 */
int main( int argc, char **argv )
{
    int idx = 0;
    unsigned count = 0;
    
    for( idx = 1; idx < argc; idx++ ) {
        count += process_directory( argv[idx] );
    }
    
    return EXIT_SUCCESS;
}

Open in new window


cpfoo@csa02 ~$ gcc as3.c -o MY
cpfoo@csa02 ~$ MY CS224
processing CS224/as3/
      CS224/as3/ourhdr.h has 4128 bytes
Error statting CS224/as3/error.c: No such file or directory
Error statting CS224/as3/as3.c: No such file or directory
Error statting CS224/as1: No such file or directory
Error statting CS224/.deps: No such file or directory
Error statting CS224/test: No such file or directory
Error statting CS224/as2: No such file or directory
cpfoo@csa02 ~$

dunno why it keeps appearing no such file or directory?
0
 
Infinity08Commented:
>> can i change it into something like this while (retval != NULL) as in referring to struct dirent *retval?

If you think that would do what you want it to do ... why not ? :)


Btw, we've strayed quite far from the original question now. So, let's go back to the original question. If you have any more questions about that, feel free to ask. Otherwise, this question should probably be closed. When doing so, keep in mind that you should accept those post(s) that answered the original question - not the ones that answered all the follow-up stuff ;)
0
 
Infinity08Commented:
>> dunno why it keeps appearing no such file or directory?

Because you changed the working directory with chdir ;)
0
 
crazy4sAuthor Commented:
ok so back to my question 2? how should i put it so i make full use of this func?
currently i'm getting error because of this func?
0
 
crazy4sAuthor Commented:
but even without the chdir func i seems to get a segmentation fault at the end?

cpfoo@csa02 ~$ gcc as3.c -o MY
cpfoo@csa02 ~$ MY CS224
processing CS224/as3/
      CS224/as3/ourhdr.h has 4128 bytes
      CS224/as3/error.c has 1837 bytes
      CS224/as3/as3.c has 2887 bytes
processing CS224/as1/
      CS224/as1/stamp-h1 has 23 bytes
      CS224/as1/configure has 137161 bytes
      CS224/as1/cpwh.c has 3503 bytes
      CS224/as1/missing has 11492 bytes
      CS224/as1/error.o has 5604 bytes
      CS224/as1/config.h.in has 625 bytes
Segmentation Fault (core dumped)
0
 
crazy4sAuthor Commented:
the segmentation fault appeared is it because the files in that sub dir are not dir or files but more to some kind like hmm i'm not sure what's that like command that I used "MY"?
because when i used other directory that only have files, it compiled with no segmentation fault?
sorry i know i get out of the question.
0
 
Infinity08Commented:
>> ok so back to my question 2? how should i put it so i make full use of this func?

You mean chdir ?

You use it when you want to change the working directory. When you do that, is up to you, and depends on what you're trying to do.
For example, if you have the name of a directory in the current working directory, then you can chdir into this directory, and perform some actions in there.


>> but even without the chdir func i seems to get a segmentation fault at the end?

Make sure to always check for NULL and other error conditions.
0
 
crazy4sAuthor Commented:
how if let's say i remove the first chdir(entry.d_name) and remain the 2nd chdir("..") before the end of the loop just to switch back to the parent directory? is this possible?
0
 
Infinity08Commented:
Everything is possible. But would it be useful ?

When is it that you want to change directories ? Or maybe a better question is : why ?
0
 
crazy4sAuthor Commented:
hmm let's say cpfoo is my cwd... and i have subdir like cs224 and cs224 has subdir and files in it.
so when i enter cs224 in my command line...
supposed to be output all the sub dir and files in it... but the sub dir may have files in it too....
so when it is in this subdir, after finish processing this sub dir, we've to move on to the next sub dir in cs224, so that's why i need chdir here? am i correct?
0
 
Infinity08Commented:
If you list all files/directories in the current directory, and iterate over all of them, then for each, there are two possibilities :

(a) it's a directory : chdir into it, and do the same (list all files/directories, etc.). When done, chdir out of it.

(b) it's not a directory
0
 
crazy4sAuthor Commented:
yes that's what i want for chdir
1)is to switch to a new directory if the sub directory is found as a directory not file (not sure where and what i should edit my codes)
2)switch back up to the parent directory (this one i put before the end of while loop)

so how should i edit it?
btw i've open a new related questions here
http://www.experts-exchange.com/Programming/Languages/C/Q_26886500.html
0
 
Infinity08Commented:
So, let's move to the other question then :)
0
 
crazy4sAuthor Commented:
i suddenly found this

cpfoo@csa02 ~$ man readdir
Reformatting page.  Please Wait... done

Standard C Library Functions                          readdir(3C)

NAME
     readdir, readdir_r - read directory

SYNOPSIS
     #include <sys/types.h>
     #include <dirent.h>

     struct dirent *readdir(DIR *dirp);

     struct dirent *readdir_r(DIR *dirp, struct dirent *entry);

  Standard conforming
     cc [ flag... ] file... -D_POSIX_PTHREAD_SEMANTICS [ library... ]

     int readdir_r(DIR *restrict dirp, struct dirent *restrict entry,
         struct dirent **restrict result);

is this means that i can use the readdir_r with 3 arguments?
0
 
Infinity08Commented:
>> is this means that i can use the readdir_r with 3 arguments?

if you use that compiler flag, yes.
0
 
crazy4sAuthor Commented:
how to use a compiler flag? can you lead me?
0
 
Infinity08Commented:
The man page shows how to do it :

>>      cc [ flag... ] file... -D_POSIX_PTHREAD_SEMANTICS [ library... ]
0
 
crazy4sAuthor Commented:
hmm i'm not quite understand but is it smt like that  at the command line?
gcc as3.c -D_POSIX_PTHREAD_SEMANTICS?
0
 
crazy4sAuthor Commented:
even i've changed it back i still get the segmentation fault?

cpfoo@csa02 ~$ gcc as3.c -D_POSIX_PTHREAD_SEMANTICS  
cpfoo@csa02 ~$ DirTrav CS224
processing CS224/as3/
        CS224/as3/ourhdr.h has 4128 bytes
        CS224/as3/error.c has 1837 bytes
        CS224/as3/as3.c has 2887 bytes
processing CS224/as1/
        CS224/as1/stamp-h1 has 23 bytes
        CS224/as1/configure has 137161 bytes
        CS224/as1/cpwh.c has 3503 bytes
        CS224/as1/missing has 11492 bytes
        CS224/as1/error.o has 5604 bytes
        CS224/as1/config.h.in has 625 bytes
Segmentation Fault (core dumped)

can't get it why i got this error?
0
 
Infinity08Commented:
>> hmm i'm not quite understand but is it smt like that  at the command line?
>> gcc as3.c -D_POSIX_PTHREAD_SEMANTICS?

Looks good.


>> even i've changed it back i still get the segmentation fault?

Switching implementations will not magically resolve this segmentation fault, because it's unrelated to the readdir function.

For both versions of the readir_r function, you were using it correctly, so switching to the other implementation doesn't gain you much (if anything).
0
 
crazy4sAuthor Commented:
hmm i'm totally stuck because i'm not sure what that make it a segmentation fault?
do u have any suggestions?
i tried bt by using gdb core and it gives me this as the prob seems to happen in as1(subdir)

(gdb) bt
#0  0xff2e5694 in readdir64_r () from /usr/lib/libc.so.1
#1  0xff2e57f4 in readdir_r () from /usr/lib/libc.so.1
#2  0x00010b90 in process_directory (theDir=0xffbff4c8 "CS224/as1") at as3.c:83
#3  0x00010a4c in process_directory (theDir=0xffbffaeb "CS224") at as3.c:57
#4  0x00010c0c in main (argc=2, argv=0xffbff9dc) at as3.c:105
(gdb) up
#1  0xff2e57f4 in readdir_r () from /usr/lib/libc.so.1
(gdb) n
The program is not being run.
(gdb) up
#2  0x00010b90 in process_directory (theDir=0xffbff4c8 "CS224/as1") at as3.c:83
83                      retval = readdir_r( dir, &entry);
(gdb) up
#3  0x00010a4c in process_directory (theDir=0xffbffaeb "CS224") at as3.c:57
57                                      count += process_directory( pathName );
(gdb) up
#4  0x00010c0c in main (argc=2, argv=0xffbff9dc) at as3.c:105
105             count += process_directory( argv[idx] );
0
 
Infinity08Commented:
>> hmm i'm totally stuck because i'm not sure what that make it a segmentation fault?

That's what your other question is about, no ?
0
 
ssnkumarCommented:
I think I have Solaris 10 virtual machine at home.
If I can get it, I will try to execute your code and see if it crashes for me also.

I don't think you are completely stuck.
You just need to debug and find your way out.
0
 
Infinity08Commented:
>> yes >> http://www.experts-exchange.com/Programming/Languages/C/Q_26886500.html#a35138030

And you're not receiving the help you need for this there ?
0
 
crazy4sAuthor Commented:
no but more help will be better for me to find where it gets wrong:)
0
 
ssnkumarCommented:
0

Featured Post

The 14th Annual Expert Award Winners

The results are in! Meet the top members of our 2017 Expert Awards. Congratulations to all who qualified!

  • 37
  • 32
  • 3
Tackle projects and never again get stuck behind a technical roadblock.
Join Now