provisioning: Fixed memory leak 23/22223/7
authorGeorge Nash <george.nash@intel.com>
Mon, 28 Aug 2017 23:25:21 +0000 (16:25 -0700)
committerNathan Heldt-Sheller <nathan.heldt-sheller@intel.com>
Tue, 19 Sep 2017 15:45:14 +0000 (15:45 +0000)
Fixed memory leak found using valgrind. The memory
leak was due to the provisionInit function calling
sqlite3_open_v2 without calling sqlite3_close

There was not provisionClose method in the C++ so it was
added to the OCSecure class. To do this OCClosePM was
also added to that the code could be used in Windows.

The provisioningClose call was added to all of the samples
that are currently calling provisioningInit(dbfile)

While updating the some of the android samples the
tab depth was cleaned.

Note the unit tests are not following one of the most
basic rules of unit testing. Tests should be isolated
and independent. When the cleanup code was added to the
unit tests it broke tests that run later. Each individual
unit test should be able to run independent of all the
other unit tests order should not matter. This commit
does a little to break the dependency tests have on other
tests, but it did not fix it completely. Many tests rely
on the DB being left in a state by another test as well as
passing test state to global variables that hold information
outside the individual test.

Change-Id: Id2c05ecc611516a5cf892ae70bb4e0cd0c115752
Signed-off-by: George Nash <george.nash@intel.com>
23 files changed:
java/common/src/main/java/org/iotivity/base/OcProvisioning.java
java/examples-android/DirectPairing/src/main/java/org/iotivity/base/examples/DirectPairing/MainActivity.java
java/examples-android/cloudprovisioningclient/src/main/java/org/iotivity/base/examples/cloudprovisioningclient/CloudProvisioningClient.java
java/examples-android/provisioningclient/src/main/java/org/iotivity/base/examples/provisioningclient/ProvisioningClient.java
java/jni/JniOcProvisioning.cpp
java/jni/JniOcProvisioning.h
resource/IPCA/src/ocfframework.cpp
resource/IPCA/src/pretendocprovision.cpp
resource/IPCA/unittests/mockOCProvision.cpp
resource/csdk/security/provisioning/include/internal/provisioningdatabasemanager.h
resource/csdk/security/provisioning/include/ocprovisioningmanager.h
resource/csdk/security/provisioning/src/ocprovisioningmanager.c
resource/csdk/security/provisioning/unittest/otmunittest.cpp
resource/csdk/security/provisioning/unittest/provisioningdatabasemanager.cpp
resource/csdk/stack/octbstack_product_secured.def
resource/include/OCProvisioningManager.hpp
resource/provisioning/examples/provisioningclient.cpp
resource/provisioning/examples/subownerclient.cpp
resource/provisioning/src/OCProvisioningManager.cpp
resource/provisioning/unittests/OCProvisioningTest.cpp
service/easy-setup/sampleapp/mediator/android/EasySetup/app/src/main/java/org/iotivity/service/easysetup/EasysetupActivity.java
service/easy-setup/sampleapp/mediator/linux/richsdk_sample/mediator.cpp
service/easy-setup/sampleapp/mediator/linux/richsdk_sample/submediator.cpp

index c5d2305..1095cb8 100644 (file)
@@ -44,6 +44,14 @@ public class OcProvisioning {
      */
     public static native void provisionInit(String dbPath) throws OcException;
 
+    /**
+     * Method is used by provisioning manager to close provisioning database.
+     *
+     * @throws OcException Indicate failure.
+     *                     Use OcException.GetErrorCode() for more details.
+     */
+    public static native void provisionClose() throws OcException;
+
     /**
      * Method to Discover un-owned devices in its subnet.Un-owned devices need
      * to be owned by calling ownershipTransferCBdata.
index 90c4301..b96576d 100644 (file)
@@ -385,6 +385,12 @@ public class MainActivity extends Activity {
 
     }
 
+    @Override
+    public void onDestroy() {
+        super.onDestroy();
+        closeIOCStack();
+    }
+
     /**
      * Copy svr db CBOR dat file from assets folder to app data files dir
      */
@@ -484,6 +490,18 @@ public class MainActivity extends Activity {
         }
     }
 
+    private void closeIOCStack() {
+        try {
+            /*
+             * Close DataBase
+             */
+            OcProvisioning.provisionClose();
+        } catch (OcException e) {
+            Log.d(TAG, "provisionClose error: " + e.getMessage());
+            Log.e(TAG, e.getMessage());
+        }
+    }
+
     class GetDiscoveredItems extends AsyncTask<Void, Void, List<String>> {
 
         ProgressDialog pDialog;
index a5ebb9c..8bd4a03 100644 (file)
@@ -326,140 +326,143 @@ public class CloudProvisioningClient extends Activity implements OcAccountManage
     private String filePath = "";
     private TextView mEventsTextView;
     @Override
-        protected void onCreate(Bundle savedInstanceState) {
-            super.onCreate(savedInstanceState);
-            setContentView(R.layout.main_activity);
-
-            signUp = (Button) findViewById(R.id.signup);
-            signIn = (Button) findViewById(R.id.signin);
-            signOut = (Button) findViewById(R.id.signout);
-            getAclId = (Button) findViewById(R.id.getAclId);
-            getAclInfo = (Button) findViewById(R.id.getAclInfo);
-            requestCert = (Button) findViewById(R.id.request);
-            postCrl = (Button) findViewById(R.id.postCRL);
-            getCrl = (Button) findViewById(R.id.getCRL);
-
-            updateAce = (Button) findViewById(R.id.updateAce);
-            lyt1 = (LinearLayout) findViewById(R.id.lyt1);
-            lyt2 = (LinearLayout) findViewById(R.id.lyt2);
-            signupLyt = (LinearLayout) findViewById(R.id.signupLyt);
-            signinLyt = (LinearLayout) findViewById(R.id.signinLyt);
-
-
-            userid = (TextView) findViewById(R.id.userid);
-
-            mEventsTextView = (TextView) findViewById(R.id.eventView);
-
-            filePath = getFilesDir().getPath() + "/"; //  data/data/<package>/files/
-            //copy CBOR file when application runs first time
-            settingPreference = PreferenceManager.getDefaultSharedPreferences(this);
-            boolean isFirstRun = settingPreference.getBoolean("FIRSTRUN", true);
-            if (isFirstRun) {
-                copyCborFromAsset();
-                SharedPreferences.Editor editor = settingPreference.edit();
-                editor.putBoolean("FIRSTRUN", false);
-                editor.putString("IP", StringConstants.DEFAULT_COAP_DERVER_IP);
-                editor.putString("PORT", StringConstants.DEFAULT_COAP_DERVER_PORT);
-                editor.putString("DEVICEID", StringConstants.DEFAULT_DEVICE_ID);
-                editor.putString("OWNERID", StringConstants.DEFAULT_OWNER_ID);
-                editor.putString("SERIALNUMBER", StringConstants.DEFAULT_SERIAL_NUMBER);
-                editor.commit();
-            }
-            if (settingPreference.getString("useruuid", "").equals("")) {
-
-                lyt1.setVisibility(View.GONE);
-                lyt2.setVisibility(View.GONE);
-                signupLyt.setVisibility(View.VISIBLE);
-                signinLyt.setVisibility(View.GONE);
-
+    protected void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        setContentView(R.layout.main_activity);
+
+        signUp = (Button) findViewById(R.id.signup);
+        signIn = (Button) findViewById(R.id.signin);
+        signOut = (Button) findViewById(R.id.signout);
+        getAclId = (Button) findViewById(R.id.getAclId);
+        getAclInfo = (Button) findViewById(R.id.getAclInfo);
+        requestCert = (Button) findViewById(R.id.request);
+        postCrl = (Button) findViewById(R.id.postCRL);
+        getCrl = (Button) findViewById(R.id.getCRL);
+
+        updateAce = (Button) findViewById(R.id.updateAce);
+        lyt1 = (LinearLayout) findViewById(R.id.lyt1);
+        lyt2 = (LinearLayout) findViewById(R.id.lyt2);
+        signupLyt = (LinearLayout) findViewById(R.id.signupLyt);
+        signinLyt = (LinearLayout) findViewById(R.id.signinLyt);
+
+
+        userid = (TextView) findViewById(R.id.userid);
+
+        mEventsTextView = (TextView) findViewById(R.id.eventView);
+
+        filePath = getFilesDir().getPath() + "/"; //  data/data/<package>/files/
+        //copy CBOR file when application runs first time
+        settingPreference = PreferenceManager.getDefaultSharedPreferences(this);
+        boolean isFirstRun = settingPreference.getBoolean("FIRSTRUN", true);
+        if (isFirstRun) {
+            copyCborFromAsset();
+            SharedPreferences.Editor editor = settingPreference.edit();
+            editor.putBoolean("FIRSTRUN", false);
+            editor.putString("IP", StringConstants.DEFAULT_COAP_DERVER_IP);
+            editor.putString("PORT", StringConstants.DEFAULT_COAP_DERVER_PORT);
+            editor.putString("DEVICEID", StringConstants.DEFAULT_DEVICE_ID);
+            editor.putString("OWNERID", StringConstants.DEFAULT_OWNER_ID);
+            editor.putString("SERIALNUMBER", StringConstants.DEFAULT_SERIAL_NUMBER);
+            editor.commit();
+        }
+        if (settingPreference.getString("useruuid", "").equals("")) {
 
-            } else {
-                userid.setText(settingPreference.getString("useruuid", ""));
-                lyt1.setVisibility(View.VISIBLE);
-                lyt2.setVisibility(View.VISIBLE);
-                signupLyt.setVisibility(View.GONE);
-                signinLyt.setVisibility(View.VISIBLE);
-            }
+            lyt1.setVisibility(View.GONE);
+            lyt2.setVisibility(View.GONE);
+            signupLyt.setVisibility(View.VISIBLE);
+            signinLyt.setVisibility(View.GONE);
 
-            initOICStack();
-            ocCloudProvisioning = new OcCloudProvisioning(settingPreference.getString("IP", ""),
-                    Integer.valueOf(settingPreference.getString("PORT", "")));
 
-            signUp.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    signUp();
-                    }
-                    });
-            signIn.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    signIn();
-                    }
-                    });
-            signOut.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    signOut();
-                    }
-                    });
-            getAclId.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    getAclId();
-                    }
-                    });
-            getAclInfo.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    getAclInfo();
-                    }
-                    });
-            requestCert.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    requestCert();
-                    }
-                    });
-            postCrl.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    postCrl();
-                    }
-                    });
-            getCrl.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    getCrl();
-                    }
-                    });
-            updateAce.setOnClickListener(new View.OnClickListener() {
-                    @Override
-                    public void onClick(View v) {
-                    updateAces();
-                    }
-                    });
+        } else {
+            userid.setText(settingPreference.getString("useruuid", ""));
+            lyt1.setVisibility(View.VISIBLE);
+            lyt2.setVisibility(View.VISIBLE);
+            signupLyt.setVisibility(View.GONE);
+            signinLyt.setVisibility(View.VISIBLE);
         }
 
+        initOICStack();
+        ocCloudProvisioning = new OcCloudProvisioning(settingPreference.getString("IP", ""),
+                Integer.valueOf(settingPreference.getString("PORT", "")));
 
-    @Override
-        public boolean onCreateOptionsMenu(Menu menu) {
-            // Inflate the menu; this adds items to the action bar if it is present.
-            getMenuInflater().inflate(R.menu.menu_cloud_provision, menu);
-            return true;
-        }
+        signUp.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                signUp();
+                }
+                });
+        signIn.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                signIn();
+                }
+                });
+        signOut.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                signOut();
+                }
+                });
+        getAclId.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                getAclId();
+                }
+                });
+        getAclInfo.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                getAclInfo();
+                }
+                });
+        requestCert.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                requestCert();
+                }
+                });
+        postCrl.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                postCrl();
+                }
+                });
+        getCrl.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                getCrl();
+                }
+                });
+        updateAce.setOnClickListener(new View.OnClickListener() {
+                @Override
+                public void onClick(View v) {
+                updateAces();
+                }
+                });
+    }
 
     @Override
-        public boolean onOptionsItemSelected(MenuItem item) {
-            switch (item.getItemId()) {
-                case R.id.action_settings:
-                    setDefualtSettings();
-                    return (true);
+    public void onDestroy() {
+        super.onDestroy();
+        closeIOCStack();
+    }
 
+    @Override
+    public boolean onCreateOptionsMenu(Menu menu) {
+        // Inflate the menu; this adds items to the action bar if it is present.
+        getMenuInflater().inflate(R.menu.menu_cloud_provision, menu);
+        return true;
+    }
 
-            }
-            return (super.onOptionsItemSelected(item));
+    @Override
+    public boolean onOptionsItemSelected(MenuItem item) {
+        switch (item.getItemId()) {
+            case R.id.action_settings:
+                setDefualtSettings();
+                return (true);
         }
+        return (super.onOptionsItemSelected(item));
+    }
 
     private void signIn() {
         try {
@@ -622,6 +625,18 @@ public class CloudProvisioningClient extends Activity implements OcAccountManage
         }
     }
 
+    private void closeIOCStack() {
+        try {
+            /*
+             * Close DataBase
+             */
+            OcProvisioning.provisionClose();
+        } catch (OcException e) {
+            logMessage(TAG + "provisionClose error: " + e.getMessage());
+            Log.e(TAG, e.getMessage());
+        }
+    }
+
     @Override
         public void onActivityResult(int requestCode, int resultCode, Intent data) {
             super.onActivityResult(requestCode, resultCode, data);
index f39558c..4a10e58 100644 (file)
@@ -242,32 +242,38 @@ OcSecureResource.DoOwnershipTransferListener, OcSecureResource.ProvisionPairwise
         };
 
     @Override
-        protected void onCreate(Bundle savedInstanceState) {
-            super.onCreate(savedInstanceState);
-            setContentView(R.layout.activity_secure_provision_client);
-            mEventsTextView = new TextView(this);
-            mEventsTextView.setGravity(Gravity.BOTTOM);
-            mEventsTextView.setMovementMethod(new ScrollingMovementMethod());
-            LinearLayout layout = (LinearLayout) findViewById(R.id.linearLayout);
-            layout.addView(mEventsTextView, new LinearLayout.LayoutParams(
-                        LinearLayout.LayoutParams.MATCH_PARENT, 0, 1f)
-                    );
-            filePath = getFilesDir().getPath() + "/"; //  data/data/<package>/files/
-            //copy CBOR file when application runs first time
-            SharedPreferences wmbPreference = PreferenceManager.getDefaultSharedPreferences(this);
-            boolean isFirstRun = wmbPreference.getBoolean("FIRSTRUN", true);
-            if (isFirstRun) {
-                copyCborFromAsset();
-                SharedPreferences.Editor editor = wmbPreference.edit();
-                editor.putBoolean("FIRSTRUN", false);
-                editor.commit();
-            }
-            initOICStack();
-            saveCertChain();
-            int ret = CaInterface.setCipherSuite(OicCipher.TLS_ECDH_anon_WITH_AES_128_CBC_SHA,
-                                                    OcConnectivityType.CT_ADAPTER_IP);
-            Log.e(TAG,"CaInterface.setCipherSuite returned = "+ret);
+    protected void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        setContentView(R.layout.activity_secure_provision_client);
+        mEventsTextView = new TextView(this);
+        mEventsTextView.setGravity(Gravity.BOTTOM);
+        mEventsTextView.setMovementMethod(new ScrollingMovementMethod());
+        LinearLayout layout = (LinearLayout) findViewById(R.id.linearLayout);
+        layout.addView(mEventsTextView, new LinearLayout.LayoutParams(
+                    LinearLayout.LayoutParams.MATCH_PARENT, 0, 1f)
+                );
+        filePath = getFilesDir().getPath() + "/"; //  data/data/<package>/files/
+        //copy CBOR file when application runs first time
+        SharedPreferences wmbPreference = PreferenceManager.getDefaultSharedPreferences(this);
+        boolean isFirstRun = wmbPreference.getBoolean("FIRSTRUN", true);
+        if (isFirstRun) {
+            copyCborFromAsset();
+            SharedPreferences.Editor editor = wmbPreference.edit();
+            editor.putBoolean("FIRSTRUN", false);
+            editor.commit();
         }
+        initOICStack();
+        saveCertChain();
+        int ret = CaInterface.setCipherSuite(OicCipher.TLS_ECDH_anon_WITH_AES_128_CBC_SHA,
+                                                OcConnectivityType.CT_ADAPTER_IP);
+        Log.e(TAG,"CaInterface.setCipherSuite returned = "+ret);
+    }
+
+    @Override
+    public void onDestroy() {
+        super.onDestroy();
+        closeIOCStack();
+    }
 
     /**
      * configure OIC platform and call findResource
@@ -330,6 +336,18 @@ OcSecureResource.DoOwnershipTransferListener, OcSecureResource.ProvisionPairwise
         new DiscoveryOTTransferAsyncTask().execute();
     }
 
+    private void closeIOCStack() {
+        try {
+            /*
+             * Close DataBase
+             */
+            OcProvisioning.provisionClose();
+        } catch (OcException e) {
+            logMessage(TAG + "provisionClose error: " + e.getMessage());
+            Log.e(TAG, e.getMessage());
+        }
+    }
+
     @Override
         synchronized public void doOwnershipTransferListener(List<ProvisionResult> ProvisionResultList,
                 int hasError) {
index d8f037c..d99ad45 100644 (file)
@@ -215,6 +215,32 @@ JNIEXPORT void JNICALL Java_org_iotivity_base_OcProvisioning_provisionInit
     }
 }
 
+/*
+ * Class:     org_iotivity_base_OcProvisioning
+ * Method:    provisionClose
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL Java_org_iotivity_base_OcProvisioning_provisionClose
+  (JNIEnv *env, jclass thiz)
+{
+    OC_UNUSED(thiz);
+    LOGD("OcProvisioning_provisionClose");
+    try
+    {
+        OCStackResult result = OCSecure::provisionClose();
+        if (OC_STACK_OK != result)
+        {
+            ThrowOcException(result, "OCSecure::provisionClose Failed");
+            return;
+        }
+    }
+    catch (OCException& e)
+    {
+        LOGE("%s", e.reason().c_str());
+        ThrowOcException(OC_STACK_ERROR, e.reason().c_str());
+    }
+}
+
 /*
  * Class:     org_iotivity_base_OcProvisioning
  * Method:    discoverOwnedDevices
index 2e2f46d..12dae0a 100644 (file)
@@ -60,6 +60,14 @@ JNIEXPORT jobjectArray JNICALL Java_org_iotivity_base_OcProvisioning_discoverUno
 JNIEXPORT void JNICALL Java_org_iotivity_base_OcProvisioning_provisionInit
   (JNIEnv *, jclass, jstring);
 
+/*
+ * Class:     org_iotivity_base_OcProvisioning
+ * Method:    provisionClose
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL Java_org_iotivity_base_OcProvisioning_provisionClose
+  (JNIEnv *, jclass);
+
 /*
  * Class:     org_iotivity_base_OcProvisioning
  * Method:    discoverOwnedDevices
index 13851af..0a3b459 100644 (file)
@@ -376,6 +376,7 @@ IPCAStatus OCFFramework::Stop(InputPinCallbackHandle passwordInputCallbackHandle
 
     OCSecure::deregisterInputPinCallback(passwordInputCallbackHandle);
     OCSecure::deregisterDisplayPinCallback(passwordDisplayCallbackHandle);
+    OCSecure::provisionClose();
 
     m_isStopping = true;
 
index 5419d32..747df7c 100644 (file)
@@ -36,6 +36,11 @@ OCStackResult OCSecure::provisionInit(const std::string& dbPath)
     return OC_STACK_OK;
 }
 
+OCStackResult OCSecure::provisionClose()
+{
+    return OC_STACK_OK;
+}
+
 OCStackResult OCSecure::registerInputPinCallback(InputPinCB inputPinCB,
                             InputPinCallbackHandle* inputPinCallbackHandle)
 {
index ccfd867..8bf968e 100644 (file)
@@ -38,6 +38,11 @@ OCStackResult OCSecure::provisionInit(const std::string& dbPath)
     return OC_STACK_OK;
 }
 
+OCStackResult OCSecure::provisionClose()
+{
+    return OC_STACK_OK;
+}
+
 OCStackResult OCSecure::registerInputPinCallback(InputPinCB inputPinCB,
                             InputPinCallbackHandle* inputPinCallbackHandle)
 {
index 9c72002..5ffafa5 100644 (file)
@@ -38,6 +38,8 @@ typedef enum PdmDeviceState {
 /**
  * This method is used by provisioning manager to open provisioning database.
  *
+ * @see PDMClose()
+ *
  * @param[in] dbPath file path of the sqlite3 db
  *
  * @return OC_STACK_OK in case of success and other value otherwise.
@@ -169,6 +171,8 @@ OCStackResult PDMGetToBeUnlinkedDevices(OCPairList_t** staleDevList, size_t* num
 /**
  * This method is used by provisioning manager to close provisioning database.
  *
+ * @see PDMInit()
+ *
  * @return  OC_STACK_OK in case of success and other value otherwise.
  */
 OCStackResult PDMClose();
index ef904bf..23b2cb1 100644 (file)
@@ -38,12 +38,23 @@ extern "C" {
  * TODO: In addition, if there is a device(s) which has not up-to-date credentials, this function will
  * automatically try to update the deivce(s).
  *
+ * @see OCClosePM()
+ *
  * @param[in] dbPath file path of the sqlite3 db
  *
  * @return OC_STACK_OK in case of success and other value otherwise.
  */
 OCStackResult OC_CALL OCInitPM(const char* dbPath);
 
+/**
+ * This method is used by provisioning manager to close provisioning database.
+ *
+ * @see OCInitPM()
+ *
+ * @return  OC_STACK_OK in case of success and other value otherwise.
+ */
+OCStackResult OC_CALL OCClosePM();
+
 /**
  * API to cleanup PDM in case of timeout.
  * It will remove the PDM_DEVICE_INIT state devices from PDM.
index 90210f5..cf71ad4 100644 (file)
@@ -70,7 +70,7 @@ struct ProvPreconfPINCtx
  * The function is responsible for initializaton of the provisioning manager. It will load
  * provisioning database which have owned device's list and their linked status.
  * TODO: In addition, if there is a device(s) which has not up-to-date credentials, this function will
- * automatically try to update the deivce(s).
+ * automatically try to update the device(s).
  *
  * @param[in] dbPath file path of the sqlite3 db
  *
@@ -81,6 +81,18 @@ OCStackResult OC_CALL OCInitPM(const char* dbPath)
     return PDMInit(dbPath);
 }
 
+/**
+ * This method is used by provisioning manager to close provisioning database.
+ *
+ * @see OCInitPM()
+ *
+ * @return  OC_STACK_OK in case of success and other value otherwise.
+ */
+OCStackResult OC_CALL OCClosePM()
+{
+    return PDMClose();
+}
+
 OCStackResult OC_CALL OCPDMCleanupForTimeout()
 {
     return PDMDeleteDeviceWithState(PDM_DEVICE_INIT);
index 7f45cbf..04c0388 100644 (file)
@@ -303,6 +303,8 @@ TEST(InitForOTM, NullParam)
 
     gNumOfUnownDevice = 0;
     gNumOfOwnDevice = 0;
+    // close Provisioning DB
+    EXPECT_EQ(OC_STACK_OK, OCClosePM());
 }
 /*
 TEST(OCDiscoverSingleDeviceInUnicast, Simple)
@@ -331,6 +333,8 @@ TEST(OCDiscoverSingleDeviceInUnicast, Simple)
 */
 TEST(OCDiscoverUnownedDevices, Simple)
 {
+    //initialize Provisioning DB Manager
+    EXPECT_EQ(OC_STACK_OK, OCInitPM(PM_DB_FILE_NAME));
     EXPECT_EQ(OC_STACK_OK, OCDiscoverUnownedDevices(DISCOVERY_TIMEOUT, &g_unownedDevices));
 
     RemoveUnknownDeviceFromDevList(g_unownedDevices);
@@ -353,10 +357,14 @@ TEST(OCDiscoverUnownedDevices, Simple)
     }
 
     EXPECT_EQ(true, gNumOfUnownDevice > 0);
+    // close Provisioning DB
+    EXPECT_EQ(OC_STACK_OK, OCClosePM());
 }
 
 TEST(OCDoOwnershipTransfer, Simple)
 {
+    //initialize Provisioning DB Manager
+    EXPECT_EQ(OC_STACK_OK, OCInitPM(PM_DB_FILE_NAME));
     ASSERT_EQ(true, gNumOfUnownDevice > 0);
 
     g_doneCB = false;
@@ -370,10 +378,14 @@ TEST(OCDoOwnershipTransfer, Simple)
 
     EXPECT_EQ(true, g_callbackResult);
     EXPECT_EQ(true, g_doneCB);
+    // close Provisioning DB
+    EXPECT_EQ(OC_STACK_OK, OCClosePM());
 }
 
 TEST(OCDiscoverOwnedDevices, Simple)
 {
+    //initialize Provisioning DB Manager
+    EXPECT_EQ(OC_STACK_OK, OCInitPM(PM_DB_FILE_NAME));
     OCStackResult result = OC_STACK_ERROR;
     gNumOfOwnDevice = 0;
 
@@ -427,6 +439,8 @@ TEST(OCDiscoverOwnedDevices, Simple)
     }
 
     EXPECT_EQ(true, gNumOfOwnDevice > 0);
+    // close Provisioning DB
+    EXPECT_EQ(OC_STACK_OK, OCClosePM());
 }
 
 TEST(PerformLinkDevices, NullParam)
@@ -639,6 +653,8 @@ TEST(DiscoverMultipleOwnedDevices, NullParam)
 
 TEST(OCRemoveDevice, Simple)
 {
+    //initialize Provisioning DB Manager
+    EXPECT_EQ(OC_STACK_OK, OCInitPM(PM_DB_FILE_NAME));
     ASSERT_EQ(true, gNumOfUnownDevice > 0);
 
     OicUuid_t myUuid;
@@ -665,6 +681,8 @@ TEST(OCRemoveDevice, Simple)
     EXPECT_EQ(OC_STACK_OK, result);
     EXPECT_EQ(true, g_callbackResult);
     EXPECT_EQ(true, g_doneCB);
+    // close Provisioning DB
+    EXPECT_EQ(OC_STACK_OK, OCClosePM());
 }
 
 TEST(FinalizeOTMTest, NullParam)
index 2af25c0..33c8349 100644 (file)
@@ -65,21 +65,27 @@ TEST(CallPDMAPIbeforeInit, BeforeInit)
 TEST(PDMInitTest, PDMInitWithNULL)
 {
     EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMAddDeviceTest, NullUUID)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMAddDevice(NULL));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMIsDuplicateDeviceTest, NullUUID)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMIsDuplicateDevice(NULL,NULL));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 
 TEST(PDMIsDuplicateDeviceTest, ValidUUID)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid1 = {{0,}};
     memcpy(&uid1.id, ID_1, sizeof(uid1.id));
     EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
@@ -96,10 +102,12 @@ TEST(PDMIsDuplicateDeviceTest, ValidUUID)
 
     EXPECT_EQ(OC_STACK_OK, PDMIsDuplicateDevice(&uid3, &isDuplicate));
     EXPECT_FALSE(isDuplicate);
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMAddDeviceTest, ValidUUID)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
 
     uint8_t id[UUID_LENGTH] = {0,};
@@ -114,24 +122,30 @@ TEST(PDMAddDeviceTest, ValidUUID)
 
     EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid));
     EXPECT_EQ(OC_STACK_OK, PDMDeleteDevice(&uid));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMLinkDevicesTest, NULLDevice1)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     memcpy(&uid.id, ID_2, sizeof(uid.id));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMLinkDevices(NULL, &uid));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMLinkDevicesTest, NULLDevice2)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     memcpy(&uid.id, ID_3, sizeof(uid.id));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMLinkDevices(&uid, NULL));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMLinkDevicesTest, ValidCase)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid1 = {{0,}};
     memcpy(&uid1.id, ID_4, sizeof(uid1.id));
     EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
@@ -143,40 +157,49 @@ TEST(PDMLinkDevicesTest, ValidCase)
     EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid2, PDM_DEVICE_ACTIVE));
 
     EXPECT_EQ(OC_STACK_OK, PDMLinkDevices(&uid1, &uid2));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMUnlinkDevicesTest, NULLDevice1)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     memcpy(&uid.id, ID_3, sizeof(uid.id));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMUnlinkDevices(NULL, &uid));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMUnlinkDevicesTest, NULLDevice2)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     memcpy(&uid.id, ID_3, sizeof(uid.id));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMUnlinkDevices(&uid, NULL));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMUnlinkDevices, ValidCase)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid1 = {{0,}};
     memcpy(&uid1.id, ID_4, sizeof(uid1.id));
     OicUuid_t uid2 = {{0,}};
     memcpy(&uid2.id, ID_5, sizeof(uid2.id));
     EXPECT_EQ(OC_STACK_OK, PDMUnlinkDevices(&uid1, &uid2));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 
 TEST (PDMDeleteDevice, NULLDeviceID)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMDeleteDevice(NULL));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST (PDMDeleteDevice, ValidButNonExistDeviceID)
 {
-
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     uint8_t id[UUID_LENGTH] = {0,};
     for (size_t i = 0 ; i < sizeof(id) ; i++)
@@ -188,56 +211,70 @@ TEST (PDMDeleteDevice, ValidButNonExistDeviceID)
 
     memcpy(&uid.id, &id, sizeof(uid.id));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMDeleteDevice(&uid));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMGetOwnedDevices, ValidCase)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OCUuidList_t *list = NULL;
     size_t noOfDevcies = 0;
     EXPECT_EQ(OC_STACK_OK, PDMGetOwnedDevices(&list, &noOfDevcies));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMGetLinkedDevices, NULLDeviceID)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OCUuidList_t *list = NULL;
     size_t noOfDevices = 0;
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMGetLinkedDevices(NULL, &list, &noOfDevices));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMGetLinkedDevices, ValidCase)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     memcpy(&uid.id, ID_1, sizeof(uid.id));
     OCUuidList_t *list = NULL;
     size_t noOfDevices = 0;
     EXPECT_EQ(OC_STACK_OK, PDMGetLinkedDevices(&uid, &list, &noOfDevices));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMGetLinkedDevices, InvalidCase)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     memcpy(&uid.id, ID_6, sizeof(uid.id));
     OCUuidList_t *list = NULL;
     size_t noOfDevices = 0;
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMGetLinkedDevices(&uid, &list, &noOfDevices));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMSetLinkStale, NULLDeviceID1)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     memcpy(&uid.id, ID_1, sizeof(uid.id));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMSetLinkStale(NULL, &uid));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMSetLinkStale, NULLDeviceID2)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid = {{0,}};
     memcpy(&uid.id, ID_1, sizeof(uid.id));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMSetLinkStale(&uid, NULL));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMSetLinkStale, ValidCase)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OicUuid_t uid1 = {{0,}};
     memcpy(&uid1.id, ID_6, sizeof(uid1.id));
     OicUuid_t uid2 = {{0,}};
@@ -252,17 +289,21 @@ TEST(PDMSetLinkStale, ValidCase)
     EXPECT_EQ(OC_STACK_OK, PDMLinkDevices(&uid1, &uid2));
 
     EXPECT_EQ(OC_STACK_OK, PDMSetLinkStale(&uid1, &uid2));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMGetToBeUnlinkedDevices, ValidCase)
 {
+    EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     OCPairList_t *list = NULL;
     size_t noOfDevices = 0;
     EXPECT_EQ(OC_STACK_OK, PDMGetToBeUnlinkedDevices(&list, &noOfDevices));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMClose, ValidCase)
 {
+   EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
@@ -293,12 +334,14 @@ TEST(PDMIsLinkExistsTest, DuplicateID)
     OCStackResult res = PDMIsLinkExists(&uid1, &uid2, &linkExisits);
     EXPECT_EQ(OC_STACK_OK, res);
     EXPECT_FALSE(linkExisits);
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMSetDeviceStaleTest, NULLUUID)
 {
     EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
     EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMSetDeviceState(NULL, PDM_DEVICE_STALE));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMSetDeviceStaleTest, VALIDUUID)
@@ -308,6 +351,7 @@ TEST(PDMSetDeviceStaleTest, VALIDUUID)
     memcpy(&uid1.id, ID_9, sizeof(uid1.id));
     EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
     EXPECT_EQ(OC_STACK_OK,PDMSetDeviceState(&uid1, PDM_DEVICE_STALE));
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMSetDeviceStaleTest, StaleDeviceNotinDeviceList)
@@ -327,6 +371,7 @@ TEST(PDMSetDeviceStaleTest, StaleDeviceNotinDeviceList)
         EXPECT_FALSE(0 == memcmp(list->dev.id, uid1.id,sizeof(uid1.id)));
         list = list->next;
     }
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
 
 TEST(PDMSetDeviceStaleTest, StaleDeviceNotinLinkedDevice)
@@ -390,4 +435,5 @@ TEST(PDMSetDeviceStaleTest, StaleDeviceNotinLinkedDevice)
         EXPECT_TRUE(0 == memcmp(ptr->dev.id, uid2.id,sizeof(uid2.id)));
         ptr = ptr->next;
     }
+    EXPECT_EQ(OC_STACK_OK, PDMClose());
 }
index d4620cc..2ba3693 100644 (file)
@@ -29,6 +29,7 @@ OCGetPublicKeyFromCSR
 OCGetRolesResource
 OCGetUuidFromCSR
 OCInitPM
+OCClosePM
 OCPDMCleanupForTimeout
 OCProvisionACL
 OCSaveACL
index be7e83d..c7a4d11 100644 (file)
@@ -190,12 +190,23 @@ namespace OC
              * The API is responsible for initialization of the provisioning manager. It will load
              * provisioning database which have owned device's list and their linked status.
              *
+             * @see OCSecure::provisionClose()
+             *
              * @param dbPath file path of the sqlite3 database.
              *
              * @return ::OC_STACK_OK in case of success and other value otherwise.
              */
             static OCStackResult provisionInit(const std::string& dbPath);
 
+            /**
+             * This method is used by provisioning manager to close provisioning database.
+             *
+             * @see OCSecure::provisionInit()
+             *
+             * @return  OC_STACK_OK in case of success and other value otherwise.
+             */
+            static OCStackResult provisionClose();
+
             /**
              * API is responsible for discovery of devices in it's subnet. It will list
              * all the device in subnet which are not yet owned.
index 5c3ea1a..c811e25 100644 (file)
@@ -1678,6 +1678,8 @@ int main(void)
 
         // Unregister the input pin callback
         OCSecure::deregisterInputPinCallback(callbackHandle);
+        // close database
+        OCSecure::provisionClose();
     }
     catch(OCException& e)
     {
index 2c9ea8e..2ca9145 100644 (file)
@@ -406,6 +406,8 @@ int main(void)
 
     // Unregister input pin callback
     OCSecure::deregisterInputPinCallback(callbackHandle);
+    // close database
+    OCSecure::provisionClose();
 
     return 0;
 }
index b37c118..14ba4ae 100644 (file)
@@ -66,6 +66,7 @@ namespace OC
 
         delete context;
     }
+
     OCStackResult OCSecure::provisionInit(const std::string& dbPath)
     {
         OCStackResult result;
@@ -85,6 +86,25 @@ namespace OC
         return result;
     }
 
+    OCStackResult OCSecure::provisionClose()
+    {
+        OCStackResult result;
+        auto cLock = OCPlatform_impl::Instance().csdkLock().lock();
+
+        if (cLock)
+        {
+            std::lock_guard<std::recursive_mutex> lock(*cLock);
+            result = OCClosePM();
+        }
+        else
+        {
+            oclog() <<"Mutex not found";
+            result = OC_STACK_ERROR;
+        }
+
+        return result;
+    }
+
     OCStackResult OCSecure::discoverUnownedDevices(unsigned short timeout,
             DeviceList_t &list)
     {
index b16bd20..3f4385d 100644 (file)
@@ -44,12 +44,14 @@ namespace OCProvisioningTest
     {
         std::string dbPath("");
         EXPECT_EQ(OC_STACK_OK, OCSecure::provisionInit(dbPath));
+        EXPECT_EQ(OC_STACK_OK, OCSecure::provisionClose());
     }
 
     TEST(ProvisionInitTest, TestValidPath)
     {
         std::string dbPath("./dbPath");
         EXPECT_EQ(OC_STACK_OK, OCSecure::provisionInit(dbPath));
+        EXPECT_EQ(OC_STACK_OK, OCSecure::provisionClose());
     }
 
     TEST(DiscoveryTest, SecureResource)
@@ -182,9 +184,12 @@ namespace OCProvisioningTest
 
     TEST(DeviceInfoTest, DevInfoFromNetwork)
     {
+        std::string dbPath("./dbPath");
+        EXPECT_EQ(OC_STACK_OK, OCSecure::provisionInit(dbPath));
         DeviceList_t owned, unowned;
         EXPECT_EQ(OC_STACK_OK, OCSecure::getDevInfoFromNetwork(TIMEOUT,
                     owned, unowned));
+        EXPECT_EQ(OC_STACK_OK, OCSecure::provisionClose());
     }
 
     TEST(SetDisplayPinCBTest, SetDisplayPinCBTestNullCB)
index 0ef8f42..cc369d9 100755 (executable)
@@ -388,6 +388,18 @@ public class EasysetupActivity extends Activity
         }
     }
 
+    private void closeIOCStack() {
+        try {
+            /*
+             * Close DataBase
+             */
+            OcProvisioning.provisionClose();
+        } catch (OcException e) {
+            logMessage(TAG + "provisionClose error: " + e.getMessage());
+            Log.e(TAG, e.getMessage());
+        }
+    }
+
     OcPlatform.OnResourceFoundListener listener =
             new OcPlatform.OnResourceFoundListener() {
                 @Override
@@ -1150,5 +1162,6 @@ public class EasysetupActivity extends Activity
     @Override
     protected void onDestroy() {
         super.onDestroy();
+        closeIOCStack();
     }
 }
index 08084a0..d4a202e 100755 (executable)
@@ -599,6 +599,10 @@ int main()
         }
     }
 
+#ifdef __WITH_DTLS__
+    // close provisioning db
+    OCSecure::provisionClose();
+#endif
     std::cout << "Stopping the client" << std::endl;
 
     return 0;
index 795b9fd..138f510 100644 (file)
@@ -597,6 +597,10 @@ int main()
         }
     }
 
+#ifdef __WITH_DTLS__
+    // close provisioning db
+    OCSecure::provisionClose();
+#endif
     std::cout << "Stopping the client" << std::endl;
 
     return 0;