diff options
author | Guang Zhu <guangzhu@google.com> | 2016-03-28 01:30:37 -0700 |
---|---|---|
committer | Guang Zhu <guangzhu@google.com> | 2016-04-07 11:39:53 -0700 |
commit | 0e9e337fbe960fdde1f8400d07432d6b085d57bd (patch) | |
tree | 155a4764942e6c2bf1116fa78f44ccf219dd42ac /src/com/android/tradefed/targetprep | |
parent | bb91c6b9689adae548fc8231944880c418d18970 (diff) | |
download | tradefederation-0e9e337fbe960fdde1f8400d07432d6b085d57bd.tar.gz |
add crash collecting mechanism for test runs
Bug: 27514313
Change-Id: I666488d41ea4755a6a57f1ab03a3bec918b1d25d
Diffstat (limited to 'src/com/android/tradefed/targetprep')
-rw-r--r-- | src/com/android/tradefed/targetprep/CrashCollector.java | 132 | ||||
-rw-r--r-- | src/com/android/tradefed/targetprep/TestFilePushSetup.java | 8 |
2 files changed, 137 insertions, 3 deletions
diff --git a/src/com/android/tradefed/targetprep/CrashCollector.java b/src/com/android/tradefed/targetprep/CrashCollector.java new file mode 100644 index 000000000..3c17023e1 --- /dev/null +++ b/src/com/android/tradefed/targetprep/CrashCollector.java @@ -0,0 +1,132 @@ +/* + * Copyright (C) 2016 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.android.tradefed.targetprep; + +import com.android.tradefed.build.IBuildInfo; +import com.android.tradefed.build.IDeviceBuildInfo; +import com.android.tradefed.config.Option; +import com.android.tradefed.config.OptionClass; +import com.android.tradefed.device.BackgroundDeviceAction; +import com.android.tradefed.device.DeviceNotAvailableException; +import com.android.tradefed.device.ITestDevice; +import com.android.tradefed.device.LargeOutputReceiver; +import com.android.tradefed.log.ITestLogger; +import com.android.tradefed.log.LogUtil.CLog; +import com.android.tradefed.result.ITestLoggerReceiver; +import com.android.tradefed.result.InputStreamSource; +import com.android.tradefed.result.LogDataType; +import com.android.tradefed.util.StreamUtil; + +/** + * A {@link ITargetPreparer} that runs crash collector on device which suppresses and logs crashes + * during test execution. + * <p> + * Note: this preparer requires N platform or newer. + */ +@OptionClass(alias = "crash-collector") +public class CrashCollector extends TestFilePushSetup + implements ITestLoggerReceiver, ITargetCleaner { + + private static String LOG_NAME = "crash-collector-log"; + private ITestLogger mTestLogger; + private BackgroundDeviceAction mCrashCollector; + private LargeOutputReceiver mCrashReceiver; + + @Option(name = "crash-collector-path", + description = "Path to crashcollector binary in test artifact bundle.") + private String mCrashCollectorPath = "local/tmp/crashcollector"; + + @Option(name = "disable", description = "If this preparer should be disabled.") + private boolean mDisable = false; + + @Option(name = "max-crash-log-size", description = "Max size to retain for crash logs.") + private long mMaxCrashLogSize = 10 * 1024 * 1024; + + boolean shouldDisable(ITestDevice device, IBuildInfo buildInfo) + throws DeviceNotAvailableException { + if (mDisable) { + return true; + } + // first get pseudo API level to check for platform support + String codeName = device.getProperty("ro.build.version.codename").trim(); + int apiLevel = device.getApiLevel(); + if ("!REL".equals(codeName)) { + apiLevel++; + } + if (apiLevel < 24) { + return true; + } + if (!(buildInfo instanceof IDeviceBuildInfo)) { + CLog.w("Unsupported build info type: %s, cannot install crashcollector binary", + buildInfo.getClass().getSimpleName()); + return true; + } + return false; + } + + /** + * {@inheritDoc} + */ + @Override + public void setUp(ITestDevice device, IBuildInfo buildInfo) + throws TargetSetupError, BuildError, DeviceNotAvailableException { + mDisable = shouldDisable(device, buildInfo); + if (mDisable) { + return; + } + // clear all existing test file names, since we may receive that from the parameter defined + // in parent class TestFilePushSetup when this class is used together with TestFilePushSetup + // in a same config + clearTestFileName(); + addTestFileName(mCrashCollectorPath); + super.setUp(device, buildInfo); + mCrashReceiver = new LargeOutputReceiver("crash-collector", + device.getSerialNumber(), mMaxCrashLogSize); + mCrashCollector = new BackgroundDeviceAction( + "/data/local/tmp/crashcollector/crashcollector", "crash-collector", + device, mCrashReceiver, 0); + mCrashCollector.start(); + } + + /** + * {@inheritDoc} + */ + @Override + public void tearDown(ITestDevice device, IBuildInfo buildInfo, Throwable e) + throws DeviceNotAvailableException { + if (mCrashCollector != null) { + mCrashCollector.cancel(); + } + if (mCrashReceiver != null) { + mCrashReceiver.cancel(); + InputStreamSource iss = mCrashReceiver.getData(); + try { + mTestLogger.testLog(LOG_NAME, LogDataType.TEXT, iss); + } finally { + StreamUtil.cancel(iss); + } + mCrashReceiver.delete(); + } + } + + /** + * {@inheritDoc} + */ + @Override + public void setTestLogger(ITestLogger testLogger) { + mTestLogger = testLogger; + } +} diff --git a/src/com/android/tradefed/targetprep/TestFilePushSetup.java b/src/com/android/tradefed/targetprep/TestFilePushSetup.java index cbf59ed9c..b3c8dc8e0 100644 --- a/src/com/android/tradefed/targetprep/TestFilePushSetup.java +++ b/src/com/android/tradefed/targetprep/TestFilePushSetup.java @@ -67,14 +67,16 @@ public class TestFilePushSetup implements ITargetPreparer { /** * Adds a file to the list of items to push * - * Used for unit testing - * * @param fileName */ - void addTestFileName(String fileName) { + protected void addTestFileName(String fileName) { mTestPaths.add(fileName); } + protected void clearTestFileName() { + mTestPaths.clear(); + } + /** * Resolve the host side path based on testing artifact information inside build info. * |