New Upstream Snapshot - golang-gopkg-mgo.v2

Ready changes

Summary

Merged new upstream version: 2016.08.01+git20180705.1.7446a03 (was: 2016.08.01).

Resulting package

Built on 2023-01-19T17:07 (took 7m25s)

The resulting binary packages can be installed (if you have the apt repository enabled) by running one of:

apt install -t fresh-snapshots golang-gopkg-mgo.v2-dev

Lintian Result

Diff

diff --git a/.travis.yml b/.travis.yml
index 45b38cf..865a838 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -41,5 +41,6 @@ script:
     - (cd bson && go test -check.v)
     - go test -check.v -fast
     - (cd txn && go test -check.v)
+    - make stopdb
 
 # vim:sw=4:ts=4:et
diff --git a/README.md b/README.md
index f4e452c..8af1527 100644
--- a/README.md
+++ b/README.md
@@ -1,4 +1,20 @@
-The MongoDB driver for Go
--------------------------
+THIS IS UNMAINTAINED
+--------------------
 
-Please go to [http://labix.org/mgo](http://labix.org/mgo) for all project details.
+Seven years after creating the mgo driver, I'm formally pausing my work on its maintenance.
+There are multiple reasons for that, but the main ones are that I've stopped using MongoDB
+for any new projects, and supporting its good community was taking too much of my
+personal time without a relevant benefit for those around me.
+
+Moving forward I would suggest you to look at one of these options:
+
+  * [globalsign/mgo](https://github.com/globalsign/mgo) - Community supported fork of mgo.
+  * [BoltDB](https://github.com/coreos/bbolt) - Single file in-memory document database for Go.
+  * [Badger](https://github.com/dgraph-io/badger) - Fast in-memory document database for Go.
+  * [DGraph](https://github.com/dgraph-io/dgraph) - Distributed graph database on top of Badger.
+  * [lib/pq](https://github.com/lib/pq) - PostgreSQL driver in pure Go.
+
+For technical questions related to mgo, [Stack Overflow](https://stackoverflow.com/questions/tagged/mgo)
+is the best place to continue obtaining support from the community.
+
+For personal contact, gustavo at http://niemeyer.net.
diff --git a/bson/bson.go b/bson/bson.go
index 7fb7f8c..90ec7e8 100644
--- a/bson/bson.go
+++ b/bson/bson.go
@@ -35,13 +35,11 @@ package bson
 import (
 	"bytes"
 	"crypto/md5"
-	"crypto/rand"
 	"encoding/binary"
 	"encoding/hex"
 	"encoding/json"
 	"errors"
 	"fmt"
-	"io"
 	"os"
 	"reflect"
 	"runtime"
@@ -194,12 +192,10 @@ var objectIdCounter uint32 = readRandomUint32()
 
 // readRandomUint32 returns a random objectIdCounter.
 func readRandomUint32() uint32 {
-	var b [4]byte
-	_, err := io.ReadFull(rand.Reader, b[:])
-	if err != nil {
-		panic(fmt.Errorf("cannot read random object id: %v", err))
-	}
-	return uint32((uint32(b[0]) << 0) | (uint32(b[1]) << 8) | (uint32(b[2]) << 16) | (uint32(b[3]) << 24))
+	// We've found systems hanging in this function due to lack of entropy.
+	// The randomness of these bytes is just preventing nearby clashes, so
+	// just look at the time.
+	return uint32(time.Now().UnixNano())
 }
 
 // machineId stores machine id generated once and used in subsequent calls
@@ -214,10 +210,10 @@ func readMachineId() []byte {
 	id := sum[:]
 	hostname, err1 := os.Hostname()
 	if err1 != nil {
-		_, err2 := io.ReadFull(rand.Reader, id)
-		if err2 != nil {
-			panic(fmt.Errorf("cannot get hostname: %v; %v", err1, err2))
-		}
+		n := uint32(time.Now().UnixNano())
+		sum[0] = byte(n >> 0)
+		sum[1] = byte(n >> 8)
+		sum[2] = byte(n >> 16)
 		return id
 	}
 	hw := md5.New()
@@ -279,7 +275,7 @@ var nullBytes = []byte("null")
 func (id *ObjectId) UnmarshalJSON(data []byte) error {
 	if len(data) > 0 && (data[0] == '{' || data[0] == 'O') {
 		var v struct {
-			Id json.RawMessage `json:"$oid"`
+			Id   json.RawMessage `json:"$oid"`
 			Func struct {
 				Id json.RawMessage
 			} `json:"$oidFunc"`
diff --git a/bson/json.go b/bson/json.go
index d37f835..09df826 100644
--- a/bson/json.go
+++ b/bson/json.go
@@ -317,7 +317,7 @@ func jencNumberLong(v interface{}) ([]byte, error) {
 func jencInt(v interface{}) ([]byte, error) {
 	n := v.(int)
 	f := `{"$numberLong":"%d"}`
-	if n <= 1<<53 {
+	if int64(n) <= 1<<53 {
 		f = `%d`
 	}
 	return fbytes(f, n), nil
diff --git a/bson/slice-getter-setter.patch b/bson/slice-getter-setter.patch
deleted file mode 100644
index dcc19e3..0000000
--- a/bson/slice-getter-setter.patch
+++ /dev/null
@@ -1,512 +0,0 @@
-diff --git a/bson/bson_test.go b/bson/bson_test.go
-index 5c1b869..630292b 100644
---- a/bson/bson_test.go
-+++ b/bson/bson_test.go
-@@ -1056,6 +1056,25 @@ func (i *getterSetterInt) SetBSON(raw bson.Raw) error {
- 	return err
- }
- 
-+type ifaceType interface {
-+	Hello()
-+}
-+
-+type ifaceSlice []ifaceType
-+
-+func (s *ifaceSlice) SetBSON(raw bson.Raw) error {
-+	var ns []int
-+	if err := raw.Unmarshal(&ns); err != nil {
-+		return err
-+	}
-+	*s = make(ifaceSlice, ns[0])
-+	return nil
-+}
-+
-+func (s ifaceSlice) GetBSON() (interface{}, error) {
-+	return []int{len(s)}, nil
-+}
-+
- type (
- 	MyString string
- 	MyBytes  []byte
-@@ -1090,197 +1109,200 @@ func parseURL(s string) *url.URL {
- // verify that the resulting value is deep-equal to the untouched second value.
- // Then, it will do the same in the *opposite* direction!
- var twoWayCrossItems = []crossTypeItem{
--	// int<=>int
--	{&struct{ I int }{42}, &struct{ I int8 }{42}},
--	{&struct{ I int }{42}, &struct{ I int32 }{42}},
--	{&struct{ I int }{42}, &struct{ I int64 }{42}},
--	{&struct{ I int8 }{42}, &struct{ I int32 }{42}},
--	{&struct{ I int8 }{42}, &struct{ I int64 }{42}},
--	{&struct{ I int32 }{42}, &struct{ I int64 }{42}},
--
--	// uint<=>uint
--	{&struct{ I uint }{42}, &struct{ I uint8 }{42}},
--	{&struct{ I uint }{42}, &struct{ I uint32 }{42}},
--	{&struct{ I uint }{42}, &struct{ I uint64 }{42}},
--	{&struct{ I uint8 }{42}, &struct{ I uint32 }{42}},
--	{&struct{ I uint8 }{42}, &struct{ I uint64 }{42}},
--	{&struct{ I uint32 }{42}, &struct{ I uint64 }{42}},
--
--	// float32<=>float64
--	{&struct{ I float32 }{42}, &struct{ I float64 }{42}},
--
--	// int<=>uint
--	{&struct{ I uint }{42}, &struct{ I int }{42}},
--	{&struct{ I uint }{42}, &struct{ I int8 }{42}},
--	{&struct{ I uint }{42}, &struct{ I int32 }{42}},
--	{&struct{ I uint }{42}, &struct{ I int64 }{42}},
--	{&struct{ I uint8 }{42}, &struct{ I int }{42}},
--	{&struct{ I uint8 }{42}, &struct{ I int8 }{42}},
--	{&struct{ I uint8 }{42}, &struct{ I int32 }{42}},
--	{&struct{ I uint8 }{42}, &struct{ I int64 }{42}},
--	{&struct{ I uint32 }{42}, &struct{ I int }{42}},
--	{&struct{ I uint32 }{42}, &struct{ I int8 }{42}},
--	{&struct{ I uint32 }{42}, &struct{ I int32 }{42}},
--	{&struct{ I uint32 }{42}, &struct{ I int64 }{42}},
--	{&struct{ I uint64 }{42}, &struct{ I int }{42}},
--	{&struct{ I uint64 }{42}, &struct{ I int8 }{42}},
--	{&struct{ I uint64 }{42}, &struct{ I int32 }{42}},
--	{&struct{ I uint64 }{42}, &struct{ I int64 }{42}},
--
--	// int <=> float
--	{&struct{ I int }{42}, &struct{ I float64 }{42}},
--
--	// int <=> bool
--	{&struct{ I int }{1}, &struct{ I bool }{true}},
--	{&struct{ I int }{0}, &struct{ I bool }{false}},
--
--	// uint <=> float64
--	{&struct{ I uint }{42}, &struct{ I float64 }{42}},
--
--	// uint <=> bool
--	{&struct{ I uint }{1}, &struct{ I bool }{true}},
--	{&struct{ I uint }{0}, &struct{ I bool }{false}},
--
--	// float64 <=> bool
--	{&struct{ I float64 }{1}, &struct{ I bool }{true}},
--	{&struct{ I float64 }{0}, &struct{ I bool }{false}},
--
--	// string <=> string and string <=> []byte
--	{&struct{ S []byte }{[]byte("abc")}, &struct{ S string }{"abc"}},
--	{&struct{ S []byte }{[]byte("def")}, &struct{ S bson.Symbol }{"def"}},
--	{&struct{ S string }{"ghi"}, &struct{ S bson.Symbol }{"ghi"}},
--
--	// map <=> struct
--	{&struct {
--		A struct {
--			B, C int
--		}
--	}{struct{ B, C int }{1, 2}},
--		map[string]map[string]int{"a": map[string]int{"b": 1, "c": 2}}},
--
--	{&struct{ A bson.Symbol }{"abc"}, map[string]string{"a": "abc"}},
--	{&struct{ A bson.Symbol }{"abc"}, map[string][]byte{"a": []byte("abc")}},
--	{&struct{ A []byte }{[]byte("abc")}, map[string]string{"a": "abc"}},
--	{&struct{ A uint }{42}, map[string]int{"a": 42}},
--	{&struct{ A uint }{42}, map[string]float64{"a": 42}},
--	{&struct{ A uint }{1}, map[string]bool{"a": true}},
--	{&struct{ A int }{42}, map[string]uint{"a": 42}},
--	{&struct{ A int }{42}, map[string]float64{"a": 42}},
--	{&struct{ A int }{1}, map[string]bool{"a": true}},
--	{&struct{ A float64 }{42}, map[string]float32{"a": 42}},
--	{&struct{ A float64 }{42}, map[string]int{"a": 42}},
--	{&struct{ A float64 }{42}, map[string]uint{"a": 42}},
--	{&struct{ A float64 }{1}, map[string]bool{"a": true}},
--	{&struct{ A bool }{true}, map[string]int{"a": 1}},
--	{&struct{ A bool }{true}, map[string]uint{"a": 1}},
--	{&struct{ A bool }{true}, map[string]float64{"a": 1}},
--	{&struct{ A **byte }{&byteptr}, map[string]byte{"a": 8}},
--
--	// url.URL <=> string
--	{&struct{ URL *url.URL }{parseURL("h://e.c/p")}, map[string]string{"url": "h://e.c/p"}},
--	{&struct{ URL url.URL }{*parseURL("h://e.c/p")}, map[string]string{"url": "h://e.c/p"}},
--
--	// Slices
--	{&struct{ S []int }{[]int{1, 2, 3}}, map[string][]int{"s": []int{1, 2, 3}}},
--	{&struct{ S *[]int }{&[]int{1, 2, 3}}, map[string][]int{"s": []int{1, 2, 3}}},
--
--	// Conditionals
--	{&condBool{true}, map[string]bool{"v": true}},
--	{&condBool{}, map[string]bool{}},
--	{&condInt{1}, map[string]int{"v": 1}},
--	{&condInt{}, map[string]int{}},
--	{&condUInt{1}, map[string]uint{"v": 1}},
--	{&condUInt{}, map[string]uint{}},
--	{&condFloat{}, map[string]int{}},
--	{&condStr{"yo"}, map[string]string{"v": "yo"}},
--	{&condStr{}, map[string]string{}},
--	{&condStrNS{"yo"}, map[string]string{"v": "yo"}},
--	{&condStrNS{}, map[string]string{}},
--	{&condSlice{[]string{"yo"}}, map[string][]string{"v": []string{"yo"}}},
--	{&condSlice{}, map[string][]string{}},
--	{&condMap{map[string]int{"k": 1}}, bson.M{"v": bson.M{"k": 1}}},
--	{&condMap{}, map[string][]string{}},
--	{&condIface{"yo"}, map[string]string{"v": "yo"}},
--	{&condIface{""}, map[string]string{"v": ""}},
--	{&condIface{}, map[string]string{}},
--	{&condPtr{&truevar}, map[string]bool{"v": true}},
--	{&condPtr{&falsevar}, map[string]bool{"v": false}},
--	{&condPtr{}, map[string]string{}},
--
--	{&condTime{time.Unix(123456789, 123e6)}, map[string]time.Time{"v": time.Unix(123456789, 123e6)}},
--	{&condTime{}, map[string]string{}},
--
--	{&condStruct{struct{ A []int }{[]int{1}}}, bson.M{"v": bson.M{"a": []interface{}{1}}}},
--	{&condStruct{struct{ A []int }{}}, bson.M{}},
--
--	{&namedCondStr{"yo"}, map[string]string{"myv": "yo"}},
--	{&namedCondStr{}, map[string]string{}},
--
--	{&shortInt{1}, map[string]interface{}{"v": 1}},
--	{&shortInt{1 << 30}, map[string]interface{}{"v": 1 << 30}},
--	{&shortInt{1 << 31}, map[string]interface{}{"v": int64(1 << 31)}},
--	{&shortUint{1 << 30}, map[string]interface{}{"v": 1 << 30}},
--	{&shortUint{1 << 31}, map[string]interface{}{"v": int64(1 << 31)}},
--	{&shortIface{int64(1) << 31}, map[string]interface{}{"v": int64(1 << 31)}},
--	{&shortPtr{int64ptr}, map[string]interface{}{"v": intvar}},
--
--	{&shortNonEmptyInt{1}, map[string]interface{}{"v": 1}},
--	{&shortNonEmptyInt{1 << 31}, map[string]interface{}{"v": int64(1 << 31)}},
--	{&shortNonEmptyInt{}, map[string]interface{}{}},
--
--	{&inlineInt{struct{ A, B int }{1, 2}}, map[string]interface{}{"a": 1, "b": 2}},
--	{&inlineMap{A: 1, M: map[string]interface{}{"b": 2}}, map[string]interface{}{"a": 1, "b": 2}},
--	{&inlineMap{A: 1, M: nil}, map[string]interface{}{"a": 1}},
--	{&inlineMapInt{A: 1, M: map[string]int{"b": 2}}, map[string]int{"a": 1, "b": 2}},
--	{&inlineMapInt{A: 1, M: nil}, map[string]int{"a": 1}},
--	{&inlineMapMyM{A: 1, M: MyM{"b": MyM{"c": 3}}}, map[string]interface{}{"a": 1, "b": map[string]interface{}{"c": 3}}},
--
--	// []byte <=> MyBytes
--	{&struct{ B MyBytes }{[]byte("abc")}, map[string]string{"b": "abc"}},
--	{&struct{ B MyBytes }{[]byte{}}, map[string]string{"b": ""}},
--	{&struct{ B MyBytes }{}, map[string]bool{}},
--	{&struct{ B []byte }{[]byte("abc")}, map[string]MyBytes{"b": []byte("abc")}},
--
--	// bool <=> MyBool
--	{&struct{ B MyBool }{true}, map[string]bool{"b": true}},
--	{&struct{ B MyBool }{}, map[string]bool{"b": false}},
--	{&struct{ B MyBool }{}, map[string]string{}},
--	{&struct{ B bool }{}, map[string]MyBool{"b": false}},
--
--	// arrays
--	{&struct{ V [2]int }{[...]int{1, 2}}, map[string][2]int{"v": [2]int{1, 2}}},
--
--	// zero time
--	{&struct{ V time.Time }{}, map[string]interface{}{"v": time.Time{}}},
--
--	// zero time + 1 second + 1 millisecond; overflows int64 as nanoseconds
--	{&struct{ V time.Time }{time.Unix(-62135596799, 1e6).Local()},
--		map[string]interface{}{"v": time.Unix(-62135596799, 1e6).Local()}},
--
--	// bson.D <=> []DocElem
--	{&bson.D{{"a", bson.D{{"b", 1}, {"c", 2}}}}, &bson.D{{"a", bson.D{{"b", 1}, {"c", 2}}}}},
--	{&bson.D{{"a", bson.D{{"b", 1}, {"c", 2}}}}, &MyD{{"a", MyD{{"b", 1}, {"c", 2}}}}},
--	{&struct{ V MyD }{MyD{{"a", 1}}}, &bson.D{{"v", bson.D{{"a", 1}}}}},
--
--	// bson.RawD <=> []RawDocElem
--	{&bson.RawD{{"a", bson.Raw{0x08, []byte{0x01}}}}, &bson.RawD{{"a", bson.Raw{0x08, []byte{0x01}}}}},
--	{&bson.RawD{{"a", bson.Raw{0x08, []byte{0x01}}}}, &MyRawD{{"a", bson.Raw{0x08, []byte{0x01}}}}},
--
--	// bson.M <=> map
--	{bson.M{"a": bson.M{"b": 1, "c": 2}}, MyM{"a": MyM{"b": 1, "c": 2}}},
--	{bson.M{"a": bson.M{"b": 1, "c": 2}}, map[string]interface{}{"a": map[string]interface{}{"b": 1, "c": 2}}},
--
--	// bson.M <=> map[MyString]
--	{bson.M{"a": bson.M{"b": 1, "c": 2}}, map[MyString]interface{}{"a": map[MyString]interface{}{"b": 1, "c": 2}}},
--
--	// json.Number <=> int64, float64
--	{&struct{ N json.Number }{"5"}, map[string]interface{}{"n": int64(5)}},
--	{&struct{ N json.Number }{"5.05"}, map[string]interface{}{"n": 5.05}},
--	{&struct{ N json.Number }{"9223372036854776000"}, map[string]interface{}{"n": float64(1 << 63)}},
--
--	// bson.D <=> non-struct getter/setter
--	{&bson.D{{"a", 1}}, &getterSetterD{{"a", 1}, {"suffix", true}}},
--	{&bson.D{{"a", 42}}, &gsintvar},
-+	//// int<=>int
-+	//{&struct{ I int }{42}, &struct{ I int8 }{42}},
-+	//{&struct{ I int }{42}, &struct{ I int32 }{42}},
-+	//{&struct{ I int }{42}, &struct{ I int64 }{42}},
-+	//{&struct{ I int8 }{42}, &struct{ I int32 }{42}},
-+	//{&struct{ I int8 }{42}, &struct{ I int64 }{42}},
-+	//{&struct{ I int32 }{42}, &struct{ I int64 }{42}},
-+
-+	//// uint<=>uint
-+	//{&struct{ I uint }{42}, &struct{ I uint8 }{42}},
-+	//{&struct{ I uint }{42}, &struct{ I uint32 }{42}},
-+	//{&struct{ I uint }{42}, &struct{ I uint64 }{42}},
-+	//{&struct{ I uint8 }{42}, &struct{ I uint32 }{42}},
-+	//{&struct{ I uint8 }{42}, &struct{ I uint64 }{42}},
-+	//{&struct{ I uint32 }{42}, &struct{ I uint64 }{42}},
-+
-+	//// float32<=>float64
-+	//{&struct{ I float32 }{42}, &struct{ I float64 }{42}},
-+
-+	//// int<=>uint
-+	//{&struct{ I uint }{42}, &struct{ I int }{42}},
-+	//{&struct{ I uint }{42}, &struct{ I int8 }{42}},
-+	//{&struct{ I uint }{42}, &struct{ I int32 }{42}},
-+	//{&struct{ I uint }{42}, &struct{ I int64 }{42}},
-+	//{&struct{ I uint8 }{42}, &struct{ I int }{42}},
-+	//{&struct{ I uint8 }{42}, &struct{ I int8 }{42}},
-+	//{&struct{ I uint8 }{42}, &struct{ I int32 }{42}},
-+	//{&struct{ I uint8 }{42}, &struct{ I int64 }{42}},
-+	//{&struct{ I uint32 }{42}, &struct{ I int }{42}},
-+	//{&struct{ I uint32 }{42}, &struct{ I int8 }{42}},
-+	//{&struct{ I uint32 }{42}, &struct{ I int32 }{42}},
-+	//{&struct{ I uint32 }{42}, &struct{ I int64 }{42}},
-+	//{&struct{ I uint64 }{42}, &struct{ I int }{42}},
-+	//{&struct{ I uint64 }{42}, &struct{ I int8 }{42}},
-+	//{&struct{ I uint64 }{42}, &struct{ I int32 }{42}},
-+	//{&struct{ I uint64 }{42}, &struct{ I int64 }{42}},
-+
-+	//// int <=> float
-+	//{&struct{ I int }{42}, &struct{ I float64 }{42}},
-+
-+	//// int <=> bool
-+	//{&struct{ I int }{1}, &struct{ I bool }{true}},
-+	//{&struct{ I int }{0}, &struct{ I bool }{false}},
-+
-+	//// uint <=> float64
-+	//{&struct{ I uint }{42}, &struct{ I float64 }{42}},
-+
-+	//// uint <=> bool
-+	//{&struct{ I uint }{1}, &struct{ I bool }{true}},
-+	//{&struct{ I uint }{0}, &struct{ I bool }{false}},
-+
-+	//// float64 <=> bool
-+	//{&struct{ I float64 }{1}, &struct{ I bool }{true}},
-+	//{&struct{ I float64 }{0}, &struct{ I bool }{false}},
-+
-+	//// string <=> string and string <=> []byte
-+	//{&struct{ S []byte }{[]byte("abc")}, &struct{ S string }{"abc"}},
-+	//{&struct{ S []byte }{[]byte("def")}, &struct{ S bson.Symbol }{"def"}},
-+	//{&struct{ S string }{"ghi"}, &struct{ S bson.Symbol }{"ghi"}},
-+
-+	//// map <=> struct
-+	//{&struct {
-+	//	A struct {
-+	//		B, C int
-+	//	}
-+	//}{struct{ B, C int }{1, 2}},
-+	//	map[string]map[string]int{"a": map[string]int{"b": 1, "c": 2}}},
-+
-+	//{&struct{ A bson.Symbol }{"abc"}, map[string]string{"a": "abc"}},
-+	//{&struct{ A bson.Symbol }{"abc"}, map[string][]byte{"a": []byte("abc")}},
-+	//{&struct{ A []byte }{[]byte("abc")}, map[string]string{"a": "abc"}},
-+	//{&struct{ A uint }{42}, map[string]int{"a": 42}},
-+	//{&struct{ A uint }{42}, map[string]float64{"a": 42}},
-+	//{&struct{ A uint }{1}, map[string]bool{"a": true}},
-+	//{&struct{ A int }{42}, map[string]uint{"a": 42}},
-+	//{&struct{ A int }{42}, map[string]float64{"a": 42}},
-+	//{&struct{ A int }{1}, map[string]bool{"a": true}},
-+	//{&struct{ A float64 }{42}, map[string]float32{"a": 42}},
-+	//{&struct{ A float64 }{42}, map[string]int{"a": 42}},
-+	//{&struct{ A float64 }{42}, map[string]uint{"a": 42}},
-+	//{&struct{ A float64 }{1}, map[string]bool{"a": true}},
-+	//{&struct{ A bool }{true}, map[string]int{"a": 1}},
-+	//{&struct{ A bool }{true}, map[string]uint{"a": 1}},
-+	//{&struct{ A bool }{true}, map[string]float64{"a": 1}},
-+	//{&struct{ A **byte }{&byteptr}, map[string]byte{"a": 8}},
-+
-+	//// url.URL <=> string
-+	//{&struct{ URL *url.URL }{parseURL("h://e.c/p")}, map[string]string{"url": "h://e.c/p"}},
-+	//{&struct{ URL url.URL }{*parseURL("h://e.c/p")}, map[string]string{"url": "h://e.c/p"}},
-+
-+	//// Slices
-+	//{&struct{ S []int }{[]int{1, 2, 3}}, map[string][]int{"s": []int{1, 2, 3}}},
-+	//{&struct{ S *[]int }{&[]int{1, 2, 3}}, map[string][]int{"s": []int{1, 2, 3}}},
-+
-+	//// Conditionals
-+	//{&condBool{true}, map[string]bool{"v": true}},
-+	//{&condBool{}, map[string]bool{}},
-+	//{&condInt{1}, map[string]int{"v": 1}},
-+	//{&condInt{}, map[string]int{}},
-+	//{&condUInt{1}, map[string]uint{"v": 1}},
-+	//{&condUInt{}, map[string]uint{}},
-+	//{&condFloat{}, map[string]int{}},
-+	//{&condStr{"yo"}, map[string]string{"v": "yo"}},
-+	//{&condStr{}, map[string]string{}},
-+	//{&condStrNS{"yo"}, map[string]string{"v": "yo"}},
-+	//{&condStrNS{}, map[string]string{}},
-+	//{&condSlice{[]string{"yo"}}, map[string][]string{"v": []string{"yo"}}},
-+	//{&condSlice{}, map[string][]string{}},
-+	//{&condMap{map[string]int{"k": 1}}, bson.M{"v": bson.M{"k": 1}}},
-+	//{&condMap{}, map[string][]string{}},
-+	//{&condIface{"yo"}, map[string]string{"v": "yo"}},
-+	//{&condIface{""}, map[string]string{"v": ""}},
-+	//{&condIface{}, map[string]string{}},
-+	//{&condPtr{&truevar}, map[string]bool{"v": true}},
-+	//{&condPtr{&falsevar}, map[string]bool{"v": false}},
-+	//{&condPtr{}, map[string]string{}},
-+
-+	//{&condTime{time.Unix(123456789, 123e6)}, map[string]time.Time{"v": time.Unix(123456789, 123e6)}},
-+	//{&condTime{}, map[string]string{}},
-+
-+	//{&condStruct{struct{ A []int }{[]int{1}}}, bson.M{"v": bson.M{"a": []interface{}{1}}}},
-+	//{&condStruct{struct{ A []int }{}}, bson.M{}},
-+
-+	//{&namedCondStr{"yo"}, map[string]string{"myv": "yo"}},
-+	//{&namedCondStr{}, map[string]string{}},
-+
-+	//{&shortInt{1}, map[string]interface{}{"v": 1}},
-+	//{&shortInt{1 << 30}, map[string]interface{}{"v": 1 << 30}},
-+	//{&shortInt{1 << 31}, map[string]interface{}{"v": int64(1 << 31)}},
-+	//{&shortUint{1 << 30}, map[string]interface{}{"v": 1 << 30}},
-+	//{&shortUint{1 << 31}, map[string]interface{}{"v": int64(1 << 31)}},
-+	//{&shortIface{int64(1) << 31}, map[string]interface{}{"v": int64(1 << 31)}},
-+	//{&shortPtr{int64ptr}, map[string]interface{}{"v": intvar}},
-+
-+	//{&shortNonEmptyInt{1}, map[string]interface{}{"v": 1}},
-+	//{&shortNonEmptyInt{1 << 31}, map[string]interface{}{"v": int64(1 << 31)}},
-+	//{&shortNonEmptyInt{}, map[string]interface{}{}},
-+
-+	//{&inlineInt{struct{ A, B int }{1, 2}}, map[string]interface{}{"a": 1, "b": 2}},
-+	//{&inlineMap{A: 1, M: map[string]interface{}{"b": 2}}, map[string]interface{}{"a": 1, "b": 2}},
-+	//{&inlineMap{A: 1, M: nil}, map[string]interface{}{"a": 1}},
-+	//{&inlineMapInt{A: 1, M: map[string]int{"b": 2}}, map[string]int{"a": 1, "b": 2}},
-+	//{&inlineMapInt{A: 1, M: nil}, map[string]int{"a": 1}},
-+	//{&inlineMapMyM{A: 1, M: MyM{"b": MyM{"c": 3}}}, map[string]interface{}{"a": 1, "b": map[string]interface{}{"c": 3}}},
-+
-+	//// []byte <=> MyBytes
-+	//{&struct{ B MyBytes }{[]byte("abc")}, map[string]string{"b": "abc"}},
-+	//{&struct{ B MyBytes }{[]byte{}}, map[string]string{"b": ""}},
-+	//{&struct{ B MyBytes }{}, map[string]bool{}},
-+	//{&struct{ B []byte }{[]byte("abc")}, map[string]MyBytes{"b": []byte("abc")}},
-+
-+	//// bool <=> MyBool
-+	//{&struct{ B MyBool }{true}, map[string]bool{"b": true}},
-+	//{&struct{ B MyBool }{}, map[string]bool{"b": false}},
-+	//{&struct{ B MyBool }{}, map[string]string{}},
-+	//{&struct{ B bool }{}, map[string]MyBool{"b": false}},
-+
-+	//// arrays
-+	//{&struct{ V [2]int }{[...]int{1, 2}}, map[string][2]int{"v": [2]int{1, 2}}},
-+
-+	//// zero time
-+	//{&struct{ V time.Time }{}, map[string]interface{}{"v": time.Time{}}},
-+
-+	//// zero time + 1 second + 1 millisecond; overflows int64 as nanoseconds
-+	//{&struct{ V time.Time }{time.Unix(-62135596799, 1e6).Local()},
-+	//	map[string]interface{}{"v": time.Unix(-62135596799, 1e6).Local()}},
-+
-+	//// bson.D <=> []DocElem
-+	//{&bson.D{{"a", bson.D{{"b", 1}, {"c", 2}}}}, &bson.D{{"a", bson.D{{"b", 1}, {"c", 2}}}}},
-+	//{&bson.D{{"a", bson.D{{"b", 1}, {"c", 2}}}}, &MyD{{"a", MyD{{"b", 1}, {"c", 2}}}}},
-+	//{&struct{ V MyD }{MyD{{"a", 1}}}, &bson.D{{"v", bson.D{{"a", 1}}}}},
-+
-+	//// bson.RawD <=> []RawDocElem
-+	//{&bson.RawD{{"a", bson.Raw{0x08, []byte{0x01}}}}, &bson.RawD{{"a", bson.Raw{0x08, []byte{0x01}}}}},
-+	//{&bson.RawD{{"a", bson.Raw{0x08, []byte{0x01}}}}, &MyRawD{{"a", bson.Raw{0x08, []byte{0x01}}}}},
-+
-+	//// bson.M <=> map
-+	//{bson.M{"a": bson.M{"b": 1, "c": 2}}, MyM{"a": MyM{"b": 1, "c": 2}}},
-+	//{bson.M{"a": bson.M{"b": 1, "c": 2}}, map[string]interface{}{"a": map[string]interface{}{"b": 1, "c": 2}}},
-+
-+	//// bson.M <=> map[MyString]
-+	//{bson.M{"a": bson.M{"b": 1, "c": 2}}, map[MyString]interface{}{"a": map[MyString]interface{}{"b": 1, "c": 2}}},
-+
-+	//// json.Number <=> int64, float64
-+	//{&struct{ N json.Number }{"5"}, map[string]interface{}{"n": int64(5)}},
-+	//{&struct{ N json.Number }{"5.05"}, map[string]interface{}{"n": 5.05}},
-+	//{&struct{ N json.Number }{"9223372036854776000"}, map[string]interface{}{"n": float64(1 << 63)}},
-+
-+	//// bson.D <=> non-struct getter/setter
-+	//{&bson.D{{"a", 1}}, &getterSetterD{{"a", 1}, {"suffix", true}}},
-+	//{&bson.D{{"a", 42}}, &gsintvar},
-+
-+	// Interface slice setter.
-+	{&struct{ V ifaceSlice }{ifaceSlice{nil, nil}}, bson.M{"v": []interface{}{2}}},
- }
- 
- // Same thing, but only one way (obj1 => obj2).
-diff --git a/bson/decode.go b/bson/decode.go
-index 782e933..bdd2e02 100644
---- a/bson/decode.go
-+++ b/bson/decode.go
-@@ -1,18 +1,18 @@
- // BSON library for Go
--// 
-+//
- // Copyright (c) 2010-2012 - Gustavo Niemeyer <gustavo@niemeyer.net>
--// 
-+//
- // All rights reserved.
- //
- // Redistribution and use in source and binary forms, with or without
--// modification, are permitted provided that the following conditions are met: 
--// 
-+// modification, are permitted provided that the following conditions are met:
-+//
- // 1. Redistributions of source code must retain the above copyright notice, this
--//    list of conditions and the following disclaimer. 
-+//    list of conditions and the following disclaimer.
- // 2. 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. 
--// 
-+//    and/or other materials provided with the distribution.
-+//
- // 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
-@@ -474,6 +474,11 @@ func (d *decoder) readElemTo(out reflect.Value, kind byte) (good bool) {
- 		panic("Can't happen. Handled above.")
- 	case 0x04: // Array
- 		outt := out.Type()
-+		if setterStyle(outt) != setterNone {
-+			// Skip the value so its data is handed to the setter below.
-+			d.dropElem(kind)
-+			break
-+		}
- 		for outt.Kind() == reflect.Ptr {
- 			outt = outt.Elem()
- 		}
-diff --git a/bson/encode.go b/bson/encode.go
-index 81a13ad..8599f03 100644
---- a/bson/encode.go
-+++ b/bson/encode.go
-@@ -1,18 +1,18 @@
- // BSON library for Go
--// 
-+//
- // Copyright (c) 2010-2012 - Gustavo Niemeyer <gustavo@niemeyer.net>
--// 
-+//
- // All rights reserved.
- //
- // Redistribution and use in source and binary forms, with or without
--// modification, are permitted provided that the following conditions are met: 
--// 
-+// modification, are permitted provided that the following conditions are met:
-+//
- // 1. Redistributions of source code must retain the above copyright notice, this
--//    list of conditions and the following disclaimer. 
-+//    list of conditions and the following disclaimer.
- // 2. 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. 
--// 
-+//    and/or other materials provided with the distribution.
-+//
- // 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
-@@ -212,7 +212,7 @@ func (e *encoder) addSlice(v reflect.Value) {
- 		return
- 	}
- 	l := v.Len()
--	et  := v.Type().Elem()
-+	et := v.Type().Elem()
- 	if et == typeDocElem {
- 		for i := 0; i < l; i++ {
- 			elem := v.Index(i).Interface().(DocElem)
-@@ -415,7 +415,7 @@ func (e *encoder) addElem(name string, v reflect.Value, minSize bool) {
- 		case time.Time:
- 			// MongoDB handles timestamps as milliseconds.
- 			e.addElemName('\x09', name)
--			e.addInt64(s.Unix() * 1000 + int64(s.Nanosecond() / 1e6))
-+			e.addInt64(s.Unix()*1000 + int64(s.Nanosecond()/1e6))
- 
- 		case url.URL:
- 			e.addElemName('\x02', name)
diff --git a/debian/changelog b/debian/changelog
index a535733..ab42c20 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,4 +1,4 @@
-golang-gopkg-mgo.v2 (2016.08.01-8) UNRELEASED; urgency=medium
+golang-gopkg-mgo.v2 (2016.08.01+git20180705.1.7446a03-1) UNRELEASED; urgency=medium
 
   * Use secure URI in Homepage field.
   * Bump debhelper dependency to >= 9, since that's what is used in
@@ -6,8 +6,11 @@ golang-gopkg-mgo.v2 (2016.08.01-8) UNRELEASED; urgency=medium
   * Bump debhelper from deprecated 9 to 13.
   * Set debhelper-compat version in Build-Depends.
   * Set upstream metadata fields: Repository-Browse.
+  * New upstream snapshot.
+  * Drop patch 0001-fix-integer-constant-overflow-on-32-bit-systems.patch,
+    present upstream.
 
- -- Debian Janitor <janitor@jelmer.uk>  Thu, 09 Sep 2021 15:13:32 -0000
+ -- Debian Janitor <janitor@jelmer.uk>  Thu, 19 Jan 2023 17:03:36 -0000
 
 golang-gopkg-mgo.v2 (2016.08.01-7) unstable; urgency=medium
 
diff --git a/debian/patches/0001-fix-integer-constant-overflow-on-32-bit-systems.patch b/debian/patches/0001-fix-integer-constant-overflow-on-32-bit-systems.patch
deleted file mode 100644
index 774c8a3..0000000
--- a/debian/patches/0001-fix-integer-constant-overflow-on-32-bit-systems.patch
+++ /dev/null
@@ -1,22 +0,0 @@
-From 1e52f6152a9b262873f831bb5a94bcd29ef38c38 Mon Sep 17 00:00:00 2001
-From: Zachary Snow <zach.snow@mongodb.com>
-Date: Wed, 3 Aug 2016 10:00:57 -0400
-Subject: [PATCH] fix integer constant overflow on 32-bit systems
-
----
- bson/json.go | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/bson/json.go b/bson/json.go
-index d37f8350..09df8260 100644
---- a/bson/json.go
-+++ b/bson/json.go
-@@ -317,7 +317,7 @@ func jencNumberLong(v interface{}) ([]byte, error) {
- func jencInt(v interface{}) ([]byte, error) {
- 	n := v.(int)
- 	f := `{"$numberLong":"%d"}`
--	if n <= 1<<53 {
-+	if int64(n) <= 1<<53 {
- 		f = `%d`
- 	}
- 	return fbytes(f, n), nil
diff --git a/debian/patches/series b/debian/patches/series
index 3f9bfbf..e69de29 100644
--- a/debian/patches/series
+++ b/debian/patches/series
@@ -1 +0,0 @@
-0001-fix-integer-constant-overflow-on-32-bit-systems.patch
diff --git a/doc.go b/doc.go
index 859fd9b..12c8db5 100644
--- a/doc.go
+++ b/doc.go
@@ -1,9 +1,12 @@
 // Package mgo offers a rich MongoDB driver for Go.
 //
-// Details about the mgo project (pronounced as "mango") are found
-// in its web page:
+// #########################################################
 //
-//     http://labix.org/mgo
+// THIS DRIVER IS UNMAINTAINED! See here for details:
+//
+// https://github.com/go-mgo/mgo/blob/v2-unstable/README.md
+//
+// #########################################################
 //
 // Usage of the driver revolves around the concept of sessions.  To
 // get started, obtain a session using the Dial function:
diff --git a/session.go b/session.go
index 12ca8f2..a541b34 100644
--- a/session.go
+++ b/session.go
@@ -1534,12 +1534,25 @@ func (idxs indexSlice) Swap(i, j int)      { idxs[i], idxs[j] = idxs[j], idxs[i]
 
 func simpleIndexKey(realKey bson.D) (key []string) {
 	for i := range realKey {
+		var vi int
 		field := realKey[i].Name
-		vi, ok := realKey[i].Value.(int)
-		if !ok {
+
+		switch realKey[i].Value.(type) {
+		case int64:
+			vf, _ := realKey[i].Value.(int64)
+			vi = int(vf)
+		case float64:
 			vf, _ := realKey[i].Value.(float64)
 			vi = int(vf)
+		case string:
+			if vs, ok := realKey[i].Value.(string); ok {
+				key = append(key, "$"+vs+":"+field)
+				continue
+			}
+		case int:
+			vi = realKey[i].Value.(int)
 		}
+
 		if vi == 1 {
 			key = append(key, field)
 			continue
@@ -1548,10 +1561,6 @@ func simpleIndexKey(realKey bson.D) (key []string) {
 			key = append(key, "-"+field)
 			continue
 		}
-		if vs, ok := realKey[i].Value.(string); ok {
-			key = append(key, "$"+vs+":"+field)
-			continue
-		}
 		panic("Got unknown index key type for field " + field)
 	}
 	return
@@ -4305,11 +4314,10 @@ func (q *Query) Apply(change Change, result interface{}) (info *ChangeInfo, err
 	var doc valueResult
 	for i := 0; i < maxUpsertRetries; i++ {
 		err = session.DB(dbname).Run(&cmd, &doc)
-
 		if err == nil {
 			break
 		}
-		if change.Upsert && IsDup(err) {
+		if change.Upsert && IsDup(err) && i+1 < maxUpsertRetries {
 			// Retry duplicate key errors on upserts.
 			// https://docs.mongodb.com/v3.2/reference/method/db.collection.update/#use-unique-indexes
 			continue
diff --git a/session_test.go b/session_test.go
index a89279d..492f210 100644
--- a/session_test.go
+++ b/session_test.go
@@ -1001,6 +1001,26 @@ func (s *S) TestIsDupFindAndModify(c *C) {
 	c.Assert(mgo.IsDup(err), Equals, true)
 }
 
+func (s *S) TestIsDupRetryUpsert(c *C) {
+	session, err := mgo.Dial("localhost:40001")
+	c.Assert(err, IsNil)
+	defer session.Close()
+
+	coll := session.DB("mydb").C("mycoll")
+
+	err = coll.Insert(bson.M{"_id": 1, "x": 1})
+	c.Assert(err, IsNil)
+
+	_, err = coll.Upsert(bson.M{"_id": 1, "x": 2}, bson.M{"$set": bson.M{"x": 3}})
+	c.Assert(mgo.IsDup(err), Equals, true)
+
+	_, err = coll.Find(bson.M{"_id": 1, "x": 2}).Apply(mgo.Change{
+		Update: bson.M{"$set": bson.M{"x": 3}},
+		Upsert: true,
+	}, nil)
+	c.Assert(mgo.IsDup(err), Equals, true)
+}
+
 func (s *S) TestFindAndModify(c *C) {
 	session, err := mgo.Dial("localhost:40011")
 	c.Assert(err, IsNil)
@@ -4159,11 +4179,11 @@ func (s *S) TestBypassValidation(c *C) {
 
 func (s *S) TestVersionAtLeast(c *C) {
 	tests := [][][]int{
-		{{3,2,1}, {3,2,0}},
-		{{3,2,1}, {3,2}},
-		{{3,2,1}, {2,5,5,5}},
-		{{3,2,1}, {2,5,5}},
-		{{3,2,1}, {2,5}},
+		{{3, 2, 1}, {3, 2, 0}},
+		{{3, 2, 1}, {3, 2}},
+		{{3, 2, 1}, {2, 5, 5, 5}},
+		{{3, 2, 1}, {2, 5, 5}},
+		{{3, 2, 1}, {2, 5}},
 	}
 	for _, pair := range tests {
 		bi := mgo.BuildInfo{VersionArray: pair[0]}

Debdiff

File lists identical (after any substitutions)

No differences were encountered in the control files

More details

Full run details