Merge "Refactor variable name from gce_user to user."
diff --git a/create/avd_spec.py b/create/avd_spec.py
index b87874d..27bf6fe 100644
--- a/create/avd_spec.py
+++ b/create/avd_spec.py
@@ -639,8 +639,24 @@
 
     @property
     def autoconnect(self):
-        """Return autoconnect."""
-        return self._autoconnect
+        """autoconnect.
+
+        args.autoconnect could pass in type of Boolean or String.
+
+        Return: Boolean, True only if self._autoconnect is not False.
+        """
+        return self._autoconnect is not False
+
+    @property
+    def connect_vnc(self):
+        """launch vnc.
+
+        args.autoconnect could pass in type of Boolean or String.
+        if args.autoconnect is "adb" or False, no need to launch vnc.
+
+        Return: Boolean, True only if self._autoconnect is True.
+        """
+        return self._autoconnect is True
 
     @property
     def unlock_screen(self):
diff --git a/create/avd_spec_test.py b/create/avd_spec_test.py
index 2ec9f94..448cd39 100644
--- a/create/avd_spec_test.py
+++ b/create/avd_spec_test.py
@@ -354,6 +354,22 @@
         self.AvdSpec._ProcessMiscArgs(self.args)
         self.assertEqual(self.AvdSpec._instance_type, constants.INSTANCE_TYPE_HOST)
 
+        # Test avd_spec.autoconnect and avd_spec.connect_vnc
+        self.args.autoconnect = True
+        self.AvdSpec._ProcessMiscArgs(self.args)
+        self.assertEqual(self.AvdSpec.autoconnect, True)
+        self.assertEqual(self.AvdSpec.connect_vnc, True)
+
+        self.args.autoconnect = False
+        self.AvdSpec._ProcessMiscArgs(self.args)
+        self.assertEqual(self.AvdSpec.autoconnect, False)
+        self.assertEqual(self.AvdSpec.connect_vnc, False)
+
+        self.args.autoconnect = "adb"
+        self.AvdSpec._ProcessMiscArgs(self.args)
+        self.assertEqual(self.AvdSpec.autoconnect, True)
+        self.assertEqual(self.AvdSpec.connect_vnc, False)
+
 
 if __name__ == "__main__":
     unittest.main()
diff --git a/create/cheeps_remote_image_remote_instance.py b/create/cheeps_remote_image_remote_instance.py
index d1efd73..357e0b2 100644
--- a/create/cheeps_remote_image_remote_instance.py
+++ b/create/cheeps_remote_image_remote_instance.py
@@ -63,7 +63,7 @@
             boot_timeout_secs=avd_spec.boot_timeout_secs)
 
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(report, avd_spec, no_prompts)
 
         return report
diff --git a/create/create_args.py b/create/create_args.py
index 1c5dfbb..733215a 100644
--- a/create/create_args.py
+++ b/create/create_args.py
@@ -51,13 +51,17 @@
              "when a device fails on boot.")
     parser.add_argument(
         "--autoconnect",
-        action="store_true",
+        type=str,
+        nargs="?",
+        const=True,
         dest="autoconnect",
         required=False,
+        choices=[True, "adb"],
         help="For each remote instance, automatically create 2 ssh tunnels "
              "forwarding both adb & vnc, and then add the device to adb. "
              "For local cuttlefish instance, create a vnc connection. "
-             "For local goldfish instance, create a window.")
+             "For local goldfish instance, create a window."
+             "If need adb only, you can pass in 'adb' here.")
     parser.add_argument(
         "--no-autoconnect",
         action="store_false",
diff --git a/create/gce_local_image_remote_instance.py b/create/gce_local_image_remote_instance.py
index 0b56cc9..b18bd86 100644
--- a/create/gce_local_image_remote_instance.py
+++ b/create/gce_local_image_remote_instance.py
@@ -53,7 +53,7 @@
             avd_spec=avd_spec)
 
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(report, avd_spec, no_prompts)
 
         return report
diff --git a/create/gce_remote_image_remote_instance.py b/create/gce_remote_image_remote_instance.py
index 2d1fb6c..52ab375 100644
--- a/create/gce_remote_image_remote_instance.py
+++ b/create/gce_remote_image_remote_instance.py
@@ -53,7 +53,7 @@
             avd_spec=avd_spec)
 
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(report, avd_spec, no_prompts)
 
         return report
diff --git a/create/goldfish_local_image_local_instance.py b/create/goldfish_local_image_local_instance.py
index 7736588..e09267e 100644
--- a/create/goldfish_local_image_local_instance.py
+++ b/create/goldfish_local_image_local_instance.py
@@ -229,6 +229,8 @@
                              _DEFAULT_EMULATOR_TIMEOUT_SECS)
         self._WaitForEmulatorToStart(adb, proc, boot_timeout_secs)
 
+        inst.WriteCreationTimestamp()
+
         result_report = report.Report(command="create")
         result_report.SetStatus(report.Status.SUCCESS)
         # Emulator has no VNC port.
@@ -410,6 +412,8 @@
         """
         emulator_env = os.environ.copy()
         emulator_env[constants.ENV_ANDROID_PRODUCT_OUT] = image_dir
+        # Set ANDROID_TMP for emulator to create AVD info files in.
+        emulator_env[constants.ENV_ANDROID_TMP] = working_dir
         # Set ANDROID_BUILD_TOP so that the emulator considers itself to be in
         # build environment.
         if constants.ENV_ANDROID_BUILD_TOP not in emulator_env:
diff --git a/create/goldfish_remote_image_remote_instance.py b/create/goldfish_remote_image_remote_instance.py
index 592ffaf..31e24ec 100644
--- a/create/goldfish_remote_image_remote_instance.py
+++ b/create/goldfish_remote_image_remote_instance.py
@@ -40,6 +40,6 @@
         report = create_goldfish_action.CreateDevices(avd_spec=avd_spec)
 
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(report, avd_spec, no_prompts)
         return report
diff --git a/create/local_image_local_instance.py b/create/local_image_local_instance.py
index dfeee30..6787b2f 100644
--- a/create/local_image_local_instance.py
+++ b/create/local_image_local_instance.py
@@ -67,7 +67,7 @@
 _ENV_ANDROID_HOST_OUT = "ANDROID_HOST_OUT"
 _ENV_CVD_HOME = "HOME"
 _ENV_CUTTLEFISH_INSTANCE = "CUTTLEFISH_INSTANCE"
-_LAUNCH_CVD_TIMEOUT_SECS = 60  # default timeout as 60 seconds
+_LAUNCH_CVD_TIMEOUT_SECS = 120  # default timeout as 120 seconds
 _LAUNCH_CVD_TIMEOUT_ERROR = ("Cuttlefish AVD launch timeout, did not complete "
                              "within %d secs.")
 _VIRTUAL_DISK_PATHS = "virtual_disk_paths"
@@ -121,7 +121,7 @@
             value={constants.ADB_PORT: local_ports.adb_port,
                    constants.VNC_PORT: local_ports.vnc_port})
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(result_report, avd_spec, no_prompts)
         if avd_spec.unlock_screen:
             AdbTools(local_ports.adb_port).AutoUnlockScreen()
@@ -282,7 +282,8 @@
         cvd_env[_ENV_CUTTLEFISH_INSTANCE] = str(local_instance_id)
         # Check the result of launch_cvd command.
         # An exit code of 0 is equivalent to VIRTUAL_DEVICE_BOOT_COMPLETED
-        process = subprocess.Popen(cmd, shell=True, stderr=subprocess.STDOUT)
+        process = subprocess.Popen(cmd, shell=True, stderr=subprocess.STDOUT,
+                                   env=cvd_env)
         if timeout:
             timer = threading.Timer(timeout, process.kill)
             timer.start()
diff --git a/create/local_image_local_instance_test.py b/create/local_image_local_instance_test.py
index ffe6f49..accdd5e 100644
--- a/create/local_image_local_instance_test.py
+++ b/create/local_image_local_instance_test.py
@@ -15,16 +15,20 @@
 # limitations under the License.
 """Tests for LocalImageLocalInstance."""
 
+import os
+import shutil
+import subprocess
 import unittest
 import mock
 
 from acloud.create import local_image_local_instance
 from acloud.list import instance
 from acloud.internal import constants
+from acloud.internal.lib import driver_test_lib
 from acloud.internal.lib import utils
 
 
-class LocalImageLocalInstanceTest(unittest.TestCase):
+class LocalImageLocalInstanceTest(driver_test_lib.BaseDriverTest):
     """Test LocalImageLocalInstance method."""
 
     LAUNCH_CVD_CMD_WITH_DISK = """sg group1 <<EOF
@@ -39,6 +43,7 @@
 
     def setUp(self):
         """Initialize new LocalImageLocalInstance."""
+        super(LocalImageLocalInstanceTest, self).setUp()
         self.local_image_local_instance = local_image_local_instance.LocalImageLocalInstance()
 
     # pylint: disable=protected-access
@@ -109,5 +114,33 @@
         mock_launch_cvd.assert_called_once_with(
             "fake_launch_cvd", 3, timeout=local_image_local_instance._LAUNCH_CVD_TIMEOUT_SECS)
 
+    # pylint: disable=protected-access
+    @mock.patch.dict("os.environ", clear=True)
+    def testLaunchCVD(self):
+        """test _LaunchCvd should call subprocess.Popen with the specific env"""
+        local_instance_id = 3
+        launch_cvd_cmd = "launch_cvd"
+        cvd_env = {}
+        cvd_env[local_image_local_instance._ENV_CVD_HOME] = "fake_home"
+        cvd_env[local_image_local_instance._ENV_CUTTLEFISH_INSTANCE] = str(
+            local_instance_id)
+        process = mock.MagicMock()
+        process.wait.return_value = True
+        process.returncode = 0
+        self.Patch(subprocess, "Popen", return_value=process)
+        self.Patch(instance, "GetLocalInstanceHomeDir",
+                   return_value="fake_home")
+        self.Patch(os, "makedirs")
+        self.Patch(shutil, "rmtree")
+
+        self.local_image_local_instance._LaunchCvd(launch_cvd_cmd,
+                                                   local_instance_id)
+        # pylint: disable=no-member
+        subprocess.Popen.assert_called_once_with(launch_cvd_cmd,
+                                                 shell=True,
+                                                 stderr=subprocess.STDOUT,
+                                                 env=cvd_env)
+
+
 if __name__ == "__main__":
     unittest.main()
diff --git a/create/local_image_remote_host.py b/create/local_image_remote_host.py
index 1aa999f..d812771 100644
--- a/create/local_image_remote_host.py
+++ b/create/local_image_remote_host.py
@@ -55,6 +55,6 @@
             unlock_screen=avd_spec.unlock_screen,
             wait_for_boot=False)
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(report, avd_spec, no_prompts)
         return report
diff --git a/create/local_image_remote_instance.py b/create/local_image_remote_instance.py
index b6c1411..a0f5ca2 100644
--- a/create/local_image_remote_instance.py
+++ b/create/local_image_remote_instance.py
@@ -55,6 +55,6 @@
             unlock_screen=avd_spec.unlock_screen,
             wait_for_boot=False)
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(report, avd_spec, no_prompts)
         return report
diff --git a/create/remote_image_remote_host.py b/create/remote_image_remote_host.py
index 4bc619c..700b169 100644
--- a/create/remote_image_remote_host.py
+++ b/create/remote_image_remote_host.py
@@ -91,7 +91,7 @@
             unlock_screen=avd_spec.unlock_screen,
             wait_for_boot=False)
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(report, avd_spec, no_prompts)
         shutil.rmtree(extract_path)
         return report
diff --git a/create/remote_image_remote_instance.py b/create/remote_image_remote_instance.py
index d10c5ce..13d24ad 100644
--- a/create/remote_image_remote_instance.py
+++ b/create/remote_image_remote_instance.py
@@ -52,7 +52,7 @@
             unlock_screen=avd_spec.unlock_screen,
             wait_for_boot=False)
         # Launch vnc client if we're auto-connecting.
-        if avd_spec.autoconnect:
+        if avd_spec.connect_vnc:
             utils.LaunchVNCFromReport(report, avd_spec, no_prompts)
 
         return report
diff --git a/delete/delete.py b/delete/delete.py
index c7aec43..7e26d0f 100644
--- a/delete/delete.py
+++ b/delete/delete.py
@@ -22,7 +22,6 @@
 import logging
 import os
 import re
-import shutil
 import subprocess
 
 from acloud import errors
@@ -221,7 +220,7 @@
         delete_report.AddError("Cannot kill %s." % instance.device_serial)
         delete_report.SetStatus(report.Status.FAIL)
 
-    shutil.rmtree(instance.instance_dir, ignore_errors=True)
+    instance.DeleteCreationTimestamp(ignore_errors=True)
     return delete_report
 
 
diff --git a/delete/delete_test.py b/delete/delete_test.py
index 0e48153..b50de00 100644
--- a/delete/delete_test.py
+++ b/delete/delete_test.py
@@ -58,10 +58,8 @@
         })
         self.assertEqual(delete_report.status, "SUCCESS")
 
-    @mock.patch("acloud.delete.delete.shutil")
     @mock.patch("acloud.delete.delete.adb_tools.AdbTools")
-    def testDeleteLocalGoldfishInstanceSuccess(self, mock_adb_tools,
-                                               mock_shutil):
+    def testDeleteLocalGoldfishInstanceSuccess(self, mock_adb_tools):
         """Test DeleteLocalGoldfishInstance."""
         mock_instance = mock.Mock(adb_port=5555,
                                   device_serial="serial",
@@ -77,7 +75,7 @@
         delete.DeleteLocalGoldfishInstance(mock_instance, delete_report)
 
         mock_adb_tools_obj.EmuCommand.assert_called_with("kill")
-        mock_shutil.rmtree.assert_called_with("/unit/test", ignore_errors=True)
+        mock_instance.DeleteCreationTimestamp.assert_called()
         self.assertEqual(delete_report.data, {
             "deleted": [
                 {
@@ -88,10 +86,8 @@
         })
         self.assertEqual(delete_report.status, "SUCCESS")
 
-    @mock.patch("acloud.delete.delete.shutil")
     @mock.patch("acloud.delete.delete.adb_tools.AdbTools")
-    def testDeleteLocalGoldfishInstanceFailure(self, mock_adb_tools,
-                                               mock_shutil):
+    def testDeleteLocalGoldfishInstanceFailure(self, mock_adb_tools):
         """Test DeleteLocalGoldfishInstance with adb command failure."""
         mock_instance = mock.Mock(adb_port=5555,
                                   device_serial="serial",
@@ -107,7 +103,7 @@
         delete.DeleteLocalGoldfishInstance(mock_instance, delete_report)
 
         mock_adb_tools_obj.EmuCommand.assert_called_with("kill")
-        mock_shutil.rmtree.assert_called_with("/unit/test", ignore_errors=True)
+        mock_instance.DeleteCreationTimestamp.assert_called()
         self.assertTrue(len(delete_report.errors) > 0)
         self.assertEqual(delete_report.status, "FAIL")
 
diff --git a/internal/constants.py b/internal/constants.py
index dc42864..5890aad 100755
--- a/internal/constants.py
+++ b/internal/constants.py
@@ -121,6 +121,7 @@
 ENV_ANDROID_EMULATOR_PREBUILTS = "ANDROID_EMULATOR_PREBUILTS"
 ENV_ANDROID_HOST_OUT = "ANDROID_HOST_OUT"
 ENV_ANDROID_PRODUCT_OUT = "ANDROID_PRODUCT_OUT"
+ENV_ANDROID_TMP = "ANDROID_TMP"
 ENV_BUILD_TARGET = "TARGET_PRODUCT"
 
 LOCALHOST = "127.0.0.1"
diff --git a/list/instance.py b/list/instance.py
index 97f68a8..f54b5dc 100644
--- a/list/instance.py
+++ b/list/instance.py
@@ -130,6 +130,11 @@
                       adb_port=constants.CF_ADB_PORT + local_instance_id - 1)
 
 
+def _GetCurrentLocalTime():
+    """Return a datetime object for current time in local time zone."""
+    return datetime.datetime.now(dateutil.tz.tzlocal())
+
+
 def _GetElapsedTime(start_time):
     """Calculate the elapsed time from start_time till now.
 
@@ -145,12 +150,10 @@
         # Check start_time has timezone or not. If timezone can't be found,
         # use local timezone to get elapsed time.
         if match:
-            return datetime.datetime.now(
-                dateutil.tz.tzlocal()) - dateutil.parser.parse(start_time)
+            return _GetCurrentLocalTime() - dateutil.parser.parse(start_time)
 
-        return datetime.datetime.now(
-            dateutil.tz.tzlocal()) - dateutil.parser.parse(
-                start_time).replace(tzinfo=dateutil.tz.tzlocal())
+        return _GetCurrentLocalTime() - dateutil.parser.parse(
+            start_time).replace(tzinfo=dateutil.tz.tzlocal())
     except ValueError:
         logger.debug(("Can't parse datetime string(%s)."), start_time)
         return _MSG_UNABLE_TO_CALCULATE
@@ -342,17 +345,19 @@
 
     _INSTANCE_DIR_PATTERN = re.compile(r"^instance-(?P<id>\d+)$")
     _INSTANCE_DIR_FORMAT = "instance-%(id)s"
+    _CREATION_TIMESTAMP_FILE_NAME = "creation_timestamp.txt"
     _INSTANCE_NAME_FORMAT = "local-goldfish-instance-%(id)s"
     _EMULATOR_DEFAULT_CONSOLE_PORT = 5554
     _GF_ADB_DEVICE_SERIAL = "emulator-%(console_port)s"
 
-    def __init__(self, local_instance_id, avd_flavor=None, x_res=None,
-                 y_res=None, dpi=None):
+    def __init__(self, local_instance_id, avd_flavor=None, create_time=None,
+                 x_res=None, y_res=None, dpi=None):
         """Initialize a LocalGoldfishInstance object.
 
         Args:
             local_instance_id: Integer of instance id.
             avd_flavor: String, the flavor of the virtual device.
+            create_time: String, the creation date and time.
             x_res: Integer of x dimension.
             y_res: Integer of y dimension.
             dpi: Integer of dpi.
@@ -363,10 +368,11 @@
 
         name = self._INSTANCE_NAME_FORMAT % {"id": local_instance_id}
 
-        fullname = (_FULL_NAME_STRING %
-                    {"device_serial": self.device_serial,
-                     "instance_name": name,
-                     "elapsed_time": None})
+        elapsed_time = _GetElapsedTime(create_time) if create_time else None
+
+        fullname = _FULL_NAME_STRING % {"device_serial": self.device_serial,
+                                        "instance_name": name,
+                                        "elapsed_time": elapsed_time}
 
         if x_res and y_res and dpi:
             display = _DISPLAY_STRING % {"x_res": x_res, "y_res": y_res,
@@ -381,6 +387,7 @@
         super(LocalGoldfishInstance, self).__init__(
             name=name, fullname=fullname, display=display, ip="127.0.0.1",
             status=None, adb_port=adb_port, avd_type=constants.TYPE_GF,
+            createtime=create_time, elapsed_time=elapsed_time,
             avd_flavor=avd_flavor, is_local=True,
             device_information=device_information)
 
@@ -406,18 +413,51 @@
         return os.path.join(self._GetInstanceDirRoot(),
                             self._INSTANCE_DIR_FORMAT % {"id": self._id})
 
+    @property
+    def creation_timestamp_path(self):
+        """Return the file path containing the creation timestamp."""
+        return os.path.join(self.instance_dir,
+                            self._CREATION_TIMESTAMP_FILE_NAME)
+
+    def WriteCreationTimestamp(self):
+        """Write creation timestamp to file."""
+        with open(self.creation_timestamp_path, "w") as timestamp_file:
+            timestamp_file.write(str(_GetCurrentLocalTime()))
+
+    def DeleteCreationTimestamp(self, ignore_errors):
+        """Delete the creation timestamp file.
+
+        Args:
+            ignore_errors: Boolean, whether to ignore the errors.
+
+        Raises:
+            OSError if fails to delete the file.
+        """
+        try:
+            os.remove(self.creation_timestamp_path)
+        except OSError as e:
+            if not ignore_errors:
+                raise
+            logger.warning("Can't delete creation timestamp: %s", e)
+
     @classmethod
     def GetExistingInstances(cls):
-        """Get a list of instances from existing instance directories."""
+        """Get a list of instances that have creation timestamp files."""
         instance_root = cls._GetInstanceDirRoot()
         if not os.path.isdir(instance_root):
             return []
+
         instances = []
         for name in os.listdir(instance_root):
             match = cls._INSTANCE_DIR_PATTERN.match(name)
-            if match and os.path.isdir(os.path.join(instance_root, name)):
+            timestamp_path = os.path.join(instance_root, name,
+                                          cls._CREATION_TIMESTAMP_FILE_NAME)
+            if match and os.path.isfile(timestamp_path):
                 instance_id = int(match.group("id"))
-                instances.append(LocalGoldfishInstance(instance_id))
+                with open(timestamp_path, "r") as timestamp_file:
+                    timestamp = timestamp_file.read().strip()
+                instances.append(LocalGoldfishInstance(instance_id,
+                                                       create_time=timestamp))
         return instances
 
 
diff --git a/list/instance_test.py b/list/instance_test.py
index efbc0d0..635a512 100644
--- a/list/instance_test.py
+++ b/list/instance_test.py
@@ -102,31 +102,53 @@
         self.assertEqual(inst.instance_dir,
                          "/unit/test/acloud_gf_temp/instance-1")
 
+    @mock.patch("acloud.list.instance.open",
+                mock.mock_open(read_data="test createtime"))
+    @mock.patch("acloud.list.instance.os.path.isfile")
     @mock.patch("acloud.list.instance.os.listdir")
     @mock.patch("acloud.list.instance.os.path.isdir")
     @mock.patch("acloud.list.instance.tempfile")
     @mock.patch("acloud.list.instance.AdbTools")
-    def testGetLocalGoldfishInstances(self, mock_adb_tools, mock_tempfile,
-                                      mock_isdir, mock_listdir):
+    @mock.patch("acloud.list.instance._GetElapsedTime")
+    def testGetLocalGoldfishInstances(self, mock_get_elapsed_time,
+                                      mock_adb_tools, mock_tempfile,
+                                      mock_isdir, mock_listdir, mock_isfile):
         """Test LocalGoldfishInstance.GetExistingInstances."""
-        mock_tempfile.gettempdir.return_value = "/unit/test"
+        mock_get_elapsed_time.return_value = datetime.timedelta(hours=10)
         mock_adb_tools.return_value = mock.Mock(device_information={})
-        mock_listdir.side_effect = lambda path: (
-            ["instance-1", "instance-3"] if
-            path == "/unit/test/acloud_gf_temp" else [])
+        mock_tempfile.gettempdir.return_value = "/unit/test"
         mock_isdir.side_effect = lambda path: (
-            path in ("/unit/test/acloud_gf_temp",
-                     "/unit/test/acloud_gf_temp/instance-1",
-                     "/unit/test/acloud_gf_temp/instance-3"))
+            path == "/unit/test/acloud_gf_temp")
+        mock_listdir.side_effect = lambda path: (
+            ["instance-1", "instance-2", "instance-3"] if
+            path == "/unit/test/acloud_gf_temp" else [])
+        mock_isfile.side_effect = lambda path: path in (
+            "/unit/test/acloud_gf_temp/instance-1/creation_timestamp.txt",
+            "/unit/test/acloud_gf_temp/instance-3/creation_timestamp.txt")
 
         instances = instance.LocalGoldfishInstance.GetExistingInstances()
 
+        mock_isdir.assert_called_with("/unit/test/acloud_gf_temp")
         mock_listdir.assert_called_with("/unit/test/acloud_gf_temp")
-        mock_isdir.assert_any_call("/unit/test/acloud_gf_temp/instance-1")
-        mock_isdir.assert_any_call("/unit/test/acloud_gf_temp/instance-3")
+        mock_isfile.assert_any_call(
+            "/unit/test/acloud_gf_temp/instance-1/creation_timestamp.txt")
+        mock_isfile.assert_any_call(
+            "/unit/test/acloud_gf_temp/instance-2/creation_timestamp.txt")
+        mock_isfile.assert_any_call(
+            "/unit/test/acloud_gf_temp/instance-3/creation_timestamp.txt")
         self.assertEqual(len(instances), 2)
         self.assertEqual(instances[0].console_port, 5554)
+        self.assertEqual(instances[0].createtime, "test createtime")
+        self.assertEqual(instances[0].fullname,
+                         "device serial: emulator-5554 "
+                         "(local-goldfish-instance-1) "
+                         "elapsed time: 10:00:00")
         self.assertEqual(instances[1].console_port, 5558)
+        self.assertEqual(instances[1].createtime, "test createtime")
+        self.assertEqual(instances[1].fullname,
+                         "device serial: emulator-5558 "
+                         "(local-goldfish-instance-3) "
+                         "elapsed time: 10:00:00")
 
     def testGetElapsedTime(self):
         """Test _GetElapsedTime"""
diff --git a/reconnect/reconnect.py b/reconnect/reconnect.py
index 2c653ec..c87269f 100644
--- a/reconnect/reconnect.py
+++ b/reconnect/reconnect.py
@@ -85,7 +85,8 @@
 def ReconnectInstance(ssh_private_key_path,
                       instance,
                       reconnect_report,
-                      extra_args_ssh_tunnel=None):
+                      extra_args_ssh_tunnel=None,
+                      connect_vnc=True):
     """Reconnect to the specified instance.
 
     It will:
@@ -100,6 +101,7 @@
         instance: list.Instance() object.
         reconnect_report: Report object.
         extra_args_ssh_tunnel: String, extra args for ssh tunnel connection.
+        connect_vnc: Boolean, True will launch vnc.
 
     Raises:
         errors.UnknownAvdType: Unable to reconnect to instance of unknown avd
@@ -130,7 +132,7 @@
         vnc_port = forwarded_ports.vnc_port
         adb_port = forwarded_ports.adb_port
 
-    if vnc_port:
+    if vnc_port and connect_vnc:
         StartVnc(vnc_port, instance.display)
 
     device_dict = {
@@ -178,6 +180,7 @@
         ReconnectInstance(cfg.ssh_private_key_path,
                           instance,
                           reconnect_report,
-                          cfg.extra_args_ssh_tunnel)
+                          cfg.extra_args_ssh_tunnel,
+                          connect_vnc=(args.autoconnect is True))
 
     utils.PrintDeviceSummary(reconnect_report)
diff --git a/reconnect/reconnect_args.py b/reconnect/reconnect_args.py
index f481bbe..503f000 100644
--- a/reconnect/reconnect_args.py
+++ b/reconnect/reconnect_args.py
@@ -46,5 +46,15 @@
         dest="all",
         required=False,
         help="If more than 1 AVD instance is found, reconnect them all.")
+    reconnect_parser.add_argument(
+        "--autoconnect",
+        type=str,
+        nargs="?",
+        const=True,
+        dest="autoconnect",
+        required=False,
+        choices=[True, "adb"],
+        default=True,
+        help="If need adb only, you can pass in 'adb' here.")
 
     return reconnect_parser