/[tivodecode]/tivodecode/trunk/tivodecode.c
ViewVC logotype

Contents of /tivodecode/trunk/tivodecode.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 66 - (show annotations) (download)
Wed Dec 13 00:43:25 2006 UTC (15 years, 5 months ago) by jeremyd2019
File MIME type: text/plain
File size: 6802 byte(s)
make process_frame use a write function.  add target to make libtivodecode.a

1 /*
2 * tivodecode, (c) 2006, Jeremy Drake
3 * See COPYING file for license terms
4 *
5 * derived from mpegcat, copyright 2006 Kees Cook, used with permission
6 */
7 #include <stdio.h>
8 #include <stddef.h>
9 #include <stdlib.h>
10 #include <string.h>
11 #include <ctype.h>
12 #include "getopt_long.h"
13 #include "happyfile.h"
14 #include "tivo-parse.h"
15 #include "turing_stream.h"
16 #include "tivodecoder.h"
17
18 #ifdef WIN32
19 # define HOME_ENV_NAME "USERPROFILE"
20 # define DEFAULT_EMPTY_HOME "C:"
21 #else
22 # define HOME_ENV_NAME "HOME"
23 # define DEFAULT_EMPTY_HOME ""
24 #endif
25
26 static const char MAK_DOTFILE_NAME[] = "/.tivodecode_mak";
27
28 static const char * VERSION_STR = "CVS Head";
29
30 int o_verbose = 0;
31 int o_no_verify = 0;
32
33 happy_file * hfh=NULL;
34 // file position options
35 off_t begin_at = 0;
36
37
38 static int hread_wrapper (void * mem, int size, void * fh)
39 {
40 return (int)hread (mem, size, (happy_file *)fh);
41 }
42
43 static int fwrite_wrapper (void * mem, int size, void * fh)
44 {
45 return (int)fwrite (mem, 1, size, (FILE *)fh);
46 }
47
48 static struct option long_options[] = {
49 {"mak", 1, 0, 'm'},
50 {"out", 1, 0, 'o'},
51 {"help", 0, 0, 'h'},
52 {"verbose", 0, 0, 'v'},
53 {"version", 0, 0, 'V'},
54 {"no-verify", 0, 0, 'n'},
55 {0, 0, 0, 0}
56 };
57
58 static void do_help(char * arg0, int exitval)
59 {
60 fprintf(stderr, "Usage: %s [--help] [--verbose|-v] [--no-verify|-n] {--mak|-m} mak [{--out|-o} outfile] <tivofile>\n\n", arg0);
61 #define ERROUT(s) fprintf(stderr, s)
62 ERROUT (" --mak, -m media access key (required)\n");
63 ERROUT (" --out, -o output file (default stdout)\n");
64 ERROUT (" --verbose, -v verbose\n");
65 ERROUT (" --no-verify, -n do not verify MAK while decoding\n");
66 ERROUT (" --version, -V print the version information and exit\n\n");
67 ERROUT (" --help, -h print this help and exit\n\n");
68 ERROUT ("The file names specified for the output file or the tivo file may be -, which\n");
69 ERROUT ("means stdout or stdin respectively\n\n");
70 #undef ERROUT
71
72 exit (exitval);
73 }
74
75 static void do_version(int exitval)
76 {
77 fprintf (stderr, "tivodecode version %s\n", VERSION_STR);
78 fprintf (stderr, "Copyright (c) 2006, Jeremy Drake\n");
79 fprintf (stderr, "See COPYING file in distribution for details\n");
80
81 exit (exitval);
82 }
83
84
85 int main(int argc, char *argv[])
86 {
87 unsigned int marker;
88 unsigned char byte;
89 char first = 1;
90
91 int running = 1;
92
93 char * tivofile = NULL;
94 char * outfile = NULL;
95 char mak[12];
96
97 int makgiven = 0;
98
99 turing_state turing;
100
101 FILE * ofh;
102
103 memset(&turing, 0, sizeof(turing));
104 memset(mak, 0, sizeof(mak));
105
106 fprintf(stderr, "Encryption by QUALCOMM ;)\n\n");
107
108 while (1)
109 {
110 int c = getopt_long (argc, argv, "m:o:hnvV", long_options, 0);
111
112 if (c == -1)
113 break;
114
115 switch (c)
116 {
117 case 'm':
118 strncpy(mak, optarg, 11);
119 mak[11] = '\0';
120 makgiven = 1;
121 break;
122 case 'o':
123 outfile = optarg;
124 break;
125 case 'h':
126 do_help(argv[0], 1);
127 break;
128 case 'v':
129 o_verbose = 1;
130 break;
131 case 'n':
132 o_no_verify = 1;
133 break;
134 case '?':
135 do_help(argv[0], 2);
136 break;
137 case 'V':
138 do_version(10);
139 break;
140 default:
141 do_help(argv[0], 3);
142 break;
143 }
144 }
145
146 if (optind < argc)
147 {
148 tivofile=argv[optind++];
149 if (optind < argc)
150 do_help(argv[0], 4);
151 }
152
153 if (!makgiven)
154 {
155 char * mak_fname;
156 FILE * mak_file;
157 const char * home_dir = getenv(HOME_ENV_NAME);
158 size_t home_dir_len;
159
160 if (!home_dir)
161 home_dir = DEFAULT_EMPTY_HOME;
162
163 home_dir_len = strlen(home_dir);
164
165 mak_fname = malloc (home_dir_len + sizeof(MAK_DOTFILE_NAME));
166 if (!mak_fname)
167 {
168 fprintf(stderr, "error allocing string for mak config file name\n");
169 exit(11);
170 }
171
172 memcpy (mak_fname, home_dir, home_dir_len);
173 memcpy (mak_fname + home_dir_len, MAK_DOTFILE_NAME, sizeof(MAK_DOTFILE_NAME));
174
175 if ((mak_file = fopen(mak_fname, "r")))
176 {
177 if (fread(mak, 1, 11, mak_file) >= 10)
178 {
179 int i;
180 for (i = 11; i >= 10 && (mak[i] == '\0' || isspace(mak[i])); --i)
181 {
182 mak[i] = '\0';
183 }
184
185 makgiven = 1;
186 }
187 else if (ferror(mak_file))
188 {
189 perror ("reading mak config file");
190 exit(12);
191 }
192 else
193 {
194 fprintf(stderr, "mak too short in mak config file\n");
195 exit(13);
196 }
197
198 fclose (mak_file);
199 }
200
201 free(mak_fname);
202 }
203
204 if (!makgiven || !tivofile)
205 {
206 do_help(argv[0], 5);
207 }
208
209 if (!strcmp(tivofile, "-"))
210 {
211 hfh=hattach(stdin);
212 }
213 else
214 {
215 if (!(hfh=hopen(tivofile, "rb")))
216 {
217 perror(tivofile);
218 return 6;
219 }
220 }
221
222 if (!outfile || !strcmp(outfile, "-"))
223 {
224 ofh = stdout;
225 }
226 else
227 {
228 if (!(ofh = fopen(outfile, "wb")))
229 {
230 perror("opening output file");
231 return 7;
232 }
233 }
234
235 if ((begin_at = setup_turing_key (&turing, hfh, &hread_wrapper, mak)) < 0)
236 {
237 return 8;
238 }
239
240 if (hseek(hfh, begin_at, SEEK_SET) < 0)
241 {
242 perror ("seek");
243 return 9;
244 }
245
246 marker = 0xFFFFFFFF;
247 while (running)
248 {
249 if ((marker & 0xFFFFFF00) == 0x100)
250 {
251 int ret = process_frame(byte, &turing, htell(hfh), hfh, &hread_wrapper, ofh, &fwrite_wrapper);
252 if (ret == 1)
253 {
254 marker = 0xFFFFFFFF;
255 }
256 else if (ret == 0)
257 {
258 fwrite(&byte, 1, 1, ofh);
259 }
260 else if (ret < 0)
261 {
262 perror ("processing frame");
263 return 10;
264 }
265 }
266 else if (!first)
267 {
268 fwrite(&byte, 1, 1, ofh);
269 }
270 marker <<= 8;
271 if (hread(&byte, 1, hfh) == 0)
272 {
273 fprintf(stderr, "End of File\n");
274 running = 0;
275 }
276 else
277 marker |= byte;
278 first = 0;
279 }
280
281 destruct_turing (&turing);
282
283 if (hfh->fh == stdin)
284 hdetach(hfh);
285 else
286 hclose(hfh);
287
288 if (ofh != stdout)
289 fclose(ofh);
290
291 return 0;
292 }
293
294 /* vi:set ai ts=4 sw=4 expandtab: */

cvs@jdrake.com
ViewVC Help
Powered by ViewVC 1.1.13