diff options
| author | Rémy Oudompheng <oudomphe@phare.normalesup.org> | 2013-01-30 01:55:02 +0100 |
|---|---|---|
| committer | Rémy Oudompheng <oudomphe@phare.normalesup.org> | 2013-01-30 01:55:02 +0100 |
| commit | ccc61eadd548e66c906a0a33e8a9c2d03238649a (patch) | |
| tree | 668cbe9fff3a49001975caf5772f8541675429bb /src/pkg/runtime/slice.c | |
| parent | 76c18a8c4894dcc094f357980bbca8fddf0e98ae (diff) | |
| download | go-ccc61eadd548e66c906a0a33e8a9c2d03238649a.tar.xz | |
runtime: implement range access functions in race detector.
Range access functions are already available in TSan library
but were not yet used.
Time for go test -race -short:
Before:
compress/flate 24.244s
exp/norm >200s
go/printer 78.268s
After:
compress/flate 17.760s
exp/norm 5.537s
go/printer 5.738s
Fixes #4250.
R=dvyukov, golang-dev, fullung
CC=golang-dev
https://golang.org/cl/7229044
Diffstat (limited to 'src/pkg/runtime/slice.c')
| -rw-r--r-- | src/pkg/runtime/slice.c | 64 |
1 files changed, 31 insertions, 33 deletions
diff --git a/src/pkg/runtime/slice.c b/src/pkg/runtime/slice.c index e2c76eb8e7..eda14f85c1 100644 --- a/src/pkg/runtime/slice.c +++ b/src/pkg/runtime/slice.c @@ -71,31 +71,34 @@ makeslice1(SliceType *t, intgo len, intgo cap, Slice *ret) void runtime·appendslice(SliceType *t, Slice x, Slice y, Slice ret) { - intgo m, i; + intgo m; uintptr w; void *pc; m = x.len+y.len; + w = t->elem->size; if(m < x.len) runtime·throw("append: slice overflow"); - if(raceenabled) { - pc = runtime·getcallerpc(&t); - for(i=0; i<x.len; i++) - runtime·racereadpc(x.array + i*t->elem->size, pc, runtime·appendslice); - for(i=x.len; i<x.cap; i++) - runtime·racewritepc(x.array + i*t->elem->size, pc, runtime·appendslice); - for(i=0; i<y.len; i++) - runtime·racereadpc(y.array + i*t->elem->size, pc, runtime·appendslice); - } - if(m > x.cap) growslice1(t, x, m, &ret); else ret = x; - w = t->elem->size; + if(raceenabled) { + // Don't mark read/writes on the newly allocated slice. + pc = runtime·getcallerpc(&t); + // read x[:len] + if(m > x.cap) + runtime·racereadrangepc(x.array, x.len*w, w, pc, runtime·appendslice); + // read y + runtime·racereadrangepc(y.array, y.len*w, w, pc, runtime·appendslice); + // write x[len(x):len(x)+len(y)] + if(m <= x.cap) + runtime·racewriterangepc(ret.array+ret.len*w, y.len*w, w, pc, runtime·appendslice); + } + runtime·memmove(ret.array + ret.len*w, y.array, y.len*w); ret.len += y.len; FLUSH(&ret); @@ -107,7 +110,7 @@ runtime·appendslice(SliceType *t, Slice x, Slice y, Slice ret) void runtime·appendstr(SliceType *t, Slice x, String y, Slice ret) { - intgo m, i; + intgo m; void *pc; m = x.len+y.len; @@ -115,19 +118,22 @@ runtime·appendstr(SliceType *t, Slice x, String y, Slice ret) if(m < x.len) runtime·throw("append: slice overflow"); - if(raceenabled) { - pc = runtime·getcallerpc(&t); - for(i=0; i<x.len; i++) - runtime·racereadpc(x.array + i*t->elem->size, pc, runtime·appendstr); - for(i=x.len; i<x.cap; i++) - runtime·racewritepc(x.array + i*t->elem->size, pc, runtime·appendstr); - } - if(m > x.cap) growslice1(t, x, m, &ret); else ret = x; + if(raceenabled) { + // Don't mark read/writes on the newly allocated slice. + pc = runtime·getcallerpc(&t); + // read x[:len] + if(m > x.cap) + runtime·racereadrangepc(x.array, x.len, 1, pc, runtime·appendstr); + // write x[len(x):len(x)+len(y)] + if(m <= x.cap) + runtime·racewriterangepc(ret.array+ret.len, y.len, 1, pc, runtime·appendstr); + } + runtime·memmove(ret.array + ret.len, y.str, y.len); ret.len += y.len; FLUSH(&ret); @@ -140,7 +146,6 @@ runtime·growslice(SliceType *t, Slice old, int64 n, Slice ret) { int64 cap; void *pc; - int32 i; if(n < 1) runtime·panicstring("growslice: invalid n"); @@ -152,8 +157,7 @@ runtime·growslice(SliceType *t, Slice old, int64 n, Slice ret) if(raceenabled) { pc = runtime·getcallerpc(&t); - for(i=0; i<old.len; i++) - runtime·racewritepc(old.array + i*t->elem->size, pc, runtime·growslice); + runtime·racereadrangepc(old.array, old.len*t->elem->size, t->elem->size, pc, runtime·growslice); } growslice1(t, old, cap, &ret); @@ -199,7 +203,6 @@ void runtime·copy(Slice to, Slice fm, uintptr width, intgo ret) { void *pc; - int32 i; if(fm.len == 0 || to.len == 0 || width == 0) { ret = 0; @@ -212,10 +215,8 @@ runtime·copy(Slice to, Slice fm, uintptr width, intgo ret) if(raceenabled) { pc = runtime·getcallerpc(&to); - for(i=0; i<ret; i++) { - runtime·racewritepc(to.array + i*width, pc, runtime·copy); - runtime·racereadpc(fm.array + i*width, pc, runtime·copy); - } + runtime·racewriterangepc(to.array, ret*width, width, pc, runtime·copy); + runtime·racereadrangepc(fm.array, ret*width, width, pc, runtime·copy); } if(ret == 1 && width == 1) { // common case worth about 2x to do here @@ -245,7 +246,6 @@ void runtime·slicestringcopy(Slice to, String fm, intgo ret) { void *pc; - int32 i; if(fm.len == 0 || to.len == 0) { ret = 0; @@ -258,9 +258,7 @@ runtime·slicestringcopy(Slice to, String fm, intgo ret) if(raceenabled) { pc = runtime·getcallerpc(&to); - for(i=0; i<ret; i++) { - runtime·racewritepc(to.array + i, pc, runtime·slicestringcopy); - } + runtime·racewriterangepc(to.array, ret, 1, pc, runtime·slicestringcopy); } runtime·memmove(to.array, fm.str, ret); |
