aboutsummaryrefslogtreecommitdiff
path: root/src/pkg/runtime
diff options
context:
space:
mode:
authorRuss Cox <rsc@golang.org>2010-05-01 13:15:42 -0700
committerRuss Cox <rsc@golang.org>2010-05-01 13:15:42 -0700
commit6361f52fc4ae682e3dae3264cee1f45876272c54 (patch)
treea65064ae7640c7a8164bf962f33c61998068ed4a /src/pkg/runtime
parent97576673bd22ab77e9ca9f9bea27f91a895ca4a2 (diff)
downloadgo-6361f52fc4ae682e3dae3264cee1f45876272c54.tar.xz
gc: be pickier about slice, chan, array, and map sizes
Fixes #589. R=ken2 CC=golang-dev https://golang.org/cl/1032044
Diffstat (limited to 'src/pkg/runtime')
-rw-r--r--src/pkg/runtime/chan.c9
-rw-r--r--src/pkg/runtime/hashmap.c9
-rw-r--r--src/pkg/runtime/runtime.h4
-rw-r--r--src/pkg/runtime/slice.c19
4 files changed, 25 insertions, 16 deletions
diff --git a/src/pkg/runtime/chan.c b/src/pkg/runtime/chan.c
index 5793159062..08cd75a6e5 100644
--- a/src/pkg/runtime/chan.c
+++ b/src/pkg/runtime/chan.c
@@ -90,11 +90,14 @@ static uint32 fastrand2(void);
static void destroychan(Hchan*);
Hchan*
-makechan(Type *elem, uint32 hint)
+makechan(Type *elem, int64 hint)
{
Hchan *c;
int32 i;
+ if(hint < 0 || (int32)hint != hint || hint > ((uintptr)-1) / elem->size)
+ panicstring("makechan: size out of range");
+
if(elem->alg >= nelem(algarray)) {
printf("chan(alg=%d)\n", elem->alg);
throw("runtime.makechan: unsupported elem type");
@@ -141,9 +144,9 @@ destroychan(Hchan *c)
}
-// makechan(elemsize uint32, elemalg uint32, hint uint32) (hchan *chan any);
+// makechan(elem *Type, hint int64) (hchan *chan any);
void
-·makechan(Type *elem, uint32 hint, Hchan *ret)
+·makechan(Type *elem, int64 hint, Hchan *ret)
{
ret = makechan(elem, hint);
FLUSH(&ret);
diff --git a/src/pkg/runtime/hashmap.c b/src/pkg/runtime/hashmap.c
index f27264b682..9b039121bb 100644
--- a/src/pkg/runtime/hashmap.c
+++ b/src/pkg/runtime/hashmap.c
@@ -667,11 +667,14 @@ static int32 debug = 0;
// makemap(key, val *Type, hint uint32) (hmap *map[any]any);
Hmap*
-makemap(Type *key, Type *val, uint32 hint)
+makemap(Type *key, Type *val, int64 hint)
{
Hmap *h;
int32 keyalg, valalg, keysize, valsize;
+ if(hint < 0 || (int32)hint != hint)
+ panicstring("makemap: size out of range");
+
keyalg = key->alg;
valalg = val->alg;
keysize = key->size;
@@ -731,9 +734,9 @@ makemap(Type *key, Type *val, uint32 hint)
return h;
}
-// makemap(key, val *Type, hint uint32) (hmap *map[any]any);
+// makemap(key, val *Type, hint int64) (hmap *map[any]any);
void
-·makemap(Type *key, Type *val, uint32 hint, Hmap *ret)
+·makemap(Type *key, Type *val, int64 hint, Hmap *ret)
{
ret = makemap(key, val, hint);
FLUSH(&ret);
diff --git a/src/pkg/runtime/runtime.h b/src/pkg/runtime/runtime.h
index ff4f463b37..4c9f52e85c 100644
--- a/src/pkg/runtime/runtime.h
+++ b/src/pkg/runtime/runtime.h
@@ -577,9 +577,9 @@ struct hash_iter* mapiterinit(Hmap*);
void mapiternext(struct hash_iter*);
bool mapiterkey(struct hash_iter*, void*);
void mapiterkeyvalue(struct hash_iter*, void*, void*);
-Hmap* makemap(Type*, Type*, uint32);
+Hmap* makemap(Type*, Type*, int64);
-Hchan* makechan(Type*, uint32);
+Hchan* makechan(Type*, int64);
void chansend(Hchan*, void*, bool*);
void chanrecv(Hchan*, void*, bool*);
void chanclose(Hchan*);
diff --git a/src/pkg/runtime/slice.c b/src/pkg/runtime/slice.c
index c3c079c670..d967b1669b 100644
--- a/src/pkg/runtime/slice.c
+++ b/src/pkg/runtime/slice.c
@@ -9,17 +9,20 @@
static int32 debug = 0;
// see also unsafe·NewArray
-// makeslice(typ *Type, nel int, cap int) (ary []any);
+// makeslice(typ *Type, len, cap int64) (ary []any);
void
-·makeslice(SliceType *t, uint32 nel, uint32 cap, Slice ret)
+·makeslice(SliceType *t, int64 len, int64 cap, Slice ret)
{
- uint64 size;
+ uintptr size;
+
+ if(len < 0 || (int32)len != len)
+ panicstring("makeslice: len out of range");
+ if(cap < len || (int32)cap != cap || cap > ((uintptr)-1) / t->elem->size)
+ panicstring("makeslice: cap out of range");
- if(cap < nel)
- cap = nel;
size = cap*t->elem->size;
- ret.len = nel;
+ ret.len = len;
ret.cap = cap;
if((t->elem->kind&KindNoPointers))
@@ -30,8 +33,8 @@ void
FLUSH(&ret);
if(debug) {
- printf("makeslice(%S, %d, %d); ret=",
- *t->string, nel, cap);
+ printf("makeslice(%S, %D, %D); ret=",
+ *t->string, len, cap);
·printslice(ret);
}
}