import java.util.List;
import java.util.Map;
+import java.util.Set;
import java.util.HashSet;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.ConcurrentHashMap;
* @version 1.0
* @since 2016-12-14
*/
-public class HomeSecurityController implements SmartthingsSensorCallback {
+public class HomeSecurityController implements SmartthingsSensorCallback, SmartthingsActuatorCallback {
/*
* Constants
private static final int CHECK_TIME_WAIT = 1; // in seconds
private static final int SECOND_TO_TURN_ON = 60; // in seconds
private static final int SECOND_TO_TURN_OFF = 1; // in seconds
+ private static final int LOCK_DOOR = 0;
+ private static final int UNLOCK_DOOR = 1;
/**
* IoT Sets and Relations
* 4) Camera (detect motion)
* 5) Alarm (using ESP board) - assuming 1 house alarm
* 6) Room (object as place of device)
- *
- * Additionals (for more extensive home management)
* 7) Doorlock (detect open/locked)
- * 8) Power outlet (detect on/off, monitor watt)
*/
- // This comprises multipurpose, motion, and water leak sensors
- // TODO: Per 01/2017, doorlock and outlet are not ready, ESP board will be used for alarm
@config private IoTSet<SmartthingsSensorSmart> smartSensorsSet;
@config private IoTSet<CameraSmart> camSet;
@config private IoTSet<AlarmSmart> alarmSet;
@config private IoTSet<RoomSmart> roomSet;
- //@config private IoTSet<DoorLock> doorlockSet;
- //@config private IoTSet<Outlet> outletSet;
+ @config private IoTSet<SmartthingsActuatorSmart> doorlockSet;
@config private IoTRelation<RoomSmart, SmartthingsSensorSmart> roomSensorRelation;
@config private IoTRelation<RoomSmart, CameraSmart> roomCameraRelation;
//@config private IoTRelation<RoomSmart, DoorLock> roomDoorLockRelation;
- //@config private IoTRelation<RoomSmart, Outlet> roomOutletRelation;
/*******************************************************************************************************************************************
**
long lastTimeChecked = 0;
private static int sensorId = 0;
+ private static int doorlockId = 0;
/*******************************************************************************************************************************************
**
// Camera (true = motion)
private Map<CameraSmart, Boolean> camDetectStatus =
new HashMap<CameraSmart, Boolean>();
- // Doorlock (true = open - not locked)
- //private Map<DoorLock, Boolean> doorlockStatus =
- // new HashMap<DoorLock, Boolean>();
- // Outlet (true = on - outlet is used)
- //private Map<Outlet, Boolean> outletStatus =
- // new HashMap<Outlet, Boolean>();
+ // Doorlock (true = locked)
+ private Map<Integer, Boolean> doorlockStatus =
+ new HashMap<Integer, Boolean>();
// Alarm status
private Map<Integer, Boolean> alarmStatus =
*
* @return [void] None.
*/
- private void initDoorLocks(RoomSmart rm) {
+ private void initDoorLocks() {
- // Get and init the doorlocks for this specific room
- /*HashSet<DoorLock> doorlocks = roomDoorLockRelation.get(rm);
- for (DoorLock doorlock : doorlocks) {
+ // Get and init the doorlocks (we only assume 1 main doorlock)
+ Set<SmartthingsActuatorSmart> doorlocks = doorlockSet.values();
+ for (SmartthingsActuatorSmart doorlock : doorlocks) {
try {
// Initialize doorlocks
doorlock.init();
- System.out.println("DEBUG: Initialized doorlock!");
+ System.out.println("DEBUG: Initialized doorlock! ID: " + doorlockId);
+ doorlockStatus.put(doorlockId, false);
+ System.out.println("DEBUG: Initialized doorlock status to false!");
+ doorlock.setId(doorlockId++);
+ doorlock.registerCallback(this);
+ System.out.println("DEBUG: Registered doorlock callback!");
} catch (Exception e) {
e.printStackTrace();
}
- }*/
- }
-
-
- /** Method to initialize power outlets
- *
- * @return [void] None.
- */
- private void initOutlets(RoomSmart rm) {
-
- // Get and init the outlets for this specific room
- /*HashSet<Outlet> outlets = roomOutletRelation.get(rm);
- for (Outlet outlet : outlets) {
-
- try {
- // Initialize outlets
- outlet.init();
- System.out.println("DEBUG: Initialized outlet!");
- } catch (Exception e) {
- e.printStackTrace();
- }
- }*/
+ }
}
}
}
-
- /** Method to update state data structures for doorlocks
- *
- * @return [void] None.
- */
- private void updateDoorLockStatus(RoomSmart rm) {
-
- // Get and init the outlets for this specific room
- /*HashSet<DoorLock> doorlocks = roomDoorLockRelation.get(rm);
- for (DoorLock doorlock : doorlocks) {
-
- // Change is detected! Set to true for report...
- if(isChangeDetected()) {
-
- doorlockStatus.put(doorlock, true);
- } else {
-
- doorlockStatus.put(doorlock, false);
- }
- }*/
- }
-
-
- /** Method to update state data structures for outlets
+ /** Method to update state data structures for Smartthings actuators
*
* @return [void] None.
*/
- private void updateOutletStatus(RoomSmart rm) {
-
- // Get and init the outlets for this specific room
- /*HashSet<Outlet> outlets = roomOutletRelation.get(rm);
- for (Outlet outlet : outlets) {
-
- // Change is detected! Set to true for report...
- if(isChangeDetected()) {
+ public void newActuatorReadingAvailable(int _sensorId, int _value, boolean _activeValue) {
- outletStatus.put(outlet, true);
- } else {
+ System.out.println("DEBUG: Actuator reading value: " + _value);
+ if(_activeValue) {
+ System.out.println("DEBUG: Actuator is detecting something: " + _activeValue);
+ doorlockStatus.put(_sensorId, true);
- outletStatus.put(outlet, false);
- }
- }*/
+ } else {
+ //System.out.println("DEBUG: Sensor is not detecting something: " + _activeValue);
+ doorlockStatus.put(_sensorId, false);
+ }
}
// Update status of camera
updateCameraStatus(room);
- // Update status of doorlocks
- //updateDoorLockStatus(room);
-
- // Update status of outlets
- //updateOutletStatus(room);
+ // Update status of other devices if any
+ // ...
}
}
}
+ /** Method to lock doors
+ *
+ * @return [void] None.
+ */
+ private void lockDoors() {
+
+ // Get and lock the doorlocks (we only assume 1 main doorlock)
+ Set<SmartthingsActuatorSmart> doorlocks = doorlockSet.values();
+ for (SmartthingsActuatorSmart doorlock : doorlocks) {
+
+ doorlock.actuate(LOCK_DOOR);
+ System.out.println("DEBUG: Lock doorlock! ID: " + doorlock.getId());
+ }
+ }
+
+
/** Check status of devices and turn on alarm accordingly
* <p>
* Simple rule is whenever any sensor or camera detect something unusual
zoneId = room.getRoomID();
turnOnAlarms(zoneId);
System.out.println("DETECTION: Camera active in room: " + zoneId);
+ lockDoors();
}
}
turnOnAlarms(zoneId);
System.out.println("DETECTION: Sensor active in room: " + zoneId);
System.out.println("DETECTION: Detection by sensor: " + sensor.getId());
+ lockDoors();
}
}
}
initCameras(rm);
// Init all doorlocks
- //initDoorLocks();
+ initDoorLocks();
- // Init all outlets
- //initOutlets();
}
// Init all alarms
homesecurity:
$(JAVAC) $(JFLAGS) *.java
cp HomeSecurityController.config $(BIN_DIR)/HomeSecurityController
- cd $(BIN_DIR)/HomeSecurityController; $(JAR) $(JARFLAGS) HomeSecurityController.jar ../HomeSecurityController/HomeSecurityController*.class ../HomeSecurityController/*.class ../iotcode/interfaces/SmartthingsSensor*.class ../iotcode/interfaces/Camera*.class ../iotcode/interfaces/Alarm*.class ../iotcode/interfaces/Room*.class ../iotcode/interfaces/ZoneState*.class ../iotcode/interfaces/Resolution*.class
+ cd $(BIN_DIR)/HomeSecurityController; $(JAR) $(JARFLAGS) HomeSecurityController.jar ../HomeSecurityController/HomeSecurityController*.class ../HomeSecurityController/*.class ../iotcode/interfaces/SmartthingsSensor*.class ../iotcode/interfaces/SmartthingsActuator*.class ../iotcode/interfaces/Camera*.class ../iotcode/interfaces/Alarm*.class ../iotcode/interfaces/Room*.class ../iotcode/interfaces/ZoneState*.class ../iotcode/interfaces/Resolution*.class
PHONY += check-homesecurity
check-homesecurity:
$(JAVAC) $(JFLAGS) $(CHECKER_OPT) $(ASTUBS) *.java
cp HomeSecurityController.config $(BIN_DIR)/HomeSecurityController
- cd $(BIN_DIR)/HomeSecurityController; $(JAR) $(JARFLAGS) HomeSecurityController.jar ../HomeSecurityController/HomeSecurityController*.class ../HomeSecurityController/*.class ../iotcode/interfaces/SmartthingsSensor*.class ../iotcode/interfaces/Camera*.class ../iotcode/interfaces/Alarm*.class ../iotcode/interfaces/Room*.class ../iotcode/interfaces/ZoneState*.class ../iotcode/interfaces/Resolution*.class
+ cd $(BIN_DIR)/HomeSecurityController; $(JAR) $(JARFLAGS) HomeSecurityController.jar ../HomeSecurityController/HomeSecurityController*.class ../HomeSecurityController/*.class ../iotcode/interfaces/SmartthingsSensor*.class ../iotcode/interfaces/SmartthingsActuator*.class ../iotcode/interfaces/Camera*.class ../iotcode/interfaces/Alarm*.class ../iotcode/interfaces/Room*.class ../iotcode/interfaces/ZoneState*.class ../iotcode/interfaces/Resolution*.class
.PHONY: $(PHONY)
--- /dev/null
+package HomeSecurityController;
+
+import java.io.IOException;
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Map;
+import java.util.HashMap;
+import java.util.concurrent.atomic.AtomicBoolean;
+import iotrmi.Java.IoTRMIComm;
+import iotrmi.Java.IoTRMICommClient;
+import iotrmi.Java.IoTRMICommServer;
+import iotrmi.Java.IoTRMIUtil;
+
+import iotcode.interfaces.*;
+
+public class SmartthingsActuatorCallback_Skeleton implements SmartthingsActuatorCallback {
+
+ private SmartthingsActuatorCallback mainObj;
+ private int objectId = 2;
+ // Communications and synchronizations
+ private IoTRMIComm rmiComm;
+ private AtomicBoolean didAlreadyInitWaitInvoke;
+ private AtomicBoolean methodReceived;
+ private byte[] methodBytes = null;
+ // Permissions
+ private static Integer[] object2Permission = { 0 };
+ private static List<Integer> set2Allowed;
+
+
+ public SmartthingsActuatorCallback_Skeleton(SmartthingsActuatorCallback _mainObj, int _portSend, int _portRecv) throws Exception {
+ mainObj = _mainObj;
+ rmiComm = new IoTRMICommServer(_portSend, _portRecv);
+ set2Allowed = new ArrayList<Integer>(Arrays.asList(object2Permission));
+ IoTRMIUtil.mapSkel.put(_mainObj, this);
+ IoTRMIUtil.mapSkelId.put(_mainObj, objectId);
+ didAlreadyInitWaitInvoke = new AtomicBoolean(false);
+ methodReceived = new AtomicBoolean(false);
+ rmiComm.registerSkeleton(objectId, methodReceived);
+ Thread thread1 = new Thread() {
+ public void run() {
+ try {
+ ___waitRequestInvokeMethod();
+ }
+ catch (Exception ex)
+ {
+ ex.printStackTrace();
+ }
+ }
+ };
+ thread1.start();
+ }
+
+ public SmartthingsActuatorCallback_Skeleton(SmartthingsActuatorCallback _mainObj, IoTRMIComm _rmiComm, int _objectId) throws Exception {
+ mainObj = _mainObj;
+ rmiComm = _rmiComm;
+ objectId = _objectId;
+ set2Allowed = new ArrayList<Integer>(Arrays.asList(object2Permission));
+ didAlreadyInitWaitInvoke = new AtomicBoolean(false);
+ methodReceived = new AtomicBoolean(false);
+ rmiComm.registerSkeleton(objectId, methodReceived);
+ }
+
+ public boolean didAlreadyInitWaitInvoke() {
+ return didAlreadyInitWaitInvoke.get();
+ }
+
+ public void newActuatorReadingAvailable(int _sensorId, int _value, boolean _activeValue) {
+ mainObj.newActuatorReadingAvailable(_sensorId, _value, _activeValue);
+ }
+
+ public void ___newActuatorReadingAvailable() {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { int.class, int.class, boolean.class }, new Class<?>[] { null, null, null }, localMethodBytes);
+ newActuatorReadingAvailable((int) paramObj[0], (int) paramObj[1], (boolean) paramObj[2]);
+ }
+
+ public void ___waitRequestInvokeMethod() throws IOException {
+ didAlreadyInitWaitInvoke.compareAndSet(false, true);
+ while (true) {
+ if (!methodReceived.get()) {
+ continue;
+ }
+ methodBytes = rmiComm.getMethodBytes();
+ methodReceived.set(false);
+ int _objectId = IoTRMIComm.getObjectId(methodBytes);
+ int methodId = IoTRMIComm.getMethodId(methodBytes);
+ if (_objectId == objectId) {
+ if (!set2Allowed.contains(methodId)) {
+ throw new Error("Object with object Id: " + _objectId + " is not allowed to access method: " + methodId);
+ }
+ }
+ else {
+ continue;
+ }
+ switch (methodId) {
+ case 0:
+ new Thread() {
+ public void run() {
+ try {
+ ___newActuatorReadingAvailable();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ default:
+ throw new Error("Method Id " + methodId + " not recognized!");
+ }
+ }
+ }
+
+}
--- /dev/null
+package HomeSecurityController;
+
+import java.io.IOException;
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Map;
+import java.util.HashMap;
+import java.util.concurrent.atomic.AtomicBoolean;
+import iotrmi.Java.IoTRMIComm;
+import iotrmi.Java.IoTRMICommClient;
+import iotrmi.Java.IoTRMICommServer;
+import iotrmi.Java.IoTRMIUtil;
+
+import iotcode.interfaces.*;
+
+public class SmartthingsActuatorSmart_Stub implements SmartthingsActuatorSmart {
+
+ private int objectId = 1;
+ private IoTRMIComm rmiComm;
+ // Synchronization variables
+ private AtomicBoolean retValueReceived5 = new AtomicBoolean(false);
+ private AtomicBoolean retValueReceived7 = new AtomicBoolean(false);
+ private AtomicBoolean retValueReceived4 = new AtomicBoolean(false);
+ private AtomicBoolean retValueReceived3 = new AtomicBoolean(false);
+ private AtomicBoolean retValueReceived1 = new AtomicBoolean(false);
+
+
+ public SmartthingsActuatorSmart_Stub(int _localPortSend, int _localPortRecv, int _portSend, int _portRecv, String _skeletonAddress, int _rev) throws Exception {
+ if (_localPortSend != 0 && _localPortRecv != 0) {
+ rmiComm = new IoTRMICommClient(_localPortSend, _localPortRecv, _portSend, _portRecv, _skeletonAddress, _rev);
+ } else
+ {
+ rmiComm = new IoTRMICommClient(_portSend, _portRecv, _skeletonAddress, _rev);
+ }
+ rmiComm.registerStub(objectId, 5, retValueReceived5);
+ rmiComm.registerStub(objectId, 7, retValueReceived7);
+ rmiComm.registerStub(objectId, 4, retValueReceived4);
+ rmiComm.registerStub(objectId, 3, retValueReceived3);
+ rmiComm.registerStub(objectId, 1, retValueReceived1);
+ IoTRMIUtil.mapStub.put(objectId, this);
+ }
+
+ public SmartthingsActuatorSmart_Stub(IoTRMIComm _rmiComm, int _objectId) throws Exception {
+ rmiComm = _rmiComm;
+ objectId = _objectId;
+ rmiComm.registerStub(objectId, 5, retValueReceived5);
+ rmiComm.registerStub(objectId, 7, retValueReceived7);
+ rmiComm.registerStub(objectId, 4, retValueReceived4);
+ rmiComm.registerStub(objectId, 3, retValueReceived3);
+ rmiComm.registerStub(objectId, 1, retValueReceived1);
+ }
+
+ public long getTimestampOfLastReading() {
+ int methodId = 5;
+ Class<?> retType = long.class;
+ Class<?>[] paramCls = new Class<?>[] { };
+ Object[] paramObj = new Object[] { };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ // Waiting for return value
+ while (!retValueReceived5.get());
+ Object retObj = rmiComm.getReturnValue(retType, null);
+ retValueReceived5.set(false);
+ rmiComm.setGetReturnBytes();
+
+ return (long)retObj;
+ }
+
+ public int getId() {
+ int methodId = 7;
+ Class<?> retType = int.class;
+ Class<?>[] paramCls = new Class<?>[] { };
+ Object[] paramObj = new Object[] { };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ // Waiting for return value
+ while (!retValueReceived7.get());
+ Object retObj = rmiComm.getReturnValue(retType, null);
+ retValueReceived7.set(false);
+ rmiComm.setGetReturnBytes();
+
+ return (int)retObj;
+ }
+
+ public void registerCallback(SmartthingsActuatorCallback _callbackTo) {
+ int[] objIdSent0 = new int[1];
+ try {
+ if (!IoTRMIUtil.mapSkel.containsKey(_callbackTo)) {
+ int newObjIdSent = rmiComm.getObjectIdCounter();
+ objIdSent0[0] = newObjIdSent;
+ rmiComm.decrementObjectIdCounter();
+ SmartthingsActuatorCallback_Skeleton skel0 = new SmartthingsActuatorCallback_Skeleton(_callbackTo, rmiComm, newObjIdSent);
+ IoTRMIUtil.mapSkel.put(_callbackTo, skel0);
+ IoTRMIUtil.mapSkelId.put(_callbackTo, newObjIdSent);
+ Thread thread = new Thread() {
+ public void run() {
+ try {
+ skel0.___waitRequestInvokeMethod();
+ } catch (Exception ex) {
+ ex.printStackTrace();
+ throw new Error("Exception when trying to run ___waitRequestInvokeMethod() for SmartthingsActuatorCallback_Skeleton!");
+ }
+ }
+ };
+ thread.start();
+ while(!skel0.didAlreadyInitWaitInvoke());
+ }
+ else
+ {
+ int newObjIdSent = IoTRMIUtil.mapSkelId.get(_callbackTo);
+ objIdSent0[0] = newObjIdSent;
+ }
+ } catch (Exception ex) {
+ ex.printStackTrace();
+ throw new Error("Exception when generating skeleton objects!");
+ }
+
+ int methodId = 8;
+ Class<?> retType = void.class;
+ Class<?>[] paramCls = new Class<?>[] { int[].class };
+ Object[] paramObj = new Object[] { objIdSent0 };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ }
+
+ public void requestStatus() {
+ int methodId = 2;
+ Class<?> retType = void.class;
+ Class<?>[] paramCls = new Class<?>[] { };
+ Object[] paramObj = new Object[] { };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ }
+
+ public void setId(int id) {
+ int methodId = 6;
+ Class<?> retType = void.class;
+ Class<?>[] paramCls = new Class<?>[] { int.class };
+ Object[] paramObj = new Object[] { id };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ }
+
+ public boolean isActiveStatus() {
+ int methodId = 4;
+ Class<?> retType = boolean.class;
+ Class<?>[] paramCls = new Class<?>[] { };
+ Object[] paramObj = new Object[] { };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ // Waiting for return value
+ while (!retValueReceived4.get());
+ Object retObj = rmiComm.getReturnValue(retType, null);
+ retValueReceived4.set(false);
+ rmiComm.setGetReturnBytes();
+
+ return (boolean)retObj;
+ }
+
+ public int getStatus() {
+ int methodId = 3;
+ Class<?> retType = int.class;
+ Class<?>[] paramCls = new Class<?>[] { };
+ Object[] paramObj = new Object[] { };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ // Waiting for return value
+ while (!retValueReceived3.get());
+ Object retObj = rmiComm.getReturnValue(retType, null);
+ retValueReceived3.set(false);
+ rmiComm.setGetReturnBytes();
+
+ return (int)retObj;
+ }
+
+ public void init() {
+ int methodId = 0;
+ Class<?> retType = void.class;
+ Class<?>[] paramCls = new Class<?>[] { };
+ Object[] paramObj = new Object[] { };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ }
+
+ public boolean actuate(int value) {
+ int methodId = 1;
+ Class<?> retType = boolean.class;
+ Class<?>[] paramCls = new Class<?>[] { int.class };
+ Object[] paramObj = new Object[] { value };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ // Waiting for return value
+ while (!retValueReceived1.get());
+ Object retObj = rmiComm.getReturnValue(retType, null);
+ retValueReceived1.set(false);
+ rmiComm.setGetReturnBytes();
+
+ return (boolean)retObj;
+ }
+
+}
--- /dev/null
+# Skeleton/original interface
+INTERFACE_CLASS=SmartthingsActuator
+# Stub
+INTERFACE_STUB_CLASS=SmartthingsActuatorSmart
+
+# Language
+LANGUAGE=Java
--- /dev/null
+package iotcode.DoorlockActuator;
+
+// Standard Java Packages
+import java.util.*;
+import java.util.concurrent.atomic.AtomicBoolean;
+import java.util.concurrent.CopyOnWriteArrayList;
+import java.util.concurrent.Semaphore;
+
+// Checker annotations
+//import iotchecker.qual.*;
+import iotcode.annotation.*;
+
+// IoT Packages
+import iotruntime.slave.*;
+import iotcode.interfaces.*;
+import iotruntime.zigbee.*;
+
+/** Class Smartthings sensor driver for Smartthings sensor devices.
+ *
+ * @author Changwoo Lee, Rahmadi Trimananda <rtrimana @ uci.edu>
+ * @version 1.0
+ * @since 2016-12-01
+ */
+public class DoorlockActuator implements IoTZigbeeCallback, SmartthingsActuator {
+
+ private final int TIMEOUT_FOR_RESEND_MSEC = 900;
+
+ private IoTZigbee zigConnection = null;
+ private boolean didClose; // make sure that the clean up was done correctly
+ private boolean detectStatus = false;
+
+ private int detectedValue = 0;
+ private Date timestampOfLastDetecting = null;
+
+ private AtomicBoolean didAlreadyClose = new AtomicBoolean(true);
+ private AtomicBoolean didAlreadyInit = new AtomicBoolean(false);
+ private AtomicBoolean didWriteAttrb = new AtomicBoolean(false);
+ private AtomicBoolean didMatchDscr = new AtomicBoolean(false);
+ private AtomicBoolean didBind = new AtomicBoolean(false);
+ private AtomicBoolean didDoorLockConfigureReporting = new AtomicBoolean(false); //made by Jiawei
+ static Semaphore gettingLatestDataMutex = new Semaphore(1);
+
+ private List < SmartthingsActuatorSmartCallback > callbackList = new CopyOnWriteArrayList < SmartthingsActuatorSmartCallback > ();
+
+ private int sensorId = 0;
+
+ @config private IoTSet<IoTDeviceAddress> doorlockActuatorUdpAddress;
+ @config private IoTSet<IoTZigbeeAddress> doorlockActuatorZigbeeAddress;
+
+ public DoorlockActuator(IoTSet<IoTDeviceAddress> dSet, IoTSet<IoTZigbeeAddress> zigSet) {
+ doorlockActuatorUdpAddress = dSet;
+ doorlockActuatorZigbeeAddress = zigSet;
+ }
+
+ public DoorlockActuator() {
+ }
+
+ public void init() {
+
+ if (didAlreadyInit.compareAndSet(false, true) == false) {
+ return; // already init
+ }
+
+ didAlreadyClose.set(false);
+
+ try {
+ Iterator itrUdp = doorlockActuatorUdpAddress.iterator();
+ Iterator itrZig = doorlockActuatorZigbeeAddress.iterator();
+
+ zigConnection = new IoTZigbee((IoTDeviceAddress)itrUdp.next(), (IoTZigbeeAddress)itrZig.next());
+
+ // DEBUG
+ System.out.println("DEBUG: Allocate iterators to print out addresses!");
+ Iterator itrDebugUdp = doorlockActuatorUdpAddress.iterator();
+ IoTDeviceAddress iotaddDebug = (IoTDeviceAddress)itrDebugUdp.next();
+ System.out.println("IP address: " + iotaddDebug.getCompleteAddress());
+ System.out.println("Source port: " + iotaddDebug.getSourcePortNumber());
+ System.out.println("Destination port: " + iotaddDebug.getDestinationPortNumber());
+
+ Iterator itrDebugZig = doorlockActuatorZigbeeAddress.iterator();
+ IoTZigbeeAddress iotzbaddDebug = (IoTZigbeeAddress)itrDebugZig.next();
+ System.out.println("Zigbee address: " + iotzbaddDebug.getAddress());
+
+ zigConnection.registerCallback(this);
+ System.out.println("Register callback!");
+ zigConnection.init();
+ System.out.println("Initialized!");
+
+
+
+ //made by changwoo
+ sleep(10);
+
+ // System.out.println("BroadcastingRouteRecordRequest ");
+ // zigConnection.sendBroadcastingRouteRecordRequest(0x0001);
+ // sleep(6);
+
+ System.out.println("Sending Management Permit Joining Request");
+ // for(int z=0; z<3; z++){
+ zigConnection.sendManagementPermitJoiningRequest(0x0002, 0x0036, 0x00);
+ sleep(0);
+ // }
+
+
+ while(!didBind.get()){
+ System.out.println("Sending Bind Request");
+ zigConnection.sendBindRequest(0x0003, 0x0101, 0x02);
+ sleep(0);
+ }
+
+ while(!didDoorLockConfigureReporting.get()){
+ System.out.println("Sending Door Lock: Configure Reporting");
+ zigConnection.sendConfigureReportingCommand(0x0004, 0x0101, 0x0104, 0x01, 0x02, 0x0000, 0x30, 0x0000, 0x100E, null);
+ sleep(0);
+ }
+
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ * actuate() method
+ *
+ * @param value Integer value for actuation
+ * @return boolean Status of sending actuate command
+ */
+ public boolean actuate(int value) {
+
+ // Value check
+ if (value == 0)
+ System.out.println("Doorlock: Is locking!");
+ else if(value == 1)
+ System.out.println("Doorlock: Is unlocking!");
+ else { // Failed to send command because of invalid value
+ throw new Error("Doorlock: Actuate value " + value + " is not recognized (only 0 or 1)! Please check your method call...");
+ }
+ try {
+ zigConnection.sendLockOrUnlockDoorRequest(0x0005, 0x0101, 0x0104, 0x02, value);
+ sleep(0);
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ return true;
+ }
+
+ /**
+ * requestStatus() method
+ *
+ * @return void
+ */
+ public void requestStatus() {
+ System.out.println("Doorlock: Requesting status... Receiving answer through callback...");
+ try {
+ zigConnection.sendReadDoorStatusRequest(0x0005, 0x0101, 0x0104, 0x02, 0x10, 0x00, 0x0000);
+ sleep(0);
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
+ //made by changwoo
+ private void sleep(int multipleTime){
+ if(multipleTime<=0){
+ multipleTime=1;
+ }
+ try{
+ Thread.sleep(TIMEOUT_FOR_RESEND_MSEC*multipleTime);
+ } catch(Exception e){
+ e.printStackTrace();
+ }
+ }
+
+ // made by Jiawei
+ public int getStatus() {
+
+ int tmp = 0;
+
+ try {
+ gettingLatestDataMutex.acquire();
+ tmp = detectedValue;
+
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ gettingLatestDataMutex.release();
+
+ return tmp;
+ }
+
+ public boolean isActiveStatus() {
+
+ int tmp = getStatus();
+ if (tmp == 1)
+ detectStatus = true; // ACTIVE == Door is locked
+ else
+ detectStatus = false; // NOT ACTIVE == Door is not locked/not fully locked
+ return detectStatus;
+ }
+
+ public void close() {
+
+ if (didAlreadyClose.compareAndSet(false, true) == false) {
+ return; // already init
+ }
+
+ didAlreadyInit.set(false);
+
+
+ try {
+ zigConnection.close();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
+ public void Finalize() {
+ if (!didClose) {
+ close();
+ }
+ }
+
+ public void setId(int id) {
+
+ sensorId = id;
+
+ }
+
+ public int getId() {
+
+ return sensorId;
+
+ }
+
+
+ public long getTimestampOfLastReading() {
+
+ Date tmp = null;
+ try {
+ gettingLatestDataMutex.acquire();
+ tmp = (Date)timestampOfLastDetecting.clone();
+
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ gettingLatestDataMutex.release();
+ long retLong = tmp.getTime();
+
+ return retLong;
+ }
+
+ public void newMessageAvailable(IoTZigbeeMessage _zm) {
+
+ //made by yuting
+ if (_zm instanceof IoTZigbeeMessageZdoBindResponse) {
+ IoTZigbeeMessageZdoBindResponse message = (IoTZigbeeMessageZdoBindResponse)_zm;
+ if (message.getSucceeded()) {
+ didBind.set(true);
+ }
+ }
+ else if (_zm instanceof IoTZigbeeMessageZclConfigureReportingResponse){
+ IoTZigbeeMessageZclConfigureReportingResponse message = (IoTZigbeeMessageZclConfigureReportingResponse)_zm;
+ if (message.getAllSuccess()) {
+ didDoorLockConfigureReporting.set(true);
+ }
+ }
+ else if (_zm instanceof IoTZigbeeMessageZclReadAttributesResponse) {
+ IoTZigbeeMessageZclReadAttributesResponse message = (IoTZigbeeMessageZclReadAttributesResponse)_zm;
+ List <IoTZigbeeMessageZclReadAttributesResponse.Attribute> attrList = message.getAttributes();
+
+ if (attrList.size() == 1) {
+ if(attrList.get(0).getAttributeId() == 0) {
+ byte[] data = attrList.get(0).getData();
+ int value = data[0];
+
+ try {
+ gettingLatestDataMutex.acquire();
+ detectedValue = value;
+ timestampOfLastDetecting = new Date();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ gettingLatestDataMutex.release();
+
+ try {
+ for (SmartthingsActuatorSmartCallback cb : callbackList) {
+ cb.newActuatorReadingAvailable(this.getId(), this.getStatus(), this.isActiveStatus());
+ }
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+ }
+ }
+ }
+
+ public void registerCallback(SmartthingsActuatorSmartCallback _callbackTo) {
+ callbackList.add(_callbackTo);
+ }
+}
--- /dev/null
+package iotcode.DoorlockActuator;
+
+import java.io.IOException;
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Map;
+import java.util.HashMap;
+import java.util.concurrent.atomic.AtomicBoolean;
+import iotrmi.Java.IoTRMIComm;
+import iotrmi.Java.IoTRMICommClient;
+import iotrmi.Java.IoTRMICommServer;
+import iotrmi.Java.IoTRMIUtil;
+
+import iotcode.interfaces.*;
+
+public class SmartthingsActuatorSmartCallback_Stub implements SmartthingsActuatorSmartCallback {
+
+ private int objectId = 2;
+ private IoTRMIComm rmiComm;
+ // Synchronization variables
+
+
+ public SmartthingsActuatorSmartCallback_Stub(int _localPortSend, int _localPortRecv, int _portSend, int _portRecv, String _skeletonAddress, int _rev) throws Exception {
+ if (_localPortSend != 0 && _localPortRecv != 0) {
+ rmiComm = new IoTRMICommClient(_localPortSend, _localPortRecv, _portSend, _portRecv, _skeletonAddress, _rev);
+ } else
+ {
+ rmiComm = new IoTRMICommClient(_portSend, _portRecv, _skeletonAddress, _rev);
+ }
+ IoTRMIUtil.mapStub.put(objectId, this);
+ }
+
+ public SmartthingsActuatorSmartCallback_Stub(IoTRMIComm _rmiComm, int _objectId) throws Exception {
+ rmiComm = _rmiComm;
+ objectId = _objectId;
+ }
+
+ public void newActuatorReadingAvailable(int _sensorId, int _value, boolean _activeValue) {
+ int methodId = 0;
+ Class<?> retType = void.class;
+ Class<?>[] paramCls = new Class<?>[] { int.class, int.class, boolean.class };
+ Object[] paramObj = new Object[] { _sensorId, _value, _activeValue };
+ rmiComm.remoteCall(objectId, methodId, paramCls, paramObj);
+ }
+
+}
--- /dev/null
+package iotcode.DoorlockActuator;
+
+import java.io.IOException;
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Map;
+import java.util.HashMap;
+import java.util.concurrent.atomic.AtomicBoolean;
+import iotrmi.Java.IoTRMIComm;
+import iotrmi.Java.IoTRMICommClient;
+import iotrmi.Java.IoTRMICommServer;
+import iotrmi.Java.IoTRMIUtil;
+
+import iotcode.interfaces.*;
+
+public class SmartthingsActuator_Skeleton implements SmartthingsActuator {
+
+ private SmartthingsActuator mainObj;
+ private int objectId = 1;
+ // Communications and synchronizations
+ private IoTRMIComm rmiComm;
+ private AtomicBoolean didAlreadyInitWaitInvoke;
+ private AtomicBoolean methodReceived;
+ private byte[] methodBytes = null;
+ // Permissions
+ private static Integer[] object1Permission = { 5, 7, 8, 2, 6, 4, 3, 0, 1 };
+ private static List<Integer> set1Allowed;
+
+
+ public SmartthingsActuator_Skeleton(SmartthingsActuator _mainObj, int _portSend, int _portRecv) throws Exception {
+ mainObj = _mainObj;
+ rmiComm = new IoTRMICommServer(_portSend, _portRecv);
+ set1Allowed = new ArrayList<Integer>(Arrays.asList(object1Permission));
+ IoTRMIUtil.mapSkel.put(_mainObj, this);
+ IoTRMIUtil.mapSkelId.put(_mainObj, objectId);
+ didAlreadyInitWaitInvoke = new AtomicBoolean(false);
+ methodReceived = new AtomicBoolean(false);
+ rmiComm.registerSkeleton(objectId, methodReceived);
+ Thread thread1 = new Thread() {
+ public void run() {
+ try {
+ ___waitRequestInvokeMethod();
+ }
+ catch (Exception ex)
+ {
+ ex.printStackTrace();
+ }
+ }
+ };
+ thread1.start();
+ }
+
+ public SmartthingsActuator_Skeleton(SmartthingsActuator _mainObj, IoTRMIComm _rmiComm, int _objectId) throws Exception {
+ mainObj = _mainObj;
+ rmiComm = _rmiComm;
+ objectId = _objectId;
+ set1Allowed = new ArrayList<Integer>(Arrays.asList(object1Permission));
+ didAlreadyInitWaitInvoke = new AtomicBoolean(false);
+ methodReceived = new AtomicBoolean(false);
+ rmiComm.registerSkeleton(objectId, methodReceived);
+ }
+
+ public boolean didAlreadyInitWaitInvoke() {
+ return didAlreadyInitWaitInvoke.get();
+ }
+
+ public void init() {
+ mainObj.init();
+ }
+
+ public boolean actuate(int value) {
+ return mainObj.actuate(value);
+ }
+
+ public void requestStatus() {
+ mainObj.requestStatus();
+ }
+
+ public int getStatus() {
+ return mainObj.getStatus();
+ }
+
+ public boolean isActiveStatus() {
+ return mainObj.isActiveStatus();
+ }
+
+ public long getTimestampOfLastReading() {
+ return mainObj.getTimestampOfLastReading();
+ }
+
+ public void setId(int id) {
+ mainObj.setId(id);
+ }
+
+ public int getId() {
+ return mainObj.getId();
+ }
+
+ public void registerCallback(SmartthingsActuatorSmartCallback _callbackTo) {
+ mainObj.registerCallback(_callbackTo);
+ }
+
+ public void ___init() {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { }, new Class<?>[] { }, localMethodBytes);
+ init();
+ }
+
+ public void ___actuate() throws IOException {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { int.class }, new Class<?>[] { null }, localMethodBytes);
+ Object retObj = actuate((int) paramObj[0]);
+ rmiComm.sendReturnObj(retObj, localMethodBytes);
+ }
+
+ public void ___requestStatus() {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { }, new Class<?>[] { }, localMethodBytes);
+ requestStatus();
+ }
+
+ public void ___getStatus() throws IOException {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { }, new Class<?>[] { }, localMethodBytes);
+ Object retObj = getStatus();
+ rmiComm.sendReturnObj(retObj, localMethodBytes);
+ }
+
+ public void ___isActiveStatus() throws IOException {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { }, new Class<?>[] { }, localMethodBytes);
+ Object retObj = isActiveStatus();
+ rmiComm.sendReturnObj(retObj, localMethodBytes);
+ }
+
+ public void ___getTimestampOfLastReading() throws IOException {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { }, new Class<?>[] { }, localMethodBytes);
+ Object retObj = getTimestampOfLastReading();
+ rmiComm.sendReturnObj(retObj, localMethodBytes);
+ }
+
+ public void ___setId() {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { int.class }, new Class<?>[] { null }, localMethodBytes);
+ setId((int) paramObj[0]);
+ }
+
+ public void ___getId() throws IOException {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { }, new Class<?>[] { }, localMethodBytes);
+ Object retObj = getId();
+ rmiComm.sendReturnObj(retObj, localMethodBytes);
+ }
+
+ public void ___registerCallback() {
+ byte[] localMethodBytes = methodBytes;
+ rmiComm.setGetMethodBytes();
+ Object[] paramObj = rmiComm.getMethodParams(new Class<?>[] { int[].class }, new Class<?>[] { null }, localMethodBytes);
+ try {
+ int[] stubIdArray0 = (int[]) paramObj[0];
+ int objIdRecv0 = stubIdArray0[0];
+ SmartthingsActuatorSmartCallback newStub0 = null;
+ if(!IoTRMIUtil.mapStub.containsKey(objIdRecv0)) {
+ newStub0 = new SmartthingsActuatorSmartCallback_Stub(rmiComm, objIdRecv0);
+ IoTRMIUtil.mapStub.put(objIdRecv0, newStub0);
+ rmiComm.setObjectIdCounter(objIdRecv0);
+ rmiComm.decrementObjectIdCounter();
+ }
+ else {
+ newStub0 = (SmartthingsActuatorSmartCallback_Stub) IoTRMIUtil.mapStub.get(objIdRecv0);
+ }
+ SmartthingsActuatorSmartCallback stub0 = newStub0;
+ registerCallback(stub0);
+ } catch(Exception ex) {
+ ex.printStackTrace();
+ throw new Error("Exception from callback object instantiation!");
+ }
+ }
+
+ public void ___waitRequestInvokeMethod() throws IOException {
+ didAlreadyInitWaitInvoke.compareAndSet(false, true);
+ while (true) {
+ if (!methodReceived.get()) {
+ continue;
+ }
+ methodBytes = rmiComm.getMethodBytes();
+ methodReceived.set(false);
+ int _objectId = IoTRMIComm.getObjectId(methodBytes);
+ int methodId = IoTRMIComm.getMethodId(methodBytes);
+ if (_objectId == objectId) {
+ if (!set1Allowed.contains(methodId)) {
+ throw new Error("Object with object Id: " + _objectId + " is not allowed to access method: " + methodId);
+ }
+ }
+ else {
+ continue;
+ }
+ switch (methodId) {
+ case 0:
+ new Thread() {
+ public void run() {
+ try {
+ ___init();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ case 1:
+ new Thread() {
+ public void run() {
+ try {
+ ___actuate();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ case 2:
+ new Thread() {
+ public void run() {
+ try {
+ ___requestStatus();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ case 3:
+ new Thread() {
+ public void run() {
+ try {
+ ___getStatus();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ case 4:
+ new Thread() {
+ public void run() {
+ try {
+ ___isActiveStatus();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ case 5:
+ new Thread() {
+ public void run() {
+ try {
+ ___getTimestampOfLastReading();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ case 6:
+ new Thread() {
+ public void run() {
+ try {
+ ___setId();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ case 7:
+ new Thread() {
+ public void run() {
+ try {
+ ___getId();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ case 8:
+ new Thread() {
+ public void run() {
+ try {
+ ___registerCallback();
+ }
+ catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+ }.start();
+ break;
+ default:
+ throw new Error("Method Id " + methodId + " not recognized!");
+ }
+ }
+ }
+
+}
ASTUBS = -Astubs=../../../checker/astubs/
-all: light camera labroom greenlawn sprinkler moisture weathergateway audioroom gpsgateway ihome homeroom alarm motion multipurpose waterleak
-check-all: check-light check-camera check-labroom check-greenlawn check-sprinkler check-moisture check-weathergateway check-audioroom check-gpsgateway check-ihome check-homeroom check-alarm check-motion check-multipurpose check-waterleak
+all: light camera labroom greenlawn sprinkler moisture weathergateway audioroom gpsgateway ihome homeroom alarm motion multipurpose waterleak doorlock doorlockactuator
+check-all: check-light check-camera check-labroom check-greenlawn check-sprinkler check-moisture check-weathergateway check-audioroom check-gpsgateway check-ihome check-homeroom check-alarm check-motion check-multipurpose check-waterleak check-doorlock check-doorlockactuator
# Compile - without checker
#
cp DoorlockSensor/DoorlockSensor.config $(BIN_DIR)/iotcode/DoorlockSensor
cd $(BIN_DIR)/iotcode/DoorlockSensor; $(JAR) $(JARFLAGS) DoorlockSensor.jar ../../iotcode/DoorlockSensor/*.class ../../iotcode/interfaces/SmartthingsSensor*.class ../../iotcode/interfaces/Camera*.class
+PHONY += doorlockactuator
+doorlockactuator:
+ $(JAVAC) $(JFLAGS) DoorlockActuator/*.java
+ cp DoorlockActuator/DoorlockActuator.config $(BIN_DIR)/iotcode/DoorlockActuator
+ cd $(BIN_DIR)/iotcode/DoorlockActuator; $(JAR) $(JARFLAGS) DoorlockActuator.jar ../../iotcode/DoorlockActuator/*.class ../../iotcode/interfaces/SmartthingsActuator*.class ../../iotcode/interfaces/Camera*.class
+
# Compile - with checker
#
PHONY += check-light
cp DoorlockSensor/DoorlockSensor.config $(BIN_DIR)/iotcode/DoorlockSensor
cd $(BIN_DIR)/iotcode/DoorlockSensor; $(JAR) $(JARFLAGS) DoorlockSensor.jar ../../iotcode/DoorlockSensor/*.class ../../iotcode/interfaces/SmartthingsSensor*.class ../../iotcode/interfaces/Camera*.class
+PHONY += check-doorlockactuator
+check-doorlockactuator:
+ $(JAVAC) $(JFLAGS) $(CHECKER_OPT) $(ASTUBS) DoorlockActuator/*.java
+ cp DoorlockActuator/DoorlockActuator.config $(BIN_DIR)/iotcode/DoorlockActuator
+ cd $(BIN_DIR)/iotcode/DoorlockActuator; $(JAR) $(JARFLAGS) DoorlockActuator.jar ../../iotcode/DoorlockActuator/*.class ../../iotcode/interfaces/SmartthingsActuator*.class ../../iotcode/interfaces/Camera*.class
+
.PHONY: $(PHONY)
--- /dev/null
+package iotcode.interfaces;
+
+import java.util.List;
+import java.util.ArrayList;
+
+public interface SmartthingsActuator {
+ public void init();
+ public boolean actuate(int value);
+ public void requestStatus();
+ public int getStatus();
+ public boolean isActiveStatus();
+ public long getTimestampOfLastReading();
+ public void setId(int id);
+ public int getId();
+ public void registerCallback(SmartthingsActuatorSmartCallback _callbackTo);
+}
--- /dev/null
+package iotcode.interfaces;
+
+import java.util.List;
+import java.util.ArrayList;
+
+public interface SmartthingsActuatorCallback {
+ public void newActuatorReadingAvailable(int _sensorId, int _value, boolean _activeValue);
+}
--- /dev/null
+package iotcode.interfaces;
+
+import java.util.List;
+import java.util.ArrayList;
+
+public interface SmartthingsActuatorSmart {
+
+ public long getTimestampOfLastReading();
+ public int getId();
+ public void registerCallback(SmartthingsActuatorCallback _callbackTo);
+ public void requestStatus();
+ public void setId(int id);
+ public boolean isActiveStatus();
+ public int getStatus();
+ public void init();
+ public boolean actuate(int value);
+}
--- /dev/null
+package iotcode.interfaces;
+
+import java.util.List;
+import java.util.ArrayList;
+
+public interface SmartthingsActuatorSmartCallback {
+
+ public void newActuatorReadingAvailable(int _sensorId, int _value, boolean _activeValue);
+}
cp ../localconfig/iotpolicy/SmartthingsSensor/*.req $(BIN_DIR)/iotpolicy/
cd $(BIN_DIR)/iotpolicy; $(JAVA) -cp .:..:../$(PARSERJARS):../$(BIN_DIR) iotpolicy.IoTCompiler smartthingssensor.pol smartthingssensor.req smartthingssensorcallback.pol smartthingssensorcallback.req -java Java
+PHONY += run-compiler-actuate
+run-compiler-actuate:
+ cp ../localconfig/iotpolicy/SmartthingsActuator/*.pol $(BIN_DIR)/iotpolicy/
+ cp ../localconfig/iotpolicy/SmartthingsActuator/*.req $(BIN_DIR)/iotpolicy/
+ cd $(BIN_DIR)/iotpolicy; $(JAVA) -cp .:..:../$(PARSERJARS):../$(BIN_DIR) iotpolicy.IoTCompiler smartthingsactuator.pol smartthingsactuator.req smartthingsactuatorcallback.pol smartthingsactuatorcallback.req -java Java
+
# TODO: Can remove this later - just to test-compile the resulted files from the compiler
PHONY += compile
compile:
--- /dev/null
+public interface SmartthingsActuator {
+
+ public void init();
+ public boolean actuate(int value);
+ public void requestStatus();
+ public int getStatus();
+ public boolean isActiveStatus();
+ public long getTimestampOfLastReading();
+ public void setId(int id);
+ public int getId();
+ public void registerCallback(SmartthingsActuatorCallback _callbackTo);
+
+ capability Initialize {
+ description = "Initialize object";
+ method = "init()";
+ method = "registerCallback(SmartthingsActuatorCallback _callbackTo)";
+ }
+
+ capability Actuate {
+ description = "Actuate device";
+ method = "actuate(int value)";
+ }
+
+ capability Status {
+ description = "Handle status";
+ method = "requestStatus()";
+ method = "getStatus()";
+ method = "isActiveStatus()";
+ method = "getTimestampOfLastReading()";
+ }
+
+ capability ActuatorId {
+ description = "Manage actuator Id";
+ method = "setId(int id)";
+ method = "getId()";
+ }
+}
+
+
--- /dev/null
+
+requires SmartthingsSensor with Initialize, Actuate, Status, ActuatorId as interface SmartthingsActuatorSmart;
+
--- /dev/null
+public interface SmartthingsActuatorCallback {
+
+ public void newActuatorReadingAvailable(int _sensorId, int _value, boolean _activeValue);
+
+ capability Callback {
+ description = "Callback method";
+ method = "newActuatorReadingAvailable(int _sensorId, int _value, boolean _activeValue)";
+ }
+}
+
+
--- /dev/null
+
+requires SmartthingsActuatorCallback with Callback as interface SmartthingsActuatorSmartCallback;
+
--- /dev/null
+SELECT * FROM
+IoTDeviceAddress
+WHERE
+TYPE='DoorlockActuatorAdd'
+;
--- /dev/null
+SELECT * FROM
+IoTZigbeeAddress
+WHERE
+TYPE='DoorlockActuatorZBAdd'
+;
--- /dev/null
+SELECT * FROM
+SmartthingsActuatorSmart
+;
</value>
</option>
</component>
- <component name="ProjectRootManager" version="2" languageLevel="JDK_1_7" assert-keyword="true" jdk-15="true" project-jdk-name="1.8" project-jdk-type="JavaSDK">
+ <component name="ProjectRootManager" version="2" languageLevel="JDK_1_8" assert-keyword="true" jdk-15="true" project-jdk-name="1.8" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/build/classes" />
</component>
<component name="ProjectType">
<file leaf-file-name="MainActivity.java" pinned="false" current-in-tab="false">
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/MainActivity.java">
<provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="607">
+ <state relative-caret-position="1350">
<caret line="101" column="21" selection-start-line="100" selection-start-column="12" selection-end-line="101" selection-end-column="21" />
<folding>
- <element signature="imports" expanded="true" />
- <element signature="e#3760#3821#0" expanded="true" />
- <element signature="e#4406#4461#0" expanded="true" />
+ <element signature="imports" expanded="false" />
</folding>
</state>
</provider>
<file leaf-file-name="EnrollDeviceActivity.java" pinned="false" current-in-tab="false">
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/EnrollDeviceActivity.java">
<provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="315">
+ <state relative-caret-position="525">
<caret line="51" column="12" selection-start-line="51" selection-start-column="8" selection-end-line="51" selection-end-column="12" />
- <folding>
- <element signature="imports" expanded="true" />
- <element signature="e#4975#4993#0" expanded="true" />
- </folding>
+ <folding />
</state>
</provider>
</entry>
<file leaf-file-name="SSH.java" pinned="false" current-in-tab="false">
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/SSH.java">
<provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="127">
+ <state relative-caret-position="1590">
<caret line="124" column="30" selection-start-line="124" selection-start-column="30" selection-end-line="124" selection-end-column="30" />
- <folding>
- <element signature="e#0#121#0" expanded="true" />
- <element signature="imports" expanded="true" />
- <element signature="e#2775#2783#0" expanded="true" />
- </folding>
+ <folding />
</state>
</provider>
</entry>
</file>
- <file leaf-file-name="ListActivity.java" pinned="false" current-in-tab="false">
+ <file leaf-file-name="ListActivity.java" pinned="false" current-in-tab="true">
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/ListActivity.java">
<provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="440">
+ <state relative-caret-position="15">
<caret line="47" column="8" selection-start-line="47" selection-start-column="8" selection-end-line="47" selection-end-column="8" />
<folding>
<element signature="imports" expanded="true" />
- <element signature="e#1953#2177#0" expanded="true" />
- <element signature="e#2176#2177#0" expanded="true" />
</folding>
</state>
</provider>
</entry>
</file>
- <file leaf-file-name="activity_list.xml" pinned="false" current-in-tab="false">
- <entry file="file://$PROJECT_DIR$/src/main/res/layout/activity_list.xml">
- <provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="126">
- <caret line="21" column="36" selection-start-line="21" selection-start-column="36" selection-end-line="21" selection-end-column="36" />
- <folding />
- </state>
- </provider>
- <provider editor-type-id="android-designer2">
- <state />
- </provider>
- </entry>
- </file>
- <file leaf-file-name="strings.xml" pinned="false" current-in-tab="true">
- <entry file="file://$PROJECT_DIR$/src/main/res/values/strings.xml">
- <provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="105">
- <caret line="7" column="80" selection-start-line="7" selection-start-column="80" selection-end-line="7" selection-end-column="80" />
- <folding />
- </state>
- </provider>
- </entry>
- </file>
</leaf>
</component>
<component name="FileTemplateManagerImpl">
<foldersAlwaysOnTop value="true" />
</navigator>
<panes>
- <pane id="Scratches" />
- <pane id="PackagesPane" />
- <pane id="AndroidView">
- <subPane />
- </pane>
<pane id="ProjectPane">
<subPane>
<PATH>
</subPane>
</pane>
<pane id="Scope" />
+ <pane id="PackagesPane" />
+ <pane id="AndroidView">
+ <subPane />
+ </pane>
+ <pane id="Scratches" />
</panes>
</component>
<component name="PropertiesComponent">
</component>
<component name="ToolWindowManager">
<frame x="65" y="24" width="1615" height="1026" extended-state="6" />
- <editor active="true" />
+ <editor active="false" />
<layout>
<window_info id="TODO" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.32719547" sideWeight="0.49475157" order="6" side_tool="false" content_ui="tabs" />
- <window_info id="Messages" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.28713968" sideWeight="0.458891" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Build Variants" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="true" content_ui="tabs" />
<window_info id="Image Layers" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="Capture Analysis" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="Event Log" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.32786885" sideWeight="0.5022307" order="7" side_tool="true" content_ui="tabs" />
<window_info id="Android Monitor" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.2827051" sideWeight="0.49840662" order="7" side_tool="false" content_ui="tabs" />
- <window_info id="Preview" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.2974108" sideWeight="0.5" order="4" side_tool="false" content_ui="tabs" />
<window_info id="Run" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25055432" sideWeight="0.5589548" order="2" side_tool="false" content_ui="tabs" />
<window_info id="Version Control" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Terminal" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3292683" sideWeight="0.4901211" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Captures" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="2" side_tool="false" content_ui="tabs" />
<window_info id="Capture Tool" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
- <window_info id="Gradle Console" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.28713968" sideWeight="0.54110897" order="7" side_tool="true" content_ui="tabs" />
- <window_info id="Project" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.22370937" sideWeight="0.4915254" order="0" side_tool="false" content_ui="combo" />
- <window_info id="Find" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.20066519" sideWeight="0.4901211" order="1" side_tool="false" content_ui="tabs" />
+ <window_info id="Gradle Console" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.135255" sideWeight="0.5436584" order="7" side_tool="true" content_ui="tabs" />
+ <window_info id="Project" active="true" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.22370937" sideWeight="0.4915254" order="0" side_tool="false" content_ui="combo" />
<window_info id="Gradle" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.32981715" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="Structure" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" />
<window_info id="Android Model" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="true" content_ui="tabs" />
<window_info id="Hierarchy" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="2" side_tool="false" content_ui="combo" />
<window_info id="Assistant" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.32950923" sideWeight="0.5" order="5" side_tool="false" content_ui="tabs" />
<window_info id="Ant Build" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" />
+ <window_info id="Messages" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.28713968" sideWeight="0.45634162" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Inspection" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.4" sideWeight="0.5" order="5" side_tool="false" content_ui="tabs" />
+ <window_info id="Preview" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.2974108" sideWeight="0.5" order="4" side_tool="false" content_ui="tabs" />
+ <window_info id="Find" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.20066519" sideWeight="0.4901211" order="1" side_tool="false" content_ui="tabs" />
</layout>
</component>
<component name="UnknownFeatures">
<state />
</provider>
</entry>
- <entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/AddDeviceInfoActivity.java">
- <provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="34">
- <caret line="45" column="29" selection-start-line="45" selection-start-column="29" selection-end-line="45" selection-end-column="29" />
- <folding />
- </state>
- </provider>
- </entry>
- <entry file="file://$PROJECT_DIR$/src/main/res/layout/activity_add_device_info.xml">
- <provider editor-type-id="text-editor">
- <state relative-caret-position="0">
- <caret line="0" column="0" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" />
- <folding />
- </state>
- </provider>
- <provider selected="true" editor-type-id="android-designer2">
- <state />
- </provider>
- </entry>
- <entry file="file://$PROJECT_DIR$/src/main/res/layout/content_add_device_info.xml">
- <provider editor-type-id="text-editor">
- <state relative-caret-position="705">
- <caret line="47" column="0" selection-start-line="47" selection-start-column="0" selection-end-line="47" selection-end-column="0" />
- <folding />
- </state>
- </provider>
- <provider selected="true" editor-type-id="android-designer2">
- <state />
- </provider>
- </entry>
+ <entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/AddDeviceInfoActivity.java" />
+ <entry file="file://$PROJECT_DIR$/src/main/res/layout/activity_add_device_info.xml" />
+ <entry file="file://$PROJECT_DIR$/src/main/res/layout/content_add_device_info.xml" />
<entry file="jar://$USER_HOME$/Android/Sdk/platforms/android-26/android.jar!/java/lang/ClassLoader.class">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="377">
<caret line="145" column="0" selection-start-line="145" selection-start-column="0" selection-end-line="145" selection-end-column="0" />
- <folding />
- </state>
- </provider>
- </entry>
- <entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/MySQLInterface.config">
- <provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="45">
- <caret line="3" column="18" selection-start-line="3" selection-start-column="18" selection-end-line="3" selection-end-column="18" />
- <folding />
</state>
</provider>
</entry>
- <entry file="file://$PROJECT_DIR$/src/main/res/layout/content_delete_device.xml">
- <provider editor-type-id="text-editor">
- <state relative-caret-position="0">
- <caret line="0" column="0" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" />
- <folding />
- </state>
- </provider>
- <provider selected="true" editor-type-id="android-designer2">
- <state />
- </provider>
- </entry>
+ <entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/MySQLInterface.config" />
+ <entry file="file://$PROJECT_DIR$/src/main/res/layout/content_delete_device.xml" />
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/SSH_MySQL.java">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="1426">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="15">
<caret line="1" column="3" selection-start-line="1" selection-start-column="3" selection-end-line="1" selection-end-column="3" />
- <folding />
</state>
</provider>
</entry>
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="15">
<caret line="1" column="27" selection-start-line="1" selection-start-column="27" selection-end-line="1" selection-end-column="27" />
- <folding />
</state>
</provider>
</entry>
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="30">
<caret line="2" column="5" selection-start-line="2" selection-start-column="5" selection-end-line="2" selection-end-column="5" />
- <folding />
</state>
</provider>
</entry>
</state>
</provider>
</entry>
- <entry file="file://$PROJECT_DIR$/src/main/res/layout/content_add_relation.xml">
- <provider editor-type-id="text-editor">
- <state relative-caret-position="0">
- <caret line="0" column="0" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" />
- <folding />
- </state>
- </provider>
- <provider selected="true" editor-type-id="android-designer2">
- <state />
- </provider>
- </entry>
- <entry file="file://$PROJECT_DIR$/src/main/res/layout/activity_add_comm.xml">
- <provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="90">
- <caret line="6" column="52" selection-start-line="0" selection-start-column="0" selection-end-line="92" selection-end-column="0" />
- <folding />
- </state>
- </provider>
- <provider editor-type-id="android-designer2">
- <state />
- </provider>
- </entry>
+ <entry file="file://$PROJECT_DIR$/src/main/res/layout/content_add_relation.xml" />
+ <entry file="file://$PROJECT_DIR$/src/main/res/layout/activity_add_comm.xml" />
<entry file="file://$PROJECT_DIR$/src/main/res/layout/activity_add_device.xml">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="90">
<state />
</provider>
</entry>
- <entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/AddCommActivity.java">
- <provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="195">
- <caret line="17" column="114" selection-start-line="17" selection-start-column="54" selection-end-line="17" selection-end-column="114" />
- <folding />
- </state>
- </provider>
- </entry>
+ <entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/AddCommActivity.java" />
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/AddDeviceActivity.java">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="398">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="207">
<caret line="25" column="0" selection-start-line="25" selection-start-column="0" selection-end-line="25" selection-end-column="0" />
- <folding />
</state>
</provider>
</entry>
</entry>
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/MainActivity.java">
<provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="607">
+ <state relative-caret-position="1350">
<caret line="101" column="21" selection-start-line="100" selection-start-column="12" selection-end-line="101" selection-end-column="21" />
<folding>
- <element signature="imports" expanded="true" />
- <element signature="e#3760#3821#0" expanded="true" />
- <element signature="e#4406#4461#0" expanded="true" />
+ <element signature="imports" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/EnrollDeviceActivity.java">
<provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="315">
+ <state relative-caret-position="525">
<caret line="51" column="12" selection-start-line="51" selection-start-column="8" selection-end-line="51" selection-end-column="12" />
- <folding>
- <element signature="imports" expanded="true" />
- <element signature="e#4975#4993#0" expanded="true" />
- </folding>
+ <folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/SSH.java">
<provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="127">
+ <state relative-caret-position="1590">
<caret line="124" column="30" selection-start-line="124" selection-start-column="30" selection-end-line="124" selection-end-column="30" />
- <folding>
- <element signature="e#0#121#0" expanded="true" />
- <element signature="imports" expanded="true" />
- <element signature="e#2775#2783#0" expanded="true" />
- </folding>
- </state>
- </provider>
- </entry>
- <entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/ListActivity.java">
- <provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="440">
- <caret line="47" column="8" selection-start-line="47" selection-start-column="8" selection-end-line="47" selection-end-column="8" />
- <folding>
- <element signature="imports" expanded="true" />
- <element signature="e#1953#2177#0" expanded="true" />
- <element signature="e#2176#2177#0" expanded="true" />
- </folding>
- </state>
- </provider>
- </entry>
- <entry file="file://$PROJECT_DIR$/src/main/res/layout/activity_list.xml">
- <provider selected="true" editor-type-id="text-editor">
- <state relative-caret-position="126">
- <caret line="21" column="36" selection-start-line="21" selection-start-column="36" selection-end-line="21" selection-end-column="36" />
<folding />
</state>
</provider>
- <provider editor-type-id="android-designer2">
- <state />
- </provider>
</entry>
<entry file="file://$PROJECT_DIR$/src/main/res/values/constants.xml">
<provider selected="true" editor-type-id="text-editor">
</state>
</provider>
</entry>
+ <entry file="file://$PROJECT_DIR$/src/main/res/layout/activity_list.xml">
+ <provider selected="true" editor-type-id="text-editor">
+ <state relative-caret-position="126">
+ <caret line="21" column="36" selection-start-line="21" selection-start-column="36" selection-end-line="21" selection-end-column="36" />
+ <folding />
+ </state>
+ </provider>
+ <provider editor-type-id="android-designer2">
+ <state />
+ </provider>
+ </entry>
+ <entry file="file://$PROJECT_DIR$/src/main/java/com/example/lede2/ListActivity.java">
+ <provider selected="true" editor-type-id="text-editor">
+ <state relative-caret-position="15">
+ <caret line="47" column="8" selection-start-line="47" selection-start-column="8" selection-end-line="47" selection-end-column="8" />
+ <folding>
+ <element signature="imports" expanded="true" />
+ </folding>
+ </state>
+ </provider>
+ </entry>
</component>
</project>
\ No newline at end of file
<sourceFolder url="file://$MODULE_DIR$/src/test/rs" isTestSource="true" />
<sourceFolder url="file://$MODULE_DIR$/src/test/shaders" isTestSource="true" />
<excludeFolder url="file://$MODULE_DIR$/build/android-profile" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/assets" />
<excludeFolder url="file://$MODULE_DIR$/build/intermediates/blame" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/builds" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/classes" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/dex-cache" />
<excludeFolder url="file://$MODULE_DIR$/build/intermediates/incremental" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/incremental-classes" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/incremental-runtime-classes" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/incremental-safeguard" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/incremental-verifier" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/instant-run-resources" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/instant-run-support" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/jniLibs" />
<excludeFolder url="file://$MODULE_DIR$/build/intermediates/manifests" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/pre-dexed" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/reload-dex" />
<excludeFolder url="file://$MODULE_DIR$/build/intermediates/res" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/restart-dex" />
<excludeFolder url="file://$MODULE_DIR$/build/intermediates/rs" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/shaders" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/split-apk" />
<excludeFolder url="file://$MODULE_DIR$/build/intermediates/symbols" />
- <excludeFolder url="file://$MODULE_DIR$/build/intermediates/transforms" />
<excludeFolder url="file://$MODULE_DIR$/build/outputs" />
- <excludeFolder url="file://$MODULE_DIR$/build/tmp" />
</content>
<orderEntry type="jdk" jdkName="Android API 26 Platform" jdkType="Android SDK" />
<orderEntry type="sourceFolder" forTests="false" />