X-Git-Url: http://plrg.eecs.uci.edu/git/?p=iot2.git;a=blobdiff_plain;f=iotjava%2Fiotruntime%2Fmaster%2FIoTMaster.java;h=7dc41d7a2b2274c70ba2c1ccb79b1102be9ef372;hp=7578f3b332b1450790f48e23f1735a886237af2b;hb=612e0a2208677f14c86063d7354e5aa9eaea2099;hpb=97db3fd3c9be0d324ea4a1a7f410c8d7ec45f055 diff --git a/iotjava/iotruntime/master/IoTMaster.java b/iotjava/iotruntime/master/IoTMaster.java index 7578f3b..7dc41d7 100644 --- a/iotjava/iotruntime/master/IoTMaster.java +++ b/iotjava/iotruntime/master/IoTMaster.java @@ -40,7 +40,7 @@ import static java.lang.Math.toIntExact; * @version 1.0 * @since 2016-06-16 */ -public class IoTMaster { +public final class IoTMaster { /** * IoTMaster class properties @@ -51,6 +51,7 @@ public class IoTMaster { private CommunicationHandler commHan; private LoadBalancer lbIoT; private RouterConfig routerConfig; + private ProcessJailConfig processJailConfig; private ObjectInitHandler objInitHand; private ObjectAddressInitHandler objAddInitHand; private String[] strObjectNames; @@ -96,12 +97,12 @@ public class IoTMaster { private static String STR_ZB_GATEWAY_ADDRESS; private static String STR_ZB_GATEWAY_PORT; private static String STR_ZB_IOTMASTER_PORT; - private static String STR_NUM_CALLBACK_PORTS; private static String STR_JVM_INIT_HEAP_SIZE; private static String STR_JVM_MAX_HEAP_SIZE; - private static String STR_LANGUAGE; + private static String STR_LANGUAGE_CONTROLLER; private static String STR_SKEL_CLASS_SUFFIX; private static String STR_STUB_CLASS_SUFFIX; + private static String STR_ACTIVATE_SANDBOXING; private static boolean BOOL_VERBOSE; /** @@ -113,6 +114,8 @@ public class IoTMaster { private static final String STR_CFG_FILE_EXT = ".config"; private static final String STR_CLS_FILE_EXT = ".class"; private static final String STR_JAR_FILE_EXT = ".jar"; + private static final String STR_MAC_POLICY_EXT = ".tomoyo.pol"; + private static final String STR_SHELL_FILE_EXT = ".sh"; private static final String STR_SO_FILE_EXT = ".so"; private static final String STR_ZIP_FILE_EXT = ".zip"; private static final String STR_TCP_PROTOCOL = "tcp"; @@ -123,6 +126,7 @@ public class IoTMaster { private static final String STR_INTERFACE_CLS_CFG = "INTERFACE_CLASS"; private static final String STR_INT_STUB_CLS_CFG = "INTERFACE_STUB_CLASS"; private static final String STR_FILE_TRF_CFG = "ADDITIONAL_ZIP_FILE"; + private static final String STR_LANGUAGE = "LANGUAGE"; private static final String STR_YES = "Yes"; private static final String STR_NO = "No"; private static final String STR_JAVA = "Java"; @@ -130,8 +134,12 @@ public class IoTMaster { private static final String STR_SSH = "ssh"; private static final String STR_SCP = "scp"; private static final String STR_IOTSLAVE_CPP = "./IoTSlave.o"; + private static final String STR_SHELL_HEADER = "#!/bin/sh"; + private static final String STR_JAVA_PATH = "/usr/bin/java"; + private static final String STR_MAC_POL_PATH = "tomoyo/"; private static int INT_SIZE = 4; // send length in the size of integer (4 bytes) + private static final int INT_DNS_PORT = 53; /** * Runtime class name constants - not to be configured by users @@ -152,6 +160,7 @@ public class IoTMaster { commHan = null; lbIoT = null; routerConfig = null; + processJailConfig = null; objInitHand = null; objAddInitHand = null; strObjectNames = argObjNms; @@ -187,10 +196,10 @@ public class IoTMaster { STR_ZB_GATEWAY_ADDRESS = null; STR_ZB_GATEWAY_PORT = null; STR_ZB_IOTMASTER_PORT = null; - STR_NUM_CALLBACK_PORTS = null; STR_JVM_INIT_HEAP_SIZE = null; STR_JVM_MAX_HEAP_SIZE = null; - STR_LANGUAGE = null; + STR_LANGUAGE_CONTROLLER = null; + STR_ACTIVATE_SANDBOXING = null; BOOL_VERBOSE = false; } @@ -206,11 +215,31 @@ public class IoTMaster { lbIoT.setupLoadBalancer(); routerConfig = new RouterConfig(); routerConfig.getAddressList(STR_ROUTER_ADD); + processJailConfig = new ProcessJailConfig(); + //processJailConfig.setAddressListObject(routerConfig.getAddressListObject()); objInitHand = new ObjectInitHandler(BOOL_VERBOSE); objAddInitHand = new ObjectAddressInitHandler(BOOL_VERBOSE); mapClassNameToCrim = new HashMap(); } + /** + * getPrintWriter() gets a new PrintWriter for a new object + * + * @param strObjectName String object name + * @return PrintWriter + */ + private PrintWriter getPrintWriter(String strObjectName) { + + FileWriter fw = null; + try { + fw = new FileWriter(strObjectName); + } catch (IOException ex) { + ex.printStackTrace(); + } + PrintWriter printWriter = new PrintWriter(new BufferedWriter(fw)); + return printWriter; + } + /** * A method to initialize constants from config file * @@ -246,12 +275,11 @@ public class IoTMaster { STR_ZB_GATEWAY_ADDRESS = prop.getProperty("ZIGBEE_GATEWAY_ADDRESS"); STR_ZB_GATEWAY_PORT = prop.getProperty("ZIGBEE_GATEWAY_PORT"); STR_ZB_IOTMASTER_PORT = prop.getProperty("ZIGBEE_IOTMASTER_PORT"); - STR_NUM_CALLBACK_PORTS = prop.getProperty("NUMBER_CALLBACK_PORTS"); STR_JVM_INIT_HEAP_SIZE = prop.getProperty("JVM_INIT_HEAP_SIZE"); STR_JVM_MAX_HEAP_SIZE = prop.getProperty("JVM_MAX_HEAP_SIZE"); - STR_LANGUAGE = prop.getProperty("LANGUAGE"); STR_SKEL_CLASS_SUFFIX = prop.getProperty("SKEL_CLASS_SUFFIX"); STR_STUB_CLASS_SUFFIX = prop.getProperty("STUB_CLASS_SUFFIX"); + STR_ACTIVATE_SANDBOXING = prop.getProperty("ACTIVATE_SANDBOXING"); if(prop.getProperty("VERBOSE").equals(STR_YES)) { BOOL_VERBOSE = true; } @@ -272,12 +300,11 @@ public class IoTMaster { RuntimeOutput.print("STR_ZB_GATEWAY_ADDRESS=" + STR_ZB_GATEWAY_ADDRESS, BOOL_VERBOSE); RuntimeOutput.print("STR_ZB_GATEWAY_PORT=" + STR_ZB_GATEWAY_PORT, BOOL_VERBOSE); RuntimeOutput.print("STR_ZB_IOTMASTER_PORT=" + STR_ZB_IOTMASTER_PORT, BOOL_VERBOSE); - RuntimeOutput.print("STR_NUM_CALLBACK_PORTS=" + STR_NUM_CALLBACK_PORTS, BOOL_VERBOSE); RuntimeOutput.print("STR_JVM_INIT_HEAP_SIZE=" + STR_JVM_INIT_HEAP_SIZE, BOOL_VERBOSE); RuntimeOutput.print("STR_JVM_MAX_HEAP_SIZE=" + STR_JVM_MAX_HEAP_SIZE, BOOL_VERBOSE); - RuntimeOutput.print("STR_LANGUAGE=" + STR_LANGUAGE, BOOL_VERBOSE); RuntimeOutput.print("STR_SKEL_CLASS_SUFFIX=" + STR_SKEL_CLASS_SUFFIX, BOOL_VERBOSE); RuntimeOutput.print("STR_STUB_CLASS_SUFFIX=" + STR_STUB_CLASS_SUFFIX, BOOL_VERBOSE); + RuntimeOutput.print("STR_ACTIVATE_SANDBOXING=" + STR_ACTIVATE_SANDBOXING, BOOL_VERBOSE); RuntimeOutput.print("BOOL_VERBOSE=" + BOOL_VERBOSE, BOOL_VERBOSE); RuntimeOutput.print("IoTMaster: Information extracted successfully!", BOOL_VERBOSE); } @@ -380,16 +407,18 @@ public class IoTMaster { * @params strIoTSlaveObjectHostAdd String slave host address * @params inStream ObjectInputStream communication * @params inStream ObjectOutputStream communication + * @params strLanguage String language * @return void */ private void instrumentIoTSetDevice(String strFieldIdentifier, String strObjName, String strFieldName, String strIoTSlaveObjectHostAdd, - InputStream inStream, OutputStream outStream) + InputStream inStream, OutputStream outStream, String strLanguage) throws IOException, ClassNotFoundException, InterruptedException { // Get information from the set List listObject = objAddInitHand.getFields(strFieldIdentifier); + RuntimeOutput.print("IoTMaster: DEBUG: Getting into instrumentIoTSetDevice!", BOOL_VERBOSE); // Create a new IoTSet - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguage.equals(STR_JAVA)) { Message msgCrtIoTSet = new MessageCreateSetRelation(IoTCommCode.CREATE_NEW_IOTSET, strFieldName); commMasterToSlave(msgCrtIoTSet, "Create new IoTSet for IoTDeviceAddress!", inStream, outStream); } else @@ -429,7 +458,7 @@ public class IoTMaster { System.out.println("DEBUG: InstrumentSetDevice: Device address: " + strDeviceAddressKey + "\n\n"); // Send address one by one - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguage.equals(STR_JAVA)) { Message msgGetIoTSetObj = null; if (bDstPortWildCard) { String strUniqueDev = strDeviceAddressKey + ":" + iRow; @@ -444,7 +473,7 @@ public class IoTMaster { bSrcPortWildCard, bDstPortWildCard); } // Reinitialize IoTSet on device object - if(STR_LANGUAGE.equals(STR_JAVA)) + if(strLanguage.equals(STR_JAVA)) commMasterToSlave(new MessageSimple(IoTCommCode.REINITIALIZE_IOTSET_FIELD), "Reinitialize IoTSet fields!", inStream, outStream); else reinitializeIoTSetFieldCpp(outStream, inStream); @@ -459,16 +488,17 @@ public class IoTMaster { * @params strIoTSlaveObjectHostAdd String slave host address * @params inStream ObjectInputStream communication * @params inStream ObjectOutputStream communication + * @params strLanguage String language * @return void */ private void instrumentIoTSetZBDevice(Map.Entry map, String strObjName, String strFieldName, String strIoTSlaveObjectHostAdd, - InputStream inStream, OutputStream outStream) + InputStream inStream, OutputStream outStream, String strLanguage) throws IOException, ClassNotFoundException, InterruptedException { // Get information from the set SetInstrumenter setInstrumenter = (SetInstrumenter) map.getValue(); // Create a new IoTSet - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguage.equals(STR_JAVA)) { Message msgCrtIoTSet = new MessageCreateSetRelation(IoTCommCode.CREATE_NEW_IOTSET, strFieldName); commMasterToSlave(msgCrtIoTSet, "Create new IoTSet for IoTZigbeeAddress!", inStream, outStream); } else // TODO: will need to implement IoTSet Zigbee for C++ later @@ -489,7 +519,7 @@ public class IoTMaster { RuntimeOutput.print("IoTMaster: Number of rows for IoTZigbeeAddress: " + iRows, BOOL_VERBOSE); // TODO: DEBUG!!! - System.out.println("\n\n DEBUG: InstrumentZigbeeDevice: Object Name: " + strObjName); + System.out.println("\n\nDEBUG: InstrumentZigbeeDevice: Object Name: " + strObjName); System.out.println("DEBUG: InstrumentZigbeeDevice: Port number: " + commHan.getComPort(strZigbeeGWAddressKey)); System.out.println("DEBUG: InstrumentZigbeeDevice: Device address: " + strZigbeeGWAddress + "\n\n"); @@ -501,7 +531,7 @@ public class IoTMaster { // Send policy to Zigbee gateway - TODO: Need to clear policy first? zbConfig.setPolicy(strIoTSlaveObjectHostAdd, commHan.getComPort(strZigbeeGWAddressKey), strZBDevAddress); // Send address one by one - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguage.equals(STR_JAVA)) { Message msgGetIoTSetZBObj = new MessageGetSimpleDeviceObject(IoTCommCode.GET_ZB_DEV_IOTSET_OBJECT, strZBDevAddress); commMasterToSlave(msgGetIoTSetZBObj, "Get IoTSet objects!", inStream, outStream); } else // TODO: Implement IoTSet Zigbee for C++ @@ -520,16 +550,17 @@ public class IoTMaster { * @params strFieldName String field name * @params inStream ObjectInputStream communication * @params inStream ObjectOutputStream communication + * @params strLanguage String language * @return void */ private void instrumentIoTSetAddress(String strFieldIdentifier, String strFieldName, - InputStream inStream, OutputStream outStream) + InputStream inStream, OutputStream outStream, String strLanguage) throws IOException, ClassNotFoundException, InterruptedException { // Get information from the set List listObject = objAddInitHand.getFields(strFieldIdentifier); // Create a new IoTSet - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguage.equals(STR_JAVA)) { Message msgCrtIoTSet = new MessageCreateSetRelation(IoTCommCode.CREATE_NEW_IOTSET, strFieldName); commMasterToSlave(msgCrtIoTSet, "Create new IoTSet for IoTAddress!", inStream, outStream); } else @@ -542,7 +573,7 @@ public class IoTMaster { // Get device address String strAddress = (String) arrFieldValues[0]; // Send address one by one - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguage.equals(STR_JAVA)) { Message msgGetIoTSetAddObj = new MessageGetSimpleDeviceObject(IoTCommCode.GET_ADD_IOTSET_OBJECT, strAddress); commMasterToSlave(msgGetIoTSetAddObj, "Get IoTSet objects!", inStream, outStream); } else // TODO: Implement IoTSet Address for C++ @@ -557,10 +588,12 @@ public class IoTMaster { /** * A private method to instrument an object on a specific machine and setting up policies * - * @params strFieldObjectID String field object ID + * @params strFieldObjectID String field object ID + * @params strObjControllerName String object controller name + * @params strLanguage String language * @return void */ - private void instrumentObject(String strFieldObjectID) throws IOException { + private void instrumentObject(String strFieldObjectID, String strObjControllerName, String strLanguage) throws IOException { // Extract the interface name for RMI // e.g. ProximitySensorInterface, TempSensorInterface, etc. @@ -605,8 +638,18 @@ public class IoTMaster { strIoTSlaveObjectHostAdd, STR_TCP_PROTOCOL); routerConfig.configureHostMainPolicies(strIoTSlaveObjectHostAdd, strIoTSlaveControllerHostAdd, strIoTSlaveObjectHostAdd, STR_TCP_PROTOCOL); + // Configure MAC policies for objects + //String strFileName = STR_MAC_POL_PATH + strObjClassName + STR_MAC_POLICY_EXT; + String strFileName = STR_MAC_POL_PATH + STR_JAVA + STR_MAC_POLICY_EXT; + if (STR_ACTIVATE_SANDBOXING.equals("Yes")) { + processJailConfig.configureProcessJailDeviceDriverPolicies(strIoTSlaveObjectHostAdd, strObjName, strObjClassName, + strFileName, strIoTMasterHostAdd, commHan.getComPort(strObjName), commHan.getRMIRegPort(strObjName), + commHan.getRMIStubPort(strObjName)); + processJailConfig.configureProcessJailContRMIPolicies(strObjControllerName, strIoTSlaveObjectHostAdd, + commHan.getRMIRegPort(strObjName), commHan.getRMIStubPort(strObjName)); + } // Instrument the IoTSet declarations inside the class file - instrumentObjectIoTSet(strFieldObjectID); + instrumentObjectIoTSet(strFieldObjectID, strLanguage); } // Send routing policy to router for controller object // ROUTING POLICY: RMI communication - RMI registry and stub ports @@ -623,35 +666,8 @@ public class IoTMaster { STR_TCP_PROTOCOL, commHan.getRMIStubPort(strObjName)); routerConfig.configureHostMainPolicies(strIoTSlaveObjectHostAdd, strIoTSlaveControllerHostAdd, strIoTSlaveObjectHostAdd, STR_TCP_PROTOCOL, commHan.getRMIStubPort(strObjName)); - // Send the same set of routing policies for callback ports - setCallbackPortsPolicy(strObjName, STR_ROUTER_ADD, strIoTSlaveControllerHostAdd, strIoTSlaveObjectHostAdd, STR_TCP_PROTOCOL); } - /** - * A private method to set router policies for callback ports - * - * @params strRouterAdd String router address - * @params strIoTSlaveControllerHostAdd String slave controller host address - * @params strIoTSlaveObjectHostAdd String slave object host address - * @params strProtocol String protocol - * @return iPort Integer port number - */ - private void setCallbackPortsPolicy(String strObjName, String strRouterAdd, String strIoTSlaveControllerHostAdd, - String strIoTSlaveObjectHostAdd, String strProtocol) { - - int iNumCallbackPorts = Integer.parseInt(STR_NUM_CALLBACK_PORTS); - Integer[] rmiCallbackPorts = commHan.getCallbackPorts(strObjName, iNumCallbackPorts); - - // Iterate over port numbers and set up policies - for (int i=0; i map, - String strHostAddress) { + String strHostAddress, String strControllerName) { // Get information from the set SetInstrumenter setInstrumenter = (SetInstrumenter) map.getValue(); @@ -755,6 +778,13 @@ public class IoTMaster { // Get device address String strAddress = (String) arrFieldValues[0]; // Setting up router policies for HTTP/HTTPs + if (STR_ACTIVATE_SANDBOXING.equals("Yes")) { + if (strControllerName != null) { + processJailConfig.configureProcessJailInetAddressPolicies(strControllerName, STR_ROUTER_ADD, strAddress); + } else { + processJailConfig.configureProcessJailInetAddressPolicies(strHostAddress, STR_ROUTER_ADD, strAddress); + } + } routerConfig.configureRouterHTTPPolicies(STR_ROUTER_ADD, strHostAddress, strAddress); routerConfig.configureHostHTTPPolicies(strHostAddress, strHostAddress, strAddress); } @@ -765,16 +795,17 @@ public class IoTMaster { *

* Mostly the IoTSet fields would contain IoTDeviceAddress objects * - * @params strFieldObjectID String field object ID + * @params strFieldObjectID String field object ID + * @params strLanguage String language * @return void */ - private void instrumentObjectIoTSet(String strFieldObjectID) throws IOException { + private void instrumentObjectIoTSet(String strFieldObjectID, String strLanguage) throws IOException { // If this is a new object ... then create one // Instrument the class source code and look for IoTSet for device addresses // e.g. @config private IoTSet lb_addresses; HashMap hmObjectFieldObjects = null; - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguage.equals(STR_JAVA)) { String strObjectClassNamePath = STR_IOT_CODE_PATH + strObjClassName + "/" + strObjClassName + STR_CLS_FILE_EXT; FileInputStream fis = new FileInputStream(strObjectClassNamePath); ClassReader cr = new ClassReader(fis); @@ -808,7 +839,7 @@ public class IoTMaster { setRouterPolicyIoTSetDevice(strFieldIdentifier, map, strIoTSlaveObjectHostAdd); } else if(setInstrumenter.getObjTableName().equals(STR_IOT_ADD_CLS)) { // Instrument the IoTAddress - setRouterPolicyIoTSetAddress(strFieldIdentifier, map, strIoTSlaveObjectHostAdd); + setRouterPolicyIoTSetAddress(strFieldIdentifier, map, strIoTSlaveObjectHostAdd, null); } else if(setInstrumenter.getObjTableName().equals(STR_IOT_ZB_ADD_CLS)) { // Instrument the IoTZigbeeAddress - special feature for Zigbee device support RuntimeOutput.print("IoTMaster: IoTZigbeeAddress found! No router policy is set here..", @@ -899,11 +930,18 @@ public class IoTMaster { */ private String getCmdJavaDriverIoTSlave(String strIoTMasterHostAdd, String strIoTSlaveObjectHostAdd, String strObjName) { - return STR_SSH + " " + STR_USERNAME + strIoTSlaveObjectHostAdd + " cd " + STR_RUNTIME_DIR + " sudo java " + - STR_CLS_PATH + " " + STR_RMI_PATH + " " + STR_RMI_HOSTNAME + - strIoTSlaveObjectHostAdd + " " + STR_IOT_SLAVE_CLS + " " + strIoTMasterHostAdd + " " + + // Create an Shell executable + String strJavaCommand = STR_SHELL_HEADER + "\nexec " + STR_JAVA_PATH + " " + STR_CLS_PATH + " " + STR_RMI_PATH + " " + + STR_RMI_HOSTNAME + strIoTSlaveObjectHostAdd + " " + STR_IOT_SLAVE_CLS + " " + strIoTMasterHostAdd + " " + commHan.getComPort(strObjName) + " " + commHan.getRMIRegPort(strObjName) + " " + - commHan.getRMIStubPort(strObjName) + " >& " + STR_LOG_FILE_PATH + strObjName + ".log &"; + commHan.getRMIStubPort(strObjName) + " > " + STR_LOG_FILE_PATH + strObjName + ".log &"; + String shellFile = "./" + strObjName + STR_SHELL_FILE_EXT; + createWrapperShellScript(strJavaCommand, shellFile); + // Send the file to the compute node + String strCmdSend = "scp " + shellFile + " " + STR_USERNAME + strIoTSlaveObjectHostAdd + ":" + STR_RUNTIME_DIR; + runCommand(strCmdSend); + System.out.println("IoTMaster: Sending shell file: " + strCmdSend); + return STR_SSH + " " + STR_USERNAME + strIoTSlaveObjectHostAdd + " cd " + STR_RUNTIME_DIR + " " + shellFile; } @@ -920,6 +958,22 @@ public class IoTMaster { } + /** + * createWrapperShellScript() gets a wrapper shell script + * + * @param strCommand String command + * @param strObjectName String object name + * @return PrintWriter + */ + private void createWrapperShellScript(String strCommand, String strFileName) { + + PrintWriter printWriter = getPrintWriter(strFileName); + printWriter.println(strCommand); + printWriter.close(); + runCommand("chmod 755 " + strFileName); + } + + /** * A private method to create an object on a specific machine * @@ -936,10 +990,16 @@ public class IoTMaster { String strIoTSlaveObjectHostAdd, String strFieldObjectID, Object[] arrFieldValues, Class[] arrFieldClasses) throws IOException, FileNotFoundException, ClassNotFoundException, InterruptedException { + // Read config file + String sCfgFile = STR_IOT_CODE_PATH + strObjClassName + "/" + strObjClassName + STR_CFG_FILE_EXT; + String strLanguageDriver = parseConfigFile(sCfgFile, STR_LANGUAGE + "_" + strObjName); + if(strLanguageDriver == null) // Read just the field LANGUAGE if the first read is null + strLanguageDriver = parseConfigFile(sCfgFile, STR_LANGUAGE); + if(strLanguageDriver == null) // Check nullness for the second time - report if it is still null + throw new Error("IoTMaster: Language specification missing in config file: " + sCfgFile); // PROFILING long start = 0; long result = 0; - // PROFILING start = System.currentTimeMillis(); @@ -950,10 +1010,13 @@ public class IoTMaster { // iotruntime.IoTSlave dw-1.eecs.uci.edu 46151 23829 42874 & // The In-Port for IoTMaster is the Out-Port for IoTSlave and vice versa String strSSHCommand = null; - if(STR_LANGUAGE.equals(STR_JAVA)) + if(strLanguageDriver.equals(STR_JAVA)) strSSHCommand = getCmdJavaDriverIoTSlave(strIoTMasterHostAdd, strIoTSlaveObjectHostAdd, strObjName); - else + else if(strLanguageDriver.equals(STR_CPP)) strSSHCommand = getCmdCppDriverIoTSlave(strIoTMasterHostAdd, strIoTSlaveObjectHostAdd, strObjName); + else + throw new Error("IoTMaster: Language specification not recognized: " + strLanguageDriver); + RuntimeOutput.print("IoTMaster: Language for " + strObjName + " is " + strLanguageDriver, BOOL_VERBOSE); RuntimeOutput.print(strSSHCommand, BOOL_VERBOSE); // Start a new thread to start a new JVM @@ -964,7 +1027,7 @@ public class IoTMaster { //OutputStream outStream = new ObjectOutputStream(socket.getOutputStream()); InputStream inStream = null; OutputStream outStream = null; - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguageDriver.equals(STR_JAVA)) { inStream = new ObjectInputStream(socket.getInputStream()); outStream = new ObjectOutputStream(socket.getOutputStream()); } else { // At this point the language is certainly C++, otherwise would've complained above @@ -980,7 +1043,7 @@ public class IoTMaster { // PROFILING start = System.currentTimeMillis(); - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguageDriver.equals(STR_JAVA)) { sendFileToJavaSlaveDriver(serverSocket, inStream, outStream, strObjName, strObjClassName, strObjClassInterfaceName, strObjStubClsIntfaceName, strIoTSlaveObjectHostAdd, strFieldObjectID, arrFieldValues, arrFieldClasses); @@ -1023,17 +1086,18 @@ public class IoTMaster { if(setInstrumenter.getObjTableName().equals(STR_IOT_DEV_ADD_CLS)) { // Instrument the normal IoTDeviceAddress synchronized(this) { - instrumentIoTSetDevice(strFieldIdentifier, strObjName, strFieldName, strIoTSlaveObjectHostAdd, inStream, outStream); + //RuntimeOutput.print("IoTMaster: DEBUG: Processing " + STR_IOT_DEV_ADD_CLS + "!", BOOL_VERBOSE); + instrumentIoTSetDevice(strFieldIdentifier, strObjName, strFieldName, strIoTSlaveObjectHostAdd, inStream, outStream, strLanguageDriver); } } else if(setInstrumenter.getObjTableName().equals(STR_IOT_ZB_ADD_CLS)) { // Instrument the IoTZigbeeAddress - special feature for Zigbee device support synchronized(this) { - instrumentIoTSetZBDevice(map, strObjName, strFieldName, strIoTSlaveObjectHostAdd, inStream, outStream); + instrumentIoTSetZBDevice(map, strObjName, strFieldName, strIoTSlaveObjectHostAdd, inStream, outStream, strLanguageDriver); } } else if(setInstrumenter.getObjTableName().equals(STR_IOT_ADD_CLS)) { // Instrument the IoTAddress synchronized(this) { - instrumentIoTSetAddress(strFieldIdentifier, strFieldName, inStream, outStream); + instrumentIoTSetAddress(strFieldIdentifier, strFieldName, inStream, outStream, strLanguageDriver); } } else { String strErrMsg = "IoTMaster: Device driver object can only have IoTSet, IoTSet," + @@ -1047,8 +1111,7 @@ public class IoTMaster { } // End the session // TODO: Change this later - - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(strLanguageDriver.equals(STR_JAVA)) { ObjectOutputStream oStream = (ObjectOutputStream) outStream; oStream.writeObject(new MessageSimple(IoTCommCode.END_SESSION)); } else { // C++ side for now will be running continuously because it's an infinite loop (not in a separate thread) @@ -1073,7 +1136,7 @@ public class IoTMaster { * * @return void */ - private void createControllerObjects() throws InterruptedException { + private void createDriverObjects() throws InterruptedException { // Create a list of threads List threads = new ArrayList(); @@ -1117,9 +1180,10 @@ public class IoTMaster { * * @params Map.Entry Entry of map IoTSet instrumentation * @params strFieldName String field name + * @params strLanguage String language * @return void */ - private void instrumentIoTSet(Map.Entry map, String strFieldName) + private void instrumentIoTSet(Map.Entry map, String strFieldName, String strObjControllerName, String strLanguage) throws IOException, ClassNotFoundException, InterruptedException { // Get information from the set @@ -1135,11 +1199,10 @@ public class IoTMaster { String strObjID = setInstrumenter.fieldObjectID(iRow); strObjClassName = setInstrumenter.fieldEntryType(strObjID); // Call the method to create an object - instrumentObject(strObjID); - int iNumOfPorts = Integer.parseInt(STR_NUM_CALLBACK_PORTS); + instrumentObject(strObjID, strObjControllerName, strLanguage); objInitHand.addObjectIntoField(strFieldName, strIoTSlaveObjectHostAdd, strObjName, strObjClassName, strObjClassInterfaceName, strObjStubClsIntfaceName, commHan.getRMIRegPort(strObjName), - commHan.getRMIStubPort(strObjName), commHan.getCallbackPorts(strObjName, iNumOfPorts)); + commHan.getRMIStubPort(strObjName)); } } @@ -1149,9 +1212,10 @@ public class IoTMaster { * * @params Map.Entry Entry of map IoTRelation instrumentation * @params strFieldName String field name + * @params strLanguage String language * @return void */ - private void instrumentIoTRelation(Map.Entry map, String strFieldName) + private void instrumentIoTRelation(Map.Entry map, String strFieldName, String strObjControllerName, String strLanguage) throws IOException, ClassNotFoundException, InterruptedException { // Get information from the set @@ -1166,27 +1230,24 @@ public class IoTMaster { String strObjID = relationInstrumenter.firstFieldObjectID(iRow); strObjClassName = relationInstrumenter.firstEntryFieldType(strObjID); // Call the method to create an object - instrumentObject(strObjID); + instrumentObject(strObjID, strObjControllerName, strLanguage); // Get the first object controller host address String strFirstIoTSlaveObjectHostAdd = strIoTSlaveObjectHostAdd; - int iNumOfPorts = Integer.parseInt(STR_NUM_CALLBACK_PORTS); objInitHand.addObjectIntoField(strFieldName, strIoTSlaveObjectHostAdd, strObjName, strObjClassName, strObjClassInterfaceName, strObjStubClsIntfaceName, - commHan.getRMIRegPort(strObjName), commHan.getRMIStubPort(strObjName), - commHan.getCallbackPorts(strObjName, iNumOfPorts)); + commHan.getRMIRegPort(strObjName), commHan.getRMIStubPort(strObjName)); // Operate on the second set arrFieldClasses = relationInstrumenter.secondFieldClasses(iRow); arrFieldValues = relationInstrumenter.secondFieldValues(iRow); strObjID = relationInstrumenter.secondFieldObjectID(iRow); strObjClassName = relationInstrumenter.secondEntryFieldType(strObjID); // Call the method to create an object - instrumentObject(strObjID); + instrumentObject(strObjID, strObjControllerName, strLanguage); // Get the second object controller host address String strSecondIoTSlaveObjectHostAdd = strIoTSlaveObjectHostAdd; objInitHand.addSecondObjectIntoField(strFieldName, strIoTSlaveObjectHostAdd, strObjName, strObjClassName, strObjClassInterfaceName, strObjStubClsIntfaceName, - commHan.getRMIRegPort(strObjName), commHan.getRMIStubPort(strObjName), - commHan.getCallbackPorts(strObjName, iNumOfPorts)); + commHan.getRMIRegPort(strObjName), commHan.getRMIStubPort(strObjName)); // ROUTING POLICY: first and second controller objects in IoTRelation routerConfig.configureRouterMainPolicies(STR_ROUTER_ADD, strFirstIoTSlaveObjectHostAdd, strSecondIoTSlaveObjectHostAdd, STR_TCP_PROTOCOL); @@ -1221,8 +1282,8 @@ public class IoTMaster { // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO FILL IN IOTSET commMasterToSlave(new MessageGetObject(IoTCommCode.GET_IOTSET_OBJECT, objInitInfo.getIoTSlaveObjectHostAdd(), objInitInfo.getObjectName(), objInitInfo.getObjectClassName(), objInitInfo.getObjectClassInterfaceName(), - objInitInfo.getObjectStubClassInterfaceName(), objInitInfo.getRMIRegistryPort(), objInitInfo.getRMIStubPort(), - objInitInfo.getRMICallbackPorts()), "Get IoTSet object!", inStream, outStream); + objInitInfo.getObjectStubClassInterfaceName(), objInitInfo.getRMIRegistryPort(), objInitInfo.getRMIStubPort()), + "Get IoTSet object!", inStream, outStream); } // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO REINITIALIZE IOTSET FIELD @@ -1240,14 +1301,14 @@ public class IoTMaster { commMasterToSlave(new MessageGetObject(IoTCommCode.GET_IOTRELATION_FIRST_OBJECT, objInitInfo.getIoTSlaveObjectHostAdd(), objInitInfo.getObjectName(), objInitInfo.getObjectClassName(), objInitInfo.getObjectClassInterfaceName(), objInitInfo.getObjectStubClassInterfaceName(), - objInitInfo.getRMIRegistryPort(), objInitInfo.getRMIStubPort(), objInitInfo.getRMICallbackPorts()), + objInitInfo.getRMIRegistryPort(), objInitInfo.getRMIStubPort()), "Get IoTRelation first object!", inStream, outStream); ObjectInitInfo objSecObj = (ObjectInitInfo) it.next(); // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO FILL IN IOTRELATION (SECOND OBJECT) commMasterToSlave(new MessageGetObject(IoTCommCode.GET_IOTRELATION_SECOND_OBJECT, objSecObj.getIoTSlaveObjectHostAdd(), objSecObj.getObjectName(), objSecObj.getObjectClassName(), objSecObj.getObjectClassInterfaceName(), objSecObj.getObjectStubClassInterfaceName(), - objSecObj.getRMIRegistryPort(), objSecObj.getRMIStubPort(), objSecObj.getRMICallbackPorts()), + objSecObj.getRMIRegistryPort(), objSecObj.getRMIStubPort()), "Get IoTRelation second object!", inStream, outStream); } // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO REINITIALIZE IOTRELATION FIELD @@ -1279,7 +1340,7 @@ public class IoTMaster { // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO FILL IN IOTSET getIoTSetRelationObjectCpp(IoTCommCode.GET_IOTSET_OBJECT, objInitInfo.getIoTSlaveObjectHostAdd(), objInitInfo.getObjectName(), objInitInfo.getObjectClassName(), objInitInfo.getObjectClassInterfaceName(), objInitInfo.getObjectStubClassInterfaceName(), - objInitInfo.getRMIRegistryPort(), objInitInfo.getRMIStubPort(), objInitInfo.getRMICallbackPorts(), outStream, inStream); + objInitInfo.getRMIRegistryPort(), objInitInfo.getRMIStubPort(), outStream, inStream); } // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO REINITIALIZE IOTSET FIELD reinitializeIoTSetFieldCpp(outStream, inStream); @@ -1294,12 +1355,12 @@ public class IoTMaster { // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO FILL IN IOTRELATION (FIRST OBJECT) getIoTSetRelationObjectCpp(IoTCommCode.GET_IOTRELATION_FIRST_OBJECT, objInitInfo.getIoTSlaveObjectHostAdd(), objInitInfo.getObjectName(), objInitInfo.getObjectClassName(), objInitInfo.getObjectClassInterfaceName(), objInitInfo.getObjectStubClassInterfaceName(), - objInitInfo.getRMIRegistryPort(), objInitInfo.getRMIStubPort(), objInitInfo.getRMICallbackPorts(), outStream, inStream); + objInitInfo.getRMIRegistryPort(), objInitInfo.getRMIStubPort(), outStream, inStream); ObjectInitInfo objSecObj = (ObjectInitInfo) it.next(); // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO FILL IN IOTRELATION (SECOND OBJECT) getIoTSetRelationObjectCpp(IoTCommCode.GET_IOTRELATION_SECOND_OBJECT, objSecObj.getIoTSlaveObjectHostAdd(), objSecObj.getObjectName(), objSecObj.getObjectClassName(), objSecObj.getObjectClassInterfaceName(), objSecObj.getObjectStubClassInterfaceName(), - objSecObj.getRMIRegistryPort(), objSecObj.getRMIStubPort(), objSecObj.getRMICallbackPorts(), outStream, inStream); + objSecObj.getRMIRegistryPort(), objSecObj.getRMIStubPort(), outStream, inStream); } // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO REINITIALIZE IOTRELATION FIELD reinitializeIoTRelationFieldCpp(outStream, inStream); @@ -1394,6 +1455,39 @@ public class IoTMaster { } } + /** + * A method to create a thread for policy deployment + * + * @param setHostAddresses Set of strings for host addresses to configure + * @return void + */ + private void createMACPolicyThreads(Set setHostAddresses) throws IOException { + + // Create a list of threads + List threads = new ArrayList(); + // Start threads for hosts + for(String strAddress : setHostAddresses) { + Thread policyThread = new Thread(new Runnable() { + public void run() { + synchronized(this) { + processJailConfig.sendMACPolicies(strAddress); + } + } + }); + threads.add(policyThread); + policyThread.start(); + RuntimeOutput.print("Deploying MAC policies for: " + strAddress, BOOL_VERBOSE); + } + // Join all threads + for (Thread thread : threads) { + try { + thread.join(); + } catch (InterruptedException ex) { + ex.printStackTrace(); + } + } + } + /** * A method to send files to Java IoTSlave @@ -1523,14 +1617,19 @@ public class IoTMaster { */ private String getCmdJavaIoTSlave(String strObjControllerName) { - return STR_SSH + " " + STR_USERNAME + strIoTSlaveControllerHostAdd + " cd " + - STR_RUNTIME_DIR + " sudo java " + STR_JVM_INIT_HEAP_SIZE + " " + - STR_JVM_MAX_HEAP_SIZE + " " + STR_CLS_PATH + " " + - STR_RMI_PATH + " " + STR_IOT_SLAVE_CLS + " " + strIoTMasterHostAdd + " " + - commHan.getComPort(strObjControllerName) + " " + - commHan.getRMIRegPort(strObjControllerName) + " " + - commHan.getRMIStubPort(strObjControllerName) + " >& " + - STR_LOG_FILE_PATH + strObjControllerName + ".log &"; + // Create an Shell executable + String strJavaCommand = STR_SHELL_HEADER + "\nexec " + STR_JAVA_PATH + " " + STR_JVM_INIT_HEAP_SIZE + " " + + STR_JVM_MAX_HEAP_SIZE + " " + STR_CLS_PATH + " " + STR_RMI_PATH + " " + STR_IOT_SLAVE_CLS + " " + + strIoTMasterHostAdd + " " + commHan.getComPort(strObjControllerName) + " " + + commHan.getRMIRegPort(strObjControllerName) + " " + commHan.getRMIStubPort(strObjControllerName) + + " > " + STR_LOG_FILE_PATH + strObjControllerName + ".log &"; + String shellFile = "./" + strObjControllerName + STR_SHELL_FILE_EXT; + createWrapperShellScript(strJavaCommand, shellFile); + // Send the file to the compute node + String strCmdSend = "scp " + shellFile + " " + STR_USERNAME + strIoTSlaveControllerHostAdd + ":" + STR_RUNTIME_DIR; + runCommand(strCmdSend); + System.out.println("IoTMaster: Sending main controller shell file: " + strCmdSend); + return STR_SSH + " " + STR_USERNAME + strIoTSlaveControllerHostAdd + " cd " + STR_RUNTIME_DIR + " " + shellFile; } @@ -1629,7 +1728,7 @@ public class IoTMaster { /** * Receive ACK */ - public boolean recvAck(InputStream inStream) throws IOException { + public synchronized boolean recvAck(InputStream inStream) throws IOException { int intAck = recvInteger(inStream); IoTCommCode codeAck = getCode(intAck); @@ -1797,7 +1896,7 @@ public class IoTMaster { */ public void getIoTSetRelationObjectCpp(IoTCommCode iotCommCode, String strIoTSlaveHostAddress, String strObjectName, String strObjectClassName, String strObjectClassInterfaceName, String strObjectStubClassInterfaceName, int iRMIRegistryPort, int iRMIStubPort, - Integer[] iCallbackPorts, OutputStream outStream, InputStream inStream) throws IOException { + OutputStream outStream, InputStream inStream) throws IOException { sendCommCode(iotCommCode, outStream, inStream); RuntimeOutput.print("IoTMaster: Getting IoTSet object content...", BOOL_VERBOSE); @@ -1816,10 +1915,6 @@ public class IoTMaster { sendInteger(iRMIRegistryPort, outStream); recvAck(inStream); RuntimeOutput.print("IoTMaster: Driver object stub port: " + iRMIStubPort, BOOL_VERBOSE); sendInteger(iRMIStubPort, outStream); recvAck(inStream); - sendInteger(iCallbackPorts.length, outStream); recvAck(inStream); - for(Integer i : iCallbackPorts) { - sendInteger(i, outStream); recvAck(inStream); - } } @@ -1921,15 +2016,19 @@ public class IoTMaster { strIoTSlaveControllerHostAdd, STR_TCP_PROTOCOL, commHan.getComPort(strObjControllerName)); routerConfig.configureHostMainPolicies(strIoTSlaveControllerHostAdd, strIoTMasterHostAdd, strIoTSlaveControllerHostAdd, STR_TCP_PROTOCOL, commHan.getComPort(strObjControllerName)); - + // Read config file + String strControllerCfg = STR_CONT_PATH + strObjControllerName + "/" + strObjControllerName + STR_CFG_FILE_EXT; + STR_LANGUAGE_CONTROLLER = parseConfigFile(strControllerCfg, STR_LANGUAGE); + if(STR_LANGUAGE_CONTROLLER == null) + throw new Error("IoTMaster: Language specification missing in config file: " + strControllerCfg); // Construct ssh command line and create a controller thread for e.g. AcmeProximity String strSSHCommand = null; - if(STR_LANGUAGE.equals(STR_JAVA)) + if(STR_LANGUAGE_CONTROLLER.equals(STR_JAVA)) strSSHCommand = getCmdJavaIoTSlave(strObjControllerName); - else if(STR_LANGUAGE.equals(STR_CPP)) + else if(STR_LANGUAGE_CONTROLLER.equals(STR_CPP)) strSSHCommand = getCmdCppIoTSlave(strObjControllerName); else - throw new Error("IoTMaster: Language specification not recognized: " + STR_LANGUAGE); + throw new Error("IoTMaster: Language specification not recognized: " + STR_LANGUAGE_CONTROLLER); RuntimeOutput.print(strSSHCommand, BOOL_VERBOSE); createThread(strSSHCommand); // Wait for connection @@ -1938,7 +2037,7 @@ public class IoTMaster { Socket socket = serverSocket.accept(); InputStream inStream = null; OutputStream outStream = null; - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(STR_LANGUAGE_CONTROLLER.equals(STR_JAVA)) { inStream = new ObjectInputStream(socket.getInputStream()); outStream = new ObjectOutputStream(socket.getOutputStream()); } else { // At this point the language is certainly C++, otherwise would've complained above @@ -1960,7 +2059,7 @@ public class IoTMaster { String strControllerClassNamePath = STR_CONT_PATH + strObjControllerName + "/" + strControllerClassName; - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(STR_LANGUAGE_CONTROLLER.equals(STR_JAVA)) { sendFileToJavaSlave(strObjControllerName, serverSocket, inStream, outStream); // Create main controller/device object commMasterToSlave(new MessageCreateMainObject(IoTCommCode.CREATE_MAIN_OBJECT, strObjControllerName), @@ -1971,7 +2070,13 @@ public class IoTMaster { sendFileToCppSlave(strControllerFilePath, strControllerZipFile); createMainObjectCpp(strObjControllerName, outStream, inStream); } - + // Write basic MAC policies for controller + //String strFileName = STR_MAC_POL_PATH + strObjControllerName + STR_MAC_POLICY_EXT; + if (STR_ACTIVATE_SANDBOXING.equals("Yes")) { + String strFileName = STR_MAC_POL_PATH + STR_JAVA + STR_MAC_POLICY_EXT; + processJailConfig.configureProcessJailControllerPolicies(strObjControllerName, strFileName, + strIoTMasterHostAdd, commHan.getComPort(strObjControllerName)); + } // PROFILING result = System.currentTimeMillis()-start; System.out.println("\n\n ==> From IoTSlave start until main controller object is created: " + result); @@ -1984,7 +2089,7 @@ public class IoTMaster { RuntimeOutput.print("IoTMaster: Opening class file: " + strControllerClassName, BOOL_VERBOSE); RuntimeOutput.print("IoTMaster: Class file path: " + strControllerClassNamePath, BOOL_VERBOSE); HashMap hmControllerFieldObjects = null; - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(STR_LANGUAGE_CONTROLLER.equals(STR_JAVA)) { FileInputStream fis = new FileInputStream(strControllerClassNamePath); ClassReader cr = new ClassReader(fis); ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_FRAMES); @@ -2018,16 +2123,21 @@ public class IoTMaster { throw new Error(strErrMsg); } else if(setInstrumenter.getObjTableName().equals(STR_IOT_ADD_CLS)) { // Instrument the IoTAddress - setRouterPolicyIoTSetAddress(strFieldName, map, strIoTSlaveControllerHostAdd); - instrumentIoTSetAddress(strFieldName, strFieldName, inStream, outStream); + setRouterPolicyIoTSetAddress(strFieldName, map, strIoTSlaveControllerHostAdd, strObjControllerName); + instrumentIoTSetAddress(strFieldName, strFieldName, inStream, outStream, STR_LANGUAGE_CONTROLLER); } else { // Any other cases - instrumentIoTSet(map, strFieldName); + instrumentIoTSet(map, strFieldName, strObjControllerName, STR_LANGUAGE_CONTROLLER); } } else if (strClassName.equals(STR_REL_INSTRUMENTER_CLS)) { - instrumentIoTRelation(map, strFieldName); + instrumentIoTRelation(map, strFieldName, strObjControllerName, STR_LANGUAGE_CONTROLLER); } } + // Combine controller MAC policies with the main policy file for the host + String strTempFileName = "./" + strObjControllerName + STR_MAC_POLICY_EXT; + processJailConfig.combineControllerMACPolicies(strIoTSlaveControllerHostAdd, strObjControllerName, strTempFileName); + processJailConfig.close(); + // PROFILING result = System.currentTimeMillis()-start; System.out.println("\n\n ==> Time needed to instrument device driver objects: " + result + "\n\n"); @@ -2061,7 +2171,7 @@ public class IoTMaster { start = System.currentTimeMillis(); // Separating object creations and Set/Relation initializations - createControllerObjects(); + createDriverObjects(); // PROFILING result = System.currentTimeMillis()-start; @@ -2070,7 +2180,7 @@ public class IoTMaster { start = System.currentTimeMillis(); // Sets and relations initializations - if(STR_LANGUAGE.equals(STR_JAVA)) + if(STR_LANGUAGE_CONTROLLER.equals(STR_JAVA)) initializeSetsAndRelationsJava(inStream, outStream); else initializeSetsAndRelationsCpp(inStream, outStream);; @@ -2079,13 +2189,13 @@ public class IoTMaster { result = System.currentTimeMillis()-start; System.out.println("\n\n ==> Time needed to initialize sets and relations: " + result + "\n\n"); - if(STR_LANGUAGE.equals(STR_JAVA)) + if(STR_LANGUAGE_CONTROLLER.equals(STR_JAVA)) // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO EXECUTE INIT METHOD commMasterToSlave(new MessageSimple(IoTCommCode.INVOKE_INIT_METHOD), "Invoke init() method!", inStream, outStream); else invokeInitMethodCpp(outStream, inStream); // == COMMUNICATION WITH IOTSLAVE CONTROLLER TO END PROCESS - if(STR_LANGUAGE.equals(STR_JAVA)) { + if(STR_LANGUAGE_CONTROLLER.equals(STR_JAVA)) { ObjectOutputStream oStream = (ObjectOutputStream) outStream; oStream.writeObject(new MessageSimple(IoTCommCode.END_SESSION)); } else // C++ side will wait until the program finishes, it's not generating a separate thread for now @@ -2096,6 +2206,8 @@ public class IoTMaster { serverSocket.close(); commHan.printLists(); lbIoT.printHostInfo(); + if (STR_ACTIVATE_SANDBOXING.equals("Yes")) + createMACPolicyThreads(setAddresses); } } catch (IOException |