SongZihuan преди 4 години
родител
ревизия
2fce7c8cc5
променени са 8 файла, в които са добавени 60 реда и са изтрити 11 реда
  1. 9 3
      argument/argument.c
  2. 1 0
      include/arguement.h
  3. 3 1
      include/inter.h
  4. 1 1
      main.c
  5. 3 2
      memory/mem.c
  6. 23 0
      ofunc/src/io.c
  7. 17 3
      src/inter.c
  8. 3 1
      src/runfile.c

+ 9 - 3
argument/argument.c

@@ -9,13 +9,14 @@ char *HelloString = "Welcome To VirtualMath ("__TIME__", "__DATE__") \n"
                     "VirtualMath Command Line Mode\n";
 
 static const struct option long_option[]={
-        {"log-err",required_argument,NULL,'o'},
-        {"log-out",required_argument,NULL,'e'},
+        {"stderr",required_argument,NULL,'o'},
+        {"stdout",required_argument,NULL,'e'},
+        {"stdin",required_argument,NULL,'i'},
         {"not-run-cl",required_argument,NULL,'n'},
         {NULL,0,NULL,0}
 };
 
-static const char *short_option = "o:e:n";
+static const char *short_option = "o:e:i:n";
 
 /**
  * 参数设置, args是全局结构体, 保存全局的参数设置
@@ -27,6 +28,7 @@ int getArgs(const int argc, char **argv)
 {
     args.out_file = NULL;
     args.error_file = NULL;
+    args.in_file = NULL;
     args.run_commandLine = true;
     opterr = true;
     int opt;
@@ -42,6 +44,9 @@ int getArgs(const int argc, char **argv)
             case 'e':
                 args.error_file = memStrcpy(optarg);
                 break;
+            case 'i':
+                args.in_file = memStrcpy(optarg);
+                break;
             case 'n':
                 args.run_commandLine = false;
                 break;
@@ -61,4 +66,5 @@ int getArgs(const int argc, char **argv)
 void freeArgs(void){
     memFree(args.out_file);
     memFree(args.error_file);
+    memFree(args.in_file);
 }

+ 1 - 0
include/arguement.h

@@ -5,6 +5,7 @@ extern char *HelloString;
 struct Args{
     char *error_file;
     char *out_file;
+    char *in_file;
     bool run_commandLine;
 } args;
 

+ 3 - 1
include/inter.h

@@ -14,8 +14,10 @@ struct Inter{
     struct InterData{
         FILE *inter_stdout;
         FILE *inter_stderr;
+        FILE *inter_stdin;
         bool is_stdout;
         bool is_stderr;
+        bool is_stdin;
 
         struct Value *object;
         struct Value *vobject;
@@ -77,7 +79,7 @@ typedef struct Inter Inter;
 typedef struct Statement Statement;
 typedef enum ResultType ResultType;
 
-Inter *makeInter(char *out, char *error_, struct LinkValue *belong);
+Inter *makeInter(char *out, char *error_, char *in, LinkValue *belong);
 void freeInter(Inter *inter, bool show_gc);
 void setBaseInterData(struct Inter *inter);
 ResultType runCodeBlock(char *code_file, Inter *inter);

+ 1 - 1
main.c

@@ -14,7 +14,7 @@ int main(int argc, char *argv[]) {
 
     if (getArgs(argc, argv))
         goto args_error;
-    inter = makeInter(args.out_file, args.error_file, NULL);
+    inter = makeInter(args.out_file, args.error_file, args.in_file, NULL);
 
     ctrlCUseJmp = true;
     signal(SIGINT, signalStop);

+ 3 - 2
memory/mem.c

@@ -43,13 +43,14 @@ char *memStrcpy(const char *const str){
 
 char *memStrCharcpy(char *str, size_t nsize, bool free_old, bool write, ...) {  // 复制str到新的空间,nszie是要扩展的大小。该函数支持让str=NULL,则变为单纯的memString
     char *tmp = memString(memStrlen(str) + nsize);
-    if (str != NULL)
+    size_t base_len = memStrlen(str);
+    if (base_len != 0)
         strcpy(tmp, str);
     if (write){
         va_list argp;
         va_start(argp, write);
         for (int i = 0; i < nsize; i++)
-            tmp[memStrlen(str) + i] = (char)va_arg(argp, int);
+            tmp[base_len + i] = (char)va_arg(argp, int);
         va_end(argp);
     }
     if (free_old)

+ 23 - 0
ofunc/src/io.c

@@ -44,10 +44,33 @@ ResultType vm_printCore(OFFICAL_FUNCTIONSIG, int type){
     return result->type;
 }
 
+ResultType vm_input(OFFICAL_FUNCTIONSIG){
+    setResultCore(result);
+    ArgumentParser ap[] = {{.type=name_value, .name="message", .must=0, .value=NULL},
+                           {.must=-1}};
+    char *str = memStrcpy("\0");
+    int ch;
+    parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
+    if (!CHECK_RESULT(result))
+        return result->type;
+    freeResult(result);
+
+    if (ap[0].value != NULL)
+        printValue(ap[0].value->value, inter->data.inter_stdout, false);
+
+    while ((ch = fgetc(inter->data.inter_stdin)) != '\n' && ch != EOF)
+        str = memStrCharcpy(str, 1, true, true, ch);
+
+    setResultOperationBase(result, makeLinkValue(makeStringValue(str, inter), belong, inter));
+    memFree(str);
+    return result->type;
+}
+
 void registeredIOFunction(REGISTERED_FUNCTIONSIG){
     NameFunc tmp[] = {{"print", vm_print, free_},
                       {"print_link", vm_printLink, free_},
                       {"print_all", vm_printAll, free_},
+                      {"input", vm_input, free_},
                       {NULL, NULL}};
     iterNameFunc(tmp, belong, CALL_INTER_FUNCTIONSIG_CORE(var_list));
 }

+ 17 - 3
src/inter.c

@@ -1,6 +1,6 @@
 #include "__virtualmath.h"
 
-Inter *makeInter(char *out, char *error_, LinkValue *belong) {
+Inter *makeInter(char *out, char *error_, char *in, LinkValue *belong) {
     Inter *tmp = memCalloc(1, sizeof(Inter));
     LinkValue *base_father = NULL;
     setBaseInterData(tmp);
@@ -11,7 +11,7 @@ Inter *makeInter(char *out, char *error_, LinkValue *belong) {
 
     tmp->var_list = makeVarList(tmp, true);
 
-    if (out) {
+    if (out != NULL) {
         tmp->data.inter_stdout = fopen(out, "w");
         tmp->data.is_stdout = false;
         if (tmp->data.inter_stdout == NULL)
@@ -23,7 +23,7 @@ Inter *makeInter(char *out, char *error_, LinkValue *belong) {
         tmp->data.is_stdout = true;
     }
 
-    if (error_) {
+    if (error_ != NULL) {
         tmp->data.inter_stdout = fopen(error_, "w");
         tmp->data.is_stderr = false;
         if (tmp->data.inter_stdout == NULL)
@@ -35,6 +35,18 @@ Inter *makeInter(char *out, char *error_, LinkValue *belong) {
         tmp->data.is_stderr = true;
     }
 
+    if (in != NULL) {
+        tmp->data.inter_stdin = fopen(in, "r");
+        tmp->data.is_stdin = false;
+        if (tmp->data.inter_stdin == NULL)
+            goto set_stdin_;
+    }
+    else {
+        set_stdin_:
+        tmp->data.inter_stdin = stdin;
+        tmp->data.is_stdin = true;
+    }
+
     registeredFunctionName(tmp);
 
     tmp->data.none = makeNoneValue(tmp);
@@ -141,6 +153,8 @@ void freeBaseInterData(struct Inter *inter){
         fclose(inter->data.inter_stdout);
     if (!inter->data.is_stderr)
         fclose(inter->data.inter_stderr);
+    if (!inter->data.is_stdin)
+        fclose(inter->data.inter_stdin);
 }
 
 void freeInter(Inter *inter, bool show_gc) {

+ 3 - 1
src/runfile.c

@@ -61,11 +61,13 @@ ResultType importFileCore(VarList **new_object, char **file_dir, INTER_FUNCTIONS
     }
 
 
-    import_inter = makeInter(NULL, NULL, belong);
+    import_inter = makeInter(NULL, NULL, NULL, belong);
     import_inter->data.inter_stdout = inter->data.inter_stdout;
     import_inter->data.inter_stderr = inter->data.inter_stderr;
+    import_inter->data.inter_stdin = inter->data.inter_stdin;
     import_inter->data.is_stdout = true;
     import_inter->data.is_stderr = true;
+    import_inter->data.is_stdin = true;
 
     pm = makeParserMessage(*file_dir);
     run_st = makeStatement(0, *file_dir);