This is AmigaDaLua based on Lua 5.4.8.
This fork has (some) Amiga NDK bindings such that you can write Amiga programs in Lua.
NOTE: This is incomplete and not really usable for anything for the time being.
For installation instructions, license details, and further information about Lua, see doc/readme.html.
AmigaDaLua and Lua in general uses a large stack. Set the stack on your shell before running.
CLI>stack 256000There are two ways to access the Amiga NDK bindings in AmigaDaLua
- Use
lua_bigwhich has all configured Amiga NDK bindings available - Use
luaand dynamically load bindings via lua
LoadBindings("exec")When you load a binding, the corrensponding .bindings file must be available. For example exec.bindings
Currently available bindings libraries:
LoadBindings("dos")
LoadBindings("exec")
LoadBindings("graphics")
LoadBindings("intuition")To get an idea of which symbols should have bindings see:
They have been automatically generated so symbols for these libraries may have been missed. More comprehensive binding coverage and documentation will follow.
The bindings code is automatically generated and quite memory heavy
Functions that take a variable number of tags such as OpenWindowTags on the Amiga would require a TAG_END tag to indicate the end of the tag arguments. On AmigaDaLua this is not currently required/supported.
mywin = OpenWindowTags(nil,
WA_Title, "GadTools Gadget Demo (Lua)",
WA_Gadgets, GetPtr(glist),
WA_AutoAdjust, true,
WA_Width, 400,
WA_MinWidth, 50,
WA_InnerHeight, 140,
WA_MinHeight, 50,
WA_DragBar, true,
WA_DepthGadget, true,
WA_Activate, true,
WA_CloseGadget, true,
WA_SizeGadget, true,
WA_SimpleRefresh, true,
WA_IDCMP, IDCMP_CLOSEWINDOW | IDCMP_REFRESHWINDOW | IDCMP_VANILLAKEY | SLIDERIDCMP | STRINGIDCMP | BUTTONIDCMP,
WA_PubScreen, GetPtr(mysc))Creating a TagList requires Lua utility code (found in util.lua). Again, no need for TAG_END.
local Util = require("util")
local tags = Util.TagList {
WA_Title = "GadTools Gadget Demo (Lua)",
WA_Gadgets = GetPtr(gad),
WA_Width = 400,
WA_InnerHeight = 100,
WA_AutoAdjust = true,
WA_DragBar = true,
WA_DepthGadget = true,
WA_CloseGadget = true,
WA_Activate = true,
WA_PubScreen = GetPtr(mysc),
WA_IDCMP = IDCMP_CLOSEWINDOW|IDCMP_REFRESHWINDOW|BUTTONIDCMP,
}
local mywin = OpenWindowTagList(nil, tags)To create a variable of TextAttr type you can create it inline as follows:
local Topaz80 = TextAttr {
ta_Name = "topaz.font",
ta_YSize = 8,
ta_Style = 0,
ta_Flags = 0,
}This can then be used by any type that expects a TextAttr, eg:
local ng = NewGadget {
ng_TextAttr = Topaz80,
ng_VisualInfo = vi,
ng_LeftEdge = 150,
ng_TopEdge = 20 + mysc.WBorTop + (mysc.Font.ta_YSize + 1),
ng_Width = 100,
ng_Height = 12,
ng_GadgetText = "Click Me",
ng_GadgetID = MYGAD_BUTTON,
ng_Flags = 0,
}If you are assigning a typed variable to something untyped (like a TAG or void *) you must use the GetPtr function to convert the type to a pointer.
local screen = OpenScreenTags(nil,
SA_Overscan, OSCAN_STANDARD,
SA_Title, "User Copper List Example",
SA_Font, GetPtr(Topaz80))AmigaDaLua has some special types for creating arrays of words. Note: these arrays are indexed as Lua arrays (1 based index)
local spectrum = CreateArrayUWORD {
0x0604, 0x0605, 0x0606, 0x0607, 0x0617, 0x0618, 0x0619,
0x0629, 0x072a, 0x073b, 0x074b, 0x074c, 0x075d, 0x076e,
0x077e, 0x088f, 0x07af, 0x06cf, 0x05ff, 0x04fb, 0x04f7,
0x03f3, 0x07f2, 0x0bf1, 0x0ff0, 0x0fc0, 0x0ea0, 0x0e80,
0x0e60, 0x0d40, 0x0d20, 0x0d00
}If you need to create the array in chip ram, use CreateChipArrayUWORD
Amiga examples might use a static buffer to store data, the easiest way to do this in AmigaDaLua is to use AllocMem
/* C example */
char buffer[1024];-- Easiest to do this with AllocMem in AmigaDaLua
local buffer = AllocMem(1024, MEMF_PUBLIC)Use the special :ptr() array extension to get the address of an array element. Note: array indexes are 1 indexed.
CMOVE(uCopList, custom.color:ptr(1), spectrum[i])Many AmigaOS functions will return 0. In Lua this is not == false - Safest to use Amiga defined return value variables.
Structure fields of real types or AmigaOS functions that return real types will be equal to nil when there is no value.
NewGadgetList will create the equivalent of a pointer-to-pointer (GadgetPtr) for use with CreateContext(). Once the context is created you can use the returned gadget as a pointer to the gadget list.
local gad = CreateContext(NewGadgetList())
local glist = gad -- Lua slightly different way of keeping track of the glistA selection of examples mainly taken from the Amiga RKM. Many examples have the original C code as a reference.
You can run the examples from a shell:
CLI>lua dos_simple.luaReads a file uses Open/Read/Write/Output etc.
Basic example of Lua coroutines
From RKM Simple example of using a number of gadtools gadgets. Here's a working example showing how to set up and use a linked list of GadTools gadgets complete with keyboard shortcuts.
From RKM The example listed here shows how to use the NewGadget structure and the GadTools library functions discussed above to create a simple button gadget.
This also shows how to use tag lists with AmigaDaLua.
From RKM The example program below shows the use of user Copper lists under Intuition.
From RKM This example must be linked with animtools.c and includes the header files animtools.h and animtools_proto.h. These files are listed at the end of the chapter.
Shows how to use a Bob under intuition.
From RKM Uses the amiga.lib function CreateTask() to create a simple subtask. See the Includes and Autodocs manual for CreateTask() source code.
This is a little funky under Lua - remember don't use Dos functions inside a Task!
Bindings are automatically generated based on the Amiga NDK includes.
For each library, the bindings are configured in an associated python file:
The TYPES array is a list of structs or typedefs you wish to bind.
The TYPE_CONFIG array lets you optionally configure certain generation parameters for types specified in the TYPES array. This is currently used to allow types to be referenced between libraries without whole bindings being generated in both.
The FUNCTION_CONFIG array lists all the functions for which you wish to generate bindings.
The DEFINE_CONFIGS lists any #define or other global variables for which you wish to generate bindings.
The TAGS_FUNCTION_CONFIG dictionary is a special case for functions with tag lists. You must specify the name of the function which takes a variable number of tags, and associate it with a function that takes a tag list. For example:
{ "name": "OpenWindowTags", "tagList": "OpenWindowTagList"},The ENUM_CONFIG, FAKE_FUNCTION_CONFIG, BOOL_FUNCTION_CONFIG, FUNCTOR_SKIP arrays are not currently used by AmigaDaLua
- Add the name of the library in the src/Makefile using the
LUA_BINDINGSvariable - say for examplelayers
LUA_BINDINGS=dos exec graphics intuition layers- Create a new file
lua_layers.pyand configure the bindings
Two python programs extract_defines.py and extract_from_sfd.py might help you automatically extract the names of items to bind.
- Create a new file
bindings_layers.cand include the following code
#include "bindings.h"
#include "_lua_gen_layers.h"makeshould now create a filelayers.bindingsas well as include all new bindings inlua_big
- Install bebbo's Amiga GCC (only tested with the gcc-6 branch)
- Install the Amiga NDK
- Ensure you have
python3to regenerate bindings files - Install
python.clang.cindexfor parsing Amiga NDK via clang - Install
clang - Edit src/lua_generate.py to correct the path to clang:
clang.cindex.Config.set_library_file('/opt/homebrew/opt/llvm/lib/libclang.dylib')And to correct the include path to the NDK:
tu = index.parse(header, args=['-x', 'c', '-I/usr/local/amiga/bebbo/m68k-amigaos/sys-include/', '-I/usr/local/amiga/bebbo/m68k-amigaos/ndk-includ\
e'])makeshould then build the lua commandlua, the full bindings versionlua_bigthe bindings files*.bindingsas well as the lua compiler which at this stage is totally untested in AmigaDaLualuac






