Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

patch fun after how get origin fun #12

Open
zeromake opened this issue Apr 6, 2021 · 3 comments
Open

patch fun after how get origin fun #12

zeromake opened this issue Apr 6, 2021 · 3 comments
Labels
question Further information is requested

Comments

@zeromake
Copy link

zeromake commented Apr 6, 2021

not use UnPatch

package main

import (
	"fmt"
	sm "github.com/cch123/supermonkey"
	"time"
)
//go:noinline
func Now() time.Time {
	return time.Time{}
}

func main() {
	sm.Patch(time.Now, Now)
	fmt.Println(time.Now())
	// how call origin Now fun
}
@zeromake
Copy link
Author

zeromake commented Apr 6, 2021

@Mutated1994 What I want is not to use Unpatch

@ioworker0
Copy link
Collaborator

@Mutated1994 What I want is not to use Unpatch

Unfortunately, you might not be able to call original function without Unpatch.

@cch123 cch123 added the question Further information is requested label Apr 15, 2021
@zeromake
Copy link
Author

zeromake commented Sep 22, 2021

a scenario main.go:

package main

import (
	sm "github.com/cch123/supermonkey"
	"log"
	"time"
	"unsafe"
)

//go:linkname runtimeNano runtime.nanotime
func runtimeNano() int64

//go:linkname now time.now
func now() (sec int64, nsec int32, mono int64)

var startNano = runtimeNano() - 1

type _time struct {
	wall uint64
	ext  int64
	loc  *time.Location
}


const (
	secondsPerMinute = 60
	secondsPerHour   = 60 * secondsPerMinute
	secondsPerDay    = 24 * secondsPerHour
)

const (
	unixToInternal int64 = (1969*365 + 1969/4 - 1969/100 + 1969/400) * secondsPerDay
	wallToInternal int64 = (1884*365 + 1884/4 - 1884/100 + 1884/400) * secondsPerDay
)

const (
	hasMonotonic = 1 << 63
	minWall      = wallToInternal // year 1885
	nsecShift    = 30
)

func _now() time.Time {
	sec, nsec, mono := now()
	mono -= startNano
	sec += unixToInternal - minWall
	var t *_time
	if uint64(sec)>>33 != 0 {
		t = &_time{uint64(nsec), sec + minWall, time.Local}
	} else {
		t = &_time{hasMonotonic | uint64(sec)<<nsecShift | uint64(nsec), mono, time.Local}
	}
	return *(*time.Time)(unsafe.Pointer(t))
}

func patchNow() time.Time {
	return time.Time{}
}

func main()  {
	log.Println("std:", time.Now())
	log.Println("customization:", _now())
	sm.Patch(time.Now, patchNow)
	log.Println("std:", time.Now())
	log.Println("customization:", _now())
}

output:

$ go run main.go
2021/09/22 19:08:03 std: 2021-09-22 19:08:03.4244406 +0800 CST m=+0.006212801
2021/09/22 19:08:03 customization: 2021-09-22 19:08:03.430072 +0800 CST m=+0.005631401
0001/01/01 00:00:00 std: 0001-01-01 00:00:00 +0000 UTC
0001/01/01 00:00:00 customization: 2021-09-22 19:08:03.430072 +0800 CST m=+0.005631401

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested
Projects
None yet
Development

No branches or pull requests

3 participants