簡體   English   中英

有沒有一種方法可以在不需要任何特殊設置的情況下從另一個二進制文件執行已編譯的 golang 二進制文件中的函數?

[英]Is there a way to execute functions in a compiled golang binary from another binary without needing any special setup?

我有一個 RPC 類型的設置,其中一個二進制文件 (binaryA) 請求從另一個二進制文件 (binaryB) 完成工作。 它們都以相同的方式編譯並且在同一個系統上。 我無法使用 binaryA,因為所涉及的任務涉及大量數據,這些數據需要很長時間才能序列化,而且我無法使用golang 插件,因為我希望能夠在無需創建特殊二進制文件的情況下調用函數.

這大致是我試圖實現的設置:

binaryA 用go build mainA.go編譯。 在那個二進制文件的某個地方,這個文件被編譯:

package demo
import "fmt"

func TestFn(){
    fmt.Println("binaryA")
    func(){ someFn() }()
}

我希望能夠使用 binaryB 調用 TestFn() 和匿名函數。

這是我到目前為止所擁有的。

import (
    "debug/macho"
    "fmt"
    "os"
    "reflect"
    "unsafe"
)

func main() {
    filename := "binaryA"
    f, _ := os.Open(filename)
    defer f.Close()

    mf, _ := macho.NewFile(f)

    sym2Addr := make(map[string]uintptr)
    for _, sym := range mf.Symtab.Syms {
        if int(sym.Sect-1) >= len(mf.Sections) || 
           mf.Sections[sym.Sect-1].Seg != "__TEXT" { continue }
        value := uintptr(sym.Value)
        sym2Addr[sym.Name] = value
    }

    funcType := reflect.TypeOf(func() {})
    if testFnPtr, ok := sym2Addr["main.TestFn"]; ok {
        TestFn := reflect.New(funcType).Elem()
        p := new(uintptr)
        *p = testFnPtr
        *(*unsafe.Pointer)(unsafe.Pointer(TestFn.Addr().Pointer())) = unsafe.Pointer(p)
        TestFn.Call([]reflect.Value{})
    }
}

使用上面的代碼我可以找到符號main.TestFn但它最終失敗了:

unexpected fault address 0x210d0fb1
fatal error: fault
[signal SIGBUS: bus error code=0x2 addr=0x210d0fb1 pc=0x210d0fb1]

goroutine 1 [running]:
runtime.throw(...)
        .asdf/installs/golang/1.15/go/src/runtime/panic.go:1116 
runtime.sigpanic()
        .asdf/installs/golang/1.15/go/src/runtime/signal_unix.go:717
runtime.call32(...)
        .asdf/installs/golang/1.15/go/src/runtime/asm_amd64.s:540 
reflect.Value.call(...)
        .asdf/installs/golang/1.15/go/src/reflect/value.go:475 
reflect.Value.Call(...)
        .asdf/installs/golang/1.15/go/src/reflect/value.go:336
main.main()
        plugin_demo.go:106
runtime.main()
        .asdf/installs/golang/1.15/go/src/runtime/proc.go:204
runtime.goexit()
        .asdf/installs/golang/1.15/go/src/runtime/asm_amd64.s:1374
exit status 2

編輯:我可以使用我想要的任何構建標志重新編譯 binaryA。

有沒有一種方法可以在不需要任何特殊設置的情況下從另一個二進制文件執行已編譯的 golang 二進制文件中的函數?

不,這根本不是編譯(機器代碼)程序的工作方式(以任何語言)。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM