compiler, libgo: Permit testing package when test imports it circularly.
From-SVN: r195931
This commit is contained in:
parent
8e29a61c2d
commit
d54fc07473
16 changed files with 84 additions and 264 deletions
|
@ -515,16 +515,23 @@ Gogo::add_import_init_fn(const std::string& package_name,
|
||||||
p != this->imported_init_fns_.end();
|
p != this->imported_init_fns_.end();
|
||||||
++p)
|
++p)
|
||||||
{
|
{
|
||||||
if (p->init_name() == init_name
|
if (p->init_name() == init_name)
|
||||||
&& (p->package_name() != package_name || p->priority() != prio))
|
|
||||||
{
|
{
|
||||||
error("duplicate package initialization name %qs",
|
// If a test of package P1, built as part of package P1,
|
||||||
Gogo::message_name(init_name).c_str());
|
// imports package P2, and P2 imports P1 (perhaps
|
||||||
inform(UNKNOWN_LOCATION, "used by package %qs at priority %d",
|
// indirectly), then we will see the same import name with
|
||||||
Gogo::message_name(p->package_name()).c_str(),
|
// different import priorities. That is OK, so don't give
|
||||||
p->priority());
|
// an error about it.
|
||||||
inform(UNKNOWN_LOCATION, " and by package %qs at priority %d",
|
if (p->package_name() != package_name)
|
||||||
Gogo::message_name(package_name).c_str(), prio);
|
{
|
||||||
|
error("duplicate package initialization name %qs",
|
||||||
|
Gogo::message_name(init_name).c_str());
|
||||||
|
inform(UNKNOWN_LOCATION, "used by package %qs at priority %d",
|
||||||
|
Gogo::message_name(p->package_name()).c_str(),
|
||||||
|
p->priority());
|
||||||
|
inform(UNKNOWN_LOCATION, " and by package %qs at priority %d",
|
||||||
|
Gogo::message_name(package_name).c_str(), prio);
|
||||||
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,10 +2,9 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package macho_test
|
package macho
|
||||||
|
|
||||||
import (
|
import (
|
||||||
. "debug/macho"
|
|
||||||
"reflect"
|
"reflect"
|
||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
|
@ -2,11 +2,10 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package binary_test
|
package binary
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
. "encoding/binary"
|
|
||||||
"io"
|
"io"
|
||||||
"math"
|
"math"
|
||||||
"reflect"
|
"reflect"
|
||||||
|
@ -239,7 +238,7 @@ func BenchmarkReadStruct(b *testing.B) {
|
||||||
bsr := &byteSliceReader{}
|
bsr := &byteSliceReader{}
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
Write(&buf, BigEndian, &s)
|
Write(&buf, BigEndian, &s)
|
||||||
n := DataSize(reflect.ValueOf(s))
|
n := dataSize(reflect.ValueOf(s))
|
||||||
b.SetBytes(int64(n))
|
b.SetBytes(int64(n))
|
||||||
t := s
|
t := s
|
||||||
b.ResetTimer()
|
b.ResetTimer()
|
||||||
|
|
|
@ -1,15 +0,0 @@
|
||||||
// Copyright 2012 The Go Authors. All rights reserved.
|
|
||||||
// Use of this source code is governed by a BSD-style
|
|
||||||
// license that can be found in the LICENSE file.
|
|
||||||
|
|
||||||
package binary
|
|
||||||
|
|
||||||
import "reflect"
|
|
||||||
|
|
||||||
// Export for testing.
|
|
||||||
|
|
||||||
func DataSize(v reflect.Value) int {
|
|
||||||
return dataSize(v)
|
|
||||||
}
|
|
||||||
|
|
||||||
var Overflow = overflow
|
|
|
@ -2,11 +2,10 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package binary_test
|
package binary
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
. "encoding/binary"
|
|
||||||
"io"
|
"io"
|
||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
@ -135,8 +134,8 @@ func testOverflow(t *testing.T, buf []byte, n0 int, err0 error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestOverflow(t *testing.T) {
|
func TestOverflow(t *testing.T) {
|
||||||
testOverflow(t, []byte{0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x2}, -10, Overflow)
|
testOverflow(t, []byte{0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x2}, -10, overflow)
|
||||||
testOverflow(t, []byte{0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x1, 0, 0}, -13, Overflow)
|
testOverflow(t, []byte{0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x1, 0, 0}, -13, overflow)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestNonCanonicalZero(t *testing.T) {
|
func TestNonCanonicalZero(t *testing.T) {
|
||||||
|
|
|
@ -2,15 +2,14 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package image_test
|
package image
|
||||||
|
|
||||||
import (
|
import (
|
||||||
. "image"
|
|
||||||
"image/color"
|
"image/color"
|
||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
||||||
type timage interface {
|
type image interface {
|
||||||
Image
|
Image
|
||||||
Opaque() bool
|
Opaque() bool
|
||||||
Set(int, int, color.Color)
|
Set(int, int, color.Color)
|
||||||
|
@ -24,7 +23,7 @@ func cmp(t *testing.T, cm color.Model, c0, c1 color.Color) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestImage(t *testing.T) {
|
func TestImage(t *testing.T) {
|
||||||
testImage := []timage{
|
testImage := []image{
|
||||||
NewRGBA(Rect(0, 0, 10, 10)),
|
NewRGBA(Rect(0, 0, 10, 10)),
|
||||||
NewRGBA64(Rect(0, 0, 10, 10)),
|
NewRGBA64(Rect(0, 0, 10, 10)),
|
||||||
NewNRGBA(Rect(0, 0, 10, 10)),
|
NewNRGBA(Rect(0, 0, 10, 10)),
|
||||||
|
@ -52,11 +51,11 @@ func TestImage(t *testing.T) {
|
||||||
t.Errorf("%T: at (6, 3), want a non-zero color, got %v", m, m.At(6, 3))
|
t.Errorf("%T: at (6, 3), want a non-zero color, got %v", m, m.At(6, 3))
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if !m.SubImage(Rect(6, 3, 7, 4)).(timage).Opaque() {
|
if !m.SubImage(Rect(6, 3, 7, 4)).(image).Opaque() {
|
||||||
t.Errorf("%T: at (6, 3) was not opaque", m)
|
t.Errorf("%T: at (6, 3) was not opaque", m)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
m = m.SubImage(Rect(3, 2, 9, 8)).(timage)
|
m = m.SubImage(Rect(3, 2, 9, 8)).(image)
|
||||||
if !Rect(3, 2, 9, 8).Eq(m.Bounds()) {
|
if !Rect(3, 2, 9, 8).Eq(m.Bounds()) {
|
||||||
t.Errorf("%T: sub-image want bounds %v, got %v", m, Rect(3, 2, 9, 8), m.Bounds())
|
t.Errorf("%T: sub-image want bounds %v, got %v", m, Rect(3, 2, 9, 8), m.Bounds())
|
||||||
continue
|
continue
|
||||||
|
@ -97,7 +96,7 @@ func Test16BitsPerColorChannel(t *testing.T) {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
testImage := []timage{
|
testImage := []image{
|
||||||
NewRGBA64(Rect(0, 0, 10, 10)),
|
NewRGBA64(Rect(0, 0, 10, 10)),
|
||||||
NewNRGBA64(Rect(0, 0, 10, 10)),
|
NewNRGBA64(Rect(0, 0, 10, 10)),
|
||||||
NewAlpha16(Rect(0, 0, 10, 10)),
|
NewAlpha16(Rect(0, 0, 10, 10)),
|
||||||
|
|
|
@ -2,10 +2,9 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package image_test
|
package image
|
||||||
|
|
||||||
import (
|
import (
|
||||||
. "image"
|
|
||||||
"image/color"
|
"image/color"
|
||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
|
@ -2,11 +2,10 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package regexp_test
|
package regexp
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"reflect"
|
"reflect"
|
||||||
. "regexp"
|
|
||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
|
@ -1,144 +0,0 @@
|
||||||
package regexp_test
|
|
||||||
|
|
||||||
import (
|
|
||||||
"fmt"
|
|
||||||
"regexp"
|
|
||||||
)
|
|
||||||
|
|
||||||
func Example() {
|
|
||||||
// Compile the expression once, usually at init time.
|
|
||||||
// Use raw strings to avoid having to quote the backslashes.
|
|
||||||
var validID = regexp.MustCompile(`^[a-z]+\[[0-9]+\]$`)
|
|
||||||
|
|
||||||
fmt.Println(validID.MatchString("adam[23]"))
|
|
||||||
fmt.Println(validID.MatchString("eve[7]"))
|
|
||||||
fmt.Println(validID.MatchString("Job[48]"))
|
|
||||||
fmt.Println(validID.MatchString("snakey"))
|
|
||||||
// Output:
|
|
||||||
// true
|
|
||||||
// true
|
|
||||||
// false
|
|
||||||
// false
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleMatchString() {
|
|
||||||
matched, err := regexp.MatchString("foo.*", "seafood")
|
|
||||||
fmt.Println(matched, err)
|
|
||||||
matched, err = regexp.MatchString("bar.*", "seafood")
|
|
||||||
fmt.Println(matched, err)
|
|
||||||
matched, err = regexp.MatchString("a(b", "seafood")
|
|
||||||
fmt.Println(matched, err)
|
|
||||||
// Output:
|
|
||||||
// true <nil>
|
|
||||||
// false <nil>
|
|
||||||
// false error parsing regexp: missing closing ): `a(b`
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_FindString() {
|
|
||||||
re := regexp.MustCompile("fo.?")
|
|
||||||
fmt.Printf("%q\n", re.FindString("seafood"))
|
|
||||||
fmt.Printf("%q\n", re.FindString("meat"))
|
|
||||||
// Output:
|
|
||||||
// "foo"
|
|
||||||
// ""
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_FindStringIndex() {
|
|
||||||
re := regexp.MustCompile("ab?")
|
|
||||||
fmt.Println(re.FindStringIndex("tablett"))
|
|
||||||
fmt.Println(re.FindStringIndex("foo") == nil)
|
|
||||||
// Output:
|
|
||||||
// [1 3]
|
|
||||||
// true
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_FindStringSubmatch() {
|
|
||||||
re := regexp.MustCompile("a(x*)b(y|z)c")
|
|
||||||
fmt.Printf("%q\n", re.FindStringSubmatch("-axxxbyc-"))
|
|
||||||
fmt.Printf("%q\n", re.FindStringSubmatch("-abzc-"))
|
|
||||||
// Output:
|
|
||||||
// ["axxxbyc" "xxx" "y"]
|
|
||||||
// ["abzc" "" "z"]
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_FindAllString() {
|
|
||||||
re := regexp.MustCompile("a.")
|
|
||||||
fmt.Println(re.FindAllString("paranormal", -1))
|
|
||||||
fmt.Println(re.FindAllString("paranormal", 2))
|
|
||||||
fmt.Println(re.FindAllString("graal", -1))
|
|
||||||
fmt.Println(re.FindAllString("none", -1))
|
|
||||||
// Output:
|
|
||||||
// [ar an al]
|
|
||||||
// [ar an]
|
|
||||||
// [aa]
|
|
||||||
// []
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_FindAllStringSubmatch() {
|
|
||||||
re := regexp.MustCompile("a(x*)b")
|
|
||||||
fmt.Printf("%q\n", re.FindAllStringSubmatch("-ab-", -1))
|
|
||||||
fmt.Printf("%q\n", re.FindAllStringSubmatch("-axxb-", -1))
|
|
||||||
fmt.Printf("%q\n", re.FindAllStringSubmatch("-ab-axb-", -1))
|
|
||||||
fmt.Printf("%q\n", re.FindAllStringSubmatch("-axxb-ab-", -1))
|
|
||||||
// Output:
|
|
||||||
// [["ab" ""]]
|
|
||||||
// [["axxb" "xx"]]
|
|
||||||
// [["ab" ""] ["axb" "x"]]
|
|
||||||
// [["axxb" "xx"] ["ab" ""]]
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_FindAllStringSubmatchIndex() {
|
|
||||||
re := regexp.MustCompile("a(x*)b")
|
|
||||||
// Indices:
|
|
||||||
// 01234567 012345678
|
|
||||||
// -ab-axb- -axxb-ab-
|
|
||||||
fmt.Println(re.FindAllStringSubmatchIndex("-ab-", -1))
|
|
||||||
fmt.Println(re.FindAllStringSubmatchIndex("-axxb-", -1))
|
|
||||||
fmt.Println(re.FindAllStringSubmatchIndex("-ab-axb-", -1))
|
|
||||||
fmt.Println(re.FindAllStringSubmatchIndex("-axxb-ab-", -1))
|
|
||||||
fmt.Println(re.FindAllStringSubmatchIndex("-foo-", -1))
|
|
||||||
// Output:
|
|
||||||
// [[1 3 2 2]]
|
|
||||||
// [[1 5 2 4]]
|
|
||||||
// [[1 3 2 2] [4 7 5 6]]
|
|
||||||
// [[1 5 2 4] [6 8 7 7]]
|
|
||||||
// []
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_ReplaceAllLiteralString() {
|
|
||||||
re := regexp.MustCompile("a(x*)b")
|
|
||||||
fmt.Println(re.ReplaceAllLiteralString("-ab-axxb-", "T"))
|
|
||||||
fmt.Println(re.ReplaceAllLiteralString("-ab-axxb-", "$1"))
|
|
||||||
fmt.Println(re.ReplaceAllLiteralString("-ab-axxb-", "${1}"))
|
|
||||||
// Output:
|
|
||||||
// -T-T-
|
|
||||||
// -$1-$1-
|
|
||||||
// -${1}-${1}-
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_ReplaceAllString() {
|
|
||||||
re := regexp.MustCompile("a(x*)b")
|
|
||||||
fmt.Println(re.ReplaceAllString("-ab-axxb-", "T"))
|
|
||||||
fmt.Println(re.ReplaceAllString("-ab-axxb-", "$1"))
|
|
||||||
fmt.Println(re.ReplaceAllString("-ab-axxb-", "$1W"))
|
|
||||||
fmt.Println(re.ReplaceAllString("-ab-axxb-", "${1}W"))
|
|
||||||
// Output:
|
|
||||||
// -T-T-
|
|
||||||
// --xx-
|
|
||||||
// ---
|
|
||||||
// -W-xxW-
|
|
||||||
}
|
|
||||||
|
|
||||||
func ExampleRegexp_SubexpNames() {
|
|
||||||
re := regexp.MustCompile("(?P<first>[a-zA-Z]+) (?P<last>[a-zA-Z]+)")
|
|
||||||
fmt.Println(re.MatchString("Alan Turing"))
|
|
||||||
fmt.Printf("%q\n", re.SubexpNames())
|
|
||||||
reversed := fmt.Sprintf("${%s} ${%s}", re.SubexpNames()[2], re.SubexpNames()[1])
|
|
||||||
fmt.Println(reversed)
|
|
||||||
fmt.Println(re.ReplaceAllString("Alan Turing", reversed))
|
|
||||||
// Output:
|
|
||||||
// true
|
|
||||||
// ["" "first" "last"]
|
|
||||||
// ${last} ${first}
|
|
||||||
// Turing Alan
|
|
||||||
}
|
|
|
@ -2,11 +2,9 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package regexp_test
|
package regexp
|
||||||
|
|
||||||
import (
|
import (
|
||||||
. "regexp"
|
|
||||||
|
|
||||||
"bufio"
|
"bufio"
|
||||||
"compress/bzip2"
|
"compress/bzip2"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
@ -220,22 +218,22 @@ var run = []func(*Regexp, *Regexp, string) ([]int, string){
|
||||||
}
|
}
|
||||||
|
|
||||||
func runFull(re, refull *Regexp, text string) ([]int, string) {
|
func runFull(re, refull *Regexp, text string) ([]int, string) {
|
||||||
refull.SetLongest(false)
|
refull.longest = false
|
||||||
return refull.FindStringSubmatchIndex(text), "[full]"
|
return refull.FindStringSubmatchIndex(text), "[full]"
|
||||||
}
|
}
|
||||||
|
|
||||||
func runPartial(re, refull *Regexp, text string) ([]int, string) {
|
func runPartial(re, refull *Regexp, text string) ([]int, string) {
|
||||||
re.SetLongest(false)
|
re.longest = false
|
||||||
return re.FindStringSubmatchIndex(text), ""
|
return re.FindStringSubmatchIndex(text), ""
|
||||||
}
|
}
|
||||||
|
|
||||||
func runFullLongest(re, refull *Regexp, text string) ([]int, string) {
|
func runFullLongest(re, refull *Regexp, text string) ([]int, string) {
|
||||||
refull.SetLongest(true)
|
refull.longest = true
|
||||||
return refull.FindStringSubmatchIndex(text), "[full,longest]"
|
return refull.FindStringSubmatchIndex(text), "[full,longest]"
|
||||||
}
|
}
|
||||||
|
|
||||||
func runPartialLongest(re, refull *Regexp, text string) ([]int, string) {
|
func runPartialLongest(re, refull *Regexp, text string) ([]int, string) {
|
||||||
re.SetLongest(true)
|
re.longest = true
|
||||||
return re.FindStringSubmatchIndex(text), "[longest]"
|
return re.FindStringSubmatchIndex(text), "[longest]"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -247,22 +245,22 @@ var match = []func(*Regexp, *Regexp, string) (bool, string){
|
||||||
}
|
}
|
||||||
|
|
||||||
func matchFull(re, refull *Regexp, text string) (bool, string) {
|
func matchFull(re, refull *Regexp, text string) (bool, string) {
|
||||||
refull.SetLongest(false)
|
refull.longest = false
|
||||||
return refull.MatchString(text), "[full]"
|
return refull.MatchString(text), "[full]"
|
||||||
}
|
}
|
||||||
|
|
||||||
func matchPartial(re, refull *Regexp, text string) (bool, string) {
|
func matchPartial(re, refull *Regexp, text string) (bool, string) {
|
||||||
re.SetLongest(false)
|
re.longest = false
|
||||||
return re.MatchString(text), ""
|
return re.MatchString(text), ""
|
||||||
}
|
}
|
||||||
|
|
||||||
func matchFullLongest(re, refull *Regexp, text string) (bool, string) {
|
func matchFullLongest(re, refull *Regexp, text string) (bool, string) {
|
||||||
refull.SetLongest(true)
|
refull.longest = true
|
||||||
return refull.MatchString(text), "[full,longest]"
|
return refull.MatchString(text), "[full,longest]"
|
||||||
}
|
}
|
||||||
|
|
||||||
func matchPartialLongest(re, refull *Regexp, text string) (bool, string) {
|
func matchPartialLongest(re, refull *Regexp, text string) (bool, string) {
|
||||||
re.SetLongest(true)
|
re.longest = true
|
||||||
return re.MatchString(text), "[longest]"
|
return re.MatchString(text), "[longest]"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -542,7 +540,7 @@ Reading:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
re, err := CompileInternal(pattern, syn, true)
|
re, err := compile(pattern, syn, true)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
if shouldCompile {
|
if shouldCompile {
|
||||||
t.Errorf("%s:%d: %#q did not compile", file, lineno, pattern)
|
t.Errorf("%s:%d: %#q did not compile", file, lineno, pattern)
|
||||||
|
|
|
@ -1,15 +0,0 @@
|
||||||
// Copyright 2012 The Go Authors. All rights reserved.
|
|
||||||
// Use of this source code is governed by a BSD-style
|
|
||||||
// license that can be found in the LICENSE file.
|
|
||||||
|
|
||||||
package regexp
|
|
||||||
|
|
||||||
import "regexp/syntax"
|
|
||||||
|
|
||||||
func (re *Regexp) SetLongest(b bool) {
|
|
||||||
re.longest = b
|
|
||||||
}
|
|
||||||
|
|
||||||
func CompileInternal(expr string, mode syntax.Flags, longest bool) (*Regexp, error) {
|
|
||||||
return compile(expr, mode, longest)
|
|
||||||
}
|
|
|
@ -2,11 +2,9 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package regexp_test
|
package regexp
|
||||||
|
|
||||||
import (
|
import (
|
||||||
. "regexp"
|
|
||||||
|
|
||||||
"fmt"
|
"fmt"
|
||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
|
@ -191,7 +191,7 @@ func (p *parser) newLiteral(r rune, flags Flags) *Regexp {
|
||||||
|
|
||||||
// minFoldRune returns the minimum rune fold-equivalent to r.
|
// minFoldRune returns the minimum rune fold-equivalent to r.
|
||||||
func minFoldRune(r rune) rune {
|
func minFoldRune(r rune) rune {
|
||||||
if r < MinFold || r > MaxFold {
|
if r < minFold || r > maxFold {
|
||||||
return r
|
return r
|
||||||
}
|
}
|
||||||
min := r
|
min := r
|
||||||
|
@ -1553,7 +1553,7 @@ func (p *parser) parseClass(s string) (rest string, err error) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if p.flags&FoldCase == 0 {
|
if p.flags&FoldCase == 0 {
|
||||||
class = AppendRange(class, lo, hi)
|
class = appendRange(class, lo, hi)
|
||||||
} else {
|
} else {
|
||||||
class = appendFoldedRange(class, lo, hi)
|
class = appendFoldedRange(class, lo, hi)
|
||||||
}
|
}
|
||||||
|
@ -1608,11 +1608,11 @@ func appendLiteral(r []rune, x rune, flags Flags) []rune {
|
||||||
if flags&FoldCase != 0 {
|
if flags&FoldCase != 0 {
|
||||||
return appendFoldedRange(r, x, x)
|
return appendFoldedRange(r, x, x)
|
||||||
}
|
}
|
||||||
return AppendRange(r, x, x)
|
return appendRange(r, x, x)
|
||||||
}
|
}
|
||||||
|
|
||||||
// appendRange returns the result of appending the range lo-hi to the class r.
|
// appendRange returns the result of appending the range lo-hi to the class r.
|
||||||
func AppendRange(r []rune, lo, hi rune) []rune {
|
func appendRange(r []rune, lo, hi rune) []rune {
|
||||||
// Expand last range or next to last range if it overlaps or abuts.
|
// Expand last range or next to last range if it overlaps or abuts.
|
||||||
// Checking two ranges helps when appending case-folded
|
// Checking two ranges helps when appending case-folded
|
||||||
// alphabets, so that one range can be expanding A-Z and the
|
// alphabets, so that one range can be expanding A-Z and the
|
||||||
|
@ -1639,39 +1639,39 @@ func AppendRange(r []rune, lo, hi rune) []rune {
|
||||||
const (
|
const (
|
||||||
// minimum and maximum runes involved in folding.
|
// minimum and maximum runes involved in folding.
|
||||||
// checked during test.
|
// checked during test.
|
||||||
MinFold = 0x0041
|
minFold = 0x0041
|
||||||
MaxFold = 0x1044f
|
maxFold = 0x1044f
|
||||||
)
|
)
|
||||||
|
|
||||||
// appendFoldedRange returns the result of appending the range lo-hi
|
// appendFoldedRange returns the result of appending the range lo-hi
|
||||||
// and its case folding-equivalent runes to the class r.
|
// and its case folding-equivalent runes to the class r.
|
||||||
func appendFoldedRange(r []rune, lo, hi rune) []rune {
|
func appendFoldedRange(r []rune, lo, hi rune) []rune {
|
||||||
// Optimizations.
|
// Optimizations.
|
||||||
if lo <= MinFold && hi >= MaxFold {
|
if lo <= minFold && hi >= maxFold {
|
||||||
// Range is full: folding can't add more.
|
// Range is full: folding can't add more.
|
||||||
return AppendRange(r, lo, hi)
|
return appendRange(r, lo, hi)
|
||||||
}
|
}
|
||||||
if hi < MinFold || lo > MaxFold {
|
if hi < minFold || lo > maxFold {
|
||||||
// Range is outside folding possibilities.
|
// Range is outside folding possibilities.
|
||||||
return AppendRange(r, lo, hi)
|
return appendRange(r, lo, hi)
|
||||||
}
|
}
|
||||||
if lo < MinFold {
|
if lo < minFold {
|
||||||
// [lo, MinFold-1] needs no folding.
|
// [lo, minFold-1] needs no folding.
|
||||||
r = AppendRange(r, lo, MinFold-1)
|
r = appendRange(r, lo, minFold-1)
|
||||||
lo = MinFold
|
lo = minFold
|
||||||
}
|
}
|
||||||
if hi > MaxFold {
|
if hi > maxFold {
|
||||||
// [MaxFold+1, hi] needs no folding.
|
// [maxFold+1, hi] needs no folding.
|
||||||
r = AppendRange(r, MaxFold+1, hi)
|
r = appendRange(r, maxFold+1, hi)
|
||||||
hi = MaxFold
|
hi = maxFold
|
||||||
}
|
}
|
||||||
|
|
||||||
// Brute force. Depend on AppendRange to coalesce ranges on the fly.
|
// Brute force. Depend on appendRange to coalesce ranges on the fly.
|
||||||
for c := lo; c <= hi; c++ {
|
for c := lo; c <= hi; c++ {
|
||||||
r = AppendRange(r, c, c)
|
r = appendRange(r, c, c)
|
||||||
f := unicode.SimpleFold(c)
|
f := unicode.SimpleFold(c)
|
||||||
for f != c {
|
for f != c {
|
||||||
r = AppendRange(r, f, f)
|
r = appendRange(r, f, f)
|
||||||
f = unicode.SimpleFold(f)
|
f = unicode.SimpleFold(f)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1682,7 +1682,7 @@ func appendFoldedRange(r []rune, lo, hi rune) []rune {
|
||||||
// It assume x is clean.
|
// It assume x is clean.
|
||||||
func appendClass(r []rune, x []rune) []rune {
|
func appendClass(r []rune, x []rune) []rune {
|
||||||
for i := 0; i < len(x); i += 2 {
|
for i := 0; i < len(x); i += 2 {
|
||||||
r = AppendRange(r, x[i], x[i+1])
|
r = appendRange(r, x[i], x[i+1])
|
||||||
}
|
}
|
||||||
return r
|
return r
|
||||||
}
|
}
|
||||||
|
@ -1702,12 +1702,12 @@ func appendNegatedClass(r []rune, x []rune) []rune {
|
||||||
for i := 0; i < len(x); i += 2 {
|
for i := 0; i < len(x); i += 2 {
|
||||||
lo, hi := x[i], x[i+1]
|
lo, hi := x[i], x[i+1]
|
||||||
if nextLo <= lo-1 {
|
if nextLo <= lo-1 {
|
||||||
r = AppendRange(r, nextLo, lo-1)
|
r = appendRange(r, nextLo, lo-1)
|
||||||
}
|
}
|
||||||
nextLo = hi + 1
|
nextLo = hi + 1
|
||||||
}
|
}
|
||||||
if nextLo <= unicode.MaxRune {
|
if nextLo <= unicode.MaxRune {
|
||||||
r = AppendRange(r, nextLo, unicode.MaxRune)
|
r = appendRange(r, nextLo, unicode.MaxRune)
|
||||||
}
|
}
|
||||||
return r
|
return r
|
||||||
}
|
}
|
||||||
|
@ -1717,21 +1717,21 @@ func appendTable(r []rune, x *unicode.RangeTable) []rune {
|
||||||
for _, xr := range x.R16 {
|
for _, xr := range x.R16 {
|
||||||
lo, hi, stride := rune(xr.Lo), rune(xr.Hi), rune(xr.Stride)
|
lo, hi, stride := rune(xr.Lo), rune(xr.Hi), rune(xr.Stride)
|
||||||
if stride == 1 {
|
if stride == 1 {
|
||||||
r = AppendRange(r, lo, hi)
|
r = appendRange(r, lo, hi)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
for c := lo; c <= hi; c += stride {
|
for c := lo; c <= hi; c += stride {
|
||||||
r = AppendRange(r, c, c)
|
r = appendRange(r, c, c)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for _, xr := range x.R32 {
|
for _, xr := range x.R32 {
|
||||||
lo, hi, stride := rune(xr.Lo), rune(xr.Hi), rune(xr.Stride)
|
lo, hi, stride := rune(xr.Lo), rune(xr.Hi), rune(xr.Stride)
|
||||||
if stride == 1 {
|
if stride == 1 {
|
||||||
r = AppendRange(r, lo, hi)
|
r = appendRange(r, lo, hi)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
for c := lo; c <= hi; c += stride {
|
for c := lo; c <= hi; c += stride {
|
||||||
r = AppendRange(r, c, c)
|
r = appendRange(r, c, c)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return r
|
return r
|
||||||
|
@ -1744,14 +1744,14 @@ func appendNegatedTable(r []rune, x *unicode.RangeTable) []rune {
|
||||||
lo, hi, stride := rune(xr.Lo), rune(xr.Hi), rune(xr.Stride)
|
lo, hi, stride := rune(xr.Lo), rune(xr.Hi), rune(xr.Stride)
|
||||||
if stride == 1 {
|
if stride == 1 {
|
||||||
if nextLo <= lo-1 {
|
if nextLo <= lo-1 {
|
||||||
r = AppendRange(r, nextLo, lo-1)
|
r = appendRange(r, nextLo, lo-1)
|
||||||
}
|
}
|
||||||
nextLo = hi + 1
|
nextLo = hi + 1
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
for c := lo; c <= hi; c += stride {
|
for c := lo; c <= hi; c += stride {
|
||||||
if nextLo <= c-1 {
|
if nextLo <= c-1 {
|
||||||
r = AppendRange(r, nextLo, c-1)
|
r = appendRange(r, nextLo, c-1)
|
||||||
}
|
}
|
||||||
nextLo = c + 1
|
nextLo = c + 1
|
||||||
}
|
}
|
||||||
|
@ -1760,20 +1760,20 @@ func appendNegatedTable(r []rune, x *unicode.RangeTable) []rune {
|
||||||
lo, hi, stride := rune(xr.Lo), rune(xr.Hi), rune(xr.Stride)
|
lo, hi, stride := rune(xr.Lo), rune(xr.Hi), rune(xr.Stride)
|
||||||
if stride == 1 {
|
if stride == 1 {
|
||||||
if nextLo <= lo-1 {
|
if nextLo <= lo-1 {
|
||||||
r = AppendRange(r, nextLo, lo-1)
|
r = appendRange(r, nextLo, lo-1)
|
||||||
}
|
}
|
||||||
nextLo = hi + 1
|
nextLo = hi + 1
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
for c := lo; c <= hi; c += stride {
|
for c := lo; c <= hi; c += stride {
|
||||||
if nextLo <= c-1 {
|
if nextLo <= c-1 {
|
||||||
r = AppendRange(r, nextLo, c-1)
|
r = appendRange(r, nextLo, c-1)
|
||||||
}
|
}
|
||||||
nextLo = c + 1
|
nextLo = c + 1
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if nextLo <= unicode.MaxRune {
|
if nextLo <= unicode.MaxRune {
|
||||||
r = AppendRange(r, nextLo, unicode.MaxRune)
|
r = appendRange(r, nextLo, unicode.MaxRune)
|
||||||
}
|
}
|
||||||
return r
|
return r
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,12 +2,11 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package syntax_test
|
package syntax
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"fmt"
|
"fmt"
|
||||||
. "regexp/syntax"
|
|
||||||
"testing"
|
"testing"
|
||||||
"unicode"
|
"unicode"
|
||||||
)
|
)
|
||||||
|
@ -413,13 +412,13 @@ func TestFoldConstants(t *testing.T) {
|
||||||
if unicode.SimpleFold(i) == i {
|
if unicode.SimpleFold(i) == i {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if last == -1 && MinFold != i {
|
if last == -1 && minFold != i {
|
||||||
t.Errorf("MinFold=%#U should be %#U", MinFold, i)
|
t.Errorf("minFold=%#U should be %#U", minFold, i)
|
||||||
}
|
}
|
||||||
last = i
|
last = i
|
||||||
}
|
}
|
||||||
if MaxFold != last {
|
if maxFold != last {
|
||||||
t.Errorf("MaxFold=%#U should be %#U", MaxFold, last)
|
t.Errorf("maxFold=%#U should be %#U", maxFold, last)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -430,11 +429,11 @@ func TestAppendRangeCollapse(t *testing.T) {
|
||||||
// Note that we are not calling cleanClass.
|
// Note that we are not calling cleanClass.
|
||||||
var r []rune
|
var r []rune
|
||||||
for i := rune('A'); i <= 'Z'; i++ {
|
for i := rune('A'); i <= 'Z'; i++ {
|
||||||
r = AppendRange(r, i, i)
|
r = appendRange(r, i, i)
|
||||||
r = AppendRange(r, i+'a'-'A', i+'a'-'A')
|
r = appendRange(r, i+'a'-'A', i+'a'-'A')
|
||||||
}
|
}
|
||||||
if string(r) != "AZaz" {
|
if string(r) != "AZaz" {
|
||||||
t.Errorf("AppendRange interlaced A-Z a-z = %s, want AZaz", string(r))
|
t.Errorf("appendRange interlaced A-Z a-z = %s, want AZaz", string(r))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -2,10 +2,9 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package syntax_test
|
package syntax
|
||||||
|
|
||||||
import (
|
import (
|
||||||
. "regexp/syntax"
|
|
||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
|
@ -2,9 +2,8 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package syntax_test
|
package syntax
|
||||||
|
|
||||||
import . "regexp/syntax"
|
|
||||||
import "testing"
|
import "testing"
|
||||||
|
|
||||||
var simplifyTests = []struct {
|
var simplifyTests = []struct {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue