From 780f2f681bccf82024bdb6da2e2cccaa0e084663 Mon Sep 17 00:00:00 2001 From: Andre Noll Date: Tue, 23 Dec 2014 12:52:03 +0000 Subject: [PATCH] aft: Update mtime and file size on afhi changes. If the current audio file is re-added to the osl database, for example because meta tags have changed, file size and modification time change. However, the paraslash stat command still shows the old values because currently the virtual streaming system calls fstat(2) only once when the audio file is opened and keeps reporting the resulting mtime and file size values until the file is closed. This commit introduces make_inode_status_items() which is called from make_status_items() on AFSI_CHANGE and AFHI_CHANGE events for the current audio file. The new function calls stat(2) on the path obtained from the current aft row. We can't use fstat(2) since (a) we don't have an open file descriptor any more and (b) this would not work anyway if the original file was overwritten. Due to the new helper, mmd->mtime can be removed. We must keep mmd->size though, since we need the original file size for the call to munmap(). --- aft.c | 24 ++++++++++++++++++++++++ command.c | 8 -------- server.h | 2 -- vss.c | 2 -- 4 files changed, 24 insertions(+), 12 deletions(-) diff --git a/aft.c b/aft.c index 0e86b12d..59be56eb 100644 --- a/aft.c +++ b/aft.c @@ -1043,6 +1043,28 @@ out: static struct ls_data status_item_ls_data; static struct osl_row *current_aft_row; +static void make_inode_status_items(struct para_buffer *pb) +{ + struct stat statbuf = {.st_size = 0}; + char *path, mtime_str[30] = "\0"; + struct tm mtime_tm; + int ret; + + ret = get_audio_file_path_of_row(current_aft_row, &path); + if (ret < 0) + goto out; + ret = stat(path, &statbuf); + if (ret < 0) + goto out; + localtime_r(&statbuf.st_mtime, &mtime_tm); + ret = strftime(mtime_str, 29, "%b %d %Y", &mtime_tm); + assert(ret > 0); /* number of bytes placed in mtime_str */ +out: + /* We don't care too much about errors here */ + (void)WRITE_STATUS_ITEM(pb, SI_MTIME, "%s\n", mtime_str); + (void)WRITE_STATUS_ITEM(pb, SI_FILE_SIZE, "%ld\n", statbuf.st_size / 1024); +} + static int make_status_items(void) { struct ls_options opts = { @@ -1057,6 +1079,7 @@ static int make_status_items(void) ret = print_list_item(&status_item_ls_data, &opts, &pb, current_time); if (ret < 0) return ret; + make_inode_status_items(&pb); free(status_items); status_items = pb.buf; memset(&pb, 0, sizeof(pb)); @@ -1068,6 +1091,7 @@ static int make_status_items(void) status_items = NULL; return ret; } + make_inode_status_items(&pb); free(parser_friendly_status_items); parser_friendly_status_items = pb.buf; return 1; diff --git a/command.c b/command.c index 2ef9c5a8..0baad5dc 100644 --- a/command.c +++ b/command.c @@ -112,21 +112,15 @@ static char *vss_get_status_flags(unsigned int flags) static unsigned get_status(struct misc_meta_data *nmmd, int parser_friendly, char **result) { - char mtime[30] = ""; char *status, *flags; /* vss status info */ /* nobody updates our version of "now" */ long offset = (nmmd->offset + 500) / 1000; struct timeval current_time; - struct tm mtime_tm; struct para_buffer b = {.flags = parser_friendly? PBF_SIZE_PREFIX : 0}; /* report real status */ status = vss_status_tohuman(nmmd->vss_status_flags); flags = vss_get_status_flags(nmmd->vss_status_flags); - if (nmmd->size) { /* parent currently has an audio file open */ - localtime_r(&nmmd->mtime, &mtime_tm); - strftime(mtime, 29, "%b %d %Y", &mtime_tm); - } clock_get_realtime(¤t_time); /* * The calls to WRITE_STATUS_ITEM() below never fail because @@ -134,8 +128,6 @@ static unsigned get_status(struct misc_meta_data *nmmd, int parser_friendly, * is not smart enough to prove this and complains nevertheless. * Casting the return value to void silences clang. */ - (void)WRITE_STATUS_ITEM(&b, SI_FILE_SIZE, "%zu\n", nmmd->size / 1024); - (void)WRITE_STATUS_ITEM(&b, SI_MTIME, "%s\n", mtime); (void)WRITE_STATUS_ITEM(&b, SI_STATUS, "%s\n", status); (void)WRITE_STATUS_ITEM(&b, SI_STATUS_FLAGS, "%s\n", flags); (void)WRITE_STATUS_ITEM(&b, SI_OFFSET, "%li\n", offset); diff --git a/server.h b/server.h index a89e005a..287614c8 100644 --- a/server.h +++ b/server.h @@ -52,8 +52,6 @@ struct sender_command_data{ struct misc_meta_data { /** The size of the current audio file in bytes. */ size_t size; - /** The last modification time of the current audio file. */ - time_t mtime; /** The "old" status flags -- commands may only read them. */ unsigned int vss_status_flags; /** The new status flags -- commands may set them. */ diff --git a/vss.c b/vss.c index fc42ba68..ea075df9 100644 --- a/vss.c +++ b/vss.c @@ -855,7 +855,6 @@ static void vss_eof(struct vss_task *vsst) mmd->afd.afhi.chunk_tv.tv_usec = 0; free(mmd->afd.afhi.chunk_table); mmd->afd.afhi.chunk_table = NULL; - mmd->mtime = 0; mmd->size = 0; mmd->events++; } @@ -1011,7 +1010,6 @@ static void recv_afs_result(struct vss_task *vsst, fd_set *rfds) goto err; } mmd->size = statbuf.st_size; - mmd->mtime = statbuf.st_mtime; ret = para_mmap(mmd->size, PROT_READ, MAP_PRIVATE | MAP_POPULATE, passed_fd, 0, &vsst->map); if (ret < 0) -- 2.39.5