Skip to main content

module analysis::m3::LearnPrettyPrinter

rascal-0.34.0
clair-0.12.0

Usage

import analysis::m3::LearnPrettyPrinter;

Source code

http://github.com/usethesource/clair/blob/main/src/analysis/m3/LearnPrettyPrinter.rsc

Dependencies

import IO;
import Node;
import Type;
import List;
import Location;
import String;
import Set;
import util::FileSystem;
import lang::cpp::AST;

function generateFormatterForC

this is a demo/test function that learns a C pretty printer from the C files in the example folder.

void generateFormatterForC()

function filesToPrettyPrinter

Takes a corpus of example files and an (external) parser for the given language and produces a pretty printing function as Rascal code.

str filesToPrettyPrinter(set[loc] files, type[node] grammar, node (loc) parser)

If the external parser satisfies the specification in analysis::m3::AST then this function will learn a basic unparser (a.k.a. pretty printer) from the corpus of files.

The code that is generated is Rascal code which can be expanded into a module that imports the right AST format, and nothing else.

The "pretty" aspect should not be over-estimated:

  • The generated formatter does not deal with nested indentation.
  • It has one rule for every unique AST node kind (constructor), so special combinations do not get special treatment
  • It is not able to generate syntactically correct files for layout-sensitive languages
  • If the core example for a node contains source code comments, these will end up in the output

This function is typically used in source-to-source transformations where an intermediate AST to AST transformation takes place. To derive source code from fresh syntax nodes, the format function is required.

function treesToPrettyPrinter

Takes a corpus of syntax trees (for the same language!) and produces Rascal code that can generate code back from ASTs.

str treesToPrettyPrinter(set[node] asts, type[node] grammar)

function formatFunction

str formatFunction(str yield, node n)

data Template

data Template  
= hole(int n)
| sep(str chars)
| \list(str sep, int n)
| const(str chars, int n)
;

function cutOut

get a template out of an example node by replacing the children with holes

list[Template] cutOut(str yield, node n)

function template

Turns a child into a template element

Template template(int _begin, int _, int i, str _yield)

Template template(int _begin, str s, int i, str _yield)

Template template(int _begin, node _, int i, str _yield)

Template template(int _begin, [], int i, str _yield)

Template template(int _begin, [node a], int i, str yield)

Template template(int begin, [node a, node b, *_], int i, str yield)

function print

Prints a rascal code template part, including recursive calls.

str print(hole(int i))

str print(sep(str chars))

str print(const(str _chars, int i))

str print(\list(str sep, int i))

function position

Give every element a true location for later processing.

list[loc] position(loc span, list[value] l)

function pos

loc pos(loc span, int _)

loc pos(loc span, str _)

loc pos(loc _span, [])

loc pos(loc _span, node n)

loc pos(loc _span, [node n])

loc pos(loc _span, [node a, *_, node b])

function infer

Replaces all |empty:///| with a correct loc inferred from the surroundings

list[loc] infer(loc span, [loc l, *loc rest])

list[loc] infer(loc span, [*loc rest, loc l])

list[loc] infer(loc span, [*loc pre, loc before, loc l, *loc post])

list[loc] infer(loc span, [*loc pre, loc l, loc after, *loc post])

default list[loc] infer(loc _span, list[loc] done)

function \type

Print the type of a value, as Rascal code

str \type(value n)

function escape

Escape string elements for use in a Rascal template string

str escape(str s)

function \loc

Waiting for node.src to be available in Rascal for good...

loc \loc(node n)