Go, meet Lua
Using Lua in Go and vice-versa!
André Burgaud @andreburgaud
4/15/2020
You 💖Go... Why would you need Lua?
● NGINX (OpenResty)
● Wireshark
● Nmap
● Pandoc
● HAProxy
● Redis
● Roblox
● Rockbox
● SciTE
● LÖVE
Agenda
● CGO
○ Using C from Go (inline code and separate files)
○ Using Go from C (export)
● Embedding Lua in Go (CGO)
○ Executing a lua script from Go
○ Building a basic Lua REPL in Go
● Extending Lua with Go
○ LuaJIT FFI
● Using a Lua Interpreter in Go
CGO ☠
CGO - Inline C code in GO
Go code
C code in Go comments
main.go
I’m using C
code!
CGO - Inline C code in GO (code/demo)
package main
/*
#include <stdio.h>
void hello() {
printf("Hello from C!n");
}
*/
import "C" // No new line between block comment and 'import "C"'
func main() {
C.hello()
}
CGO - Separate *.h and *.c Files
Go code
C code in Go comments
Go code
header files in Go comments
main.go
hello.h
hello.a
exe
hello.c
①
②
CGO - Separate *.h and *.c Files (code/demo)
package main
// #include <stdlib.h>
// #include <hello.h>
import "C"
import (
"unsafe"
)
func main() {
C.hello()
name := C.CString("GoMN")
defer C.free(unsafe.Pointer(name))
C.print(name)
}
main.c
CGO - Using Go from C (export)
Include golib.h
Go code with
Exported functions
main.go
golib.h
golib.so
a.out
①
②
-buildmode=c-shared
golib.so
③
a.out
No fair! C is
using me!
CGO - Using Go from C (code / demo)
package main
import (
"C"
"os"
)
//export Pwd
func Pwd() *C.char {
d, err := os.Getwd()
if err != nil {
return C.CString("Error")
}
return C.CString(d)
}
func main() {}
Embedding Lua in Go
Executing a Lua Script in Go
Go code
C code in Go comments
Go code
Executes hello.lua
header files and
CGO linking
in Go comments
main.go
lua*.h
liblua.a
exe
lauxlib.h
I’m using
Lua C code!
hello.lua
Executing a Lua Script in Go
● CGO ☠ … Again
● Problem with C Macros - #define luaL_loadfile(L,f) luaL_loadfilex(L,f,NULL)
● Unsafe pointers (need to free allocated memory)
Building a Lua REPL in Go
Go code
C code in Go comments
Go code
Executes REPL loop and
Interpretes Lua instructions
header files and
CGO linking
in Go comments
main.go
lua*.h
liblua.a
exe
lauxlib.h
I’m using
Lua C code!
>>> print “hello”
Building a Lua REPL in Go
● Here we CGO ☠ … Again
● Problem with C Macros - #define luaL_loadfile(L,f) luaL_loadfilex(L,f,NULL)
● Unsafe
● Hard to debug
Extending Lua with Go
Extend LuaJIT with Go
Go code with
Exported functions
main.go
golib.so
①
②
-buildmode=c-shared
$ luajit getcwd.lua
/a/b/c/d
$
getcwd.lua
I’m happy to
give a hand
to my friend
Lua
Extend LuaJIT with Go
● LuaJIT FFI
● Extend Lua to include functions not available in the interpreter STL
● Example: current working directory
● In Go: os.Getwd()
○ Export function in Go
○ Use the FFI module available in LuaJIT (calling external C functions)
○ Add C declaration
○ Call the Go function (LuaJIT sees it as a C function)
Export Function in Go (same as C example)
package main
import "C"
import (
"os"
)
//export Pwd
func Pwd() *C.char {
d, err := os.Getwd()
if err != nil {
return C.CString("Error")
}
return C.CString(d)
}
func main() {}
Using a Lua Interpreter in Go
Lua Interpreter in Go 💖
● https://github.com/yuin/gopher-lua
● DoString()
● DoFile()
● Base64 (Bi-directional)
Lua Interpreter in Go 💖
Go code
C code in Go comments
💘
Import gopher-lua
Go code
Executes and extends lua
code
main.go
Go plugin
● Allows creating modular Go programs
● Allows reusing “plugins” across multiple programs
● https://golang.org/pkg/plugin/
$ go build -buildmode=plugin
Ideas 💡
● Configuration files
● Expose internal APIs
● Extension/Customization (games)
● Templating language (HTML, XML, next ML or JSON…)
● Filtering text processing (pandoc)
● ...
Summary
● Quick review of CGO
● Embed Lua in Go (CGO)
● Extend LuaJIT with Go (FFI)
● Embed and Extend with a Lua interpreter written in Go
● More ideas to explore
Go Online Resources
● https://github.com/andreburgaud/meetup-golang-lua Source code
● https://golang.org/cmd/cgo/ Command cgo
● https://nick.groenen.me/posts/plugins-in-go-18/ Plugins in Go 1.8
● https://medium.com/learning-the-go-programming-language/writing-modular-g
o-programs-with-plugins-ec46381ee1a9 Writing Modular Go Programs with
Plugins
● https://docs.google.com/document/d/1nr-TQHw_er6GOQRsF6T43GGhFDelr
AP0NqSS_00RgZ Go Execution Modes
Lua Interpreters in Go
● https://github.com/Azure/golua A Lua 5.3 engine implemented in Go (MIT)
● https://github.com/Shopify/go-lua A Lua VM in Go (MIT)
● https://github.com/yuin/gopher-lua GopherLua: VM and compiler for Lua in Go
(MIT)
● https://github.com/milochristiansen/lua A Lua 5.3 VM and compiler written in
Go (Zlib)
Go Books
● https://nostarch.com/blackhatgo Black Hat Go
● https://www.gopl.io/ The Go Programming Language
● https://www.packtpub.com/programming/mastering-go-second-edition
Mastering Go
Lua Online Resources
● https://www.lua.org/ Lua Web Site
● https://luajit.org/ The LuaJIT Project
● https://www.oreilly.com/content/learn-lua-from-javascript-part-1-an-introductio
n-to-lua/ Learn Lua from JavaScript, part 1: An introduction to Lua
Lua Books
● https://www.lua.org/pil/ Programming in Lua
● https://www.packtpub.com/application-development/lua-quick-start-guide Lua
Quick Start Guide
Other Resources
● https://love2d.org/ LÖVE
● https://github.com/love2d/love LÖVE
Attributions
● Lua Logo: By Alexandre Nakonechnyj (Grafik-Design) und Lua-Team
(PostScript-Code) - svg from PostScript Source (see below) created from
Lumu, Public Domain,
https://commons.wikimedia.org/w/index.php?curid=37714918
● Gopher: By Takuya Ueda (https://twitter.com/tenntenn). Licensed under the
Creative Commons 3.0 Attributions license,
https://github.com/golang-samples/gopher-vector
License
● Copyright © 2020 by Andre Burgaud https://burgaud.com
● Released under https://creativecommons.org/licenses/by/4.0/

Go, meet Lua

  • 1.
    Go, meet Lua UsingLua in Go and vice-versa! André Burgaud @andreburgaud 4/15/2020
  • 2.
    You 💖Go... Whywould you need Lua? ● NGINX (OpenResty) ● Wireshark ● Nmap ● Pandoc ● HAProxy ● Redis ● Roblox ● Rockbox ● SciTE ● LÖVE
  • 3.
    Agenda ● CGO ○ UsingC from Go (inline code and separate files) ○ Using Go from C (export) ● Embedding Lua in Go (CGO) ○ Executing a lua script from Go ○ Building a basic Lua REPL in Go ● Extending Lua with Go ○ LuaJIT FFI ● Using a Lua Interpreter in Go
  • 4.
  • 5.
    CGO - InlineC code in GO Go code C code in Go comments main.go I’m using C code!
  • 6.
    CGO - InlineC code in GO (code/demo) package main /* #include <stdio.h> void hello() { printf("Hello from C!n"); } */ import "C" // No new line between block comment and 'import "C"' func main() { C.hello() }
  • 7.
    CGO - Separate*.h and *.c Files Go code C code in Go comments Go code header files in Go comments main.go hello.h hello.a exe hello.c ① ②
  • 8.
    CGO - Separate*.h and *.c Files (code/demo) package main // #include <stdlib.h> // #include <hello.h> import "C" import ( "unsafe" ) func main() { C.hello() name := C.CString("GoMN") defer C.free(unsafe.Pointer(name)) C.print(name) }
  • 9.
    main.c CGO - UsingGo from C (export) Include golib.h Go code with Exported functions main.go golib.h golib.so a.out ① ② -buildmode=c-shared golib.so ③ a.out No fair! C is using me!
  • 10.
    CGO - UsingGo from C (code / demo) package main import ( "C" "os" ) //export Pwd func Pwd() *C.char { d, err := os.Getwd() if err != nil { return C.CString("Error") } return C.CString(d) } func main() {}
  • 11.
  • 12.
    Executing a LuaScript in Go Go code C code in Go comments Go code Executes hello.lua header files and CGO linking in Go comments main.go lua*.h liblua.a exe lauxlib.h I’m using Lua C code! hello.lua
  • 13.
    Executing a LuaScript in Go ● CGO ☠ … Again ● Problem with C Macros - #define luaL_loadfile(L,f) luaL_loadfilex(L,f,NULL) ● Unsafe pointers (need to free allocated memory)
  • 14.
    Building a LuaREPL in Go Go code C code in Go comments Go code Executes REPL loop and Interpretes Lua instructions header files and CGO linking in Go comments main.go lua*.h liblua.a exe lauxlib.h I’m using Lua C code! >>> print “hello”
  • 15.
    Building a LuaREPL in Go ● Here we CGO ☠ … Again ● Problem with C Macros - #define luaL_loadfile(L,f) luaL_loadfilex(L,f,NULL) ● Unsafe ● Hard to debug
  • 16.
  • 17.
    Extend LuaJIT withGo Go code with Exported functions main.go golib.so ① ② -buildmode=c-shared $ luajit getcwd.lua /a/b/c/d $ getcwd.lua I’m happy to give a hand to my friend Lua
  • 18.
    Extend LuaJIT withGo ● LuaJIT FFI ● Extend Lua to include functions not available in the interpreter STL ● Example: current working directory ● In Go: os.Getwd() ○ Export function in Go ○ Use the FFI module available in LuaJIT (calling external C functions) ○ Add C declaration ○ Call the Go function (LuaJIT sees it as a C function)
  • 19.
    Export Function inGo (same as C example) package main import "C" import ( "os" ) //export Pwd func Pwd() *C.char { d, err := os.Getwd() if err != nil { return C.CString("Error") } return C.CString(d) } func main() {}
  • 20.
    Using a LuaInterpreter in Go
  • 21.
    Lua Interpreter inGo 💖 ● https://github.com/yuin/gopher-lua ● DoString() ● DoFile() ● Base64 (Bi-directional)
  • 22.
    Lua Interpreter inGo 💖 Go code C code in Go comments 💘 Import gopher-lua Go code Executes and extends lua code main.go
  • 23.
    Go plugin ● Allowscreating modular Go programs ● Allows reusing “plugins” across multiple programs ● https://golang.org/pkg/plugin/ $ go build -buildmode=plugin
  • 24.
    Ideas 💡 ● Configurationfiles ● Expose internal APIs ● Extension/Customization (games) ● Templating language (HTML, XML, next ML or JSON…) ● Filtering text processing (pandoc) ● ...
  • 25.
    Summary ● Quick reviewof CGO ● Embed Lua in Go (CGO) ● Extend LuaJIT with Go (FFI) ● Embed and Extend with a Lua interpreter written in Go ● More ideas to explore
  • 26.
    Go Online Resources ●https://github.com/andreburgaud/meetup-golang-lua Source code ● https://golang.org/cmd/cgo/ Command cgo ● https://nick.groenen.me/posts/plugins-in-go-18/ Plugins in Go 1.8 ● https://medium.com/learning-the-go-programming-language/writing-modular-g o-programs-with-plugins-ec46381ee1a9 Writing Modular Go Programs with Plugins ● https://docs.google.com/document/d/1nr-TQHw_er6GOQRsF6T43GGhFDelr AP0NqSS_00RgZ Go Execution Modes
  • 27.
    Lua Interpreters inGo ● https://github.com/Azure/golua A Lua 5.3 engine implemented in Go (MIT) ● https://github.com/Shopify/go-lua A Lua VM in Go (MIT) ● https://github.com/yuin/gopher-lua GopherLua: VM and compiler for Lua in Go (MIT) ● https://github.com/milochristiansen/lua A Lua 5.3 VM and compiler written in Go (Zlib)
  • 28.
    Go Books ● https://nostarch.com/blackhatgoBlack Hat Go ● https://www.gopl.io/ The Go Programming Language ● https://www.packtpub.com/programming/mastering-go-second-edition Mastering Go
  • 29.
    Lua Online Resources ●https://www.lua.org/ Lua Web Site ● https://luajit.org/ The LuaJIT Project ● https://www.oreilly.com/content/learn-lua-from-javascript-part-1-an-introductio n-to-lua/ Learn Lua from JavaScript, part 1: An introduction to Lua
  • 30.
    Lua Books ● https://www.lua.org/pil/Programming in Lua ● https://www.packtpub.com/application-development/lua-quick-start-guide Lua Quick Start Guide
  • 31.
    Other Resources ● https://love2d.org/LÖVE ● https://github.com/love2d/love LÖVE
  • 32.
    Attributions ● Lua Logo:By Alexandre Nakonechnyj (Grafik-Design) und Lua-Team (PostScript-Code) - svg from PostScript Source (see below) created from Lumu, Public Domain, https://commons.wikimedia.org/w/index.php?curid=37714918 ● Gopher: By Takuya Ueda (https://twitter.com/tenntenn). Licensed under the Creative Commons 3.0 Attributions license, https://github.com/golang-samples/gopher-vector
  • 33.
    License ● Copyright ©2020 by Andre Burgaud https://burgaud.com ● Released under https://creativecommons.org/licenses/by/4.0/