?login_element?

Subversion Repositories NedoOS

Rev

Blame | Last modification | View Log | Download

  1. /*
  2. ** $Id: ldump.c,v 2.37.1.1 2017/04/19 17:20:42 roberto Exp $
  3. ** save precompiled Lua chunks
  4. ** See Copyright Notice in lua.h
  5. */
  6.  
  7. #define ldump_c
  8. #define LUA_CORE
  9.  
  10. #include "lprefix.h"
  11.  
  12.  
  13. #include <stddef.h>
  14.  
  15. #include "lua.h"
  16.  
  17. #include "lobject.h"
  18. #include "lstate.h"
  19. #include "lundump.h"
  20.  
  21.  
  22. typedef struct {
  23.   lua_State *L;
  24.   lua_Writer writer;
  25.   void *data;
  26.   int strip;
  27.   int status;
  28. } DumpState;
  29.  
  30.  
  31. /*
  32. ** All high-level dumps go through DumpVector; you can change it to
  33. ** change the endianness of the result
  34. */
  35. #define DumpVector(v,n,D)       DumpBlock(v,(n)*sizeof((v)[0]),D)
  36.  
  37. #define DumpLiteral(s,D)        DumpBlock(s, sizeof(s) - sizeof(char), D)
  38.  
  39.  
  40. static void DumpBlock (const void *b, size_t size, DumpState *D) {
  41.   if (D->status == 0 && size > 0) {
  42.     lua_unlock(D->L);
  43.     D->status = (*D->writer)(D->L, b, size, D->data);
  44.     lua_lock(D->L);
  45.   }
  46. }
  47.  
  48.  
  49. #define DumpVar(x,D)            DumpVector(&x,1,D)
  50.  
  51.  
  52. static void DumpByte (int y, DumpState *D) {
  53.   lu_byte x = (lu_byte)y;
  54.   DumpVar(x, D);
  55. }
  56.  
  57.  
  58. static void DumpInt (int x, DumpState *D) {
  59.   DumpVar(x, D);
  60. }
  61.  
  62.  
  63. static void DumpNumber (lua_Number x, DumpState *D) {
  64.   DumpVar(x, D);
  65. }
  66.  
  67.  
  68. static void DumpInteger (lua_Integer x, DumpState *D) {
  69.   DumpVar(x, D);
  70. }
  71.  
  72.  
  73. static void DumpString (const TString *s, DumpState *D) {
  74.   if (s == NULL)
  75.     DumpByte(0, D);
  76.   else {
  77.     size_t size = tsslen(s) + 1;  /* include trailing '\0' */
  78.     const char *str = getstr(s);
  79.     if (size < 0xFF)
  80.       DumpByte(cast_int(size), D);
  81.     else {
  82.       DumpByte(0xFF, D);
  83.       DumpVar(size, D);
  84.     }
  85.     DumpVector(str, size - 1, D);  /* no need to save '\0' */
  86.   }
  87. }
  88.  
  89.  
  90. static void DumpCode (const Proto *f, DumpState *D) {
  91.   DumpInt(f->sizecode, D);
  92.   DumpVector(f->code, f->sizecode, D);
  93. }
  94.  
  95.  
  96. static void DumpFunction(const Proto *f, TString *psource, DumpState *D);
  97.  
  98. static void DumpConstants (const Proto *f, DumpState *D) {
  99.   int i;
  100.   int n = f->sizek;
  101.   DumpInt(n, D);
  102.   for (i = 0; i < n; i++) {
  103.     const TValue *o = &f->k[i];
  104.     DumpByte(ttype(o), D);
  105.     switch (ttype(o)) {
  106.     case LUA_TNIL:
  107.       break;
  108.     case LUA_TBOOLEAN:
  109.       DumpByte(bvalue(o), D);
  110.       break;
  111.     case LUA_TNUMFLT:
  112.       DumpNumber(fltvalue(o), D);
  113.       break;
  114.     case LUA_TNUMINT:
  115.       DumpInteger(ivalue(o), D);
  116.       break;
  117.     case LUA_TSHRSTR:
  118.     case LUA_TLNGSTR:
  119.       DumpString(tsvalue(o), D);
  120.       break;
  121.     default:
  122.       lua_assert(0);
  123.     }
  124.   }
  125. }
  126.  
  127.  
  128. static void DumpProtos (const Proto *f, DumpState *D) {
  129.   int i;
  130.   int n = f->sizep;
  131.   DumpInt(n, D);
  132.   for (i = 0; i < n; i++)
  133.     DumpFunction(f->p[i], f->source, D);
  134. }
  135.  
  136.  
  137. static void DumpUpvalues (const Proto *f, DumpState *D) {
  138.   int i, n = f->sizeupvalues;
  139.   DumpInt(n, D);
  140.   for (i = 0; i < n; i++) {
  141.     DumpByte(f->upvalues[i].instack, D);
  142.     DumpByte(f->upvalues[i].idx, D);
  143.   }
  144. }
  145.  
  146.  
  147. static void DumpDebug (const Proto *f, DumpState *D) {
  148.   int i, n;
  149.   n = (D->strip) ? 0 : f->sizelineinfo;
  150.   DumpInt(n, D);
  151.   DumpVector(f->lineinfo, n, D);
  152.   n = (D->strip) ? 0 : f->sizelocvars;
  153.   DumpInt(n, D);
  154.   for (i = 0; i < n; i++) {
  155.     DumpString(f->locvars[i].varname, D);
  156.     DumpInt(f->locvars[i].startpc, D);
  157.     DumpInt(f->locvars[i].endpc, D);
  158.   }
  159.   n = (D->strip) ? 0 : f->sizeupvalues;
  160.   DumpInt(n, D);
  161.   for (i = 0; i < n; i++)
  162.     DumpString(f->upvalues[i].name, D);
  163. }
  164.  
  165.  
  166. static void DumpFunction (const Proto *f, TString *psource, DumpState *D) {
  167.   if (D->strip || f->source == psource)
  168.     DumpString(NULL, D);  /* no debug info or same source as its parent */
  169.   else
  170.     DumpString(f->source, D);
  171.   DumpInt(f->linedefined, D);
  172.   DumpInt(f->lastlinedefined, D);
  173.   DumpByte(f->numparams, D);
  174.   DumpByte(f->is_vararg, D);
  175.   DumpByte(f->maxstacksize, D);
  176.   DumpCode(f, D);
  177.   DumpConstants(f, D);
  178.   DumpUpvalues(f, D);
  179.   DumpProtos(f, D);
  180.   DumpDebug(f, D);
  181. }
  182.  
  183.  
  184. static void DumpHeader (DumpState *D) {
  185.   DumpLiteral(LUA_SIGNATURE, D);
  186.   DumpByte(LUAC_VERSION, D);
  187.   DumpByte(LUAC_FORMAT, D);
  188.   DumpLiteral(LUAC_DATA, D);
  189.   DumpByte(sizeof(int), D);
  190.   DumpByte(sizeof(size_t), D);
  191.   DumpByte(sizeof(Instruction), D);
  192.   DumpByte(sizeof(lua_Integer), D);
  193.   DumpByte(sizeof(lua_Number), D);
  194.   DumpInteger(LUAC_INT, D);
  195.   DumpNumber(LUAC_NUM, D);
  196. }
  197.  
  198.  
  199. /*
  200. ** dump Lua function as precompiled chunk
  201. */
  202. int luaU_dump(lua_State *L, const Proto *f, lua_Writer w, void *data,
  203.               int strip) {
  204.   DumpState D;
  205.   D.L = L;
  206.   D.writer = w;
  207.   D.data = data;
  208.   D.strip = strip;
  209.   D.status = 0;
  210.   DumpHeader(&D);
  211.   DumpByte(f->sizeupvalues, &D);
  212.   DumpFunction(f, NULL, &D);
  213.   return D.status;
  214. }
  215.  
  216.