Main Page | Modules | Data Structures | File List | Data Fields | Globals | Examples

cmml-validate.c

This is the full source code of the cmml-validate program, which parses a CMML instance document and validates it against the cmml.dtd returning true/false. In case of an error the faulty tag including line and col number is reported. It also spits out warnings for strange stuff.
/* Copyright (C) 2003 CSIRO Australia Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. - Neither the name of the CSIRO nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #include "config.h" #include <stdio.h> #include <stdlib.h> #include <fcntl.h> #include <ctype.h> #include <string.h> #include <errno.h> #ifndef WIN32 #include <unistd.h> #endif #ifdef HAVE_GETOPT_H #include <getopt.h> #endif #include <cmml.h> #define BUFSIZE 100000 /* #define DEBUG */ static int verbose; static void PrintUsage(char *prog) { fprintf(stderr, "Usage: %s [options] filename\n", prog); fprintf(stderr, "Validate a CMML file.\n\n"); fprintf(stderr, "Possible options:\n"); #ifdef HAVE_GETOPT_LONG fprintf(stderr, " -i clip_id, --id clip_id\n"); fprintf(stderr, " Start parsing from the named clip.\n"); fprintf(stderr, " -s seconds, --sec seconds\n"); fprintf(stderr, " Start parsing from the given seconds offset\n"); fprintf(stderr, " -u utc, --utc utc\n"); fprintf(stderr, " Start parsing from the given utc time\n"); fprintf(stderr, " -b, --verbose Output parsed file to stdout\n"); fprintf(stderr, " -h, --help Display this help information\n"); fprintf(stderr, " -v, --version Display version information\n"); #else fprintf(stderr, " -i clip_id Start parsing from the named clip\n"); fprintf(stderr, " -s seconds Start parsing from the given seconds offset\n"); fprintf(stderr, " -u utc Start parsing from the given utc time\n"); fprintf(stderr, " -b Output parsed file to stdout\n"); fprintf(stderr, " -h Display this help information\n"); fprintf(stderr, " -v Display version information\n"); #endif fprintf(stderr, "\nPlease report bugs to <libcmml-devel@cmis.csiro.au>.\n"); exit(1); } static int read_stream (CMML * cmml, const CMML_Stream * stream, void * user_data) { char buf[BUFSIZE]; CMML_Error * err; if ((err = cmml_get_last_error(cmml)) != NULL) { cmml_error_snprint(buf, BUFSIZE, err, cmml); fprintf(stderr, "cmml-validate: Parsing stream tag %s\n", buf); fprintf(stderr, "cmml-validate: Non-recoverable error\n"); return -1; } else { /* print stream */ if (verbose) { cmml_stream_pretty_snprint (buf, BUFSIZE, (CMML_Stream *) stream); fprintf(stdout, "%s\n", buf); } } return 0; } static int read_head (CMML * cmml, const CMML_Head * head, void * user_data) { char buf[BUFSIZE]; CMML_Error * err; if ((err = cmml_get_last_error(cmml)) != NULL) { cmml_error_snprint(buf, BUFSIZE, err, cmml); fprintf(stderr, "cmml-validate: Parsing head tag %s\n", buf); fprintf(stderr, "cmml-validate: Non-recoverable error\n"); return -1; } else { if (verbose) { cmml_head_pretty_snprint (buf, BUFSIZE, (CMML_Head *) head); fprintf(stdout, "%s\n", buf); } } return 0; } static int read_clip (CMML * cmml, const CMML_Clip * clip, void * user_data) { char buf[BUFSIZE]; CMML_Error * err; if ((err = cmml_get_last_error(cmml)) != NULL) { cmml_error_snprint(buf, BUFSIZE, err, cmml); fprintf(stderr, "cmml-validate: Parsing clip %s\n", buf); fprintf(stderr, "cmml-validate: Skipping clip\n\n"); return -1; } else { if (verbose) { cmml_clip_pretty_snprint (buf, BUFSIZE, (CMML_Clip *) clip); fprintf(stdout, "%s\n", buf); } } return 0; } int main(int argc, char *argv[]) { char *pathfile = NULL; int i; char buf[BUFSIZE]; CMML * doc; CMML_Error * err; CMML_Preamble * pre; long n = 0; char * clip_id = NULL; double secs = -1.0; char * utc = NULL; int sloppy = 0; verbose = 0; while (1) { char * optstring = "hvbyi:s:u:"; #ifdef HAVE_GETOPT_LONG static struct option long_options[] = { {"help",no_argument,0,'h'}, {"version",no_argument,0, 'v'}, {"verbose",no_argument,0,'b'}, {"sloppy",no_argument,0,'y'}, {"id",required_argument,0,'i'}, {"sec",required_argument,0,'s'}, {"utc",required_argument,0,'u'}, {0,0,0,0} }; i = getopt_long(argc, argv, optstring, long_options, NULL); #else i = getopt(argc, argv, optstring); #endif if (i == -1) break; if (i == ':') PrintUsage(argv[0]); switch (i) { case 'h': /* help */ PrintUsage(argv[0]); break; case 'v': /* version */ fprintf(stdout, "cmml-validate version " VERSION "\n"); fprintf(stdout, "# cmml-validate, Copyright (C) 2003 CSIRO Australia www.csiro.au ; www.annodex.net\n"); break; case 'i': /* clip_id */ clip_id = optarg; break; case 's': /* seconds */ if (!isalpha(optarg[0])) { secs = atof(optarg); } break; case 'u': /* utc */ utc = optarg; break; case 'y': /* sloppy */ sloppy = 1; break; case 'b': /* verbose */ verbose = 1; break; default: break; } } /* more arguments that were not parsed */ if (optind > argc) { PrintUsage(argv[0]); } /* no filename given? */ if (optind == argc) { pathfile = "-"; } else { pathfile = argv[optind++]; } /* try open file for parsing and setup cmml parsing */ errno=0; if (strcmp (pathfile, "-") == 0) { doc = cmml_new (stdin); } else { doc = cmml_open (pathfile); } if (doc == NULL) { if (errno == 0) { fprintf(stderr, "%s: %s: CMML error opening file\n", argv[0], pathfile); } else { fprintf(stderr, "%s: %s: %s\n", argv[0], pathfile, strerror(errno)); } PrintUsage(argv[0]); } /* turn on sloppy parsing if requested */ if (sloppy) { cmml_set_sloppy(doc, 1); } /* print preamble */ if (verbose) { pre = cmml_get_preamble(doc); cmml_preamble_snprint(buf, BUFSIZE, pre); fprintf(stdout, "%s\n", buf); } /* seek to clip_id; if not found, to file end */ if (clip_id != NULL) { /* register callbacks */ cmml_set_read_callbacks (doc, read_stream, read_head, NULL, NULL); cmml_skip_to_id (doc, clip_id); } /* seek to time offset; if not found, to file end */ if (secs > 0 || utc != NULL) { /* register callbacks */ cmml_set_read_callbacks (doc, read_stream, read_head, NULL, NULL); if (secs > 0) { cmml_skip_to_secs (doc, secs); } else { /* if (utc != NULL) { */ cmml_skip_to_utc (doc, utc); } } /* register callbacks */ cmml_set_read_callbacks (doc, read_stream, read_head, read_clip, NULL); /* read document frame-wise and check against CMML.dtd */ while ((n = cmml_read (doc, BUFSIZE)) > 0) { /* if error reading, print and exit */ if ((err = cmml_get_last_error(doc)) != NULL && err->type != CMML_EOF) { char *filename; filename = (strrchr(pathfile, '/') == NULL ? pathfile : strrchr(pathfile, '/')+1); cmml_error_snprint(buf, BUFSIZE, err, doc); fprintf (stderr, "%s:%s\n", filename, buf); goto cleanup; } } err = cmml_get_last_error(doc); if (n == -1 || (err!=NULL && err->type != CMML_EOF)) { char *filename; filename = (strrchr(pathfile, '/') == NULL ? pathfile : strrchr(pathfile, '/')+1); cmml_error_snprint(buf, BUFSIZE, err, doc); fprintf (stderr, "%s:%s\n", filename, buf); goto cleanup; } /* write end tag */ if (verbose) { fprintf(stdout, "</cmml>\n"); } cleanup: /* clean up */ cmml_close(doc); return 0; }
00001 /* Copyright (C) 2003 CSIRO Australia 00002 00003 Redistribution and use in source and binary forms, with or without 00004 modification, are permitted provided that the following conditions 00005 are met: 00006 00007 - Redistributions of source code must retain the above copyright 00008 notice, this list of conditions and the following disclaimer. 00009 00010 - Redistributions in binary form must reproduce the above copyright 00011 notice, this list of conditions and the following disclaimer in the 00012 documentation and/or other materials provided with the distribution. 00013 00014 - Neither the name of the CSIRO nor the names of its 00015 contributors may be used to endorse or promote products derived from 00016 this software without specific prior written permission. 00017 00018 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 00019 ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 00020 LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A 00021 PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR 00022 CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 00023 EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 00024 PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 00025 PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 00026 LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 00027 NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 00028 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00029 */ 00030 00031 #include "config.h" 00032 00033 #include <stdio.h> 00034 #include <stdlib.h> 00035 #include <fcntl.h> 00036 #include <ctype.h> 00037 #include <string.h> 00038 #include <errno.h> 00039 00040 #ifndef WIN32 00041 #include <unistd.h> 00042 #endif 00043 00044 #ifdef HAVE_GETOPT_H 00045 #include <getopt.h> 00046 #endif 00047 00048 #include <cmml.h> 00049 00079 #define BUFSIZE 100000 00080 00081 /* 00082 #define DEBUG 00083 */ 00084 00088 static int verbose; 00089 00095 static void 00096 PrintUsage(char *prog) { 00097 fprintf(stderr, "Usage: %s [options] filename\n", prog); 00098 fprintf(stderr, "Validate a CMML file.\n\n"); 00099 fprintf(stderr, "Possible options:\n"); 00100 #ifdef HAVE_GETOPT_LONG 00101 fprintf(stderr, " -i clip_id, --id clip_id\n"); 00102 fprintf(stderr, " Start parsing from the named clip.\n"); 00103 fprintf(stderr, " -s seconds, --sec seconds\n"); 00104 fprintf(stderr, " Start parsing from the given seconds offset\n"); 00105 fprintf(stderr, " -u utc, --utc utc\n"); 00106 fprintf(stderr, " Start parsing from the given utc time\n"); 00107 fprintf(stderr, " -b, --verbose Output parsed file to stdout\n"); 00108 fprintf(stderr, " -h, --help Display this help information\n"); 00109 fprintf(stderr, " -v, --version Display version information\n"); 00110 #else 00111 fprintf(stderr, " -i clip_id Start parsing from the named clip\n"); 00112 fprintf(stderr, " -s seconds Start parsing from the given seconds offset\n"); 00113 fprintf(stderr, " -u utc Start parsing from the given utc time\n"); 00114 fprintf(stderr, " -b Output parsed file to stdout\n"); 00115 fprintf(stderr, " -h Display this help information\n"); 00116 fprintf(stderr, " -v Display version information\n"); 00117 #endif 00118 fprintf(stderr, "\nPlease report bugs to <libcmml-devel@cmis.csiro.au>.\n"); 00119 exit(1); 00120 } 00121 00132 static int 00133 read_stream (CMML * cmml, const CMML_Stream * stream, void * user_data) { 00134 char buf[BUFSIZE]; 00135 CMML_Error * err; 00136 if ((err = cmml_get_last_error(cmml)) != NULL) { 00137 cmml_error_snprint(buf, BUFSIZE, err, cmml); 00138 fprintf(stderr, "cmml-validate: Parsing stream tag %s\n", buf); 00139 fprintf(stderr, "cmml-validate: Non-recoverable error\n"); 00140 return -1; 00141 } else { 00142 /* print stream */ 00143 if (verbose) { 00144 cmml_stream_pretty_snprint (buf, BUFSIZE, (CMML_Stream *) stream); 00145 fprintf(stdout, "%s\n", buf); 00146 } 00147 } return 0; 00148 } 00149 00160 static int 00161 read_head (CMML * cmml, const CMML_Head * head, void * user_data) { 00162 char buf[BUFSIZE]; 00163 CMML_Error * err; 00164 if ((err = cmml_get_last_error(cmml)) != NULL) { 00165 cmml_error_snprint(buf, BUFSIZE, err, cmml); 00166 fprintf(stderr, "cmml-validate: Parsing head tag %s\n", buf); 00167 fprintf(stderr, "cmml-validate: Non-recoverable error\n"); 00168 return -1; 00169 } else { 00170 if (verbose) { 00171 cmml_head_pretty_snprint (buf, BUFSIZE, (CMML_Head *) head); 00172 fprintf(stdout, "%s\n", buf); 00173 } 00174 } 00175 return 0; 00176 } 00177 00188 static int 00189 read_clip (CMML * cmml, const CMML_Clip * clip, void * user_data) { 00190 char buf[BUFSIZE]; 00191 CMML_Error * err; 00192 if ((err = cmml_get_last_error(cmml)) != NULL) { 00193 cmml_error_snprint(buf, BUFSIZE, err, cmml); 00194 fprintf(stderr, "cmml-validate: Parsing clip %s\n", buf); 00195 fprintf(stderr, "cmml-validate: Skipping clip\n\n"); 00196 return -1; 00197 } else { 00198 if (verbose) { 00199 cmml_clip_pretty_snprint (buf, BUFSIZE, (CMML_Clip *) clip); 00200 fprintf(stdout, "%s\n", buf); 00201 } 00202 } 00203 return 0; 00204 } 00205 00212 int main(int argc, char *argv[]) 00213 { 00214 char *pathfile = NULL; 00215 int i; 00216 char buf[BUFSIZE]; 00217 CMML * doc; 00218 CMML_Error * err; 00219 CMML_Preamble * pre; 00220 long n = 0; 00221 char * clip_id = NULL; 00222 double secs = -1.0; 00223 char * utc = NULL; 00224 int sloppy = 0; 00225 verbose = 0; 00226 00227 while (1) { 00228 char * optstring = "hvbyi:s:u:"; 00229 00230 #ifdef HAVE_GETOPT_LONG 00231 static struct option long_options[] = { 00232 {"help",no_argument,0,'h'}, 00233 {"version",no_argument,0, 'v'}, 00234 {"verbose",no_argument,0,'b'}, 00235 {"sloppy",no_argument,0,'y'}, 00236 {"id",required_argument,0,'i'}, 00237 {"sec",required_argument,0,'s'}, 00238 {"utc",required_argument,0,'u'}, 00239 {0,0,0,0} 00240 }; 00241 00242 i = getopt_long(argc, argv, optstring, long_options, NULL); 00243 #else 00244 i = getopt(argc, argv, optstring); 00245 #endif 00246 00247 if (i == -1) break; 00248 if (i == ':') PrintUsage(argv[0]); 00249 00250 switch (i) { 00251 case 'h': /* help */ 00252 PrintUsage(argv[0]); 00253 break; 00254 case 'v': /* version */ 00255 fprintf(stdout, "cmml-validate version " VERSION "\n"); 00256 fprintf(stdout, "# cmml-validate, Copyright (C) 2003 CSIRO Australia www.csiro.au ; www.annodex.net\n"); 00257 break; 00258 case 'i': /* clip_id */ 00259 clip_id = optarg; 00260 break; 00261 case 's': /* seconds */ 00262 if (!isalpha(optarg[0])) { 00263 secs = atof(optarg); 00264 } 00265 break; 00266 case 'u': /* utc */ 00267 utc = optarg; 00268 break; 00269 case 'y': /* sloppy */ 00270 sloppy = 1; 00271 break; 00272 case 'b': /* verbose */ 00273 verbose = 1; 00274 break; 00275 default: 00276 break; 00277 } 00278 } 00279 00280 /* more arguments that were not parsed */ 00281 if (optind > argc) { 00282 PrintUsage(argv[0]); 00283 } 00284 00285 /* no filename given? */ 00286 if (optind == argc) { 00287 pathfile = "-"; 00288 } else { 00289 pathfile = argv[optind++]; 00290 } 00291 00292 /* try open file for parsing and setup cmml parsing */ 00293 errno=0; 00294 if (strcmp (pathfile, "-") == 0) { 00295 doc = cmml_new (stdin); 00296 } else { 00297 doc = cmml_open (pathfile); 00298 } 00299 00300 if (doc == NULL) { 00301 if (errno == 0) { 00302 fprintf(stderr, "%s: %s: CMML error opening file\n", argv[0], pathfile); 00303 } else { 00304 fprintf(stderr, "%s: %s: %s\n", argv[0], pathfile, strerror(errno)); 00305 } 00306 PrintUsage(argv[0]); 00307 } 00308 00309 /* turn on sloppy parsing if requested */ 00310 if (sloppy) { 00311 cmml_set_sloppy(doc, 1); 00312 } 00313 00314 /* print preamble */ 00315 if (verbose) { 00316 pre = cmml_get_preamble(doc); 00317 cmml_preamble_snprint(buf, BUFSIZE, pre); 00318 fprintf(stdout, "%s\n", buf); 00319 } 00320 00321 /* seek to clip_id; if not found, to file end */ 00322 if (clip_id != NULL) { 00323 /* register callbacks */ 00324 cmml_set_read_callbacks (doc, read_stream, read_head, NULL, NULL); 00325 cmml_skip_to_id (doc, clip_id); 00326 } 00327 00328 /* seek to time offset; if not found, to file end */ 00329 if (secs > 0 || utc != NULL) { 00330 /* register callbacks */ 00331 cmml_set_read_callbacks (doc, read_stream, read_head, NULL, NULL); 00332 if (secs > 0) { 00333 cmml_skip_to_secs (doc, secs); 00334 } else { /* if (utc != NULL) { */ 00335 cmml_skip_to_utc (doc, utc); 00336 } 00337 } 00338 00339 /* register callbacks */ 00340 cmml_set_read_callbacks (doc, read_stream, read_head, read_clip, NULL); 00341 00342 /* read document frame-wise and check against CMML.dtd */ 00343 while ((n = cmml_read (doc, BUFSIZE)) > 0) { 00344 /* if error reading, print and exit */ 00345 if ((err = cmml_get_last_error(doc)) != NULL && err->type != CMML_EOF) { 00346 char *filename; 00347 filename = (strrchr(pathfile, '/') == NULL ? pathfile 00348 : strrchr(pathfile, '/')+1); 00349 cmml_error_snprint(buf, BUFSIZE, err, doc); 00350 fprintf (stderr, "%s:%s\n", filename, buf); 00351 goto cleanup; 00352 } 00353 } 00354 00355 err = cmml_get_last_error(doc); 00356 if (n == -1 || (err!=NULL && err->type != CMML_EOF)) { 00357 char *filename; 00358 filename = (strrchr(pathfile, '/') == NULL ? pathfile 00359 : strrchr(pathfile, '/')+1); 00360 cmml_error_snprint(buf, BUFSIZE, err, doc); 00361 fprintf (stderr, "%s:%s\n", filename, buf); 00362 goto cleanup; 00363 } 00364 00365 /* write end tag */ 00366 if (verbose) { 00367 fprintf(stdout, "</cmml>\n"); 00368 } 00369 00370 cleanup: 00371 /* clean up */ 00372 cmml_close(doc); 00373 00374 return 0; 00375 }

Generated on Wed Jul 28 08:04:05 2004 for libcmml by doxygen 1.3.7