1b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru/* 2b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * [The "BSD license"] 3fceb39872958b9fa2505e63f8b8699a9e0f882f4ccornelius * Copyright (c) 2005-2008 Terence Parr 4b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * All rights reserved. 5b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * 6b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * Conversion to C#: 7b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * Copyright (c) 2008-2010 Sam Harwell, Pixel Mine, Inc. 8b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * All rights reserved. 9b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * 10b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * Redistribution and use in source and binary forms, with or without 11b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * modification, are permitted provided that the following conditions 12b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * are met: 13b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * 1. Redistributions of source code must retain the above copyright 14b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * notice, this list of conditions and the following disclaimer. 15b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * 2. Redistributions in binary form must reproduce the above copyright 16b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * notice, this list of conditions and the following disclaimer in the 17b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * documentation and/or other materials provided with the distribution. 18b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * 3. The name of the author may not be used to endorse or promote products 19b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * derived from this software without specific prior written permission. 20b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * 21b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 22b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 23b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 24b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 25b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 2683a171d1a62abf406f7f44ae671823d5ec20db7dCraig Cornelius * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 27b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 28b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 29b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 30b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 31b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru */ 32b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 33b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Querupackage org.antlr.codegen; 34b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 35b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport org.antlr.Tool; 36b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport org.antlr.tool.Grammar; 37b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport org.stringtemplate.v4.AttributeRenderer; 38b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport org.stringtemplate.v4.ST; 39b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 40b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport java.io.IOException; 41b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport java.util.HashMap; 42b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport java.util.HashSet; 43b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport java.util.Locale; 44b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruimport java.util.Map; 45b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 46b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Querupublic class CSharp3Target extends Target { 47b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru private static final HashSet<String> _languageKeywords = new HashSet<String>() 48b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru {{ 49b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("abstract"); add("event"); add("new"); add("struct"); 50b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("as"); add("explicit"); add("null"); add("switch"); 51b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("base"); add("extern"); add("object"); add("this"); 52b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("bool"); add("false"); add("operator"); add("throw"); 53b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("break"); add("finally"); add("out"); add("true"); 54b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("byte"); add("fixed"); add("override"); add("try"); 55b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("case"); add("float"); add("params"); add("typeof"); 56b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("catch"); add("for"); add("private"); add("uint"); 57b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("char"); add("foreach"); add("protected"); add("ulong"); 58b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("checked"); add("goto"); add("public"); add("unchecked"); 59b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("class"); add("if"); add("readonly"); add("unsafe"); 60b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("const"); add("implicit"); add("ref"); add("ushort"); 61b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("continue"); add("in"); add("return"); add("using"); 62b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("decimal"); add("int"); add("sbyte"); add("virtual"); 63b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("default"); add("interface"); add("sealed"); add("volatile"); 64b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("delegate"); add("internal"); add("short"); add("void"); 65b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("do"); add("is"); add("sizeof"); add("while"); 66b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("double"); add("lock"); add("stackalloc"); 67b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("else"); add("long"); add("static"); 68b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru add("enum"); add("namespace"); add("string"); 69b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru }}; 70b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 71b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru @Override 72b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru public String encodeIntAsCharEscape(int v) { 73b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return "\\x" + Integer.toHexString(v).toUpperCase(); 74b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 75b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 76b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru @Override 77b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru public String getTarget64BitStringFromValue(long word) { 78b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return "0x" + Long.toHexString(word).toUpperCase(); 79b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 80b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 81b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru @Override 82b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru protected void genRecognizerFile(Tool tool, CodeGenerator generator, Grammar grammar, ST outputFileST) throws IOException 83b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru { 84b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (!grammar.getGrammarIsRoot()) 85b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru { 86b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru Grammar rootGrammar = grammar.composite.getRootGrammar(); 87b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru String actionScope = grammar.getDefaultActionScope(grammar.type); 88b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru Map<String, Object> actions = rootGrammar.getActions().get(actionScope); 89b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru Object rootNamespace = actions != null ? actions.get("namespace") : null; 90b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (actions != null && rootNamespace != null) 91b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru { 92b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru actions = grammar.getActions().get(actionScope); 93b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (actions == null) 94b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru { 95b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru actions = new HashMap<String, Object>(); 96b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru grammar.getActions().put(actionScope, actions); 97b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 98b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 99b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru actions.put("namespace", rootNamespace); 100b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 101b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 102b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 103b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru generator.getTemplates().registerRenderer(String.class, new StringRenderer(generator, this)); 104b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru super.genRecognizerFile(tool, generator, grammar, outputFileST); 105b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 106b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 107b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru public static class StringRenderer implements AttributeRenderer 108b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru { 109b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru private final CodeGenerator _generator; 110b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru private final CSharp3Target _target; 111b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 112b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru public StringRenderer(CodeGenerator generator, CSharp3Target target) 113b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru { 114b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru _generator = generator; 115b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru _target = target; 116b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 117b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 118b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru public String toString(Object obj, String formatName, Locale locale) 119b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru { 120b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru String value = (String)obj; 121b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (value == null || formatName == null) 122b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return value; 123b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 124b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (formatName.equals("id")) { 125b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (_languageKeywords.contains(value)) 126b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return "@" + value; 127b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 128b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return value; 129b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } else if (formatName.equals("cap")) { 130b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return Character.toUpperCase(value.charAt(0)) + value.substring(1); 131b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } else if (formatName.equals("string")) { 132b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return _target.getTargetStringLiteralFromString(value, true); 133b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } else { 134b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru throw new IllegalArgumentException("Unsupported format name: '" + formatName + "'"); 135b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 136b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 137b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 138b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru} 139b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 140b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru