1 /* 2 * Copyright (C) 2010 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 package com.android.tradefed.testtype; 17 18 import static org.junit.Assert.assertEquals; 19 import static org.junit.Assert.assertFalse; 20 import static org.junit.Assert.assertTrue; 21 import static org.junit.Assert.fail; 22 23 import com.android.ddmlib.FileListingService; 24 import com.android.ddmlib.IShellOutputReceiver; 25 import com.android.tradefed.config.Configuration; 26 import com.android.tradefed.config.OptionSetter; 27 import com.android.tradefed.device.CollectingOutputReceiver; 28 import com.android.tradefed.device.DeviceNotAvailableException; 29 import com.android.tradefed.device.ITestDevice; 30 import com.android.tradefed.device.MockFileUtil; 31 import com.android.tradefed.invoker.TestInformation; 32 import com.android.tradefed.result.ITestInvocationListener; 33 import com.android.tradefed.testtype.coverage.CoverageOptions; 34 35 import org.easymock.EasyMock; 36 import org.junit.Before; 37 import org.junit.Test; 38 import org.junit.runner.RunWith; 39 import org.junit.runners.JUnit4; 40 41 import java.io.File; 42 import java.util.ArrayList; 43 import java.util.List; 44 import java.util.concurrent.TimeUnit; 45 46 47 /** Unit tests for {@link GTest}. */ 48 @RunWith(JUnit4.class) 49 public class GTestTest { 50 private static final String GTEST_FLAG_FILTER = "--gtest_filter"; 51 private ITestInvocationListener mMockInvocationListener = null; 52 private IShellOutputReceiver mMockReceiver = null; 53 private ITestDevice mMockITestDevice = null; 54 private GTest mGTest; 55 private OptionSetter mSetter; 56 57 private TestInformation mTestInfo; 58 private Configuration mConfiguration; 59 private CoverageOptions mCoverageOptions; 60 private OptionSetter mCoverageOptionsSetter; 61 62 /** Helper to initialize the various EasyMocks we'll need. */ 63 @Before setUp()64 public void setUp() throws Exception { 65 mMockInvocationListener = EasyMock.createMock(ITestInvocationListener.class); 66 mMockReceiver = EasyMock.createMock(IShellOutputReceiver.class); 67 mMockITestDevice = EasyMock.createMock(ITestDevice.class); 68 mMockReceiver.flush(); 69 EasyMock.expectLastCall().anyTimes(); 70 EasyMock.expect(mMockITestDevice.getSerialNumber()).andStubReturn("serial"); 71 mGTest = 72 new GTest() { 73 @Override 74 IShellOutputReceiver createResultParser( 75 String runName, ITestInvocationListener listener) { 76 return mMockReceiver; 77 } 78 79 @Override 80 GTestXmlResultParser createXmlParser( 81 String testRunName, ITestInvocationListener listener) { 82 return new GTestXmlResultParser(testRunName, listener) { 83 @Override 84 public void parseResult(File f, CollectingOutputReceiver output) { 85 return; 86 } 87 }; 88 } 89 }; 90 mGTest.setDevice(mMockITestDevice); 91 mSetter = new OptionSetter(mGTest); 92 93 // Set up the coverage options 94 mConfiguration = new Configuration("", ""); 95 mCoverageOptions = new CoverageOptions(); 96 mCoverageOptionsSetter = new OptionSetter(mCoverageOptions); 97 98 mConfiguration.setCoverageOptions(mCoverageOptions); 99 mGTest.setConfiguration(mConfiguration); 100 101 mTestInfo = TestInformation.newBuilder().build(); 102 } 103 104 /** 105 * Helper that replays all mocks. 106 */ replayMocks()107 private void replayMocks() { 108 EasyMock.replay(mMockInvocationListener, mMockITestDevice, mMockReceiver); 109 } 110 111 /** 112 * Helper that verifies all mocks. 113 */ verifyMocks()114 private void verifyMocks() { 115 EasyMock.verify(mMockInvocationListener, mMockITestDevice, mMockReceiver); 116 } 117 118 /** Test run when the test dir is not found on the device. */ 119 @Test testRun_noTestDir()120 public void testRun_noTestDir() throws DeviceNotAvailableException { 121 EasyMock.expect(mMockITestDevice.doesFileExist(GTest.DEFAULT_NATIVETEST_PATH)) 122 .andReturn(false); 123 replayMocks(); 124 mGTest.run(mTestInfo, mMockInvocationListener); 125 verifyMocks(); 126 } 127 128 /** Test run when no device is set should throw an exception. */ 129 @Test testRun_noDevice()130 public void testRun_noDevice() throws DeviceNotAvailableException { 131 mGTest.setDevice(null); 132 replayMocks(); 133 try { 134 mGTest.run(mTestInfo, mMockInvocationListener); 135 fail("an exception should have been thrown"); 136 } catch (IllegalArgumentException e) { 137 // expected 138 } 139 verifyMocks(); 140 } 141 142 /** Test the run method for a couple tests */ 143 @Test testRun()144 public void testRun() throws DeviceNotAvailableException { 145 final String nativeTestPath = GTest.DEFAULT_NATIVETEST_PATH; 146 final String test1 = "test1"; 147 final String test2 = "test2"; 148 final String testPath1 = String.format("%s/%s", nativeTestPath, test1); 149 final String testPath2 = String.format("%s/%s", nativeTestPath, test2); 150 151 152 MockFileUtil.setMockDirContents(mMockITestDevice, nativeTestPath, test1, test2); 153 EasyMock.expect(mMockITestDevice.doesFileExist(nativeTestPath)).andReturn(true); 154 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath)).andReturn(true); 155 EasyMock.expect(mMockITestDevice.isDirectory(testPath1)).andReturn(false); 156 // report the file as executable 157 EasyMock.expect(mMockITestDevice.isExecutable(testPath1)).andReturn(true); 158 EasyMock.expect(mMockITestDevice.isDirectory(testPath2)).andReturn(false); 159 // report the file as executable 160 EasyMock.expect(mMockITestDevice.isExecutable(testPath2)).andReturn(true); 161 162 String[] files = new String[] {"test1", "test2"}; 163 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath)).andReturn(files); 164 mMockITestDevice.executeShellCommand( 165 EasyMock.contains(test1), 166 EasyMock.same(mMockReceiver), 167 EasyMock.anyLong(), 168 (TimeUnit) EasyMock.anyObject(), 169 EasyMock.anyInt()); 170 mMockITestDevice.executeShellCommand( 171 EasyMock.contains(test2), 172 EasyMock.same(mMockReceiver), 173 EasyMock.anyLong(), 174 (TimeUnit) EasyMock.anyObject(), 175 EasyMock.anyInt()); 176 177 replayMocks(); 178 179 mGTest.run(mTestInfo, mMockInvocationListener); 180 verifyMocks(); 181 } 182 183 @Test testRunFilterAbiPath()184 public void testRunFilterAbiPath() throws DeviceNotAvailableException { 185 final String nativeTestPath = GTest.DEFAULT_NATIVETEST_PATH; 186 final String test1 = "arm/test1"; 187 final String test2 = "arm64/test2"; 188 final String testPath2 = String.format("%s/%s", nativeTestPath, test2); 189 MockFileUtil.setMockDirContents(mMockITestDevice, nativeTestPath, test1, test2); 190 mGTest.setAbi(new Abi("arm64-v8a", "64")); 191 192 EasyMock.expect(mMockITestDevice.doesFileExist(nativeTestPath)).andReturn(true); 193 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath)).andReturn(true); 194 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath + "/arm")).andReturn(true); 195 196 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath + "/arm64")).andReturn(true); 197 EasyMock.expect(mMockITestDevice.isDirectory(testPath2)).andReturn(false); 198 // report the file as executable 199 EasyMock.expect(mMockITestDevice.isExecutable(testPath2)).andReturn(true); 200 201 String[] dirs = new String[] {"arm", "arm64"}; 202 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath)).andReturn(dirs); 203 String[] testFiles = new String[] {"test2"}; 204 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath + "/arm64")) 205 .andReturn(testFiles); 206 mMockITestDevice.executeShellCommand( 207 EasyMock.contains(test2), 208 EasyMock.same(mMockReceiver), 209 EasyMock.anyLong(), 210 (TimeUnit) EasyMock.anyObject(), 211 EasyMock.anyInt()); 212 213 replayMocks(); 214 215 mGTest.run(mTestInfo, mMockInvocationListener); 216 verifyMocks(); 217 } 218 219 /** Test the run method when module name is specified */ 220 @Test testRun_moduleName()221 public void testRun_moduleName() throws DeviceNotAvailableException { 222 final String module = "test1"; 223 final String modulePath = String.format("%s%s%s", 224 GTest.DEFAULT_NATIVETEST_PATH, FileListingService.FILE_SEPARATOR, module); 225 MockFileUtil.setMockDirContents(mMockITestDevice, modulePath, new String[] {}); 226 227 mGTest.setModuleName(module); 228 229 EasyMock.expect(mMockITestDevice.doesFileExist(modulePath)).andReturn(true); 230 EasyMock.expect(mMockITestDevice.isDirectory(modulePath)).andReturn(false); 231 mMockITestDevice.executeShellCommand(EasyMock.contains(modulePath), 232 EasyMock.same(mMockReceiver), 233 EasyMock.anyLong(), (TimeUnit)EasyMock.anyObject(), EasyMock.anyInt()); 234 // report the file as executable 235 EasyMock.expect(mMockITestDevice.isExecutable(modulePath)).andReturn(true); 236 237 replayMocks(); 238 239 mGTest.run(mTestInfo, mMockInvocationListener); 240 verifyMocks(); 241 } 242 243 /** Test the run method for a test in a subdirectory */ 244 @Test testRun_nested()245 public void testRun_nested() throws DeviceNotAvailableException { 246 final String nativeTestPath = GTest.DEFAULT_NATIVETEST_PATH; 247 final String subFolderName = "subFolder"; 248 final String test1 = "test1"; 249 final String test1Path = String.format("%s%s%s%s%s", nativeTestPath, 250 FileListingService.FILE_SEPARATOR, 251 subFolderName, 252 FileListingService.FILE_SEPARATOR, test1); 253 MockFileUtil.setMockDirPath(mMockITestDevice, nativeTestPath, subFolderName, test1); 254 EasyMock.expect(mMockITestDevice.doesFileExist(nativeTestPath)).andReturn(true); 255 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath)).andReturn(true); 256 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath + "/" + subFolderName)) 257 .andReturn(true); 258 EasyMock.expect(mMockITestDevice.isDirectory(test1Path)).andReturn(false); 259 // report the file as executable 260 EasyMock.expect(mMockITestDevice.isExecutable(test1Path)).andReturn(true); 261 String[] files = new String[] {subFolderName}; 262 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath)).andReturn(files); 263 String[] files2 = new String[] {"test1"}; 264 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath + "/" + subFolderName)) 265 .andReturn(files2); 266 mMockITestDevice.executeShellCommand(EasyMock.contains(test1Path), 267 EasyMock.same(mMockReceiver), 268 EasyMock.anyLong(), (TimeUnit)EasyMock.anyObject(), EasyMock.anyInt()); 269 270 replayMocks(); 271 272 mGTest.run(mTestInfo, mMockInvocationListener); 273 verifyMocks(); 274 } 275 276 /** 277 * Helper function to do the actual filtering test. 278 * 279 * @param filterString The string to search for in the Mock, to verify filtering was called 280 * @throws DeviceNotAvailableException 281 */ doTestFilter(String filterString)282 private void doTestFilter(String filterString) throws DeviceNotAvailableException { 283 String nativeTestPath = GTest.DEFAULT_NATIVETEST_PATH; 284 String testPath = nativeTestPath + "/test1"; 285 // configure the mock file system to have a single test 286 MockFileUtil.setMockDirContents(mMockITestDevice, nativeTestPath, "test1"); 287 EasyMock.expect(mMockITestDevice.doesFileExist(nativeTestPath)).andReturn(true); 288 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath)).andReturn(true); 289 EasyMock.expect(mMockITestDevice.isDirectory(testPath)).andReturn(false); 290 // report the file as executable 291 EasyMock.expect(mMockITestDevice.isExecutable(testPath)).andReturn(true); 292 String[] files = new String[] {"test1"}; 293 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath)).andReturn(files); 294 mMockITestDevice.executeShellCommand(EasyMock.contains(filterString), 295 EasyMock.same(mMockReceiver), EasyMock.anyLong(), (TimeUnit)EasyMock.anyObject(), 296 EasyMock.anyInt()); 297 replayMocks(); 298 mGTest.run(mTestInfo, mMockInvocationListener); 299 300 verifyMocks(); 301 } 302 303 /** Test the include filtering of test methods. */ 304 @Test testIncludeFilter()305 public void testIncludeFilter() throws DeviceNotAvailableException { 306 String includeFilter1 = "abc"; 307 String includeFilter2 = "def"; 308 mGTest.addIncludeFilter(includeFilter1); 309 mGTest.addIncludeFilter(includeFilter2); 310 doTestFilter(String.format("%s=%s:%s", GTEST_FLAG_FILTER, includeFilter1, includeFilter2)); 311 } 312 313 /** Test that large filters are converted to flagfile. */ 314 @Test testLargeFilters()315 public void testLargeFilters() throws DeviceNotAvailableException { 316 StringBuilder includeFilter1 = new StringBuilder("abc"); 317 for (int i = 0; i < 550; i++) { 318 includeFilter1.append("a"); 319 } 320 String includeFilter2 = "def"; 321 mGTest.addIncludeFilter(includeFilter1.toString()); 322 mGTest.addIncludeFilter(includeFilter2); 323 324 EasyMock.expect(mMockITestDevice.pushFile(EasyMock.anyObject(), EasyMock.anyObject())) 325 .andReturn(true); 326 327 doTestFilter(String.format("%s=/data/local/tmp/flagfile", GTestBase.GTEST_FLAG_FILE)); 328 } 329 330 /** Test the exclude filtering of test methods. */ 331 @Test testExcludeFilter()332 public void testExcludeFilter() throws DeviceNotAvailableException { 333 String excludeFilter1 = "*don?tRunMe*"; 334 mGTest.addExcludeFilter(excludeFilter1); 335 336 doTestFilter(String.format( 337 "%s=-%s", GTEST_FLAG_FILTER, excludeFilter1)); 338 } 339 340 /** Test simultaneous include and exclude filtering of test methods. */ 341 @Test testIncludeAndExcludeFilters()342 public void testIncludeAndExcludeFilters() throws DeviceNotAvailableException { 343 String includeFilter1 = "pleaseRunMe"; 344 String includeFilter2 = "andMe"; 345 String excludeFilter1 = "dontRunMe"; 346 String excludeFilter2 = "orMe"; 347 mGTest.addIncludeFilter(includeFilter1); 348 mGTest.addExcludeFilter(excludeFilter1); 349 mGTest.addIncludeFilter(includeFilter2); 350 mGTest.addExcludeFilter(excludeFilter2); 351 352 doTestFilter(String.format("%s=%s:%s-%s:%s", GTEST_FLAG_FILTER, 353 includeFilter1, includeFilter2, excludeFilter1, excludeFilter2)); 354 } 355 356 /** Test behavior for command lines too long to be run by ADB */ 357 @Test testCommandTooLong()358 public void testCommandTooLong() throws DeviceNotAvailableException { 359 String deviceScriptPath = "/data/local/tmp/gtest_script.sh"; 360 StringBuilder testNameBuilder = new StringBuilder(); 361 for (int i = 0; i < 1005; i++) { 362 testNameBuilder.append("a"); 363 } 364 String testName = testNameBuilder.toString(); 365 // filter string will be longer than GTest.GTEST_CMD_CHAR_LIMIT 366 367 String nativeTestPath = GTest.DEFAULT_NATIVETEST_PATH; 368 String testPath = nativeTestPath + "/" + testName; 369 // configure the mock file system to have a single test 370 MockFileUtil.setMockDirContents(mMockITestDevice, nativeTestPath, "test1"); 371 EasyMock.expect(mMockITestDevice.doesFileExist(nativeTestPath)).andReturn(true); 372 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath)).andReturn(true); 373 EasyMock.expect(mMockITestDevice.isDirectory(testPath)).andReturn(false); 374 // report the file as executable 375 EasyMock.expect(mMockITestDevice.isExecutable(testPath)).andReturn(true); 376 String[] files = new String[] {testName}; 377 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath)).andReturn(files); 378 // Expect push of script file 379 EasyMock.expect(mMockITestDevice.pushString(EasyMock.<String>anyObject(), 380 EasyMock.eq(deviceScriptPath))).andReturn(Boolean.TRUE); 381 // chmod 755 for the shell script 382 EasyMock.expect(mMockITestDevice.executeShellCommand(EasyMock.contains("chmod"))) 383 .andReturn("") 384 .times(1); 385 // Expect command to run shell script, rather than direct adb command 386 mMockITestDevice.executeShellCommand(EasyMock.eq(String.format("sh %s", deviceScriptPath)), 387 EasyMock.same(mMockReceiver), EasyMock.anyLong(), (TimeUnit)EasyMock.anyObject(), 388 EasyMock.anyInt()); 389 // Expect deletion of file on device 390 mMockITestDevice.deleteFile(deviceScriptPath); 391 replayMocks(); 392 mGTest.run(mTestInfo, mMockInvocationListener); 393 394 verifyMocks(); 395 } 396 397 /** Empty file exclusion regex filter should not skip any files */ 398 @Test testFileExclusionRegexFilter_emptyfilters()399 public void testFileExclusionRegexFilter_emptyfilters() throws Exception { 400 // report /test_file as executable 401 ITestDevice mockDevice = EasyMock.createMock(ITestDevice.class); 402 EasyMock.expect(mockDevice.isExecutable("/test_file")).andReturn(true); 403 EasyMock.replay(mockDevice); 404 mGTest.setDevice(mockDevice); 405 assertFalse(mGTest.shouldSkipFile("/test_file")); 406 EasyMock.verify(mockDevice); 407 } 408 409 /** File exclusion regex filter should skip invalid filepath. */ 410 @Test testFileExclusionRegexFilter_invalidInputString()411 public void testFileExclusionRegexFilter_invalidInputString() throws Exception { 412 assertTrue(mGTest.shouldSkipFile(null)); 413 assertTrue(mGTest.shouldSkipFile("")); 414 } 415 416 /** File exclusion regex filter should skip matched filepaths. */ 417 @Test testFileExclusionRegexFilter_skipMatched()418 public void testFileExclusionRegexFilter_skipMatched() throws Exception { 419 // report all files as executable 420 ITestDevice mockDevice = EasyMock.createMock(ITestDevice.class); 421 EasyMock.expect(mockDevice.isExecutable("/some/path/file/run_me")).andReturn(true); 422 EasyMock.expect(mockDevice.isExecutable("/some/path/file/run_me2")).andReturn(true); 423 EasyMock.expect(mockDevice.isExecutable("/some/path/file/run_me.not")).andReturn(true); 424 EasyMock.expect(mockDevice.isExecutable("/some/path/file/run_me.so")).andReturn(true); 425 EasyMock.replay(mockDevice); 426 mGTest.setDevice(mockDevice); 427 // Skip files ending in .not 428 mGTest.addFileExclusionFilterRegex(".*\\.not"); 429 assertFalse(mGTest.shouldSkipFile("/some/path/file/run_me")); 430 assertFalse(mGTest.shouldSkipFile("/some/path/file/run_me2")); 431 assertTrue(mGTest.shouldSkipFile("/some/path/file/run_me.not")); 432 // Ensure that the default .so filter is present. 433 assertTrue(mGTest.shouldSkipFile("/some/path/file/run_me.so")); 434 EasyMock.verify(mockDevice); 435 } 436 437 /** File exclusion regex filter for multi filters. */ 438 @Test testFileExclusionRegexFilter_skipMultiMatched()439 public void testFileExclusionRegexFilter_skipMultiMatched() throws Exception { 440 // report all files as executable 441 ITestDevice mockDevice = EasyMock.createMock(ITestDevice.class); 442 EasyMock.expect(mockDevice.isExecutable("/some/path/file/run_me")).andReturn(true); 443 EasyMock.expect(mockDevice.isExecutable("/some/path/file/run_me.not")).andReturn(true); 444 EasyMock.expect(mockDevice.isExecutable("/some/path/file/run_me.not2")).andReturn(true); 445 EasyMock.replay(mockDevice); 446 mGTest.setDevice(mockDevice); 447 // Skip files ending in .not 448 mGTest.addFileExclusionFilterRegex(".*\\.not"); 449 // Also skip files ending in .not2 450 mGTest.addFileExclusionFilterRegex(".*\\.not2"); 451 assertFalse(mGTest.shouldSkipFile("/some/path/file/run_me")); 452 assertTrue(mGTest.shouldSkipFile("/some/path/file/run_me.not")); 453 assertTrue(mGTest.shouldSkipFile("/some/path/file/run_me.not2")); 454 } 455 456 /** Test the run method for a couple tests */ 457 @Test testRunXml()458 public void testRunXml() throws Exception { 459 mSetter.setOptionValue("xml-output", "true"); 460 461 final String nativeTestPath = GTest.DEFAULT_NATIVETEST_PATH; 462 final String test1 = "test1"; 463 final String test2 = "test2"; 464 final String testPath1 = String.format("%s/%s", nativeTestPath, test1); 465 final String testPath2 = String.format("%s/%s", nativeTestPath, test2); 466 467 MockFileUtil.setMockDirContents(mMockITestDevice, nativeTestPath, test1, test2); 468 EasyMock.expect(mMockITestDevice.doesFileExist(nativeTestPath)).andReturn(true); 469 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath)).andReturn(true); 470 EasyMock.expect(mMockITestDevice.isDirectory(testPath1)).andReturn(false); 471 EasyMock.expect(mMockITestDevice.isExecutable(testPath1)).andReturn(true); 472 EasyMock.expect(mMockITestDevice.isDirectory(testPath2)).andReturn(false); 473 EasyMock.expect(mMockITestDevice.isExecutable(testPath2)).andReturn(true); 474 String[] files = new String[] {"test1", "test2"}; 475 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath)).andReturn(files); 476 mMockITestDevice.deleteFile(testPath1 + "_res.xml"); 477 mMockITestDevice.deleteFile(testPath2 + "_res.xml"); 478 EasyMock.expect(mMockITestDevice.pullFile((String)EasyMock.anyObject(), 479 (File)EasyMock.anyObject())).andStubReturn(true); 480 mMockITestDevice.executeShellCommand(EasyMock.contains(test1), 481 (CollectingOutputReceiver) EasyMock.anyObject(), 482 EasyMock.anyLong(), (TimeUnit)EasyMock.anyObject(), EasyMock.anyInt()); 483 mMockITestDevice.executeShellCommand(EasyMock.contains(test2), 484 (CollectingOutputReceiver) EasyMock.anyObject(), 485 EasyMock.anyLong(), (TimeUnit)EasyMock.anyObject(), EasyMock.anyInt()); 486 replayMocks(); 487 488 mGTest.run(mTestInfo, mMockInvocationListener); 489 verifyMocks(); 490 } 491 492 /** Test cross-process coverage dump for all native processes */ 493 @Test testNativeCoverageAllProcesses()494 public void testNativeCoverageAllProcesses() throws Exception { 495 mCoverageOptionsSetter.setOptionValue("coverage", "true"); 496 mCoverageOptionsSetter.setOptionValue("coverage-toolchain", "GCOV"); 497 mCoverageOptionsSetter.setOptionValue("coverage-flush", "true"); 498 499 final String nativeTestPath = GTest.DEFAULT_NATIVETEST_PATH; 500 final String test1 = "test1"; 501 final String test2 = "test2"; 502 final String testPath1 = String.format("%s/%s", nativeTestPath, test1); 503 final String testPath2 = String.format("%s/%s", nativeTestPath, test2); 504 505 MockFileUtil.setMockDirContents(mMockITestDevice, nativeTestPath, test1, test2); 506 EasyMock.expect(mMockITestDevice.enableAdbRoot()).andReturn(true); 507 EasyMock.expect(mMockITestDevice.executeShellCommand("mkdir /data/misc/trace/testcoverage")) 508 .andReturn(""); 509 EasyMock.expect(mMockITestDevice.isAdbRoot()).andReturn(true); 510 EasyMock.expect(mMockITestDevice.executeShellCommand("kill -37 -1")).andReturn(""); 511 // Wait up to 5 minutes for the device to be available after flushing coverage data. 512 mMockITestDevice.waitForDeviceAvailable(5 * 60 * 1000); 513 EasyMock.expect(mMockITestDevice.executeShellCommand("rm -rf /data/misc/trace/*")) 514 .andReturn(""); 515 EasyMock.expect(mMockITestDevice.doesFileExist(nativeTestPath)).andReturn(true); 516 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath)).andReturn(true); 517 EasyMock.expect(mMockITestDevice.isDirectory(testPath1)).andReturn(false); 518 // report the file as executable 519 EasyMock.expect(mMockITestDevice.isExecutable(testPath1)).andReturn(true); 520 EasyMock.expect(mMockITestDevice.isDirectory(testPath2)).andReturn(false); 521 // report the file as executable 522 EasyMock.expect(mMockITestDevice.isExecutable(testPath2)).andReturn(true); 523 524 String[] files = new String[] {"test1", "test2"}; 525 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath)).andReturn(files); 526 mMockITestDevice.executeShellCommand( 527 EasyMock.contains(test1), 528 EasyMock.same(mMockReceiver), 529 EasyMock.anyLong(), 530 (TimeUnit) EasyMock.anyObject(), 531 EasyMock.anyInt()); 532 mMockITestDevice.executeShellCommand( 533 EasyMock.contains(test2), 534 EasyMock.same(mMockReceiver), 535 EasyMock.anyLong(), 536 (TimeUnit) EasyMock.anyObject(), 537 EasyMock.anyInt()); 538 539 replayMocks(); 540 541 mGTest.run(mTestInfo, mMockInvocationListener); 542 verifyMocks(); 543 } 544 545 /** Test cross-process coverage dump for specific processes */ 546 @Test testNativeCoverageSpecificProcesses()547 public void testNativeCoverageSpecificProcesses() throws Exception { 548 final List<String> processNames = new ArrayList<>(); 549 processNames.add("init"); 550 processNames.add("surfaceflinger"); 551 552 mCoverageOptionsSetter.setOptionValue("coverage", "true"); 553 mCoverageOptionsSetter.setOptionValue("coverage-toolchain", "GCOV"); 554 mCoverageOptionsSetter.setOptionValue("coverage-flush", "true"); 555 for (String processName : processNames) { 556 mCoverageOptionsSetter.setOptionValue("coverage-processes", processName); 557 } 558 559 final String nativeTestPath = GTest.DEFAULT_NATIVETEST_PATH; 560 final String test1 = "test1"; 561 final String test2 = "test2"; 562 final String testPath1 = String.format("%s/%s", nativeTestPath, test1); 563 final String testPath2 = String.format("%s/%s", nativeTestPath, test2); 564 565 MockFileUtil.setMockDirContents(mMockITestDevice, nativeTestPath, test1, test2); 566 EasyMock.expect(mMockITestDevice.enableAdbRoot()).andReturn(true); 567 EasyMock.expect(mMockITestDevice.executeShellCommand("mkdir /data/misc/trace/testcoverage")) 568 .andReturn(""); 569 // Get the pids to flush coverage data. 570 EasyMock.expect(mMockITestDevice.isAdbRoot()).andReturn(true); 571 EasyMock.expect(mMockITestDevice.getProcessPid(processNames.get(0))).andReturn("1"); 572 EasyMock.expect(mMockITestDevice.getProcessPid(processNames.get(1))).andReturn("1000"); 573 EasyMock.expect(mMockITestDevice.executeShellCommand("kill -37 1 1000")).andReturn(""); 574 // Wait up to 5 minutes for the device to be available after flushing coverage data. 575 mMockITestDevice.waitForDeviceAvailable(5 * 60 * 1000); 576 577 // Clear the coverage data. 578 EasyMock.expect(mMockITestDevice.executeShellCommand("rm -rf /data/misc/trace/*")) 579 .andReturn(""); 580 EasyMock.expect(mMockITestDevice.doesFileExist(nativeTestPath)).andReturn(true); 581 EasyMock.expect(mMockITestDevice.isDirectory(nativeTestPath)).andReturn(true); 582 EasyMock.expect(mMockITestDevice.isDirectory(testPath1)).andReturn(false); 583 // report the file as executable 584 EasyMock.expect(mMockITestDevice.isExecutable(testPath1)).andReturn(true); 585 EasyMock.expect(mMockITestDevice.isDirectory(testPath2)).andReturn(false); 586 // report the file as executable 587 EasyMock.expect(mMockITestDevice.isExecutable(testPath2)).andReturn(true); 588 589 String[] files = new String[] {"test1", "test2"}; 590 EasyMock.expect(mMockITestDevice.getChildren(nativeTestPath)).andReturn(files); 591 mMockITestDevice.executeShellCommand( 592 EasyMock.contains(test1), 593 EasyMock.same(mMockReceiver), 594 EasyMock.anyLong(), 595 (TimeUnit) EasyMock.anyObject(), 596 EasyMock.anyInt()); 597 mMockITestDevice.executeShellCommand( 598 EasyMock.contains(test2), 599 EasyMock.same(mMockReceiver), 600 EasyMock.anyLong(), 601 (TimeUnit) EasyMock.anyObject(), 602 EasyMock.anyInt()); 603 604 replayMocks(); 605 606 mGTest.run(mTestInfo, mMockInvocationListener); 607 verifyMocks(); 608 } 609 610 @Test testGetFileName()611 public void testGetFileName() { 612 String expected = "bar"; 613 String s1 = "/foo/" + expected; 614 String s2 = expected; 615 String s3 = "/foo/"; 616 assertEquals(expected, mGTest.getFileName(s1)); 617 assertEquals(expected, mGTest.getFileName(s2)); 618 try { 619 mGTest.getFileName(s3); 620 fail("Expected IllegalArgumentException not thrown"); 621 } catch (IllegalArgumentException iae) { 622 // expected 623 } 624 } 625 626 /** Test the include filtering by file of test methods. */ 627 @Test testFileFilter()628 public void testFileFilter() throws Exception { 629 String fileFilter = "presubmit"; 630 mSetter.setOptionValue("test-filter-key", fileFilter); 631 String expectedFilterFile = String.format("%s/test1%s", 632 GTest.DEFAULT_NATIVETEST_PATH, GTest.FILTER_EXTENSION); 633 String fakeContent = "{\n" + 634 " \"presubmit\": {\n" + 635 " \"filter\": \"Foo1.*:Foo2.*\"\n" + 636 " },\n" + 637 " \"continuous\": {\n" + 638 " \"filter\": \"Foo1.*:Foo2.*:Bar.*\"\n" + 639 " }\n" + 640 "}\n"; 641 EasyMock.expect(mMockITestDevice.doesFileExist(expectedFilterFile)).andReturn(true); 642 EasyMock.expect(mMockITestDevice.executeShellCommand("cat \"" + expectedFilterFile + "\"")) 643 .andReturn(fakeContent); 644 doTestFilter(String.format("%s=%s", GTEST_FLAG_FILTER, "Foo1.*:Foo2.*")); 645 } 646 647 @Test testFileFilter_negative()648 public void testFileFilter_negative() throws Exception { 649 String fileFilter = "presubmit"; 650 mSetter.setOptionValue("test-filter-key", fileFilter); 651 String expectedFilterFile = 652 String.format("%s/test1%s", GTest.DEFAULT_NATIVETEST_PATH, GTest.FILTER_EXTENSION); 653 String fakeContent = 654 "{\n" 655 + " \"presubmit\": {\n" 656 + " \"filter\": \"Foo1.*-Foo2.*\"\n" 657 + " },\n" 658 + " \"continuous\": {\n" 659 + " \"filter\": \"Foo1.*:Foo2.*:Bar.*\"\n" 660 + " }\n" 661 + "}\n"; 662 EasyMock.expect(mMockITestDevice.doesFileExist(expectedFilterFile)).andReturn(true); 663 EasyMock.expect(mMockITestDevice.executeShellCommand("cat \"" + expectedFilterFile + "\"")) 664 .andReturn(fakeContent); 665 doTestFilter(String.format("%s=%s", GTEST_FLAG_FILTER, "Foo1.*-Foo2.*")); 666 } 667 668 @Test testFileFilter_negativeOnly()669 public void testFileFilter_negativeOnly() throws Exception { 670 String fileFilter = "presubmit"; 671 mSetter.setOptionValue("test-filter-key", fileFilter); 672 String expectedFilterFile = 673 String.format("%s/test1%s", GTest.DEFAULT_NATIVETEST_PATH, GTest.FILTER_EXTENSION); 674 String fakeContent = 675 "{\n" 676 + " \"presubmit\": {\n" 677 + " \"filter\": \"-Foo1.*:Foo2.*\"\n" 678 + " },\n" 679 + " \"continuous\": {\n" 680 + " \"filter\": \"Foo1.*:Foo2.*:Bar.*\"\n" 681 + " }\n" 682 + "}\n"; 683 EasyMock.expect(mMockITestDevice.doesFileExist(expectedFilterFile)).andReturn(true); 684 EasyMock.expect(mMockITestDevice.executeShellCommand("cat \"" + expectedFilterFile + "\"")) 685 .andReturn(fakeContent); 686 doTestFilter(String.format("%s=%s", GTEST_FLAG_FILTER, "-Foo1.*:Foo2.*")); 687 } 688 689 /** 690 * Test the include filtering by providing a non existing filter. No filter will be applied in 691 * this case. 692 */ 693 @Test testFileFilter_notfound()694 public void testFileFilter_notfound() throws Exception { 695 String fileFilter = "garbage"; 696 mSetter.setOptionValue("test-filter-key", fileFilter); 697 String expectedFilterFile = String.format("%s/test1%s", 698 GTest.DEFAULT_NATIVETEST_PATH, GTest.FILTER_EXTENSION); 699 String fakeContent = "{\n" + 700 " \"presubmit\": {\n" + 701 " \"filter\": \"Foo1.*:Foo2.*\"\n" + 702 " },\n" + 703 " \"continuous\": {\n" + 704 " \"filter\": \"Foo1.*:Foo2.*:Bar.*\"\n" + 705 " }\n" + 706 "}\n"; 707 EasyMock.expect(mMockITestDevice.doesFileExist(expectedFilterFile)).andReturn(true); 708 EasyMock.expect(mMockITestDevice.executeShellCommand("cat \"" + expectedFilterFile + "\"")) 709 .andReturn(fakeContent); 710 doTestFilter(""); 711 } 712 713 /** Test {@link GTest#getGTestCmdLine(String, String)} with default options. */ 714 @Test testGetGTestCmdLine_defaults()715 public void testGetGTestCmdLine_defaults() { 716 String cmd_line = mGTest.getGTestCmdLine("test_path", "flags"); 717 assertEquals("test_path flags", cmd_line); 718 } 719 720 /** 721 * Test {@link GTest#getGTestFilters(String)} When the push to file fails, in this case we use 722 * the original filter arguments instead of hte flagfile. 723 */ 724 @Test testGetGTestFilters_largeFilters_pushFail()725 public void testGetGTestFilters_largeFilters_pushFail() throws Exception { 726 StringBuilder includeFilter1 = new StringBuilder("abc"); 727 for (int i = 0; i < 550; i++) { 728 includeFilter1.append("a"); 729 } 730 mGTest.addIncludeFilter(includeFilter1.toString()); 731 // Fail to push 732 EasyMock.expect(mMockITestDevice.pushFile(EasyMock.anyObject(), EasyMock.anyObject())) 733 .andReturn(false); 734 735 EasyMock.replay(mMockITestDevice); 736 String flag = mGTest.getGTestFilters("/path/"); 737 // We fallback to the original command line filter 738 assertEquals("--gtest_filter=" + includeFilter1.toString(), flag); 739 EasyMock.verify(mMockITestDevice); 740 } 741 742 /** Test {@link GTest#getGTestCmdLine(String, String)} with non-default user. */ 743 @Test testGetGTestCmdLine_runAs()744 public void testGetGTestCmdLine_runAs() throws Exception { 745 mSetter.setOptionValue("run-test-as", "shell"); 746 747 String cmd_line = mGTest.getGTestCmdLine("test_path", "flags"); 748 assertEquals("su shell test_path flags", cmd_line); 749 } 750 751 /** Test GTest command line string for sharded tests. */ 752 @Test testGetGTestCmdLine_testShard()753 public void testGetGTestCmdLine_testShard() { 754 mGTest.setShardIndex(1); 755 mGTest.setShardCount(3); 756 757 String cmd_line = mGTest.getGTestCmdLine("test_path", "flags"); 758 assertEquals("GTEST_SHARD_INDEX=1 GTEST_TOTAL_SHARDS=3 test_path flags", cmd_line); 759 } 760 } 761