diff --git a/OMCompiler/Compiler/FrontEnd/ClassLoader.mo b/OMCompiler/Compiler/FrontEnd/ClassLoader.mo index c7c5a04d658..eb4ac1ebc3b 100644 --- a/OMCompiler/Compiler/FrontEnd/ClassLoader.mo +++ b/OMCompiler/Compiler/FrontEnd/ClassLoader.mo @@ -211,6 +211,7 @@ algorithm encodingfile = stringAppendList({path,pd,name,pd,"package.encoding"}); encoding = System.trimChar(System.trimChar(if System.regularFileExists(encodingfile) then System.readFile(encodingfile) else Util.getOptionOrDefault(optEncoding,"UTF-8"),"\n")," "); + lveInstance = NONE(); if encrypted then (lveStarted, lveInstance) = Parser.startLibraryVendorExecutable(path + pd + name); if not lveStarted then diff --git a/OMCompiler/Compiler/FrontEnd/Parser.mo b/OMCompiler/Compiler/FrontEnd/Parser.mo index 232d7c3bd92..8a0ade8da2a 100644 --- a/OMCompiler/Compiler/FrontEnd/Parser.mo +++ b/OMCompiler/Compiler/FrontEnd/Parser.mo @@ -52,6 +52,7 @@ import AbsynToSCode; import System; import Testsuite; import Util; +import List; public @@ -61,10 +62,25 @@ function parse "Parse a mo-file" input String libraryPath = ""; input Option lveInstance = NONE(); output Absyn.Program outProgram; +protected + list classes, classes1; + Absyn.Within w; + Absyn.Class cs; algorithm outProgram := parsebuiltin(filename,encoding,libraryPath,lveInstance); /* Check that the program is not totally off the charts */ _ := AbsynToSCode.translateAbsyn2SCode(outProgram); + // Check license features + if (isSome(lveInstance)) then + Absyn.PROGRAM(classes, w) := outProgram; + classes1 := {}; + for cs in classes loop + if checkLicenseAndFeatures(cs, lveInstance) then + classes1 := cs :: classes1; + end if; + end for; + outProgram := Absyn.PROGRAM(classes1, w); + end if; end parse; function parseexp "Parse a mos-file" @@ -245,5 +261,226 @@ algorithm end if; end loadFileThread; +public function checkLicenseAndFeatures + input Absyn.Class c1; + input Option lveInstance = NONE(); + output Boolean result; +protected + list orFeatures; + list andFeatures; +algorithm + // check license + //print("Parser.checkLVEToolLicense returned = " + boolString(Parser.checkLVEToolLicense(lveInstance, AbsynUtil.getClassName(c1))) + "\n"); + //(libraryKey, licenseFile) := getLicenseAnnotation(c1); + //print("Library Key is : " + libraryKey + "\n"); + //print("License File is : " + licenseFile + "\n"); + + // annotation(Protection(features={"LicenseOption1 LicenseOption2", "LicenseOption3"})); + // For above annotation. Requires license features ("LicenseOption1" and "LicenseOption2") or "LicenseOption3" + result := true; + orFeatures := getFeaturesAnnotation(c1); + for orFeature in orFeatures loop + andFeatures := Util.stringSplitAtChar(orFeature, " "); + result := true; + for andFeature in andFeatures loop + if not checkLVEToolFeature(lveInstance, andFeature) then + result := false; + break; + end if; + end for; + // If we one of the feature is there then do not look for other features. + // If the features vector has more than one element, then at least a license feature according to one of the elements must be present + if result then + break; + end if; + end for; +end checkLicenseAndFeatures; + +protected function getLicenseAnnotation + "Returns the Protection(License=) annotation of a class. + This is annotated with the annotation: + annotation(Protection(License(libraryKey=\"15783-A39323-498222-444ckk4ll\", licenseFile=\"MyLibraryAuthorization_Tool.mo_lic\"))); in the class definition" + input Absyn.Class className; + output tuple license; +protected + Option> opt_license; +algorithm + opt_license := AbsynUtil.getNamedAnnotationInClass(className, Absyn.IDENT("Protection"), getLicenseAnnotationWork1); + license := Util.getOptionOrDefault(opt_license, ("", "")); +end getLicenseAnnotation; + +protected function getLicenseAnnotationWork1 + "Extractor function for getLicenseAnnotation" + input Option mod; + output tuple license; +algorithm + license := match (mod) + local + list arglst; + String libraryKey, licenseFile; + + case (SOME(Absyn.CLASSMOD(elementArgLst = arglst))) + equation + (libraryKey, licenseFile) = getLicenseAnnotationWork2(arglst); + then (libraryKey, licenseFile); + end match; +end getLicenseAnnotationWork1; + +protected function getLicenseAnnotationWork2 + "Extractor function for getLicenseAnnotation" + input list eltArgs; + output tuple license; +algorithm + license := match eltArgs + local + Option mod; + list xs; + String libraryKey, licenseFile; + + case ({}) then ("", ""); + + case (Absyn.MODIFICATION(path = Absyn.IDENT(name="License"), modification = mod)::_) + equation + (libraryKey, licenseFile) = getLicenseAnnotationTuple(mod); + then (libraryKey, licenseFile); + + case (_::xs) + equation + (libraryKey, licenseFile) = getLicenseAnnotationWork2(xs); + then (libraryKey, licenseFile); + + end match; +end getLicenseAnnotationWork2; + +protected function getLicenseAnnotationTuple + "Extractor function for getLicenseAnnotation" + input Option mod; + output tuple license; +algorithm + license := match (mod) + local + list arglst; + String libraryKey, licenseFile; + + case (SOME(Absyn.CLASSMOD(elementArgLst = arglst))) + equation + libraryKey = getLicenseAnnotationLibraryKey(arglst); + licenseFile = getLicenseAnnotationLicenseFile(arglst); + then (libraryKey, licenseFile); + end match; +end getLicenseAnnotationTuple; + +protected function getLicenseAnnotationLibraryKey + "Extractor function for getLicenseAnnotation" + input list eltArgs; + output String libraryKey; +algorithm + libraryKey := match eltArgs + local + list xs; + String s; + + case ({}) then ""; + + case (Absyn.MODIFICATION(path = Absyn.IDENT(name="libraryKey"), modification = SOME(Absyn.CLASSMOD(eqMod=Absyn.EQMOD(exp=Absyn.STRING(s)))))::_) + then s; + + case (_::xs) + equation + s = getLicenseAnnotationLibraryKey(xs); + then s; + + end match; +end getLicenseAnnotationLibraryKey; + +protected function getLicenseAnnotationLicenseFile + "Extractor function for getLicenseAnnotation" + input list eltArgs; + output String licenseFile; +algorithm + licenseFile := match eltArgs + local + list xs; + String s; + + case ({}) then ""; + + case (Absyn.MODIFICATION(path = Absyn.IDENT(name="licenseFile"), modification = SOME(Absyn.CLASSMOD(eqMod=Absyn.EQMOD(exp=Absyn.STRING(s)))))::_) + then s; + + case (_::xs) + equation + s = getLicenseAnnotationLicenseFile(xs); + then s; + + end match; +end getLicenseAnnotationLicenseFile; + +protected function getFeaturesAnnotation + "Returns the Protection(features=) annotation of a class. + This is annotated with the annotation: + annotation(Protection(features={\"LicenseOption1 LicenseOption2\", \"LicenseOption3\"})); in the class definition" + input Absyn.Class className; + output list features; +protected + Option> opt_featuresList; +algorithm + opt_featuresList := AbsynUtil.getNamedAnnotationInClass(className, Absyn.IDENT("Protection"), getFeaturesAnnotationList); + features := Util.getOptionOrDefault(opt_featuresList, {}); +end getFeaturesAnnotation; + +protected function getFeaturesAnnotationList + "Extractor function for getFeaturesAnnotation" + input Option mod; + output list features; +algorithm + features := match (mod) + local + list arglst; + + case (SOME(Absyn.CLASSMOD(elementArgLst = arglst))) + then getFeaturesAnnotationList2(arglst); + + end match; +end getFeaturesAnnotationList; + +protected function getFeaturesAnnotationList2 + "Extractor function for getFeaturesAnnotation" + input list eltArgs; + output list features; +algorithm + features := match eltArgs + local + list expList; + list xs; + list featuresList; + + case ({}) then {}; + + case (Absyn.MODIFICATION(path = Absyn.IDENT(name="features"), modification = SOME(Absyn.CLASSMOD(eqMod=Absyn.EQMOD(exp=Absyn.ARRAY(expList)))))::_) + equation + featuresList = List.map(expList, expToString); + then featuresList; + + case (_::xs) + equation + featuresList = getFeaturesAnnotationList2(xs); + then featuresList; + + end match; +end getFeaturesAnnotationList2; + +protected function expToString + input Absyn.Exp inExp; + output String outExp; +algorithm + outExp := match (inExp) + local + String str; + case (Absyn.STRING(str)) then str; + case (_) then ""; + end match; +end expToString; + annotation(__OpenModelica_Interface="frontend"); end Parser; diff --git a/OMCompiler/Compiler/Script/CevalScript.mo b/OMCompiler/Compiler/Script/CevalScript.mo index 4ffa73a18f4..f117331d6a4 100644 --- a/OMCompiler/Compiler/Script/CevalScript.mo +++ b/OMCompiler/Compiler/Script/CevalScript.mo @@ -400,7 +400,6 @@ algorithm if pathToFile=="" then pnew := ClassLoader.loadClass(path, versionsLst, thisModelicaPath, NONE(), requireExactVersion, encrypted); else - pnew := ClassLoader.loadClass(path, versionsLst, thisModelicaPath, NONE(), requireExactVersion, encrypted); dir := System.dirname(pathToFile); pnew := Absyn.PROGRAM({ClassLoader.loadClassFromMp(AbsynUtil.pathFirstIdent(path), System.dirname(dir), System.basename(dir), true, NONE(), encrypted)}, Absyn.TOP()); end if; diff --git a/OMCompiler/Compiler/Script/Interactive.mo b/OMCompiler/Compiler/Script/Interactive.mo index 2a7bae82d8f..c505bd977cf 100644 --- a/OMCompiler/Compiler/Script/Interactive.mo +++ b/OMCompiler/Compiler/Script/Interactive.mo @@ -17521,20 +17521,6 @@ algorithm parsed := MetaUtil.createMetaClassesInProgram(parsed); topClassNamesQualified := getTopQualifiedClassnames(parsed); if (lveStarted) then - for topClassNameQualified in topClassNamesQualified loop - // check license - //print("Parser.checkLVEToolLicense returned = " + boolString(Parser.checkLVEToolLicense(lveInstance, AbsynUtil.pathString(topClassNameQualified))) + "\n"); - //(libraryKey, licenseFile) := getLicenseAnnotation(topClassNameQualified, parsed); - //print("Library Key is : " + libraryKey + "\n"); - //print("License File is : " + licenseFile + "\n"); - features := getFeaturesAnnotation(topClassNameQualified, parsed); - for feature in features loop - if not Parser.checkLVEToolFeature(lveInstance, feature) then - topClassNamesQualified := {}; - return; - end if; - end for; - end for; Parser.stopLibraryVendorExecutable(lveInstance); end if; if updateProgram then @@ -18467,209 +18453,6 @@ algorithm end match; end getAccessAnnotationString2; -public function getLicenseAnnotation - "Returns the Protection(License=) annotation of a class. - This is annotated with the annotation: - annotation(Protection(License(libraryKey=\"15783-A39323-498222-444ckk4ll\", licenseFile=\"MyLibraryAuthorization_Tool.mo_lic\"))); in the class definition" - input Absyn.Path className; - input Absyn.Program p; - output tuple license; -algorithm - license := match(className,p) - local - tuple licenseAnn; - case(_,_) - equation - licenseAnn = getNamedAnnotation(className, p, Absyn.IDENT("Protection"), SOME(("","")), getLicenseAnnotationWork1); - then - licenseAnn; - else ("", ""); - end match; -end getLicenseAnnotation; - -protected function getLicenseAnnotationWork1 - "Extractor function for getLicenseAnnotation" - input Option mod; - output tuple license; -algorithm - license := match (mod) - local - list arglst; - String libraryKey, licenseFile; - - case (SOME(Absyn.CLASSMOD(elementArgLst = arglst))) - equation - (libraryKey, licenseFile) = getLicenseAnnotationWork2(arglst); - then (libraryKey, licenseFile); - end match; -end getLicenseAnnotationWork1; - -protected function getLicenseAnnotationWork2 - "Extractor function for getLicenseAnnotation" - input list eltArgs; - output tuple license; -algorithm - license := match eltArgs - local - Option mod; - list xs; - String libraryKey, licenseFile; - - case ({}) then ("", ""); - - case (Absyn.MODIFICATION(path = Absyn.IDENT(name="License"), modification = mod)::_) - equation - (libraryKey, licenseFile) = getLicenseAnnotationTuple(mod); - then (libraryKey, licenseFile); - - case (_::xs) - equation - (libraryKey, licenseFile) = getLicenseAnnotationWork2(xs); - then (libraryKey, licenseFile); - - end match; -end getLicenseAnnotationWork2; - -protected function getLicenseAnnotationTuple - "Extractor function for getLicenseAnnotation" - input Option mod; - output tuple license; -algorithm - license := match (mod) - local - list arglst; - String libraryKey, licenseFile; - - case (SOME(Absyn.CLASSMOD(elementArgLst = arglst))) - equation - libraryKey = getLicenseAnnotationLibraryKey(arglst); - licenseFile = getLicenseAnnotationLicenseFile(arglst); - then (libraryKey, licenseFile); - end match; -end getLicenseAnnotationTuple; - -protected function getLicenseAnnotationLibraryKey - "Extractor function for getLicenseAnnotation" - input list eltArgs; - output String libraryKey; -algorithm - libraryKey := match eltArgs - local - list xs; - String s; - - case ({}) then ""; - - case (Absyn.MODIFICATION(path = Absyn.IDENT(name="libraryKey"), - modification = SOME(Absyn.CLASSMOD(eqMod=Absyn.EQMOD(exp=Absyn.STRING(s)))))::_) - then s; - - case (_::xs) - equation - s = getLicenseAnnotationLibraryKey(xs); - then s; - - end match; -end getLicenseAnnotationLibraryKey; - -protected function getLicenseAnnotationLicenseFile - "Extractor function for getLicenseAnnotation" - input list eltArgs; - output String licenseFile; -algorithm - licenseFile := match eltArgs - local - list xs; - String s; - - case ({}) then ""; - - case (Absyn.MODIFICATION(path = Absyn.IDENT(name="licenseFile"), - modification = SOME(Absyn.CLASSMOD(eqMod=Absyn.EQMOD(exp=Absyn.STRING(s)))))::_) - then s; - - case (_::xs) - equation - s = getLicenseAnnotationLicenseFile(xs); - then s; - - end match; -end getLicenseAnnotationLicenseFile; - -public function getFeaturesAnnotation - "Returns the Protection(features=) annotation of a class. - This is annotated with the annotation: - annotation(Protection(features={\"LicenseOption1 LicenseOption2\", \"LicenseOption3\"})); in the class definition" - input Absyn.Path className; - input Absyn.Program p; - output list features; -algorithm - features := match(className,p) - local - list featuresList; - case(_,_) - equation - featuresList = getNamedAnnotation(className, p, Absyn.IDENT("Protection"), SOME({}), getFeaturesAnnotationList); - then - featuresList; - else {}; - end match; -end getFeaturesAnnotation; - -protected function getFeaturesAnnotationList - "Extractor function for getFeaturesAnnotation" - input Option mod; - output list features; -algorithm - features := match (mod) - local - list arglst; - - case (SOME(Absyn.CLASSMOD(elementArgLst = arglst))) - then getFeaturesAnnotationList2(arglst); - - end match; -end getFeaturesAnnotationList; - -protected function getFeaturesAnnotationList2 - "Extractor function for getFeaturesAnnotation" - input list eltArgs; - output list features; -algorithm - features := match eltArgs - local - list expList; - list xs; - list featuresList; - - case ({}) then {}; - - case (Absyn.MODIFICATION(path = Absyn.IDENT(name="features"), - modification = SOME(Absyn.CLASSMOD(eqMod=Absyn.EQMOD(exp=Absyn.ARRAY(expList)))))::_) - equation - featuresList = List.map(expList, expToString); - then featuresList; - - case (_::xs) - equation - featuresList = getFeaturesAnnotationList2(xs); - then featuresList; - - end match; -end getFeaturesAnnotationList2; - -protected function expToString - input Absyn.Exp inExp; - output String outExp; -algorithm - outExp := match (inExp) - local - String str; - case (Absyn.STRING(str)) then str; - case (_) then ""; - end match; -end expToString; - public function checkAccessAnnotationAndEncryption input Absyn.Path path; input Absyn.Program p;