diff --git a/libports/run/libc_ffat.run b/libports/run/libc_ffat.run
index a0726759d1..71dbd42ebb 100644
--- a/libports/run/libc_ffat.run
+++ b/libports/run/libc_ffat.run
@@ -53,6 +53,9 @@ set config {
+
+
+
}
diff --git a/libports/run/libc_fs.run b/libports/run/libc_fs.run
index ce26ba2234..d18a2764f3 100644
--- a/libports/run/libc_fs.run
+++ b/libports/run/libc_fs.run
@@ -38,6 +38,9 @@ install_config {
+
+
+
}
diff --git a/libports/src/lib/libc_ffat/plugin.cc b/libports/src/lib/libc_ffat/plugin.cc
index 167a674a29..92e88c0860 100644
--- a/libports/src/lib/libc_ffat/plugin.cc
+++ b/libports/src/lib/libc_ffat/plugin.cc
@@ -449,7 +449,10 @@ class Plugin : public Libc::Plugin
ffat_flags |= FA_WRITE;
if ((flags & O_CREAT) == O_CREAT)
- ffat_flags |= FA_CREATE_NEW;
+ if ((flags & O_EXCL) == O_EXCL)
+ ffat_flags |= FA_CREATE_NEW;
+ else
+ ffat_flags |= FA_CREATE_ALWAYS;
FRESULT res = f_open(&ffat_file, pathname, ffat_flags);
diff --git a/libports/src/test/libc_ffat/main.cc b/libports/src/test/libc_ffat/main.cc
index 7c39e8eba0..6d635e401e 100644
--- a/libports/src/test/libc_ffat/main.cc
+++ b/libports/src/test/libc_ffat/main.cc
@@ -12,6 +12,9 @@
* under the terms of the GNU General Public License version 2.
*/
+/* Genode includes */
+#include
+
/* libc includes */
#include
#include
@@ -38,62 +41,70 @@ int main(int argc, char *argv[])
int ret, fd;
char const *dir_name = "/testdir";
- char const *dir_name_long = "testdir long";
char const *file_name = "test.tst";
char const *pattern = "a single line of text";
- /* create directory (short name) */
- CALL_AND_CHECK(ret, mkdir(dir_name, 0777), ret == 0, "dir_name=%s", dir_name);
+ unsigned int iterations = 1;
- /* change to new directory */
- CALL_AND_CHECK(ret, chdir(dir_name), ret == 0, "dir_name=%s", dir_name);
+ try {
+ Genode::config()->xml_node().sub_node("iterations").attribute("value").value(&iterations);
+ } catch(...) { }
- /* create directory (long name) */
- CALL_AND_CHECK(ret, mkdir(dir_name_long, 0777), ret == 0, "dir_name_long=%s", dir_name_long);
+ for (unsigned int i = 0; i < iterations; i++) {
- /* write pattern to a file */
- CALL_AND_CHECK(fd, open(file_name, O_CREAT | O_WRONLY), fd >= 0, "file_name=%s", file_name);
- size_t count = strlen(pattern);
- CALL_AND_CHECK(ret, write(fd, pattern, count), ret > 0, "count=%zd", count);
- CALL_AND_CHECK(ret, close(fd), ret == 0, "");
+ /* create directory (short name) */
+ CALL_AND_CHECK(ret, mkdir(dir_name, 0777), ((ret == 0) || (errno == EEXIST)), "dir_name=%s", dir_name);
- /* query file status of new file */
- struct stat stat_buf;
- CALL_AND_CHECK(ret, stat(file_name, &stat_buf), ret == 0, "file_name=%s", file_name);
- printf("file size: %u bytes\n", (unsigned)stat_buf.st_size);
- struct tm *file_time = gmtime(&stat_buf.st_mtime);
- printf("last modified: %04u-%02u-%02u %02u:%02u:%02u\n",
- file_time->tm_year, file_time->tm_mon, file_time->tm_mday,
- file_time->tm_hour, file_time->tm_min, file_time->tm_sec);
+ /* change to new directory */
+ CALL_AND_CHECK(ret, chdir(dir_name), ret == 0, "dir_name=%s", dir_name);
- /* read and verify file content */
- CALL_AND_CHECK(fd, open(file_name, O_RDONLY), fd >= 0, "file_name=%s", file_name);
- static char buf[512];
- CALL_AND_CHECK(count, read(fd, buf, sizeof(buf)), count > 0, "");
- CALL_AND_CHECK(ret, close(fd), ret == 0, "");
- printf("content of file: \"%s\"\n", buf);
- if (strcmp(buf, pattern) != 0) {
- printf("unexpected content of file\n");
- return -1;
- } else {
- printf("file content is correct\n");
- }
+ /* write pattern to a file */
+ CALL_AND_CHECK(fd, open(file_name, O_CREAT | O_WRONLY), fd >= 0, "file_name=%s", file_name);
+ size_t count = strlen(pattern);
+ CALL_AND_CHECK(ret, write(fd, pattern, count), ret > 0, "count=%zd", count);
+ CALL_AND_CHECK(ret, close(fd), ret == 0, "");
- /* read directory entries */
- DIR *dir;
- CALL_AND_CHECK(dir, opendir(dir_name), dir, "dir_name=\"%s\"", dir_name);
- printf("calling readdir()\n");
- for (;;) {
- struct dirent *dirent = readdir(dir);
- if (dirent) {
- if (dirent->d_type == DT_DIR)
- printf("found directory %s\n", dirent->d_name);
- else
- printf("found file %s\n", dirent->d_name);
+ /* query file status of new file */
+ struct stat stat_buf;
+ CALL_AND_CHECK(ret, stat(file_name, &stat_buf), ret == 0, "file_name=%s", file_name);
+ printf("file size: %u bytes\n", (unsigned)stat_buf.st_size);
+ struct tm *file_time = gmtime(&stat_buf.st_mtime);
+ printf("last modified: %04u-%02u-%02u %02u:%02u:%02u\n",
+ file_time->tm_year, file_time->tm_mon, file_time->tm_mday,
+ file_time->tm_hour, file_time->tm_min, file_time->tm_sec);
+
+ /* read and verify file content */
+ CALL_AND_CHECK(fd, open(file_name, O_RDONLY), fd >= 0, "file_name=%s", file_name);
+ static char buf[512];
+ CALL_AND_CHECK(count, read(fd, buf, sizeof(buf)), count > 0, "");
+ CALL_AND_CHECK(ret, close(fd), ret == 0, "");
+ printf("content of file: \"%s\"\n", buf);
+ if (strcmp(buf, pattern) != 0) {
+ printf("unexpected content of file\n");
+ return -1;
} else {
- printf("no (more) direntries found\n");
- break;
+ printf("file content is correct\n");
}
+
+ /* read directory entries */
+ DIR *dir;
+ CALL_AND_CHECK(dir, opendir(dir_name), dir, "dir_name=\"%s\"", dir_name);
+ printf("calling readdir()\n");
+ for (;;) {
+ struct dirent *dirent = readdir(dir);
+ if (dirent) {
+ if (dirent->d_type == DT_DIR)
+ printf("found directory %s\n", dirent->d_name);
+ else
+ printf("found file %s\n", dirent->d_name);
+ } else {
+ printf("no (more) direntries found\n");
+ break;
+ }
+ }
+
+ if (i < (iterations - 1))
+ sleep(2);
}
return 0;