summaryrefslogtreecommitdiffstats
path: root/vendor/modernc.org/memory
diff options
context:
space:
mode:
Diffstat (limited to 'vendor/modernc.org/memory')
-rw-r--r--vendor/modernc.org/memory/AUTHORS12
-rw-r--r--vendor/modernc.org/memory/CONTRIBUTORS10
-rw-r--r--vendor/modernc.org/memory/LICENSE27
-rw-r--r--vendor/modernc.org/memory/LICENSE-MMAP-GO25
-rw-r--r--vendor/modernc.org/memory/Makefile66
-rw-r--r--vendor/modernc.org/memory/README.md13
-rw-r--r--vendor/modernc.org/memory/counters.go9
-rw-r--r--vendor/modernc.org/memory/memory.go542
-rw-r--r--vendor/modernc.org/memory/memory32.go9
-rw-r--r--vendor/modernc.org/memory/memory64.go9
-rw-r--r--vendor/modernc.org/memory/mmap_unix.go69
-rw-r--r--vendor/modernc.org/memory/mmap_windows.go49
-rw-r--r--vendor/modernc.org/memory/nocounters.go9
-rw-r--r--vendor/modernc.org/memory/trace_disabled.go9
-rw-r--r--vendor/modernc.org/memory/trace_enabled.go9
15 files changed, 867 insertions, 0 deletions
diff --git a/vendor/modernc.org/memory/AUTHORS b/vendor/modernc.org/memory/AUTHORS
new file mode 100644
index 00000000..50f44cec
--- /dev/null
+++ b/vendor/modernc.org/memory/AUTHORS
@@ -0,0 +1,12 @@
+# This file lists authors for copyright purposes. This file is distinct from
+# the CONTRIBUTORS files. See the latter for an explanation.
+#
+# Names should be added to this file as:
+# Name or Organization <email address>
+#
+# The email address is not required for organizations.
+#
+# Please keep the list sorted.
+
+Jan Mercl <0xjnml@gmail.com>
+Steffen Butzer <steffen(dot)butzer@outlook.com>
diff --git a/vendor/modernc.org/memory/CONTRIBUTORS b/vendor/modernc.org/memory/CONTRIBUTORS
new file mode 100644
index 00000000..988458ca
--- /dev/null
+++ b/vendor/modernc.org/memory/CONTRIBUTORS
@@ -0,0 +1,10 @@
+# This file lists people who contributed code to this repository. The AUTHORS
+# file lists the copyright holders; this file lists people.
+#
+# Names should be added to this file like so:
+# Name <email address>
+#
+# Please keep the list sorted.
+
+Jan Mercl <0xjnml@gmail.com>
+Steffen Butzer <steffen(dot)butzer@outlook.com>
diff --git a/vendor/modernc.org/memory/LICENSE b/vendor/modernc.org/memory/LICENSE
new file mode 100644
index 00000000..967339af
--- /dev/null
+++ b/vendor/modernc.org/memory/LICENSE
@@ -0,0 +1,27 @@
+Copyright (c) 2017 The Memory Authors. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the names of the authors nor the names of the
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/vendor/modernc.org/memory/LICENSE-MMAP-GO b/vendor/modernc.org/memory/LICENSE-MMAP-GO
new file mode 100644
index 00000000..8f05f338
--- /dev/null
+++ b/vendor/modernc.org/memory/LICENSE-MMAP-GO
@@ -0,0 +1,25 @@
+Copyright (c) 2011, Evan Shaw <edsrzf@gmail.com>
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+ * Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the distribution.
+ * Neither the name of the copyright holder nor the
+ names of its contributors may be used to endorse or promote products
+ derived from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+DISCLAIMED. IN NO EVENT SHALL <COPYRIGHT HOLDER> BE LIABLE FOR ANY
+DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
diff --git a/vendor/modernc.org/memory/Makefile b/vendor/modernc.org/memory/Makefile
new file mode 100644
index 00000000..fbb3e4ee
--- /dev/null
+++ b/vendor/modernc.org/memory/Makefile
@@ -0,0 +1,66 @@
+# Copyright 2017 The Memory Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style
+# license that can be found in the LICENSE file.
+
+.PHONY: all clean cover cpu editor internalError later mem nuke todo edit
+
+grep=--include=*.go --include=*.l --include=*.y --include=*.yy
+ngrep='TODOOK\|parser\.go\|scanner\.go\|.*_string\.go'
+
+all: editor
+ go vet 2>&1 | grep -v $(ngrep) || true
+ golint 2>&1 | grep -v $(ngrep) || true
+ make todo
+ misspell *.go
+ maligned || true
+ unconvert -apply
+ staticcheck | grep -v 'lexer\.go' || true
+ grep -n 'FAIL\|PASS' log
+ date
+
+clean:
+ go clean
+ rm -f *~ *.test *.out
+
+cover:
+ t=$(shell tempfile) ; go test -coverprofile $$t && go tool cover -html $$t && unlink $$t
+
+cpu: clean
+ go test -run @ -bench . -cpuprofile cpu.out
+ go tool pprof -lines *.test cpu.out
+
+edit:
+ @ 1>/dev/null 2>/dev/null gvim -p Makefile *.go &
+
+editor:
+ gofmt -l -s -w *.go
+ GOOS=darwin GOARCH=amd64 go build
+ GOOS=darwin GOARCH=arm64 go build
+ GOOS=linux GOARCH=386 go build
+ GOOS=linux GOARCH=amd64 go build
+ GOOS=linux GOARCH=arm go build
+ GOOS=linux GOARCH=arm64 go build
+ GOOS=linux GOARCH=s390x go build
+ GOOS=windows GOARCH=386 go build
+ GOOS=windows GOARCH=amd64 go build
+ go test 2>&1 | tee log
+
+internalError:
+ egrep -ho '"internal error.*"' *.go | sort | cat -n
+
+later:
+ @grep -n $(grep) LATER * || true
+ @grep -n $(grep) MAYBE * || true
+
+mem: clean
+ go test -run @ -bench . -memprofile mem.out -memprofilerate 1 -timeout 24h
+ go tool pprof -lines -web -alloc_space *.test mem.out
+
+nuke: clean
+ go clean -i
+
+todo:
+ @grep -nr $(grep) ^[[:space:]]*_[[:space:]]*=[[:space:]][[:alpha:]][[:alnum:]]* * | grep -v $(ngrep) || true
+ @grep -nr $(grep) TODO * | grep -v $(ngrep) || true
+ @grep -nr $(grep) BUG * | grep -v $(ngrep) || true
+ @grep -nr $(grep) [^[:alpha:]]println * | grep -v $(ngrep) || true
diff --git a/vendor/modernc.org/memory/README.md b/vendor/modernc.org/memory/README.md
new file mode 100644
index 00000000..9354a365
--- /dev/null
+++ b/vendor/modernc.org/memory/README.md
@@ -0,0 +1,13 @@
+# memory
+
+Package memory implements a memory allocator.
+
+## Build status
+
+available at https://modern-c.appspot.com/-/builder/?importpath=modernc.org%2fmemory
+
+Installation
+
+ $ go get modernc.org/memory
+
+Documentation: [godoc.org/modernc.org/memory](http://godoc.org/modernc.org/memory)
diff --git a/vendor/modernc.org/memory/counters.go b/vendor/modernc.org/memory/counters.go
new file mode 100644
index 00000000..ca4024fc
--- /dev/null
+++ b/vendor/modernc.org/memory/counters.go
@@ -0,0 +1,9 @@
+// Copyright 2017 The Memory Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+// +build memory.counters
+
+package memory // import "modernc.org/memory"
+
+const counters = true
diff --git a/vendor/modernc.org/memory/memory.go b/vendor/modernc.org/memory/memory.go
new file mode 100644
index 00000000..bbfaffcf
--- /dev/null
+++ b/vendor/modernc.org/memory/memory.go
@@ -0,0 +1,542 @@
+// Copyright 2017 The Memory 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 memory implements a memory allocator.
+//
+// Build status
+//
+// available at https://modern-c.appspot.com/-/builder/?importpath=modernc.org%2fmemory
+//
+// Changelog
+//
+// 2017-10-03 Added alternative, unsafe.Pointer-based API.
+//
+// Package memory implements a memory allocator.
+//
+// Changelog
+//
+// 2017-10-03 Added alternative, unsafe.Pointer-based API.
+//
+// Benchmarks
+//
+// AMD Ryzen 9 3900X 12-Core Processor × 24
+//
+// jnml@3900x:~/src/modernc.org/memory$ date ; go version ; go test -run @ -bench . -benchmem |& tee log
+// Fri Nov 20 17:23:04 CET 2020
+// go version go1.15.5 linux/amd64
+// goos: linux
+// goarch: amd64
+// pkg: modernc.org/memory
+// BenchmarkFree16-24 141188362 8.26 ns/op 0 B/op 0 allocs/op
+// BenchmarkFree32-24 100000000 11.4 ns/op 0 B/op 0 allocs/op
+// BenchmarkFree64-24 67160647 18.3 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc16-24 60612698 19.8 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc32-24 47968105 23.8 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc64-24 40752181 28.6 ns/op 0 B/op 0 allocs/op
+// BenchmarkGoCalloc16-24 66487354 17.8 ns/op 16 B/op 1 allocs/op
+// BenchmarkGoCalloc32-24 56009206 21.2 ns/op 32 B/op 1 allocs/op
+// BenchmarkGoCalloc64-24 52086571 23.4 ns/op 64 B/op 1 allocs/op
+// BenchmarkMalloc16-24 113943390 10.2 ns/op 0 B/op 0 allocs/op
+// BenchmarkMalloc32-24 113520471 10.2 ns/op 0 B/op 0 allocs/op
+// BenchmarkMalloc64-24 108787056 10.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree16-24 146110286 7.94 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree32-24 93052707 12.0 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree64-24 69805262 17.3 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc16-24 85282725 13.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc32-24 66489789 17.9 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc64-24 53561092 22.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc16-24 222978858 5.28 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc32-24 210443384 5.30 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc64-24 213706227 5.47 ns/op 0 B/op 0 allocs/op
+// PASS
+// ok modernc.org/memory 70.528s
+// jnml@3900x:~/src/modernc.org/memory$
+//
+// Intel® Core™ i5-4670 CPU @ 3.40GHz × 4
+//
+// ==== jnml@4670:~/src/modernc.org/memory> date ; go version ; go test -run @ -bench . -benchmem |& tee log
+// Sat Dec 8 12:56:53 CET 2018
+// go version go1.11.2 linux/amd64
+// goos: linux
+// goarch: amd64
+// pkg: modernc.org/memory
+// BenchmarkFree16-4 100000000 14.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkFree32-4 100000000 20.5 ns/op 0 B/op 0 allocs/op
+// BenchmarkFree64-4 50000000 32.8 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc16-4 50000000 24.4 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc32-4 50000000 29.2 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc64-4 50000000 35.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkGoCalloc16-4 50000000 27.0 ns/op 16 B/op 1 allocs/op
+// BenchmarkGoCalloc32-4 50000000 27.3 ns/op 32 B/op 1 allocs/op
+// BenchmarkGoCalloc64-4 30000000 37.9 ns/op 64 B/op 1 allocs/op
+// BenchmarkMalloc16-4 100000000 12.9 ns/op 0 B/op 0 allocs/op
+// BenchmarkMalloc32-4 100000000 12.9 ns/op 0 B/op 0 allocs/op
+// BenchmarkMalloc64-4 100000000 13.2 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree16-4 100000000 12.0 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree32-4 100000000 17.5 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree64-4 50000000 28.9 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc16-4 100000000 17.8 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc32-4 100000000 22.9 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc64-4 50000000 29.6 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc16-4 200000000 7.31 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc32-4 200000000 7.47 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc64-4 200000000 7.68 ns/op 0 B/op 0 allocs/op
+// PASS
+// ok modernc.org/memory 73.859s
+// //
+// Intel® Xeon(R) CPU E5-1650 v2 @ 3.50GHz × 12
+//
+// ==== jnml@e5-1650:~/src/modernc.org/memory> date ; go version ; go test -run @ -bench . -benchmem
+// Fri Dec 7 14:18:50 CET 2018
+// go version go1.11.2 linux/amd64
+// goos: linux
+// goarch: amd64
+// pkg: modernc.org/memory
+// BenchmarkFree16-12 100000000 16.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkFree32-12 50000000 25.0 ns/op 0 B/op 0 allocs/op
+// BenchmarkFree64-12 30000000 39.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc16-12 50000000 26.3 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc32-12 50000000 33.4 ns/op 0 B/op 0 allocs/op
+// BenchmarkCalloc64-12 30000000 38.3 ns/op 0 B/op 0 allocs/op
+// BenchmarkGoCalloc16-12 50000000 26.6 ns/op 16 B/op 1 allocs/op
+// BenchmarkGoCalloc32-12 50000000 26.8 ns/op 32 B/op 1 allocs/op
+// BenchmarkGoCalloc64-12 30000000 35.1 ns/op 64 B/op 1 allocs/op
+// BenchmarkMalloc16-12 100000000 13.5 ns/op 0 B/op 0 allocs/op
+// BenchmarkMalloc32-12 100000000 13.4 ns/op 0 B/op 0 allocs/op
+// BenchmarkMalloc64-12 100000000 14.1 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree16-12 100000000 14.4 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree32-12 100000000 21.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrFree64-12 50000000 36.7 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc16-12 100000000 20.4 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc32-12 50000000 27.1 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrCalloc64-12 50000000 33.4 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc16-12 200000000 8.02 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc32-12 200000000 8.28 ns/op 0 B/op 0 allocs/op
+// BenchmarkUintptrMalloc64-12 200000000 8.29 ns/op 0 B/op 0 allocs/op
+// PASS
+// ok modernc.org/memory 80.896s
+package memory // import "modernc.org/memory"
+
+import (
+ "fmt"
+ "math/bits"
+ "os"
+ "reflect"
+ "unsafe"
+)
+
+const (
+ headerSize = unsafe.Sizeof(page{})
+ mallocAllign = 2 * unsafe.Sizeof(uintptr(0))
+ maxSlotSize = 1 << maxSlotSizeLog
+ maxSlotSizeLog = pageSizeLog - 2
+ pageAvail = pageSize - headerSize
+ pageMask = pageSize - 1
+ pageSize = 1 << pageSizeLog
+)
+
+func init() {
+ if unsafe.Sizeof(page{})%mallocAllign != 0 {
+ panic("internal error")
+ }
+}
+
+// if n%m != 0 { n += m-n%m }. m must be a power of 2.
+func roundup(n, m int) int { return (n + m - 1) &^ (m - 1) }
+
+type node struct {
+ prev, next uintptr // *node
+}
+
+type page struct {
+ brk int
+ log uint
+ size int
+ used int
+}
+
+// Allocator allocates and frees memory. Its zero value is ready for use. The
+// exported counters are updated only when build tag memory.counters is
+// present.
+type Allocator struct {
+ Allocs int // # of allocs.
+ Bytes int // Asked from OS.
+ cap [64]int
+ lists [64]uintptr // *node
+ Mmaps int // Asked from OS.
+ pages [64]uintptr // *page
+ regs map[uintptr]struct{} // map[*page]struct{}
+}
+
+func (a *Allocator) mmap(size int) (uintptr /* *page */, error) {
+ p, size, err := mmap(size)
+ if err != nil {
+ return 0, err
+ }
+
+ if counters {
+ a.Mmaps++
+ a.Bytes += size
+ }
+ if a.regs == nil {
+ a.regs = map[uintptr]struct{}{}
+ }
+ (*page)(unsafe.Pointer(p)).size = size
+ a.regs[p] = struct{}{}
+ return p, nil
+}
+
+func (a *Allocator) newPage(size int) (uintptr /* *page */, error) {
+ size += int(headerSize)
+ p, err := a.mmap(size)
+ if err != nil {
+ return 0, err
+ }
+
+ (*page)(unsafe.Pointer(p)).log = 0
+ return p, nil
+}
+
+func (a *Allocator) newSharedPage(log uint) (uintptr /* *page */, error) {
+ if a.cap[log] == 0 {
+ a.cap[log] = int(pageAvail) / (1 << log)
+ }
+ size := int(headerSize) + a.cap[log]<<log
+ p, err := a.mmap(size)
+ if err != nil {
+ return 0, err
+ }
+
+ a.pages[log] = p
+ (*page)(unsafe.Pointer(p)).log = log
+ return p, nil
+}
+
+func (a *Allocator) unmap(p uintptr /* *page */) error {
+ delete(a.regs, p)
+ if counters {
+ a.Mmaps--
+ }
+ return unmap(p, (*page)(unsafe.Pointer(p)).size)
+}
+
+// UintptrCalloc is like Calloc except it returns an uintptr.
+func (a *Allocator) UintptrCalloc(size int) (r uintptr, err error) {
+ if trace {
+ defer func() {
+ fmt.Fprintf(os.Stderr, "Calloc(%#x) %#x, %v\n", size, r, err)
+ }()
+ }
+ if r, err = a.UintptrMalloc(size); r == 0 || err != nil {
+ return 0, err
+ }
+ b := ((*rawmem)(unsafe.Pointer(r)))[:size:size]
+ for i := range b {
+ b[i] = 0
+ }
+ return r, nil
+}
+
+// UintptrFree is like Free except its argument is an uintptr, which must have
+// been acquired from UintptrCalloc or UintptrMalloc or UintptrRealloc.
+func (a *Allocator) UintptrFree(p uintptr) (err error) {
+ if trace {
+ defer func() {
+ fmt.Fprintf(os.Stderr, "Free(%#x) %v\n", p, err)
+ }()
+ }
+ if p == 0 {
+ return nil
+ }
+
+ if counters {
+ a.Allocs--
+ }
+ pg := p &^ uintptr(pageMask)
+ log := (*page)(unsafe.Pointer(pg)).log
+ if log == 0 {
+ if counters {
+ a.Bytes -= (*page)(unsafe.Pointer(pg)).size
+ }
+ return a.unmap(pg)
+ }
+
+ (*node)(unsafe.Pointer(p)).prev = 0
+ (*node)(unsafe.Pointer(p)).next = a.lists[log]
+ if next := (*node)(unsafe.Pointer(p)).next; next != 0 {
+ (*node)(unsafe.Pointer(next)).prev = p
+ }
+ a.lists[log] = p
+ (*page)(unsafe.Pointer(pg)).used--
+ if (*page)(unsafe.Pointer(pg)).used != 0 {
+ return nil
+ }
+
+ for i := 0; i < (*page)(unsafe.Pointer(pg)).brk; i++ {
+ n := pg + headerSize + uintptr(i)<<log
+ next := (*node)(unsafe.Pointer(n)).next
+ prev := (*node)(unsafe.Pointer(n)).prev
+ switch {
+ case prev == 0:
+ a.lists[log] = next
+ if next != 0 {
+ (*node)(unsafe.Pointer(next)).prev = 0
+ }
+ case next == 0:
+ (*node)(unsafe.Pointer(prev)).next = 0
+ default:
+ (*node)(unsafe.Pointer(prev)).next = next
+ (*node)(unsafe.Pointer(next)).prev = prev
+ }
+ }
+
+ if a.pages[log] == pg {
+ a.pages[log] = 0
+ }
+ if counters {
+ a.Bytes -= (*page)(unsafe.Pointer(pg)).size
+ }
+ return a.unmap(pg)
+}
+
+// UintptrMalloc is like Malloc except it returns an uinptr.
+func (a *Allocator) UintptrMalloc(size int) (r uintptr, err error) {
+ if trace {
+ defer func() {
+ fmt.Fprintf(os.Stderr, "Malloc(%#x) %#x, %v\n", size, r, err)
+ }()
+ }
+ if size < 0 {
+ panic("invalid malloc size")
+ }
+
+ if size == 0 {
+ return 0, nil
+ }
+
+ if counters {
+ a.Allocs++
+ }
+ log := uint(bits.Len(uint((size+int(mallocAllign)-1)&^int(mallocAllign-1) - 1)))
+ if log > maxSlotSizeLog {
+ p, err := a.newPage(size)
+ if err != nil {
+ return 0, err
+ }
+
+ return p + headerSize, nil
+ }
+
+ if a.lists[log] == 0 && a.pages[log] == 0 {
+ if _, err := a.newSharedPage(log); err != nil {
+ return 0, err
+ }
+ }
+
+ if p := a.pages[log]; p != 0 {
+ (*page)(unsafe.Pointer(p)).used++
+ (*page)(unsafe.Pointer(p)).brk++
+ if (*page)(unsafe.Pointer(p)).brk == a.cap[log] {
+ a.pages[log] = 0
+ }
+ return p + headerSize + uintptr((*page)(unsafe.Pointer(p)).brk-1)<<log, nil
+ }
+
+ n := a.lists[log]
+ p := n &^ uintptr(pageMask)
+ a.lists[log] = (*node)(unsafe.Pointer(n)).next
+ if next := (*node)(unsafe.Pointer(n)).next; next != 0 {
+ (*node)(unsafe.Pointer(next)).prev = 0
+ }
+ (*page)(unsafe.Pointer(p)).used++
+ return n, nil
+}
+
+// UintptrRealloc is like Realloc except its first argument is an uintptr,
+// which must have been returned from UintptrCalloc, UintptrMalloc or
+// UintptrRealloc.
+func (a *Allocator) UintptrRealloc(p uintptr, size int) (r uintptr, err error) {
+ if trace {
+ defer func() {
+ fmt.Fprintf(os.Stderr, "UnsafeRealloc(%#x, %#x) %#x, %v\n", p, size, r, err)
+ }()
+ }
+ switch {
+ case p == 0:
+ return a.UintptrMalloc(size)
+ case size == 0 && p != 0:
+ return 0, a.UintptrFree(p)
+ }
+
+ us := UintptrUsableSize(p)
+ if us > size {
+ return p, nil
+ }
+
+ if r, err = a.UintptrMalloc(size); err != nil {
+ return 0, err
+ }
+
+ if us < size {
+ size = us
+ }
+ copy((*rawmem)(unsafe.Pointer(r))[:size:size], (*rawmem)(unsafe.Pointer(p))[:size:size])
+ return r, a.UintptrFree(p)
+}
+
+// UintptrUsableSize is like UsableSize except its argument is an uintptr,
+// which must have been returned from UintptrCalloc, UintptrMalloc or
+// UintptrRealloc.
+func UintptrUsableSize(p uintptr) (r int) {
+ if trace {
+ defer func() {
+ fmt.Fprintf(os.Stderr, "UsableSize(%#x) %#x\n", p, r)
+ }()
+ }
+ if p == 0 {
+ return 0
+ }
+
+ return usableSize(p)
+}
+
+func usableSize(p uintptr) (r int) {
+ pg := p &^ uintptr(pageMask)
+ if log := (*page)(unsafe.Pointer(pg)).log; log != 0 {
+ return 1 << log
+ }
+
+ return (*page)(unsafe.Pointer(pg)).size - int(headerSize)
+}
+
+// Calloc is like Malloc except the allocated memory is zeroed.
+func (a *Allocator) Calloc(size int) (r []byte, err error) {
+ p, err := a.UintptrCalloc(size)
+ if err != nil {
+ return nil, err
+ }
+
+ var b []byte
+ sh := (*reflect.SliceHeader)(unsafe.Pointer(&b))
+ sh.Cap = usableSize(p)
+ sh.Data = p
+ sh.Len = size
+ return b, nil
+}
+
+// Close releases all OS resources used by a and sets it to its zero value.
+//
+// It's not necessary to Close the Allocator when exiting a process.
+func (a *Allocator) Close() (err error) {
+ for p := range a.regs {
+ if e := a.unmap(p); e != nil && err == nil {
+ err = e
+ }
+ }
+ *a = Allocator{}
+ return err
+}
+
+// Free deallocates memory (as in C.free). The argument of Free must have been
+// acquired from Calloc or Malloc or Realloc.
+func (a *Allocator) Free(b []byte) (err error) {
+ if b = b[:cap(b)]; len(b) == 0 {
+ return nil
+ }
+
+ return a.UintptrFree(uintptr(unsafe.Pointer(&b[0])))
+}
+
+// Malloc allocates size bytes and returns a byte slice of the allocated
+// memory. The memory is not initialized. Malloc panics for size < 0 and
+// returns (nil, nil) for zero size.
+//
+// It's ok to reslice the returned slice but the result of appending to it
+// cannot be passed to Free or Realloc as it may refer to a different backing
+// array afterwards.
+func (a *Allocator) Malloc(size int) (r []byte, err error) {
+ p, err := a.UintptrMalloc(size)
+ if p == 0 || err != nil {
+ return nil, err
+ }
+
+ sh := (*reflect.SliceHeader)(unsafe.Pointer(&r))
+ sh.Cap = usableSize(p)
+ sh.Data = p
+ sh.Len = size
+ return r, nil
+}
+
+// Realloc changes the size of the backing array of b to size bytes or returns
+// an error, if any. The contents will be unchanged in the range from the
+// start of the region up to the minimum of the old and new sizes. If the
+// new size is larger than the old size, the added memory will not be
+// initialized. If b's backing array is of zero size, then the call is
+// equivalent to Malloc(size), for all values of size; if size is equal to
+// zero, and b's backing array is not of zero size, then the call is equivalent
+// to Free(b). Unless b's backing array is of zero size, it must have been
+// returned by an earlier call to Malloc, Calloc or Realloc. If the area
+// pointed to was moved, a Free(b) is done.
+func (a *Allocator) Realloc(b []byte, size int) (r []byte, err error) {
+ var p uintptr
+ if b = b[:cap(b)]; len(b) != 0 {
+ p = uintptr(unsafe.Pointer(&b[0]))
+ }
+ if p, err = a.UintptrRealloc(p, size); p == 0 || err != nil {
+ return nil, err
+ }
+
+ sh := (*reflect.SliceHeader)(unsafe.Pointer(&r))
+ sh.Cap = usableSize(p)
+ sh.Data = p
+ sh.Len = size
+ return r, nil
+}
+
+// UsableSize reports the size of the memory block allocated at p, which must
+// point to the first byte of a slice returned from Calloc, Malloc or Realloc.
+// The allocated memory block size can be larger than the size originally
+// requested from Calloc, Malloc or Realloc.
+func UsableSize(p *byte) (r int) { return UintptrUsableSize(uintptr(unsafe.Pointer(p))) }
+
+// UnsafeCalloc is like Calloc except it returns an unsafe.Pointer.
+func (a *Allocator) UnsafeCalloc(size int) (r unsafe.Pointer, err error) {
+ p, err := a.UintptrCalloc(size)
+ if err != nil {
+ return nil, err
+ }
+
+ return unsafe.Pointer(p), nil
+}
+
+// UnsafeFree is like Free except its argument is an unsafe.Pointer, which must
+// have been acquired from UnsafeCalloc or UnsafeMalloc or UnsafeRealloc.
+func (a *Allocator) UnsafeFree(p unsafe.Pointer) (err error) { return a.UintptrFree(uintptr(p)) }
+
+// UnsafeMalloc is like Malloc except it returns an unsafe.Pointer.
+func (a *Allocator) UnsafeMalloc(size int) (r unsafe.Pointer, err error) {
+ p, err := a.UintptrMalloc(size)
+ if err != nil {
+ return nil, err
+ }
+
+ return unsafe.Pointer(p), nil
+}
+
+// UnsafeRealloc is like Realloc except its first argument is an
+// unsafe.Pointer, which must have been returned from UnsafeCalloc,
+// UnsafeMalloc or UnsafeRealloc.
+func (a *Allocator) UnsafeRealloc(p unsafe.Pointer, size int) (r unsafe.Pointer, err error) {
+ q, err := a.UintptrRealloc(uintptr(p), size)
+ if err != nil {
+ return nil, err
+ }
+
+ return unsafe.Pointer(q), nil
+}
+
+// UnsafeUsableSize is like UsableSize except its argument is an
+// unsafe.Pointer, which must have been returned from UnsafeCalloc,
+// UnsafeMalloc or UnsafeRealloc.
+func UnsafeUsableSize(p unsafe.Pointer) (r int) { return UintptrUsableSize(uintptr(p)) }
diff --git a/vendor/modernc.org/memory/memory32.go b/vendor/modernc.org/memory/memory32.go
new file mode 100644
index 00000000..f13a8ae6
--- /dev/null
+++ b/vendor/modernc.org/memory/memory32.go
@@ -0,0 +1,9 @@
+// Copyright 2018 The Memory Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+// +build 386 arm armbe mips mipsle ppc ppc64le s390 s390x sparc
+
+package memory // import "modernc.org/memory"
+
+type rawmem [1<<31 - 1]byte
diff --git a/vendor/modernc.org/memory/memory64.go b/vendor/modernc.org/memory/memory64.go
new file mode 100644
index 00000000..2c7cfee1
--- /dev/null
+++ b/vendor/modernc.org/memory/memory64.go
@@ -0,0 +1,9 @@
+// Copyright 2018 The Memory Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+// +build amd64 amd64p32 arm64 arm64be mips64 mips64le mips64p32 mips64p32le ppc64 sparc64
+
+package memory // import "modernc.org/memory"
+
+type rawmem [1<<50 - 1]byte
diff --git a/vendor/modernc.org/memory/mmap_unix.go b/vendor/modernc.org/memory/mmap_unix.go
new file mode 100644
index 00000000..8fee87e6
--- /dev/null
+++ b/vendor/modernc.org/memory/mmap_unix.go
@@ -0,0 +1,69 @@
+// Copyright 2011 Evan Shaw. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE-MMAP-GO file.
+
+// +build darwin dragonfly freebsd linux openbsd solaris netbsd
+
+// Modifications (c) 2017 The Memory Authors.
+
+package memory // import "modernc.org/memory"
+
+import (
+ "os"
+ "syscall"
+ "unsafe"
+)
+
+const pageSizeLog = 20
+
+var (
+ osPageMask = osPageSize - 1
+ osPageSize = os.Getpagesize()
+)
+
+func unmap(addr uintptr, size int) error {
+ _, _, errno := syscall.Syscall(syscall.SYS_MUNMAP, addr, uintptr(size), 0)
+ if errno != 0 {
+ return errno
+ }
+
+ return nil
+}
+
+// pageSize aligned.
+func mmap(size int) (uintptr, int, error) {
+ size = roundup(size, osPageSize)
+ b, err := syscall.Mmap(-1, 0, size+pageSize, syscall.PROT_READ|syscall.PROT_WRITE, syscall.MAP_SHARED|syscall.MAP_ANON)
+ if err != nil {
+ return 0, 0, err
+ }
+
+ n := len(b)
+ p := uintptr(unsafe.Pointer(&b[0]))
+ if p&uintptr(osPageMask) != 0 {
+ panic("internal error")
+ }
+
+ mod := int(p) & pageMask
+ if mod != 0 {
+ m := pageSize - mod
+ if err := unmap(p, m); err != nil {
+ return 0, 0, err
+ }
+
+ n -= m
+ p += uintptr(m)
+ }
+
+ if p&uintptr(pageMask) != 0 {
+ panic("internal error")
+ }
+
+ if n-size != 0 {
+ if err := unmap(p+uintptr(size), n-size); err != nil {
+ return 0, 0, err
+ }
+ }
+
+ return p, size, nil
+}
diff --git a/vendor/modernc.org/memory/mmap_windows.go b/vendor/modernc.org/memory/mmap_windows.go
new file mode 100644
index 00000000..3c402039
--- /dev/null
+++ b/vendor/modernc.org/memory/mmap_windows.go
@@ -0,0 +1,49 @@
+// Copyright 2017 The Memory 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 memory // import "modernc.org/memory"
+
+import (
+ "os"
+ "syscall"
+)
+
+const (
+ _MEM_COMMIT = 0x1000
+ _MEM_RESERVE = 0x2000
+ _MEM_DECOMMIT = 0x4000
+ _MEM_RELEASE = 0x8000
+
+ _PAGE_READWRITE = 0x0004
+ _PAGE_NOACCESS = 0x0001
+)
+
+const pageSizeLog = 16
+
+var (
+ modkernel32 = syscall.NewLazyDLL("kernel32.dll")
+ osPageMask = osPageSize - 1
+ osPageSize = os.Getpagesize()
+ procVirtualAlloc = modkernel32.NewProc("VirtualAlloc")
+ procVirtualFree = modkernel32.NewProc("VirtualFree")
+)
+
+// pageSize aligned.
+func mmap(size int) (uintptr, int, error) {
+ size = roundup(size, pageSize)
+ addr, _, err := procVirtualAlloc.Call(0, uintptr(size), _MEM_COMMIT|_MEM_RESERVE, _PAGE_READWRITE)
+ if err.(syscall.Errno) != 0 || addr == 0 {
+ return addr, size, err
+ }
+ return addr, size, nil
+}
+
+func unmap(addr uintptr, size int) error {
+ r, _, err := procVirtualFree.Call(addr, 0, _MEM_RELEASE)
+ if r == 0 {
+ return err
+ }
+
+ return nil
+}
diff --git a/vendor/modernc.org/memory/nocounters.go b/vendor/modernc.org/memory/nocounters.go
new file mode 100644
index 00000000..40af6a9a
--- /dev/null
+++ b/vendor/modernc.org/memory/nocounters.go
@@ -0,0 +1,9 @@
+// Copyright 2017 The Memory Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+// +build !memory.counters
+
+package memory // import "modernc.org/memory"
+
+const counters = false
diff --git a/vendor/modernc.org/memory/trace_disabled.go b/vendor/modernc.org/memory/trace_disabled.go
new file mode 100644
index 00000000..76e60766
--- /dev/null
+++ b/vendor/modernc.org/memory/trace_disabled.go
@@ -0,0 +1,9 @@
+// Copyright 2017 The Memory Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+// +build !memory.trace
+
+package memory // import "modernc.org/memory"
+
+const trace = false
diff --git a/vendor/modernc.org/memory/trace_enabled.go b/vendor/modernc.org/memory/trace_enabled.go
new file mode 100644
index 00000000..55e65f4a
--- /dev/null
+++ b/vendor/modernc.org/memory/trace_enabled.go
@@ -0,0 +1,9 @@
+// Copyright 2017 The Memory Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+// +build memory.trace
+
+package memory // import "modernc.org/memory"
+
+const trace = true