I am using a patch in dvsink-files which turned out to be helpful. Users
are concerned about location of files when starting dvsink-files, so
this appears a good place to print an estimate of available recording time.
See attached.
There are many more 'goodies' included in
https://github.com/jnweiger/dvswitch/tree/susedevel
free for cherry picking :-)
cheers, JW-
diff --git a/src/dvsink-files.c b/src/dvsink-files.c
index 78a74d8..c5aa5c1 100644
--- a/src/dvsink-files.c
+++ b/src/dvsink-files.c
@@ -1,5 +1,7 @@
// Copyright 2007-2008 Ben Hutchings.
// Copyright 2008 Petter Reinholdtsen.
+// Copyright 2014 Jürgen Weigert <jnwei...@gmail.com>
+//
// See the file "COPYING" for licence details.
// Sink that creates DIF ("raw DV") files
@@ -17,12 +19,16 @@
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
+#include <sys/statvfs.h>
#include "config.h"
#include "dif.h"
#include "protocol.h"
#include "socket.h"
+#define MAX_PATH 4096
+#define MBYTES_PER_HOUR 6500 // Standard DV-files (slight over-estimation)
+
static struct option options[] = {
{"host", 1, NULL, 'h'},
{"port", 1, NULL, 'p'},
@@ -59,8 +65,10 @@ static void usage(const char * progname)
{
fprintf(stderr,
"\
-Usage: %s [-h HOST] [-p PORT] [-P PID filename] [NAME-FORMAT]\n",
- progname);
+Usage: %s [-h HOST] [-p PORT] [-P PID filename] [NAME-FORMAT]\n\
+ or\n\
+ %s -t PATH_WHERE_TO_CHECK_DISK_SPACE\n",
+ progname, progname);
}
struct transfer_params {
@@ -163,6 +171,53 @@ static ssize_t write_retry(int fd, const void * buf, size_t count)
return total;
}
+
+static void print_disk_full_estimate(char *filename)
+{
+ char *path = strdup(filename);
+
+ if (path[0] != '/') // path = abs_path(path)
+ {
+ char cwd[MAX_PATH];
+ char *c = getcwd(cwd, MAX_PATH);
+ char *old = path;
+ path = (char *)malloc(strlen(old)+strlen(c)+3);
+ path[0] = '\0';
+ strcat(path, c);
+ if (path[strlen(path)] != '/')
+ strcat(path, "/");
+ strcat(path, old);
+ }
+
+ char *p = path+strlen(path);
+
+ while (p > path) // path = dirname(path); # file may not yet exist.
+ {
+ if (p[-1] == '/')
+ {
+ *p = '\0';
+ break;
+ }
+ p--;
+ }
+
+ struct statvfs buf;
+ int r = statvfs(path, &buf);
+
+ if (r)
+ {
+ printf("WARN: %s: cannot calculate free space\n", path);
+ }
+ else
+ {
+ unsigned long mbytes = buf.f_bsize*buf.f_bavail/1024/1024;
+ double hours = mbytes / MBYTES_PER_HOUR;
+
+ // printf("r=%d, blocksize = %ld, available blocks = %ld bytes=%ld\n", r, buf.f_bsize, buf.f_bavail, buf.f_bsize*buf.f_bavail);
+ printf("%s: %.1fGB free; disk full in %.1f hours\n", path, mbytes/1024., hours);
+ }
+ free(path);
+}
static void transfer_frames(struct transfer_params * params)
{
@@ -202,6 +257,7 @@ static void transfer_frames(struct transfer_params * params)
if (buf[SINK_FRAME_CUT_FLAG_POS] == SINK_FRAME_CUT_STOP)
{
printf("INFO: Stopped recording\n");
+ print_disk_full_estimate(name);
fflush(stdout);
continue;
}
@@ -209,8 +265,8 @@ static void transfer_frames(struct transfer_params * params)
file = create_file(output_name_format, &name);
if (starting)
printf("INFO: Started recording\n");
+ print_disk_full_estimate(name);
printf("INFO: Created file %s\n", name);
- free(name);
fflush(stdout);
}
@@ -260,14 +316,18 @@ int main(int argc, char ** argv)
{
// Initialise settings from configuration files.
dvswitch_read_config(handle_config);
+ int test_only = 0;
// Parse arguments.
int opt;
- while ((opt = getopt_long(argc, argv, "h:p:P:", options, NULL)) != -1)
+ while ((opt = getopt_long(argc, argv, "h:p:P:t", options, NULL)) != -1)
{
switch (opt)
{
+ case 't':
+ test_only = 1;
+ break;
case 'h':
free(mixer_host);
mixer_host = strdup(optarg);
@@ -289,6 +349,10 @@ int main(int argc, char ** argv)
}
}
+ print_disk_full_estimate(output_name_format);
+ if (test_only)
+ exit(0);
+
if (!mixer_host || !mixer_port)
{
fprintf(stderr, "%s: mixer hostname and port not defined\n",
@@ -338,7 +402,7 @@ int main(int argc, char ** argv)
perror("ERROR: write");
exit(1);
}
- printf("INFO: Connected.\n");
+ printf("INFO: Connected. (Waiting for start record)\n");
transfer_frames(¶ms);