diff --git a/deps/uv/README.md b/deps/uv/README.md index 880c5138cd..8e569bbfb6 100644 --- a/deps/uv/README.md +++ b/deps/uv/README.md @@ -8,8 +8,6 @@ http://nodejs.org/ ## Features -Implemented: - * Non-blocking TCP sockets * Non-blocking named pipes @@ -32,13 +30,11 @@ Implemented: * ANSI escape code controlled TTY `uv_tty_t` -In-progress: - - * File system events (Currently supports inotify, `ReadDirectoryChangesW` - and will support kqueue and event ports in the near future.) + * File system events Currently supports inotify, `ReadDirectoryChangesW` + and kqueue. Event ports in the near future. `uv_fs_event_t` - * Socket sharing between processes `uv_ipc_t` + * IPC and socket sharing between processes `uv_write2` ## Documentation diff --git a/deps/uv/src/unix/fs.c b/deps/uv/src/unix/fs.c index 1bc4f71eeb..76de94dea9 100644 --- a/deps/uv/src/unix/fs.c +++ b/deps/uv/src/unix/fs.c @@ -85,8 +85,7 @@ void uv_fs_req_cleanup(uv_fs_t* req) { switch (req->fs_type) { case UV_FS_READDIR: - assert((req->result == -1 && req->ptr == NULL) - || (req->result >= 0 && req->ptr != NULL)); + assert(req->result > 0 ? (req->ptr != NULL) : (req->ptr == NULL)); free(req->ptr); req->ptr = NULL; break; @@ -116,9 +115,6 @@ static int uv__fs_after(eio_req* eio) { switch (req->fs_type) { case UV_FS_READDIR: - if (req->eio->result == -1) - break; /* opendir() or readdir() operation failed. */ - /* * XXX This is pretty bad. * We alloc and copy the large null terminated string list from libeio. @@ -128,16 +124,21 @@ static int uv__fs_after(eio_req* eio) { */ buflen = 0; name = req->eio->ptr2; + for (i = 0; i < req->result; i++) { namelen = strlen(name); buflen += namelen + 1; - /* TODO check ENOMEM */ name += namelen; assert(*name == '\0'); name++; } - req->ptr = malloc(buflen); - memcpy(req->ptr, req->eio->ptr2, buflen); + + if (buflen) { + if ((req->ptr = malloc(buflen))) + memcpy(req->ptr, req->eio->ptr2, buflen); + else + uv__set_sys_error(req->loop, ENOMEM); + } break; case UV_FS_STAT: diff --git a/deps/uv/test/test-fs.c b/deps/uv/test/test-fs.c index 73939e2bfd..38953fd3c4 100644 --- a/deps/uv/test/test-fs.c +++ b/deps/uv/test/test-fs.c @@ -155,7 +155,7 @@ static void fchmod_cb(uv_fs_t* req) { ASSERT(req->result == 0); fchmod_cb_count++; uv_fs_req_cleanup(req); - check_permission("test_file", (int)req->data); + check_permission("test_file", *(int*)req->data); } @@ -164,7 +164,7 @@ static void chmod_cb(uv_fs_t* req) { ASSERT(req->result == 0); chmod_cb_count++; uv_fs_req_cleanup(req); - check_permission("test_file", (int)req->data); + check_permission("test_file", *(int*)req->data); } @@ -354,6 +354,16 @@ static void readdir_cb(uv_fs_t* req) { } +static void empty_readdir_cb(uv_fs_t* req) { + ASSERT(req == &readdir_req); + ASSERT(req->fs_type == UV_FS_READDIR); + ASSERT(req->result == 0); + ASSERT(req->ptr == NULL); + uv_fs_req_cleanup(req); + readdir_cb_count++; +} + + static void stat_cb(uv_fs_t* req) { ASSERT(req == &stat_req); ASSERT(req->fs_type == UV_FS_STAT || req->fs_type == UV_FS_LSTAT); @@ -869,7 +879,10 @@ TEST_IMPL(fs_chmod) { #ifndef _WIN32 /* async chmod */ - req.data = (void*)0200; + { + static int mode = 0200; + req.data = &mode; + } r = uv_fs_chmod(loop, &req, "test_file", 0200, chmod_cb); ASSERT(r == 0); uv_run(loop); @@ -878,14 +891,20 @@ TEST_IMPL(fs_chmod) { #endif /* async chmod */ - req.data = (void*)0400; + { + static int mode = 0400; + req.data = &mode; + } r = uv_fs_chmod(loop, &req, "test_file", 0400, chmod_cb); ASSERT(r == 0); uv_run(loop); ASSERT(chmod_cb_count == 1); /* async fchmod */ - req.data = (void*)0600; + { + static int mode = 0600; + req.data = &mode; + } r = uv_fs_fchmod(loop, &req, file, 0600, fchmod_cb); ASSERT(r == 0); uv_run(loop); @@ -1283,3 +1302,34 @@ TEST_IMPL(fs_stat_missing_path) { return 0; } + + +TEST_IMPL(fs_readdir_empty_dir) { + const char* path; + uv_fs_t req; + int r; + + path = "./empty_dir/"; + loop = uv_default_loop(); + + uv_fs_mkdir(loop, &req, path, 0777, NULL); + uv_fs_req_cleanup(&req); + + r = uv_fs_readdir(loop, &req, path, 0, NULL); + ASSERT(r == 0); + ASSERT(req.result == 0); + ASSERT(req.ptr == NULL); + uv_fs_req_cleanup(&req); + + r = uv_fs_readdir(loop, &readdir_req, path, 0, empty_readdir_cb); + ASSERT(r == 0); + + ASSERT(readdir_cb_count == 0); + uv_run(loop); + ASSERT(readdir_cb_count == 1); + + uv_fs_rmdir(loop, &req, path, NULL); + uv_fs_req_cleanup(&req); + + return 0; +} diff --git a/deps/uv/test/test-list.h b/deps/uv/test/test-list.h index d11257aa95..dcf278608c 100644 --- a/deps/uv/test/test-list.h +++ b/deps/uv/test/test-list.h @@ -99,6 +99,7 @@ TEST_DECLARE (fs_stat_missing_path) TEST_DECLARE (fs_event_watch_dir) TEST_DECLARE (fs_event_watch_file) TEST_DECLARE (fs_event_watch_file_current_dir) +TEST_DECLARE (fs_readdir_empty_dir) TEST_DECLARE (threadpool_queue_work_simple) #ifdef _WIN32 TEST_DECLARE (spawn_detect_pipe_name_collisions_on_windows) @@ -232,6 +233,7 @@ TASK_LIST_START TEST_ENTRY (fs_event_watch_dir) TEST_ENTRY (fs_event_watch_file) TEST_ENTRY (fs_event_watch_file_current_dir) + TEST_ENTRY (fs_readdir_empty_dir) TEST_ENTRY (threadpool_queue_work_simple)