このページの内容

4.6 – 関数と型

ここではC APIのすべての関数と型をアルファベット順に列挙します。各関数には次のような指示子があります:[-o, +p, x]

第1フィールドoは関数がスタックからポップする要素数です。第2フィールドpは関数がスタックへプッシュする要素数です。(すべての関数は必ず、引数をポップした後に結果をプッシュします。)x|y形式のフィールドは、状況に応じて関数がx個またはy個の要素をプッシュ(またはポップ)できることを意味します。疑問符’?’は、引数だけを見ても関数がポップまたはプッシュする要素数を判断できないことを意味します。(たとえば、スタック内の内容に依存する場合があります。)第3フィールドxは、関数がエラーを発生させる可能性があるかを示します。‘-’は関数がエラーを決して発生させない、‘m’はメモリ不足エラーだけを発生させる可能性がある、‘v’は本文で説明されたエラーを発生させる可能性がある、‘e’は関数が直接またはメタメソッドを通じて任意のLuaコードを実行でき、そのため任意のエラーを発生させる可能性があることを意味します。


lua_absindex

[-0, +0, –]

int lua_absindex (lua_State *L, int idx);

許容されるインデックスidxを、等価な絶対インデックス(つまりスタックサイズに依存しないインデックス)へ変換します。


lua_Alloc

typedef void * (*lua_Alloc) (void *ud,
                             void *ptr,
                             size_t osize,
                             size_t nsize);

Luaステートが使うメモリアロケーター関数の型です。アロケーター関数はreallocに似た機能を提供しなければなりませんが、まったく同じではありません。引数は、lua_newstateへ渡された不透明ポインターud、割り当て、再割り当て、解放されるブロックへのポインターptr、ブロックの元のサイズまたは割り当てるものに関する符号osize、ブロックの新しいサイズnsizeです。

ptrNULLでない場合、osizeptrが指すブロックのサイズ、つまり割り当てまたは再割り当て時に指定されたサイズです。

ptrNULLの場合、osizeはLuaが割り当てるオブジェクトの種類を符号化します。Luaがその型の新しいオブジェクトを作成するとき(かつ、そのときだけ)、osizeLUA_TSTRINGLUA_TTABLELUA_TFUNCTIONLUA_TUSERDATALUA_TTHREADのいずれかです。osizeがそのほかの値なら、Luaは別のもののメモリを割り当てています。

Luaはアロケーター関数に次の動作を仮定します。

nsizeが0なら、アロケーターはfreeのように動作し、その後NULLを返さなければなりません。

nsizeが0でなければ、アロケーターはreallocのように動作しなければなりません。特に、要求を満たせない場合に限りNULLを返します。

次は、補助ライブラリの関数luaL_allocに対応する、アロケーター関数の簡単な実装です。

     void *luaL_alloc (void *ud, void *ptr, size_t osize,
                                            size_t nsize) {
       (void)ud;  (void)osize;  /* not used */
       if (nsize == 0) {
         free(ptr);
         return NULL;
       }
       else
         return realloc(ptr, nsize);
     }

ISO Cはfree(NULL)が何もせず、realloc(NULL,size)malloc(size)と等価であることを保証している点に注意してください。


lua_arith

[-(2|1), +1, e]

void lua_arith (lua_State *L, int op);

スタック最上部の2つの値(否定の場合は1つ)に対して算術演算またはビット演算を実行します。最上部の値を第2オペランドとして値をポップし、演算結果をプッシュします。関数は対応するLua演算子の意味論に従います(つまり、メタメソッドを呼び出す可能性があります)。

opの値は次の定数のいずれかでなければなりません。

  • LUA_OPADD:加算(+)を実行します。
  • LUA_OPSUB:減算(-)を実行します。
  • LUA_OPMUL:乗算(*)を実行します。
  • LUA_OPDIV:浮動小数点除算(/)を実行します。
  • LUA_OPIDIV:床除算(//)を実行します。
  • LUA_OPMOD:剰余(%)を実行します。
  • LUA_OPPOW:累乗(^)を実行します。
  • LUA_OPUNM:数学的な否定(単項-)を実行します。
  • LUA_OPBNOT:ビット単位NOT(~)を実行します。
  • LUA_OPBAND:ビット単位AND(&)を実行します。
  • LUA_OPBOR:ビット単位OR(|)を実行します。
  • LUA_OPBXOR:ビット単位排他的OR(~)を実行します。
  • LUA_OPSHL:左シフト(<<)を実行します。
  • LUA_OPSHR:右シフト(>>)を実行します。

lua_atpanic

[-0, +0, –]

lua_CFunction lua_atpanic (lua_State *L, lua_CFunction panicf);

新しいパニック関数を設定し、以前の関数を返します(§4.4を参照)。


lua_call

[-(nargs+1), +nresults, e]

void lua_call (lua_State *L, int nargs, int nresults);

関数を呼び出します。通常のLua呼び出しと同様、lua_call__callメタメソッドに従います。そのため、ここで「関数」は任意の呼び出し可能な値を意味します。

呼び出しを行うには次のプロトコルを使う必要があります。まず、呼び出す関数をスタックへプッシュします。次に、呼び出しへの引数を正順、つまり第1引数を最初としてプッシュします。最後にlua_callを呼び出します。nargsはスタックへプッシュした引数の数です。関数が返ると、すべての引数と関数値がポップされ、呼び出しの結果がスタックへプッシュされます。nresultsLUA_MULTRETでない限り、結果数はnresultsへ調整されます。その定数を指定した場合、関数のすべての結果をプッシュします。前者のように結果数を明示する場合、呼び出し元は戻り値を置く領域がスタックにあることを保証する必要があります。後者のようにすべての結果を取得する場合、Luaは戻り値がスタック領域に収まるようにしますが、スタック内の追加領域は保証しません。関数の結果は正順(最初の結果を最初)でスタックへプッシュされるため、呼び出し後は最後の結果がスタック最上部にあります。

nresultsの最大値は250です。

関数の呼び出し・実行中のすべてのエラーは(longjmpによって)上へ伝播します。

次の例は、ホストプログラムが次のLuaコードと等価な操作を行う方法を示します。

     a = f("how", t.x, 14)

Cでは次のようになります。

     lua_getglobal(L, "f");                  /* function to be called */
     lua_pushliteral(L, "how");                       /* 1st argument */
     lua_getglobal(L, "t");                    /* table to be indexed */
     lua_getfield(L, -1, "x");        /* push result of t.x (2nd arg) */
     lua_remove(L, -2);                  /* remove 't' from the stack */
     lua_pushinteger(L, 14);                          /* 3rd argument */
     lua_call(L, 3, 1);     /* call 'f' with 3 arguments and 1 result */
     lua_setglobal(L, "a");                         /* set global 'a' */

上のコードが釣り合っていることに注意してください。終了時、スタックは元の構成へ戻っています。これは良いプログラミング慣行とみなされます。


lua_callk

[-(nargs + 1), +nresults, e]

void lua_callk (lua_State *L,
                int nargs,
                int nresults,
                lua_KContext ctx,
                lua_KFunction k);

この関数は、呼び出された関数がyieldすることを許可する点(§4.5を参照)を除き、lua_callとまったく同様に動作します。


lua_CFunction

typedef int (*lua_CFunction) (lua_State *L);

C関数の型です。

Luaと正しく通信するため、C関数は引数と結果の受け渡し方法を定義する次のプロトコルを使う必要があります。C関数はLuaから引数をスタック内の正順(最初の引数を最初にプッシュ)で受け取ります。そのため、関数の開始時、lua_gettop(L)は関数が受け取った引数の数を返します。第1引数(ある場合)はインデックス1、最後の引数はインデックスlua_gettop(L)にあります。Luaへ値を返すには、C関数は正順(最初の結果を最初にプッシュ)でスタックへプッシュし、結果の数をCで返すだけです。結果より下にあるスタック内のそのほかの値はLuaによって適切に破棄されます。Lua関数と同様に、Luaから呼び出されたC関数も複数の結果を返せます。

例として、次の関数は可変数の数値引数を受け取り、その平均と合計を返します。

     static int foo (lua_State *L) {
       int n = lua_gettop(L);    /* number of arguments */
       lua_Number sum = 0.0;
       int i;
       for (i = 1; i <= n; i++) {
         if (!lua_isnumber(L, i)) {
           lua_pushliteral(L, "incorrect argument");
           lua_error(L);
         }
         sum += lua_tonumber(L, i);
       }
       lua_pushnumber(L, sum/n);        /* first result */
       lua_pushnumber(L, sum);         /* second result */
       return 2;                   /* number of results */
     }

lua_checkstack

[-0, +0, –]

int lua_checkstack (lua_State *L, int n);

スタックに少なくともn個の追加要素を置く領域、つまり最大n個の値を安全にプッシュできる領域があることを保証します。スタックが固定の最大サイズ(通常は少なくとも数千要素)を超えるか、追加領域のメモリを割り当てられないために要求を満たせなければ、falseを返します。この関数がスタックを縮小することはありません。スタックに追加要素用の領域がすでにある場合は変更しません。


lua_close

[-0, +0, –]

void lua_close (lua_State *L);

メインスレッドのすべてのアクティブなクローズ対象変数を閉じ、指定されたLuaステートのすべてのオブジェクトを解放し(対応するガベージコレクションのメタメソッドがあれば呼び出します)、このステートが使うすべての動的メモリを解放します。

複数のプラットフォームでは、ホストプログラム終了時にすべてのリソースが自然に解放されるため、この関数を呼び出す必要がない場合があります。一方、デーモンやWebサーバーなど、複数のステートを作成する長時間実行プログラムでは、不要になったステートをすぐに閉じる必要があるでしょう。


lua_closeslot

[-0, +0, e]

void lua_closeslot (lua_State *L, int index);

指定されたインデックスのクローズ対象スロットを閉じ、その値をnilへ設定します。このインデックスは、以前にクローズ対象として印を付けられ(lua_tocloseを参照)、まだアクティブ(つまり、まだ閉じていない)な最後のインデックスでなければなりません。

この関数を通じて呼び出された__closeメタメソッドはyieldできません。


lua_closethread

[-0, +?, –]

int lua_closethread (lua_State *L, lua_State *from);

スレッドをリセットし、そのコールスタックを消去して、保留中のすべてのクローズ対象変数を閉じます。引数fromLをリセットしているコルーチンを表します。そのようなコルーチンがなければ、この引数をNULLにできます。

Lfromが等しくない限り、呼び出しはステータスコードを返します。スレッド内にエラー(スレッドを停止させた元のエラー、またはクローズメソッド内のエラー)がなければLUA_OK、それ以外ならエラーステータスです。エラーの場合、エラーオブジェクトをスタック最上部へ置きます。

Lfromが等しい場合は、スレッドが自身を閉じることに相当します。この場合、呼び出しは返りません。代わりに、そのスレッドを(再)開始したresumeが返ります。スレッドはresume内で実行中でなければなりません。


lua_compare

[-0, +0, e]

int lua_compare (lua_State *L, int index1, int index2, int op);

2つのLua値を比較します。対応するLua演算子の意味論(つまり、メタメソッドを呼び出す可能性があります)に従って、インデックスindex1の値をインデックスindex2の値と比較したときにopを満たすなら1を返します。それ以外の場合は0を返します。いずれかのインデックスが有効でない場合も0を返します。

opの値は次の定数のいずれかでなければなりません。

  • LUA_OPEQ:等しいか(==)を比較します。
  • LUA_OPLT:より小さいか(<)を比較します。
  • LUA_OPLE:以下か(<=)を比較します。