1 /** 2 * Compiler implementation of the 3 * $(LINK2 http://www.dlang.org, D programming language). 4 * 5 * Copyright: Copyright (c) 1999-2016 by Digital Mars, All Rights Reserved 6 * Authors: $(LINK2 http://www.digitalmars.com, Walter Bright) 7 * License: $(LINK2 http://www.boost.org/LICENSE_1_0.txt, Boost License 1.0) 8 * Source: $(DMDSRC _dversion.d) 9 */ 10 11 module ddmd.dversion; 12 13 import ddmd.arraytypes; 14 import ddmd.cond; 15 import ddmd.dmodule; 16 import ddmd.dscope; 17 import ddmd.dsymbol; 18 import ddmd.globals; 19 import ddmd.identifier; 20 import ddmd.root.outbuffer; 21 import ddmd.visitor; 22 23 /*********************************************************** 24 * DebugSymbol's happen for statements like: 25 * debug = identifier; 26 * debug = integer; 27 */ 28 extern (C++) final class DebugSymbol : Dsymbol 29 { 30 uint level; 31 32 extern (D) this(Loc loc, Identifier ident) 33 { 34 super(ident); 35 this.loc = loc; 36 } 37 38 extern (D) this(Loc loc, uint level) 39 { 40 this.level = level; 41 this.loc = loc; 42 } 43 44 override Dsymbol syntaxCopy(Dsymbol s) 45 { 46 assert(!s); 47 auto ds = new DebugSymbol(loc, ident); 48 ds.level = level; 49 return ds; 50 } 51 52 override const(char)* toChars() const 53 { 54 if (ident) 55 return ident.toChars(); 56 else 57 { 58 OutBuffer buf; 59 buf.printf("%d", level); 60 return buf.extractString(); 61 } 62 } 63 64 override void addMember(Scope* sc, ScopeDsymbol sds) 65 { 66 //printf("DebugSymbol::addMember('%s') %s\n", sds->toChars(), toChars()); 67 Module m = sds.isModule(); 68 // Do not add the member to the symbol table, 69 // just make sure subsequent debug declarations work. 70 if (ident) 71 { 72 if (!m) 73 { 74 error("declaration must be at module level"); 75 errors = true; 76 } 77 else 78 { 79 if (findCondition(m.debugidsNot, ident)) 80 { 81 error("defined after use"); 82 errors = true; 83 } 84 if (!m.debugids) 85 m.debugids = new Strings(); 86 m.debugids.push(ident.toChars()); 87 } 88 } 89 else 90 { 91 if (!m) 92 { 93 error("level declaration must be at module level"); 94 errors = true; 95 } 96 else 97 m.debuglevel = level; 98 } 99 } 100 101 override void semantic(Scope* sc) 102 { 103 //printf("DebugSymbol::semantic() %s\n", toChars()); 104 } 105 106 override const(char)* kind() const 107 { 108 return "debug"; 109 } 110 111 override void accept(Visitor v) 112 { 113 v.visit(this); 114 } 115 } 116 117 /*********************************************************** 118 * VersionSymbol's happen for statements like: 119 * version = identifier; 120 * version = integer; 121 */ 122 extern (C++) final class VersionSymbol : Dsymbol 123 { 124 uint level; 125 126 extern (D) this(Loc loc, Identifier ident) 127 { 128 super(ident); 129 this.loc = loc; 130 } 131 132 extern (D) this(Loc loc, uint level) 133 { 134 this.level = level; 135 this.loc = loc; 136 } 137 138 override Dsymbol syntaxCopy(Dsymbol s) 139 { 140 assert(!s); 141 auto ds = new VersionSymbol(loc, ident); 142 ds.level = level; 143 return ds; 144 } 145 146 override const(char)* toChars() 147 { 148 if (ident) 149 return ident.toChars(); 150 else 151 { 152 OutBuffer buf; 153 buf.printf("%d", level); 154 return buf.extractString(); 155 } 156 } 157 158 override void addMember(Scope* sc, ScopeDsymbol sds) 159 { 160 //printf("VersionSymbol::addMember('%s') %s\n", sds->toChars(), toChars()); 161 Module m = sds.isModule(); 162 // Do not add the member to the symbol table, 163 // just make sure subsequent debug declarations work. 164 if (ident) 165 { 166 VersionCondition.checkReserved(loc, ident.toString()); 167 if (!m) 168 { 169 error("declaration must be at module level"); 170 errors = true; 171 } 172 else 173 { 174 if (findCondition(m.versionidsNot, ident)) 175 { 176 error("defined after use"); 177 errors = true; 178 } 179 if (!m.versionids) 180 m.versionids = new Strings(); 181 m.versionids.push(ident.toChars()); 182 } 183 } 184 else 185 { 186 if (!m) 187 { 188 error("level declaration must be at module level"); 189 errors = true; 190 } 191 else 192 m.versionlevel = level; 193 } 194 } 195 196 override void semantic(Scope* sc) 197 { 198 } 199 200 override const(char)* kind() const 201 { 202 return "version"; 203 } 204 205 override void accept(Visitor v) 206 { 207 v.visit(this); 208 } 209 }