mirror of
https://github.com/SquidDev-CC/CC-Tweaked
synced 2024-08-19 14:16:14 +00:00
781 lines
26 KiB
HTML
781 lines
26 KiB
HTML
![]() |
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
|
||
|
<html>
|
||
|
|
||
|
<head>
|
||
|
<title>Getting Started with LuaJ</title>
|
||
|
<link rel="stylesheet" type="text/css" href="http://www.lua.org/lua.css">
|
||
|
<META HTTP-EQUIV="content-type" CONTENT="text/html; charset=iso-8859-1">
|
||
|
</head>
|
||
|
|
||
|
<body>
|
||
|
|
||
|
<hr>
|
||
|
<h1>
|
||
|
<a href="README.html"><img src="http://sourceforge.net/dbimage.php?id=196139" alt="" border="0"></a>
|
||
|
|
||
|
Getting Started with LuaJ
|
||
|
|
||
|
</h1>
|
||
|
James Roseborough, Ian Farmer, Version 2.0.3
|
||
|
<p>
|
||
|
<small>
|
||
|
Copyright © 2009-2012 Luaj.org.
|
||
|
Freely available under the terms of the
|
||
|
<a href="http://sourceforge.net/dbimage.php?id=196142">Luaj license</a>.
|
||
|
</small>
|
||
|
<hr>
|
||
|
<p>
|
||
|
|
||
|
<a href="#1">introduction</a>
|
||
|
·
|
||
|
<a href="#2">examples</a>
|
||
|
·
|
||
|
<a href="#3">concepts</a>
|
||
|
·
|
||
|
<a href="#4">libraries</a>
|
||
|
·
|
||
|
<a href="#5">luaj api</a>
|
||
|
·
|
||
|
<a href="#6">parser</a>
|
||
|
·
|
||
|
<a href="#7">building</a>
|
||
|
·
|
||
|
<a href="#8">downloads</a>
|
||
|
·
|
||
|
<a href="#9">release notes</a>
|
||
|
|
||
|
<!-- ====================================================================== -->
|
||
|
<p>
|
||
|
|
||
|
<h1>1 - <a name="1">Introduction</a></h1>
|
||
|
<h2>Goals of Luaj</h2>
|
||
|
Luaj is a lua interpreter based on the 5.1.x version of lua with the following goals in mind:
|
||
|
<ul>
|
||
|
<li>Java-centric implementation of lua vm built to leverage standard Java features.
|
||
|
<li>Lightweight, high performance execution of lua.
|
||
|
<li>Multi-platform to be able to run on JME, JSE, or JEE environments.
|
||
|
<li>Complete set of libraries and tools for integration into real-world projects.
|
||
|
<li>Dependable due to sufficient unit testing of vm and library features.
|
||
|
</ul>
|
||
|
|
||
|
<h2>Differences with 1.0</h2>
|
||
|
In addition to the basic goals of luaj, version 2.0 is aimed
|
||
|
at improving on the 1.0 vm in the following aspects.
|
||
|
<ul>
|
||
|
<li>Support for compiling lua source code into Java source code.
|
||
|
<li>Support for compiling lua bytecode directly into Java bytecode.
|
||
|
<li>Improved performance of of lua bytecode processing.
|
||
|
<li>Stackless vm design centered around dynamically typed objects.
|
||
|
<li>More alignment with C API (see <a href="names.csv">names.csv</a> for details)
|
||
|
<li>Improved class and package naming conventions.
|
||
|
<li>Improved unit tests of core classes.
|
||
|
<li>Improved quality due to major redesign and rewrite of core elements.
|
||
|
<li>More complete implementation including weak keys and values, and all metatags.
|
||
|
</ul>
|
||
|
|
||
|
<h2>Performance</h2>
|
||
|
Good performance is a major goal of luaj.
|
||
|
The following table provides measured execution times on a subset of benchmarks from
|
||
|
<a href="http://shootout.alioth.debian.org/">the computer language benchmarks game</a>
|
||
|
in comparison with the standard C distribution.
|
||
|
<table cellspacing="10"><tr><td><table>
|
||
|
<tr valign="top">
|
||
|
<td><u>Project</td>
|
||
|
<td><u>Version</td>
|
||
|
<td><u>Mode</td>
|
||
|
<td rowspan="9"> </td>
|
||
|
<td colspan="4" align="center"><u>Benchmark execution time (sec)</td>
|
||
|
<td rowspan="9"> </td>
|
||
|
<td><u>Language</td>
|
||
|
<td><u>Sample command</td>
|
||
|
</tr>
|
||
|
<tr valign="top">
|
||
|
<td colspan="2"></td>
|
||
|
<td></td>
|
||
|
<td><em>binarytrees 15</em></td>
|
||
|
<td><em>fannkuch 10</em></td>
|
||
|
<td><em>nbody 1e6</em></td>
|
||
|
<td><em>nsieve 9</em></td>
|
||
|
</tr>
|
||
|
<tr valign="top">
|
||
|
<td>luaj</td>
|
||
|
<td>2.0</td>
|
||
|
<td>-b (luajc)</td>
|
||
|
<td>2.980</td>
|
||
|
<td>5.073</td>
|
||
|
<td>16.794</td>
|
||
|
<td>11.274</td>
|
||
|
<td>Java</td>
|
||
|
<td>java -cp luaj-jse-2.0.3.jar;bcel-5.2.jar lua <b>-b</b> fannkuch.lua 10</td></tr>
|
||
|
<tr valign="top">
|
||
|
<td></td>
|
||
|
<td></td>
|
||
|
<td>-j (lua2java)</td>
|
||
|
<td>4.463</td>
|
||
|
<td>5.884</td>
|
||
|
<td>16.701</td>
|
||
|
<td>13.789</td>
|
||
|
<td></td>
|
||
|
<td>java -cp luaj-jse-2.0.3.jar lua <b>-j</b> fannkuch.lua 10</td></tr>
|
||
|
<tr valign="top">
|
||
|
<td></td>
|
||
|
<td></td>
|
||
|
<td>-n (interpreted)</td>
|
||
|
<td>12.838</td>
|
||
|
<td>23.290</td>
|
||
|
<td>36.894</td>
|
||
|
<td>15.163</td>
|
||
|
<td></td>
|
||
|
<td>java -cp luaj-jse-2.0.3.jar lua -n fannkuch.lua 10</td></tr>
|
||
|
<tr valign="top">
|
||
|
<td>lua</td>
|
||
|
<td>5.1.4</td>
|
||
|
<td></td>
|
||
|
<td>17.637</td>
|
||
|
<td>16.044</td>
|
||
|
<td>15.201</td>
|
||
|
<td>5.477</td>
|
||
|
<td>C</td>
|
||
|
<td>lua fannkuch.lua 10</td></tr>
|
||
|
<tr valign="top">
|
||
|
<td>jill</td>
|
||
|
<td>1.0.1</td>
|
||
|
<td></td>
|
||
|
<td>44.512</td>
|
||
|
<td>54.630</td>
|
||
|
<td>72.172</td>
|
||
|
<td>20.779</td>
|
||
|
<td>Java</td>
|
||
|
<td></td></tr>
|
||
|
<tr valign="top">
|
||
|
<td>kahlua</td>
|
||
|
<td>1.0</td>
|
||
|
<td>jse</td>
|
||
|
<td>22.963</td>
|
||
|
<td>63.277</td>
|
||
|
<td>68.223</td>
|
||
|
<td>21.529</td>
|
||
|
<td>Java</td>
|
||
|
<td></td></tr>
|
||
|
<tr valign="top">
|
||
|
<td>mochalua</td>
|
||
|
<td>1.0</td>
|
||
|
<td></td>
|
||
|
<td>50.457</td>
|
||
|
<td>70.368</td>
|
||
|
<td>82.868</td>
|
||
|
<td>41.262</td>
|
||
|
<td>Java</td>
|
||
|
<td></td></tr>
|
||
|
</table></td></tr></table>
|
||
|
|
||
|
Luaj in interpreted mode performs well for the benchmarks, and even better when source-to-source (lua2java)
|
||
|
or bytecode-to-bytecode (luajc) compilers are used,
|
||
|
and actually executes <em>faster</em> than C-based lua in some cases.
|
||
|
It is also faster than Java-lua implementations Jill, Kahlua, and Mochalua for all benchmarks tested.
|
||
|
|
||
|
<h1>2 - <a name="2">Simple Examples</a></h1>
|
||
|
|
||
|
<h2>Run a lua script in Java SE</h2>
|
||
|
|
||
|
<p>
|
||
|
From the main distribution directory line type:
|
||
|
|
||
|
<pre>
|
||
|
java -cp lib/luaj-jse-2.0.3.jar lua examples/lua/hello.lua
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
You should see the following output:
|
||
|
<pre>
|
||
|
hello, world
|
||
|
</pre>
|
||
|
|
||
|
To see how luaj can be used to acccess most Java API's including swing, try:
|
||
|
|
||
|
<pre>
|
||
|
java -cp lib/luaj-jse-2.0.3.jar lua examples/lua/swingapp.lua
|
||
|
</pre>
|
||
|
|
||
|
<h2>Compile lua source to lua bytecode</h2>
|
||
|
|
||
|
<p>
|
||
|
From the main distribution directory line type:
|
||
|
|
||
|
<pre>
|
||
|
java -cp lib/luaj-jse-2.0.3.jar luac examples/lua/hello.lua
|
||
|
java -cp lib/luaj-jse-2.0.3.jar lua luac.out
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
The compiled output "luac.out" is lua bytecode and should run and produce the same result.
|
||
|
|
||
|
<h2>Compile lua source to java source</h2>
|
||
|
|
||
|
<p>
|
||
|
Luaj can compile to lua source code to Java source code:
|
||
|
|
||
|
<pre>
|
||
|
java -cp lib/luaj-jse-2.0.3.jar lua2java -s examples/lua -d . hello.lua
|
||
|
javac -cp lib/luaj-jse-2.0.3.jar hello.java
|
||
|
java -cp "lib/luaj-jse-2.0.3.jar;." lua -l hello
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
The output <em>hello.java</em> is Java source, that implements the logic in hello.lua directly.
|
||
|
Once <em>hello.java</em> is compiled into <em>hello.class</em> it can be required and used in place of the original lua script, but with better performance.
|
||
|
There are no additional dependencies for compiling or running source-to-source compiled lua.
|
||
|
|
||
|
<p>
|
||
|
Lua scripts can also be run directly in this mode without precompiling using the <em>lua</em> command with the <b><em>-j</em></b> option when run in JDK 1.5 or higher:
|
||
|
<pre>
|
||
|
java -cp lib/luaj-jse-2.0.3.jar lua -j examples/lua/hello.lua
|
||
|
</pre>
|
||
|
|
||
|
<h2>Compile lua bytecode to java bytecode</h2>
|
||
|
|
||
|
<p>
|
||
|
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:
|
||
|
|
||
|
<pre>
|
||
|
ant bcel-lib
|
||
|
java -cp "lib/luaj-jse-2.0.3.jar;lib/bcel-5.2.jar" luajc -s examples/lua -d . hello.lua
|
||
|
java -cp "lib/luaj-jse-2.0.3.jar;." lua -l hello
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
The output <em>hello.class</em> 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).
|
||
|
|
||
|
<p>
|
||
|
Lua scripts can also be run directly in this mode without precompiling using the <em>lua</em> command with the <b><em>-b</em></b> option and providing the <em>bcel</em> library in the class path:
|
||
|
<pre>
|
||
|
java -cp "lib/luaj-jse-2.0.3.jar;lib/bcel-5.2.jar" lua -b examples/lua/hello.lua
|
||
|
</pre>
|
||
|
|
||
|
|
||
|
<h2>Run a script in a Java Application</h2>
|
||
|
|
||
|
<p>
|
||
|
The following pattern is used within Java SE
|
||
|
|
||
|
<pre>
|
||
|
import org.luaj.vm2.*;
|
||
|
import org.luaj.vm2.lib.jse.*;
|
||
|
|
||
|
String script = "examples/lua/hello.lua";
|
||
|
LuaValue _G = JsePlatform.standardGlobals();
|
||
|
_G.get("dofile").call( LuaValue.valueOf(script) );
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
A simple example may be found in
|
||
|
<pre>
|
||
|
examples/jse/SampleJseMain.java
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
You must include the library <b>lib/luaj-jse-2.0.3.jar</b> in your class path.
|
||
|
|
||
|
<h2>Run a script in a MIDlet</h2>
|
||
|
|
||
|
<p>
|
||
|
The for MIDlets the <em>JmePlatform</em> is used instead:
|
||
|
|
||
|
<pre>
|
||
|
import org.luaj.vm2.*;
|
||
|
import org.luaj.vm2.lib.jme.*;
|
||
|
|
||
|
String script = "examples/lua/hello.lua";
|
||
|
LuaValue _G = JmePlatform.standardGlobals();
|
||
|
_G.get("dofile").call( LuaValue.valueOf(script) );
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
The file must be a resource within within the midlet jar for <em>dofile()</em> to find it.
|
||
|
Any files included via <em>require()</em> must also be part of the midlet resources.
|
||
|
|
||
|
<p>
|
||
|
A simple example may be found in
|
||
|
<pre>
|
||
|
examples/jme/SampleMIDlet.java
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
You must include the library <b>lib/luaj-jme-2.0.3.jar</b> in your midlet jar.
|
||
|
|
||
|
<p>
|
||
|
An ant script to build and run the midlet is in
|
||
|
<pre>
|
||
|
build-midlet.xml
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
You must install the wireless toolkit and define <em>WTK_HOME</em> for this script to work.
|
||
|
|
||
|
<h2>Run a script using JSR-223 Dynamic Scripting</h2>
|
||
|
|
||
|
<p>
|
||
|
The standard use of JSR-223 scripting engines may be used:
|
||
|
|
||
|
<pre>
|
||
|
ScriptEngineManager mgr = new ScriptEngineManager();
|
||
|
ScriptEngine e = mgr.getEngineByExtension(".lua");
|
||
|
e.put("x", 25);
|
||
|
e.eval("y = math.sqrt(x)");
|
||
|
System.out.println( "y="+e.get("y") );
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
All standard aspects of script engines including compiled statements should be supported.
|
||
|
|
||
|
<p>
|
||
|
You must include the library <b>lib/luaj-jse-2.0.3.jar</b> in your class path.
|
||
|
|
||
|
<p>
|
||
|
A working example may be found in
|
||
|
<pre>
|
||
|
examples/jse/ScriptEngineSample.java
|
||
|
</pre>
|
||
|
|
||
|
To compile and run it using Java 1.6 or higher:
|
||
|
|
||
|
<pre>
|
||
|
javac examples/jse/ScriptEngineSample.java
|
||
|
java -cp "lib/luaj-jse-2.0.3.jar;examples/jse" ScriptEngineSample
|
||
|
</pre>
|
||
|
|
||
|
<h2>Excluding the lua bytecode compiler</h2>
|
||
|
|
||
|
By default, the compiler is included whenever <em>standardGlobals()</em> or <em>debugGlobals()</em> 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.
|
||
|
|
||
|
<p>
|
||
|
To exclude the lua-to-lua-bytecode compiler, do not call
|
||
|
<em>standardGlobals()</em> or <em>debugGlobals()</em>
|
||
|
but instead initialize globals with including only those libraries
|
||
|
that are needed and omitting the line:
|
||
|
<pre>
|
||
|
org.luaj.vm2.compiler.LuaC.install();
|
||
|
</pre>
|
||
|
|
||
|
|
||
|
<h2>Including the Lua2Java lua-source-to-Java-source compiler</h2>
|
||
|
|
||
|
<p>
|
||
|
To compile from lua sources to Java sources for all lua loaded at runtime,
|
||
|
install the Lua2Java compiler <em>after</em> globals have been created using:
|
||
|
|
||
|
<pre>
|
||
|
org.luaj.vm2.jse.lua2java.Lua2Java.install();
|
||
|
</pre>
|
||
|
|
||
|
This uses the system Java compiler to compile from Java source to Java bytecode,
|
||
|
and cannot compile lua binary files containing lua bytecode at runtime.
|
||
|
|
||
|
<h2>Including the LuaJC lua-bytecode-to-Java-bytecode compiler</h2>
|
||
|
|
||
|
<p>
|
||
|
To compile from lua to Java bytecode for all lua loaded at runtime,
|
||
|
install the LuaJC compiler <em>after</em> globals have been created using:
|
||
|
|
||
|
<pre>
|
||
|
org.luaj.vm2.jse.luajc.LuaJC.install();
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
This will compile all lua bytecode into Java bytecode, regardless of if they are loaded as
|
||
|
lua source or lua binary files.
|
||
|
|
||
|
<p>
|
||
|
The requires <em>bcel</em> to be on the class path, and the ClassLoader of JSE or CDC.
|
||
|
|
||
|
<h1>3 - <a name="3">Concepts</a></h1>
|
||
|
|
||
|
<h2>Globals</h2>
|
||
|
The old notion of platform has been replaced with creation of globals.
|
||
|
Two classes are provided to encapsulate common combinations of libraries.
|
||
|
|
||
|
<h3>JsePlatform</h3>
|
||
|
|
||
|
This 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.
|
||
|
|
||
|
<h3>JmePlatform</h3>
|
||
|
|
||
|
This 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.
|
||
|
|
||
|
|
||
|
<h1>4 - <a name="4">Libraries</a></h1>
|
||
|
|
||
|
<h2>Standard Libraries</h2>
|
||
|
|
||
|
Libraries are coded to closely match the behavior specified in
|
||
|
See <a href="http://www.lua.org/manual/5.1/">standard lua documentation</a> for details on the library API's
|
||
|
|
||
|
<p>
|
||
|
The following libraries are loaded by both <em>JsePlatform.standardGlobals()</em> and <em>JmePlatform.standardGlobals()</em>:
|
||
|
<pre> base
|
||
|
coroutine
|
||
|
io
|
||
|
math
|
||
|
os
|
||
|
package
|
||
|
string
|
||
|
table
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
The <em>JsePlatform.standardGlobals()</em> globals also include:
|
||
|
<pre> luajava
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
The <em>JsePlatform.debugGlobals()</em> and <em>JsePlatform.debugGlobals()</em> functions produce globals that include:
|
||
|
<pre> debug
|
||
|
</pre>
|
||
|
|
||
|
<h3>I/O Library</h3>
|
||
|
The implementation of the <em>io</em> library differs by platform owing to platform limitations.
|
||
|
|
||
|
<p>
|
||
|
The <em>JmePlatform.standardGlobals()</em> instantiated the io library <em>io</em> in
|
||
|
<pre>
|
||
|
src/jme/org/luaj/vm2/lib/jme/JmeIoLib.java
|
||
|
</pre>
|
||
|
|
||
|
The <em>JsePlatform.standardGlobals()</em> includes support for random access and is in
|
||
|
<pre>
|
||
|
src/jse/org/luaj/vm2/lib/jse/JseIoLib.java
|
||
|
</pre>
|
||
|
|
||
|
<h3>OS Library</h3>
|
||
|
The implementation of the <em>os</em> library also differs per platform.
|
||
|
|
||
|
<p>
|
||
|
The basic <em>os</em> library implementation us used by <em>JmePlatform</em> and is in:
|
||
|
<pre>
|
||
|
src/core/org/luaj/lib/OsLib.java
|
||
|
</pre>
|
||
|
|
||
|
A richer version for use by <em>JsePlatform</em> is :
|
||
|
<pre>
|
||
|
src/jse/org/luaj/vm2/lib/jse/JseOsLib.java
|
||
|
</pre>
|
||
|
|
||
|
Time is a represented as number of milliseconds since the epoch,
|
||
|
and most time and date formatting, locales, and other features
|
||
|
are not implemented.
|
||
|
|
||
|
<h3>Coroutine Library</h3>
|
||
|
The <em>coroutine</em> library is implemented using one JavaThread per coroutine.
|
||
|
This allows <em>coroutine.yield()</em> can be called from anywhere,
|
||
|
as with the yield-from-anywhere patch in C-based lua.
|
||
|
|
||
|
<p>
|
||
|
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 <a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/LuaThread.html">LuaThread</a>
|
||
|
and <a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/OrphanedThread.html">OrphanedThread</a>
|
||
|
javadoc for details.
|
||
|
|
||
|
<h3>Debug Library</h3>
|
||
|
The <em>debug</em> library is not included by default by
|
||
|
<em>JmePlatform.standardGlobals()</em> or <em>JsePlatform.standardGlobsls()</em> .
|
||
|
|
||
|
The functions <em>JmePlatform.debugGlobals()</em> and <em>JsePlatform.debugGlobsls()</em>
|
||
|
create globals that contain the debug library in addition to the other standard libraries.
|
||
|
|
||
|
To install dynamically from lua use java-class-based require:</em>:
|
||
|
<pre>
|
||
|
require 'org.luaj.vm2.lib.DebugLib'
|
||
|
</pre>
|
||
|
|
||
|
The <em>lua</em> command line utility includes the <em>debug</em> library by default.
|
||
|
|
||
|
|
||
|
<h3>The Luajava Library</h3>
|
||
|
The <em>JsePlatform.standardGlobals()</em> includes the <em>luajava</em> library, which simplifies binding to Java classes and methods.
|
||
|
It is patterned after the original <a href="http://www.keplerproject.org/luajava/">luajava project</a>.
|
||
|
|
||
|
<p>
|
||
|
The following lua script will open a swing frame on Java SE:
|
||
|
<pre>
|
||
|
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)
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
See a longer sample in <em>examples/lua/swingapp.lua</em> for details, including a simple animation loop, rendering graphics, mouse and key handling, and image loading.
|
||
|
Or try running it using:
|
||
|
<pre>
|
||
|
java -cp lib/luaj-jse-2.0.3.jar lua examples/lua/swingapp.lua
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
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.
|
||
|
|
||
|
<p>
|
||
|
The <em>lua</em> connand line tool includes <em>luajava</em>.
|
||
|
|
||
|
<h1>5 - <a name="5">LuaJ API</a></h1>
|
||
|
|
||
|
<h2>API Javadoc</h2>
|
||
|
The javadoc for the main classes in the LuaJ API are on line at
|
||
|
<pre>
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/index.html">http://luaj.sourceforge.net/api/2.0</a>
|
||
|
</pre>
|
||
|
|
||
|
You can also build a local version from sources using
|
||
|
<pre>
|
||
|
ant doc
|
||
|
</pre>
|
||
|
|
||
|
<h2>LuaValue and Varargs</h2>
|
||
|
All lua value manipulation is now organized around
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/LuaValue.html">LuaValue</a>
|
||
|
which exposes the majority of interfaces used for lua computation.
|
||
|
<pre>
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/LuaValue.html">org.luaj.vm2.LuaValue</a>
|
||
|
</pre>
|
||
|
|
||
|
<h3>Common Functions</h3>
|
||
|
<em>LuaValue</em> exposes functions for each of the operations in LuaJ.
|
||
|
Some commonly used functions and constants include:
|
||
|
<pre>
|
||
|
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
|
||
|
</pre>
|
||
|
|
||
|
<h2>Varargs</h2>
|
||
|
The interface <a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/Varargs.html">Varargs</a> provides an abstraction for
|
||
|
both a variable argument list and multiple return values.
|
||
|
For convenience, <em>LuaValue</em> implements <em>Varargs</em> so a single value can be supplied anywhere
|
||
|
variable arguments are expected.
|
||
|
<pre>
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/Varargs.html">org.luaj.vm2.Varargs</a>
|
||
|
</pre>
|
||
|
|
||
|
<h3>Common Functions</h3>
|
||
|
<em>Varargs</em> exposes functions for accessing elements, and coercing them to specific types:
|
||
|
<pre>
|
||
|
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
|
||
|
</pre>
|
||
|
|
||
|
See the <a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/Varargs.html">Varargs</a> API for a complete list.
|
||
|
|
||
|
<h2>LibFunction</h2>
|
||
|
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.
|
||
|
<pre>
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/lib/ZeroArgFunction.html">org.luaj.vm2.lib.ZeroArgFunction</a>
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/lib/OneArgFunction.html">org.luaj.vm2.lib.OneArgFunction</a>
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/lib/TwoArgFunction.html">org.luaj.vm2.lib.TwoArgFunction</a>
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/lib/ThreeArgFunction.html">org.luaj.vm2.lib.ThreeArgFunction</a>
|
||
|
<a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/lib/VarArgFunction.html">org.luaj.vm2.lib.VarArgFunction</a>
|
||
|
</pre>
|
||
|
|
||
|
Each of these functions has an abstract method that must be implemented,
|
||
|
and argument fixup is done automatically by the classes as each Java function is invoked.
|
||
|
|
||
|
<p>
|
||
|
For example, to implement a "hello, world" function, we could supply:
|
||
|
<pre>
|
||
|
pubic class hello extends ZeroArgFunction {
|
||
|
public LuaValue call() {
|
||
|
env.get("print").call(valueOf("hello, world"));
|
||
|
}
|
||
|
}
|
||
|
</pre>
|
||
|
|
||
|
The value <em>env</em> is the environment of the function, and is normally supplied
|
||
|
by the instantiating object whenever default loading is used.
|
||
|
|
||
|
<p>
|
||
|
Calling this function from lua could be done by:
|
||
|
<pre>
|
||
|
require( 'hello' )()
|
||
|
</pre>
|
||
|
|
||
|
while calling this function from Java would look like:
|
||
|
<pre>
|
||
|
new hello().call();
|
||
|
</pre>
|
||
|
|
||
|
Note that in both the lua and Java case, extra arguments will be ignored, and the function will be called.
|
||
|
Also, no virtual machine instance is necessary to call the function.
|
||
|
To allow for arguments, or return multiple values, extend one of the other base classes.
|
||
|
|
||
|
<h2>Closures</h2>
|
||
|
Closures still exist in this framework, but are optional, and are only used to implement lua bytecode execution.
|
||
|
|
||
|
<h1>6 - <a name="6">Parser</a></h1>
|
||
|
|
||
|
<h2>Javacc Grammar</h2>
|
||
|
A Javacc grammarwas developed to simplify the creation of Java-based parsers for the lua language.
|
||
|
The grammar is specified for <a href="https://javacc.dev.java.net/">javacc version 5.0</a> because that tool generates standalone
|
||
|
parsers that do not require a separate runtime.
|
||
|
|
||
|
<p>
|
||
|
A plain undecorated grammer that can be used for validation is available in <a href="grammar/Lua51.jj">grammar/Lua51.jj</a>
|
||
|
while a grammar that generates a typed parse tree is in <a href="grammar/LuaParser.jj">grammar/LuaParser.jj</a>
|
||
|
|
||
|
<h2>Creating a Parse Tree from Lua Source</h2>
|
||
|
The default lu compiler does a single-pass compile of lua source to lua bytecode, so no explicit parse tree is produced.
|
||
|
|
||
|
<p>
|
||
|
To simplify the creation of abstract syntax trees from lua sources, the LuaParser class is generated as part of the JME build.
|
||
|
To use it, provide an input stream, and invoke the root generator, which will return a Chunk if the file is valid,
|
||
|
or throw a ParseException if there is a syntax error.
|
||
|
|
||
|
<p>
|
||
|
For example, to parse a file and print all variable names, use code like:
|
||
|
<pre>
|
||
|
try {
|
||
|
String file = "main.lua";
|
||
|
LuaParser parser = new LuaParser(new FileInputStream(file));
|
||
|
Chunk chunk = parser.Chunk();
|
||
|
chunk.accept( new Visitor() {
|
||
|
public void visit(Exp.NameExp exp) {
|
||
|
System.out.println("Name in use: "+exp.name.name);
|
||
|
}
|
||
|
} );
|
||
|
} catch ( ParseException e ) {
|
||
|
System.out.println("parse failed: " + e.getMessage() + "\n"
|
||
|
+ "Token Image: '" + e.currentToken.image + "'\n"
|
||
|
+ "Location: " + e.currentToken.beginLine + ":" + e.currentToken.beginColumn
|
||
|
+ "-" + e.currentToken.endLine + "," + e.currentToken.endColumn);
|
||
|
}
|
||
|
</pre>
|
||
|
In luaj 2.0.3 error reporting was turned on in the parser so line numbers are avaiable for most parse exceptions.
|
||
|
This example may be found in
|
||
|
<pre>
|
||
|
examples/jse/SampleParser.java
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
See the <a href="http://luaj.sourceforge.net/api/2.0/org/luaj/vm2/ast/package-summary.html">org.luaj.vm2.ast package</a> javadoc for the API relating to the syntax tree that is produced.
|
||
|
|
||
|
<h1>7 - <a name="7">Building and Testing</a></h1>
|
||
|
|
||
|
<h2>Building the jars</h2>
|
||
|
An ant file is included in the root directory which builds the libraries by default.
|
||
|
|
||
|
<p>
|
||
|
Other targets exist for creating distribution file an measuring code coverage of unit tests.
|
||
|
|
||
|
<h2>Unit tests</h2>
|
||
|
|
||
|
<p>
|
||
|
The main luaj JUnit tests are organized into a JUnit 3 suite:
|
||
|
<pre>
|
||
|
test/junit/org/luaj/vm2/AllTests.lua
|
||
|
</pre>
|
||
|
|
||
|
<p>
|
||
|
Unit test scripts can be found in these locations
|
||
|
<pre>
|
||
|
test/lua/*.lua
|
||
|
test/junit/org/luaj/vm2/compiler/lua5.1-tests.zip
|
||
|
test/junit/org/luaj/vm2/compiler/regressions.zip
|
||
|
test/junit/org/luaj/vm2/vm1/luajvm1-tests.zip
|
||
|
</pre>
|
||
|
|
||
|
<h2>Code coverage</h2>
|
||
|
|
||
|
<p>
|
||
|
A build script for running unit tests and producing code coverage statistics is in
|
||
|
<pre>
|
||
|
build-coverage.xml
|
||
|
</pre>
|
||
|
|
||
|
It relies on the cobertura code coverage library.
|
||
|
|
||
|
<h1>8 - <a name="8">Downloads</a></h1>
|
||
|
|
||
|
<h2>Downloads and Project Pages</h2>
|
||
|
Downloads for all version available on SourceForge or LuaForge.
|
||
|
Sources are hosted on SourceForge and available via sourceforge.net
|
||
|
<br/>
|
||
|
<pre>
|
||
|
<a href="http://luaj.sourceforge.net/">SourceForge Luaj Project Page</a>
|
||
|
<a href="http://sourceforge.net/project/platformdownload.php?group_id=197627">SourceForge Luaj Download Area</a>
|
||
|
</pre>
|
||
|
<p/>
|
||
|
and LuaForge:
|
||
|
<pre>
|
||
|
<a href="http://luaforge.net/projects/luaj/">LuaForge Luaj Project Page</a>
|
||
|
<a href="http://luaforge.net/frs/?group_id=457">LuaForge Luaj Project Area</a>
|
||
|
</pre>
|
||
|
|
||
|
<h1>9 - <a name="9">Release Notes</a></h1>
|
||
|
|
||
|
<h2>Main Changes by Version</h2>
|
||
|
<table cellspacing="10"><tr><td><table cellspacing="4">
|
||
|
<tr valign="top"><td> <b>2.0</b></td><td><ul>
|
||
|
<li>Initial release of 2.0 version </li>
|
||
|
</ul></td></tr>
|
||
|
<tr valign="top"><td> <b>2.0.1</b></td><td><ul>
|
||
|
<li>Improve correctness of singleton construction related to static initialization </li>
|
||
|
<li>Fix nan-related error in constant folding logic that was failing on some JVMs </li>
|
||
|
<li>JSR-223 fixes: add META-INF/services entry in jse jar, improve bindings implementation </li>
|
||
|
</ul></td></tr>
|
||
|
<tr valign="top"><td> <b>2.0.2</b></td><td><ul>
|
||
|
<li>JSR-223 bindings change: non Java-primitives will now be passed as LuaValue </li>
|
||
|
<li>JSR-223 enhancement: allow both ".lua" and "lua" as extensions in getScriptEngine() </li>
|
||
|
<li>JSR-223 fix: use system class loader to support using luaj as JRE extension </li>
|
||
|
<li>Improve selection logic when binding to overloaded functions using luajava</li>
|
||
|
<li>Enhance javadoc, put it <a href="docs/api/index.html">in distribution</a> and <a href="http://luaj.sourceforge.net/api/2.0/index.html">on line</a></li>
|
||
|
<li>Major refactor of luajava type coercion logic, improve method selection.</li>
|
||
|
<li>Add lib/luaj-sources-2.0.2.jar for easier integration into an IDE such as Netbeans </li>
|
||
|
<tr valign="top"><td> <b>2.0.3</b></td><td><ul>
|
||
|
<li>Improve coroutine state logic including let unreferenced coroutines be garbage collected </li>
|
||
|
<li>Fix lua command vararg values passed into main script to match what is in global arg table </li>
|
||
|
<li>Add arithmetic metatag processing when left hand side is a number and right hand side has metatable </li>
|
||
|
<li>Fix load(func) when mutiple string fragments are supplied by calls to func </li>
|
||
|
<li>Allow access to public members of private inner classes where possible </li>
|
||
|
<li>Turn on error reporting in LuaParser so line numbers ar available in ParseException </li>
|
||
|
<li>Improve compatibility of table.remove() </li>
|
||
|
<li>Disallow base library setfenv() calls on Java functions </li>
|
||
|
</ul></td></tr>
|
||
|
</table></td></tr></table>
|
||
|
|
||
|
<h2>Known Issues</h2>
|
||
|
<ul>
|
||
|
<li>debug code may not be completely removed by some obfuscators
|
||
|
<li>tail calls are not tracked in debug information
|
||
|
<li>using both version 1 and 2 libraries together in the same java vm has not been tested
|
||
|
<li>module() and setfenv() only partially supported for lau2java or luajc compiled lua
|
||
|
<li>values associated with weak keys may linger longer than expected
|
||
|
<li>behavior of luaj when a SecurityManager is used has not been fully characterized
|
||
|
</ul>
|
||
|
|