The Sol Programming Language!
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

sol.h 45KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056
  1. #ifndef SOL_H
  2. #define SOL_H
  3. #ifndef NULL
  4. #define NULL ((void *) 0)
  5. #endif
  6. #include <stdio.h>
  7. #include <stdarg.h>
  8. #include "dsl/dsl.h"
  9. /** The version of the project, as made available through `debug.version`. */
  10. #define VERSION "0.2a2"
  11. /** The hexadecimal version of the project, formatted 0xAAIIRPP where:
  12. *
  13. * - AA is the two-digit major version
  14. * - II is the two-digit minor version
  15. * - R is 'A' for alpha, 'B' for beta, 'C' for candidate, and 'F' for final
  16. * - PP is the two-digit patch
  17. *
  18. * This value is guaranteed to always increase by revision.
  19. */
  20. #define HEXVER 0x0002A02
  21. #ifndef SOL_ICACHE_MIN
  22. /** The smallest integer to cache. */
  23. #define SOL_ICACHE_MIN -128
  24. #endif
  25. #ifndef SOL_ICACHE_MAX
  26. /** The largest integer to cache. */
  27. #define SOL_ICACHE_MAX 256
  28. #endif
  29. #if !defined(SOL_ICACHE) && (SOL_ICACHE_MIN < SOL_ICACHE_MAX)
  30. #define SOL_ICACHE
  31. #endif
  32. // Forward declarations:
  33. struct sol_tag_object_t;
  34. typedef struct sol_tag_object_t sol_object_t;
  35. struct sol_tag_state_t;
  36. typedef struct sol_tag_state_t sol_state_t;
  37. /** CFunction type.
  38. *
  39. * This is the essential type for most C interface routines. It receives two
  40. * parameters:
  41. *
  42. * - The state under which the function is invoked, and
  43. * - A list object containing a set of parameters, which are generally
  44. * well-defined per location or operation.
  45. *
  46. * The function should return a new reference to an object. If the value is
  47. * unimportant or otherwise ignored, the canonical return value is
  48. * `sol_incref`(state->None).
  49. */
  50. typedef sol_object_t *(*sol_cfunc_t)(sol_state_t *, sol_object_t *);
  51. /** Print function type.
  52. *
  53. * \rst
  54. * .. admonition:: Deprecated
  55. *
  56. * This is not used anywhere and is likely to be removed in the
  57. * near future.
  58. * \endrst
  59. */
  60. typedef void (*sol_printfunc_t)(sol_object_t *);
  61. /** Type methods structure.
  62. *
  63. * Sol bases most of its object behavior on methods defined on so-called "ops
  64. * structures" of this type pointed to by the objects themselves. In general,
  65. * these contain the address of one such structure stored directly in the state
  66. * (each state has its own set of these structures for all the builtin types,
  67. * initialized in `sol_state_init`), but they can conceivably be allocated and
  68. * initialized elsewhere, e.g., in extension modules.
  69. *
  70. * Nearly all of the fields in this structure are function pointers to
  71. * `sol_cfunc_t` that are called when an operator is invoked on an object. In
  72. * the case of binary operators, only the left operand is considered.
  73. *
  74. * In member documentation of these functions, the list [in brackets]
  75. * represents, visually, the list that the function can expect to receive as
  76. * the second argument (where "rhs" is right-hand-side of a binary operator,
  77. * and "this" is the object whose ops structure was indexed). Note that the
  78. * runtime does not use nor take advantage of the returns of all of these
  79. * methods.
  80. */
  81. typedef struct {
  82. /** A C-string naming the type, for use by the built-in `type` function. */
  83. char *tname;
  84. /** Called with [this, rhs] to perform binary addition ("+"). */
  85. sol_cfunc_t add;
  86. /** Called with [this, rhs] to perform binary subtraction ("-"). */
  87. sol_cfunc_t sub;
  88. /** Called with [this, rhs] to perform binary multiplication ("*"). */
  89. sol_cfunc_t mul;
  90. /** Called with [this, rhs] to perform binary division ("/"). */
  91. sol_cfunc_t div;
  92. /** Called with [this, rhs] to perform binary modulus ("%"). */
  93. sol_cfunc_t mod;
  94. /** Called with [this, rhs] to perform binary exponentiation ("**"). */
  95. sol_cfunc_t pow;
  96. /** Called with [this, rhs] to perform the triple-bang operation ("!!!"), defaults to identity-swapping two objects. */
  97. sol_cfunc_t tbang;
  98. /** Called with [this, rhs] to perform binary bitwise AND ("&") */
  99. sol_cfunc_t band;
  100. /** Called with [this, rhs] to perform binary bitwise OR ("|") */
  101. sol_cfunc_t bor;
  102. /** Called with [this, rhs] to perform binary bitwise XOR ("^") */
  103. sol_cfunc_t bxor;
  104. /** Called with [this, rhs] to perform binary bitwise left shift ("<<") */
  105. sol_cfunc_t blsh;
  106. /** Called with [this, rhs] to perform binary bitwise right shift (">>") */
  107. sol_cfunc_t brsh;
  108. /** Called with [this] to perform bitwise not ("~") */
  109. sol_cfunc_t bnot;
  110. /** Called with [this, rhs] to perform comparison; the result should be an integer object of value -1 (this < rhs), 0 (this == rhs), or 1 (this > rhs) */
  111. sol_cfunc_t cmp;
  112. /** Called with [this, arg1, arg2, ...] to perform a call (as "this(arg1, arg2, ...)") */
  113. sol_cfunc_t call;
  114. /** Called with [this, index] to perform an index like "this[index]" or "this.index" (in the latter, index will be a string object) */
  115. sol_cfunc_t index;
  116. /** Called with [this, index, value] to perform a setindex (like "this[index] = value" or "this.index = value" for index being a string object) */
  117. sol_cfunc_t setindex;
  118. /** Called with [this] to perform a length predicate (like "#this") */
  119. sol_cfunc_t len;
  120. /** Called with [this] to return a function object (or cfunction object) that will iterate over "this" (see the iterator protocol for more details) */
  121. sol_cfunc_t iter;
  122. /** Called with [this] to cast "this" to an integer object. This may raise an error, which should be checked. */
  123. sol_cfunc_t toint;
  124. /** Called with [this] to cast "this" to a float object. This may raise an error, which should be checked. */
  125. sol_cfunc_t tofloat;
  126. /** Called with [this] to cast "this" to a string object. This generally shouldn't raise an error, and usually falls back to a simple representation. */
  127. sol_cfunc_t tostring;
  128. /** Called with [this] to provide a representation of "this", in the sense that it is human-readable and informative. This usually falls back to tostring. */
  129. sol_cfunc_t repr;
  130. /** Called with this (*not a list*) as a result of calling `sol_init_object`. Since this is usually called from a constructor anyway, it's usually fairly useless. It should return this. */
  131. sol_cfunc_t init;
  132. /** Called with this (*not a list*) and *with a NULL state* before an object is freed; it should free any resources this object exclusively holds, and return this. */
  133. sol_cfunc_t free;
  134. } sol_ops_t;
  135. /** Object types known to Sol.
  136. *
  137. * This is rarely checked and generally only used where necessary, as there is
  138. * no way to extend this list naturally for an extension developer.
  139. *
  140. * For each of these types, there is almost certainly a test macro for it.
  141. */
  142. typedef enum {
  143. /** The singlet type--the type of None, as well as StopIteration and OutOfMemory. It is also the "default" type. */
  144. SOL_SINGLET,
  145. /** The integer type, implemented as a long. */
  146. SOL_INTEGER,
  147. /** The floating point type, implemented as a double. */
  148. SOL_FLOAT,
  149. /** The string type, implemented as a C string. */
  150. SOL_STRING,
  151. /** The list type, implemented as a DSL sequence of object pointers. */
  152. SOL_LIST,
  153. /** The map type, implemented as a DSL sequence of MCELL object pointers arranged as an associative array.. */
  154. SOL_MAP,
  155. /** The mcell type, a simple key-value pair only to be found in a map. */
  156. SOL_MCELL,
  157. /** The function type, the type of all user-defined functions in Sol. */
  158. SOL_FUNCTION,
  159. /** The cfunction type, the type of objects wrapping a `sol_cfunc_t`. */
  160. SOL_CFUNCTION,
  161. /** The statement type, the type of objects wrapping a `stmt_node`. */
  162. SOL_STMT,
  163. /** The expression type, the type of objects wrapping an `expr_node`. */
  164. SOL_EXPR,
  165. /** The buffer type, a type designed to access arbitrary memory. */
  166. SOL_BUFFER,
  167. /** The dylib type, the type of dynamically-loaded shared libraries. */
  168. SOL_DYLIB,
  169. /** The dysym type, the type of symbols resolved in dylib objects. */
  170. SOL_DYSYM,
  171. /** The stream type, the type wrapping FILE *. */
  172. SOL_STREAM,
  173. /** The cdata type, the type used for extension by various modules. */
  174. SOL_CDATA
  175. } sol_objtype_t;
  176. /** Buffer types.
  177. *
  178. * These types indicate what a buffer or subsection of a buffer may refer to.
  179. */
  180. typedef enum {
  181. /** The region is typeless. This is the default, and prohibits access unless it is retyped. */
  182. BUF_NONE,
  183. /** The region contains an 8-bit signed integer. */
  184. BUF_INT8,
  185. /** The region contains a 16-bit signed integer. */
  186. BUF_INT16,
  187. /** The region contains a 32-bit signed integer. */
  188. BUF_INT32,
  189. /** The region contains a 64-bit signed integer. */
  190. BUF_INT64,
  191. /** The region contains an 8-bit unsigned integer. */
  192. BUF_UINT8,
  193. /** The region contains a 16-bit unsigned integer. */
  194. BUF_UINT16,
  195. /** The region contains a 32-bit unsigned integer. */
  196. BUF_UINT32,
  197. /** The region contains a 64-bit unsigned integer. */
  198. BUF_UINT64,
  199. /** The region contains an ASCII character. */
  200. BUF_CHAR,
  201. /** The region contains exactly one addressable unit. */
  202. BUF_BYTE,
  203. /** The region contains a platform-sized signed integer. */
  204. BUF_INT,
  205. /** The region contains a platform-sized unsigned integer. */
  206. BUF_UINT,
  207. /** The region contains a platform-sized signed long integer. */
  208. BUF_LONG,
  209. /** The region contains a platform-sized unsigned long integer. */
  210. BUF_ULONG,
  211. /** The region contains a platform single-precision floating point. */
  212. BUF_FLOAT,
  213. /** The region contains a platform double-precision floating point. */
  214. BUF_DOUBLE,
  215. /** The region contains a pointer to a NUL-terminated C string. */
  216. BUF_CSTR,
  217. /** The region contains a generic pointer (which will instantiate another buffer). */
  218. BUF_PTR
  219. } sol_buftype_t;
  220. /** Ownership types.
  221. *
  222. * These functions determine what happens to the memory region aliased by a
  223. * buffer when that object is freed or copied.
  224. */
  225. typedef enum {
  226. /** Nothing happens; the object is freed or copied normally. */
  227. OWN_NONE,
  228. /** The libc `free` function is called on the buffer. Nothing happens when a new buffer is made to alias it. */
  229. OWN_FREE,
  230. /** The movefunc and freefunc are respectively consulted. */
  231. OWN_CALLF
  232. } sol_owntype_t;
  233. /**
  234. * Transput modes.
  235. *
  236. * These constants are defined (by the same name) on the `io` module as valid bits for the second argument to `io.open`.
  237. */
  238. typedef enum {
  239. /** Permit reading. If this is not set, any attempt to read will raise an error. */
  240. MODE_READ = 1,
  241. /** Permit writing. If this is not set, any attempt to write will raise an error. */
  242. MODE_WRITE = 2,
  243. /** When opening for writing, direct all writes to the end of the file. This has no effect on read positions, when opened in both modes. */
  244. MODE_APPEND = 4,
  245. /** When opened for writing, truncate the file to zero size. Previous contents are lost. */
  246. MODE_TRUNCATE = 8,
  247. /** Prepare the file for reading or writing binary data as opposed to text. */
  248. MODE_BINARY = 16
  249. } sol_modes_t;
  250. /** Buffer freeing function.
  251. *
  252. * This is called with the buffer region and given size when a buffer object is
  253. * freed (from state.BufferOps.free) when the `sol_owntype_t` is set to
  254. * `OWN_CALLF`. It should do whatever is needed to release this one alias of
  255. * memory. Note that care should be taken if multiple buffer objects alias the
  256. * same region.
  257. */
  258. typedef void (*sol_freefunc_t)(void *, size_t);
  259. /** Buffer moving function.
  260. *
  261. * This is called with the buffer region and given size when a buffer object is
  262. * somehow copied (usually by dereferencing a `BUF_PTR`). It should return the
  263. * region that the new buffer object should refer to. The size is assumed to
  264. * not change.
  265. */
  266. typedef void *(*sol_movefunc_t)(void *, size_t);
  267. /** Object structure.
  268. *
  269. * This structure defines the interface of every Sol object. Just as well (and
  270. * as an implementation detail), it contains the operative members of every
  271. * built-in type.
  272. */
  273. typedef struct sol_tag_object_t {
  274. /** The type of this object. */
  275. sol_objtype_t type;
  276. /** The number of living references to this object, increased by `sol_incref` and decreased by `sol_obj_free`. */
  277. int refcnt;
  278. /** The ops structure defining the behavior of this object under certain operations (more or less, its behavioral "type"). */
  279. sol_ops_t *ops;
  280. union {
  281. /** For `SOL_INTEGER`, the value of the integer. */
  282. long ival;
  283. /** For `SOL_FLOAT`, the value of the floating point number. */
  284. double fval;
  285. /** For `SOL_STRING`, the C string pointer. For `SOL_SINGLET`, the name of this singlet. */
  286. char *str;
  287. /** For `SOL_LIST` and `SOL_MAP`, the DSL sequence that contains the items or pairs. */
  288. dsl_seq *seq;
  289. struct {
  290. /** For `SOL_MCELL`, the key of the pair. */
  291. struct sol_tag_object_t *key;
  292. /** For `SOL_MCELL`, the value of the pair. */
  293. struct sol_tag_object_t *val;
  294. };
  295. struct {
  296. /** For `SOL_FUNCTION`, the `stmt_node` pointer representing the function's body. */
  297. void *func; // Actually a stmt_node *
  298. /** For `SOL_FUNCTION`, the `identlist_node` pointer representing the list of the functions argument names. */
  299. void *args; // Actually an identlist_node *
  300. /** For `SOL_FUNCTION`, a map representing the closure (initial scope, updated on exit) of the function. */
  301. struct sol_tag_object_t *closure;
  302. /** For `SOL_FUNCTION`, a map of data defined by the user on this function object. */
  303. struct sol_tag_object_t *udata;
  304. /** For `SOL_FUNCTION`, the name of the function if it was not declared anonymously (otherwise NULL). */
  305. char *fname;
  306. };
  307. /** For `SOL_CFUNCTION`, the C function pointer. */
  308. sol_cfunc_t cfunc;
  309. /** For `SOL_STMT` and `SOL_EXPR`, the `stmt_node` or `expr_node` pointer, respectively. */
  310. void *node;
  311. struct {
  312. /** For `SOL_BUFFER`, the memory region referred to by this buffer. */
  313. void *buffer;
  314. /** For `SOL_BUFFER`, the size of this memory region. Negative values indicate no or unknown size. */
  315. ssize_t sz;
  316. /** For `SOL_BUFFER`, the ownership type of this buffer's region. */
  317. sol_owntype_t own;
  318. /** For `SOL_BUFFER`, the freeing function if own == `OWN_CALLF` */
  319. sol_freefunc_t freef;
  320. /** For `SOL_BUFFER`, the moving function if own == `OWN_CALLF` */
  321. sol_movefunc_t movef;
  322. };
  323. /** For `SOL_DYLIB`, the handle as returned by `dlopen`. */
  324. void *dlhandle;
  325. struct {
  326. /** For `SOL_DYSYM`, the symbol as resolved by `dlsym`. */
  327. void *dlsym;
  328. /** For `SOL_DYSYM`, a sequence of the types of the arguments (a set of `sol_buftype_t` cast to void *, the native type of DSL), if the symbol is a function. */
  329. dsl_seq *argtp;
  330. /** For `SOL_DYSYM`, the return type of the symbol if it is a function; otherwise, the type of the symbol if it is a variable. */
  331. sol_buftype_t rettp;
  332. };
  333. struct {
  334. /** For `SOL_STREAM`, the actual file object. */
  335. FILE *stream;
  336. /** For `SOL_STREAM`, the modes for which this stream is open. */
  337. sol_modes_t modes;
  338. };
  339. /** For `SOL_CDATA`, an arbitrary, user-defined pointer. */
  340. void *cdata;
  341. };
  342. } sol_object_t;
  343. /** State flags.
  344. *
  345. * These flags get set during execution and indicate an altered state of
  346. * interpretation (other than the altered state of interpretation that comes
  347. * about due to an error propagation).
  348. */
  349. typedef enum {SF_NORMAL, SF_BREAKING, SF_CONTINUING} sol_state_flag_t;
  350. typedef struct sol_tag_state_t {
  351. sol_object_t *scopes; ///< A list of scope maps, innermost out, ending at the global scope
  352. sol_object_t *ret; ///< Return value of this function, for early return
  353. sol_object_t *traceback; ///< The last stack of statement (nodes) in the last error, or NULL
  354. sol_state_flag_t sflag; ///< Used to implement break/continue
  355. sol_object_t *error; ///< Some arbitrary error descriptor, `None` if no error
  356. sol_object_t *stdout; ///< Standard output stream object (for print(), type `SOL_STREAM`)
  357. sol_object_t *stdin; ///< Standard input stream object (type `SOL_STREAM`)
  358. sol_object_t *stderr; ///< Standard error stream object (type `SOL_STREAM`)
  359. sol_object_t *None; ///< The all-important `None` object
  360. sol_object_t *OutOfMemory; ///< The semi-important `OutOfMemory` object
  361. sol_object_t *StopIteration; ///< The somewhat-important `StopIteration` object
  362. sol_ops_t NullOps; ///< Basic, initialized operations. Not used by any extant object type.
  363. sol_ops_t SingletOps; ///< Operations on singlets (`None`, `OutOfMemory`, `StopIteration`, etc.)
  364. sol_ops_t IntOps; ///< Operations on integers
  365. sol_ops_t FloatOps; ///< Operations on floats
  366. sol_ops_t StringOps; ///< Operations on strings
  367. sol_ops_t ListOps; ///< Operations on lists
  368. sol_ops_t MapOps; ///< Operations on maps
  369. sol_ops_t MCellOps; ///< Operations on map cells (rarely used)
  370. sol_ops_t FuncOps; ///< Operations on functions
  371. sol_ops_t CFuncOps; ///< Operations on C functions
  372. sol_ops_t ASTNodeOps; ///< Operations on AST nodes
  373. sol_ops_t BufferOps; ///< Operations on buffers
  374. sol_ops_t DyLibOps; ///< Operations on dynamic library objects
  375. sol_ops_t DySymOps; ///< Operations on dynamic symbol objects
  376. sol_ops_t StreamOps; ///< Operations on streams
  377. sol_object_t *modules; ///< A map of modules, string name to contents, resolved at "super-global" scope (and thus overrideable)
  378. sol_object_t *methods; ///< A map of string names to methods (like "list" -> {insert=<CFunction>, remove=<CFunction>, ...}) free for private use by extension developers
  379. dsl_object_funcs obfuncs; ///< The set of object functions that allows DSL to integrate with Sol's reference counting
  380. const char *calling_type; ///< Set (during `CALL_METHOD`) to determine the type (ops structure) being invoked for this method (mostly for sol_f_not_impl)
  381. const char *calling_meth; ///< Set (during `CALL_METHOD`) to determine the method name being invoked (mostly for sol_f_not_impl)
  382. #ifdef SOL_ICACHE
  383. sol_object_t *icache[SOL_ICACHE_MAX - SOL_ICACHE_MIN + 1]; ///< The integer cache (holds integers from `SOL_ICACHE_MIN` to `SOL_ICACHE_MAX` indexed by `[i - SOL_ICACHE_MIN]`)
  384. char icache_bypass; ///< Set to true to bypass caching--needed to avoid infinite recursion when initially populating the cache
  385. #endif
  386. sol_object_t *lastvalue; ///< Holds the value of the last expression evaluated, returned by an `if` expression
  387. sol_object_t *loopvalue; ///< Holds an initially-empty list appended to by `continue <expr>` or set to another object by `break <expr>`
  388. } sol_state_t;
  389. // state.c
  390. /** Initializes the state.
  391. *
  392. * This should be called once (and only once!) for every state; it does the important
  393. * work of ensuring that the state is ready to execute code, including:
  394. *
  395. * - Creating the initial singlet values `None`, `OutOfMemory`, and `StopIteration`,
  396. * - Creating and populating the operations on all internally-defined object types.
  397. * - Initializing all built-in modules and methods.
  398. * - Running any "init.sol" files.
  399. * - Recognizing early-init errors and aborting.
  400. *
  401. * It is the singular, monolithic place where most pre-execution occurs, and language
  402. * developers may thus use it at their discretion. Extension developers should provide
  403. * their own documented initializers, and embedders should do their own initialization
  404. * immediately after calling this function.
  405. */
  406. int sol_state_init(sol_state_t *);
  407. /** Cleans up the state.
  408. *
  409. * In theory, after calling this, the state should be ready to be released (e.g., freed
  410. * if it was allocated on the heap). Importantly, it should NOT be used for any code
  411. * execution after this call (it WILL segfault).
  412. */
  413. void sol_state_cleanup(sol_state_t *);
  414. /** Resolve a name.
  415. *
  416. * Technically, a "name" can be anything (any key in a map, more precisely), but the
  417. * runtime (and most sane code) generally depends on names being strings. It is, however,
  418. * emphatically possible to populate the scopes with non-string names--for potential use
  419. * cases, see `programs/monty.sol`
  420. */
  421. sol_object_t *sol_state_resolve(sol_state_t *, sol_object_t *);
  422. /** Resolve a string name, given as a C string.
  423. *
  424. * This handles the popular case where a C program would like to resolve the value of a
  425. * variable by (string) name. In particular, it handles the memory of doing so properly.
  426. */
  427. sol_object_t *sol_state_resolve_name(sol_state_t *, const char *);
  428. /** Assign to a global name.
  429. *
  430. * This is rarely used, except in `sol_state_init`. It sets the value of the given name
  431. * (as an object) in the global (outermost) scope. Code execution generally uses the
  432. * local scope instead.
  433. */
  434. void sol_state_assign(sol_state_t *, sol_object_t *, sol_object_t *);
  435. /** Assign to a global string name, given as a C string.
  436. *
  437. * This is a convenience for `sol_state_assign`, which handles the creation and destruction
  438. * of the Sol string.
  439. */
  440. void sol_state_assign_name(sol_state_t *, const char *, sol_object_t *);
  441. /** Assign to a local name.
  442. *
  443. * Sets the name to the value in the local (innermost) scope. It has the functional equivalent
  444. * of the Sol code `<name> = <value>` in whatever context the state is in.
  445. */
  446. void sol_state_assign_l(sol_state_t *, sol_object_t *, sol_object_t *);
  447. /** Assign to a local string name, given as a C string.
  448. *
  449. * Another convenience for `sol_state_assign_l`.
  450. */
  451. void sol_state_assign_l_name(sol_state_t *, const char *, sol_object_t *);
  452. /** Push a scope.
  453. *
  454. * This adds a new (more-local) scope to the scope stack (`state->scopes`). This permits values
  455. * in such a scope to be manipulated independently of those in enclosing scopes, and their references
  456. * are discarded during the next `sol_state_pop_scope`. (The values may, of course, be present via
  457. * other references.)
  458. *
  459. * Scope stack manipulation MUST be balanced; egregious errors will occur otherwise.
  460. *
  461. * Scope stack manipulation is generally only necessary where another environment is expected for the
  462. * code running in that context; e.g., the body of a function, or an AST node from an imported file. In
  463. * particular, most control structures do NOT introduce scopes, due to the deleterious effects of having
  464. * no direct influence on enclosing scopes.
  465. */
  466. void sol_state_push_scope(sol_state_t *, sol_object_t *);
  467. /** Pops a scope.
  468. *
  469. * Removes and discards the local scope. All names and associated value references are lost.
  470. *
  471. * This MUST be balanced with `sol_state_push_scope`.
  472. */
  473. sol_object_t *sol_state_pop_scope(sol_state_t *);
  474. /** Returns the current error.
  475. *
  476. * This object is `None` if there is no error. See `sol_has_error`.
  477. */
  478. sol_object_t *sol_get_error(sol_state_t *);
  479. /** Set the current error.
  480. *
  481. * Sets the current error object. Clears the error if the object is `None`.
  482. */
  483. sol_object_t *sol_set_error(sol_state_t *, sol_object_t *);
  484. /** Set the current error to a string, given a C string.
  485. *
  486. * Conveniently sets the error to a string object created from the given C string.
  487. */
  488. sol_object_t *sol_set_error_string(sol_state_t *, const char *);
  489. /** Clear the current error.
  490. *
  491. * Equivalent to `sol_set_error(state, state->None)`.
  492. */
  493. void sol_clear_error(sol_state_t *);
  494. /** Prepares a traceback.
  495. *
  496. * Initializes the traceback stack to an empty list in preparation of `sol_add_traceback`.
  497. * Typically used by the runtime while recovering from an error; the value is ultimately
  498. * returned as the third element of the return list from `try`.
  499. */
  500. void sol_init_traceback(sol_state_t *);
  501. /** Adds an object to a traceback.
  502. *
  503. * This object is usually an ASTNode; typically, it is a statement which was being executed
  504. * when the relevant error occurred. This object is made the first item of the traceback pair
  505. * (the second element is the current local scope).
  506. */
  507. void sol_add_traceback(sol_state_t *, sol_object_t *);
  508. /** Gets the traceback.
  509. *
  510. * This will be a list of traceback pairs; each such pair will be [<value given to `sol_add_traceback`>,
  511. * <local scope>].
  512. */
  513. sol_object_t *sol_traceback(sol_state_t *);
  514. /** Registers a module.
  515. *
  516. * Creates a module entry by name, referring to its value. Modules resolve after globals, and
  517. * therefore form a sort of untouchable "super-global" scope. Most built-in modules reside in
  518. * this namespace.
  519. */
  520. void sol_register_module(sol_state_t *, sol_object_t *, sol_object_t *);
  521. /** Registers a module by string name, given a C string.
  522. *
  523. * A convenience for `sol_register_module`.
  524. */
  525. void sol_register_module_name(sol_state_t *, char *, sol_object_t *);
  526. /** Gets a module.
  527. *
  528. * Retrieves a module by its given name. Its value will be as it was registered.
  529. */
  530. sol_object_t *sol_get_module(sol_state_t *, sol_object_t *);
  531. /** Gets a module by string name, given a C string.
  532. *
  533. * A convenience for `sol_get_module`.
  534. */
  535. sol_object_t *sol_get_module_name(sol_state_t *, char *);
  536. /** Registers methods.
  537. *
  538. * Creates a methods entry by name, referring to its value. Methods are never resolved directly
  539. * by (non-debug) code, but are used liberally throughout the C interface for implementing named
  540. * methods on objects (such as lists, buffers, etc.) that wouldn't normally resolve names--thus
  541. * the name. Thus, the mapping forms a sort of private namespace that may freely be used by
  542. * developers as they see fit.
  543. */
  544. void sol_register_methods(sol_state_t *, sol_object_t *, sol_object_t *);
  545. /** Registers a method by string name, given a C string.
  546. *
  547. * A convenience for `sol_register_methods`.
  548. */
  549. void sol_register_methods_name(sol_state_t *, char *, sol_object_t *);
  550. /** Gets methods.
  551. *
  552. * Retrieves the methods by its name, returning the value that was registered.
  553. */
  554. sol_object_t *sol_get_methods(sol_state_t *, sol_object_t *);
  555. /** Gets methods by string name, given a C string.
  556. *
  557. * A convenience for `sol_get_methods`.
  558. */
  559. sol_object_t *sol_get_methods_name(sol_state_t *, char *);
  560. /** Index operation override for the `io` module.
  561. *
  562. * This hook virtually provides `stdin`, `stdout`, and `stderr` by returning the relevant
  563. * values on the states.
  564. */
  565. sol_object_t *sol_f_io_index(sol_state_t *, sol_object_t *);
  566. /** Setindex operation override for the `io` module.
  567. *
  568. * This hook intercepts and specially handles attempts to set `stdin`, `stdout`, and `stderr`
  569. * by setting the relevant values on the state.
  570. */
  571. sol_object_t *sol_f_io_setindex(sol_state_t *, sol_object_t *);
  572. /** Retrieves the stdin stream.
  573. *
  574. * Returns the stream object used to read program input.
  575. */
  576. sol_object_t *sol_get_stdin(sol_state_t *);
  577. /** Retrieves the stdout stream.
  578. *
  579. * Returns the stream object used to write program output.
  580. */
  581. sol_object_t *sol_get_stdout(sol_state_t *);
  582. /** Retrieves the stderr stream.
  583. *
  584. * Returns the stream object used to write program errors or out-of-band data.
  585. */
  586. sol_object_t *sol_get_stderr(sol_state_t *);
  587. /** Initializes an ops structure.
  588. *
  589. * This sets all the fields of a `sol_ops_t` to their sensible defaults. Such an initialized
  590. * structure is available on the state as `state->NullOps`.
  591. */
  592. void sol_ops_init(sol_ops_t *);
  593. // builtins.c
  594. /** Not implemented handler.
  595. *
  596. * This raises the "Undefined method" error.
  597. */
  598. sol_object_t *sol_f_not_impl(sol_state_t *, sol_object_t *);
  599. /** !!! handler.
  600. *
  601. * Swaps objects by value.
  602. */
  603. sol_object_t *sol_f_tbang(sol_state_t *, sol_object_t *);
  604. /** No operation handler.
  605. *
  606. * Does nothing.
  607. */
  608. sol_object_t *sol_f_no_op(sol_state_t *, sol_object_t *);
  609. /** Default comparison handler.
  610. *
  611. * Returns 0 (equal) if the references refer to exactly the same object, or
  612. * 1 (greater) otherwise.
  613. *
  614. * Note that this is not a partial order.
  615. */
  616. sol_object_t *sol_f_default_cmp(sol_state_t *, sol_object_t *);
  617. /** Default tostring handler.
  618. *
  619. * Returns a string formatted as "<<typename> object at <address>>".
  620. */
  621. sol_object_t *sol_f_default_tostring(sol_state_t *, sol_object_t *);
  622. /** Default torepr handler.
  623. *
  624. * Returns tostring(object).
  625. */
  626. sol_object_t *sol_f_default_repr(sol_state_t *, sol_object_t *);
  627. /// Built-in function toint
  628. sol_object_t *sol_f_toint(sol_state_t *, sol_object_t *);
  629. /// Built-in function tofloat
  630. sol_object_t *sol_f_tofloat(sol_state_t *, sol_object_t *);
  631. /// Built-in function tostring
  632. sol_object_t *sol_f_tostring(sol_state_t *, sol_object_t *);
  633. /// Built-in function try
  634. sol_object_t *sol_f_try(sol_state_t *, sol_object_t *);
  635. /// Built-in function error
  636. sol_object_t *sol_f_error(sol_state_t *, sol_object_t *);
  637. /// Built-in function type
  638. sol_object_t *sol_f_type(sol_state_t *, sol_object_t *);
  639. /// Built-in function prepr
  640. sol_object_t *sol_f_prepr(sol_state_t *, sol_object_t *);
  641. /// Built-in function print
  642. sol_object_t *sol_f_print(sol_state_t *, sol_object_t *);
  643. /// Built-in function rawget
  644. sol_object_t *sol_f_rawget(sol_state_t *, sol_object_t *);
  645. /// Built-in function rawset
  646. sol_object_t *sol_f_rawset(sol_state_t *, sol_object_t *);
  647. /// Built-in function range
  648. sol_object_t *sol_f_range(sol_state_t *, sol_object_t *);
  649. /// Built-in function exec
  650. sol_object_t *sol_f_exec(sol_state_t *, sol_object_t *);
  651. /// Built-in function eval
  652. sol_object_t *sol_f_eval(sol_state_t *, sol_object_t *);
  653. /// Built-in function execfile
  654. sol_object_t *sol_f_execfile(sol_state_t *, sol_object_t *);
  655. /// Built-in function parse
  656. sol_object_t *sol_f_parse(sol_state_t *, sol_object_t *);
  657. /// Built-in function ord
  658. sol_object_t *sol_f_ord(sol_state_t *, sol_object_t *);
  659. /// Built-in function chr
  660. sol_object_t *sol_f_chr(sol_state_t *, sol_object_t *);
  661. sol_object_t *sol_f_debug_getref(sol_state_t *, sol_object_t *);
  662. sol_object_t *sol_f_debug_setref(sol_state_t *, sol_object_t *);
  663. sol_object_t *sol_f_debug_closure(sol_state_t *, sol_object_t *);
  664. sol_object_t *sol_f_debug_globals(sol_state_t *, sol_object_t *);
  665. sol_object_t *sol_f_debug_locals(sol_state_t *, sol_object_t *);
  666. sol_object_t *sol_f_debug_scopes(sol_state_t *, sol_object_t *);
  667. sol_object_t *sol_f_iter_str(sol_state_t *, sol_object_t *);
  668. sol_object_t *sol_f_iter_list(sol_state_t *, sol_object_t *);
  669. sol_object_t *sol_f_iter_map(sol_state_t *, sol_object_t *);
  670. sol_object_t *sol_f_readline_readline(sol_state_t *, sol_object_t *);
  671. sol_object_t *sol_f_readline_add_history(sol_state_t *, sol_object_t *);
  672. sol_object_t *sol_f_ast_print(sol_state_t *, sol_object_t *);
  673. sol_object_t *sol_f_singlet_tostring(sol_state_t *, sol_object_t *);
  674. sol_object_t *sol_f_int_add(sol_state_t *, sol_object_t *);
  675. sol_object_t *sol_f_int_sub(sol_state_t *, sol_object_t *);
  676. sol_object_t *sol_f_int_mul(sol_state_t *, sol_object_t *);
  677. sol_object_t *sol_f_int_div(sol_state_t *, sol_object_t *);
  678. sol_object_t *sol_f_int_mod(sol_state_t *, sol_object_t *);
  679. sol_object_t *sol_f_int_pow(sol_state_t *, sol_object_t *);
  680. sol_object_t *sol_f_int_band(sol_state_t *, sol_object_t *);
  681. sol_object_t *sol_f_int_bor(sol_state_t *, sol_object_t *);
  682. sol_object_t *sol_f_int_bxor(sol_state_t *, sol_object_t *);
  683. sol_object_t *sol_f_int_blsh(sol_state_t *, sol_object_t *);
  684. sol_object_t *sol_f_int_brsh(sol_state_t *, sol_object_t *);
  685. sol_object_t *sol_f_int_bnot(sol_state_t *, sol_object_t *);
  686. sol_object_t *sol_f_int_cmp(sol_state_t *, sol_object_t *);
  687. sol_object_t *sol_f_int_toint(sol_state_t *, sol_object_t *);
  688. sol_object_t *sol_f_int_tofloat(sol_state_t *, sol_object_t *);
  689. sol_object_t *sol_f_int_tostring(sol_state_t *, sol_object_t *);
  690. sol_object_t *sol_f_float_add(sol_state_t *, sol_object_t *);
  691. sol_object_t *sol_f_float_sub(sol_state_t *, sol_object_t *);
  692. sol_object_t *sol_f_float_mul(sol_state_t *, sol_object_t *);
  693. sol_object_t *sol_f_float_div(sol_state_t *, sol_object_t *);
  694. sol_object_t *sol_f_float_pow(sol_state_t *, sol_object_t *);
  695. sol_object_t *sol_f_float_cmp(sol_state_t *, sol_object_t *);
  696. sol_object_t *sol_f_float_toint(sol_state_t *, sol_object_t *);
  697. sol_object_t *sol_f_float_tofloat(sol_state_t *, sol_object_t *);
  698. sol_object_t *sol_f_float_tostring(sol_state_t *, sol_object_t *);
  699. sol_object_t *sol_f_str_add(sol_state_t *, sol_object_t *);
  700. sol_object_t *sol_f_str_mul(sol_state_t *, sol_object_t *);
  701. sol_object_t *sol_f_str_len(sol_state_t *, sol_object_t *);
  702. sol_object_t *sol_f_str_iter(sol_state_t *, sol_object_t *);
  703. sol_object_t *sol_f_str_cmp(sol_state_t *, sol_object_t *);
  704. sol_object_t *sol_f_str_index(sol_state_t *, sol_object_t *);
  705. sol_object_t *sol_f_str_toint(sol_state_t *, sol_object_t *);
  706. sol_object_t *sol_f_str_tofloat(sol_state_t *, sol_object_t *);
  707. sol_object_t *sol_f_str_tostring(sol_state_t *, sol_object_t *);
  708. sol_object_t *sol_f_str_repr(sol_state_t *, sol_object_t *);
  709. sol_object_t *sol_f_str_sub(sol_state_t *, sol_object_t *);
  710. sol_object_t *sol_f_str_split(sol_state_t *, sol_object_t *);
  711. sol_object_t *sol_f_str_find(sol_state_t *, sol_object_t *);
  712. sol_object_t *sol_f_list_add(sol_state_t *, sol_object_t *);
  713. sol_object_t *sol_f_list_mul(sol_state_t *, sol_object_t *);
  714. sol_object_t *sol_f_list_index(sol_state_t *, sol_object_t *);
  715. sol_object_t *sol_f_list_setindex(sol_state_t *, sol_object_t *);
  716. sol_object_t *sol_f_list_len(sol_state_t *, sol_object_t *);
  717. sol_object_t *sol_f_list_iter(sol_state_t *, sol_object_t *);
  718. sol_object_t *sol_f_list_tostring(sol_state_t *, sol_object_t *);
  719. sol_object_t *sol_f_list_copy(sol_state_t *, sol_object_t *);
  720. sol_object_t *sol_f_list_insert(sol_state_t *, sol_object_t *);
  721. sol_object_t *sol_f_list_remove(sol_state_t *, sol_object_t *);
  722. sol_object_t *sol_f_list_truncate(sol_state_t *, sol_object_t *);
  723. sol_object_t *sol_f_list_map(sol_state_t *, sol_object_t *);
  724. sol_object_t *sol_f_list_filter(sol_state_t *, sol_object_t *);
  725. sol_object_t *sol_f_map_add(sol_state_t *, sol_object_t *);
  726. sol_object_t *sol_f_map_index(sol_state_t *, sol_object_t *);
  727. sol_object_t *sol_f_map_setindex(sol_state_t *, sol_object_t *);
  728. sol_object_t *sol_f_map_call(sol_state_t *, sol_object_t *);
  729. sol_object_t *sol_f_map_len(sol_state_t *, sol_object_t *);
  730. sol_object_t *sol_f_map_iter(sol_state_t *, sol_object_t *);
  731. sol_object_t *sol_f_map_tostring(sol_state_t *, sol_object_t *);
  732. sol_object_t *sol_f_map_repr(sol_state_t *, sol_object_t *);
  733. sol_object_t *sol_f_mcell_tostring(sol_state_t *, sol_object_t *);
  734. sol_object_t *sol_f_func_call(sol_state_t *, sol_object_t *); // Defined in ast.c
  735. sol_object_t *sol_f_func_index(sol_state_t *, sol_object_t *);
  736. sol_object_t *sol_f_func_setindex(sol_state_t *, sol_object_t *);
  737. sol_object_t *sol_f_func_tostring(sol_state_t *, sol_object_t *);
  738. sol_object_t *sol_f_cfunc_call(sol_state_t *, sol_object_t *);
  739. sol_object_t *sol_f_cfunc_tostring(sol_state_t *, sol_object_t *);
  740. sol_object_t *sol_f_astnode_call(sol_state_t *, sol_object_t *);
  741. sol_object_t *sol_f_astnode_index(sol_state_t *, sol_object_t *);
  742. sol_object_t *sol_f_astnode_setindex(sol_state_t *, sol_object_t *);
  743. sol_object_t *sol_f_astnode_tostring(sol_state_t *, sol_object_t *);
  744. sol_object_t *sol_f_buffer_index(sol_state_t *, sol_object_t *);
  745. sol_object_t *sol_f_buffer_tostring(sol_state_t *, sol_object_t *);
  746. sol_object_t *sol_f_buffer_get(sol_state_t *, sol_object_t *);
  747. sol_object_t *sol_f_buffer_set(sol_state_t *, sol_object_t *);
  748. sol_object_t *sol_f_buffer_address(sol_state_t *, sol_object_t *);
  749. sol_object_t *sol_f_buffer_size(sol_state_t *, sol_object_t *);
  750. sol_object_t *sol_f_buffer_new(sol_state_t *, sol_object_t *);
  751. sol_object_t *sol_f_buffer_fromstring(sol_state_t *, sol_object_t *);
  752. sol_object_t *sol_f_buffer_fromobject(sol_state_t *, sol_object_t *);
  753. sol_object_t *sol_f_buffer_fromaddress(sol_state_t *, sol_object_t *);
  754. sol_object_t *sol_f_dylib_index(sol_state_t *, sol_object_t *);
  755. sol_object_t *sol_f_dylib_tostring(sol_state_t *, sol_object_t *);
  756. sol_object_t *sol_f_dylib_open(sol_state_t *, sol_object_t *);
  757. sol_object_t *sol_f_dysym_call(sol_state_t *, sol_object_t *);
  758. sol_object_t *sol_f_dysym_index(sol_state_t *, sol_object_t *);
  759. sol_object_t *sol_f_dysym_setindex(sol_state_t *, sol_object_t *);
  760. sol_object_t *sol_f_dysym_tostring(sol_state_t *, sol_object_t *);
  761. sol_object_t *sol_f_dysym_get(sol_state_t *, sol_object_t *);
  762. sol_object_t *sol_f_dysym_set(sol_state_t *, sol_object_t *);
  763. sol_object_t *sol_f_stream_blsh(sol_state_t *, sol_object_t *);
  764. sol_object_t *sol_f_stream_brsh(sol_state_t *, sol_object_t *);
  765. sol_object_t *sol_f_stream_index(sol_state_t *, sol_object_t *);
  766. sol_object_t *sol_f_stream_tostring(sol_state_t *, sol_object_t *);
  767. sol_object_t *sol_f_stream_write(sol_state_t *, sol_object_t *);
  768. sol_object_t *sol_f_stream_read(sol_state_t *, sol_object_t *);
  769. sol_object_t *sol_f_stream_seek(sol_state_t *, sol_object_t *);
  770. sol_object_t *sol_f_stream_tell(sol_state_t *, sol_object_t *);
  771. sol_object_t *sol_f_stream_flush(sol_state_t *, sol_object_t *);
  772. sol_object_t *sol_f_stream_eof(sol_state_t *, sol_object_t *);
  773. sol_object_t *sol_f_stream_open(sol_state_t *, sol_object_t *);
  774. // object.c
  775. #define sol_is_singlet(obj) ((obj)->type == SOL_SINGLET)
  776. #define sol_is_none(state, obj) ((obj) == state->None)
  777. #define sol_is_oom(state, obj) ((obj) == state->OutOfMemory)
  778. #define sol_is_int(obj) ((obj)-> type == SOL_INTEGER)
  779. #define sol_is_float(obj) ((obj)->type == SOL_FLOAT)
  780. #define sol_is_string(obj) ((obj)->type == SOL_STRING)
  781. #define sol_is_list(obj) ((obj)->type == SOL_LIST)
  782. #define sol_is_map(obj) ((obj)->type == SOL_MAP || (obj)->type == SOL_MCELL)
  783. #define sol_is_func(obj) ((obj)->type == SOL_FUNCTION)
  784. #define sol_is_cfunc(obj) ((obj)->type == SOL_CFUNCTION)
  785. #define sol_is_aststmt(obj) ((obj)->type == SOL_STMT)
  786. #define sol_is_astexpr(obj) ((obj)->type == SOL_EXPR)
  787. #define sol_is_astnode(obj) (sol_is_aststmt(obj) || sol_is_astexpr(obj))
  788. #define sol_is_buffer(obj) ((obj)->type == SOL_BUFFER)
  789. #define sol_is_cdata(obj) ((obj)->type == SOL_CDATA)
  790. #define sol_has_error(state) (!sol_is_none((state), (state)->error))
  791. /** Creates a new singlet object with the specified name (or NULL).
  792. *
  793. * Singlets are special objects that are equal only by identity. They are used
  794. * wherever a particular value has special meaning (e.g. None). Other than
  795. * that, their lack of function makes them difficult to manipulate, and many
  796. * internal routines are special-cased for certain singlets.
  797. */
  798. sol_object_t *sol_new_singlet(sol_state_t *, const char *);
  799. /** Creates a new integer object with the specified value. */
  800. sol_object_t *sol_new_int(sol_state_t *, long);
  801. /** Creates a new float object with the specified value. */
  802. sol_object_t *sol_new_float(sol_state_t *, double);
  803. /** Creates a new string object with the specified value. */
  804. sol_object_t *sol_new_string(sol_state_t *, const char *);
  805. /** Utility function to compare a Sol string and a C string, used often in
  806. * builtin and extension code. */
  807. int sol_string_cmp(sol_state_t *, sol_object_t *, const char *);
  808. /** Utility macro wrapping `sol_string_cmp`. */
  809. #define sol_string_eq(state, string, cstr) (sol_string_cmp((state), (string), (cstr))==0)
  810. /** Internal routine that returns a new Sol string that results from the
  811. * concatenation of two Sol strings (in the order given). */
  812. sol_object_t *sol_string_concat(sol_state_t *, sol_object_t *, sol_object_t *);
  813. /** Utility function for conveniently concatenating a Sol string and a C string
  814. * (and returning a Sol string). */
  815. sol_object_t *sol_string_concat_cstr(sol_state_t *, sol_object_t *, char *);
  816. /** Creates a new empty Sol list. */
  817. sol_object_t *sol_new_list(sol_state_t *);
  818. /** Creates a new Sol list populated with objects obtained by iterating over a
  819. * DSL sequence. */
  820. sol_object_t *sol_list_from_seq(sol_state_t *, dsl_seq *);
  821. /** Internal routine to get the length of a Sol list */
  822. int sol_list_len(sol_state_t *, sol_object_t *);
  823. /** Internal routine to return a new Sol list equivalent to its input with the
  824. * first n elements skipped. */
  825. sol_object_t *sol_list_sublist(sol_state_t *, sol_object_t *, int);
  826. /** Internal routine to get the object at the specified index in a Sol list. */
  827. sol_object_t *sol_list_get_index(sol_state_t *, sol_object_t *, int);
  828. /** Internal routine to set the object at the specified index in a Sol list. */
  829. void sol_list_set_index(sol_state_t *, sol_object_t *, int, sol_object_t *);
  830. /** Internal routine to insert an object at the specified index in a Sol list.
  831. *
  832. * Unlike setting, insertion may happen at the lists length, inclusive (in
  833. * which case it appends an element). When this routine returns successfully
  834. * (without an error on the state), the index specified should hold a reference
  835. * to the object given as a parameter.
  836. */
  837. void sol_list_insert(sol_state_t *, sol_object_t *, int, sol_object_t *);
  838. /** Internal routine to remove an object at the specified index in a Sol list,
  839. * returning a reference to that object. */
  840. sol_object_t *sol_list_remove(sol_state_t *, sol_object_t *, int);
  841. /** Internal routine to return a copy of a Sol list.
  842. *
  843. * Note that this performs a "shallow" copy, in that while the new list is a
  844. * different reference, the references inside the list are the same.
  845. */
  846. sol_object_t *sol_list_copy(sol_state_t *, sol_object_t *);
  847. /** Internal routine to return a new Sol list equivalent to its input up to the
  848. * first n elements. */
  849. sol_object_t *sol_list_truncate(sol_state_t *, sol_object_t *, int);
  850. /** Utility routine to insert at the end of a Sol list. */
  851. void sol_list_append(sol_state_t *, sol_object_t *, sol_object_t *);
  852. /** Utility macro to insert an object at the beginning of a Sol list. */
  853. #define sol_list_push(st, ls, obj) sol_list_insert(st, ls, 0, obj);
  854. /** Utility macro to remove and return the object at the beginning of a Sol
  855. * list. */
  856. #define sol_list_pop(st, ls) sol_list_remove(st, ls, 0);
  857. sol_object_t *sol_new_map(sol_state_t *);
  858. int sol_map_len(sol_state_t *, sol_object_t *);
  859. sol_object_t *sol_map_mcell(sol_state_t *, sol_object_t *, sol_object_t *);
  860. int sol_map_has(sol_state_t *, sol_object_t *, sol_object_t *);
  861. sol_object_t *sol_map_get(sol_state_t *, sol_object_t *, sol_object_t *);
  862. sol_object_t *sol_map_get_name(sol_state_t *, sol_object_t *, char *);
  863. void sol_map_set(sol_state_t *, sol_object_t *, sol_object_t *, sol_object_t *);
  864. #define sol_map_borrow(state, map, key, object) do {\
  865. sol_object_t *__obj = (object);\
  866. sol_map_set((state), (map), (key), __obj);\
  867. sol_obj_free(__obj);\
  868. } while(0)
  869. void sol_map_set_name(sol_state_t *, sol_object_t *, char *, sol_object_t *);
  870. #define sol_map_borrow_name(state, map, str, object) do {\
  871. sol_object_t *__obj = (object);\
  872. sol_map_set_name((state), (map), (str), __obj);\
  873. sol_obj_free(__obj);\
  874. } while(0)
  875. void sol_map_set_existing(sol_state_t *, sol_object_t *, sol_object_t *, sol_object_t *);
  876. sol_object_t *sol_map_copy(sol_state_t *, sol_object_t *);
  877. void sol_map_merge(sol_state_t *, sol_object_t *, sol_object_t *);
  878. void sol_map_merge_existing(sol_state_t *, sol_object_t *, sol_object_t *);
  879. void sol_map_invert(sol_state_t *, sol_object_t *);
  880. // Defined in ast.h
  881. // sol_object_t *sol_new_func(sol_state_t *, identlist_node *, stmt_node *, char *);
  882. // sol_object_t *sol_new_stmtnode(sol_state_t *, stmt_node *);
  883. // sol_object_t *sol_new_exprnode(sol_state_t *, expr_node *);
  884. sol_object_t *sol_new_cfunc(sol_state_t *, sol_cfunc_t);
  885. sol_object_t *sol_new_cdata(sol_state_t *, void *, sol_ops_t *);
  886. sol_object_t *sol_new_buffer(sol_state_t *, void *, ssize_t, sol_owntype_t, sol_freefunc_t, sol_movefunc_t);
  887. sol_object_t *sol_new_dylib(sol_state_t *, void *);
  888. sol_object_t *sol_new_dysym(sol_state_t *, void *, dsl_seq *, sol_buftype_t);
  889. sol_object_t *sol_new_stream(sol_state_t *, FILE *, sol_modes_t);
  890. size_t sol_stream_printf(sol_state_t *, sol_object_t *, const char *, ...);
  891. size_t sol_stream_vprintf(sol_state_t *, sol_object_t *, const char *, va_list);
  892. size_t sol_stream_scanf(sol_state_t *, sol_object_t *, const char *, ...);
  893. size_t sol_stream_fread(sol_state_t *, sol_object_t *, char *, size_t, size_t);
  894. size_t sol_stream_fwrite(sol_state_t *, sol_object_t *, char *, size_t, size_t);
  895. char *sol_stream_fgets(sol_state_t *, sol_object_t *, char *, size_t);
  896. int sol_stream_fputc(sol_state_t *, sol_object_t *, int);
  897. #define _sol_io_on(state, op, strname, ...) do {\
  898. sol_object_t *__str = sol_get_##strname(state);\
  899. sol_stream_##op((state), __str, __VA_ARGS__);\
  900. sol_obj_free(__str);\
  901. } while(0)
  902. #define sol_printf(state, ...) _sol_io_on(state, printf, stdout, __VA_ARGS__)
  903. #define sol_vprintf(state, ...) _sol_io_on(state, vprintf, stdout, __VA_ARGS__)
  904. #define sol_scanf(state, ...) _sol_io_on(state, scanf, stdin, __VA_ARGS__)
  905. #define sol_fread(state, ...) _sol_io_on(state, fread, stdin, __VA_ARGS__)
  906. #define sol_fwrite(state, ...) _sol_io_on(state, fwrite, stdout, __VA_ARGS__)
  907. #define sol_putchar(state, ...) _sol_io_on(state, fputc, stdout, __VA_ARGS__)
  908. int sol_stream_feof(sol_state_t *, sol_object_t *);
  909. int sol_stream_ferror(sol_state_t *, sol_object_t *);
  910. #define sol_stream_ready(state, stream) (!(sol_stream_feof((state), (stream)) || sol_stream_ferror((state), (stream))))
  911. int sol_stream_fseek(sol_state_t *, sol_object_t *, long, int);
  912. long sol_stream_ftell(sol_state_t *, sol_object_t *);
  913. int sol_stream_fflush(sol_state_t *, sol_object_t *);
  914. sol_object_t *sol_cast_int(sol_state_t *, sol_object_t *);
  915. sol_object_t *sol_cast_float(sol_state_t *, sol_object_t *);
  916. sol_object_t *sol_cast_string(sol_state_t *, sol_object_t *);
  917. sol_object_t *sol_cast_repr(sol_state_t *, sol_object_t *);
  918. sol_object_t *sol_f_singlet_free(sol_state_t *, sol_object_t *);
  919. sol_object_t *sol_f_str_free(sol_state_t *, sol_object_t *);
  920. sol_object_t *sol_f_list_free(sol_state_t *, sol_object_t *);
  921. sol_object_t *sol_f_map_free(sol_state_t *, sol_object_t *);
  922. sol_object_t *sol_f_mcell_free(sol_state_t *, sol_object_t *);
  923. sol_object_t *sol_f_func_free(sol_state_t *, sol_object_t *);
  924. sol_object_t *sol_f_astnode_free(sol_state_t *, sol_object_t *);
  925. sol_object_t *sol_f_buffer_free(sol_state_t *, sol_object_t *);
  926. sol_object_t *sol_f_dylib_free(sol_state_t *, sol_object_t *);
  927. sol_object_t *sol_f_stream_free(sol_state_t *, sol_object_t *);
  928. int sol_validate_list(sol_state_t *, sol_object_t *);
  929. int sol_validate_map(sol_state_t *, sol_object_t *);
  930. // util.c
  931. sol_object_t *sol_util_call(sol_state_t *, sol_object_t *, int *, int, ...);
  932. // gc.c
  933. #ifdef DEBUG_GC
  934. sol_object_t *_int_sol_incref(const char *, sol_object_t *);
  935. void _int_sol_obj_free(const char *, sol_object_t *);
  936. sol_object_t *_sol_gc_dsl_copier(sol_object_t *);
  937. void _sol_gc_dsl_destructor(sol_object_t *);
  938. sol_object_t *_int_sol_alloc_object(const char *, sol_state_t *);
  939. #define sol_incref(obj) (_int_sol_incref(__func__, (obj)))
  940. #define sol_obj_free(obj) (_int_sol_obj_free(__func__, (obj)))
  941. #define sol_alloc_object(state) (_int_sol_alloc_object(__func__, (state)))
  942. #else
  943. #define sol_incref(obj) (++((obj)->refcnt), obj)
  944. void sol_obj_free(sol_object_t *);
  945. sol_object_t *sol_alloc_object(sol_state_t *);
  946. #endif
  947. #define sol_decref(obj) (--((obj)->refcnt))
  948. sol_object_t *sol_obj_acquire(sol_object_t *);
  949. void sol_obj_release(sol_object_t *);
  950. void sol_mm_initialize(sol_state_t *);
  951. void sol_mm_finalize(sol_state_t *);
  952. #define AS_OBJ(x) ((sol_object_t *) (x))
  953. #endif