go/ssa/interp: add intrinsic for runtime.NumGoroutine
...which is used by $GOROOT/test/goprint.go. Change-Id: I4626b8fae3f87d9c8dd8cdcd8c05036955a36262 Reviewed-on: https://go-review.googlesource.com/22560 Reviewed-by: Robert Griesemer <gri@golang.org>
This commit is contained in:
parent
50ff896a1c
commit
56005b4126
|
@ -15,6 +15,7 @@ import (
|
|||
"os"
|
||||
"runtime"
|
||||
"strings"
|
||||
"sync/atomic"
|
||||
"syscall"
|
||||
"time"
|
||||
"unsafe"
|
||||
|
@ -104,6 +105,7 @@ func init() {
|
|||
"runtime.Gosched": ext۰runtime۰Gosched,
|
||||
"runtime.init": ext۰runtime۰init,
|
||||
"runtime.NumCPU": ext۰runtime۰NumCPU,
|
||||
"runtime.NumGoroutine": ext۰runtime۰NumGoroutine,
|
||||
"runtime.ReadMemStats": ext۰runtime۰ReadMemStats,
|
||||
"runtime.SetFinalizer": ext۰runtime۰SetFinalizer,
|
||||
"(*runtime.Func).Entry": ext۰runtime۰Func۰Entry,
|
||||
|
@ -387,6 +389,10 @@ func ext۰runtime۰NumCPU(fr *frame, args []value) value {
|
|||
return runtime.NumCPU()
|
||||
}
|
||||
|
||||
func ext۰runtime۰NumGoroutine(fr *frame, args []value) value {
|
||||
return int(atomic.LoadInt32(&fr.i.goroutines))
|
||||
}
|
||||
|
||||
func ext۰runtime۰ReadMemStats(fr *frame, args []value) value {
|
||||
// TODO(adonovan): populate args[0].(Struct)
|
||||
return nil
|
||||
|
|
|
@ -53,6 +53,7 @@ import (
|
|||
"os"
|
||||
"reflect"
|
||||
"runtime"
|
||||
"sync/atomic"
|
||||
|
||||
"golang.org/x/tools/go/ssa"
|
||||
)
|
||||
|
@ -86,6 +87,7 @@ type interpreter struct {
|
|||
rtypeMethods methodSet // the method set of rtype, which implements the reflect.Type interface.
|
||||
runtimeErrorString types.Type // the runtime.errorString type
|
||||
sizes types.Sizes // the effective type-sizing function
|
||||
goroutines int32 // atomically updated
|
||||
}
|
||||
|
||||
type deferred struct {
|
||||
|
@ -269,7 +271,11 @@ func visitInstr(fr *frame, instr ssa.Instruction) continuation {
|
|||
|
||||
case *ssa.Go:
|
||||
fn, args := prepareCall(fr, &instr.Call)
|
||||
go call(fr.i, nil, instr.Pos(), fn, args)
|
||||
atomic.AddInt32(&fr.i.goroutines, 1)
|
||||
go func() {
|
||||
call(fr.i, nil, instr.Pos(), fn, args)
|
||||
atomic.AddInt32(&fr.i.goroutines, -1)
|
||||
}()
|
||||
|
||||
case *ssa.MakeChan:
|
||||
fr.env[instr] = make(chan value, asInt(fr.get(instr.Size)))
|
||||
|
@ -660,10 +666,11 @@ func deleteBodies(pkg *ssa.Package, except ...string) {
|
|||
//
|
||||
func Interpret(mainpkg *ssa.Package, mode Mode, sizes types.Sizes, filename string, args []string) (exitCode int) {
|
||||
i := &interpreter{
|
||||
prog: mainpkg.Prog,
|
||||
globals: make(map[ssa.Value]*value),
|
||||
mode: mode,
|
||||
sizes: sizes,
|
||||
prog: mainpkg.Prog,
|
||||
globals: make(map[ssa.Value]*value),
|
||||
mode: mode,
|
||||
sizes: sizes,
|
||||
goroutines: 1,
|
||||
}
|
||||
runtimePkg := i.prog.ImportedPackage("runtime")
|
||||
if runtimePkg == nil {
|
||||
|
|
Loading…
Reference in New Issue