Listing 3: The Delete Directory program using the setjmp/longjmp
mechanism
/* ddir3.c: Remove subdirectory tree */
#include <stdio.h>
#include <stdlib.h>
#include <io.h>
#include <string.h>
#include <sys/stat.h>
#include <dirent.h>
#include <dir.h>
#include <setjmp.h>
/* Calling environment buffer (global!) */
jmp_buf env;
main(volatile int argc, volatile char **argv)
{
volatile char *old_path = getcwd(NULL,64);
void rd(char *);
switch(setjmp(env)) /* returns 0 once */
{
case BAD_DIR:
puts("Invalid directory");
break;
case DIR_OPEN_ERR:
puts("Error opening directory");
break;
case FILE_DEL_ERR:
puts("Error deleting file");
break;
case DIR_DEL_ERR:
puts("Error deleting directory");
break;
}
/* Delete the directories (re-entrant!) */
while (--argc)
rd((char *) *++argv);
chdir((char *) old_path);
return 0;
}
void rd(char* dir)
{
void erase_dir(void);
if (chdir(dir))
longjmp(env,BAD_DIR);
system("del /q *.* > nul");
erase_dir();
chdir("..");
if (rmdir(dir))
longjmp(env,DIR_DEL_ERR);
}
void erase_dir(void)
{
DIR *dirp;
struct dirent *entry;
struct stat finfo;
if ((dirp = opendir(".")) == NULL)
longjmp(env,DIR_OPEN_ERR);
while ((entry = readdir(dirp)) != NULL)
{
if (entry->d_name[0] == '.')
continue;
stat(entry->d_name,&finfo); if (finfo.st_mode & S_IFDIR)
rd(entry->d_name);
else
{
chmod(entry->d_name,S_IWRITE);
if (unlink(entry->d_name))
{
closedir(dirp);
longjmp(env,FILE_DEL_ERR);
}
}
}
closedir(dirp);
}
//End of File