2022-07-07 04:32:00 +00:00
|
|
|
package main
|
|
|
|
|
|
|
|
import (
|
2023-02-19 19:27:25 +00:00
|
|
|
"plugin"
|
2022-07-07 04:32:00 +00:00
|
|
|
|
|
|
|
"hilbish/util"
|
|
|
|
|
|
|
|
rt "github.com/arnodel/golua/runtime"
|
|
|
|
)
|
|
|
|
|
2023-07-11 02:32:59 +00:00
|
|
|
// #interface module
|
|
|
|
// native module loading
|
|
|
|
/* The hilbish.module interface provides a function
|
|
|
|
to load Hilbish plugins/modules.
|
|
|
|
Hilbish modules are Go-written plugins (see https://pkg.go.dev/plugin)
|
|
|
|
that are used to add functionality to Hilbish that cannot be written
|
|
|
|
n Lua for any reason.
|
|
|
|
|
|
|
|
To make a valid native module, the Go plugin
|
|
|
|
has to export a Loader function with a signature like so:
|
|
|
|
`func(*rt.Runtime) rt.Value`
|
|
|
|
`rt` in this case refers to the Runtime type at
|
|
|
|
https://pkg.go.dev/github.com/arnodel/golua@master/runtime#Runtime
|
|
|
|
Hilbish uses this package as its Lua runtime. You will need to read
|
|
|
|
it to use it for a native plugin.
|
|
|
|
*/
|
2022-07-07 04:32:00 +00:00
|
|
|
func moduleLoader(rtm *rt.Runtime) *rt.Table {
|
|
|
|
exports := map[string]util.LuaExport{
|
|
|
|
"load": {moduleLoad, 2, false},
|
|
|
|
}
|
|
|
|
|
|
|
|
mod := rt.NewTable()
|
|
|
|
util.SetExports(rtm, mod, exports)
|
|
|
|
|
|
|
|
return mod
|
|
|
|
}
|
|
|
|
|
2023-07-11 02:32:59 +00:00
|
|
|
// #interface module
|
|
|
|
// load(path)
|
|
|
|
// Loads a module at the designated `path`.
|
|
|
|
// It will throw if any error occurs.
|
2022-07-07 04:32:00 +00:00
|
|
|
func moduleLoad(t *rt.Thread, c *rt.GoCont) (rt.Cont, error) {
|
2023-02-19 19:27:25 +00:00
|
|
|
if err := c.CheckNArgs(1); err != nil {
|
2022-07-07 04:32:00 +00:00
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
path, err := c.StringArg(0)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2023-02-19 19:27:25 +00:00
|
|
|
p, err := plugin.Open(path)
|
2022-07-07 04:32:00 +00:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2023-02-19 19:27:25 +00:00
|
|
|
value, err := p.Lookup("Loader")
|
2022-07-07 04:32:00 +00:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2023-02-19 19:27:25 +00:00
|
|
|
loader, ok := value.(func(*rt.Runtime) rt.Value)
|
2022-07-07 04:32:00 +00:00
|
|
|
if !ok {
|
2023-02-19 19:27:25 +00:00
|
|
|
return nil, nil
|
2022-07-07 04:32:00 +00:00
|
|
|
}
|
|
|
|
|
2023-02-19 19:27:25 +00:00
|
|
|
val := loader(t.Runtime)
|
2022-07-07 04:32:00 +00:00
|
|
|
|
|
|
|
return c.PushingNext1(t.Runtime, val), nil
|
|
|
|
}
|