1 2 23 24 25 package org.javacc.jjdoc; 26 27 import java.io.PrintWriter; 28 import java.util.Vector; 29 import java.util.Enumeration; 30 import java.util.Stack; 31 32 import org.javacc.parser.*; 33 34 35 public class JJDoc extends JavaCCGlobals { 36 37 40 static void start() { 41 PrintWriter pw = create_output_stream(); 42 43 Generator gen; 44 45 if (Options.B("TEXT")) { 46 gen = new Generator(pw); 47 } else { 48 gen = new HTMLGenerator(pw); 49 } 50 gen.documentStart(); 51 emitTokenProductions(gen, rexprlist); 52 emitNormalProductions(gen, bnfproductions); 53 gen.documentEnd(); 54 55 pw.close(); 56 } 57 58 59 private static Token getPrecedingSpecialToken(Token tok) { 60 Token t = tok; 61 while (t.specialToken != null) { 62 t = t.specialToken; 63 } 64 return (t != tok) ? t : null; 65 } 66 67 private static void emitTopLevelSpecialTokens(Token tok, Generator gen) { 68 if (tok == null) { 69 return; 71 } 72 73 tok = getPrecedingSpecialToken(tok); 74 String s = ""; 75 if (tok != null) { 76 cline = tok.beginLine; 77 ccol = tok.beginColumn; 78 while (tok != null) { 79 s += printTokenOnly(tok); 80 tok = tok.next; 81 } 82 } 83 gen.specialTokens(s); 84 } 85 86 87 private static boolean toplevelExpansion(Expansion exp) { 88 return exp.parent != null 89 && ( (exp.parent instanceof NormalProduction) 90 || 91 (exp.parent instanceof TokenProduction) 92 ); 93 } 94 95 96 private static void emitTokenProductions(Generator gen, Vector prods) { 97 for (Enumeration enum = prods.elements(); enum.hasMoreElements();) { 99 TokenProduction tp = (TokenProduction)enum.nextElement(); 100 102 123 125 129 } 137 } 139 140 141 private static void emitNormalProductions(Generator gen, Vector prods) { 142 gen.nonterminalsStart(); 143 for (Enumeration enum = prods.elements(); enum.hasMoreElements();) { 144 NormalProduction np = (NormalProduction)enum.nextElement(); 145 146 emitTopLevelSpecialTokens(np.firstToken, gen); 147 148 if (np instanceof BNFProduction) { 149 gen.productionStart(np); 150 if (np.expansion instanceof Choice) { 151 boolean first = true; 152 Choice c = (Choice)np.expansion; 153 for (java.util.Enumeration enume = c.choices.elements(); 154 enume.hasMoreElements();) { 155 Expansion e = (Expansion)(enume.nextElement()); 156 gen.expansionStart(e, first); 157 emitExpansionTree(e, gen); 158 gen.expansionEnd(e, first); 159 first = false; 160 } 161 } else { 162 gen.expansionStart(np.expansion, true); 163 emitExpansionTree(np.expansion, gen); 164 gen.expansionEnd(np.expansion, true); 165 } 166 gen.productionEnd(np); 167 } else if (np instanceof JavaCodeProduction) { 168 gen.javacode((JavaCodeProduction)np); 169 } 170 } 171 gen.nonterminalsEnd(); 172 } 173 174 175 private static void emitExpansionTree(Expansion exp, Generator gen) { 176 if (exp instanceof Action) { 178 emitExpansionAction((Action)exp, gen); 179 } else if (exp instanceof Choice) { 180 emitExpansionChoice((Choice)exp, gen); 181 } else if (exp instanceof Lookahead) { 182 emitExpansionLookahead((Lookahead)exp, gen); 183 } else if (exp instanceof NonTerminal) { 184 emitExpansionNonTerminal((NonTerminal)exp, gen); 185 } else if (exp instanceof OneOrMore) { 186 emitExpansionOneOrMore((OneOrMore)exp, gen); 187 } else if (exp instanceof RegularExpression) { 188 emitExpansionRegularExpression((RegularExpression)exp, gen); 189 } else if (exp instanceof Sequence) { 190 emitExpansionSequence((Sequence)exp, gen); 191 } else if (exp instanceof TryBlock) { 192 emitExpansionTryBlock((TryBlock)exp, gen); 193 } else if (exp instanceof ZeroOrMore) { 194 emitExpansionZeroOrMore((ZeroOrMore)exp, gen); 195 } else if (exp instanceof ZeroOrOne) { 196 emitExpansionZeroOrOne((ZeroOrOne)exp, gen); 197 } else { 198 System.out.println("Oops: Unknown expansion type."); 199 } 200 } 202 203 204 private static void emitExpansionAction(Action a, Generator gen) { 205 } 206 207 private static void emitExpansionChoice(Choice c, Generator gen) { 208 for (java.util.Enumeration enum = c.choices.elements(); 209 enum.hasMoreElements();) { 210 Expansion e = (Expansion)(enum.nextElement()); 211 emitExpansionTree(e, gen); 212 if (enum.hasMoreElements()) { 213 gen.text(" | "); 214 } 215 } 216 } 217 218 private static void emitExpansionLookahead(Lookahead l, Generator gen) { 219 } 220 221 private static void emitExpansionNonTerminal(NonTerminal nt, Generator gen) { 222 gen.nonTerminalStart(nt); 223 gen.text(nt.name); 224 gen.nonTerminalEnd(nt); 225 } 226 227 private static void emitExpansionOneOrMore(OneOrMore o, Generator gen) { 228 gen.text("( "); 229 emitExpansionTree(o.expansion, gen); 230 gen.text(" )+"); 231 } 232 233 private static void emitExpansionRegularExpression(RegularExpression r, 234 Generator gen) { 235 gen.reStart(r); 236 emitRE(r, gen); 237 gen.reEnd(r); 238 } 239 240 private static void emitExpansionSequence(Sequence s, Generator gen) { 241 boolean firstUnit = true; 242 for (java.util.Enumeration enum = s.units.elements(); 243 enum.hasMoreElements();) { 244 Expansion e = (Expansion)enum.nextElement(); 245 246 if (e instanceof Lookahead || e instanceof Action) { 247 continue; 248 } 249 250 if (!firstUnit) { 251 gen.text(" "); 252 } 253 254 boolean needParens = (e instanceof Choice) || (e instanceof Sequence); 255 if (needParens) { 256 gen.text("( "); 257 } 258 emitExpansionTree(e, gen); 259 if (needParens) { 260 gen.text(" )"); 261 } 262 263 firstUnit = false; 264 } 265 } 266 267 private static void emitExpansionTryBlock(TryBlock t, Generator gen) { 268 boolean needParens = t.exp instanceof Choice; 269 if (needParens) { 270 gen.text("( "); 271 } 272 emitExpansionTree(t.exp, gen); 273 if (needParens) { 274 gen.text(" )"); 275 } 276 } 277 278 private static void emitExpansionZeroOrMore(ZeroOrMore z, Generator gen) { 279 gen.text("( "); 280 emitExpansionTree(z.expansion, gen); 281 gen.text(" )*"); 282 } 283 284 private static void emitExpansionZeroOrOne(ZeroOrOne z, Generator gen) { 285 gen.text("( "); 286 emitExpansionTree(z.expansion, gen); 287 gen.text(" )?"); 288 } 289 290 291 private static void emitRE(RegularExpression re, Generator gen) { 292 boolean hasLabel = !re.label.equals(""); 293 boolean justName = re instanceof RJustName; 294 boolean eof = re instanceof REndOfFile; 295 boolean isString = re instanceof RStringLiteral; 296 boolean toplevelRE = (re.tpContext != null); 297 298 boolean needBrackets 299 = justName || eof || hasLabel || (!isString && toplevelRE); 300 301 if (needBrackets) { 302 gen.text("<"); 303 if (!justName) { 304 if (re.private_rexp) { 305 gen.text("#"); 306 } 307 if (hasLabel) { 308 gen.text(re.label); 309 gen.text(": "); 310 } 311 } 312 } 313 314 if (re instanceof RCharacterList) { 315 RCharacterList cl = (RCharacterList)re; 316 if (cl.negated_list) { 317 gen.text("~"); 318 } 319 gen.text("["); 320 for (java.util.Enumeration enum = cl.descriptors.elements(); 321 enum.hasMoreElements();) { 322 Object o = enum.nextElement(); 323 if (o instanceof SingleCharacter) { 324 gen.text("\""); 325 char s[] = { ((SingleCharacter)o).ch }; 326 gen.text(add_escapes(new String(s))); 327 gen.text("\""); 328 } else if (o instanceof CharacterRange) { 329 gen.text("\""); 330 char s[] = { ((CharacterRange)o).left }; 331 gen.text(add_escapes(new String(s))); 332 gen.text("\"-\""); 333 s[0] = ((CharacterRange)o).right; 334 gen.text(add_escapes(new String(s))); 335 gen.text("\""); 336 } else { 337 System.out.println("Oops: unknown character list element type."); 338 } 339 if (enum.hasMoreElements()) { 340 gen.text(","); 341 } 342 } 343 gen.text("]"); 344 345 } else if (re instanceof RChoice) { 346 RChoice c = (RChoice)re; 347 for (java.util.Enumeration enum = c.choices.elements(); 348 enum.hasMoreElements();) { 349 RegularExpression sub = (RegularExpression)(enum.nextElement()); 350 emitRE(sub, gen); 351 if (enum.hasMoreElements()) { 352 gen.text(" | "); 353 } 354 } 355 356 } else if (re instanceof REndOfFile) { 357 gen.text("EOF"); 358 359 } else if (re instanceof RJustName) { 360 RJustName jn = (RJustName)re; 361 gen.text(jn.label); 362 363 } else if (re instanceof ROneOrMore) { 364 ROneOrMore om = (ROneOrMore)re; 365 gen.text("("); 366 emitRE(om.regexpr, gen); 367 gen.text(")+"); 368 369 } else if (re instanceof RSequence) { 370 RSequence s = (RSequence)re; 371 for (java.util.Enumeration enum = s.units.elements(); 372 enum.hasMoreElements();) { 373 RegularExpression sub = (RegularExpression)(enum.nextElement()); 374 boolean needParens = false; 375 if (sub instanceof RChoice) { 376 needParens = true; 377 } 378 if (needParens) { 379 gen.text("("); 380 } 381 emitRE(sub, gen); 382 if (needParens) { 383 gen.text(")"); 384 } 385 if (enum.hasMoreElements()) { 386 gen.text(" "); 387 } 388 } 389 390 } else if (re instanceof RStringLiteral) { 391 RStringLiteral sl = (RStringLiteral)re; 392 gen.text("\"" + JavaCCParserInternals.add_escapes(sl.image) + "\""); 393 394 } else if (re instanceof RZeroOrMore) { 395 RZeroOrMore zm = (RZeroOrMore)re; 396 gen.text("("); 397 emitRE(zm.regexpr, gen); 398 gen.text(")*"); 399 400 } else if (re instanceof RZeroOrOne) { 401 RZeroOrOne zo = (RZeroOrOne)re; 402 gen.text("("); 403 emitRE(zo.regexpr, gen); 404 gen.text(")?"); 405 406 } else { 407 System.out.println("Oops: Unknown regular expression type."); 408 } 409 410 if (needBrackets) { 411 gen.text(">"); 412 } 413 } 414 415 416 private static String v2s(Vector v, boolean newLine) { 417 String s = ""; 418 boolean firstToken = true; 419 for (Enumeration enum = v.elements(); enum.hasMoreElements();) { 420 Token tok = (Token)enum.nextElement(); 421 Token stok = getPrecedingSpecialToken(tok); 422 423 if (firstToken) { 424 if (stok != null) { 425 cline = stok.beginLine; 426 ccol = stok.beginColumn; 427 } else { 428 cline = tok.beginLine; 429 ccol = tok.beginColumn; 430 } 431 s = ws(ccol - 1); 432 firstToken = false; 433 } 434 while (stok != null) { 435 s += printToken(stok); 436 stok = stok.next; 437 } 438 s += printToken(tok); 439 } 440 return s; 441 } 442 443 444 449 private static PrintWriter create_output_stream() { 450 PrintWriter ostr; 451 452 if (Options.S("OUTPUT_FILE").equals("")) { 453 if (JJDocGlobals.input_file.equals("standard input")) { 454 return new java.io.PrintWriter(new java.io.OutputStreamWriter(System.out)); 455 } else { 456 String ext = ".html"; 457 if (Options.B("TEXT")) { 458 ext = ".txt"; 459 } 460 int i = JJDocGlobals.input_file.lastIndexOf('.'); 461 if (i == -1) { 462 JJDocGlobals.output_file = JJDocGlobals.input_file + ext; 463 } else { 464 String suffix = JJDocGlobals.input_file.substring(i); 465 if (suffix.equals(ext)) { 466 JJDocGlobals.output_file = JJDocGlobals.input_file + ext; 467 } else { 468 JJDocGlobals.output_file = JJDocGlobals.input_file.substring(0, i) + ext; 469 } 470 } 471 } 472 } else { 473 JJDocGlobals.output_file = Options.S("OUTPUT_FILE"); 474 } 475 476 try { 477 ostr = new java.io.PrintWriter(new java.io.FileWriter(JJDocGlobals.output_file)); 478 } catch (java.io.IOException e) { 479 System.err.println("JJDoc: can't open output stream on file " + 480 JJDocGlobals.output_file + ". Using standard output."); 481 ostr = new java.io.PrintWriter(new java.io.OutputStreamWriter(System.out)); 482 } 483 484 return ostr; 485 } 486 487 488 491 private static String ws(int len) { 492 String s = ""; 493 for (int i = 0; i < len; ++i) { 494 s += " "; 495 } 496 return s; 497 } 498 499 500 } 501 502 | Popular Tags |