github.com/spotify/syslog-redirector-golang@v0.0.0-20140320174030-4859f03d829a/src/pkg/fmt/fmt_test.go (about)

     1  // Copyright 2009 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package fmt_test
     6  
     7  import (
     8  	"bytes"
     9  	. "fmt"
    10  	"io"
    11  	"math"
    12  	"runtime"
    13  	"strings"
    14  	"testing"
    15  	"time"
    16  	"unicode"
    17  )
    18  
    19  type (
    20  	renamedBool       bool
    21  	renamedInt        int
    22  	renamedInt8       int8
    23  	renamedInt16      int16
    24  	renamedInt32      int32
    25  	renamedInt64      int64
    26  	renamedUint       uint
    27  	renamedUint8      uint8
    28  	renamedUint16     uint16
    29  	renamedUint32     uint32
    30  	renamedUint64     uint64
    31  	renamedUintptr    uintptr
    32  	renamedString     string
    33  	renamedBytes      []byte
    34  	renamedFloat32    float32
    35  	renamedFloat64    float64
    36  	renamedComplex64  complex64
    37  	renamedComplex128 complex128
    38  )
    39  
    40  func TestFmtInterface(t *testing.T) {
    41  	var i1 interface{}
    42  	i1 = "abc"
    43  	s := Sprintf("%s", i1)
    44  	if s != "abc" {
    45  		t.Errorf(`Sprintf("%%s", empty("abc")) = %q want %q`, s, "abc")
    46  	}
    47  }
    48  
    49  const b32 uint32 = 1<<32 - 1
    50  const b64 uint64 = 1<<64 - 1
    51  
    52  var array = [5]int{1, 2, 3, 4, 5}
    53  var iarray = [4]interface{}{1, "hello", 2.5, nil}
    54  var slice = array[:]
    55  var islice = iarray[:]
    56  
    57  type A struct {
    58  	i int
    59  	j uint
    60  	s string
    61  	x []int
    62  }
    63  
    64  type I int
    65  
    66  func (i I) String() string { return Sprintf("<%d>", int(i)) }
    67  
    68  type B struct {
    69  	I I
    70  	j int
    71  }
    72  
    73  type C struct {
    74  	i int
    75  	B
    76  }
    77  
    78  type F int
    79  
    80  func (f F) Format(s State, c rune) {
    81  	Fprintf(s, "<%c=F(%d)>", c, int(f))
    82  }
    83  
    84  type G int
    85  
    86  func (g G) GoString() string {
    87  	return Sprintf("GoString(%d)", int(g))
    88  }
    89  
    90  type S struct {
    91  	F F // a struct field that Formats
    92  	G G // a struct field that GoStrings
    93  }
    94  
    95  type SI struct {
    96  	I interface{}
    97  }
    98  
    99  // P is a type with a String method with pointer receiver for testing %p.
   100  type P int
   101  
   102  var pValue P
   103  
   104  func (p *P) String() string {
   105  	return "String(p)"
   106  }
   107  
   108  var barray = [5]renamedUint8{1, 2, 3, 4, 5}
   109  var bslice = barray[:]
   110  
   111  var b byte
   112  
   113  var fmtTests = []struct {
   114  	fmt string
   115  	val interface{}
   116  	out string
   117  }{
   118  	{"%d", 12345, "12345"},
   119  	{"%v", 12345, "12345"},
   120  	{"%t", true, "true"},
   121  
   122  	// basic string
   123  	{"%s", "abc", "abc"},
   124  	{"%x", "abc", "616263"},
   125  	{"%x", "xyz", "78797a"},
   126  	{"%X", "xyz", "78797A"},
   127  	{"%q", "abc", `"abc"`},
   128  
   129  	// basic bytes
   130  	{"%s", []byte("abc"), "abc"},
   131  	{"%x", []byte("abc"), "616263"},
   132  	{"% x", []byte("abc\xff"), "61 62 63 ff"},
   133  	{"%#x", []byte("abc\xff"), "0x610x620x630xff"},
   134  	{"%#X", []byte("abc\xff"), "0X610X620X630XFF"},
   135  	{"%# x", []byte("abc\xff"), "0x61 0x62 0x63 0xff"},
   136  	{"%# X", []byte("abc\xff"), "0X61 0X62 0X63 0XFF"},
   137  	{"% X", []byte("abc\xff"), "61 62 63 FF"},
   138  	{"%x", []byte("xyz"), "78797a"},
   139  	{"%X", []byte("xyz"), "78797A"},
   140  	{"%q", []byte("abc"), `"abc"`},
   141  
   142  	// escaped strings
   143  	{"%#q", `abc`, "`abc`"},
   144  	{"%#q", `"`, "`\"`"},
   145  	{"1 %#q", `\n`, "1 `\\n`"},
   146  	{"2 %#q", "\n", `2 "\n"`},
   147  	{"%q", `"`, `"\""`},
   148  	{"%q", "\a\b\f\r\n\t\v", `"\a\b\f\r\n\t\v"`},
   149  	{"%q", "abc\xffdef", `"abc\xffdef"`},
   150  	{"%q", "\u263a", `"☺"`},
   151  	{"%+q", "\u263a", `"\u263a"`},
   152  	{"%q", "\U0010ffff", `"\U0010ffff"`},
   153  
   154  	// escaped characters
   155  	{"%q", 'x', `'x'`},
   156  	{"%q", 0, `'\x00'`},
   157  	{"%q", '\n', `'\n'`},
   158  	{"%q", '\u0e00', `'\u0e00'`},         // not a printable rune.
   159  	{"%q", '\U000c2345', `'\U000c2345'`}, // not a printable rune.
   160  	{"%q", int64(0x7FFFFFFF), `%!q(int64=2147483647)`},
   161  	{"%q", uint64(0xFFFFFFFF), `%!q(uint64=4294967295)`},
   162  	{"%q", '"', `'"'`},
   163  	{"%q", '\'', `'\''`},
   164  	{"%q", "\u263a", `"☺"`},
   165  	{"%+q", "\u263a", `"\u263a"`},
   166  
   167  	// width
   168  	{"%5s", "abc", "  abc"},
   169  	{"%2s", "\u263a", " ☺"},
   170  	{"%-5s", "abc", "abc  "},
   171  	{"%-8q", "abc", `"abc"   `},
   172  	{"%05s", "abc", "00abc"},
   173  	{"%08q", "abc", `000"abc"`},
   174  	{"%5s", "abcdefghijklmnopqrstuvwxyz", "abcdefghijklmnopqrstuvwxyz"},
   175  	{"%.5s", "abcdefghijklmnopqrstuvwxyz", "abcde"},
   176  	{"%.5s", "日本語日本語", "日本語日本"},
   177  	{"%.5s", []byte("日本語日本語"), "日本語日本"},
   178  	{"%.5q", "abcdefghijklmnopqrstuvwxyz", `"abcde"`},
   179  	{"%.3q", "日本語日本語", `"日本語"`},
   180  	{"%.3q", []byte("日本語日本語"), `"日本語"`},
   181  	{"%10.1q", "日本語日本語", `       "日"`},
   182  	{"%10v", nil, "     <nil>"},
   183  	{"%-10v", nil, "<nil>     "},
   184  
   185  	// integers
   186  	{"%d", 12345, "12345"},
   187  	{"%d", -12345, "-12345"},
   188  	{"%10d", 12345, "     12345"},
   189  	{"%10d", -12345, "    -12345"},
   190  	{"%+10d", 12345, "    +12345"},
   191  	{"%010d", 12345, "0000012345"},
   192  	{"%010d", -12345, "-000012345"},
   193  	{"%-10d", 12345, "12345     "},
   194  	{"%010.3d", 1, "       001"},
   195  	{"%010.3d", -1, "      -001"},
   196  	{"%+d", 12345, "+12345"},
   197  	{"%+d", -12345, "-12345"},
   198  	{"%+d", 0, "+0"},
   199  	{"% d", 0, " 0"},
   200  	{"% d", 12345, " 12345"},
   201  	{"%.0d", 0, ""},
   202  	{"%.d", 0, ""},
   203  
   204  	// unicode format
   205  	{"%U", 0x1, "U+0001"},
   206  	{"%U", uint(0x1), "U+0001"},
   207  	{"%.8U", 0x2, "U+00000002"},
   208  	{"%U", 0x1234, "U+1234"},
   209  	{"%U", 0x12345, "U+12345"},
   210  	{"%10.6U", 0xABC, "  U+000ABC"},
   211  	{"%-10.6U", 0xABC, "U+000ABC  "},
   212  	{"%U", '\n', `U+000A`},
   213  	{"%#U", '\n', `U+000A`},
   214  	{"%U", 'x', `U+0078`},
   215  	{"%#U", 'x', `U+0078 'x'`},
   216  	{"%U", '\u263a', `U+263A`},
   217  	{"%#U", '\u263a', `U+263A '☺'`},
   218  
   219  	// floats
   220  	{"%+.3e", 0.0, "+0.000e+00"},
   221  	{"%+.3e", 1.0, "+1.000e+00"},
   222  	{"%+.3f", -1.0, "-1.000"},
   223  	{"% .3E", -1.0, "-1.000E+00"},
   224  	{"% .3e", 1.0, " 1.000e+00"},
   225  	{"%+.3g", 0.0, "+0"},
   226  	{"%+.3g", 1.0, "+1"},
   227  	{"%+.3g", -1.0, "-1"},
   228  	{"% .3g", -1.0, "-1"},
   229  	{"% .3g", 1.0, " 1"},
   230  	{"%b", float32(1.0), "8388608p-23"},
   231  	{"%b", 1.0, "4503599627370496p-52"},
   232  
   233  	// complex values
   234  	{"%+.3e", 0i, "(+0.000e+00+0.000e+00i)"},
   235  	{"%+.3f", 0i, "(+0.000+0.000i)"},
   236  	{"%+.3g", 0i, "(+0+0i)"},
   237  	{"%+.3e", 1 + 2i, "(+1.000e+00+2.000e+00i)"},
   238  	{"%+.3f", 1 + 2i, "(+1.000+2.000i)"},
   239  	{"%+.3g", 1 + 2i, "(+1+2i)"},
   240  	{"%.3e", 0i, "(0.000e+00+0.000e+00i)"},
   241  	{"%.3f", 0i, "(0.000+0.000i)"},
   242  	{"%.3g", 0i, "(0+0i)"},
   243  	{"%.3e", 1 + 2i, "(1.000e+00+2.000e+00i)"},
   244  	{"%.3f", 1 + 2i, "(1.000+2.000i)"},
   245  	{"%.3g", 1 + 2i, "(1+2i)"},
   246  	{"%.3e", -1 - 2i, "(-1.000e+00-2.000e+00i)"},
   247  	{"%.3f", -1 - 2i, "(-1.000-2.000i)"},
   248  	{"%.3g", -1 - 2i, "(-1-2i)"},
   249  	{"% .3E", -1 - 2i, "(-1.000E+00-2.000E+00i)"},
   250  	{"%+.3g", complex64(1 + 2i), "(+1+2i)"},
   251  	{"%+.3g", complex128(1 + 2i), "(+1+2i)"},
   252  	{"%b", complex64(1 + 2i), "(8388608p-23+8388608p-22i)"},
   253  	{"%b", 1 + 2i, "(4503599627370496p-52+4503599627370496p-51i)"},
   254  
   255  	// erroneous formats
   256  	{"", 2, "%!(EXTRA int=2)"},
   257  	{"%d", "hello", "%!d(string=hello)"},
   258  
   259  	// old test/fmt_test.go
   260  	{"%d", 1234, "1234"},
   261  	{"%d", -1234, "-1234"},
   262  	{"%d", uint(1234), "1234"},
   263  	{"%d", uint32(b32), "4294967295"},
   264  	{"%d", uint64(b64), "18446744073709551615"},
   265  	{"%o", 01234, "1234"},
   266  	{"%#o", 01234, "01234"},
   267  	{"%o", uint32(b32), "37777777777"},
   268  	{"%o", uint64(b64), "1777777777777777777777"},
   269  	{"%x", 0x1234abcd, "1234abcd"},
   270  	{"%#x", 0x1234abcd, "0x1234abcd"},
   271  	{"%x", b32 - 0x1234567, "fedcba98"},
   272  	{"%X", 0x1234abcd, "1234ABCD"},
   273  	{"%X", b32 - 0x1234567, "FEDCBA98"},
   274  	{"%#X", 0, "0X0"},
   275  	{"%x", b64, "ffffffffffffffff"},
   276  	{"%b", 7, "111"},
   277  	{"%b", b64, "1111111111111111111111111111111111111111111111111111111111111111"},
   278  	{"%b", -6, "-110"},
   279  	{"%e", 1.0, "1.000000e+00"},
   280  	{"%e", 1234.5678e3, "1.234568e+06"},
   281  	{"%e", 1234.5678e-8, "1.234568e-05"},
   282  	{"%e", -7.0, "-7.000000e+00"},
   283  	{"%e", -1e-9, "-1.000000e-09"},
   284  	{"%f", 1234.5678e3, "1234567.800000"},
   285  	{"%f", 1234.5678e-8, "0.000012"},
   286  	{"%f", -7.0, "-7.000000"},
   287  	{"%f", -1e-9, "-0.000000"},
   288  	{"%g", 1234.5678e3, "1.2345678e+06"},
   289  	{"%g", float32(1234.5678e3), "1.2345678e+06"},
   290  	{"%g", 1234.5678e-8, "1.2345678e-05"},
   291  	{"%g", -7.0, "-7"},
   292  	{"%g", -1e-9, "-1e-09"},
   293  	{"%g", float32(-1e-9), "-1e-09"},
   294  	{"%E", 1.0, "1.000000E+00"},
   295  	{"%E", 1234.5678e3, "1.234568E+06"},
   296  	{"%E", 1234.5678e-8, "1.234568E-05"},
   297  	{"%E", -7.0, "-7.000000E+00"},
   298  	{"%E", -1e-9, "-1.000000E-09"},
   299  	{"%G", 1234.5678e3, "1.2345678E+06"},
   300  	{"%G", float32(1234.5678e3), "1.2345678E+06"},
   301  	{"%G", 1234.5678e-8, "1.2345678E-05"},
   302  	{"%G", -7.0, "-7"},
   303  	{"%G", -1e-9, "-1E-09"},
   304  	{"%G", float32(-1e-9), "-1E-09"},
   305  	{"%c", 'x', "x"},
   306  	{"%c", 0xe4, "ä"},
   307  	{"%c", 0x672c, "本"},
   308  	{"%c", '日', "日"},
   309  	{"%20.8d", 1234, "            00001234"},
   310  	{"%20.8d", -1234, "           -00001234"},
   311  	{"%20d", 1234, "                1234"},
   312  	{"%-20.8d", 1234, "00001234            "},
   313  	{"%-20.8d", -1234, "-00001234           "},
   314  	{"%-#20.8x", 0x1234abc, "0x01234abc          "},
   315  	{"%-#20.8X", 0x1234abc, "0X01234ABC          "},
   316  	{"%-#20.8o", 01234, "00001234            "},
   317  	{"%.20b", 7, "00000000000000000111"},
   318  	{"%20.5s", "qwertyuiop", "               qwert"},
   319  	{"%.5s", "qwertyuiop", "qwert"},
   320  	{"%-20.5s", "qwertyuiop", "qwert               "},
   321  	{"%20c", 'x', "                   x"},
   322  	{"%-20c", 'x', "x                   "},
   323  	{"%20.6e", 1.2345e3, "        1.234500e+03"},
   324  	{"%20.6e", 1.2345e-3, "        1.234500e-03"},
   325  	{"%20e", 1.2345e3, "        1.234500e+03"},
   326  	{"%20e", 1.2345e-3, "        1.234500e-03"},
   327  	{"%20.8e", 1.2345e3, "      1.23450000e+03"},
   328  	{"%20f", 1.23456789e3, "         1234.567890"},
   329  	{"%20f", 1.23456789e-3, "            0.001235"},
   330  	{"%20f", 12345678901.23456789, "  12345678901.234568"},
   331  	{"%-20f", 1.23456789e3, "1234.567890         "},
   332  	{"%20.8f", 1.23456789e3, "       1234.56789000"},
   333  	{"%20.8f", 1.23456789e-3, "          0.00123457"},
   334  	{"%g", 1.23456789e3, "1234.56789"},
   335  	{"%g", 1.23456789e-3, "0.00123456789"},
   336  	{"%g", 1.23456789e20, "1.23456789e+20"},
   337  	{"%20e", math.Inf(1), "                +Inf"},
   338  	{"%-20f", math.Inf(-1), "-Inf                "},
   339  	{"%20g", math.NaN(), "                 NaN"},
   340  
   341  	// arrays
   342  	{"%v", array, "[1 2 3 4 5]"},
   343  	{"%v", iarray, "[1 hello 2.5 <nil>]"},
   344  	{"%v", barray, "[1 2 3 4 5]"},
   345  	{"%v", &array, "&[1 2 3 4 5]"},
   346  	{"%v", &iarray, "&[1 hello 2.5 <nil>]"},
   347  	{"%v", &barray, "&[1 2 3 4 5]"},
   348  
   349  	// slices
   350  	{"%v", slice, "[1 2 3 4 5]"},
   351  	{"%v", islice, "[1 hello 2.5 <nil>]"},
   352  	{"%v", bslice, "[1 2 3 4 5]"},
   353  	{"%v", &slice, "&[1 2 3 4 5]"},
   354  	{"%v", &islice, "&[1 hello 2.5 <nil>]"},
   355  	{"%v", &bslice, "&[1 2 3 4 5]"},
   356  
   357  	// complexes with %v
   358  	{"%v", 1 + 2i, "(1+2i)"},
   359  	{"%v", complex64(1 + 2i), "(1+2i)"},
   360  	{"%v", complex128(1 + 2i), "(1+2i)"},
   361  
   362  	// structs
   363  	{"%v", A{1, 2, "a", []int{1, 2}}, `{1 2 a [1 2]}`},
   364  	{"%+v", A{1, 2, "a", []int{1, 2}}, `{i:1 j:2 s:a x:[1 2]}`},
   365  
   366  	// +v on structs with Stringable items
   367  	{"%+v", B{1, 2}, `{I:<1> j:2}`},
   368  	{"%+v", C{1, B{2, 3}}, `{i:1 B:{I:<2> j:3}}`},
   369  
   370  	// other formats on Stringable items
   371  	{"%s", I(23), `<23>`},
   372  	{"%q", I(23), `"<23>"`},
   373  	{"%x", I(23), `3c32333e`},
   374  	{"%#x", I(23), `0x3c0x320x330x3e`},
   375  	{"%# x", I(23), `0x3c 0x32 0x33 0x3e`},
   376  	{"%d", I(23), `23`}, // Stringer applies only to string formats.
   377  
   378  	// go syntax
   379  	{"%#v", A{1, 2, "a", []int{1, 2}}, `fmt_test.A{i:1, j:0x2, s:"a", x:[]int{1, 2}}`},
   380  	{"%#v", &b, "(*uint8)(0xPTR)"},
   381  	{"%#v", TestFmtInterface, "(func(*testing.T))(0xPTR)"},
   382  	{"%#v", make(chan int), "(chan int)(0xPTR)"},
   383  	{"%#v", uint64(1<<64 - 1), "0xffffffffffffffff"},
   384  	{"%#v", 1000000000, "1000000000"},
   385  	{"%#v", map[string]int{"a": 1}, `map[string]int{"a":1}`},
   386  	{"%#v", map[string]B{"a": {1, 2}}, `map[string]fmt_test.B{"a":fmt_test.B{I:1, j:2}}`},
   387  	{"%#v", []string{"a", "b"}, `[]string{"a", "b"}`},
   388  	{"%#v", SI{}, `fmt_test.SI{I:interface {}(nil)}`},
   389  	{"%#v", []int(nil), `[]int(nil)`},
   390  	{"%#v", []int{}, `[]int{}`},
   391  	{"%#v", array, `[5]int{1, 2, 3, 4, 5}`},
   392  	{"%#v", &array, `&[5]int{1, 2, 3, 4, 5}`},
   393  	{"%#v", iarray, `[4]interface {}{1, "hello", 2.5, interface {}(nil)}`},
   394  	{"%#v", &iarray, `&[4]interface {}{1, "hello", 2.5, interface {}(nil)}`},
   395  	{"%#v", map[int]byte(nil), `map[int]uint8(nil)`},
   396  	{"%#v", map[int]byte{}, `map[int]uint8{}`},
   397  	{"%#v", "foo", `"foo"`},
   398  	{"%#v", barray, `[5]fmt_test.renamedUint8{0x1, 0x2, 0x3, 0x4, 0x5}`},
   399  	{"%#v", bslice, `[]fmt_test.renamedUint8{0x1, 0x2, 0x3, 0x4, 0x5}`},
   400  
   401  	// slices with other formats
   402  	{"%#x", []int{1, 2, 15}, `[0x1 0x2 0xf]`},
   403  	{"%x", []int{1, 2, 15}, `[1 2 f]`},
   404  	{"%d", []int{1, 2, 15}, `[1 2 15]`},
   405  	{"%d", []byte{1, 2, 15}, `[1 2 15]`},
   406  	{"%q", []string{"a", "b"}, `["a" "b"]`},
   407  
   408  	// renamings
   409  	{"%v", renamedBool(true), "true"},
   410  	{"%d", renamedBool(true), "%!d(fmt_test.renamedBool=true)"},
   411  	{"%o", renamedInt(8), "10"},
   412  	{"%d", renamedInt8(-9), "-9"},
   413  	{"%v", renamedInt16(10), "10"},
   414  	{"%v", renamedInt32(-11), "-11"},
   415  	{"%X", renamedInt64(255), "FF"},
   416  	{"%v", renamedUint(13), "13"},
   417  	{"%o", renamedUint8(14), "16"},
   418  	{"%X", renamedUint16(15), "F"},
   419  	{"%d", renamedUint32(16), "16"},
   420  	{"%X", renamedUint64(17), "11"},
   421  	{"%o", renamedUintptr(18), "22"},
   422  	{"%x", renamedString("thing"), "7468696e67"},
   423  	{"%d", renamedBytes([]byte{1, 2, 15}), `[1 2 15]`},
   424  	{"%q", renamedBytes([]byte("hello")), `"hello"`},
   425  	{"%x", []renamedUint8{'a', 'b', 'c'}, "616263"},
   426  	{"%s", []renamedUint8{'h', 'e', 'l', 'l', 'o'}, "hello"},
   427  	{"%q", []renamedUint8{'h', 'e', 'l', 'l', 'o'}, `"hello"`},
   428  	{"%v", renamedFloat32(22), "22"},
   429  	{"%v", renamedFloat64(33), "33"},
   430  	{"%v", renamedComplex64(3 + 4i), "(3+4i)"},
   431  	{"%v", renamedComplex128(4 - 3i), "(4-3i)"},
   432  
   433  	// Formatter
   434  	{"%x", F(1), "<x=F(1)>"},
   435  	{"%x", G(2), "2"},
   436  	{"%+v", S{F(4), G(5)}, "{F:<v=F(4)> G:5}"},
   437  
   438  	// GoStringer
   439  	{"%#v", G(6), "GoString(6)"},
   440  	{"%#v", S{F(7), G(8)}, "fmt_test.S{F:<v=F(7)>, G:GoString(8)}"},
   441  
   442  	// %T
   443  	{"%T", (4 - 3i), "complex128"},
   444  	{"%T", renamedComplex128(4 - 3i), "fmt_test.renamedComplex128"},
   445  	{"%T", intVal, "int"},
   446  	{"%6T", &intVal, "  *int"},
   447  	{"%10T", nil, "     <nil>"},
   448  	{"%-10T", nil, "<nil>     "},
   449  
   450  	// %p
   451  	{"p0=%p", new(int), "p0=0xPTR"},
   452  	{"p1=%s", &pValue, "p1=String(p)"}, // String method...
   453  	{"p2=%p", &pValue, "p2=0xPTR"},     // ... not called with %p
   454  	{"p3=%p", (*int)(nil), "p3=0x0"},
   455  	{"p4=%#p", new(int), "p4=PTR"},
   456  
   457  	// %p on non-pointers
   458  	{"%p", make(chan int), "0xPTR"},
   459  	{"%p", make(map[int]int), "0xPTR"},
   460  	{"%p", make([]int, 1), "0xPTR"},
   461  	{"%p", 27, "%!p(int=27)"}, // not a pointer at all
   462  
   463  	// %q on pointers
   464  	{"%q", (*int)(nil), "%!q(*int=<nil>)"},
   465  	{"%q", new(int), "%!q(*int=0xPTR)"},
   466  
   467  	// %v on pointers formats 0 as <nil>
   468  	{"%v", (*int)(nil), "<nil>"},
   469  	{"%v", new(int), "0xPTR"},
   470  
   471  	// %d etc. pointers use specified base.
   472  	{"%d", new(int), "PTR_d"},
   473  	{"%o", new(int), "PTR_o"},
   474  	{"%x", new(int), "PTR_x"},
   475  
   476  	// %d on Stringer should give integer if possible
   477  	{"%s", time.Time{}.Month(), "January"},
   478  	{"%d", time.Time{}.Month(), "1"},
   479  
   480  	// erroneous things
   481  	{"%s %", "hello", "hello %!(NOVERB)"},
   482  	{"%s %.2", "hello", "hello %!(NOVERB)"},
   483  	{"%d", "hello", "%!d(string=hello)"},
   484  	{"no args", "hello", "no args%!(EXTRA string=hello)"},
   485  	{"%s", nil, "%!s(<nil>)"},
   486  	{"%T", nil, "<nil>"},
   487  	{"%-1", 100, "%!(NOVERB)%!(EXTRA int=100)"},
   488  
   489  	// The "<nil>" show up because maps are printed by
   490  	// first obtaining a list of keys and then looking up
   491  	// each key.  Since NaNs can be map keys but cannot
   492  	// be fetched directly, the lookup fails and returns a
   493  	// zero reflect.Value, which formats as <nil>.
   494  	// This test is just to check that it shows the two NaNs at all.
   495  	{"%v", map[float64]int{math.NaN(): 1, math.NaN(): 2}, "map[NaN:<nil> NaN:<nil>]"},
   496  
   497  	// Used to crash because nByte didn't allow for a sign.
   498  	{"%b", int64(-1 << 63), "-1000000000000000000000000000000000000000000000000000000000000000"},
   499  
   500  	// Used to panic.
   501  	{"%0100d", 1, "0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001"},
   502  	{"%0100d", -1, "-000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001"},
   503  	{"%0.100f", 1.0, "1.0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"},
   504  	{"%0.100f", -1.0, "-1.0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"},
   505  
   506  	// Zero padding floats used to put the minus sign in the middle.
   507  	{"%020f", -1.0, "-000000000001.000000"},
   508  	{"%20f", -1.0, "           -1.000000"},
   509  	{"%0100f", -1.0, "-00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001.000000"},
   510  
   511  	// Complex fmt used to leave the plus flag set for future entries in the array
   512  	// causing +2+0i and +3+0i instead of 2+0i and 3+0i.
   513  	{"%v", []complex64{1, 2, 3}, "[(1+0i) (2+0i) (3+0i)]"},
   514  	{"%v", []complex128{1, 2, 3}, "[(1+0i) (2+0i) (3+0i)]"},
   515  
   516  	// Incomplete format specification caused crash.
   517  	{"%.", 3, "%!.(int=3)"},
   518  }
   519  
   520  func TestSprintf(t *testing.T) {
   521  	for _, tt := range fmtTests {
   522  		s := Sprintf(tt.fmt, tt.val)
   523  		if i := strings.Index(tt.out, "PTR"); i >= 0 {
   524  			pattern := "PTR"
   525  			chars := "0123456789abcdefABCDEF"
   526  			switch {
   527  			case strings.HasPrefix(tt.out[i:], "PTR_d"):
   528  				pattern = "PTR_d"
   529  				chars = chars[:10]
   530  			case strings.HasPrefix(tt.out[i:], "PTR_o"):
   531  				pattern = "PTR_o"
   532  				chars = chars[:8]
   533  			case strings.HasPrefix(tt.out[i:], "PTR_x"):
   534  				pattern = "PTR_x"
   535  			}
   536  			j := i
   537  			for ; j < len(s); j++ {
   538  				c := s[j]
   539  				if !strings.ContainsRune(chars, rune(c)) {
   540  					break
   541  				}
   542  			}
   543  			s = s[0:i] + pattern + s[j:]
   544  		}
   545  		if s != tt.out {
   546  			if _, ok := tt.val.(string); ok {
   547  				// Don't requote the already-quoted strings.
   548  				// It's too confusing to read the errors.
   549  				t.Errorf("Sprintf(%q, %q) = <%s> want <%s>", tt.fmt, tt.val, s, tt.out)
   550  			} else {
   551  				t.Errorf("Sprintf(%q, %v) = %q want %q", tt.fmt, tt.val, s, tt.out)
   552  			}
   553  		}
   554  	}
   555  }
   556  
   557  type SE []interface{} // slice of empty; notational compactness.
   558  
   559  var reorderTests = []struct {
   560  	fmt string
   561  	val SE
   562  	out string
   563  }{
   564  	{"%[1]d", SE{1}, "1"},
   565  	{"%[2]d", SE{2, 1}, "1"},
   566  	{"%[2]d %[1]d", SE{1, 2}, "2 1"},
   567  	{"%[2]*[1]d", SE{2, 5}, "    2"},
   568  	{"%6.2f", SE{12.0}, " 12.00"}, // Explicit version of next line.
   569  	{"%[3]*.[2]*[1]f", SE{12.0, 2, 6}, " 12.00"},
   570  	{"%[1]*.[2]*[3]f", SE{6, 2, 12.0}, " 12.00"},
   571  	{"%10f", SE{12.0}, " 12.000000"},
   572  	{"%[1]*[3]f", SE{10, 99, 12.0}, " 12.000000"},
   573  	{"%.6f", SE{12.0}, "12.000000"}, // Explicit version of next line.
   574  	{"%.[1]*[3]f", SE{6, 99, 12.0}, "12.000000"},
   575  	{"%6.f", SE{12.0}, "    12"}, //  // Explicit version of next line; empty precision means zero.
   576  	{"%[1]*.[3]f", SE{6, 3, 12.0}, "    12"},
   577  	// An actual use! Print the same arguments twice.
   578  	{"%d %d %d %#[1]o %#o %#o", SE{11, 12, 13}, "11 12 13 013 014 015"},
   579  
   580  	// Erroneous cases.
   581  	{"%[d", SE{2, 1}, "%!d(BADINDEX)"},
   582  	{"%]d", SE{2, 1}, "%!](int=2)d%!(EXTRA int=1)"},
   583  	{"%[]d", SE{2, 1}, "%!d(BADINDEX)"},
   584  	{"%[-3]d", SE{2, 1}, "%!d(BADINDEX)"},
   585  	{"%[99]d", SE{2, 1}, "%!d(BADINDEX)"},
   586  	{"%[3]", SE{2, 1}, "%!(NOVERB)"},
   587  	{"%[1].2d", SE{5, 6}, "%!d(BADINDEX)"},
   588  	{"%[1]2d", SE{2, 1}, "%!d(BADINDEX)"},
   589  	{"%3.[2]d", SE{7}, "%!d(BADINDEX)"},
   590  	{"%.[2]d", SE{7}, "%!d(BADINDEX)"},
   591  	{"%d %d %d %#[1]o %#o %#o %#o", SE{11, 12, 13}, "11 12 13 013 014 015 %!o(MISSING)"},
   592  	{"%[5]d %[2]d %d", SE{1, 2, 3}, "%!d(BADINDEX) 2 3"},
   593  	{"%d %[3]d %d", SE{1, 2}, "1 %!d(BADINDEX) 2"}, // Erroneous index does not affect sequence.
   594  }
   595  
   596  func TestReorder(t *testing.T) {
   597  	for _, tt := range reorderTests {
   598  		s := Sprintf(tt.fmt, tt.val...)
   599  		if s != tt.out {
   600  			t.Errorf("Sprintf(%q, %v) = <%s> want <%s>", tt.fmt, tt.val, s, tt.out)
   601  		} else {
   602  		}
   603  	}
   604  }
   605  
   606  func BenchmarkSprintfEmpty(b *testing.B) {
   607  	for i := 0; i < b.N; i++ {
   608  		Sprintf("")
   609  	}
   610  }
   611  
   612  func BenchmarkSprintfString(b *testing.B) {
   613  	for i := 0; i < b.N; i++ {
   614  		Sprintf("%s", "hello")
   615  	}
   616  }
   617  
   618  func BenchmarkSprintfInt(b *testing.B) {
   619  	for i := 0; i < b.N; i++ {
   620  		Sprintf("%d", 5)
   621  	}
   622  }
   623  
   624  func BenchmarkSprintfIntInt(b *testing.B) {
   625  	for i := 0; i < b.N; i++ {
   626  		Sprintf("%d %d", 5, 6)
   627  	}
   628  }
   629  
   630  func BenchmarkSprintfPrefixedInt(b *testing.B) {
   631  	for i := 0; i < b.N; i++ {
   632  		Sprintf("This is some meaningless prefix text that needs to be scanned %d", 6)
   633  	}
   634  }
   635  
   636  func BenchmarkSprintfFloat(b *testing.B) {
   637  	for i := 0; i < b.N; i++ {
   638  		Sprintf("%g", 5.23184)
   639  	}
   640  }
   641  
   642  func BenchmarkManyArgs(b *testing.B) {
   643  	var buf bytes.Buffer
   644  	for i := 0; i < b.N; i++ {
   645  		buf.Reset()
   646  		Fprintf(&buf, "%2d/%2d/%2d %d:%d:%d %s %s\n", 3, 4, 5, 11, 12, 13, "hello", "world")
   647  	}
   648  }
   649  
   650  var mallocBuf bytes.Buffer
   651  
   652  var mallocTest = []struct {
   653  	count int
   654  	desc  string
   655  	fn    func()
   656  }{
   657  	{0, `Sprintf("")`, func() { Sprintf("") }},
   658  	{1, `Sprintf("xxx")`, func() { Sprintf("xxx") }},
   659  	{1, `Sprintf("%x")`, func() { Sprintf("%x", 7) }},
   660  	{2, `Sprintf("%s")`, func() { Sprintf("%s", "hello") }},
   661  	{1, `Sprintf("%x %x")`, func() { Sprintf("%x %x", 7, 112) }},
   662  	// For %g we use a float32, not float64, to guarantee passing the argument
   663  	// does not need to allocate memory to store the result in a pointer-sized word.
   664  	{2, `Sprintf("%g")`, func() { Sprintf("%g", float32(3.14159)) }},
   665  	{0, `Fprintf(buf, "%x %x %x")`, func() { mallocBuf.Reset(); Fprintf(&mallocBuf, "%x %x %x", 7, 8, 9) }},
   666  	{1, `Fprintf(buf, "%s")`, func() { mallocBuf.Reset(); Fprintf(&mallocBuf, "%s", "hello") }},
   667  }
   668  
   669  var _ bytes.Buffer
   670  
   671  func TestCountMallocs(t *testing.T) {
   672  	if testing.Short() {
   673  		t.Skip("skipping malloc count in short mode")
   674  	}
   675  	if runtime.GOMAXPROCS(0) > 1 {
   676  		t.Skip("skipping; GOMAXPROCS>1")
   677  	}
   678  	for _, mt := range mallocTest {
   679  		mallocs := testing.AllocsPerRun(100, mt.fn)
   680  		if got, max := mallocs, float64(mt.count); got > max {
   681  			t.Errorf("%s: got %v allocs, want <=%v", mt.desc, got, max)
   682  		}
   683  	}
   684  }
   685  
   686  type flagPrinter struct{}
   687  
   688  func (*flagPrinter) Format(f State, c rune) {
   689  	s := "%"
   690  	for i := 0; i < 128; i++ {
   691  		if f.Flag(i) {
   692  			s += string(i)
   693  		}
   694  	}
   695  	if w, ok := f.Width(); ok {
   696  		s += Sprintf("%d", w)
   697  	}
   698  	if p, ok := f.Precision(); ok {
   699  		s += Sprintf(".%d", p)
   700  	}
   701  	s += string(c)
   702  	io.WriteString(f, "["+s+"]")
   703  }
   704  
   705  var flagtests = []struct {
   706  	in  string
   707  	out string
   708  }{
   709  	{"%a", "[%a]"},
   710  	{"%-a", "[%-a]"},
   711  	{"%+a", "[%+a]"},
   712  	{"%#a", "[%#a]"},
   713  	{"% a", "[% a]"},
   714  	{"%0a", "[%0a]"},
   715  	{"%1.2a", "[%1.2a]"},
   716  	{"%-1.2a", "[%-1.2a]"},
   717  	{"%+1.2a", "[%+1.2a]"},
   718  	{"%-+1.2a", "[%+-1.2a]"},
   719  	{"%-+1.2abc", "[%+-1.2a]bc"},
   720  	{"%-1.2abc", "[%-1.2a]bc"},
   721  }
   722  
   723  func TestFlagParser(t *testing.T) {
   724  	var flagprinter flagPrinter
   725  	for _, tt := range flagtests {
   726  		s := Sprintf(tt.in, &flagprinter)
   727  		if s != tt.out {
   728  			t.Errorf("Sprintf(%q, &flagprinter) => %q, want %q", tt.in, s, tt.out)
   729  		}
   730  	}
   731  }
   732  
   733  func TestStructPrinter(t *testing.T) {
   734  	var s struct {
   735  		a string
   736  		b string
   737  		c int
   738  	}
   739  	s.a = "abc"
   740  	s.b = "def"
   741  	s.c = 123
   742  	var tests = []struct {
   743  		fmt string
   744  		out string
   745  	}{
   746  		{"%v", "{abc def 123}"},
   747  		{"%+v", "{a:abc b:def c:123}"},
   748  	}
   749  	for _, tt := range tests {
   750  		out := Sprintf(tt.fmt, s)
   751  		if out != tt.out {
   752  			t.Errorf("Sprintf(%q, &s) = %q, want %q", tt.fmt, out, tt.out)
   753  		}
   754  	}
   755  }
   756  
   757  // presentInMap checks map printing using substrings so we don't depend on the
   758  // print order.
   759  func presentInMap(s string, a []string, t *testing.T) {
   760  	for i := 0; i < len(a); i++ {
   761  		loc := strings.Index(s, a[i])
   762  		if loc < 0 {
   763  			t.Errorf("map print: expected to find %q in %q", a[i], s)
   764  		}
   765  		// make sure the match ends here
   766  		loc += len(a[i])
   767  		if loc >= len(s) || (s[loc] != ' ' && s[loc] != ']') {
   768  			t.Errorf("map print: %q not properly terminated in %q", a[i], s)
   769  		}
   770  	}
   771  }
   772  
   773  func TestMapPrinter(t *testing.T) {
   774  	m0 := make(map[int]string)
   775  	s := Sprint(m0)
   776  	if s != "map[]" {
   777  		t.Errorf("empty map printed as %q not %q", s, "map[]")
   778  	}
   779  	m1 := map[int]string{1: "one", 2: "two", 3: "three"}
   780  	a := []string{"1:one", "2:two", "3:three"}
   781  	presentInMap(Sprintf("%v", m1), a, t)
   782  	presentInMap(Sprint(m1), a, t)
   783  }
   784  
   785  func TestEmptyMap(t *testing.T) {
   786  	const emptyMapStr = "map[]"
   787  	var m map[string]int
   788  	s := Sprint(m)
   789  	if s != emptyMapStr {
   790  		t.Errorf("nil map printed as %q not %q", s, emptyMapStr)
   791  	}
   792  	m = make(map[string]int)
   793  	s = Sprint(m)
   794  	if s != emptyMapStr {
   795  		t.Errorf("empty map printed as %q not %q", s, emptyMapStr)
   796  	}
   797  }
   798  
   799  // TestBlank checks that Sprint (and hence Print, Fprint) puts spaces in the
   800  // right places, that is, between arg pairs in which neither is a string.
   801  func TestBlank(t *testing.T) {
   802  	got := Sprint("<", 1, ">:", 1, 2, 3, "!")
   803  	expect := "<1>:1 2 3!"
   804  	if got != expect {
   805  		t.Errorf("got %q expected %q", got, expect)
   806  	}
   807  }
   808  
   809  // TestBlankln checks that Sprintln (and hence Println, Fprintln) puts spaces in
   810  // the right places, that is, between all arg pairs.
   811  func TestBlankln(t *testing.T) {
   812  	got := Sprintln("<", 1, ">:", 1, 2, 3, "!")
   813  	expect := "< 1 >: 1 2 3 !\n"
   814  	if got != expect {
   815  		t.Errorf("got %q expected %q", got, expect)
   816  	}
   817  }
   818  
   819  // TestFormatterPrintln checks Formatter with Sprint, Sprintln, Sprintf.
   820  func TestFormatterPrintln(t *testing.T) {
   821  	f := F(1)
   822  	expect := "<v=F(1)>\n"
   823  	s := Sprint(f, "\n")
   824  	if s != expect {
   825  		t.Errorf("Sprint wrong with Formatter: expected %q got %q", expect, s)
   826  	}
   827  	s = Sprintln(f)
   828  	if s != expect {
   829  		t.Errorf("Sprintln wrong with Formatter: expected %q got %q", expect, s)
   830  	}
   831  	s = Sprintf("%v\n", f)
   832  	if s != expect {
   833  		t.Errorf("Sprintf wrong with Formatter: expected %q got %q", expect, s)
   834  	}
   835  }
   836  
   837  func args(a ...interface{}) []interface{} { return a }
   838  
   839  var startests = []struct {
   840  	fmt string
   841  	in  []interface{}
   842  	out string
   843  }{
   844  	{"%*d", args(4, 42), "  42"},
   845  	{"%.*d", args(4, 42), "0042"},
   846  	{"%*.*d", args(8, 4, 42), "    0042"},
   847  	{"%0*d", args(4, 42), "0042"},
   848  	{"%-*d", args(4, 42), "42  "},
   849  
   850  	// erroneous
   851  	{"%*d", args(nil, 42), "%!(BADWIDTH)42"},
   852  	{"%.*d", args(nil, 42), "%!(BADPREC)42"},
   853  	{"%*d", args(5, "foo"), "%!d(string=  foo)"},
   854  	{"%*% %d", args(20, 5), "% 5"},
   855  	{"%*", args(4), "%!(NOVERB)"},
   856  	{"%*d", args(int32(4), 42), "%!(BADWIDTH)42"},
   857  }
   858  
   859  func TestWidthAndPrecision(t *testing.T) {
   860  	for _, tt := range startests {
   861  		s := Sprintf(tt.fmt, tt.in...)
   862  		if s != tt.out {
   863  			t.Errorf("%q: got %q expected %q", tt.fmt, s, tt.out)
   864  		}
   865  	}
   866  }
   867  
   868  // Panic is a type that panics in String.
   869  type Panic struct {
   870  	message interface{}
   871  }
   872  
   873  // Value receiver.
   874  func (p Panic) GoString() string {
   875  	panic(p.message)
   876  }
   877  
   878  // Value receiver.
   879  func (p Panic) String() string {
   880  	panic(p.message)
   881  }
   882  
   883  // PanicF is a type that panics in Format.
   884  type PanicF struct {
   885  	message interface{}
   886  }
   887  
   888  // Value receiver.
   889  func (p PanicF) Format(f State, c rune) {
   890  	panic(p.message)
   891  }
   892  
   893  var panictests = []struct {
   894  	fmt string
   895  	in  interface{}
   896  	out string
   897  }{
   898  	// String
   899  	{"%s", (*Panic)(nil), "<nil>"}, // nil pointer special case
   900  	{"%s", Panic{io.ErrUnexpectedEOF}, "%!s(PANIC=unexpected EOF)"},
   901  	{"%s", Panic{3}, "%!s(PANIC=3)"},
   902  	// GoString
   903  	{"%#v", (*Panic)(nil), "<nil>"}, // nil pointer special case
   904  	{"%#v", Panic{io.ErrUnexpectedEOF}, "%!v(PANIC=unexpected EOF)"},
   905  	{"%#v", Panic{3}, "%!v(PANIC=3)"},
   906  	// Format
   907  	{"%s", (*PanicF)(nil), "<nil>"}, // nil pointer special case
   908  	{"%s", PanicF{io.ErrUnexpectedEOF}, "%!s(PANIC=unexpected EOF)"},
   909  	{"%s", PanicF{3}, "%!s(PANIC=3)"},
   910  }
   911  
   912  func TestPanics(t *testing.T) {
   913  	for _, tt := range panictests {
   914  		s := Sprintf(tt.fmt, tt.in)
   915  		if s != tt.out {
   916  			t.Errorf("%q: got %q expected %q", tt.fmt, s, tt.out)
   917  		}
   918  	}
   919  }
   920  
   921  // recurCount tests that erroneous String routine doesn't cause fatal recursion.
   922  var recurCount = 0
   923  
   924  type Recur struct {
   925  	i      int
   926  	failed *bool
   927  }
   928  
   929  func (r *Recur) String() string {
   930  	if recurCount++; recurCount > 10 {
   931  		*r.failed = true
   932  		return "FAIL"
   933  	}
   934  	// This will call badVerb. Before the fix, that would cause us to recur into
   935  	// this routine to print %!p(value). Now we don't call the user's method
   936  	// during an error.
   937  	return Sprintf("recur@%p value: %d", r, r.i)
   938  }
   939  
   940  func TestBadVerbRecursion(t *testing.T) {
   941  	failed := false
   942  	r := &Recur{3, &failed}
   943  	Sprintf("recur@%p value: %d\n", &r, r.i)
   944  	if failed {
   945  		t.Error("fail with pointer")
   946  	}
   947  	failed = false
   948  	r = &Recur{4, &failed}
   949  	Sprintf("recur@%p, value: %d\n", r, r.i)
   950  	if failed {
   951  		t.Error("fail with value")
   952  	}
   953  }
   954  
   955  func TestIsSpace(t *testing.T) {
   956  	// This tests the internal isSpace function.
   957  	// IsSpace = isSpace is defined in export_test.go.
   958  	for i := rune(0); i <= unicode.MaxRune; i++ {
   959  		if IsSpace(i) != unicode.IsSpace(i) {
   960  			t.Errorf("isSpace(%U) = %v, want %v", i, IsSpace(i), unicode.IsSpace(i))
   961  		}
   962  	}
   963  }
   964  
   965  func TestNilDoesNotBecomeTyped(t *testing.T) {
   966  	type A struct{}
   967  	type B struct{}
   968  	var a *A = nil
   969  	var b B = B{}
   970  	got := Sprintf("%s %s %s %s %s", nil, a, nil, b, nil)
   971  	const expect = "%!s(<nil>) %!s(*fmt_test.A=<nil>) %!s(<nil>) {} %!s(<nil>)"
   972  	if got != expect {
   973  		t.Errorf("expected:\n\t%q\ngot:\n\t%q", expect, got)
   974  	}
   975  }