A new command 'create_speed', has been introduced to measure the performance of creating and deleting many files.
Signed-off-by: Daniel Lee <chul...@google.com> --- tools/f2fs_io/f2fs_io.c | 112 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 112 insertions(+) diff --git a/tools/f2fs_io/f2fs_io.c b/tools/f2fs_io/f2fs_io.c index 6531b55..ea6a3ff 100644 --- a/tools/f2fs_io/f2fs_io.c +++ b/tools/f2fs_io/f2fs_io.c @@ -2092,6 +2092,117 @@ static void do_ftruncate(int argc, char **argv, const struct cmd_desc *cmd) exit(0); } +#define create_speed_desc "create_speed a file" +#define create_speed_help \ +"f2fs_io create_speed [dir] [num_files] [size_kb]\n\n" \ +"Measures file creation and deletion performance.\n" + +static void do_create_speed(int argc, char **argv, const struct cmd_desc *cmd) +{ + if (argc != 4) { + fputs("Usage: f2fs_io create_latency <directory> <num_files> [size_kb]\n", stderr); + fputs(cmd->cmd_help, stderr); + exit(1); + } + + const char *dir = argv[1]; + int num_files = atoi(argv[2]); + int size_kb = atoi(argv[3]); + char *write_buffer = NULL; + + if (num_files <= 0) { + fprintf(stderr, "Error: Number of files must be positive.\n"); + exit(1); + } + + if (size_kb > 0) { + write_buffer = malloc(size_kb * 1024); + if (!write_buffer) { + perror("Failed to allocate write buffer"); + exit(1); + } + memset(write_buffer, 'a', size_kb * 1024); + } + + // Creation Phase + printf("Starting test: Creating %d files of %dKB each in %s\n", num_files, size_kb, dir); + + struct timespec create_start, create_end; + + clock_gettime(CLOCK_MONOTONIC, &create_start); + + for (int i = 0; i < num_files; i++) { + char path[1024]; + + snprintf(path, sizeof(path), "%s/test_file_%d", dir, i); + + int fd = open(path, O_WRONLY | O_CREAT, 0644); + + if (fd < 0) { + perror("Error opening file"); + continue; + } + if (size_kb > 0) { + if (write(fd, write_buffer, size_kb * 1024) < 0) + perror("Error writing to file"); + } + if (fsync(fd) < 0) + perror("Error fsyncing file"); + + close(fd); + } + + clock_gettime(CLOCK_MONOTONIC, &create_end); + + + // Deletion Phase + printf("Deleting %d created files...\n", num_files); + + struct timespec del_start, del_end; + + clock_gettime(CLOCK_MONOTONIC, &del_start); + + for (int i = 0; i < num_files; i++) { + char path[1024]; + + snprintf(path, sizeof(path), "%s/test_file_%d", dir, i); + if (unlink(path) != 0) + perror("Error unlinking file"); + } + sync(); + + clock_gettime(CLOCK_MONOTONIC, &del_end); + + long create_seconds = create_end.tv_sec - create_start.tv_sec; + long create_ns = create_end.tv_nsec - create_start.tv_nsec; + double create_time_s = (double)create_seconds + (double)create_ns / 1000000000.0; + double create_throughput = (create_time_s > 0) ? (num_files / create_time_s) : 0; + + long del_seconds = del_end.tv_sec - del_start.tv_sec; + long del_ns = del_end.tv_nsec - del_start.tv_nsec; + double del_time_s = (double)del_seconds + (double)del_ns / 1000000000.0; + double del_throughput = (del_time_s > 0) ? (num_files / del_time_s) : 0; + + printf("Operation,total_files,file_size_kb,total_time_s,throughput_files_per_sec\n"); + + printf("CREATE,%d,%d,%.4f,%.2f\n", + num_files, + size_kb, + create_time_s, + create_throughput); + + printf("DELETE,%d,%d,%.4f,%.2f\n", + num_files, + size_kb, + del_time_s, + del_throughput); + + if (write_buffer) + free(write_buffer); + + exit(0); +} + #define CMD_HIDDEN 0x0001 #define CMD(name) { #name, do_##name, name##_desc, name##_help, 0 } #define _CMD(name) { #name, do_##name, NULL, NULL, CMD_HIDDEN } @@ -2140,6 +2251,7 @@ const struct cmd_desc cmd_list[] = { CMD(get_advise), CMD(ioprio), CMD(ftruncate), + CMD(create_speed), { NULL, NULL, NULL, NULL, 0 } }; -- 2.50.0.rc1.591.g9c95f17f64-goog _______________________________________________ Linux-f2fs-devel mailing list Linux-f2fs-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/linux-f2fs-devel