Annotation of embedaddon/libxml2/doc/examples/index.py, revision 1.1.1.2

1.1       misho       1: #!/usr/bin/python -u
                      2: #
                      3: # Indexes the examples and build an XML description
                      4: #
                      5: import string
                      6: import glob
                      7: import sys
                      8: try:
                      9:     import libxml2
                     10: except:
                     11:     sys.exit(1)
                     12: sys.path.insert(0, "..")
                     13: from apibuild import CParser, escape
                     14: 
                     15: examples = []
1.1.1.2 ! misho      16: extras = ['examples.xsl', 'index.html', 'index.py']
1.1       misho      17: tests = []
                     18: sections = {}
                     19: symbols = {}
                     20: api_dict = None
                     21: api_doc = None
                     22: 
                     23: def load_api():
                     24:     global api_dict
                     25:     global api_doc
                     26: 
                     27:     if api_dict != None:
                     28:         return
                     29:     api_dict = {}
                     30:     try:
                     31:         print "loading ../libxml2-api.xml"
                     32:         api_doc = libxml2.parseFile("../libxml2-api.xml")
                     33:     except:
                     34:         print "failed to parse ../libxml2-api.xml"
                     35:        sys.exit(1)
                     36: 
                     37: def find_symbol(name):
                     38:     global api_dict
                     39:     global api_doc
                     40: 
                     41:     if api_doc == None:
                     42:         load_api()
                     43: 
                     44:     if name == None:
                     45:         return
                     46:     if api_dict.has_key(name):
                     47:         return api_dict[name]
                     48:     ctxt = api_doc.xpathNewContext()
                     49:     res = ctxt.xpathEval("/api/symbols/*[@name = '%s']" % (name))
                     50:     if type(res) == type([]) and len(res) >= 1:
                     51:         if len(res) > 1:
                     52:            print "Found %d references to %s in the API" % (len(res), name)
                     53:        node = res[0]
                     54:        typ = node.name
                     55:        file = node.xpathEval("string(@file)")
                     56:        info = node.xpathEval("string(info)")
                     57:     else:
                     58:         print "Reference %s not found in the API" % (name)
                     59:        return None
                     60:     ret = (typ, file, info)
                     61:     api_dict[name] = ret
                     62:     return ret
                     63: 
                     64: def parse_top_comment(filename, comment):
                     65:     res = {}
                     66:     lines = string.split(comment, "\n")
                     67:     item = None
                     68:     for line in lines:
                     69:         while line != "" and (line[0] == ' ' or line[0] == '\t'):
                     70:            line = line[1:]
                     71:         while line != "" and line[0] == '*':
                     72:            line = line[1:]
                     73:         while line != "" and (line[0] == ' ' or line[0] == '\t'):
                     74:            line = line[1:]
                     75:        try:
                     76:            (it, line) = string.split(line, ":", 1)
                     77:            item = it
                     78:            while line != "" and (line[0] == ' ' or line[0] == '\t'):
                     79:                line = line[1:]
                     80:            if res.has_key(item):
                     81:                res[item] = res[item] + " " + line
                     82:            else:
                     83:                res[item] = line
                     84:        except:
                     85:            if item != None:
                     86:                if res.has_key(item):
                     87:                    res[item] = res[item] + " " + line
                     88:                else:
                     89:                    res[item] = line
                     90:     return res
                     91: 
                     92: def parse(filename, output):
                     93:     global symbols
                     94:     global sections
                     95: 
                     96:     parser = CParser(filename)
                     97:     parser.collect_references()
                     98:     idx = parser.parse()
                     99:     info = parse_top_comment(filename, parser.top_comment)
                    100:     output.write("  <example filename='%s'>\n" % filename)
                    101:     try:
                    102:         synopsis = info['synopsis']
                    103:        output.write("    <synopsis>%s</synopsis>\n" % escape(synopsis));
                    104:     except:
                    105:         print "Example %s lacks a synopsis description" % (filename)
                    106:     try:
                    107:         purpose = info['purpose']
                    108:        output.write("    <purpose>%s</purpose>\n" % escape(purpose));
                    109:     except:
                    110:         print "Example %s lacks a purpose description" % (filename)
                    111:     try:
                    112:         usage = info['usage']
                    113:        output.write("    <usage>%s</usage>\n" % escape(usage));
                    114:     except:
                    115:         print "Example %s lacks an usage description" % (filename)
                    116:     try:
                    117:         test = info['test']
                    118:        output.write("    <test>%s</test>\n" % escape(test));
                    119:        progname=filename[0:-2]
                    120:        command=string.replace(test, progname, './' + progname, 1)
                    121:        tests.append(command)
                    122:     except:
                    123:         pass
                    124:     try:
                    125:         author = info['author']
                    126:        output.write("    <author>%s</author>\n" % escape(author));
                    127:     except:
                    128:         print "Example %s lacks an author description" % (filename)
                    129:     try:
                    130:         copy = info['copy']
                    131:        output.write("    <copy>%s</copy>\n" % escape(copy));
                    132:     except:
                    133:         print "Example %s lacks a copyright description" % (filename)
                    134:     try:
                    135:         section = info['section']
                    136:        output.write("    <section>%s</section>\n" % escape(section));
                    137:        if sections.has_key(section):
                    138:            sections[section].append(filename)
                    139:        else:
                    140:            sections[section] = [filename]
                    141:     except:
                    142:         print "Example %s lacks a section description" % (filename)
                    143:     for topic in info.keys():
                    144:         if topic != "purpose" and topic != "usage" and \
                    145:           topic != "author" and topic != "copy" and \
                    146:           topic != "section" and topic != "synopsis" and topic != "test":
                    147:            str = info[topic]
                    148:            output.write("    <extra topic='%s'>%s</extra>\n" % (
                    149:                         escape(topic), escape(str)))
                    150:     output.write("    <includes>\n")
                    151:     for include in idx.includes.keys():
                    152:         if include.find("libxml") != -1:
                    153:            output.write("      <include>%s</include>\n" % (escape(include)))
                    154:     output.write("    </includes>\n")
                    155:     output.write("    <uses>\n")
                    156:     for ref in idx.references.keys():
                    157:         id = idx.references[ref]
                    158:        name = id.get_name()
                    159:        line = id.get_lineno()
                    160:        if symbols.has_key(name):
                    161:            sinfo = symbols[name]
                    162:            refs = sinfo[0]
                    163:            # gather at most 5 references per symbols
                    164:            if refs > 5:
                    165:                continue
                    166:            sinfo.append(filename)
                    167:            sinfo[0] = refs + 1
                    168:        else:
                    169:            symbols[name] = [1, filename]
                    170:        info = find_symbol(name)
                    171:        if info != None:
                    172:            type = info[0]
                    173:            file = info[1]
                    174:            output.write("      <%s line='%d' file='%s' name='%s'/>\n" % (type,
                    175:                         line, file, name))
                    176:        else:
                    177:            type = id.get_type()
                    178:            output.write("      <%s line='%d' name='%s'/>\n" % (type,
                    179:                         line, name))
1.1.1.2 ! misho     180: 
1.1       misho     181:     output.write("    </uses>\n")
                    182:     output.write("  </example>\n")
1.1.1.2 ! misho     183: 
1.1       misho     184:     return idx
                    185: 
                    186: def dump_symbols(output):
                    187:     global symbols
                    188: 
                    189:     output.write("  <symbols>\n")
                    190:     keys = symbols.keys()
                    191:     keys.sort()
                    192:     for symbol in keys:
                    193:         output.write("    <symbol name='%s'>\n" % (symbol))
                    194:        info = symbols[symbol]
                    195:        i = 1
                    196:        while i < len(info):
                    197:            output.write("      <ref filename='%s'/>\n" % (info[i]))
                    198:            i = i + 1
                    199:         output.write("    </symbol>\n")
                    200:     output.write("  </symbols>\n")
                    201: 
                    202: def dump_sections(output):
                    203:     global sections
                    204: 
                    205:     output.write("  <sections>\n")
                    206:     keys = sections.keys()
                    207:     keys.sort()
                    208:     for section in keys:
                    209:         output.write("    <section name='%s'>\n" % (section))
                    210:        info = sections[section]
                    211:        i = 0
                    212:        while i < len(info):
                    213:            output.write("      <example filename='%s'/>\n" % (info[i]))
                    214:            i = i + 1
                    215:         output.write("    </section>\n")
                    216:     output.write("  </sections>\n")
                    217: 
                    218: def dump_Makefile():
                    219:     for file in glob.glob('*.xml'):
                    220:         extras.append(file)
                    221:     for file in glob.glob('*.res'):
                    222:         extras.append(file)
1.1.1.2 ! misho     223:     Makefile="""##
        !           224: ## This file is auto-generated by index.py
        !           225: ## DO NOT EDIT !!!
        !           226: ##
        !           227: 
        !           228: AM_CPPFLAGS = -I$(top_builddir)/include -I$(top_srcdir)/include -I$(srcdir)/include
        !           229: AM_CFLAGS = $(THREAD_CFLAGS) $(Z_CFLAGS)
        !           230: LDADD = $(RDL_LIBS) $(STATIC_BINARIES) $(top_builddir)/libxml2.la $(THREAD_LIBS) $(Z_LIBS) $(ICONV_LIBS) -lm $(WIN32_EXTRA_LIBADD)
        !           231: 
        !           232: CLEANFILES = *.tmp
1.1       misho     233: 
1.1.1.2 ! misho     234: if REBUILD_DOCS
1.1       misho     235: rebuild: examples.xml index.html
1.1.1.2 ! misho     236: .PHONY: rebuild
1.1       misho     237: 
1.1.1.2 ! misho     238: examples.xml: index.py $(noinst_PROGRAMS:=.c)
        !           239:        cd $(srcdir) && $(PYTHON) index.py
        !           240:        $(MAKE) Makefile
1.1       misho     241: 
                    242: index.html: examples.xml examples.xsl
1.1.1.2 ! misho     243:        cd $(srcdir) && xsltproc examples.xsl examples.xml && echo "Rebuilt web page"
        !           244:        -cd $(srcdir) && xmllint --valid --noout index.html
        !           245: endif
1.1       misho     246: 
                    247: install-data-local: 
1.1.1.2 ! misho     248:        $(MKDIR_P) $(DESTDIR)$(HTML_DIR)
        !           249:        -$(INSTALL) -m 0644 $(srcdir)/*.html $(srcdir)/*.c $(srcdir)/*.xml $(srcdir)/*.xsl $(srcdir)/*.res $(DESTDIR)$(HTML_DIR)
        !           250: 
        !           251: clean-local:
        !           252:        test -f Makefile.am || rm -f test?.xml
1.1       misho     253: 
                    254: """
1.1.1.2 ! misho     255:     examples.sort()
        !           256:     extras.sort()
        !           257:     tests.sort()
1.1       misho     258:     EXTRA_DIST=""
                    259:     for extra in extras:
1.1.1.2 ! misho     260:         EXTRA_DIST = EXTRA_DIST + " \\\n\t" + extra
        !           261:     Makefile = Makefile + "EXTRA_DIST =%s\n\n" % (EXTRA_DIST)
1.1       misho     262:     noinst_PROGRAMS=""
                    263:     for example in examples:
1.1.1.2 ! misho     264:         noinst_PROGRAMS = noinst_PROGRAMS + " \\\n\t" + example
        !           265:     Makefile = Makefile + "noinst_PROGRAMS =%s\n\n" % (noinst_PROGRAMS)
1.1       misho     266:     for example in examples:
1.1.1.2 ! misho     267:         Makefile = Makefile + "%s_SOURCES = %s.c\n\n" % (example, example)
1.1       misho     268:     Makefile = Makefile + "valgrind: \n\t$(MAKE) CHECKER='valgrind' tests\n\n"
                    269:     Makefile = Makefile + "tests: $(noinst_PROGRAMS)\n"
1.1.1.2 ! misho     270:     Makefile = Makefile + "\ttest -f Makefile.am || test -f test1.xml || $(LN_S) $(srcdir)/test?.xml .\n"
1.1       misho     271:     Makefile = Makefile + "\t@(echo '## examples regression tests')\n"
                    272:     Makefile = Makefile + "\t@(echo > .memdump)\n"
                    273:     for test in tests:
1.1.1.2 ! misho     274:         Makefile = Makefile + "\t$(CHECKER) %s\n" % (test)
        !           275:         Makefile = Makefile + '\t@grep "MORY ALLO" .memdump | grep -v "MEMORY ALLOCATED : 0" ; exit 0\n'
1.1       misho     276:     try:
                    277:        old = open("Makefile.am", "r").read()
                    278:        if old != Makefile:
                    279:            n = open("Makefile.am", "w").write(Makefile)
                    280:            print "Updated Makefile.am"
                    281:     except:
                    282:         print "Failed to read or save Makefile.am"
1.1.1.2 ! misho     283: #    #
        !           284: #    # Autogenerate the .cvsignore too ... DEPRECATED
        !           285: #    #
        !           286: #    ignore = """.memdump
        !           287: #Makefile.in
        !           288: #Makefile
        !           289: #"""
        !           290: #    for example in examples:
        !           291: #        ignore = ignore + "%s\n" % (example)
        !           292: #    try:
        !           293: #      old = open(".cvsignore", "r").read()
        !           294: #      if old != ignore:
        !           295: #          n = open(".cvsignore", "w").write(ignore)
        !           296: #          print "Updated .cvsignore"
        !           297: #    except:
        !           298: #        print "Failed to read or save .cvsignore"
        !           299: 
1.1       misho     300: if __name__ == "__main__":
                    301:     load_api()
                    302:     output = open("examples.xml", "w")
                    303:     output.write("<examples>\n")
                    304: 
                    305:     for file in glob.glob('*.c'):
                    306:        parse(file, output)
                    307:        examples.append(file[:-2])
                    308: 
                    309:     dump_symbols(output)
                    310:     dump_sections(output)
                    311:     output.write("</examples>\n")
                    312:     output.close()
                    313:     dump_Makefile()
                    314: 

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>