1 /*
2  * cmdline.c -- parse transcode command line
3  * Written by Andrew Church <achurch@achurch.org>
4  *
5  * This file is part of transcode, a video stream processing tool.
6  * transcode is free software, distributable under the terms of the GNU
7  * General Public License (version 2 or later).  See the file COPYING
8  * for details.
9  */
10 
11 #include "transcode.h"
12 #include "decoder.h"
13 #include "probe.h"
14 #include "libtc/libtc.h"
15 #include "libtc/cfgfile.h"
16 #include "libtc/ratiocodes.h"
17 #include "libtc/tccodecs.h"
18 #include "libtc/xio.h"
19 
20 #include "cmdline.h"
21 
22 #include <ctype.h>
23 #ifdef HAVE_GETOPT_LONG_ONLY
24 #include <getopt.h>
25 #else
26 #include "libtc/getopt.h"
27 #endif
28 
29 
30 /* Global variables from transcode.c that should eventually go away. */
31 int core_mode=TC_MODE_DEFAULT;
32 char *im_aud_mod = NULL, *im_vid_mod = NULL;
33 char *ex_aud_mod = NULL, *ex_vid_mod = NULL, *ex_mplex_mod = NULL;
34 char *plugins_string = NULL;
35 char
36     *nav_seek_file=NULL, *socket_file=NULL,
37     *chbase=NULL, //*dirbase=NULL,
38     base[TC_BUF_MIN];
39 int psu_frame_threshold=12; //psu with less/equal frames are skipped.
40 int
41     no_vin_codec=1, no_ain_codec=1,
42     no_v_out_codec=1, no_a_out_codec=1;
43 int
44     frame_a=TC_FRAME_FIRST,   // defaults to all frames
45     frame_b=TC_FRAME_LAST,
46     splitavi_frames=0,
47     psu_mode=TC_FALSE;
48 int preset_flag=0, auto_probe=1, seek_range=1;
49 int no_audio_adjust=TC_FALSE, no_split=TC_FALSE;
50 char *fc_ttime_string = NULL;
51 int sync_seconds=0;
52 pid_t writepid = 0;
53 
54 
55 /*************************************************************************/
56 
57 /* Utility routines used by option processing. */
58 
59 
60 /**
61  * print_option_help:  Print a help line for a given option.
62  *
63  * Parameters:
64  *         name: Option name (long name).
65  *     shortopt: Character used for the short form of the option, 0 if none.
66  *      argname: String describing the option's argument, NULL if none.
67  *     helptext: Help text for the option.  May include newlines (\n).
68  *     optwidth: Number of columns to use for the long name and argument.
69  * Return value:
70  *     None.
71  */
72 
73 #define MAX_LINELEN   79  /* Maximum line length */
74 #define MAX_OPTWIDTH  35  /* Maximum space to allocate to options */
75 
print_option_help(const char * name,char shortopt,const char * argname,const char * helptext,int optwidth)76 static void print_option_help(const char *name, char shortopt,
77                               const char *argname, const char *helptext,
78                               int optwidth)
79 {
80     int helpmax;
81     char optbuf[MAX_LINELEN+1];
82     const char *s;
83 
84     if (optwidth > MAX_OPTWIDTH)
85         optwidth = MAX_OPTWIDTH;
86     snprintf(optbuf, sizeof(optbuf), "--%s%s%s",
87              name,
88              argname ? " " : "",
89              argname ? argname : "");
90     printf("  %c%c%c%-*s  ",
91            shortopt ? '-' : ' ',
92            shortopt ? shortopt : ' ',
93            shortopt ? '/' : ' ',
94            optwidth, optbuf);
95     if (strlen(optbuf) > optwidth) {
96         /* If the option overflowed the given width, skip to the next line */
97         printf("\n%-*s", 5 + optwidth + 2, "");
98     }
99     /* Break help text into lines at whitespace or \n */
100     helpmax = MAX_LINELEN - 5 - optwidth - 2;
101     s = helptext;
102     s += strspn(s, " \t");
103     do {
104         const char *t, *next;
105         t = s + helpmax;
106         if (t > s + strlen(s))
107             t = s + strlen(s);
108         if (t > s + strcspn(s, "\n"))
109             t = s + strcspn(s, "\n");
110         /* Don't try to break text with no whitespace */
111         if (s + strcspn(s, " \t") < t) {
112             while (t > s+1 && *t && !isspace(*t))
113                 t--;
114         }
115         if (*t == '\n') {
116             /* Preserve whitespace after a newline */
117             next = t + 1;
118         } else {
119             next = t + strspn(t, " \t\n");
120         }
121         /* Only print indent if there's more text */
122         printf("%.*s\n%-*s",
123                (int)(t-s), s,
124                *next ? optwidth+7+3 : 0, "");
125         s = next;
126         /* Indent subsequent lines 3 spaces (the +3 above is also for this) */
127         helpmax = 79 - 5 - optwidth - 2 - 3;
128     } while (*s);
129 }
130 
131 /*************************************************************************/
132 
133 /* The actual option definitions are located in cmdline_def.h using macros;
134  * see that file for details. */
135 
136 enum {
137     DUMMY = 0x100,
138 #define TC_OPTIONS_TO_ENUM
139 #include "cmdline_def.h"
140 #undef TC_OPTIONS_TO_ENUM
141 };
142 
143 static struct option tc_options[] = {
144 #define TC_OPTIONS_TO_STRUCT_OPTION
145 #include "cmdline_def.h"
146 #undef TC_OPTIONS_TO_STRUCT_OPTION
147 };
148 
149 
150 /**
151  * usage:  Print a command-line help message.
152  *
153  * Parameters:
154  *     None.
155  * Return value:
156  *     None.
157  */
158 
usage(void)159 static void usage(void)
160 {
161     int optwidth = 0;
162 
163 #define TC_OPTIONS_TO_OPTWIDTH optwidth
164 #include "cmdline_def.h"
165 #undef TC_OPTIONS_TO_OPTWIDTH
166 
167     version();
168     printf("\n");
169     printf("Usage: transcode [options...]\n");
170     printf("\n");
171     printf("Options:\n");
172 #define TC_OPTIONS_TO_HELP optwidth
173 #include "cmdline_def.h"
174 #undef TC_OPTIONS_TO_HELP
175     printf("\n");
176     printf("use tcmodinfo to discover module properties and configurable options.\n");
177 }
178 
179 
180 /**
181  * parse_cmdline:  Parse all options on the transcode command line, storing
182  * appropriate values in the global "vob" data structure.
183  *
184  * Parameters:
185  *     argc: Command line argument count.
186  *     argv: Command line argument vector.
187  *      vob: Global data structure.
188  * Return value:
189  *     Nonzero on success, zero on error.
190  */
191 
parse_cmdline(int argc,char ** argv,vob_t * vob)192 int parse_cmdline(int argc, char **argv, vob_t *vob)
193 {
194     const char *shortopts;
195     int option;
196 
197 #define TC_OPTIONS_TO_SHORTOPTS shortopts
198 #include "cmdline_def.h"
199 #undef TC_OPTIONS_TO_SHORTOPTS
200 
201     while (-1 != (option = getopt_long_only(argc, argv, shortopts,
202                                             tc_options, NULL))
203     ) {
204         switch (option) {
205 #define TC_OPTIONS_TO_CODE
206 #include "cmdline_def.h"
207 #undef TC_OPTIONS_TO_CODE
208           default:
209           short_usage:  /* error-handling label */
210             fprintf(stderr, "'transcode -h | more' shows a list of available"
211                             " command line options.\n");
212             return 0;
213         }
214     }
215 
216     if (optind == 1)
217         goto short_usage;
218 
219 #ifndef __APPLE__
220     if (optind < argc) {
221         int n;
222         tc_warn("unused command line argument detected (%d/%d)", optind, argc);
223         for (n = optind; n < argc; n++)
224             tc_warn("argc[%d]=%s (unused)", n, argv[n]);
225     }
226 #endif
227 
228     return 1;
229 }
230 
231 /*************************************************************************/
232 
233 /*
234  * Local variables:
235  *   c-file-style: "stroustrup"
236  *   c-file-offsets: ((case-label . *) (statement-case-intro . *))
237  *   indent-tabs-mode: nil
238  * End:
239  *
240  * vim: expandtab shiftwidth=4:
241  */
242