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.
#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
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 {
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':
PrintUsage(argv[0]);
break;
case 'v':
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 = optarg;
break;
case 's':
if (!isalpha(optarg[0])) {
secs = atof(optarg);
}
break;
case 'u':
utc = optarg;
break;
case 'y':
sloppy = 1;
break;
case 'b':
verbose = 1;
break;
default:
break;
}
}
if (optind > argc) {
PrintUsage(argv[0]);
}
if (optind == argc) {
pathfile =
"-";
}
else {
pathfile = argv[optind++];
}
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]);
}
if (sloppy) {
cmml_set_sloppy(doc, 1);
}
if (verbose) {
pre =
cmml_get_preamble(doc);
cmml_preamble_snprint(buf, BUFSIZE, pre);
fprintf(stdout,
"%s\n", buf);
}
if (clip_id != NULL) {
cmml_set_read_callbacks (doc, read_stream, read_head, NULL, NULL);
cmml_skip_to_id (doc, clip_id);
}
if (secs > 0 || utc != NULL) {
cmml_set_read_callbacks (doc, read_stream, read_head, NULL, NULL);
if (secs > 0) {
cmml_skip_to_secs (doc, secs);
}
else {
cmml_skip_to_utc (doc, utc);
}
}
cmml_set_read_callbacks (doc, read_stream, read_head, read_clip, NULL);
while ((n =
cmml_read (doc, BUFSIZE)) > 0) {
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;
}
if (verbose) {
fprintf(stdout,
"</cmml>\n");
}
cleanup:
cmml_close(doc);
return 0;
}
00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
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
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
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':
00252
PrintUsage(argv[0]);
00253
break;
00254
case 'v':
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':
00259 clip_id = optarg;
00260
break;
00261
case 's':
00262
if (!isalpha(optarg[0])) {
00263 secs = atof(optarg);
00264 }
00265
break;
00266
case 'u':
00267 utc = optarg;
00268
break;
00269
case 'y':
00270 sloppy = 1;
00271
break;
00272
case 'b':
00273 verbose = 1;
00274
break;
00275
default:
00276
break;
00277 }
00278 }
00279
00280
00281
if (optind > argc) {
00282
PrintUsage(argv[0]);
00283 }
00284
00285
00286
if (optind == argc) {
00287 pathfile =
"-";
00288 }
else {
00289 pathfile = argv[optind++];
00290 }
00291
00292
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
00310
if (sloppy) {
00311
cmml_set_sloppy(doc, 1);
00312 }
00313
00314
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
00322
if (clip_id != NULL) {
00323
00324
cmml_set_read_callbacks (doc, read_stream, read_head, NULL, NULL);
00325
cmml_skip_to_id (doc, clip_id);
00326 }
00327
00328
00329
if (secs > 0 || utc != NULL) {
00330
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 {
00335
cmml_skip_to_utc (doc, utc);
00336 }
00337 }
00338
00339
00340
cmml_set_read_callbacks (doc, read_stream, read_head, read_clip, NULL);
00341
00342
00343
while ((n =
cmml_read (doc, BUFSIZE)) > 0) {
00344
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
00366
if (verbose) {
00367 fprintf(stdout,
"</cmml>\n");
00368 }
00369
00370 cleanup:
00371
00372
cmml_close(doc);
00373
00374
return 0;
00375 }
Generated on Thu Aug 19 03:32:59 2004 for libcmml by
1.3.7