CS 330 Lecture 17 – Callbacks and Parsing with ANTLR
Agenda
- one more thing on C function pointers: callbacks
- program this
- the translation process: lexing, parsing, generating
- ANTLR v4
- why write our own languages and parsers?
TODO
- Read chapter 2 through section 2.1.
- Walk through http://www.antlr.org/wiki/display/ANTLR4/Getting+Started+with+ANTLR+v4.
- Quarter sheet.
Program This
Write a regular expression that matches text containing balanced HTML <div> tags. Balanced means every open tag (<div>) is followed ultimately by a close tag (</div>). Within an open-close pair, one or more other balanced <div> elements may appear.
Code
torus.c
#include <stdio.h>
#include <stdlib.h>
#include <GL/glut.h>
float angle = 0.0f;
void on_draw() {
glClearColor(1.0f, 0.0f, 1.0f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT);
glColor3f(1.0f, 1.0f, 0.0f);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glRotatef(angle, 1.0f, 0.0f, 0.0f);
glutWireTorus(0.3f, 0.7f, 10, 10);
glutSwapBuffers();
}
void on_special_key(int key, int x, int y) {
switch (key) {
case GLUT_KEY_UP:
angle += 5.0f;
break;
case GLUT_KEY_DOWN:
angle -= 5.0f;
break;
default:
break;
}
glutPostRedisplay();
}
int main(int argc, char **argv) {
glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE);
glutInitWindowSize(512, 512);
glutInit(&argc, argv);
glutCreateWindow("3-D Application");
glutDisplayFunc(on_draw);
glutSpecialFunc(on_special_key);
glutMainLoop();
return 0;
}
Divs.g4
grammar Divs;
html
: element* EOF
;
element
: OPEN element* CLOSE
;
/* TOKENS or TERMINALS */
OPEN
: '<div>'
| '<DIV>'
| '<dIV>'
;
CLOSE
: '</div>'
| '</DIV>'
;
WHITESPACE
: [ \t\n\r]+ -> skip
;
messy.txt
<div><div><div></div></div><div><div><div></div></div><div><div></div><div></div><div></div><div></div><div></div><div></div></div></div></div>
PrettyPrinter.java
import org.antlr.v4.runtime.*;
import java.io.IOException;
import org.antlr.v4.runtime.tree.*;
public class PrettyPrinter extends DivsBaseListener {
private int nIndents = 0;
public static void main(String[] args) throws IOException {
ANTLRInputStream in = new ANTLRInputStream(System.in);
DivsLexer lexer = new DivsLexer(in);
CommonTokenStream tokens = new CommonTokenStream(lexer);
DivsParser parser = new DivsParser(tokens);
ParseTree tree = parser.html();
ParseTreeWalker walker = new ParseTreeWalker();
walker.walk(new PrettyPrinter(), tree);
}
public void enterElement(DivsParser.ElementContext context) {
indent();
System.out.println("<div>");
++nIndents;
}
public void exitElement(DivsParser.ElementContext context) {
--nIndents;
indent();
System.out.println("</div>");
}
private void indent() {
for (int i = 0; i < nIndents; ++i) {
System.out.print(" ");
}
}
}