说明: 为JME和JSE编写的轻量级、快速、以Java为中心的Lua解释器,具有字符串、表、包、数学、io、os、d...
(Lightweight, fast, Java-centric Lua interpreter written for JME and JSE, with string, table, package, math, io, os, debug, coroutine & luajava libraries, JSR-223 bindings, all metatags, weak tables and unique direct lua-to-java- bytecode compiling.)
.classpath (1002, 2018-06-08)
.project (366, 2018-06-08)
build-coverage.xml (4378, 2018-06-08)
build-libs.xml (2152, 2018-06-08)
build.xml (7703, 2018-06-08)
docs/ (0, 2018-06-08)
docs/api/ (0, 2018-06-08)
docs/api/allclasses-frame.html (8555, 2018-06-08)
docs/api/allclasses-noframe.html (7195, 2018-06-08)
docs/api/constant-values.html (51344, 2018-06-08)
docs/api/deprecated-list.html (5908, 2018-06-08)
docs/api/help-doc.html (9790, 2018-06-08)
docs/api/index-all.html (393669, 2018-06-08)
docs/api/index.html (2564, 2018-06-08)
docs/api/org/ (0, 2018-06-08)
docs/api/org/luaj/ (0, 2018-06-08)
docs/api/org/luaj/vm2/ (0, 2018-06-08)
docs/api/org/luaj/vm2/Buffer.html (26523, 2018-06-08)
docs/api/org/luaj/vm2/Globals.Compiler.html (8887, 2018-06-08)
docs/api/org/luaj/vm2/Globals.Loader.html (9444, 2018-06-08)
docs/api/org/luaj/vm2/Globals.Undumper.html (8700, 2018-06-08)
docs/api/org/luaj/vm2/Globals.html (75840, 2018-06-08)
docs/api/org/luaj/vm2/LoadState.html (34657, 2018-06-08)
docs/api/org/luaj/vm2/LocVars.html (12810, 2018-06-08)
docs/api/org/luaj/vm2/Lua.html (68411, 2018-06-08)
docs/api/org/luaj/vm2/LuaBoolean.html (55856, 2018-06-08)
docs/api/org/luaj/vm2/LuaClosure.html (81238, 2018-06-08)
docs/api/org/luaj/vm2/LuaDouble.html (217491, 2018-06-08)
docs/api/org/luaj/vm2/LuaError.html (18595, 2018-06-08)
docs/api/org/luaj/vm2/LuaFunction.html (57226, 2018-06-08)
docs/api/org/luaj/vm2/LuaInteger.html (205501, 2018-06-08)
docs/api/org/luaj/vm2/LuaNil.html (91065, 2018-06-08)
docs/api/org/luaj/vm2/LuaNumber.html (68623, 2018-06-08)
docs/api/org/luaj/vm2/LuaString.html (244403, 2018-06-08)
docs/api/org/luaj/vm2/LuaTable.html (110506, 2018-06-08)
docs/api/org/luaj/vm2/LuaThread.State.html (16439, 2018-06-08)
docs/api/org/luaj/vm2/LuaThread.html (66009, 2018-06-08)
... ...
![LuaJ](https://raw.githubusercontent.com/Tidal-Loop/LuaJ/master/icon.gif)
#LuaJ
* * *
#Getting Started with LuaJ.
James Roseborough, Ian Farmer, Version 3.0
Copyright 2009-2014 Luaj.org. (Also Nathan, Marcus, and Pratik for the crazy hack job with the chainsaw that makes it make it through proguard on Android without warnings.) Freely available under the terms of the [Luaj license](http://sourceforge.net/dbimage.php?id=196142).
* * *
[introduction](#1) · [examples](#2) · [concepts](#3) · [libraries](#4) · [luaj api](#5) · [parser](#6) · [building](#7) · [downloads](#8) · [release notes](#9)
# 1 -
Introduction
## Goals of Luaj
Luaj is a lua interpreter based on the 5.2.x version of lua with the following goals in mind:
* Java-centric implementation of lua vm built to leverage standard Java features.
* Lightweight, high performance execution of lua.
* Multi-platform to be able to run on JME, JSE, or JEE environments.
* Complete set of libraries and tools for integration into real-world projects.
* Dependable due to sufficient unit testing of vm and library features.
## Luaj version and Lua Versions
### Luaj 3.0.x
Support for lua 5.2.x features:
* _ENV environments model.
* yield from pcall or metatags.
* Bitwise operator library.
It also includes miscellaneous improvements over luaj 2.0.x:
* Better thread safety.
* More compatible table behavior.
* Better coroutine-related garbage collection.
* Maven integration.
* Better debug reporting when using closures.
* Line numbers in parse syntax tree.
### Luaj 2.0.x
Support for lua 5.1.x features, plus:
* Support for compiling lua source code into Java source code.
* Support for compiling lua bytecode directly into Java bytecode.
* Stackless vm design centered around dynamically typed objects.
* Good alignment with C API (see [names.csv](names.csv) for details)
* Implementation of weak keys and values, and all metatags.
### Luaj 1.0.x
Support for most lua 5.1.x features.
## Performance
Good performance is a major goal of luaj. The following table provides measured execution times on a subset of benchmarks from [the computer language benchmarks game](http://shootout.alioth.debian.org/) in comparison with the standard C distribution.
| Project | Version | Mode | Benchmark execution time (sec) | | | | Language | Sample Command |
|----------|---------|------------------|--------------------------------|---------------|-------------|----------|----------|-----------------------------------------------------------------|
| | | | binarytrees (15) | fannkuch (10) | nbody (1e6) | nsieve 9 | | |
| luaj | 3.0 | -b (luajc) | 2.980 | 5.073 | 16.794 | 11.274 | Java | java -cp luaj-jse-3.0.1.jar;bcel-5.2.jar lua -b fannkuch.lua 10 |
| | | -n (interpreted) | 12.838 | 23.290 | 36.894 | 15.163 | | java -cp luaj-jse-3.0.1.jar lua -n fannkuch.lua 10 |
| lua | 5.1.4 | | 17.637 | 16.044 | 15.201 | 5.477 | C | lua fannkuch.lua 10 |
| jill | 1.0.1 | | 44.512 | 54.630 | 72.172 | 20.779 | Java | |
| kahlua | 1.0 | jse | 22.963 | 63.277 | 68.223 | 21.529 | Java | |
| mochalua | 1.0 | | 50.457 | 70.368 | 82.868 | 41.262 | Java | |
Luaj in interpreted mode performs well for the benchmarks, and even better when the lua-to-java-bytecode (luajc) compiler is used, and actually executes _faster_ than C-based lua in some cases. It is also faster than Java-lua implementations Jill, Kahlua, and Mochalua for all benchmarks tested.
# 2 -
Examples
## Run a lua script in Java SE
From the main distribution directory line type:
java -cp lib/luaj-jse-3.0.jar lua examples/lua/hello.lua
You should see the following output:
hello, world
To see how luaj can be used to acccess most Java API's including swing, try:
java -cp lib/luaj-jse-3.0.jar lua examples/lua/swingapp.lua
Links to sources: [examples/lua/hello.lua](examples/lua/hello.lua) [examples/lua/swingapp.lua](examples/lua/swingapp.lua)
## Compile lua source to lua bytecode
From the main distribution directory line type:
java -cp lib/luaj-jse-3.0.jar luac examples/lua/hello.lua
java -cp lib/luaj-jse-3.0.jar lua luac.out
The compiled output "luac.out" is lua bytecode and should run and produce the same result.
## Compile lua source or bytecode to java bytecode
Luaj can compile lua sources or binaries directly to java bytecode if the bcel library is on the class path. From the main distribution directory line type:
ant bcel-lib
java -cp "lib/luaj-jse-3.0.jar;lib/bcel-5.2.jar" luajc -s examples/lua -d . hello.lua
java -cp "lib/luaj-jse-3.0.jar;." lua -l hello
The output _hello.class_ is Java bytecode, should run and produce the same result. There is no runtime dependency on the bcel library, but the compiled classes must be in the class path at runtime, unless runtime jit-compiling via luajc and bcel are desired (see later sections).
Lua scripts can also be run directly in this mode without precompiling using the _lua_ command with the **_-b_** option and providing the _bcel_ library in the class path:
java -cp "lib/luaj-jse-3.0.jar;lib/bcel-5.2.jar" lua -b examples/lua/hello.lua
## Run a script in a Java Application
A simple hello, world example in luaj is:
```java
import org.luaj.vm2.*;
import org.luaj.vm2.lib.jse.*;
Globals globals = JsePlatform.standardGlobals();
LuaValue chunk = globals.load("print 'hello, world'");
chunk.call();
```
Loading from a file is done via Globals.loadFile():
```java
LuaValue chunk = globals.loadfile("examples/lua/hello.lua");
```
Chunks can also be loaded from a `Reader` as text source
```java
chunk = globals.load(new StringReader("print 'hello, world'"), "main.lua");
```
or an InputStream to be loaded as text source "t", or binary lua file "b":
chunk = globals.load(new FileInputSStream("examples/lua/hello.lua"), "main.lua", "bt"));
A simple example may be found in [examples/jse/SampleJseMain.java](examples/jse/SampleJseMain.java)
You must include the library **lib/luaj-jse-3.0.jar** in your class path.
## Run a script in a MIDlet
For MIDlets the _JmePlatform_ is used instead:
```java
import org.luaj.vm2.*;
import org.luaj.vm2.lib.jme.*;
Globals globals = JmePlatform.standardGlobals();
LuaValue chunk = globals.loadfile("examples/lua/hello.lua");
chunk.call();
```
The file must be a resource within within the midlet jar for the loader to find it. Any files included via _require()_ must also be part of the midlet resources.
A simple example may be found in [examples/jme/SampleMIDlet.java](examples/jme/SampleMIDlet.java)
You must include the library **lib/luaj-jme-3.0.jar** in your midlet jar.
An ant script to build and run the midlet is in [build-midlet.xml](build-midlet.xml)
You must install the wireless toolkit and define _WTK_HOME_ for this script to work.
## Run a script using JSR-223 Dynamic Scripting
The standard use of JSR-223 scripting engines may be used:
```java
ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine e = mgr.getEngineByName("luaj");
e.put("x", 25);
e.eval("y = math.sqrt(x)");
System.out.println( "y="+e.get("y") );
```
You can also look up the engine by language "lua" or mimetypes "text/lua" or "application/lua".
All standard aspects of script engines including compiled statements are supported.
You must include the library **lib/luaj-jse-3.0.jar** in your class path.
A working example may be found in [examples/jse/ScriptEngineSample.java](examples/jse/ScriptEngineSample.java)
To compile and run it using Java 1.6 or higher:
javac -cp lib/luaj-jse-3.0.jar examples/jse/ScriptEngineSample.java
java -cp "lib/luaj-jse-3.0.jar;examples/jse" ScriptEngineSample
## Excluding the lua bytecode compiler
By default, the compiler is included whenever _standardGlobals()_ or _debugGlobals()_ are called. Without a compiler, files can still be executed, but they must be compiled elsewhere beforehand. The "luac" utility is provided in the jse jar for this purpose, or a standard lua compiler can be used.
To exclude the lua-to-lua-bytecode compiler, do not call _standardGlobals()_ or _debugGlobals()_ but instead initialize globals with including only those libraries that are needed and omitting the line:
org.luaj.vm2.compiler.LuaC.install(globals);
## Including the LuaJC lua-bytecode-to-Java-bytecode compiler
To compile from lua to Java bytecode for all lua loaded at runtime, install the LuaJC compiler into a _globals_ object use:
org.luaj.vm2.jse.luajc.LuaJC.install(globals);
This will compile all lua bytecode into Java bytecode, regardless of if they are loaded as lua source or lua binary files.
The requires _bcel_ to be on the class path, and the ClassLoader of JSE or CDC.
# 3 -
Concepts
## Globals
The old notion of platform has been replaced with creation of globals. The [Globals](http://luaj.sourceforge.net/api/3.0/org/luaj/vm2/Globals.html) class holds global state needed for executing closures as well as providing convenience functions for compiling and loading scripts.
## Platform
To simplify construction of Globals, and encapsulate differences needed to support the diverse family of Java runtimes, luaj uses a Platform notion. Typically, a platform is used to construct a Globals, which is then provided as a global environment for client scripts.
### JsePlatform
The [JsePlatform](http://luaj.sourceforge.net/api/3.0/org/luaj/vm2/lib/jse/JsePlatform.html) class can be used as a factory for globals in a typical Java SE application. All standard libraries are included, as well as the luajava library. The default search path is the current directory, and the math operations include all those supported by Java SE.
#### Android
Android applications should use the JsePlatform, and can include the [Luajava](#luajava) library to simplify access to underlying Android APIs. A specialized Globals.finder should be provided to find scripts and data for loading. See [examples/android/src/android/LuajView](https://github.com/Tidal-Loop/LuaJ/blob/master/examples/android/src/android/LuajView.java) for an example that loads from the "res" Android project directory. The ant build script is [examples/android/build.xml](examples/android/build.xml).
#### Applet
Applets in browsers should use the JsePlatform. The permissions model in applets is highly restrictive, so a specialization of the [Luajava](#luajava) library must be used that uses default class loading. This is illustrated in the sample Applet [examples/jse/SampleApplet.java](examples/jse/SampleApplet.java), which can be built using [build-applet.xml](build-applet.xml).
### JmePlatform
The [JmePlatform](http://luaj.sourceforge.net/api/3.0/org/luaj/vm2/lib/jme/JmePlatform.html) class can be used to set up the basic environment for a Java ME application. The default search path is limited to the jar resources, and the math operations are limited to those supported by Java ME. All libraries are included except luajava, and the os, io, and math libraries are limited to those functions that can be supported on that platform.
#### MIDlet
MIDlets require the JmePlatform. The JME platform has several limitations which carry over to luaj. In particular Globals.finder is overridden to load as resources, so scripts should be colocated with class files in the MIDlet jar file. [Luajava](#luajava) cannot be used. Camples code is in [examples/jme/SampleMIDlet.java](examples/jme/SampleMIDlet.java), which can be built using [build-midlet.xml](build-midlet.xml).
## Thread Safety
Luaj 3.0 can be run in multiple threads, with the following restrictions:
* Each thread created by client code must be given its own, distinct Globals instance
* Each thread must not be allowed to access Globals from other threads
* Metatables for Number, String, Thread, Function, Boolean, and and Nil are shared and therefore should not be mutated once lua code is running in any thread.
For an example of loading allocating per-thread Globals and invoking scripts in multiple threads see [examples/jse/SampleMultiThreaded.java](examples/jse/SampleMultiThreaded.java)
As an alternative, the JSR-223 scripting interface can be used, and should always provide a separate Globals instance per script engine instance by using a ThreadLocal internally.
# 4 -
Libraries
## Standard Libraries
Libraries are coded to closely match the behavior specified in See [standard lua documentation](http://www.lua.org/manual/5.1/) for details on the library API's
The following libraries are loaded by both _JsePlatform.standardGlobals()_ and _JmePlatform.standardGlobals()_:
base
bit32
coroutine
io
math
os
package
string
table
The _JsePlatform.standardGlobals()_ globals also include:
luajava
The _JsePlatform.debugGlobals()_ and _JsePlatform.debugGlobals()_ functions produce globals that include:
debug
### I/O Library
The implementation of the _io_ library differs by platform owing to platform limitations.
The _JmePlatform.standardGlobals()_ instantiated the io library _io_ in
src/jme/org/luaj/vm2/lib/jme/JmeIoLib.java
The _JsePlatform.standardGlobals()_ includes support for random access and is in
src/jse/org/luaj/vm2/lib/jse/JseIoLib.java
### OS Library
The implementation of the _os_ library also differs per platform.
The basic _os_ library implementation us used by _JmePlatform_ and is in:
src/core/org/luaj/lib/OsLib.java
A richer version for use by _JsePlatform_ is :
src/jse/org/luaj/vm2/lib/jse/JseOsLib.java
Time is a represented as number of seconds since the epoch, and locales are not implemented.
### Coroutine Library
The _coroutine_ library is implemented using one JavaThread per coroutine. This allows _coroutine.yield()_ can be called from anywhere, as with the yield-from-anywhere patch in C-based lua.
Luaj uses WeakReferences and the OrphanedThread error to ensure that coroutines that are no longer referenced are properly garbage collected. For thread safety, OrphanedThread should not be caught by Java code. See [LuaThread](http://luaj.sourceforge.net/api/3.0/org/luaj/vm2/LuaThread.html) and [OrphanedThread](http://luaj.sourceforge.net/api/3.0/org/luaj/vm2/OrphanedThread.html) javadoc for details.
### Debug Library
The _debug_ library is not included by default by _JmePlatform.standardGlobals()_ or _JsePlatform.standardGlobsls()_ . The functions _JmePlatform.debugGlobals()_ and _JsePlatform.debugGlobsls()_ create globals that contain the debug library in addition to the other standard libraries. To install dynamically from lua use java-class-based require::
```lua
require 'org.luaj.vm2.lib.DebugLib'
```
The _lua_ command line utility includes the _debug_ library by default.
###
The Luajava Library
The _JsePlatform.standardGlobals()_ includes the _luajava_ library, which simplifies binding to Java classes and methods. It is patterned after the original [luajava project](http://www.keplerproject.org/luajava/).
The following lua script will open a swing frame on Java SE:
```lua
jframe = luajava.bindClass( "javax.swing.JFrame" )
frame = luajava.newInstance( "javax.swing.JFrame", "Texts" );
frame:setDefaultCloseOperation(jframe.EXIT_ON_CLOSE)
frame:setSize(300,400)
frame:setVisible(true)
```
See a longer sample in _examples/lua/swingapp.lua_ for details, including a simple animation loop, rendering graphics, mouse and key handling, and image loading. Or try running it using:
java -cp lib/luaj-jse-3.0.jar lua examples/lua/swingapp.lua
The Java ME platform does not include this library, and it cannot be made to work because of the lack of a reflection API in Java ME.
The _lua_ connand line tool includes _luajava_.
# 5 -
LuaJ API
## API Javadoc
The javadoc for the main classes in the LuaJ API are on line at [docs/api](docs/api/index.html)
You can also build a local version from sources using
ant doc
## LuaValue and Varargs
All lua value manipulation is now organized around [LuaValue](docs/api/org/luaj/vm2/LuaValue.html) which exposes the majority of interfaces used for lua computation. [org.luaj.vm2.LuaValue](docs/api/org/luaj/vm2/LuaValue.html)
### Common Functions
_LuaValue_ exposes functions for each of the operations in LuaJ. Some commonly used functions and constants include:
```java
call(); // invoke the function with no arguments
call(LuaValue arg1); // call the function with 1 argument
invoke(Varargs arg); // call the function with variable arguments, variable return values
get(int index); // get a table entry using an integer key
get(LuaValue key); // get a table entry using an arbitrary key, may be a LuaInteger
rawget(int index); // raw get without metatable calls
valueOf(int i); // return LuaValue corresponding to an integer
valueOf(String s); // return LuaValue corresponding to a String
toint(); // return value as a Java int
tojstring(); // return value as a Java String
isnil(); // is the value nil
NIL; // the value nil
NONE; // a Varargs instance with no values
```
## Varargs
The interface [Varargs](http://luaj.sourceforge.net/api/3.0/org/luaj/vm2/Varargs.html) provides an abstraction for both a variable argument list and multiple return values. For convenience, _LuaValue_ implements _Varargs_ so a single value can be supplied anywhere variable arguments are expected. [org.luaj.vm2.Varargs](http://luaj.sourceforge.net/api/3.0/org/luaj/vm2/Varargs.html)
### Common Functions
_Varargs_ exposes functions for accessing elements, and coercing them to specific types:
```java
narg(); // return number of arguments
arg1(); // return the first argument
arg(int n); // return the nth argument
isnil(int n); // true if the nth argument is nil
checktable(int n); // return table or throw error
optlong(int n,long d); // return n if a long, d if no argument, or error if not a long
```
See the [Varargs](docs/api/org/luaj/vm2/Varargs.html) API for a complete list.
## LibFunction
The simplest way to implement a function is to choose a base class based on the number of arguments to the function. LuaJ provides 5 base classes for this purpose, depending if the function has 0, 1, 2, 3 or variable arguments, and if it provide multiple return values. [org.luaj.vm2.lib.ZeroArgFunction](docs/api/org/luaj/vm2/lib/ZeroArgFunction.html), [org.luaj. ... ...