+static int read_data(int fd, void *data, size_t size)
+{
+ ssize_t ret;
+
+ while (size) {
+ ret = read(fd, data, size);
+ if (ret < 0) {
+ if (errno == EAGAIN || errno == EINTR)
+ continue;
+ break;
+ } else if (!ret)
+ break;
+ else {
+ data += ret;
+ size -= ret;
+ }
+ }
+
+ if (size)
+ return EAGAIN;
+
+ return 0;
+}
+
+static void fio_client_json_init(void)
+{
+ char time_buf[32];
+ time_t time_p;
+
+ if (!(output_format & FIO_OUTPUT_JSON))
+ return;
+
+ time(&time_p);
+ os_ctime_r((const time_t *) &time_p, time_buf, sizeof(time_buf));
+ time_buf[strlen(time_buf) - 1] = '\0';
+
+ root = json_create_object();
+ json_object_add_value_string(root, "fio version", fio_version_string);
+ json_object_add_value_int(root, "timestamp", time_p);
+ json_object_add_value_string(root, "time", time_buf);
+
+ job_opt_object = json_create_object();
+ json_object_add_value_object(root, "global options", job_opt_object);
+ clients_array = json_create_array();
+ json_object_add_value_array(root, "client_stats", clients_array);
+ du_array = json_create_array();
+ json_object_add_value_array(root, "disk_util", du_array);
+}
+
+static void fio_client_json_fini(void)
+{
+ if (!(output_format & FIO_OUTPUT_JSON))
+ return;
+
+ log_info("\n");
+ json_print_object(root, NULL);
+ log_info("\n");
+ json_free_object(root);
+ root = NULL;
+ clients_array = NULL;
+ du_array = NULL;
+}
+