SlideShare a Scribd company logo
1 of 30
Creating a Compiler with 
Irony and RunSharp 
James M. Curran 
NYC CodeCamp 
Sept 13, 2014
Creating a Compiler with 
Irony and RunSharp 
James M. Curran 
NYC CodeCamp 
Sept 13, 2014 
Brought to you by : MARQUEE SPONSOR
Who the Heck am I? 
 Simple Country Programmer 
 20+ Years in Software Development 
 Assembler, C, C++, C# 
 Worked in Medical, Financial, Online 
Retailing, and Embedded systems 
 Microsoft MVP C++ (1994-2004) 
 Currently Itinerant Programmer at One 
Call Medical 
 Write blog: HonestIllusion.com 
 Designer: NJTheater.Com 
 Resume'n'stuff: NovelTheory.com
Who the Heck am I? 
 Simple Country Programmer 
 20+ Years in Software Development 
 Assembler, C, C++, C# 
 Worked in Medical, Financial, Online 
Retailing, and Embedded systems 
 Microsoft MVP C++ (1994-2004) 
 Currently Itinerant Programmer at One 
Call Medical 
 Write blog: HonestIllusion.com 
 Designer: NJTheater.Com 
 Resume'n'stuff: NovelTheory.com 
Brought to you by 
PLATINUM SPONSOR
Yeah, Comic Sans 
Deal with it.
“Naked Came the Null Delegate” 
➲ Collaborative blog story telling a tale of sex, betrayal 
and .NET coding. 
➲ Serialized across the blogs of several noted .NET 
writers including Charles Petzold and Jon Skeet. 
➲ Dormant since 2010, but new writers wanted. 
➲ http://nakedcamethenulldelegate.wordpress.com 
Brought to you by 
PLATINUM SPONSOR
Agenda 
 The Language 
 The Parser 
 The Code Generators (plural) 
 The Command-line interface. 
Brought to you by GOLD SPONSORS
Shakespeare Programming Language - 
History 
 Designed by Jon Åslund and Karl Hasselström in 2001. 
 The design goal was to make a language with beautiful source 
code that resembled Shakespeare plays. 
 Original compiler written in YACC (actually Bison), producing C 
code. 
 I wrote the C# compiler in Sept 2013. Apparently I was the 
first person to touch the code in 12 years. 
 Since then, Javascript, Python, Perl, and Java versions of been 
open-sourced and http://shakespearelang.org/ was launched.
Variables 
 Must be the name of an actual character from one of 
Shakespeare's play. 
 That’s exactly 152 specific allowable variable names. 
 Some names are more than one word! 
 Only data type is an integer, but it can be used for a 
character. 
 It's really a stack of integers.
Numbers/Constants 
 Nouns that are “nice” or neutral equal 1. 
 Nouns that are “not nice” equal -1. 
 Adjectives (nice or not) multiply by 2. 
 Examples: 
“big hairy hound” = 2 * 2 * (+1) = 4 
“sorry little codpiece” = 2 * 2 * (-1) = -4 
 Can be combined with “Sum of ___ and ___”, 
“Difference between”, “Square of”, “Cube of” 
 41 neutral, 13 positive, and 25 negative nouns 
20 neutral, 36 positive and 32 negative adjectives
Input and Output 
 "Open your heart" outputs the variable's value as a number 
 "Speak your mind" outputs the corresponding ASCII character. 
 "Listen to your heart" cause the variable to receive input from the user 
as a number. 
 "Open your mind" receive input from a character. 
Conditional Statements and Gotos 
 An if/then statement is phrased as a question posed by a 
character. 
 The words "as [any adjective] as" represent a test for equality, 
 "better" and "worse" correspond to greater than and less than 
 A subsequent line, starting "if so" or "if not," determines what 
happens in response to the truth or falsehood of the original 
condition. 
 A goto statement begins "Let us," "We shall," or "We must," 
continues "return to" or "proceed to," and then gives an act or 
scene.
Example 
Outputting Input Reversedly. 
Othello, a stacky man. 
Lady Macbeth, who pushes him around till he pops. 
Act I: The one and only. 
Scene I: In the beginning, there was nothing. 
[Enter Othello and Lady Macbeth] 
Othello: 
You are nothing! 
Scene II: Pushing to the very end. 
Lady Macbeth: 
Open your mind! Remember yourself. 
Othello: 
You are as hard as the sum of yourself and a stone wall. Am I as horrid 
as a flirt-gill? 
Lady Macbeth: 
If not, let us return to scene II. Recall your imminent death!
The original compiler 
Like most languages, specified in Backus–Naur Form 
(BNF) 
 Compiler coded in YACC (“Yet Another Compiler 
Compiler”) (Actually, in GNU’s version BISON) 
It’s object code (output) is C source code, which would 
then need to be compiled.
BNF & YACC 
BNF is made up of “Terminals” and “Non-terminal” 
Terminal symbols are the elementary symbols of the 
language 
Non-terminals are made of a combining terminals and 
other non-terminals. 
Example: 
digit = '0'|'1' |'2' |'3' |'4' |'5' |'6' |'7' |'8' |'9‘ 
integer = ['-'] digit+ 
YACC is a LALR parser generator. 
YACC source files are BNF with C code attached to 
some non-terminals.
Original Compiler (excerpt) 
Play: Title CharacterDeclarationList Act+ 
CharacterDeclarationList: CharacterDeclaration+ 
Act: ActHeader Scene+ 
ActHeader: ACT_ROMAN COLON Comment EndSymbol 
Constant: 
ARTICLE UnarticulatedConstant 
| 
FIRST_PERSON_POSSESSIVE UnarticulatedConstant 
| 
SECOND_PERSON_POSSESSIVE UnarticulatedConstant 
| 
THIRD_PERSON_POSSESSIVE UnarticulatedConstant 
| 
NOTHING
1st tool: Irony 
Irony is a development kit for implementing languages 
on .NET platform. 
Name is a play on IronPython, IronRuby, IronScheme : 
“Use Irony to create your own Iron* language” 
Tries to replicate BNF in C# code via operator 
overloading. 
Project home: https://irony.codeplex.com/ 
Available on nuget: “irony”
Irony Example: 
public class ShakespeareGrammar : InterpretedLanguageGrammar 
{ 
public ShakespeareGrammar() 
: base(false) 
{ 
string[] endSymbols = { ".", "?", "!" }; 
KeyTerm COLON = ToTerm(":", "colon"); 
KeyTerm COMMA = ToTerm(","); 
// : 
var Act = new NonTerminal("Act"); 
var Acts = new NonTerminal("Acts"); 
Acts.Rule = MakePlusRule(Acts, Act); 
var Play = new NonTerminal("Play"); 
Play.Rule = Title + CharacterDeclarationList + Acts;
Example, cont: 
var Constant = new NonTerminal("Constant »); 
Constant.Rule = Article + UnarticulatedConstant | 
FirstPersonPossessive + UnarticulatedConstant | 
SecondPersonPossessive + UnarticulatedConstant | 
ThirdPersonPossessive + UnarticulatedConstant ; 
UnarticulatedConstant.Rule = PositiveConstant 
| NegativeConstant; 
PositiveConstant.Rule = PositiveNoun 
| PositiveAdjective + PositiveConstant 
| NeutralAdjective + PositiveConstant; 
Question.Rule =Be + Value + Comparison + Value + QuestionSymbol;
Multi-Word keywords 
BnfTerm MultiWordTermial(string term) 
{ 
var parts = term.Split(' '); 
if (parts.Length == 1) 
return ToTerm(term); 
var nonterm = new NonTerminal(term); 
var expr = new BnfExpression(ToTerm(parts[0])); 
foreach (var part in parts.Skip(1)) 
{ 
expr += ToTerm(part); 
} 
nonterm.Rule = expr; 
return nonterm; 
}
Equivalent Keywords 
NonTerminal BuildTerminal(string name, string filename) 
{ 
var termList = new NonTerminal(name)); 
var strm = assembly.GetManifestResourceStream(filename); 
var sw = new StreamReader(strm); 
var block = sw.ReadToEnd(); 
var lines = block.Split('n', 'r'); 
if (lines.Any()) 
{ 
var expr = new BnfExpression(MultiWordTermial(lines[0])); 
foreach (var line in lines.Skip(1)) 
{ 
if (!String.IsNullOrWhiteSpace(line)) 
expr |= MultiWordTermial(line); 
} 
termList.Rule = expr; 
} 
return termList; 
}
Irony's GrammarExplorer tool
Code Generation 
• Ok, You’ve got a parser. Now what? 
• Irony documentation drops off here. 
• Here’s what I learned single-stepping with the 
debugger.
Create AST tree from source. 
var grammar = new ShakespeareGrammar(); 
var parser = new Parser(grammar); 
var text = File.ReadAllText(filename); 
var tree = parser.Parse(text, filename); 
var app = new ScriptApp(parser.Language); 
var thread = new ScriptThread(app); 
var output= tree.Root.AstNode.Evaluate(thread);
Walking the Tree 
As tree.Root.AstNode.Evaluate(thread) runs, 
node.DoEvaluate() is called for each node on the tree. 
By default, AstNode objects are in tree. 
So we need our own nodes in the tree.
ASTNode (Fixed) 
var Act = new NonTerminal("Act", typeof(ActNode)); 
var NegativeConstant = new NonTerminal("NegativeConstant", 
typeof(NegativeConstantNode)); 
public class NegativeConstantNode : AstNode 
{ 
protected override object DoEvaluate(ScriptThread thread) 
{ 
var tw = thread.tc().Writer; 
if (AstNode1 is NegativeNounNode) 
return "(-1)"; 
else 
return string.Format("2*{0}", 
AstNode2.ToString(thread)); 
} 
}
public class PlayNode : AstNode 
{ 
protected override object DoEvaluate(Irony.Interpreter.ScriptThread thread) 
{ 
var sw = thread.tc().Writer; 
sw.WriteLine("using System;"); 
sw.WriteLine("using Shakespeare.Support;"); 
sw.WriteLine(); 
sw.WriteLine("namespace Shakespeare.Program"); 
sw.WriteLine("{"); 
sw.WriteLine("tclass Program"); 
sw.WriteLine("t{"); 
sw.WriteLine("ttstatic void Main(string[] args) {"); 
sw.WriteLine("tttvar script = new Script();"); 
sw.WriteLine("tttscript.Action();"); 
sw.WriteLine("tt}"); 
sw.WriteLine("t}"); 
sw.WriteLine("ttclass Script : Dramaturge {"); 
sw.WriteLine("ttpublic Script()"); 
sw.WriteLine("tt : base(Console.In, Console.Out)"); 
sw.WriteLine("tt{ }"); 
sw.WriteLine(); 
sw.WriteLine("ttpublic void Action()"); 
sw.WriteLine("tt{"); 
AstNode1.Evaluate(thread); // Title 
sw.WriteLine(); 
var cdl = AstNode2 as CharacterDeclarationListNode; 
foreach (var ch in cdl.Characters) 
ch.Evaluate(thread); 
sw.WriteLine(); 
AstNode3.Evaluate(thread); 
sw.WriteLine("tt}"); 
sw.WriteLine("t}"); 
sw.WriteLine("}"); 
sw.Flush(); 
sw.Close(); 
return sw; 
} 
}
A second code generator 
That works fine for if you only need one code 
generator. 
But I wanted to write a C code generator, a C# code 
generator and a MSIL code generator. 
{more digging with debugger} 
I’ve got great tool from switching between several 
generators – Check the github…..
2nd tool: RunSharp 
RunSharp is a layer above the standard .NET 
Reflection.Emit API, allowing to generate/compile 
dynamic code at runtime very quickly and efficiently 
(unlike using CodeDOM and invoking the C# compiler). 
Project home : https://code.google.com/p/runsharp/ 
(but it’s stagnant, so check github for forks) 
Not on Nuget.
public class PlayNode : AstNode 
{ 
protected override object DoEvaluate(Irony.Interpreter.ScriptThread thread) 
{ 
var rs = thread.rs(); 
var ag = rs.AssemblyGen; 
using (ag.Namespace("Shakespeare.Program")) 
{ 
TypeGen scriptClass = ag.Public.Class("Script", typeof(Shakespeare.Support.Dramaturge)); 
{ 
rs.Script = scriptClass; 
var console = typeof(Console); 
CodeGen ctor = scriptClass.Public.Constructor(); 
ctor.InvokeBase(Static.Property(console, "In"), Static.Property(console, "Out")); 
{ 
} 
CodeGen action = scriptClass.Public.Void("Action"); 
{ 
rs.Action = action; 
action.At(Span); 
AstNode1.Evaluate(thread); 
var cdl = AstNode2 as CharacterDeclarationListNode; 
foreach (var ch in cdl.Characters) 
ch.Evaluate(thread); 
AstNode3.Evaluate(thread); 
} 
} 
scriptClass.Complete(); 
TypeGen MyClass = ag.Public.Class("Program"); 
CodeGen Main = MyClass.Public.Static.Void("Main").Parameter<string[]>("args"); 
{ 
var script = Main.Local(Exp.New(scriptClass.GetCompletedType())); 
Main.Invoke(script, "Action"); 
} 
} 
ag.Save(); 
return ag.GetAssembly().GetName().Name; 
} 
}
public class NegativeConstantNode : AstNode 
{ 
protected override object DoEvaluate(ScriptThread thread) 
{ 
if (AstNode1 is NegativeNounNode) 
return ((Operand) 0- 1); 
else 
return (AstNode2.Evaluate(thread) as Operand) * 2; 
} 
}

More Related Content

What's hot

Thnad's Revenge
Thnad's RevengeThnad's Revenge
Thnad's RevengeErin Dees
 
Your Own Metric System
Your Own Metric SystemYour Own Metric System
Your Own Metric SystemErin Dees
 
Groovy presentation
Groovy presentationGroovy presentation
Groovy presentationManav Prasad
 
Understanding the REST API of SharePoint 2013
Understanding the REST API of SharePoint 2013Understanding the REST API of SharePoint 2013
Understanding the REST API of SharePoint 2013SPSSTHLM
 
Fantom on the JVM Devoxx09 BOF
Fantom on the JVM Devoxx09 BOFFantom on the JVM Devoxx09 BOF
Fantom on the JVM Devoxx09 BOFDror Bereznitsky
 
P H P Part I, By Kian
P H P  Part  I,  By  KianP H P  Part  I,  By  Kian
P H P Part I, By Kianphelios
 
Ruby -the wheel Technology
Ruby -the wheel TechnologyRuby -the wheel Technology
Ruby -the wheel Technologyppparthpatel123
 
Protocols with Associated Types, and How They Got That Way
Protocols with Associated Types, and How They Got That WayProtocols with Associated Types, and How They Got That Way
Protocols with Associated Types, and How They Got That WayAlexis Gallagher
 
Regular Expressions grep and egrep
Regular Expressions grep and egrepRegular Expressions grep and egrep
Regular Expressions grep and egrepTri Truong
 
name name2 n2
name name2 n2name name2 n2
name name2 n2callroom
 
name name2 n2.ppt
name name2 n2.pptname name2 n2.ppt
name name2 n2.pptcallroom
 

What's hot (16)

Thnad's Revenge
Thnad's RevengeThnad's Revenge
Thnad's Revenge
 
Your Own Metric System
Your Own Metric SystemYour Own Metric System
Your Own Metric System
 
Groovy presentation
Groovy presentationGroovy presentation
Groovy presentation
 
Ruby cheat sheet
Ruby cheat sheetRuby cheat sheet
Ruby cheat sheet
 
Understanding the REST API of SharePoint 2013
Understanding the REST API of SharePoint 2013Understanding the REST API of SharePoint 2013
Understanding the REST API of SharePoint 2013
 
Fantom on the JVM Devoxx09 BOF
Fantom on the JVM Devoxx09 BOFFantom on the JVM Devoxx09 BOF
Fantom on the JVM Devoxx09 BOF
 
Ruby quick ref
Ruby quick refRuby quick ref
Ruby quick ref
 
P H P Part I, By Kian
P H P  Part  I,  By  KianP H P  Part  I,  By  Kian
P H P Part I, By Kian
 
Ruby -the wheel Technology
Ruby -the wheel TechnologyRuby -the wheel Technology
Ruby -the wheel Technology
 
Cleancode
CleancodeCleancode
Cleancode
 
Protocols with Associated Types, and How They Got That Way
Protocols with Associated Types, and How They Got That WayProtocols with Associated Types, and How They Got That Way
Protocols with Associated Types, and How They Got That Way
 
Regular Expressions grep and egrep
Regular Expressions grep and egrepRegular Expressions grep and egrep
Regular Expressions grep and egrep
 
ppt18
ppt18ppt18
ppt18
 
name name2 n2
name name2 n2name name2 n2
name name2 n2
 
ppt9
ppt9ppt9
ppt9
 
name name2 n2.ppt
name name2 n2.pptname name2 n2.ppt
name name2 n2.ppt
 

Similar to Build a compiler using C#, Irony and RunSharp.

Building DSLs with Xtext - Eclipse Modeling Day 2009
Building DSLs with Xtext - Eclipse Modeling Day 2009Building DSLs with Xtext - Eclipse Modeling Day 2009
Building DSLs with Xtext - Eclipse Modeling Day 2009Heiko Behrens
 
Kotlin: A pragmatic language by JetBrains
Kotlin: A pragmatic language by JetBrainsKotlin: A pragmatic language by JetBrains
Kotlin: A pragmatic language by JetBrainsJigar Gosar
 
Back to the Future with TypeScript
Back to the Future with TypeScriptBack to the Future with TypeScript
Back to the Future with TypeScriptAleš Najmann
 
Kotlin as a Better Java
Kotlin as a Better JavaKotlin as a Better Java
Kotlin as a Better JavaGarth Gilmour
 
C# 6 and 7 and Futures 20180607
C# 6 and 7 and Futures 20180607C# 6 and 7 and Futures 20180607
C# 6 and 7 and Futures 20180607Kevin Hazzard
 
MongoDB World 2019: BSON Transpilers: Transpiling from Any Language to Any La...
MongoDB World 2019: BSON Transpilers: Transpiling from Any Language to Any La...MongoDB World 2019: BSON Transpilers: Transpiling from Any Language to Any La...
MongoDB World 2019: BSON Transpilers: Transpiling from Any Language to Any La...MongoDB
 
Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]
Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]
Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]Chris Adamson
 
C# Language Overview Part I
C# Language Overview Part IC# Language Overview Part I
C# Language Overview Part IDoncho Minkov
 
Basics of Javascript
Basics of JavascriptBasics of Javascript
Basics of JavascriptUniverse41
 
Introduction to Python - Training for Kids
Introduction to Python - Training for KidsIntroduction to Python - Training for Kids
Introduction to Python - Training for KidsAimee Maree Forsstrom
 

Similar to Build a compiler using C#, Irony and RunSharp. (20)

Javascript
JavascriptJavascript
Javascript
 
Building DSLs with Xtext - Eclipse Modeling Day 2009
Building DSLs with Xtext - Eclipse Modeling Day 2009Building DSLs with Xtext - Eclipse Modeling Day 2009
Building DSLs with Xtext - Eclipse Modeling Day 2009
 
Kotlin: A pragmatic language by JetBrains
Kotlin: A pragmatic language by JetBrainsKotlin: A pragmatic language by JetBrains
Kotlin: A pragmatic language by JetBrains
 
Back to the Future with TypeScript
Back to the Future with TypeScriptBack to the Future with TypeScript
Back to the Future with TypeScript
 
Kotlin as a Better Java
Kotlin as a Better JavaKotlin as a Better Java
Kotlin as a Better Java
 
Python
PythonPython
Python
 
Python crush course
Python crush coursePython crush course
Python crush course
 
C# 6 and 7 and Futures 20180607
C# 6 and 7 and Futures 20180607C# 6 and 7 and Futures 20180607
C# 6 and 7 and Futures 20180607
 
Python basic
Python basicPython basic
Python basic
 
C# overview part 1
C# overview part 1C# overview part 1
C# overview part 1
 
MongoDB World 2019: BSON Transpilers: Transpiling from Any Language to Any La...
MongoDB World 2019: BSON Transpilers: Transpiling from Any Language to Any La...MongoDB World 2019: BSON Transpilers: Transpiling from Any Language to Any La...
MongoDB World 2019: BSON Transpilers: Transpiling from Any Language to Any La...
 
Programming with Python
Programming with PythonProgramming with Python
Programming with Python
 
Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]
Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]
Oh Crap, I Forgot (Or Never Learned) C! [CodeMash 2010]
 
python-ch2.pptx
python-ch2.pptxpython-ch2.pptx
python-ch2.pptx
 
C# Language Overview Part I
C# Language Overview Part IC# Language Overview Part I
C# Language Overview Part I
 
Basics of Javascript
Basics of JavascriptBasics of Javascript
Basics of Javascript
 
ECMA 入门
ECMA 入门ECMA 入门
ECMA 入门
 
Introduction to Python - Training for Kids
Introduction to Python - Training for KidsIntroduction to Python - Training for Kids
Introduction to Python - Training for Kids
 
C tutorial
C tutorialC tutorial
C tutorial
 
C tutorial
C tutorialC tutorial
C tutorial
 

Recently uploaded

software engineering Chapter 5 System modeling.pptx
software engineering Chapter 5 System modeling.pptxsoftware engineering Chapter 5 System modeling.pptx
software engineering Chapter 5 System modeling.pptxnada99848
 
Automate your Kamailio Test Calls - Kamailio World 2024
Automate your Kamailio Test Calls - Kamailio World 2024Automate your Kamailio Test Calls - Kamailio World 2024
Automate your Kamailio Test Calls - Kamailio World 2024Andreas Granig
 
Advancing Engineering with AI through the Next Generation of Strategic Projec...
Advancing Engineering with AI through the Next Generation of Strategic Projec...Advancing Engineering with AI through the Next Generation of Strategic Projec...
Advancing Engineering with AI through the Next Generation of Strategic Projec...OnePlan Solutions
 
Folding Cheat Sheet #4 - fourth in a series
Folding Cheat Sheet #4 - fourth in a seriesFolding Cheat Sheet #4 - fourth in a series
Folding Cheat Sheet #4 - fourth in a seriesPhilip Schwarz
 
React Server Component in Next.js by Hanief Utama
React Server Component in Next.js by Hanief UtamaReact Server Component in Next.js by Hanief Utama
React Server Component in Next.js by Hanief UtamaHanief Utama
 
Cloud Management Software Platforms: OpenStack
Cloud Management Software Platforms: OpenStackCloud Management Software Platforms: OpenStack
Cloud Management Software Platforms: OpenStackVICTOR MAESTRE RAMIREZ
 
GOING AOT WITH GRAALVM – DEVOXX GREECE.pdf
GOING AOT WITH GRAALVM – DEVOXX GREECE.pdfGOING AOT WITH GRAALVM – DEVOXX GREECE.pdf
GOING AOT WITH GRAALVM – DEVOXX GREECE.pdfAlina Yurenko
 
Steps To Getting Up And Running Quickly With MyTimeClock Employee Scheduling ...
Steps To Getting Up And Running Quickly With MyTimeClock Employee Scheduling ...Steps To Getting Up And Running Quickly With MyTimeClock Employee Scheduling ...
Steps To Getting Up And Running Quickly With MyTimeClock Employee Scheduling ...MyIntelliSource, Inc.
 
The Evolution of Karaoke From Analog to App.pdf
The Evolution of Karaoke From Analog to App.pdfThe Evolution of Karaoke From Analog to App.pdf
The Evolution of Karaoke From Analog to App.pdfPower Karaoke
 
Cloud Data Center Network Construction - IEEE
Cloud Data Center Network Construction - IEEECloud Data Center Network Construction - IEEE
Cloud Data Center Network Construction - IEEEVICTOR MAESTRE RAMIREZ
 
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样umasea
 
Asset Management Software - Infographic
Asset Management Software - InfographicAsset Management Software - Infographic
Asset Management Software - InfographicHr365.us smith
 
EY_Graph Database Powered Sustainability
EY_Graph Database Powered SustainabilityEY_Graph Database Powered Sustainability
EY_Graph Database Powered SustainabilityNeo4j
 
Building Real-Time Data Pipelines: Stream & Batch Processing workshop Slide
Building Real-Time Data Pipelines: Stream & Batch Processing workshop SlideBuilding Real-Time Data Pipelines: Stream & Batch Processing workshop Slide
Building Real-Time Data Pipelines: Stream & Batch Processing workshop SlideChristina Lin
 
Building a General PDE Solving Framework with Symbolic-Numeric Scientific Mac...
Building a General PDE Solving Framework with Symbolic-Numeric Scientific Mac...Building a General PDE Solving Framework with Symbolic-Numeric Scientific Mac...
Building a General PDE Solving Framework with Symbolic-Numeric Scientific Mac...stazi3110
 
What is Fashion PLM and Why Do You Need It
What is Fashion PLM and Why Do You Need ItWhat is Fashion PLM and Why Do You Need It
What is Fashion PLM and Why Do You Need ItWave PLM
 
Der Spagat zwischen BIAS und FAIRNESS (2024)
Der Spagat zwischen BIAS und FAIRNESS (2024)Der Spagat zwischen BIAS und FAIRNESS (2024)
Der Spagat zwischen BIAS und FAIRNESS (2024)OPEN KNOWLEDGE GmbH
 
Adobe Marketo Engage Deep Dives: Using Webhooks to Transfer Data
Adobe Marketo Engage Deep Dives: Using Webhooks to Transfer DataAdobe Marketo Engage Deep Dives: Using Webhooks to Transfer Data
Adobe Marketo Engage Deep Dives: Using Webhooks to Transfer DataBradBedford3
 
MYjobs Presentation Django-based project
MYjobs Presentation Django-based projectMYjobs Presentation Django-based project
MYjobs Presentation Django-based projectAnoyGreter
 

Recently uploaded (20)

software engineering Chapter 5 System modeling.pptx
software engineering Chapter 5 System modeling.pptxsoftware engineering Chapter 5 System modeling.pptx
software engineering Chapter 5 System modeling.pptx
 
Automate your Kamailio Test Calls - Kamailio World 2024
Automate your Kamailio Test Calls - Kamailio World 2024Automate your Kamailio Test Calls - Kamailio World 2024
Automate your Kamailio Test Calls - Kamailio World 2024
 
Advancing Engineering with AI through the Next Generation of Strategic Projec...
Advancing Engineering with AI through the Next Generation of Strategic Projec...Advancing Engineering with AI through the Next Generation of Strategic Projec...
Advancing Engineering with AI through the Next Generation of Strategic Projec...
 
Folding Cheat Sheet #4 - fourth in a series
Folding Cheat Sheet #4 - fourth in a seriesFolding Cheat Sheet #4 - fourth in a series
Folding Cheat Sheet #4 - fourth in a series
 
React Server Component in Next.js by Hanief Utama
React Server Component in Next.js by Hanief UtamaReact Server Component in Next.js by Hanief Utama
React Server Component in Next.js by Hanief Utama
 
Cloud Management Software Platforms: OpenStack
Cloud Management Software Platforms: OpenStackCloud Management Software Platforms: OpenStack
Cloud Management Software Platforms: OpenStack
 
GOING AOT WITH GRAALVM – DEVOXX GREECE.pdf
GOING AOT WITH GRAALVM – DEVOXX GREECE.pdfGOING AOT WITH GRAALVM – DEVOXX GREECE.pdf
GOING AOT WITH GRAALVM – DEVOXX GREECE.pdf
 
Steps To Getting Up And Running Quickly With MyTimeClock Employee Scheduling ...
Steps To Getting Up And Running Quickly With MyTimeClock Employee Scheduling ...Steps To Getting Up And Running Quickly With MyTimeClock Employee Scheduling ...
Steps To Getting Up And Running Quickly With MyTimeClock Employee Scheduling ...
 
The Evolution of Karaoke From Analog to App.pdf
The Evolution of Karaoke From Analog to App.pdfThe Evolution of Karaoke From Analog to App.pdf
The Evolution of Karaoke From Analog to App.pdf
 
Cloud Data Center Network Construction - IEEE
Cloud Data Center Network Construction - IEEECloud Data Center Network Construction - IEEE
Cloud Data Center Network Construction - IEEE
 
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
 
Asset Management Software - Infographic
Asset Management Software - InfographicAsset Management Software - Infographic
Asset Management Software - Infographic
 
EY_Graph Database Powered Sustainability
EY_Graph Database Powered SustainabilityEY_Graph Database Powered Sustainability
EY_Graph Database Powered Sustainability
 
Building Real-Time Data Pipelines: Stream & Batch Processing workshop Slide
Building Real-Time Data Pipelines: Stream & Batch Processing workshop SlideBuilding Real-Time Data Pipelines: Stream & Batch Processing workshop Slide
Building Real-Time Data Pipelines: Stream & Batch Processing workshop Slide
 
Hot Sexy call girls in Patel Nagar🔝 9953056974 🔝 escort Service
Hot Sexy call girls in Patel Nagar🔝 9953056974 🔝 escort ServiceHot Sexy call girls in Patel Nagar🔝 9953056974 🔝 escort Service
Hot Sexy call girls in Patel Nagar🔝 9953056974 🔝 escort Service
 
Building a General PDE Solving Framework with Symbolic-Numeric Scientific Mac...
Building a General PDE Solving Framework with Symbolic-Numeric Scientific Mac...Building a General PDE Solving Framework with Symbolic-Numeric Scientific Mac...
Building a General PDE Solving Framework with Symbolic-Numeric Scientific Mac...
 
What is Fashion PLM and Why Do You Need It
What is Fashion PLM and Why Do You Need ItWhat is Fashion PLM and Why Do You Need It
What is Fashion PLM and Why Do You Need It
 
Der Spagat zwischen BIAS und FAIRNESS (2024)
Der Spagat zwischen BIAS und FAIRNESS (2024)Der Spagat zwischen BIAS und FAIRNESS (2024)
Der Spagat zwischen BIAS und FAIRNESS (2024)
 
Adobe Marketo Engage Deep Dives: Using Webhooks to Transfer Data
Adobe Marketo Engage Deep Dives: Using Webhooks to Transfer DataAdobe Marketo Engage Deep Dives: Using Webhooks to Transfer Data
Adobe Marketo Engage Deep Dives: Using Webhooks to Transfer Data
 
MYjobs Presentation Django-based project
MYjobs Presentation Django-based projectMYjobs Presentation Django-based project
MYjobs Presentation Django-based project
 

Build a compiler using C#, Irony and RunSharp.

  • 1. Creating a Compiler with Irony and RunSharp James M. Curran NYC CodeCamp Sept 13, 2014
  • 2. Creating a Compiler with Irony and RunSharp James M. Curran NYC CodeCamp Sept 13, 2014 Brought to you by : MARQUEE SPONSOR
  • 3. Who the Heck am I?  Simple Country Programmer  20+ Years in Software Development  Assembler, C, C++, C#  Worked in Medical, Financial, Online Retailing, and Embedded systems  Microsoft MVP C++ (1994-2004)  Currently Itinerant Programmer at One Call Medical  Write blog: HonestIllusion.com  Designer: NJTheater.Com  Resume'n'stuff: NovelTheory.com
  • 4. Who the Heck am I?  Simple Country Programmer  20+ Years in Software Development  Assembler, C, C++, C#  Worked in Medical, Financial, Online Retailing, and Embedded systems  Microsoft MVP C++ (1994-2004)  Currently Itinerant Programmer at One Call Medical  Write blog: HonestIllusion.com  Designer: NJTheater.Com  Resume'n'stuff: NovelTheory.com Brought to you by PLATINUM SPONSOR
  • 5. Yeah, Comic Sans Deal with it.
  • 6. “Naked Came the Null Delegate” ➲ Collaborative blog story telling a tale of sex, betrayal and .NET coding. ➲ Serialized across the blogs of several noted .NET writers including Charles Petzold and Jon Skeet. ➲ Dormant since 2010, but new writers wanted. ➲ http://nakedcamethenulldelegate.wordpress.com Brought to you by PLATINUM SPONSOR
  • 7. Agenda  The Language  The Parser  The Code Generators (plural)  The Command-line interface. Brought to you by GOLD SPONSORS
  • 8. Shakespeare Programming Language - History  Designed by Jon Åslund and Karl Hasselström in 2001.  The design goal was to make a language with beautiful source code that resembled Shakespeare plays.  Original compiler written in YACC (actually Bison), producing C code.  I wrote the C# compiler in Sept 2013. Apparently I was the first person to touch the code in 12 years.  Since then, Javascript, Python, Perl, and Java versions of been open-sourced and http://shakespearelang.org/ was launched.
  • 9. Variables  Must be the name of an actual character from one of Shakespeare's play.  That’s exactly 152 specific allowable variable names.  Some names are more than one word!  Only data type is an integer, but it can be used for a character.  It's really a stack of integers.
  • 10. Numbers/Constants  Nouns that are “nice” or neutral equal 1.  Nouns that are “not nice” equal -1.  Adjectives (nice or not) multiply by 2.  Examples: “big hairy hound” = 2 * 2 * (+1) = 4 “sorry little codpiece” = 2 * 2 * (-1) = -4  Can be combined with “Sum of ___ and ___”, “Difference between”, “Square of”, “Cube of”  41 neutral, 13 positive, and 25 negative nouns 20 neutral, 36 positive and 32 negative adjectives
  • 11. Input and Output  "Open your heart" outputs the variable's value as a number  "Speak your mind" outputs the corresponding ASCII character.  "Listen to your heart" cause the variable to receive input from the user as a number.  "Open your mind" receive input from a character. Conditional Statements and Gotos  An if/then statement is phrased as a question posed by a character.  The words "as [any adjective] as" represent a test for equality,  "better" and "worse" correspond to greater than and less than  A subsequent line, starting "if so" or "if not," determines what happens in response to the truth or falsehood of the original condition.  A goto statement begins "Let us," "We shall," or "We must," continues "return to" or "proceed to," and then gives an act or scene.
  • 12. Example Outputting Input Reversedly. Othello, a stacky man. Lady Macbeth, who pushes him around till he pops. Act I: The one and only. Scene I: In the beginning, there was nothing. [Enter Othello and Lady Macbeth] Othello: You are nothing! Scene II: Pushing to the very end. Lady Macbeth: Open your mind! Remember yourself. Othello: You are as hard as the sum of yourself and a stone wall. Am I as horrid as a flirt-gill? Lady Macbeth: If not, let us return to scene II. Recall your imminent death!
  • 13. The original compiler Like most languages, specified in Backus–Naur Form (BNF)  Compiler coded in YACC (“Yet Another Compiler Compiler”) (Actually, in GNU’s version BISON) It’s object code (output) is C source code, which would then need to be compiled.
  • 14. BNF & YACC BNF is made up of “Terminals” and “Non-terminal” Terminal symbols are the elementary symbols of the language Non-terminals are made of a combining terminals and other non-terminals. Example: digit = '0'|'1' |'2' |'3' |'4' |'5' |'6' |'7' |'8' |'9‘ integer = ['-'] digit+ YACC is a LALR parser generator. YACC source files are BNF with C code attached to some non-terminals.
  • 15. Original Compiler (excerpt) Play: Title CharacterDeclarationList Act+ CharacterDeclarationList: CharacterDeclaration+ Act: ActHeader Scene+ ActHeader: ACT_ROMAN COLON Comment EndSymbol Constant: ARTICLE UnarticulatedConstant | FIRST_PERSON_POSSESSIVE UnarticulatedConstant | SECOND_PERSON_POSSESSIVE UnarticulatedConstant | THIRD_PERSON_POSSESSIVE UnarticulatedConstant | NOTHING
  • 16. 1st tool: Irony Irony is a development kit for implementing languages on .NET platform. Name is a play on IronPython, IronRuby, IronScheme : “Use Irony to create your own Iron* language” Tries to replicate BNF in C# code via operator overloading. Project home: https://irony.codeplex.com/ Available on nuget: “irony”
  • 17. Irony Example: public class ShakespeareGrammar : InterpretedLanguageGrammar { public ShakespeareGrammar() : base(false) { string[] endSymbols = { ".", "?", "!" }; KeyTerm COLON = ToTerm(":", "colon"); KeyTerm COMMA = ToTerm(","); // : var Act = new NonTerminal("Act"); var Acts = new NonTerminal("Acts"); Acts.Rule = MakePlusRule(Acts, Act); var Play = new NonTerminal("Play"); Play.Rule = Title + CharacterDeclarationList + Acts;
  • 18. Example, cont: var Constant = new NonTerminal("Constant »); Constant.Rule = Article + UnarticulatedConstant | FirstPersonPossessive + UnarticulatedConstant | SecondPersonPossessive + UnarticulatedConstant | ThirdPersonPossessive + UnarticulatedConstant ; UnarticulatedConstant.Rule = PositiveConstant | NegativeConstant; PositiveConstant.Rule = PositiveNoun | PositiveAdjective + PositiveConstant | NeutralAdjective + PositiveConstant; Question.Rule =Be + Value + Comparison + Value + QuestionSymbol;
  • 19. Multi-Word keywords BnfTerm MultiWordTermial(string term) { var parts = term.Split(' '); if (parts.Length == 1) return ToTerm(term); var nonterm = new NonTerminal(term); var expr = new BnfExpression(ToTerm(parts[0])); foreach (var part in parts.Skip(1)) { expr += ToTerm(part); } nonterm.Rule = expr; return nonterm; }
  • 20. Equivalent Keywords NonTerminal BuildTerminal(string name, string filename) { var termList = new NonTerminal(name)); var strm = assembly.GetManifestResourceStream(filename); var sw = new StreamReader(strm); var block = sw.ReadToEnd(); var lines = block.Split('n', 'r'); if (lines.Any()) { var expr = new BnfExpression(MultiWordTermial(lines[0])); foreach (var line in lines.Skip(1)) { if (!String.IsNullOrWhiteSpace(line)) expr |= MultiWordTermial(line); } termList.Rule = expr; } return termList; }
  • 22. Code Generation • Ok, You’ve got a parser. Now what? • Irony documentation drops off here. • Here’s what I learned single-stepping with the debugger.
  • 23. Create AST tree from source. var grammar = new ShakespeareGrammar(); var parser = new Parser(grammar); var text = File.ReadAllText(filename); var tree = parser.Parse(text, filename); var app = new ScriptApp(parser.Language); var thread = new ScriptThread(app); var output= tree.Root.AstNode.Evaluate(thread);
  • 24. Walking the Tree As tree.Root.AstNode.Evaluate(thread) runs, node.DoEvaluate() is called for each node on the tree. By default, AstNode objects are in tree. So we need our own nodes in the tree.
  • 25. ASTNode (Fixed) var Act = new NonTerminal("Act", typeof(ActNode)); var NegativeConstant = new NonTerminal("NegativeConstant", typeof(NegativeConstantNode)); public class NegativeConstantNode : AstNode { protected override object DoEvaluate(ScriptThread thread) { var tw = thread.tc().Writer; if (AstNode1 is NegativeNounNode) return "(-1)"; else return string.Format("2*{0}", AstNode2.ToString(thread)); } }
  • 26. public class PlayNode : AstNode { protected override object DoEvaluate(Irony.Interpreter.ScriptThread thread) { var sw = thread.tc().Writer; sw.WriteLine("using System;"); sw.WriteLine("using Shakespeare.Support;"); sw.WriteLine(); sw.WriteLine("namespace Shakespeare.Program"); sw.WriteLine("{"); sw.WriteLine("tclass Program"); sw.WriteLine("t{"); sw.WriteLine("ttstatic void Main(string[] args) {"); sw.WriteLine("tttvar script = new Script();"); sw.WriteLine("tttscript.Action();"); sw.WriteLine("tt}"); sw.WriteLine("t}"); sw.WriteLine("ttclass Script : Dramaturge {"); sw.WriteLine("ttpublic Script()"); sw.WriteLine("tt : base(Console.In, Console.Out)"); sw.WriteLine("tt{ }"); sw.WriteLine(); sw.WriteLine("ttpublic void Action()"); sw.WriteLine("tt{"); AstNode1.Evaluate(thread); // Title sw.WriteLine(); var cdl = AstNode2 as CharacterDeclarationListNode; foreach (var ch in cdl.Characters) ch.Evaluate(thread); sw.WriteLine(); AstNode3.Evaluate(thread); sw.WriteLine("tt}"); sw.WriteLine("t}"); sw.WriteLine("}"); sw.Flush(); sw.Close(); return sw; } }
  • 27. A second code generator That works fine for if you only need one code generator. But I wanted to write a C code generator, a C# code generator and a MSIL code generator. {more digging with debugger} I’ve got great tool from switching between several generators – Check the github…..
  • 28. 2nd tool: RunSharp RunSharp is a layer above the standard .NET Reflection.Emit API, allowing to generate/compile dynamic code at runtime very quickly and efficiently (unlike using CodeDOM and invoking the C# compiler). Project home : https://code.google.com/p/runsharp/ (but it’s stagnant, so check github for forks) Not on Nuget.
  • 29. public class PlayNode : AstNode { protected override object DoEvaluate(Irony.Interpreter.ScriptThread thread) { var rs = thread.rs(); var ag = rs.AssemblyGen; using (ag.Namespace("Shakespeare.Program")) { TypeGen scriptClass = ag.Public.Class("Script", typeof(Shakespeare.Support.Dramaturge)); { rs.Script = scriptClass; var console = typeof(Console); CodeGen ctor = scriptClass.Public.Constructor(); ctor.InvokeBase(Static.Property(console, "In"), Static.Property(console, "Out")); { } CodeGen action = scriptClass.Public.Void("Action"); { rs.Action = action; action.At(Span); AstNode1.Evaluate(thread); var cdl = AstNode2 as CharacterDeclarationListNode; foreach (var ch in cdl.Characters) ch.Evaluate(thread); AstNode3.Evaluate(thread); } } scriptClass.Complete(); TypeGen MyClass = ag.Public.Class("Program"); CodeGen Main = MyClass.Public.Static.Void("Main").Parameter<string[]>("args"); { var script = Main.Local(Exp.New(scriptClass.GetCompletedType())); Main.Invoke(script, "Action"); } } ag.Save(); return ag.GetAssembly().GetName().Name; } }
  • 30. public class NegativeConstantNode : AstNode { protected override object DoEvaluate(ScriptThread thread) { if (AstNode1 is NegativeNounNode) return ((Operand) 0- 1); else return (AstNode2.Evaluate(thread) as Operand) * 2; } }