/****************************************** * xml example with apr * Sylvain Marechal * 25/10/2005 *****************************************/ #include "apr_general.h" #include "apr_getopt.h" #include "apr_xml.h" #include "apr_file_io.h" /* args */ static apr_getopt_option_t s_opts[] = { { "help", 'h', 0, "display this help" }, { "file", 'f', 1, "" }, { 0, 0, 0, 0 } }; /********************************************* * usage ********************************************/ static void usage() { int i; printf( "Usage:\n" ); for( i = 0; i < sizeof(s_opts)/sizeof(apr_getopt_option_t) -1; i ++ ) { printf( "\t--%s\t-%c\t%s\n", s_opts[i].name, s_opts[i].optch, s_opts[i].description ); } exit(1); } /********************************************* * get_args ********************************************/ static int get_args( apr_pool_t *pool, int argc, char * argv[], char * pszfile, int cbfile ) { apr_getopt_t *os; apr_status_t ret; apr_getopt_init( &os, pool, argc, (const char * const *)argv ); do { int opt_ch; const char * opt_arg; ret = apr_getopt_long( os, s_opts, &opt_ch, &opt_arg ); if( ret == APR_SUCCESS ) { switch(opt_ch) { case 'h': { usage(); break; } case 'f': { strncpy( pszfile, opt_arg, cbfile ); break; } } } } while( ret == APR_SUCCESS ); if( pszfile[0] == 0 ) { usage(); } return 0; } /****************************************** * print_tag *****************************************/ static void print_tag( int level, const char * buf ) { int i; for( i = 0; i < level; i ++ ) { printf( "\t" ); } printf( "%s\n", buf ); } /****************************************** * dump_xml() (from apr-utils/test/test_xml.c) * and modified to print first_cdata *****************************************/ static void dump_xml(apr_xml_elem *e, int level) { apr_xml_attr *a; apr_xml_elem *ec; char buf[1024]; snprintf( buf, sizeof(buf), "%d: element %s", level, e->name); print_tag( level, buf ); if (e->attr) { a = e->attr; snprintf( buf, sizeof(buf), "%d:\tattrs\t", level); print_tag( level, buf ); while (a) { snprintf( buf, sizeof(buf), "%s=%s\t", a->name, a->value); print_tag( level, buf ); a = a->next; } } if( e->first_cdata.first && e->first_cdata.first->text ) { apr_text *next = e->first_cdata.first; while( next ) { snprintf( buf, sizeof(buf), "first_cdata '%s'", next->text ); print_tag( level, buf ); next = next->next; } } if (e->first_child) { ec = e->first_child; while (ec) { dump_xml(ec, level + 1); ec = ec->next; } } } /****************************************** * test_xml() *****************************************/ void test_xml( apr_pool_t *pool, const char * pszfile ) { apr_status_t ret; apr_file_t * fd; apr_xml_parser * parser; apr_xml_doc * doc; apr_size_t size_read = 2000; /* Open file */ ret = apr_file_open(&fd, pszfile, APR_READ, APR_OS_DEFAULT, pool ); if( ret != APR_SUCCESS ) { printf( "apr_file_open() error %d\n", ret ); exit(1); } /* Parse whole file */ ret = apr_xml_parse_file( pool, &parser, &doc, fd, size_read ); if( ret != APR_SUCCESS ) { char errbuf[1024] = {0}; apr_xml_parser_geterror( parser, errbuf, sizeof(errbuf) ); printf( "apr_xml_parse_file() error %d: '%s'\n", ret, errbuf ); exit(1); } /* dump result */ dump_xml( doc->root, 0 ); /* Close file */ apr_file_close( fd ); } /****************************************** * main() *****************************************/ int main( int argc, char * argv[] ) { apr_pool_t *pool; apr_status_t ret; char szfile[1024] = {0}; /* Init apr */ ret = apr_initialize(); if( ret != APR_SUCCESS) { printf( "apr_initialize() failed (%d)\n", ret ); exit(-1); } /* Create pool */ ret = apr_pool_create(&pool, NULL); if( ret != APR_SUCCESS) { printf( "apr_pool_create() failed %d\n", ret ); exit( -1); } /* Parse args */ get_args( pool, argc, argv, szfile, sizeof(szfile) ); /* xml test */ test_xml( pool, szfile ); /* Destroy pool */ apr_pool_destroy( pool ); return 0; }