--- /dev/null
+#!/usr/bin/env python
+import sys
+import re
+import docutils.core
+import docutils.writers.html4css1
+from subprocess import Popen, PIPE
+from jinja2 import Environment, Template
+from jinja2.filters import do_dictsort
+from spec_util import is_dynamic_pinned, verify_node, isAbstract, setdefault
+from ir_spec import nodes
+
+def trim(docstring):
+ if not docstring:
+ return ''
+ # Convert tabs to spaces (following the normal Python rules)
+ # and split into a list of lines:
+ lines = docstring.expandtabs().splitlines()
+ # Determine minimum indentation (first line doesn't count):
+ indent = sys.maxint
+ for line in lines[1:]:
+ stripped = line.lstrip()
+ if stripped:
+ indent = min(indent, len(line) - len(stripped))
+ # Remove indentation (first line is special):
+ trimmed = [lines[0].strip()]
+ if indent < sys.maxint:
+ for line in lines[1:]:
+ trimmed.append(line[indent:].rstrip())
+ # Strip off trailing and leading blank lines:
+ while trimmed and not trimmed[-1]:
+ trimmed.pop()
+ while trimmed and not trimmed[0]:
+ trimmed.pop(0)
+ # Return a single string:
+ return '\n'.join(trimmed)
+
+def format_docutils(string):
+ writer = docutils.writers.html4css1.Writer()
+ document = docutils.core.publish_parts(string, writer=writer)['body']
+ return document
+
+env = Environment()
+env.filters['docutils'] = format_docutils
+
+docu_template = env.from_string(
+'''<html>
+ <head>
+ <title>libFirm node specifications</title>
+ <link rel='stylesheet' type='text/css' href='style.css'/>
+ </head>
+ <body>
+ <div class="document">
+ <div class="documentwrapper">
+ <div class="bodywrapper"><div class="body">
+ <h1>Firm Node Types</h1>
+ {% for node in nodes %}
+ <div class="section" id="{{node.name}}">
+ <h3>{{node.name}}</h3>
+ {{node.doc|docutils}}
+ <h5>Inputs</h5>
+ <dl>
+ {% for input in node.ins %}
+ <dt>{{input[0]}}</dt><dd>{{input[1]}}</dd>
+ {% endfor %}
+ {% if node.arity == "variable" %}
+ <dt>...</dt><dd>additional inputs (oparity_variable)</dd>
+ {% elif node.arity == "dynamic" %}
+ <dt>...</dt><dd>inputs dynamically mananged (oparity_dynamic)</dd>
+ {% endif %}
+ </dl>
+ {% if node.outs %}
+ <h5>Outputs</h5>
+ <dl>
+ {% for output in node.outs %}
+ <dt>{{output[0]}}</dt><dd>{{output[1]}}</dd>
+ {% endfor %}
+ </dl>
+ {% endif %}
+ {% if node.attributes %}
+ <h5>Attributes</h5>
+ <dl>
+ {% for attr in node.attrs %}
+ <dt>{{attr.name}}</dt><dd>{{attr.comment}} ({{attr.type}})</dd>
+ {% endfor %}
+ {% endif %}
+ </dl>
+ <h5>Flags</h5>
+ {% for flag in node.flags %} {{flag}} {% endfor %}
+ </div>
+ {% endfor %}
+ </div></div>
+ </div>
+ <div class="sidebar">
+ <div class="sidebarwrapper">
+ <h3>Table Of Contents</h3>
+ <ul>
+ <li><a href="#">Firm Node Types</a>
+ <ul>
+ {% for node in nodes %}
+ <li><a href="#{{node.name}}">{{node.name}}</a></li>
+ {% endfor %}
+ </ul>
+ </li>
+ </div>
+ </div>
+ </div>
+ </body>
+</html>
+''')
+
+#############################
+
+def preprocess_node(node):
+ node.doc = trim(node.__doc__)
+
+def prepare_nodes():
+ real_nodes = []
+ for node in nodes:
+ preprocess_node(node)
+ if isAbstract(node):
+ continue
+ real_nodes.append(node)
+
+ return real_nodes
+
+def main(argv):
+ real_nodes = prepare_nodes()
+ sys.stdout.write(docu_template.render(nodes = real_nodes))
+
+main(sys.argv)
attr_struct = "cmp_attr"
class Cond(Op):
- """Conditionally change control flow.
- Input: A value of mode_b
- Output: A tuple of two control flows. The first is taken if the input is
- false, the second if it is true.
- """
+ """Conditionally change control flow."""
ins = [
("selector", "condition parameter"),
]
"""returns the remainder of its operands from an implied division.
Examples:
+
* mod(5,3) produces 2
* mod(5,-3) produces 2
* mod(-5,3) produces -2
class SymConst(Op):
"""A symbolic constant.
- - symconst_type_tag The symbolic constant represents a type tag. The
- type the tag stands for is given explicitly.
- - symconst_type_size The symbolic constant represents the size of a type.
- The type of which the constant represents the size
- is given explicitly.
- - symconst_type_align The symbolic constant represents the alignment of a
- type. The type of which the constant represents the
- size is given explicitly.
- - symconst_addr_ent The symbolic constant represents the address of an
- entity (variable or method). The variable is given
- explicitly by a firm entity.
- - symconst_ofs_ent The symbolic constant represents the offset of an
- entity in its owner type.
- - symconst_enum_const The symbolic constant is a enumeration constant of
- an enumeration type."""
+ - *symconst_type_tag* The symbolic constant represents a type tag. The
+ type the tag stands for is given explicitly.
+ - *symconst_type_size* The symbolic constant represents the size of a type.
+ The type of which the constant represents the size
+ is given explicitly.
+ - *symconst_type_align* The symbolic constant represents the alignment of a
+ type. The type of which the constant represents the
+ size is given explicitly.
+ - *symconst_addr_ent* The symbolic constant represents the address of an
+ entity (variable or method). The variable is given
+ explicitly by a firm entity.
+ - *symconst_ofs_ent* The symbolic constant represents the offset of an
+ entity in its owner type.
+ - *symconst_enum_const* The symbolic constant is a enumeration constant of
+ an enumeration type."""
mode = "mode_P"
flags = [ "constlike", "start_block" ]
knownBlock = True
--- /dev/null
+/*
+ * documentation formatting (heavily inspired by jinja.css)
+ */
+body {
+ font-family: Georgia, serif;
+ font-size: 17px;
+ background-color: white;
+ color: #000;
+ margin: 0;
+ padding: 0;
+}
+
+div.body {
+ background-color: #ffffff;
+ color: #3E4349;
+ padding: 0 30px 0 30px;
+}
+
+div.document {
+ width: 940px;
+ margin: 30px auto 0 auto;
+}
+
+div.documentwrapper {
+ float: left;
+ width: 100%;
+}
+
+div.bodywrapper {
+ margin: 0 0 0 220px;
+}
+
+div.sidebar {
+ width: 220px;
+}
+
+div.sidebarwrapper {
+ padding: 10px 5px 0 10px;
+}
+
+div.sidebar {
+ float: left;
+ width: 230px;
+ margin-left: -100%;
+ font-size: 90%;
+}
+
+div.sidebar ul {
+ list-style: none;
+}
+
+div.sidebar ul ul,
+div.sidebar ul.want-points {
+ margin-left: 20px;
+ list-style: square;
+}
+
+div.sidebar ul ul {
+ margin-top: 0;
+ margin-bottom: 0;
+}
+
+div.sidebar form {
+ margin-top: 10px;
+}
+
+div.sidebar input {
+ border: 1px solid #98dbcc;
+ font-family: sans-serif;
+ font-size: 1em;
+}
+
+a {
+ color: #aa0000;
+ text-decoration: underline;
+}
+
+a:hover {
+ color: #dd0000;
+ text-decoration: underline;
+}
+
+div.body h1,
+div.body h2,
+div.body h3,
+div.body h4,
+div.body h5,
+div.body h6 {
+ font-family: Crimson Text, Georgia, serif;
+ font-weight: normal;
+ margin: 30px 0px 10px 0px;
+ padding: 0;
+ color: black;
+}
+
+div.body h1 { margin-top: 0; padding-top: 0; font-size: 240%; }
+div.body h2 { font-size: 180%; }
+div.body h3 { font-size: 150%; }
+div.body h4 { font-size: 130%; }
+div.body h5 { font-size: 100%; }
+div.body h6 { font-size: 100%; }
+
+div.body p, div.body dd, div.body li {
+ line-height: 1.4em;
+}
+
+ul, ol {
+ margin: 10px 0 10px 30px;
+ padding: 0;
+}
+
+pre {
+ background: #eee;
+ padding: 7px 30px;
+ margin: 15px -30px;
+ line-height: 1.3em;
+}
+
+dl pre, blockquote pre, li pre {
+ margin-left: -60px;
+ padding-left: 60px;
+}
+
+dl dl pre {
+ margin-left: -90px;
+ padding-left: 90px;
+}
+
+tt {
+ background-color: #E8EFF0;
+ color: #222;
+ /* padding: 1px 2px; */
+}
+
+a.reference {
+ text-decoration: none;
+ border-bottom: 1px dotted #bb0000;
+}
+
+a.reference:hover {
+ border-bottom: 1px solid #dd0000;
+}
+
+a.footnote-reference {
+ text-decoration: none;
+ font-size: 0.7em;
+ vertical-align: top;
+ border-bottom: 1px dotted #bb0000;
+}
+
+a.footnote-reference:hover {
+ border-bottom: 1px solid #dd0000;
+}