blind-repeat.c - blind - suckless command-line video editing utility | |
git clone git://git.suckless.org/blind | |
Log | |
Files | |
Refs | |
README | |
LICENSE | |
--- | |
blind-repeat.c (2419B) | |
--- | |
1 /* See LICENSE file for copyright and license details. */ | |
2 #include "common.h" | |
3 | |
4 USAGE("([-f] count | 'inf') [file]") | |
5 | |
6 static size_t count = 0; | |
7 static int inf; | |
8 static struct stream stream; | |
9 | |
10 static int | |
11 repeat_regular_file(void) | |
12 { | |
13 stream.ptr = 0; | |
14 while (inf || count--) { | |
15 fadvise_sequential(stream.fd, (off_t)(stream.headlen), 0… | |
16 elseek(stream.fd, (off_t)(stream.headlen), SEEK_SET, str… | |
17 if (esend_stream(&stream, STDOUT_FILENO, NULL)) | |
18 return -1; | |
19 } | |
20 return 0; | |
21 } | |
22 | |
23 static int | |
24 repeat_regular_file_framewise(void) | |
25 { | |
26 size_t i; | |
27 off_t off = (off_t)(stream.headlen); | |
28 stream.ptr = 0; | |
29 echeck_dimensions(&stream, WIDTH | HEIGHT | LENGTH, "input"); | |
30 for (;; off += (off_t)(stream.frame_size)) { | |
31 for (i = 0; i < count; i++) { | |
32 elseek(stream.fd, off, SEEK_SET, stream.file); | |
33 if (!esend_frames(&stream, STDOUT_FILENO, 1, "<s… | |
34 return 0; | |
35 } | |
36 } | |
37 } | |
38 | |
39 static int | |
40 repeat_stdin(void) | |
41 { | |
42 size_t ptr = stream.ptr; | |
43 size_t size = MAX(ptr, BUFSIZ); | |
44 char *buf = memcpy(emalloc(size), stream.buf, ptr); | |
45 egetfile(STDIN_FILENO, &buf, &ptr, &size, "<stdout>"); | |
46 while (inf || count--) | |
47 if (writeall(STDOUT_FILENO, buf, ptr)) | |
48 return free(buf), -1; | |
49 return free(buf), 0; | |
50 } | |
51 | |
52 static int | |
53 repeat_stdin_framewise(void) | |
54 { | |
55 char *buf; | |
56 size_t i; | |
57 echeck_dimensions(&stream, WIDTH | HEIGHT, "input"); | |
58 buf = emalloc(stream.frame_size); | |
59 while (eread_frame(&stream, buf)) | |
60 for (i = 0; i < count; i++) | |
61 if (writeall(STDOUT_FILENO, buf, stream.frame_si… | |
62 return free(buf), -1; | |
63 return free(buf), 0; | |
64 } | |
65 | |
66 int | |
67 main(int argc, char *argv[]) | |
68 { | |
69 int framewise = 0; | |
70 | |
71 ARGBEGIN { | |
72 case 'f': | |
73 framewise = 1; | |
74 break; | |
75 default: | |
76 usage(); | |
77 } ARGEND; | |
78 | |
79 if (argc < 1 || argc > 2) | |
80 usage(); | |
81 | |
82 if ((inf = !strcmp(argv[0], "inf"))) { | |
83 if (framewise) | |
84 usage(); | |
85 einf_check_fd(STDOUT_FILENO, "<stdout>"); | |
86 } else { | |
87 count = etozu_arg("the count", argv[0], 0, SIZE_MAX); | |
88 } | |
89 | |
90 if (argv[1] && !strcmp(argv[1], "-")) | |
91 argv[1] = NULL; | |
92 | |
93 eopen_stream(&stream, argv[1]); | |
94 if (stream.frames && count > SIZE_MAX / stream.frames) | |
95 eprintf("%s: video is too long\n", stream.file); | |
96 stream.frames *= count; | |
97 fprint_stream_head(stdout, &stream); | |
98 efflush(stdout, "<stdout>"); | |
99 | |
100 if (!argv[1] | |
101 ? (framewise ? repeat_stdin_framewise() : repeat_stdin… | |
102 : (framewise ? repeat_regular_file_framewise(): repeat_regul… | |
103 if (!inf || errno != EPIPE) | |
104 eprintf("write <stdout>:"); | |
105 | |
106 close(stream.fd); | |
107 return 0; | |
108 } |