diff --git a/interp/frame.go b/interp/frame.go index ee93e5a3..6e8958ef 100644 --- a/interp/frame.go +++ b/interp/frame.go @@ -310,6 +310,8 @@ func (fr *frame) evalBasicBlock(bb, incoming llvm.BasicBlock, indent string) (re case callee.Name() == "runtime.makeInterface": uintptrType := callee.Type().Context().IntType(fr.TargetData.PointerSize() * 8) fr.locals[inst] = &LocalValue{fr.Eval, llvm.ConstPtrToInt(inst.Operand(0), uintptrType)} + case callee.Name() == "runtime.nanotime": + fr.locals[inst] = &LocalValue{fr.Eval, llvm.ConstInt(fr.Mod.Context().Int64Type(), 0, false)} case strings.HasPrefix(callee.Name(), "runtime.print") || callee.Name() == "runtime._panic": // This are all print instructions, which necessarily have side // effects but no results. diff --git a/interp/scan.go b/interp/scan.go index 1b6ed315..6b37b604 100644 --- a/interp/scan.go +++ b/interp/scan.go @@ -28,6 +28,9 @@ func (e *Eval) hasSideEffects(fn llvm.Value) *sideEffectResult { case "runtime.alloc": // Cannot be scanned but can be interpreted. return &sideEffectResult{severity: sideEffectNone} + case "runtime.nanotime": + // Fixed value at compile time. + return &sideEffectResult{severity: sideEffectNone} case "runtime._panic": return &sideEffectResult{severity: sideEffectLimited} } diff --git a/src/runtime/runtime.go b/src/runtime/runtime.go index 2e68fb8c..8a1856d5 100644 --- a/src/runtime/runtime.go +++ b/src/runtime/runtime.go @@ -84,9 +84,13 @@ func sleep(d int64) { sleepTicks(timeUnit(d / tickMicros)) } +func nanotime() int64 { + return int64(ticks()) * tickMicros +} + //go:linkname now time.now func now() (sec int64, nsec int32, mono int64) { - mono = int64(ticks()) * tickMicros + mono = nanotime() sec = mono / (1000 * 1000 * 1000) nsec = int32(mono - sec*(1000*1000*1000)) return