]> Nishi Git Mirror - gwion.git/commitdiff
:art: Use libcmdapp
authorJérémie Astor <fennecdjay@gmail.com>
Thu, 25 Feb 2021 19:16:07 +0000 (20:16 +0100)
committerJérémie Astor <fennecdjay@gmail.com>
Thu, 25 Feb 2021 19:16:07 +0000 (20:16 +0100)
21 files changed:
.github/workflows/codeql-analysis.yml
.github/workflows/coverage.yml
.github/workflows/coverity.yml
.github/workflows/linux-release.yml
.github/workflows/linux.yml
.github/workflows/macos.yml
.github/workflows/windows-release.yml
.github/workflows/windows.yml
.gitmodules
Makefile
config.mk.orig
include/arg.h
include/operator.h
libcmdapp [new submodule]
src/arg.c
src/emit/emit.c
src/env/type.c
src/gwion.c
src/parse/check.c
src/parse/operator.c
src/parse/template.c

index 4c64af7957042b0d1859d07b61ded96cbff18351..22f84fb447d13910a23cf7850fbc3eca741e7f77 100644 (file)
@@ -52,7 +52,7 @@ jobs:
         # queries: ./path/to/local/query, your-org/your-repo/queries@main
 
     - run: |
-        git submodule update --init util ast
+        git submodule update --init util ast libcmdapp
         make
     # Autobuild attempts to build any compiled languages  (C/C++, C#, or Java).
     # If this step fails, then you should remove it and run the build manually (see below)
index 08164c6ff87a6f5b4f211c9c98bcd2e23af1fa7c..8acaea62580b049bc2a9448a47c44537004c2a2c 100644 (file)
@@ -22,7 +22,7 @@ jobs:
       uses: actions/checkout@v2
 
     - name: Init submodules
-      run: git submodule update --init util ast
+      run: git submodule update --init util ast libcmdapp
 
     - name: Build Gwion
       run: make
index 59e5b8b4c7042c01195dc66f90e885a961911721..a08766f18d466544043336b885fcbe55493d8ca0 100644 (file)
@@ -17,7 +17,7 @@ jobs:
       uses: actions/checkout@v2
 
     - name: Init submodules
-      run: git submodule update --init util ast
+      run: git submodule update --init util ast libcmdapp
 
     - name: Download tool
       run: |
@@ -28,7 +28,7 @@ jobs:
     - name: Build
       run: |
         export PATH=`pwd`/cov-analysis-linux64/bin:$PATH
-        cov-build --dir cov-int make 
+        cov-build --dir cov-int make
 
     - name: Submit
       run: |
index 18753f6342748e7f022d906d2355ef606a196e8d..e2c9e706b1a6b72ef88318ebe1510fce171147b7 100644 (file)
@@ -16,7 +16,7 @@ jobs:
       uses: actions/checkout@v2
 
     - name: SubModules
-      run: git submodule update --init util ast
+      run: git submodule update --init util ast libcmdapp
 
     - name: Build
       run: make
index 831a2e331290f33dd6c34b03aaf7f3bebc9e6e03..f3397d1687c73d139be9bef0e11d0b2ca5fb18c8 100644 (file)
@@ -29,7 +29,7 @@ jobs:
       uses: actions/checkout@v2
 
     - name: Init submodules
-      run: git submodule update --init util ast
+      run: git submodule update --init util ast libcmdapp
 
     - name: Build
       run: make
index 380834d51b23fc621927dcec5851b1fa54f782ac..775963d5568717304678fee671bf455c2c3a113a 100644 (file)
@@ -29,7 +29,7 @@ jobs:
       uses: actions/checkout@v2
 
     - name: Init submodules
-      run: git submodule update --init util ast
+      run: git submodule update --init util ast libcmdapp
 
     - name: Build
       run: make
index 4021b57931272dcc6b930209f3fbaf12f4874185..fab38caf2a16a64ce5a4a5eeba9acf4e628e6612 100644 (file)
@@ -19,7 +19,7 @@ jobs:
       uses: actions/checkout@v2
 
     - name: SubModules
-      run: git submodule update --init util ast
+      run: git submodule update --init util ast libcmdapp
 
     - name: Build
       run: make
index 1492f6a206c37e5f24683cb47475283b8f6f00d9..d88062f37531e7e72432bf69dca7d4ad55bfc33f 100644 (file)
@@ -28,7 +28,7 @@ jobs:
         uses: actions/checkout@v2
 
       - name: Init submodules
-        run: git submodule update --init util ast
+        run: git submodule update --init util ast libcmdapp
 
       - name: Build
         run: make
index c6a5b606f68124ed544eeaa77295e6fe121eb07d..854622189ee971abb1e32c0df008aff839ba70df 100644 (file)
@@ -11,3 +11,6 @@
        path = ast
        url = https://github.com/Gwion/gwion-ast
        active = true
+[submodule "libcmdapp"]
+       path = libcmdapp
+       url = https://github.com/euppal/libcmdapp
index a4ed17a22db2f22aa0207ca595db34aff5dcb3ac..64457bd43f256b81148de3bc87ee451571eceb7b 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -20,6 +20,9 @@ test_ignore = tests/plug test/driver tests/module
 test_dir := $(filter-out $(test_ignore), $(test_dir_all))
 test_dir += examples
 
+
+CFLAGS += -Iutil/include -Iast/include -Ilibcmdapp/src -D_GNU_SOURCE
+
 ifeq (${DEBUG_STACK}, 1)
 CFLAGS += -DDEBUG_STACK
 endif
@@ -52,10 +55,10 @@ endif
 
 CFLAGS += -DGWION_BUILTIN
 
-GWLIBS = lib${PRG}.a ast/libgwion_ast.a util/libgwion_util.a
+GWLIBS = lib${PRG}.a ast/libgwion_ast.a util/libgwion_util.a libcmdapp/libcmdapp.a
 _LDFLAGS = ${GWLIBS} ${LDFLAGS}
 
-all: options-show util/libgwion_util.a ast/libgwion_ast.a lib${PRG}.a src/main.o
+all: options-show ${GWLIBS} src/main.o
        $(info link ${PRG})
        @${CC} src/main.o -o ${PRG} ${_LDFLAGS} ${LIBS}
 
@@ -74,6 +77,9 @@ util: util/libgwion_util.a
 ast/libgwion_ast.a:
        @+GWION_PACKAGE= ${MAKE} -s -C ast
 
+libcmdapp/libcmdapp.a:
+       @+${MAKE} -s -C libcmdapp static
+
 ast: ast/libgwion_ast.a
        @(info build ast)
 
index 18e565d7633013afdba96d78b20bc28f2b283450..8ba2903c211cabb533d64eccc7c2e9dec30fbaf7 100644 (file)
@@ -1,7 +1,6 @@
 # handle base options
 PRG ?=gwion
 PREFIX ?=/usr/local
-CFLAGS += -Iutil/include -Iast/include -D_GNU_SOURCE
 
 # base plugin directories
 GWPLUG_DIR   ?= $(shell echo ~/.gwplug)
index dfaf85870d0796b6e634a7d58b6bcb2e6b522dd0..6076e76c557bbd321e43be630fa1076c8c6ac50f 100644 (file)
@@ -9,6 +9,7 @@ typedef struct Arg_ {
   struct Vector_ config;
   struct SoundInfo_ *si;
   m_bool loop;
+  m_bool quit;
 } Arg;
 
 ANN void arg_release(Arg*);
index 1ab598f0fef088579086c48339c919833e6a0115..59bea17faea9e25f4e87102480509de57d424556 100644 (file)
@@ -20,25 +20,12 @@ struct Op_Func {
   opem em;
 };
 
-enum op_type {
-  op_implicit,
-  op_exp,
-  op_dot,
-  op_array,
-  op_binary,
-  op_cast,
-  op_postfix,
-  op_unary,
-  op_scan
-};
-
 struct Op_Import {
   Type lhs, rhs, ret;
   const struct Op_Func *func;
   uintptr_t data;
   loc_t pos;
   Symbol op;
-  enum op_type op_type;
 };
 
 struct Implicit {
diff --git a/libcmdapp b/libcmdapp
new file mode 160000 (submodule)
index 0000000..6d39da6
--- /dev/null
+++ b/libcmdapp
@@ -0,0 +1 @@
+Subproject commit 6d39da65b3eee1538c6fb4f4883b7f9072485050
index dd340388081362dedf74a807b84604e3d394051e..0dba4872eb8b3672bd59febda60b5bd34de23562 100644 (file)
--- a/src/arg.c
+++ b/src/arg.c
@@ -7,9 +7,20 @@
 #include "arg.h"
 #include "pass.h"
 #include "compile.h"
+#include "cmdapp.h"
 
 #define GWIONRC ".gwionrc"
 
+enum {
+  CONFIG, PLUGIN, MODULE,
+  LOOP, PASS, STDIN,
+// sound options
+  DRIVER, SRATE, INPUT, OUTPUT,
+// pp options
+  DEFINE, UNDEF, INCLUDE,
+  NOPTIONS
+};
+
 /* use before MemPool allocation */
 ANN static inline void config_end(const Vector config) {
   for(m_uint i = 0; i < vector_size(config); ++i) {
@@ -79,32 +90,15 @@ ANN void arg_compile(const Gwion gwion, Arg *arg) {
   }
 }
 
-static const char usage[] =
-"usage: Gwion <options>\n"
-"  -h              : this help\n"
-"  -c     <file>   : load config\n"
-"  -p     <path>   : add a plugin directory\n"
-"  -s    <number>  : set samplerate\n"
-"  -i    <number>  : set input channel number\n"
-"  -o    <number>  : set output channel number\n"
-"  -d    <number>  : set driver (and arguments)\n"
-"  -l    <number>  : set loop mode\n"
-"  -m   <mod:args> : load module (and arguments)\n"
-"  -g   <mod:args> : set Gwion compiler passes order\n";
-
-ANN static void config_parse(const Gwion, Arg*, const m_str);
-
-#define ARG2INT(a) strtol(a, NULL, 10)
-
-ANN2(1) static inline void arg_set_pass(const Gwion gwion, const m_str str) {
-  const Vector v = split_args(gwion->mp, str);
+ANN2(1) static inline void arg_set_pass(const Gwion gwion, const char *str) {
+  const Vector v = split_args(gwion->mp, (const m_str)str);
   pass_set(gwion, v);
   for(m_uint i = 0; i < vector_size(v); ++i)
     free_mstr(gwion->mp, (m_str)vector_at(v, i));
   free_vector(gwion->mp, v);
 }
 
-ANN2(1) static void module_arg(const Map map, m_str str) {
+ANN2(1) static void module_arg(const Map map, const char *str) {
   m_str val = strchr(str, '=');
   if(val) {
     *val = '\0';
@@ -113,80 +107,78 @@ ANN2(1) static void module_arg(const Map map, m_str str) {
   map_set(map, (vtype)str, (vtype)val);
 }
 
-ANN m_bool _arg_parse(const Gwion gwion, Arg* arg) {
-  struct CArg *ca = &arg->arg;
-  for(ca->idx = 1; ca->idx < ca->argc; ++ca->idx) {
-    if(ca->argv[ca->idx][0] == '-') {
-      m_str tmp;
-      switch(ca->argv[ca->idx][1]) {
-        case 'h':
-          gw_err(usage);
-          break;
-        case 'c':
-          CHECK_OB((tmp = option_argument(ca)))
-          config_parse(gwion, arg, tmp);
-          break;
-        case 'p':
-          CHECK_OB((tmp = option_argument(ca)))
-          vector_add(&arg->lib, (vtype)tmp);
-          break;
-        case 'm':
-          CHECK_OB((tmp = option_argument(ca)))
-          module_arg(&arg->mod, tmp);
-          break;
-        case 'l':
-          CHECK_OB((tmp = option_argument(ca)))
-          arg->loop = (m_bool)ARG2INT(tmp) > 0 ? 1 : -1;
-          break;
-        case 'i':
-          CHECK_OB((tmp = option_argument(ca)))
-          arg->si->in = (uint8_t)ARG2INT(tmp);
-          break;
-        case 'o':
-          CHECK_OB((tmp = option_argument(ca)))
-          arg->si->out = (uint8_t)ARG2INT(tmp);
-          break;
-        case 's':
-          CHECK_OB((tmp = option_argument(ca)))
-          arg->si->sr = (uint32_t)ARG2INT(tmp);
-          break;
-        case 'd':
-          CHECK_OB((tmp = option_argument(ca)))
-          arg->si->arg = tmp;
-          break;
-        case 'g':
-          CHECK_OB((tmp = option_argument(ca)))
-          arg_set_pass(gwion, tmp);
-          break;
-        case '\0':
-          vector_add(&arg->add, (vtype)ARG_STDIN);
-          break;
-        case 'D':
-          CHECK_OB((tmp = option_argument(ca)))
-          vector_add(&arg->add, (vtype)ARG_DEFINE);
-          vector_add(&arg->add, (vtype)tmp);
-          break;
-        case 'U':
-          CHECK_OB((tmp = option_argument(ca)))
-          vector_add(&arg->add, (vtype)ARG_UNDEF);
-          vector_add(&arg->add, (vtype)tmp);
-          break;
-        case 'I':
-          CHECK_OB((tmp = option_argument(ca)))
-          vector_add(&arg->add, (vtype)ARG_INCLUDE);
-          vector_add(&arg->add, (vtype)tmp);
-          break;
-        default:
-          gw_err(_("invalid arguments"));
-          return GW_ERROR;
-      }
-    } else
-{
-      vector_add(&arg->add, (vtype)ARG_FILE);
-      vector_add(&arg->add, (vtype)ca->argv[ca->idx]);
+static void setup_options(cmdapp_t* app, cmdopt_t* opt) {
+    cmdapp_set(app,
+        'c', "config",
+        CMDOPT_TAKESARG, NULL,
+        "parse a config file", &opt[CONFIG]
+    );
+    cmdapp_set(app,
+        'p', "plugdir",
+        CMDOPT_TAKESARG, NULL,
+        "add ARG to the plugin search path", &opt[PLUGIN]
+    );
+    cmdapp_set(app,
+        'm', "module",
+        CMDOPT_TAKESARG, NULL,
+        "activate module (and arguments)", &opt[MODULE]
+    );
+    cmdapp_set(app,
+        'l', "loop",
+        CMDOPT_TAKESARG, NULL,
+        "set loop mode", &opt[LOOP]
+    );
+    cmdapp_set(app,
+        'g', "passes",
+        CMDOPT_TAKESARG, NULL,
+        "set pass order", &opt[PASS]
+    );
+    cmdapp_set(app,
+        '\0', "stdin",
+        CMDOPT_OPTIONAL, NULL,
+        "read from stdin", &opt[STDIN]
+    );
+// sound options
+    cmdapp_set(app,
+        'd', "driver",
+        CMDOPT_TAKESARG, NULL,
+        "set driver (and arguments)", &opt[DRIVER]
+    );
+    cmdapp_set(app,
+        's', "samplerate",
+        CMDOPT_TAKESARG, NULL,
+        "set the samplerate", &opt[SRATE]
+    );
+    cmdapp_set(app,
+        'i', "input",
+        CMDOPT_TAKESARG, NULL,
+        "number of input channel", &opt[INPUT]
+    );
+    cmdapp_set(app,
+        'o', "output",
+        CMDOPT_TAKESARG, NULL,
+        "number of output channel", &opt[OUTPUT]
+    );
+    cmdapp_set(app,
+        'D', "define",
+        CMDOPT_TAKESARG, NULL,
+        "define a macro", &opt[DEFINE]
+    );
+    cmdapp_set(app,
+        'U', "undef",
+        CMDOPT_TAKESARG, NULL,
+        "undefine a macro", &opt[UNDEF]
+    );
+    cmdapp_set(app,
+        'I', "include",
+        CMDOPT_TAKESARG, NULL,
+        "add ARG to include path", &opt[INCLUDE]
+    );
 }
-  }
-  return GW_OK;
+
+static inline void add2arg(Arg *const arg, const char *data, const enum arg_type type) {
+  vector_add(&arg->add, type);
+  vector_add(&arg->add, (vtype)data);
 }
 
 ANN static void split_line(const m_str line, const Vector v) {
@@ -201,7 +193,8 @@ ANN static void split_line(const m_str line, const Vector v) {
   xfree(c);
 }
 
-ANN static Vector get_config(const m_str name) {
+
+ANN static Vector get_config(const char *name) {
   char *line = NULL;
   size_t len = 0;
   ssize_t nread;
@@ -219,30 +212,121 @@ ANN static Vector get_config(const m_str name) {
   return v;
 }
 
-ANN static void config_parse(const Gwion gwion, Arg* arg, const m_str name) {
+struct ArgInternal {
+  const Gwion gwion;
+  Arg *arg;
+};
+
+ANN m_bool _arg_parse(struct ArgInternal* arg);
+
+ANN static void config_parse(struct ArgInternal* arg, const char *name) {
   const Vector v = get_config(name);
   if(v) {
-    struct CArg ca = arg->arg;
-    arg->arg.argc = vector_size(v);
-    arg->arg.argv =  (m_str*)(v->ptr + OFFSET);
-    _arg_parse(gwion, arg);
-    arg->arg = ca;
-    vector_add(&arg->config, (vtype)v);
+    struct CArg ca = arg->arg->arg;
+    arg->arg->arg.argc = vector_size(v);
+    arg->arg->arg.argv =  (m_str*)(v->ptr + OFFSET);
+    _arg_parse(arg);
+    arg->arg->arg = ca;
+    vector_add(&arg->arg->config, (vtype)v);
   }
 }
 
-ANN static void config_default(const Gwion gwion , Arg* arg) {
+#define ARG2INT(a) strtol(a, NULL, 10)
+
+static void myproc(void *data, cmdopt_t* option, const char* arg) {
+  struct ArgInternal *arg_int = data;
+  Arg *_arg = arg_int->arg;
+  if(arg) {
+    if(!_arg->arg.idx)
+      _arg->arg.idx++;
+    else
+      add2arg(_arg, arg, ARG_FILE);
+  } else {
+    switch(option->shorto) {
+      case 'p':
+        vector_add(&_arg->lib, (vtype)option->value);
+        break;
+      case 'm':
+        module_arg(&_arg->mod, option->value);
+        break;
+      case 'c':
+        config_parse(arg_int, option->value);
+        break;
+      case 'l':
+        _arg->loop = (m_bool)ARG2INT(option->value) > 0 ? 1 : -1;
+        break;
+      case 'g':
+        arg_set_pass(arg_int->gwion, option->value);
+        break;
+      case '\0':
+        vector_add(&_arg->add, (vtype)ARG_STDIN);
+        break;
+// sound options
+        case 's':
+          _arg->si->sr = (uint32_t)ARG2INT(option->value);
+          break;
+        case 'd':
+          _arg->si->arg = (m_str)option->value;
+          break;
+        case 'i':
+          _arg->si->in = (uint8_t)ARG2INT(option->value);
+          break;
+        case 'o':
+          _arg->si->out = (uint8_t)ARG2INT(option->value);
+          break;
+// pp options
+        case 'D':
+          add2arg(_arg, option->value, ARG_DEFINE);
+          break;
+        case 'U':
+          add2arg(_arg, option->value, ARG_UNDEF);
+          break;
+        case 'I':
+          add2arg(_arg, option->value, ARG_INCLUDE);
+          break;
+    }
+  }
+}
+
+ANN m_bool _arg_parse(struct ArgInternal *arg) {
+  cmdapp_t app;
+  const cmdapp_info_t info = {
+        .program = "gwion",
+        .synopses = NULL, // so it's automatic
+        .version = "N.A.",
+        .author = "Jérémie Astor",
+        .year = 2016,
+        .description = "Strongly timed musical programming language.",
+        .help_des_offset = 28,
+        .ver_extra =
+        "License GPLv3+: GNU GPL version 3 or later <https://gnu.org/licenses/gpl.html>\n"
+        "This is free software: you are free to change and redistribute it.\n"
+        "There is NO WARRANTY, to the extent permitted by law.\n"
+  };
+  struct CArg *ca = &arg->arg->arg;
+  cmdapp_init(&app, ca->argc, ca->argv, CMDAPP_MODE_SHORTARG, &info);
+  cmdapp_enable_procedure(&app, myproc, arg);
+  cmdopt_t opt[NOPTIONS];
+  setup_options(&app, opt);
+  if(cmdapp_run(&app) == EXIT_SUCCESS && cmdapp_should_exit(&app))
+     arg->arg->quit = 1;
+  cmdapp_destroy(&app);
+  return GW_OK;
+}
+
+ANN static void config_default(struct ArgInternal* arg) {
   char* home = getenv("HOME");
   char c[strlen(home) + strlen(GWIONRC) + 2];
   sprintf(c, "%s/%s", home, GWIONRC);
-  config_parse(gwion, arg, c);
+  config_parse(arg, c);
 }
 
 ANN m_bool arg_parse(const Gwion gwion, Arg* a) {
+  struct ArgInternal arg = { .gwion=gwion, .arg=a };
   arg_init(a);
 #ifdef __FUZZING
   return;
 #endif
-  config_default(gwion, a);
-  return _arg_parse(gwion, a);
+  config_default(&arg);
+  return _arg_parse(&arg);
 }
index 4131595c7d9134867e213c5ff3ccf08110836862..e8aaebcf17cd00c95225aafa4d2ac8c5d35cd8d6 100644 (file)
@@ -557,7 +557,7 @@ ANN static m_bool emit_prim_range(const Emitter emit, Range **data) {
   const Exp e = range->start ?: range->end;
   const Symbol sym = insert_symbol("@range");
   struct Op_Import opi = { .op=sym, .rhs=e->type,
-    .pos=e->pos, .data=(uintptr_t)prim_exp(data), .op_type=op_exp };
+    .pos=e->pos, .data=(uintptr_t)prim_exp(data) };
   CHECK_BB(op_emit(emit, &opi))
   emit_gc(emit, -SZ_INT);
   return GW_OK;
@@ -570,7 +570,7 @@ ANN m_bool emit_array_access(const Emitter emit, struct ArrayAccessInfo *const i
   }
   // look mum no pos
   struct Op_Import opi = { .op=insert_symbol("@array"), .lhs=info->array.exp->type, .rhs=info->array.type,
-    .data=(uintptr_t)info, .op_type=op_array };
+    .data=(uintptr_t)info };
   if(!info->is_var && (GET_FLAG(info->array.type, abstract) || type_ref(info->array.type))) {
     const Instr instr = emit_add_instr(emit, GWOP_EXCEPT);
     instr->m_val = -SZ_INT;
@@ -591,7 +591,7 @@ ANN static m_bool emit_exp_slice(const Emitter emit, const Exp_Slice* range) {
   const Symbol sym = insert_symbol("@slice");
   const Exp e = range->range->start ?: range->range->end;
   struct Op_Import opi = { .op=sym, .lhs=e->type, .rhs=range->base->type,
-    .pos=e->pos, .data=(uintptr_t)exp_self(range), .op_type=op_exp };
+    .pos=e->pos, .data=(uintptr_t)exp_self(range) };
   return op_emit(emit, &opi);
 }
 
@@ -928,7 +928,7 @@ ANN static m_bool emit_exp_call(const Emitter emit, const Exp_Call* exp_call) {
     CHECK_BB(emit_exp_call1(emit, t->info->func))
   else {
     struct Op_Import opi = { .op=insert_symbol("@ctor"), .rhs=t,
-      .data=(uintptr_t)exp_call, .pos=exp_self(exp_call)->pos, .op_type=op_exp };
+      .data=(uintptr_t)exp_call, .pos=exp_self(exp_call)->pos };
     CHECK_BB(op_emit(emit, &opi))
   }
   const Exp e = exp_self(exp_call);
@@ -990,14 +990,14 @@ ANN static m_bool emit_exp_binary(const Emitter emit, const Exp_Binary* bin) {
 //  emit_exp_addref1(emit, lhs, -exp_size(lhs) - size);
 //  emit_exp_addref1(emit, rhs, -size);
   struct Op_Import opi = { .op=bin->op, .lhs=lhs->type, .rhs=rhs->type,
-    .pos=exp_self(bin)->pos, .data=(uintptr_t)bin, .op_type=op_binary };
+    .pos=exp_self(bin)->pos, .data=(uintptr_t)bin };
   return op_emit(emit, &opi);
 }
 
 ANN static m_bool emit_exp_cast(const Emitter emit, const Exp_Cast* cast) {
   // no pos ?
   struct Op_Import opi = { .op=insert_symbol("$"), .lhs=cast->exp->type, .rhs=exp_self(cast)->type,
-    .data=(uintptr_t)cast, .op_type=op_cast};
+    .data=(uintptr_t)cast };
   CHECK_BB(emit_exp(emit, cast->exp))
   (void)op_emit(emit, &opi);
   return GW_OK;
@@ -1006,7 +1006,7 @@ ANN static m_bool emit_exp_cast(const Emitter emit, const Exp_Cast* cast) {
 ANN static m_bool emit_exp_post(const Emitter emit, const Exp_Postfix* post) {
   // no pos ?
   struct Op_Import opi = { .op=post->op, .lhs=post->exp->type,
-    .data=(uintptr_t)post, .op_type=op_postfix };
+    .data=(uintptr_t)post };
   CHECK_BB(emit_exp(emit, post->exp))
   return op_emit(emit, &opi);
 }
@@ -1130,7 +1130,7 @@ static m_bool me_cmp(MemoizeEmitter *me, const Arg_List arg) {
   const Symbol sym = insert_symbol("==");
   struct Exp_ exp = {};
   struct Op_Import opi = { .op=sym, .lhs=arg->type, .rhs=arg->type,
-    .pos=me->fdef->pos, .data=(uintptr_t)&exp.d, .op_type=op_binary };
+    .pos=me->fdef->pos, .data=(uintptr_t)&exp.d };
   CHECK_BB(op_emit(emit, &opi))
   const Instr instr = emit_add_instr(emit, BranchEqInt);
   vector_add(&me->branch, (vtype)instr);
@@ -1373,7 +1373,7 @@ ANN static m_bool emit_exp_unary(const Emitter emit, const Exp_Unary* unary) {
   const Type base = actual_type(emit->gwion, t);
   CHECK_BB(ensure_emit(emit, base))
   // no pos ?
-  struct Op_Import opi = { .op=unary->op, .data=(uintptr_t)unary, .op_type=op_unary };
+  struct Op_Import opi = { .op=unary->op, .data=(uintptr_t)unary };
   if(unary->unary_type == unary_exp && unary->op != insert_symbol("spork") && unary->op != insert_symbol("fork")) {
     CHECK_BB(emit_exp_pop_next(emit, unary->exp))
     opi.rhs = unary->exp->type;
@@ -1386,7 +1386,7 @@ ANN static m_bool emit_implicit_cast(const Emitter emit,
   const struct Implicit imp = { from, to, from->pos };
   // no pos
   struct Op_Import opi = { .op=insert_symbol("@implicit"), .lhs=from->type, .rhs=to,
-    .data=(m_uint)&imp, .op_type=op_implicit };
+    .data=(m_uint)&imp };
   return op_emit(emit, &opi);
 }
 
@@ -1394,7 +1394,7 @@ ANN static Instr _flow(const Emitter emit, const Exp e, const m_bool b) {
   CHECK_BO(emit_exp_pop_next(emit, e))
   emit_exp_addref1(emit, e, -exp_size(e));
   struct Op_Import opi = { .op=insert_symbol(b ? "@conditionnal" : "@unconditionnal"),
-                           .rhs=e->type, .pos=e->pos, .data=(uintptr_t)e, .op_type=op_exp };
+                           .rhs=e->type, .pos=e->pos, .data=(uintptr_t)e };
   CHECK_BO(op_emit(emit, &opi))
   return (Instr)vector_back(&emit->code->instr);
 }
@@ -1896,7 +1896,7 @@ ANN static m_bool emit_case_head(const Emitter emit, const Exp base,
   const Exp_Binary bin = { .lhs=base, .rhs=e, .op=op };
   struct Exp_ ebin = { .d={.exp_binary=bin}, };
   struct Op_Import opi = { .op=op, .lhs=base->type, .rhs=e->type,
-    .data=(uintptr_t)&ebin.d.exp_binary, .pos=e->pos, .op_type=op_binary };
+    .data=(uintptr_t)&ebin.d.exp_binary, .pos=e->pos };
   CHECK_BB(op_emit(emit, &opi))
   const Instr instr = emit_add_instr(emit, BranchEqInt);
   vector_add(v, (vtype)instr);
@@ -1975,7 +1975,7 @@ ANN static Symbol case_op(const Emitter emit, const Exp base, const Exp e, const
   const Exp_Binary bin = { .lhs=base, .rhs=e, .op=insert_symbol("==") };
   struct Exp_ ebin = { .d={.exp_binary=bin}, };
   struct Op_Import opi = { .op=insert_symbol("=="), .lhs=base->type, .rhs=e->type,
-    .data=(uintptr_t)&ebin.d.exp_binary, .pos=e->pos, .op_type=op_binary };
+    .data=(uintptr_t)&ebin.d.exp_binary, .pos=e->pos };
   CHECK_BO(op_emit(emit, &opi))
   const Instr instr = emit_add_instr(emit, BranchEqInt);
   vector_add(vec, (vtype)instr);
@@ -2079,7 +2079,7 @@ ANN static m_bool emit_stmt_list(const Emitter emit, Stmt_List l) {
 
 ANN static m_bool emit_exp_dot(const Emitter emit, const Exp_Dot* member) {
   struct Op_Import opi = { .op=insert_symbol("@dot"), .lhs=member->base->type,
-    .rhs=exp_self(member)->type, .data=(uintptr_t)member, .pos=exp_self(member)->pos, .op_type=op_dot };
+    .rhs=exp_self(member)->type, .data=(uintptr_t)member, .pos=exp_self(member)->pos };
   return op_emit(emit, &opi);
 }
 
index cb09c10ee0b41ae32fd9b6f2764ce6a7574afe6a..38b772ae6faa0b95c47ec6d04d766fa96c502adc 100644 (file)
@@ -106,7 +106,7 @@ ANN Type array_type(const Env env, const Type src, const m_uint depth) {
   const size_t tdepth = depth + src->array_depth;
   const Type base = tdepth > 1 ? array_type(env, src, tdepth-1) : src;
   struct TemplateScan ts = { .t=base, /*.td=td*/ };
-  struct Op_Import opi = { .op=insert_symbol("@scan"), .lhs=env->gwion->type[et_array], .data=(uintptr_t)&ts, .op_type=op_scan };
+  struct Op_Import opi = { .op=insert_symbol("@scan"), .lhs=env->gwion->type[et_array], .data=(uintptr_t)&ts };
   return op_check(env, &opi);
 }
 
index 89f1a65307a32ebd72d501bae2d7ae61a0bce90d..48e2f180e0bcc97228af600639621121cf0b0f57 100644 (file)
@@ -92,7 +92,7 @@ ANN m_bool gwion_ini(const Gwion gwion, Arg* arg) {
   pass_default(gwion);
   arg->si = gwion->vm->bbq->si = new_soundinfo(gwion->mp);
   CHECK_BB(arg_parse(gwion, arg))
-  return gwion_ok(gwion, arg);
+  return !arg->quit ? gwion_ok(gwion, arg) : GW_ERROR;
 }
 
 ANN void gwion_run(const Gwion gwion) {
index b630281d44af37a516fb49162fecd9f42ab00155..6bd33170bab2a74e5e3efbf778dfa50dca0579c0 100644 (file)
@@ -21,7 +21,7 @@ ANN static Type check_internal(const Env env, const Symbol sym,
       const Exp e, const Type t) {
   struct Implicit imp = { .e=e, .t=t, .pos=e->pos };
   struct Op_Import opi = { .op=sym, .lhs=e->type,
-        .rhs=t, .data=(uintptr_t)&imp, .pos=e->pos, .op_type=op_implicit };
+        .rhs=t, .data=(uintptr_t)&imp, .pos=e->pos };
   return op_check(env, &opi);
 }
 
@@ -214,7 +214,7 @@ ANN static Type check_prim_range(const Env env, Range **data) {
   CHECK_BO(check_range(env, range))
   const Exp e = range->start ?: range->end;
   const Symbol sym = insert_symbol("@range");
-  struct Op_Import opi = { .op=sym, .rhs=e->type, .pos=e->pos, .data=(uintptr_t)prim_exp(data), .op_type=op_exp };
+  struct Op_Import opi = { .op=sym, .rhs=e->type, .pos=e->pos, .data=(uintptr_t)prim_exp(data) };
   return op_check(env, &opi);
 }
 
@@ -260,7 +260,7 @@ ANN static Value check_non_res_value(const Env env, const Symbol *data) {
 
 ANN static Type check_dot(const Env env, const Exp_Dot *member) {
   struct Op_Import opi = { .op=insert_symbol("@dot"), .lhs=member->base->type, .data=(uintptr_t)member,
-    .pos=exp_self(member)->pos, .op_type=op_dot };
+    .pos=exp_self(member)->pos };
   return op_check(env, &opi);
 }
 
@@ -366,7 +366,7 @@ ANN static Type check_prim(const Env env, Exp_Primary *prim) {
 ANN Type check_array_access(const Env env, const Array_Sub array) {
   const Symbol sym = insert_symbol("@array");
   struct Op_Import opi = { .op=sym, .lhs=array->exp->type, .rhs=array->type,
-    .pos=array->exp->pos, .data=(uintptr_t)array, .op_type=op_array };
+    .pos=array->exp->pos, .data=(uintptr_t)array };
   return op_check(env, &opi);
 }
 
@@ -382,7 +382,7 @@ static ANN Type check_exp_slice(const Env env, const Exp_Slice* range) {
   const Symbol sym = insert_symbol("@slice");
   const Exp e = range->range->start ?: range->range->end;
   struct Op_Import opi = { .op=sym, .lhs=e->type, .rhs=range->base->type,
-    .pos=e->pos, .data=(uintptr_t)exp_self(range), .op_type=op_exp };
+    .pos=e->pos, .data=(uintptr_t)exp_self(range) };
   return op_check(env, &opi);
 }
 
@@ -668,7 +668,7 @@ ANN m_bool func_check(const Env env, const Exp_Call *exp) {
   const Type t = actual_type(env->gwion, exp->func->type);
   const Exp e = exp_self(exp);
   struct Op_Import opi = { .op=insert_symbol("@func_check"),
-  .rhs=t, .pos=e->pos, .data=(uintptr_t)e, .op_type=op_exp };
+  .rhs=t, .pos=e->pos, .data=(uintptr_t)e };
   CHECK_NB(op_check(env, &opi)) // doesn't really return NULL
   if(e->exp_type != ae_exp_call)
     return 0;
@@ -683,7 +683,7 @@ ANN Type check_exp_call1(const Env env, const Exp_Call *exp) {
   const Type t = actual_type(env->gwion, exp->func->type);
   if(isa(t, env->gwion->type[et_function]) < 0) { // use func flag?
     struct Op_Import opi = { .op=insert_symbol("@ctor"), .rhs=actual_type(env->gwion, exp->func->type),
-      .data=(uintptr_t)exp, .pos=exp_self(exp)->pos, .op_type=op_exp };
+      .data=(uintptr_t)exp, .pos=exp_self(exp)->pos };
     const Type t = op_check(env, &opi);
     return t;
   }
@@ -716,7 +716,7 @@ ANN static Type check_exp_binary(const Env env, const Exp_Binary* bin) {
   if(is_auto)
     bin->rhs->type = bin->lhs->type;
   struct Op_Import opi = { .op=bin->op, .lhs=bin->lhs->type,
-    .rhs=bin->rhs->type, .data=(uintptr_t)bin, .pos=exp_self(bin)->pos, .op_type=op_binary };
+    .rhs=bin->rhs->type, .data=(uintptr_t)bin, .pos=exp_self(bin)->pos };
   exp_setuse(bin->lhs, 1);
   exp_setuse(bin->rhs, 1);
   const Type ret = op_check(env, &opi);
@@ -729,13 +729,13 @@ ANN static Type check_exp_cast(const Env env, const Exp_Cast* cast) {
   DECL_OO(const Type, t, = check_exp(env, cast->exp))
   CHECK_OO((exp_self(cast)->type = known_type(env, cast->td)))
   struct Op_Import opi = { .op=insert_symbol("$"), .lhs=t, .rhs=exp_self(cast)->type,
-    .data=(uintptr_t)cast, .pos=exp_self(cast)->pos, .op_type=op_cast };
+    .data=(uintptr_t)cast, .pos=exp_self(cast)->pos };
   return op_check(env, &opi);
 }
 
 ANN static Type check_exp_post(const Env env, const Exp_Postfix* post) {
   struct Op_Import opi = { .op=post->op, .lhs=check_exp(env, post->exp),
-    .data=(uintptr_t)post, .pos=exp_self(post)->pos, .op_type=op_postfix };
+    .data=(uintptr_t)post, .pos=exp_self(post)->pos };
   CHECK_OO(opi.lhs)
   exp_setuse(post->exp, 1);
   const Type t = op_check(env, &opi);
@@ -792,7 +792,7 @@ ANN static Type check_exp_unary(const Env env, const Exp_Unary* unary) {
     exp_setuse(unary->exp, 1);
   }
   struct Op_Import opi = { .op=unary->op, .rhs=rhs,
-    .data=(uintptr_t)unary, .pos=exp_self(unary)->pos, .op_type=op_unary };
+    .data=(uintptr_t)unary, .pos=exp_self(unary)->pos };
   DECL_OO(const Type, ret, = op_check(env, &opi))
   const Type t = actual_type(env->gwion, ret);
   CHECK_BO(ensure_traverse(env, t))
@@ -802,7 +802,7 @@ ANN static Type check_exp_unary(const Env env, const Exp_Unary* unary) {
 ANN static Type _flow(const Env env, const Exp e, const m_bool b) {
   DECL_OO(const Type, type, = check_exp(env, e))
   struct Op_Import opi = { .op=insert_symbol(b ? "@conditionnal" : "@unconditionnal"),
-    .rhs=type, .pos=e->pos, .data=(uintptr_t)e, .op_type=op_exp };
+    .rhs=type, .pos=e->pos, .data=(uintptr_t)e };
   return op_check(env, &opi);
 }
 #define check_flow(emit,b) _flow(emit, b, 1)
@@ -1059,7 +1059,7 @@ ANN static m_bool match_case_exp(const Env env, Exp e) {
       Exp_Binary bin = { .lhs=base, .rhs=e, .op=op };
       struct Exp_ ebin = { .d={.exp_binary=bin} };
       struct Op_Import opi = { .op=op, .lhs=base->type, .rhs=e->type,
-        .data=(uintptr_t)&ebin.d.exp_binary, .pos=e->pos, .op_type=op_binary };
+        .data=(uintptr_t)&ebin.d.exp_binary, .pos=e->pos };
       CHECK_OB(op_check(env, &opi))
     }
   }
index 027e357d24f155bd600a3f98ae12b276eb3de8ed..e394882f8d6c2efcb6d26e5d5f1fa206bee25314 100644 (file)
@@ -164,7 +164,7 @@ for(int i = 0; i < 2; ++i) {
       continue;
     Type l = opi->lhs;
     do {
-      struct Op_Import opi2 = { .op=opi->op, .lhs=l, .rhs=opi->rhs, .data=opi->data, .op_type=opi->op_type };
+      struct Op_Import opi2 = { .op=opi->op, .lhs=l, .rhs=opi->rhs, .data=opi->data };
       struct OpChecker ock = { env, &nspc->info->op_map, &opi2 };
       const Type ret = op_check_inner(&ock, i);
       if(ret) {
index 85babe9ba345b56ec1a2950099a8cc3949a10a2e..9f0a8d2126031d4d36692072cde33563c7967edf 100644 (file)
@@ -100,7 +100,7 @@ ANN Type _scan_type(const Env env, const Type t, Type_Decl* td) {
     if(tflag(t, tflag_ntmpl) && !td->types)
       return t;
     struct TemplateScan ts = { .t=t, .td=td };
-    struct Op_Import opi = { .op=insert_symbol("@scan"), .lhs=t, .data=(uintptr_t)&ts, .pos=td->pos, .op_type=op_scan };
+    struct Op_Import opi = { .op=insert_symbol("@scan"), .lhs=t, .data=(uintptr_t)&ts, .pos=td->pos };
     return op_check(env, &opi);
   } else if(td->types)
     return maybe_func(env, t, td);