浏览代码

feat: 增加访问权限

base_var的auto访问权限均为private
point的访问权限auto为public
point访问时会检测father的权限是否足够大来访问child
增加参数的权限设定
SongZihuan 4 年之前
父节点
当前提交
f25ad7382a
共有 11 个文件被更改,包括 97 次插入20 次删除
  1. 1 1
      include/parameter.h
  2. 1 0
      include/statement.h
  3. 9 0
      include/value.h
  4. 1 0
      main.c
  5. 26 0
      parser/grammar.c
  6. 16 5
      src/parameter.c
  7. 2 0
      src/run.c
  8. 2 2
      src/runcall.c
  9. 30 10
      src/runoperation.c
  10. 1 0
      src/statement.c
  11. 8 2
      src/value.c

+ 1 - 1
include/parameter.h

@@ -64,7 +64,7 @@ Argument *listToArgument(LinkValue *list_value, INTER_FUNCTIONSIG_CORE);
 Argument *dictToArgument(LinkValue *dict_value, INTER_FUNCTIONSIG_CORE);
 
 ResultType setParameterCore(Argument *call, Parameter *function_base, VarList *function_var, INTER_FUNCTIONSIG_NOT_ST);
-ResultType setParameter(Parameter *call_base, Parameter *function_base, VarList *function_var, INTER_FUNCTIONSIG_NOT_ST);
+ResultType setParameter(Parameter *call_base, Parameter *function_base, VarList *function_var, LinkValue *function_father, INTER_FUNCTIONSIG_NOT_ST);
 ResultType iterParameter(Parameter *call, Argument **base_ad, INTER_FUNCTIONSIG_NOT_ST);
 Argument *getArgument(Parameter *call, INTER_FUNCTIONSIG_NOT_ST);
 

+ 1 - 0
include/statement.h

@@ -3,6 +3,7 @@
 #include "__macro.h"
 
 struct Statement{
+    enum ValueAuthority aut;
     enum StatementType{
         start = 1,
         base_value,

+ 9 - 0
include/value.h

@@ -9,6 +9,13 @@ struct VarList;
 struct Argument;
 struct FatherValue;
 
+enum ValueAuthority{
+    auto_aut,
+    public_aut,
+    protect_aut,
+    private_aut
+};
+
 struct Value{
     struct GCStatus gc_status;
     enum ValueType{
@@ -56,6 +63,7 @@ struct Value{
 
 struct LinkValue{
     struct GCStatus gc_status;
+    enum ValueAuthority aut;
     struct Value *value;
     struct LinkValue *father;
     struct LinkValue *gc_next;
@@ -103,6 +111,7 @@ Value *makeObject(Inter *inter, VarList *object, VarList *out_var, FatherValue *
 Value * freeValue(Value *value, Inter *inter);
 LinkValue *makeLinkValue(Value *value, LinkValue *linkValue,Inter *inter);
 LinkValue * freeLinkValue(LinkValue *value, Inter *inter);
+LinkValue *copyLinkValue(LinkValue *value, Inter *inter);
 Value *makeNoneValue(Inter *inter);
 Value *makeNumberValue(long num, Inter *inter);
 Value *makeStringValue(char *str, Inter *inter);

+ 1 - 0
main.c

@@ -26,4 +26,5 @@ int main(int argc, char *argv[]) {
  * TODO-szh 生成语法树
  * TODO-szh 取反符号 -
  * TODO-szh 字面量后缀
+ * TODO-szh dict设置: 忽略变量、设置权限、设置father
  */

+ 26 - 0
parser/grammar.c

@@ -178,6 +178,9 @@ void parserCommand(PASERSSIGNATURE){
         case MATHER_LB:
         case MATHER_LP:
         case MATHER_SUB:
+        case MATHER_PROTECT:
+        case MATHER_PRIVATE:
+        case MATHER_PUBLIC:
             status = commandCallBack_(CALLPASERSSIGNATURE, parserOperation, OPERATION, &st,
                                       "Command: call operation\n");
             break;
@@ -928,6 +931,29 @@ void parserBaseValue(PASERSSIGNATURE){
         }
         st = makeBaseDictStatement(pt, value_token->line, pm->file);
     }
+    else if (MATHER_PROTECT == value_token->token_type || MATHER_PRIVATE == value_token->token_type || MATHER_PUBLIC == value_token->token_type){
+        if (MATHER_COLON != readBackToken(pm)){
+            syntaxError(pm, syntax_error, value_token->line, 1, "Don't get a : after aut token");
+            freeToken(value_token, true, true);
+            goto return_;
+        }
+        delToken(pm);
+        if (!callChildStatement(CALLPASERSSIGNATURE, parserBaseValue, BASEVALUE, &st, "Don't get Base Value after aut token")){
+            freeToken(value_token, true, true);
+            goto return_;
+        }
+        switch (value_token->token_type) {
+            case MATHER_PROTECT:
+                st->aut = protect_aut;
+                break;
+            case MATHER_PRIVATE:
+                st->aut = private_aut;
+                break;
+            case MATHER_PUBLIC:
+                st->aut = public_aut;
+                break;
+        }
+    }
     else{
         writeLog_(pm->grammar_debug, GRAMMAR_DEBUG, "Base Value: else\n", NULL);
         backToken_(pm, value_token);

+ 16 - 5
src/parameter.c

@@ -268,7 +268,7 @@ ResultType argumentToVar(Argument **call_ad, NUMBER_TYPE *num, INTER_FUNCTIONSIG
  * @return
  */
 ResultType parameterFromVar(Parameter **function_ad, VarList *function_var, NUMBER_TYPE *num, NUMBER_TYPE max, bool *status,
-                        INTER_FUNCTIONSIG_NOT_ST) {
+                            INTER_FUNCTIONSIG_NOT_ST) {
     Parameter *function = *function_ad;
     bool get = true;
     setResultCore(result);
@@ -307,9 +307,19 @@ ResultType parameterFromVar(Parameter **function_ad, VarList *function_var, NUMB
                 goto not_return;
             }
             setResultError(result, inter, "ArgumentException", "Too less Argument", name, father, true);
-            *function_ad = function;
-            return result->type;
+            goto reutnr_;
+        }
+        else if ((name->aut == public_aut || name->aut == auto_aut) && (value->aut != public_aut && value->aut != auto_aut)) {
+            setResultError(result, inter, "PermissionsException", "Wrong Permissions: access Argument as public", name,
+                           father, true);
+            goto reutnr_;
+        }
+        else if ((name->aut == protect_aut) && (value->aut == private_aut)) {
+            setResultError(result, inter, "PermissionsException", "Wrong Permissions: access variables as protect",
+                           name, father, true);
+            goto reutnr_;
         }
+        value = copyLinkValue(value, inter);
 
         not_return:
         freeResult(result);
@@ -327,6 +337,7 @@ ResultType parameterFromVar(Parameter **function_ad, VarList *function_var, NUMB
     }
 
     setResult(result, inter, father);
+    reutnr_:
     *function_ad = function;
     return result->type;
 }
@@ -420,7 +431,7 @@ Argument *getArgument(Parameter *call, INTER_FUNCTIONSIG_NOT_ST){
  * @param var_list
  * @return
  */
-ResultType setParameter(Parameter *call_base, Parameter *function_base, VarList *function_var, INTER_FUNCTIONSIG_NOT_ST) {
+ResultType setParameter(Parameter *call_base, Parameter *function_base, VarList *function_var, LinkValue *function_father, INTER_FUNCTIONSIG_NOT_ST) {
     Argument *call = NULL;
     setResultCore(result);
     call = getArgument(call_base, CALL_INTER_FUNCTIONSIG_NOT_ST (var_list, result, father));
@@ -430,7 +441,7 @@ ResultType setParameter(Parameter *call_base, Parameter *function_base, VarList
     }
 
     freeResult(result);
-    setParameterCore(call, function_base, function_var, CALL_INTER_FUNCTIONSIG_NOT_ST (var_list, result, father));
+    setParameterCore(call, function_base, function_var, CALL_INTER_FUNCTIONSIG_NOT_ST (var_list, result, function_father));
     freeArgument(call, false);
     return result->type;
 }

+ 2 - 0
src/run.c

@@ -75,6 +75,8 @@ ResultType runStatement(INTER_FUNCTIONSIG) {
             break;
     }
 
+    if (result->value->aut == auto_aut)
+        result->value->aut = st->aut;
     runGC(inter, 1, 0, 0, var_list);
     return type;
 }

+ 2 - 2
src/runcall.c

@@ -122,7 +122,7 @@ ResultType callFunction(LinkValue *function_value, Parameter *parameter, INTER_F
     gcAddTmp(&function_var->hashtable->gc_status);
     runFREEZE(inter, var_list, function_var, true);
 
-    setParameter(parameter, function_value->value->data.function.pt, function_var, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, father));
+    setParameter(parameter, function_value->value->data.function.pt, function_var, function_value, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, father));  // TODO-szh 设置双father
     if (!run_continue(result)) {
         gcAddTmp(&function_var->hashtable->gc_status);
         runFREEZE(inter, var_list, function_var, false);
@@ -131,7 +131,7 @@ ResultType callFunction(LinkValue *function_value, Parameter *parameter, INTER_F
     }
 
     freeResult(result);
-    functionSafeInterStatement(CALL_INTER_FUNCTIONSIG(function_value->value->data.function.function, function_var, result, father));
+    functionSafeInterStatement(CALL_INTER_FUNCTIONSIG(function_value->value->data.function.function, function_var, result, function_value));
 
     gcFreeTmpLink(&function_var->hashtable->gc_status);
     runFREEZE(inter, var_list, function_var, false);

+ 30 - 10
src/runoperation.c

@@ -165,13 +165,19 @@ ResultType pointOperation(INTER_FUNCTIONSIG) {
     out_var->next = left->value->object.out_var;
 
     runFREEZE(inter, var_list, object, true);
-    operationSafeInterStatement(CALL_INTER_FUNCTIONSIG(st->u.operation.right, object, result, left));
-    if (run_continue(result))
-        result->value->father = left;
+    operationSafeInterStatement(CALL_INTER_FUNCTIONSIG(st->u.operation.right, object, result, left));  // TODO-szh father设定 (添加参数规定若获得var的位置位于times后则自动设置father)
+    if (!run_continue(result))
+        goto return_;
+    else if ((left->aut == public_aut || left->aut == auto_aut) && (result->value->aut != public_aut && result->value->aut != auto_aut))
+        setResultError(result, inter, "PermissionsException", "Wrong Permissions: access variables as public", st, father, true);
+    else if ((left->aut == protect_aut) && (result->value->aut == private_aut))
+        setResultError(result, inter, "PermissionsException", "Wrong Permissions: access variables as protect", st, father, true);
+    result->value->father = left;  // 保留原father.father,为left.father
+
+    return_:
     runFREEZE(inter, var_list, object, false);
     if (out_var != NULL)
         out_var->next = NULL;
-
     gcFreeTmpLink(&left->gc_status);
     return result->type;
 }
@@ -226,7 +232,10 @@ ResultType assCore(Statement *name, LinkValue *value, INTER_FUNCTIONSIG_NOT_ST){
             memFree(str_name);
             return result->type;
         }
-        addFromVarList(str_name, result->value, int_times, value, CALL_INTER_FUNCTIONSIG_CORE(var_list));
+        LinkValue *var_value = copyLinkValue(value, inter);
+        if (var_value->aut == auto_aut)
+            var_value->aut = name->aut;
+        addFromVarList(str_name, copyLinkValue(result->value, inter), int_times, var_value, CALL_INTER_FUNCTIONSIG_CORE(var_list));
         memFree(str_name);
         freeResult(result);
 
@@ -250,9 +259,9 @@ ResultType pointAss(Statement *name, LinkValue *value, INTER_FUNCTIONSIG_NOT_ST)
     VarList *object = left.value->value->object.var;
     runFREEZE(inter, var_list, object, true);
     if (name->u.operation.right->type == OPERATION && name->u.operation.right->u.operation.OperationType == OPT_POINT)
-        pointAss(name->u.operation.right, value, CALL_INTER_FUNCTIONSIG_NOT_ST (object, result, father));
+        pointAss(name->u.operation.right, value, CALL_INTER_FUNCTIONSIG_NOT_ST(object, result, father));
     else
-        assCore(name->u.operation.right, value, CALL_INTER_FUNCTIONSIG_NOT_ST (object, result, father));
+        assCore(name->u.operation.right, value, CALL_INTER_FUNCTIONSIG_NOT_ST(object, result, father));
     runFREEZE(inter, var_list, object, true);
 
     freeResult(&left);
@@ -273,14 +282,25 @@ ResultType getVar(INTER_FUNCTIONSIG, VarInfo var_info) {
     freeResult(result);
     result->type = operation_return;
     result->value = findFromVarList(name, var_list, int_times, false);
-
-    if (result->value == NULL){
+    if (result->value == NULL) {
         char *info = memStrcat("Name Not Found: ", name, false);
         setResultError(result, inter, "NameException", info, st, father, true);
         memFree(info);
     }
+    else if ((st->aut == public_aut) && (result->value->aut != public_aut && result->value->aut != auto_aut)){
+        setResultCore(result);
+        char *info = memStrcat("Wrong Permissions: access variables as public ", name, false);
+        setResultError(result, inter, "PermissionsException", info, st, father, true);
+        memFree(info);
+    }
+    else if ((st->aut == protect_aut) && (result->value->aut == private_aut)){
+        setResultCore(result);
+        char *info = memStrcat("Wrong Permissions: access variables as protect ", name, false);
+        setResultError(result, inter, "PermissionsException", info, st, father, true);
+        memFree(info);
+    }
     else
-        gcAddTmp(&result->value->gc_status);
+        setResultOperationBase(result, copyLinkValue(result->value, inter), inter);
 
     memFree(name);
     return result->type;

+ 1 - 0
src/statement.c

@@ -4,6 +4,7 @@ Statement *makeStatement(long int line, char *file) {
     Statement *tmp = memCalloc(1, sizeof(Statement));
     tmp->type = start;
     tmp->next = NULL;
+    tmp->aut = auto_aut;
     tmp->line = line;
     tmp->code_file = memStrcpy(file);
     return tmp;

+ 8 - 2
src/value.c

@@ -16,7 +16,6 @@ Value *makeObject(Inter *inter, VarList *object, VarList *out_var, FatherValue *
         tmp->gc_last = NULL;
         goto return_;
     }
-
     for (PASS; list_tmp->gc_next != NULL; list_tmp = list_tmp->gc_next)
         PASS;
 
@@ -158,12 +157,13 @@ LinkValue *makeLinkValue(Value *value, LinkValue *linkValue, Inter *inter){
 
     list_tmp->gc_next = tmp;
     tmp->gc_last = list_tmp;
+    tmp->aut = auto_aut;
 
     return_:
     return tmp;
 }
 
-LinkValue * freeLinkValue(LinkValue *value, Inter *inter){
+LinkValue *freeLinkValue(LinkValue *value, Inter *inter){
     LinkValue *return_value = NULL;
     freeBase(value, return_);
     return_value = value->gc_next;
@@ -180,6 +180,12 @@ LinkValue * freeLinkValue(LinkValue *value, Inter *inter){
     return return_value;
 }
 
+LinkValue *copyLinkValue(LinkValue *value, Inter *inter) {
+    LinkValue *tmp = makeLinkValue(value->value, value->father, inter);
+    tmp->aut = value->aut;
+    return tmp;
+}
+
 void setResultCore(Result *ru) {
     ru->type = not_return;
     ru->times = 0;