summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRobert Griesemer <gri@golang.org>2008-12-09 15:29:15 -0800
committerRobert Griesemer <gri@golang.org>2008-12-09 15:29:15 -0800
commit4d1ed91f80b9d86053f9828e5b5328da87eca49f (patch)
tree27cd4038c030c05dd5af84ba5c5a88a2ae2ad52e
parent9069efb250a3747f751a6bb1f89615a8846a6cc0 (diff)
downloadgolang-4d1ed91f80b9d86053f9828e5b5328da87eca49f.tar.gz
- snapshot if current state
- fix pretty printer to work with new tabwriter interface R=r OCL=20854 CL=20854
-rw-r--r--usr/gri/pretty/htmlwriter.go42
-rw-r--r--usr/gri/pretty/printer.go45
-rw-r--r--usr/gri/pretty/untab.go2
3 files changed, 62 insertions, 27 deletions
diff --git a/usr/gri/pretty/htmlwriter.go b/usr/gri/pretty/htmlwriter.go
index 0e4cf6a4e..0a65d108c 100644
--- a/usr/gri/pretty/htmlwriter.go
+++ b/usr/gri/pretty/htmlwriter.go
@@ -7,13 +7,13 @@ package htmlwriter
import (
"os";
"io";
- "array";
- "utf8";
+ "fmt";
)
// Writer is a filter implementing the io.Write interface.
// It provides facilities to generate HTML tags and does
-// proper HTML-escaping for text written through it.
+// HTML-escaping for text written through Write. Incoming
+// text is assumed to be UTF-8 encoded.
export type Writer struct {
// TODO should not export any of the fields
@@ -27,17 +27,43 @@ func (b *Writer) Init(writer io.Write) *Writer {
}
-/* export */ func (b *Writer) Flush() *os.Error {
- return nil;
+/* export */ func (p *Writer) Write(buf *[]byte) (written int, err *os.Error) {
+ i0 := 0;
+ for i := i0; i < len(buf); i++ {
+ var s string;
+ switch buf[i] {
+ case '<': s = "&lt;";
+ case '&': s = "&amp;";
+ default: continue;
+ }
+ // write HTML escape instead of buf[i]
+ w1, e1 := p.writer.Write(buf[i0 : i]);
+ if e1 != nil {
+ return i0 + w1, e1;
+ }
+ w2, e2 := io.WriteString(p.writer, s);
+ if e2 != nil {
+ return i0 + w1 /* not w2! */, e2;
+ }
+ i0 = i + 1;
+ }
+ written, err = p.writer.Write(buf[i0 : len(buf)]);
+ return len(buf), err;
}
-/* export */ func (b *Writer) Write(buf *[]byte) (written int, err *os.Error) {
- written, err = b.writer.Write(buf); // BUG 6g - should just have return
- return written, err;
+// ----------------------------------------------------------------------------
+// HTML-specific interface
+
+/* export */ func (p *Writer) Tag(s string) {
+ // TODO proper error handling
+ io.WriteString(p.writer, s);
}
+// ----------------------------------------------------------------------------
+//
+
export func New(writer io.Write) *Writer {
return new(Writer).Init(writer);
}
diff --git a/usr/gri/pretty/printer.go b/usr/gri/pretty/printer.go
index 5114a6d2a..f8d29f046 100644
--- a/usr/gri/pretty/printer.go
+++ b/usr/gri/pretty/printer.go
@@ -6,6 +6,7 @@ package Printer
import (
"os";
+ "io";
"array";
"tabwriter";
"flag";
@@ -55,7 +56,8 @@ const (
type Printer struct {
// output
- writer *htmlwriter.Writer;
+ text io.Write;
+ tags *htmlwriter.Writer;
// comments
comments *array.Array; // the list of all comments
@@ -92,9 +94,10 @@ func (P *Printer) NextComment() {
}
-func (P *Printer) Init(writer *htmlwriter.Writer, comments *array.Array) {
- // writer
- P.writer = writer;
+func (P *Printer) Init(text io.Write, tags *htmlwriter.Writer, comments *array.Array) {
+ // writers
+ P.text = text;
+ P.tags = tags;
// comments
P.comments = comments;
@@ -109,7 +112,7 @@ func (P *Printer) Init(writer *htmlwriter.Writer, comments *array.Array) {
// Printing support
func (P *Printer) Printf(format string, s ...) {
- n, err := fmt.fprintf(P.writer, format, s);
+ n, err := fmt.fprintf(P.text, format, s);
if err != nil {
panic("print error - exiting");
}
@@ -311,11 +314,10 @@ func (P *Printer) Error(pos int, tok int, msg string) {
// ----------------------------------------------------------------------------
// HTML support
-// TODO Move this to html writer
func (P *Printer) HtmlPrologue(title string) {
- if html.BVal() {
- P.String(0,
+ if P.tags != nil {
+ P.tags.Tag(
"<html>\n"
"<head>\n"
" <META HTTP-EQUIV=\"Content-Type\" CONTENT=\"text/html; charset=UTF-8\">\n"
@@ -331,8 +333,8 @@ func (P *Printer) HtmlPrologue(title string) {
func (P *Printer) HtmlEpilogue() {
- if html.BVal() {
- P.String(0,
+ if P.tags != nil {
+ P.tags.Tag(
"</pre>\n"
"</body>\n"
"<html>\n"
@@ -342,8 +344,8 @@ func (P *Printer) HtmlEpilogue() {
func (P *Printer) HtmlIdentifier(pos int, ident string) {
- if html.BVal() {
- P.String(pos, `<a href="#` + ident + `">` + ident + `</a>`);
+ if false && P.tags != nil {
+ P.tags.Tag(`<a href="#` + ident + `">` + ident + `</a>`);
} else {
P.String(pos, ident);
}
@@ -831,20 +833,27 @@ func (P *Printer) Program(p *AST.Program) {
export func Print(prog *AST.Program) {
// setup
+ var P Printer;
padchar := byte(' ');
if usetabs.BVal() {
padchar = '\t';
}
- twriter := tabwriter.New(os.Stdout, int(tabwidth.IVal()), 1, padchar, true);
- hwriter := htmlwriter.New(twriter);
- var P Printer;
- P.Init(hwriter, prog.comments);
+ var (
+ text = tabwriter.New(os.Stdout, int(tabwidth.IVal()), 1, padchar, true, html.BVal());
+ tags *htmlwriter.Writer;
+ )
+ if html.BVal() {
+ tags = htmlwriter.New(text);
+ }
+ P.Init(text, tags, prog.comments);
P.HtmlPrologue("<the source>");
P.Program(prog);
P.HtmlEpilogue();
P.String(0, ""); // flush pending separator/newlines
- hwriter.Flush(); // ignore errors
- twriter.Flush(); // ignore errors
+ err := text.Flush();
+ if err != nil {
+ panic("print error - exiting");
+ }
}
diff --git a/usr/gri/pretty/untab.go b/usr/gri/pretty/untab.go
index af4814c1d..3098c9e6e 100644
--- a/usr/gri/pretty/untab.go
+++ b/usr/gri/pretty/untab.go
@@ -40,7 +40,7 @@ func main() {
if usetabs.BVal() {
padchar = '\t';
}
- dst := tabwriter.New(os.Stdout, int(tabwidth.IVal()), 1, padchar, true);
+ dst := tabwriter.New(os.Stdout, int(tabwidth.IVal()), 1, padchar, true, false);
if flag.NArg() > 0 {
for i := 0; i < flag.NArg(); i++ {
name := flag.Arg(i);