3 import java_cup.runtime.ComplexSymbolFactory;
4 import java_cup.runtime.ScannerBuffer;
6 import java.util.Collection;
7 import java.util.Collections;
8 import java.util.HashMap;
9 import java.util.HashSet;
10 import java.util.List;
14 import iotpolicy.parser.Lexer;
15 import iotpolicy.parser.Parser;
16 import iotpolicy.tree.ParseNode;
17 import iotpolicy.tree.ParseNodeVector;
18 import iotpolicy.tree.ParseTreeHandler;
19 import iotpolicy.tree.CapabilityDecl;
20 import iotpolicy.tree.InterfaceDecl;
21 import iotpolicy.tree.RequiresDecl;
23 /** Class IoTCompiler is the main interface/stub compiler for
24 * files generation. This class calls helper classes
25 * such as Parser, Lexer, InterfaceDecl, CapabilityDecl,
26 * RequiresDecl, ParseTreeHandler, etc.
28 * @author Rahmadi Trimananda <rahmadi.trimananda @ uci.edu>
32 public class IoTCompiler {
37 private String origInt;
38 private ParseTreeHandler ptHandler;
39 private InterfaceDecl intDecl;
40 private CapabilityDecl capDecl;
41 private RequiresDecl reqDecl;
42 private Map<String,Set<String>> mapCapabMethods;
43 // Data structure to store our types (primitives and non-primitives) for compilation
44 //private Set<String> setPrimitives;
45 private Map<String,String> mapPrimitives;
46 private Map<String,String> mapNonPrimitivesJava;
47 private Map<String,String> mapNonPrimitivesCplus;
48 private PrintWriter pw;
50 private String subdir;
55 private final static String OUTPUT_DIRECTORY = "output_files";
58 * Primitive data types
60 private final static String[] primitives = new String[] {
84 * Primitive data types in C++ to map the primitives list
86 private final static String[] primitivesCplus = new String[] {
110 * Non-primitive data types supported by this compiler
112 private final static String[] nonPrimitives = new String[] {
123 * Non-primitive Java libraries based on the list above
125 private final static String[] nonPrimitiveJavaLibs = new String[] {
132 "java.util.ArrayList"
136 * Non-primitive C++ libraries based on the list above
138 private final static String[] nonPrimitiveCplusLibs = new String[] {
148 private enum ParamCategory {
150 PRIMITIVES, // All the primitive types, e.g. byte, short, int, long, etc.
151 NONPRIMITIVES, // Non-primitive types, e.g. Set, Map, List, etc.
152 USERDEFINED // Non-supported type by default; assumed as driver classes
158 public IoTCompiler() {
161 ptHandler = new ParseTreeHandler();
165 mapCapabMethods = new HashMap<String,Set<String>>();
166 mapPrimitives = new HashMap<String,String>();
167 arraysToMap(mapPrimitives, primitives, primitivesCplus);
168 mapNonPrimitivesJava = new HashMap<String,String>();
169 arraysToMap(mapNonPrimitivesJava, nonPrimitives, nonPrimitiveJavaLibs);
170 mapNonPrimitivesCplus = new HashMap<String,String>();
171 arraysToMap(mapNonPrimitivesCplus, nonPrimitives, nonPrimitiveCplusLibs);
173 dir = OUTPUT_DIRECTORY;
178 public IoTCompiler(String _origInt, ParseNode _pnPol, ParseNode _pnReq) {
181 ptHandler = new ParseTreeHandler(_origInt, _pnPol, _pnReq);
185 mapCapabMethods = new HashMap<String,Set<String>>();
186 mapPrimitives = new HashMap<String,String>();
187 arraysToMap(mapPrimitives, primitives, primitivesCplus);
188 mapNonPrimitivesJava = new HashMap<String,String>();
189 arraysToMap(mapNonPrimitivesJava, nonPrimitives, nonPrimitiveJavaLibs);
190 mapNonPrimitivesCplus = new HashMap<String,String>();
191 arraysToMap(mapNonPrimitivesCplus, nonPrimitives, nonPrimitiveCplusLibs);
193 dir = OUTPUT_DIRECTORY;
199 * parsePolicyFile() parses policy file
201 * It also generates parse tree and
202 * copies useful information from parse tree into
203 * InterfaceDecl, CapabilityDecl, and RequiresDecl
205 * Additionally, the data structure handles are
206 * returned from tree-parsing for further process.
209 public void parsePolicyFile() {
211 ptHandler.processInterfaceDecl();
212 intDecl = ptHandler.getInterfaceDecl();
214 ptHandler.processCapabilityDecl();
215 capDecl = ptHandler.getCapabilityDecl();
217 ptHandler.processRequiresDecl();
218 reqDecl = ptHandler.getRequiresDecl();
223 * getMethodsForIntface() reads for methods in the data structure
225 * It is going to give list of methods for a certain interface
226 * based on the declaration of capabilities.
228 public void getMethodsForIntface() {
230 // Get set of new interfaces, e.g. CameraWithCaptureAndData
231 // Generate this new interface with all the methods it needs
232 // from different capabilities it declares
233 Set<String> setIntfaces = reqDecl.getInterfaces();
234 for (String strInt : setIntfaces) {
236 // Initialize a set of methods
237 Set<String> setMethods = new HashSet<String>();
238 // Get list of capabilities, e.g. ImageCapture, VideoRecording, etc.
239 List<String> listCapab = reqDecl.getCapabList(strInt);
240 for (String strCap : listCapab) {
242 // Get list of methods for each capability
243 List<String> listCapabMeth = capDecl.getMethods(strCap);
244 for (String strMeth : listCapabMeth) {
246 // Add methods into setMethods
247 // This is to also handle redundancies (say two capabilities
248 // share the same methods)
249 setMethods.add(strMeth);
252 // Add interface and methods information into map
253 mapCapabMethods.put(strInt, setMethods);
259 * generateJavaLocalInterface() writes the local interface to provide type-checking
261 * It needs to rewrite and exchange USERDEFINED types in input parameters of stub
262 * and original interfaces, e.g. exchange Camera and CameraWithVideoAndRecording.
263 * The local interface has to be the input parameter for the stub and the stub
264 * interface has to be the input parameter for the local class.
266 public void generateJavaLocalInterface() throws IOException {
268 // Create a new directory
269 createDirectory(dir);
270 // Open a new file to write into
271 String intface = origInt;
272 FileWriter fw = new FileWriter(dir + "/" + intface + ".java");
273 pw = new PrintWriter(new BufferedWriter(fw));
274 // Pass in set of methods and get import classes
275 List<String> methods = intDecl.getMethods();
276 Set<String> importClasses = getImportClasses(methods);
277 printImportStatements(importClasses);
278 // Write interface header
280 println("public interface " + intface + " {");
282 for (String method : methods) {
284 List<String> methParams = intDecl.getMethodParams(method);
285 List<String> methPrmTypes = intDecl.getMethodParamTypes(method);
286 print("public " + intDecl.getMethodType(method) + " " +
287 intDecl.getMethodId(method) + "(");
288 for (int i = 0; i < methParams.size(); i++) {
289 // Check for params with driver class types and exchange it
290 // with its remote interface
291 String paramType = checkAndGetParamClass(methPrmTypes.get(i));
292 print(paramType + " " + methParams.get(i));
293 // Check if this is the last element (don't print a comma)
294 if (i != methParams.size() - 1) {
302 System.out.println("IoTCompiler: Generated local interface " + intface + ".java...");
307 * generateCplusLocalInterface() writes the local interface to provide type-checking
309 * It needs to rewrite and exchange USERDEFINED types in input parameters of stub
310 * and original interfaces, e.g. exchange Camera and CameraWithVideoAndRecording.
311 * The local interface has to be the input parameter for the stub and the stub
312 * interface has to be the input parameter for the local class.
314 public void generateCplusLocalInterface() throws IOException {
316 // Create a new directory
317 createDirectory(dir);
318 // Open a new file to write into
319 String intface = origInt;
320 FileWriter fw = new FileWriter(dir + "/" + intface + ".hpp");
321 pw = new PrintWriter(new BufferedWriter(fw));
322 // Write file headers
323 println("#include <iostream>");
324 // Pass in set of methods and get import classes
325 List<String> methods = intDecl.getMethods();
326 Set<String> includeClasses = getIncludeClasses(methods);
327 printIncludeStatements(includeClasses);
329 println("using namespace std;");
331 println("class " + intface);
335 for (String method : methods) {
337 List<String> methParams = intDecl.getMethodParams(method);
338 List<String> methPrmTypes = intDecl.getMethodParamTypes(method);
339 print("virtual " + convertType(intDecl.getMethodType(method)) + " " +
340 intDecl.getMethodId(method) + "(");
341 for (int i = 0; i < methParams.size(); i++) {
342 // Check for params with driver class types and exchange it
343 // with its remote interface
344 String paramType = checkAndGetParamClass(methPrmTypes.get(i));
345 paramType = checkAndGetCplusType(paramType);
346 print(paramType + " " + methParams.get(i));
347 // Check if this is the last element (don't print a comma)
348 if (i != methParams.size() - 1) {
357 System.out.println("IoTCompiler: Generated local interface " + intface + ".hpp...");
362 * generateJavaInterfaces() generate stub interfaces based on the methods list in Java
364 public void generateJavaInterfaces() throws IOException {
366 // Create a new directory
367 createDirectories(dir, subdir);
368 for (Map.Entry<String,Set<String>> intMeth : mapCapabMethods.entrySet()) {
370 // Open a new file to write into
371 String newIntface = intMeth.getKey();
372 FileWriter fw = new FileWriter(dir + "/" + subdir + "/" + newIntface + ".java");
373 pw = new PrintWriter(new BufferedWriter(fw));
374 // Pass in set of methods and get import classes
375 Set<String> importClasses = getImportClasses(intMeth.getValue());
376 printImportStatements(importClasses);
377 // Write interface header
379 println("public interface " + newIntface + " {");
380 List<String> meths = intDecl.getMethods();
382 for (String method : intMeth.getValue()) {
384 List<String> methParams = intDecl.getMethodParams(method);
385 List<String> methPrmTypes = intDecl.getMethodParamTypes(method);
386 print("public " + intDecl.getMethodType(method) + " " +
387 intDecl.getMethodId(method) + "(");
388 for (int i = 0; i < methParams.size(); i++) {
389 print(methPrmTypes.get(i) + " " + methParams.get(i));
390 // Check if this is the last element (don't print a comma)
391 if (i != methParams.size() - 1) {
399 System.out.println("IoTCompiler: Generated interface " + newIntface + ".java...");
405 * generateCPlusInterfaces() generate stub interfaces based on the methods list in C++
407 * For C++ we use virtual classe as interface
409 public void generateCPlusInterfaces() throws IOException {
411 // Create a new directory
412 createDirectories(dir, subdir);
413 for (Map.Entry<String,Set<String>> intMeth : mapCapabMethods.entrySet()) {
415 // Open a new file to write into
416 String newIntface = intMeth.getKey();
417 FileWriter fw = new FileWriter(dir + "/" + subdir + "/" + newIntface + ".hpp");
418 pw = new PrintWriter(new BufferedWriter(fw));
419 // Write file headers
420 println("#include <iostream>");
421 // Pass in set of methods and get import classes
422 Set<String> includeClasses = getIncludeClasses(intMeth.getValue());
423 printIncludeStatements(includeClasses);
425 println("using namespace std;");
427 println("class " + newIntface);
431 for (String method : intMeth.getValue()) {
433 List<String> methParams = intDecl.getMethodParams(method);
434 List<String> methPrmTypes = intDecl.getMethodParamTypes(method);
435 print("virtual " + convertType(intDecl.getMethodType(method)) + " " +
436 intDecl.getMethodId(method) + "(");
437 for (int i = 0; i < methParams.size(); i++) {
439 String methPrmType = checkAndGetCplusType(methPrmTypes.get(i));
440 print(methPrmType + " " + methParams.get(i));
441 // Check if this is the last element (don't print a comma)
442 if (i != methParams.size() - 1) {
451 System.out.println("IoTCompiler: Generated interface " + newIntface + ".hpp...");
457 * generateJavaStubClasses() generate stubs based on the methods list in Java
459 public void generateJavaStubClasses() throws IOException {
461 // Create a new directory
462 createDirectories(dir, subdir);
463 for (Map.Entry<String,Set<String>> intMeth : mapCapabMethods.entrySet()) {
465 // Open a new file to write into
466 String newIntface = intMeth.getKey();
467 String newStubClass = newIntface + "_Stub";
468 FileWriter fw = new FileWriter(dir + "/" + subdir + "/" + newStubClass + ".java");
469 pw = new PrintWriter(new BufferedWriter(fw));
470 // Pass in set of methods and get import classes
471 Set<String> importClasses = getImportClasses(intMeth.getValue());
472 printImportStatements(importClasses);
473 // Write interface header
475 println("public class " + newStubClass + " implements " + newIntface + " {");
478 for (String method : intMeth.getValue()) {
480 List<String> methParams = intDecl.getMethodParams(method);
481 List<String> methPrmTypes = intDecl.getMethodParamTypes(method);
482 print("public " + intDecl.getMethodType(method) + " " +
483 intDecl.getMethodId(method) + "(");
484 for (int i = 0; i < methParams.size(); i++) {
486 print(methPrmTypes.get(i) + " " + methParams.get(i));
487 // Check if this is the last element (don't print a comma)
488 if (i != methParams.size() - 1) {
493 // Check if this is not "void"
494 if (!intDecl.getMethodType(method).equals("void")) {
495 String retStmt = generateReturnStmt(intDecl.getMethodType(method));
496 println("return " + retStmt + ";");
498 println("}"); println("");
502 System.out.println("IoTCompiler: Generated stub class " + newStubClass + ".java...");
508 * generateCPlusStubClasses() generate stubs based on the methods list in C++
510 public void generateCPlusStubClasses() throws IOException {
512 // Create a new directory
513 createDirectories(dir, subdir);
514 for (Map.Entry<String,Set<String>> intMeth : mapCapabMethods.entrySet()) {
516 // Open a new file to write into
517 String newIntface = intMeth.getKey();
518 String newStubClass = newIntface + "_Stub";
519 FileWriter fw = new FileWriter(dir + "/" + subdir + "/" + newStubClass + ".hpp");
520 pw = new PrintWriter(new BufferedWriter(fw));
521 // Write file headers
522 println("#include <iostream>");
523 println("#include \"" + newIntface + ".hpp\""); println("");
524 println("using namespace std;"); println("");
525 println("class " + newStubClass + " : public " + newIntface);
527 println("public:"); println("");
528 // Add default constructor and destructor
529 println(newStubClass + "() { }"); println("");
530 println("~" + newStubClass + "() { }"); println("");
532 for (String method : intMeth.getValue()) {
534 List<String> methParams = intDecl.getMethodParams(method);
535 List<String> methPrmTypes = intDecl.getMethodParamTypes(method);
536 print(convertType(intDecl.getMethodType(method)) + " " +
537 intDecl.getMethodId(method) + "(");
538 for (int i = 0; i < methParams.size(); i++) {
540 String methPrmType = checkAndGetCplusType(methPrmTypes.get(i));
541 print(methPrmType + " " + methParams.get(i));
542 // Check if this is the last element (don't print a comma)
543 if (i != methParams.size() - 1) {
548 // Check if this is not "void"
549 if (!intDecl.getMethodType(method).equals("void")) {
550 String retStmt = generateReturnStmt(intDecl.getMethodType(method));
551 if (retStmt.equals("null")) { // null = NULL in C++
554 println("return " + retStmt + ";");
556 println("}"); println("");
558 print("}"); println(";");
560 System.out.println("IoTCompiler: Generated stub class " + newIntface + ".hpp...");
566 * generateReturnStmt() generate return statement based on methType
568 public String generateReturnStmt(String methType) {
570 // Generate dummy returns for now
571 if (methType.equals("short")||
572 methType.equals("int") ||
573 methType.equals("long") ||
574 methType.equals("float")||
575 methType.equals("double")) {
578 } else if ( methType.equals("String") ||
579 methType.equals("byte")) {
582 } else if ( methType.equals("char")) {
585 } else if ( methType.equals("boolean")) {
595 * setDirectory() set a new directory for stub files
597 public void setDirectory(String _subdir) {
604 * printUsage() prints the usage of this compiler
606 public static void printUsage() {
608 System.out.println();
609 System.out.println("Sentinel interface and stub compiler version 1.0");
610 System.out.println("Copyright (c) 2015-2016 University of California, Irvine - Programming Language Group.");
611 System.out.println("All rights reserved.");
612 System.out.println("Usage:");
613 System.out.println("\tjava IoTCompiler --help / -h\t\t\t\t\tDisplay this help texts");
614 System.out.println("\tjava IoTCompiler <main-policy-file> <req-policy-file>\t\tGenerate both Java and C++ stub files");
615 System.out.println("\tjava IoTCompiler <main-policy-file> <req-policy-file> [options]");
616 System.out.println("Options:");
617 System.out.println("\t-java\t<directory>\tGenerate Java stub files");
618 System.out.println("\t-cplus\t<directory>\tGenerate C++ stub files");
619 System.out.println();
623 /**================================================
624 * Helper functions to write stub codes into files
625 **================================================
627 boolean newline=true;
630 private void print(String str) {
635 for(int i=0; i<tab; i++)
644 * This function converts Java to C++ type for compilation
646 private String convertType(String jType) {
648 return mapPrimitives.get(jType);
652 private void println(String str) {
657 for(int i=0; i<tab; i++)
666 private void updatetabbing(String str) {
667 tablevel+=count(str,'{')-count(str,'}');
671 private int count(String str, char key) {
672 char[] array = str.toCharArray();
674 for(int i=0; i<array.length; i++) {
682 private void createDirectory(String dirName) {
684 File file = new File(dirName);
685 if (!file.exists()) {
687 System.out.println("IoTCompiler: Directory " + dirName + " has been created!");
689 System.out.println("IoTCompiler: Failed to create directory " + dirName + "!");
692 System.out.println("IoTCompiler: Directory " + dirName + " exists...");
697 // Create a directory and possibly a sub directory
698 private void createDirectories(String dir, String subdir) {
700 createDirectory(dir);
701 if (subdir != null) {
702 createDirectory(dir + "/" + subdir);
707 // Inserting array members into a Map object
708 // that maps arrKey to arrVal objects
709 private void arraysToMap(Map map, Object[] arrKey, Object[] arrVal) {
711 for(int i = 0; i < arrKey.length; i++) {
713 map.put(arrKey[i], arrVal[i]);
718 // Return parameter category, i.e. PRIMITIVES, NONPRIMITIVES, or USERDEFINED
719 private ParamCategory getParamCategory(String paramType) {
721 if (mapPrimitives.containsKey(paramType)) {
722 return ParamCategory.PRIMITIVES;
723 // We can either use mapNonPrimitivesJava or mapNonPrimitivesCplus here
724 } else if (mapNonPrimitivesJava.containsKey(getSimpleType(paramType))) {
725 return ParamCategory.NONPRIMITIVES;
727 return ParamCategory.USERDEFINED;
731 // Return full class name for non-primitives to generate Java import statements
732 // e.g. java.util.Set for Set, java.util.Map for Map
733 private String getNonPrimitiveJavaClass(String paramNonPrimitives) {
735 return mapNonPrimitivesJava.get(paramNonPrimitives);
739 // Return full class name for non-primitives to generate Cplus include statements
740 // e.g. #include <set> for Set, #include <map> for Map
741 private String getNonPrimitiveCplusClass(String paramNonPrimitives) {
743 return mapNonPrimitivesCplus.get(paramNonPrimitives);
747 // Get simple types, e.g. HashSet for HashSet<...>
748 // Basically strip off the "<...>"
749 private String getSimpleType(String paramType) {
751 // Check if this is generics
752 if(paramType.contains("<")) {
753 String[] type = paramType.split("<");
760 // Generate a set of classes for import statements
761 private Set<String> getImportClasses(Collection<String> methods) {
763 Set<String> importClasses = new HashSet<String>();
764 for (String method : methods) {
765 List<String> methPrmTypes = intDecl.getMethodParamTypes(method);
766 for (String paramType : methPrmTypes) {
768 String simpleType = getSimpleType(paramType);
769 if (getParamCategory(simpleType) == ParamCategory.NONPRIMITIVES) {
770 importClasses.add(getNonPrimitiveJavaClass(simpleType));
774 return importClasses;
778 // Generate a set of classes for include statements
779 private Set<String> getIncludeClasses(Collection<String> methods) {
781 Set<String> includeClasses = new HashSet<String>();
782 for (String method : methods) {
784 List<String> methPrmTypes = intDecl.getMethodParamTypes(method);
785 for (String paramType : methPrmTypes) {
787 String simpleType = getSimpleType(paramType);
788 if (getParamCategory(simpleType) == ParamCategory.NONPRIMITIVES) {
789 includeClasses.add(getNonPrimitiveCplusClass(simpleType));
793 return includeClasses;
797 private void printImportStatements(Set<String> importClasses) {
799 for(String cls : importClasses) {
800 println("import " + cls + ";");
805 private void printIncludeStatements(Set<String> includeClasses) {
807 for(String cls : includeClasses) {
808 println("#include <" + cls + ">");
813 // Get the C++ version of a non-primitive type
814 // e.g. set for Set and map for Map
815 // Input nonPrimitiveType has to be generics in format
816 private String[] getTypeOfGeneric(String nonPrimitiveType) {
818 // Handle <, >, and , for 2-type generic/template
819 String[] substr = nonPrimitiveType.split("<")[1].split(">")[0].split(",");
824 private String checkAndGetCplusType(String paramType) {
826 if (getParamCategory(paramType) == ParamCategory.PRIMITIVES) {
827 return convertType(paramType);
828 } else if (getParamCategory(paramType) == ParamCategory.NONPRIMITIVES) {
830 // Check for generic/template format
831 if (paramType.contains("<") && paramType.contains(">")) {
833 String genericClass = getSimpleType(paramType);
834 String[] genericType = getTypeOfGeneric(paramType);
835 String cplusTemplate = null;
836 if (genericType.length == 1) // Generic/template with one type
837 cplusTemplate = getNonPrimitiveCplusClass(genericClass) +
838 "<" + convertType(genericType[0]) + ">";
839 else // Generic/template with two types
840 cplusTemplate = getNonPrimitiveCplusClass(genericClass) +
841 "<" + convertType(genericType[0]) + "," + convertType(genericType[1]) + ">";
842 return cplusTemplate;
844 return getNonPrimitiveCplusClass(paramType);
846 // Just return it as is if it's not non-primitives
851 // Get simple types, e.g. HashSet for HashSet<...>
852 // Basically strip off the "<...>"
853 private String checkAndGetParamClass(String paramType) {
855 // Check if this is generics
856 if(getParamCategory(paramType) == ParamCategory.USERDEFINED) {
857 // TODO: replace this with the proper stub interface name
858 return paramType + "Remote";
864 public static void main(String[] args) throws Exception {
867 if (args.length != 0) {
869 if ((args[0].equals("--help") ||
870 (args[0].equals("-h")))) {
871 IoTCompiler.printUsage();
873 // Parse main policy file
874 ComplexSymbolFactory csfPol = new ComplexSymbolFactory();
875 ScannerBuffer lexerPol =
876 new ScannerBuffer(new Lexer(new BufferedReader(new FileReader(args[0])),csfPol));
877 Parser parsePol = new Parser(lexerPol,csfPol);
878 ParseNode pnPol = (ParseNode) parsePol.parse().value;
879 // Parse "requires" policy file
880 ComplexSymbolFactory csfReq = new ComplexSymbolFactory();
881 ScannerBuffer lexerReq =
882 new ScannerBuffer(new Lexer(new BufferedReader(new FileReader(args[1])),csfReq));
883 Parser parseReq = new Parser(lexerReq,csfReq);
884 ParseNode pnReq = (ParseNode) parseReq.parse().value;
885 // Get interface name
886 String intFace = ParseTreeHandler.getOrigIntface(pnPol);
887 //System.out.println("IoTCompiler: Original interface: " + intFace);
888 IoTCompiler comp = new IoTCompiler(intFace, pnPol, pnReq);
889 // Generate all policy files if just policy file is provided
890 comp.parsePolicyFile();
891 comp.getMethodsForIntface();
892 if (args.length == 2) {
893 comp.generateJavaLocalInterface();
894 comp.generateJavaInterfaces();
895 comp.generateJavaStubClasses();
896 comp.generateCplusLocalInterface();
897 comp.generateCPlusInterfaces();
898 comp.generateCPlusStubClasses();
900 // Check other options
902 while(i < args.length) {
903 // Check whether <directory> is provided
904 if ((i + 1) < args.length) {
905 comp.setDirectory(args[i+1]);
907 throw new Error("IoTCompiler: ERROR - please provide <directory> after option: " + args[i]);
908 if (args[i].equals("-java")) {
909 comp.generateJavaLocalInterface();
910 comp.generateJavaInterfaces();
911 comp.generateJavaStubClasses();
912 } else if (args[i].equals("-cplus")) {
913 comp.generateCplusLocalInterface();
914 comp.generateCPlusInterfaces();
915 comp.generateCPlusStubClasses();
917 throw new Error("IoTCompiler: ERROR - unrecognized command line option: " + args[i]);
924 // Need at least the policy file name
925 IoTCompiler.printUsage();
926 throw new Error("IoTCompiler: At least two arguments (main and requires policy files) have to be provided!");