sm1.c
最終更新:2009/11/15
001: /* sm1.c
002: * SpiderMonkey を C プログラムから使う例
003: *
004: * 使い方:コマンドライン引数で JavaScript のコードを指定する。
005: * % sm1 "function f(x){if(x<=0){return 1;}else{return x*f(x-1);}};f(5)"
006: * script result: 120
007: * done.
008: */
009:
010: #define USAGE "Usage: sm1 <script>"
011:
012: #include <string.h>
013: #include "jsapi.h"
014:
015: /* グローバルオブジェクトのクラス */
016: static JSClass global_class = {
017: "global",
018: JSCLASS_GLOBAL_FLAGS,
019: JS_PropertyStub,
020: JS_PropertyStub,
021: JS_PropertyStub,
022: JS_PropertyStub,
023: JS_EnumerateStub,
024: JS_ResolveStub,
025: JS_ConvertStub,
026: JS_FinalizeStub,
027: JSCLASS_NO_OPTIONAL_MEMBERS
028: };
029:
030: /* エラーレポート用コールバック関数 */
031: void reportError(
032: JSContext *jsctx
033: , const char *message
034: , JSErrorReport *report
035: ) {
036: fprintf(stderr, "%s:%u:%s\n",
037: report->filename ? report->filename : "<no filename>",
038: (unsigned int) report->lineno,
039: message);
040: }
041:
042: int main(int ac, char **av)
043: {
044: int error_flag = 0;
045:
046: JSRuntime *jsrt = NULL;
047: JSContext *jsctx = NULL;
048: JSObject *global = NULL;
049:
050: char *script = NULL;
051:
052: if (ac < 2) {
053: fprintf(stderr, "%s\n", USAGE);
054: error_flag = 1;
055: goto _FINALLY_;
056: }
057: script = av[1];
058:
059: /* 初期化 */
060:
061: /* プロセス単位でランタイムを生成 */
062: jsrt = JS_NewRuntime(8L * 1024L * 1024L);
063: if (!jsrt) {
064: fprintf(stderr, "ERROR: JS_NewRuntime ");
065: error_flag = 1;
066: goto _FINALLY_;
067: }
068:
069: /* スレッド単位でコンテクスト生成 */
070: jsctx = JS_NewContext(jsrt, 8192);
071: if (!jsctx) {
072: fprintf(stderr, "ERROR: JS_NewContext ");
073: error_flag = 1;
074: goto _FINALLY_;
075: }
076:
077: JS_SetOptions(jsctx, JSOPTION_VAROBJFIX);
078: JS_SetVersion(jsctx, JSVERSION_LATEST);
079: JS_SetErrorReporter(jsctx, reportError);
080:
081: /* コンテクスト単位でグローバルオブジェクトを生成 */
082: global = JS_NewObject(jsctx, &global_class, NULL, NULL);
083: if (!global) {
084: fprintf(stderr, "ERROR: JS_NewObject ");
085: error_flag = 1;
086: goto _FINALLY_;
087: }
088:
089: if (!JS_InitStandardClasses(jsctx, global)) {
090: fprintf(stderr, "ERROR: JS_InitStandardClasses ");
091: error_flag = 1;
092: goto _FINALLY_;
093: }
094:
095: /* スクリプトの実行 */
096:
097: if (script) {
098: jsval rval;
099: JSBool ok = JS_EvaluateScript(jsctx, global, script, strlen(script),
100: __FILE__, __LINE__, &rval);
101: if (ok != JS_TRUE) {
102: error_flag = 1;
103: goto _FINALLY_;
104: }
105: {
106: JSString *str = JS_ValueToString(jsctx, rval);
107: if (str) {
108: printf("script result: %s\n", JS_GetStringBytes(str));
109: }
110: }
111: }
112:
113: _FINALLY_:
114:
115: /* JSContext と JSRuntime リソースの解放 */
116: if (jsctx) {
117: JS_DestroyContext(jsctx);
118: jsctx = NULL;
119: }
120: if (jsrt) {
121: JS_DestroyRuntime(jsrt);
122: jsrt = NULL;
123: }
124:
125: JS_ShutDown();
126:
127: if (error_flag) {
128: fprintf(stderr, "failed.\n");
129: return 1;
130: }
131:
132: printf("done.\n");
133: return 0;
134: } /* End of main */
![]() | KAKU PROJECT (2009) |