From 6767cd760a8f5274e238fca4567071a78ac43968 Mon Sep 17 00:00:00 2001 From: matz Date: Wed, 19 Sep 2001 06:54:11 +0000 Subject: * string.c (rb_str_init): String.new() => "" * dir.c (dir_path): new method. * dir.c (dir_initialize): wrap DIR into struct, along with path information. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@1748 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- dir.c | 86 +++++++++++++++++++++++++++++++++++++++++++------------------------ 1 file changed, 55 insertions(+), 31 deletions(-) (limited to 'dir.c') diff --git a/dir.c b/dir.c index f21051587e..567d49a86c 100644 --- a/dir.c +++ b/dir.c @@ -234,11 +234,16 @@ fnmatch(pat, string, flags) VALUE rb_cDir; +struct dir_data { + DIR *dir; + char *path; +}; + static void free_dir(dir) - DIR *dir; + struct dir_data *dir; { - if (dir) closedir(dir); + if (dir && dir->dir) closedir(dir->dir); } static VALUE dir_close _((VALUE)); @@ -249,8 +254,11 @@ dir_s_new(argc, argv, klass) VALUE *argv; VALUE klass; { - VALUE obj = Data_Wrap_Struct(klass, 0, free_dir, 0); + struct dir_data *dirp; + VALUE obj = Data_Make_Struct(klass, struct dir_data, 0, free_dir, dirp); + dirp->dir = NULL; + dirp->path = NULL; rb_obj_call_init(obj, argc, argv); return obj; @@ -260,22 +268,25 @@ static VALUE dir_initialize(dir, dirname) VALUE dir, dirname; { - DIR *dirp; + struct dir_data *dp; SafeStringValue(dirname); - if (DATA_PTR(dir)) closedir(DATA_PTR(dir)); - DATA_PTR(dir) = NULL; - dirp = opendir(RSTRING(dirname)->ptr); - if (dirp == NULL) { + Data_Get_Struct(dir, struct dir_data, dp); + if (dp->dir) closedir(dp->dir); + if (dp->path) free(dp->path); + dp->dir = NULL; + dp->path = NULL; + dp->dir = opendir(RSTRING(dirname)->ptr); + if (dp->dir == NULL) { if (errno == EMFILE || errno == ENFILE) { rb_gc(); - dirp = opendir(RSTRING(dirname)->ptr); + dp->dir = opendir(RSTRING(dirname)->ptr); } - if (dirp == NULL) { + if (dp->dir == NULL) { rb_sys_fail(RSTRING(dirname)->ptr); } } - DATA_PTR(dir) = dirp; + dp->path = strdup(RSTRING(dirname)->ptr); return dir; } @@ -284,7 +295,8 @@ static VALUE dir_s_open(klass, dirname) VALUE klass, dirname; { - VALUE dir = Data_Wrap_Struct(klass, 0, free_dir, 0); + struct dir_data *dp; + VALUE dir = Data_Make_Struct(klass, struct dir_data, 0, free_dir, dp); dir_initialize(dir, dirname); if (rb_block_given_p()) { @@ -301,22 +313,34 @@ dir_closed() } #define GetDIR(obj, dirp) {\ - Data_Get_Struct(obj, DIR, dirp);\ - if (dirp == NULL) dir_closed();\ + Data_Get_Struct(obj, struct dir_data, dirp);\ + if (dirp->dir == NULL) dir_closed();\ +} + +static VALUE +dir_path(dir) + VALUE dir; +{ + struct dir_data *dirp; + + GetDIR(dir, dirp); + if (!dirp->path) return Qnil; + return rb_str_new2(dirp->path); } static VALUE dir_read(dir) VALUE dir; { - DIR *dirp; + struct dir_data *dirp; struct dirent *dp; GetDIR(dir, dirp); errno = 0; - dp = readdir(dirp); - if (dp) + dp = readdir(dirp->dir); + if (dp) { return rb_tainted_str_new(dp->d_name, NAMLEN(dp)); + } else if (errno == 0) { /* end of stream */ return Qnil; } @@ -330,13 +354,13 @@ static VALUE dir_each(dir) VALUE dir; { - DIR *dirp; + struct dir_data *dirp; struct dirent *dp; GetDIR(dir, dirp); - for (dp = readdir(dirp); dp != NULL; dp = readdir(dirp)) { + for (dp = readdir(dirp->dir); dp != NULL; dp = readdir(dirp->dir)) { rb_yield(rb_tainted_str_new(dp->d_name, NAMLEN(dp))); - if (DATA_PTR(dir) == NULL) dir_closed(); + if (dirp->dir == NULL) dir_closed(); } return dir; } @@ -346,11 +370,11 @@ dir_tell(dir) VALUE dir; { #ifdef HAVE_TELLDIR - DIR *dirp; + struct dir_data *dirp; long pos; GetDIR(dir, dirp); - pos = telldir(dirp); + pos = telldir(dirp->dir); return rb_int2inum(pos); #else rb_notimplement(); @@ -361,11 +385,11 @@ static VALUE dir_seek(dir, pos) VALUE dir, pos; { - DIR *dirp; + struct dir_data *dirp; #ifdef HAVE_SEEKDIR GetDIR(dir, dirp); - seekdir(dirp, NUM2INT(pos)); + seekdir(dirp->dir, NUM2INT(pos)); return dir; #else rb_notimplement(); @@ -376,10 +400,10 @@ static VALUE dir_rewind(dir) VALUE dir; { - DIR *dirp; + struct dir_data *dirp; GetDIR(dir, dirp); - rewinddir(dirp); + rewinddir(dirp->dir); return dir; } @@ -387,12 +411,11 @@ static VALUE dir_close(dir) VALUE dir; { - DIR *dirp; + struct dir_data *dirp; - Data_Get_Struct(dir, DIR, dirp); - if (dirp == NULL) dir_closed(); - closedir(dirp); - DATA_PTR(dir) = NULL; + GetDIR(dir, dirp); + closedir(dirp->dir); + dirp->dir = NULL; return Qnil; } @@ -978,6 +1001,7 @@ Init_Dir() rb_define_singleton_method(rb_cDir, "entries", dir_entries, 1); rb_define_method(rb_cDir,"initialize", dir_initialize, 1); + rb_define_method(rb_cDir,"path", dir_path, 0); rb_define_method(rb_cDir,"read", dir_read, 0); rb_define_method(rb_cDir,"each", dir_each, 0); rb_define_method(rb_cDir,"rewind", dir_rewind, 0); -- cgit v1.2.3