Initial Standalone debugger SWTBot test

- includes a launch configuration for launching directly from
  an Eclipse session

Change-Id: I238e72894b739f827dd6efba3acef9d304771f0d
This commit is contained in:
Jeff Johnston 2014-11-05 16:02:51 -05:00 committed by Gerrit Code Review @ Eclipse.org
parent b36c74eb6a
commit c9f9ee1bb9
18 changed files with 706 additions and 0 deletions

View file

@ -0,0 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<classpath>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.7"/>
<classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
<classpathentry kind="src" path="src"/>
<classpathentry kind="output" path="bin"/>
</classpath>

View file

@ -0,0 +1,28 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>org.eclipse.cdt.debug.application.tests</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.jdt.core.javabuilder</name>
<arguments>
</arguments>
</buildCommand>
<buildCommand>
<name>org.eclipse.pde.ManifestBuilder</name>
<arguments>
</arguments>
</buildCommand>
<buildCommand>
<name>org.eclipse.pde.SchemaBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.PluginNature</nature>
<nature>org.eclipse.jdt.core.javanature</nature>
</natures>
</projectDescription>

View file

@ -0,0 +1,7 @@
eclipse.preferences.version=1
org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.7
org.eclipse.jdt.core.compiler.compliance=1.7
org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
org.eclipse.jdt.core.compiler.source=1.7

View file

@ -0,0 +1,20 @@
Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: %bundleName
Bundle-SymbolicName: org.eclipse.cdt.debug.application.tests
Bundle-Version: 1.0.0.qualifier
Bundle-Vendor: %bundleVendor
Bundle-RequiredExecutionEnvironment: JavaSE-1.7
Require-Bundle: org.eclipse.cdt.debug.application,
org.eclipse.cdt.debug.application.doc,
org.eclipse.swtbot.eclipse.finder,
org.eclipse.swtbot.go,
org.eclipse.swtbot.junit4_x,
org.junit,
org.eclipse.cdt.core.native
Bundle-ActivationPolicy: lazy
Bundle-Localization: plugin
Import-Package: org.eclipse.cdt.utils.pty,
org.eclipse.core.resources,
org.eclipse.debug.core
Export-Package: org.eclipse.cdt.debug.application.tests;x-internal:=true

File diff suppressed because one or more lines are too long

View file

@ -0,0 +1,22 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN">
<html>
<head>
<title>About</title>
<meta http-equiv=Content-Type content="text/html; charset=ISO-8859-1">
</head>
<body lang="EN-US">
<h2>About This Content</h2>
<p>June 23, 2005</p>
<h3>License</h3>
<p>The Eclipse Foundation makes available all content in this plug-in (&quot;Content&quot;). Unless otherwise indicated below, the Content is provided to you under the terms and conditions of the
Eclipse Public License Version 1.0 (&quot;EPL&quot;). A copy of the EPL is available at <a href="http://www.eclipse.org/legal/epl-v10.html">http://www.eclipse.org/legal/epl-v10.html</a>.
For purposes of the EPL, &quot;Program&quot; will mean the Content.</p>
<p>If you did not receive this Content directly from the Eclipse Foundation, the Content is being redistributed by another party (&quot;Redistributor&quot;) and different terms and conditions may
apply to your use of any object code in the Content. Check the Redistributor's license that was provided with the Content. If no such license exists, contact the Redistributor. Unless otherwise
indicated below, the terms and conditions of the EPL still apply to any source code in the Content.</p>
</body>
</html>

View file

@ -0,0 +1,16 @@
###############################################################################
# Copyright (c) 2015 RedHat, Inc. and others.
# All rights reserved. This program and the accompanying materials
# are made available under the terms of the Eclipse Public License v1.0
# which accompanies this distribution, and is available at
# http://www.eclipse.org/legal/epl-v10.html
#
# Contributors:
# Red Hat Incorporated - initial API and implementation
###############################################################################
source.. = src/
output.. = bin/
bin.includes = META-INF/,\
.,\
plugin.properties,\
about.html

View file

@ -0,0 +1,12 @@
#################################################################################
# Copyright (c) 2015 Red Hat, Inc.
# All rights reserved. This program and the accompanying materials
# are made available under the terms of the Eclipse Public License v1.0
# which accompanies this distribution, and is available at
# http://www.eclipse.org/legal/epl-v10.html
#
# Contributors:
# Red Hat Incorporated - initial API and implementation
#################################################################################
bundleName=C/C++ Stand-alone Debugger Tests
bundleVendor=Eclipse CDT

View file

@ -0,0 +1,51 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Copyright (C) 2014, Red Hat, Inc.
All rights reserved. This program and the accompanying materials
are made available under the terms of the Eclipse Public License v1.0
which accompanies this distribution, and is available at
http://www.eclipse.org/legal/epl-v10.html
-->
<project xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"
xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.eclipse.cdt</groupId>
<artifactId>cdt-parent</artifactId>
<version>8.6.0-SNAPSHOT</version>
<relativePath>../../pom.xml</relativePath>
</parent>
<version>1.0.0-SNAPSHOT</version>
<artifactId>org.eclipse.cdt.debug.application.tests</artifactId>
<packaging>eclipse-test-plugin</packaging>
<build>
<plugins>
<plugin>
<groupId>org.eclipse.tycho</groupId>
<artifactId>tycho-surefire-plugin</artifactId>
<version>${tycho-version}</version>
<configuration>
<useUIHarness>true</useUIHarness>
<useUIThread>false</useUIThread>
<product>org.eclipse.cdt.debug.application.product</product>
<application>org.eclipse.cdt.debug.application.app</application>
<argLine>${base.ui.test.vmargs}</argLine>
<includes>
<include>**/AllTests.*</include>
</includes>
<testFailureIgnore>true</testFailureIgnore>
<dependencies>
<dependency>
<artifactId>org.eclipse.platform.feature.group</artifactId>
<type>p2-installable-unit</type>
</dependency>
</dependencies>
</configuration>
</plugin>
</plugins>
</build>
</project>

View file

@ -0,0 +1,15 @@
all: a.out
CFLAGS=-I. -g3 -O2 -Djeff=2
a.out: hello.o x.o
gcc -g -o a.out $?
hello.o: hello.c somehdr.h
gcc -c $(CFLAGS) hello.c
x.o: x.c
gcc -c $(CFLAGS) $<
clean:
rm *.o *.out

View file

@ -0,0 +1,13 @@
#include <stdio.h>
#include "somehdr.h"
int main(int argc, char **argv) {
int k = SOME_VALUE; /* comment */
int j = x(k);
int i;
for (i = 0; i < argc; ++i) {
printf("argv %d is %s\n", i, argv[i]);
}
printf ("hello world %d\n", j);
return 0;
}

View file

@ -0,0 +1,9 @@
#ifndef _SOMEHDR_H
#define _SOMEHDR_H
#ifdef jeff
#define SOME_VALUE 6
#else
#define SOME_VALUE 8
#endif
extern int x(int);
#endif

View file

@ -0,0 +1,3 @@
int x(int y) {
return y * 7;
}

View file

@ -0,0 +1,23 @@
/*******************************************************************************
* Copyright (c) 2015 Red Hat, Inc.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Red Hat Incorporated - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.debug.application.tests;
import org.junit.runner.RunWith;
import org.junit.runners.Suite;
@RunWith(Suite.class)
@Suite.SuiteClasses({
StandaloneTest1.class,
})
public class AllTests {
}

View file

@ -0,0 +1,95 @@
/*******************************************************************************
* Copyright (c) 2015 Red Hat, Inc.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Red Hat Incorporated - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.debug.application.tests;
import static org.junit.Assert.assertNotNull;
import org.eclipse.core.runtime.IPath;
import org.eclipse.swtbot.eclipse.finder.widgets.SWTBotView;
import org.eclipse.swtbot.swt.finder.SWTBot;
import org.eclipse.swtbot.swt.finder.utils.SWTBotPreferences;
import org.eclipse.swtbot.swt.finder.widgets.SWTBotShell;
import org.junit.After;
public abstract class StandaloneTest {
protected static SWTBot bot;
protected static String projectName;
protected static SWTBotShell mainShell;
protected static SWTBotView projectExplorer;
public static void init(String projectName) throws Exception {
SWTBotPreferences.KEYBOARD_LAYOUT = "EN_US";
Utilities.getDefault().buildProject(projectName);
bot = new SWTBot();
SWTBotShell executableShell = null;
for (int i = 0, attempts = 100; i < attempts; i++) {
for (SWTBotShell shell : bot.shells()) {
if (shell.getText().contains("Debug New Executable")) {
executableShell = shell;
shell.setFocus();
break;
}
}
if (executableShell != null)
break;
bot.sleep(10);
}
IPath executablePath = Utilities.getDefault().getProjectPath(projectName).append("a.out"); // $NON-NLS-1$
executableShell.bot().textWithLabel("Binary: ").typeText(executablePath.toOSString());
bot.sleep(2000);
executableShell.bot().button("OK").click();
mainShell = null;
for (int i = 0, attempts = 100; i < attempts; i++) {
for (SWTBotShell shell : bot.shells()) {
if (shell.getText().contains("C/C++ Stand-alone Debugger")) {
mainShell = shell;
shell.setFocus();
break;
}
}
if (mainShell != null)
break;
bot.sleep(10);
}
assertNotNull(mainShell);
}
@After
public void cleanUp() {
// SWTBotShell[] shells = bot.shells();
// for (final SWTBotShell shell : shells) {
// if (!shell.equals(mainShell)) {
// String shellTitle = shell.getText();
// if (shellTitle.length() > 0
// && !shellTitle.startsWith("Quick Access")) {
// UIThreadRunnable.syncExec(new VoidResult() {
// @Override
// public void run() {
// if (shell.widget.getParent() != null
// && !shell.isOpen()) {
// shell.close();
// }
// }
// });
// }
// }
// }
// mainShell.activate();
}
}

View file

@ -0,0 +1,139 @@
/*******************************************************************************
* Copyright (c) 2015 Red Hat, Inc.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Red Hat Incorporated - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.debug.application.tests;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import org.eclipse.core.runtime.IPath;
import org.eclipse.swtbot.swt.finder.exceptions.WidgetNotFoundException;
import org.eclipse.swtbot.swt.finder.junit.SWTBotJunit4ClassRunner;
import org.eclipse.swtbot.swt.finder.widgets.SWTBotMenu;
import org.eclipse.swtbot.swt.finder.widgets.SWTBotShell;
import org.eclipse.swtbot.swt.finder.widgets.SWTBotText;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
import org.junit.runner.RunWith;
@RunWith(SWTBotJunit4ClassRunner.class)
public class StandaloneTest1 extends StandaloneTest {
private static final String PROJECT_NAME = "hello";
@BeforeClass
public static void beforeClass() throws Exception {
init(PROJECT_NAME);
}
@Test
public void Test1() throws Exception {
// Verify the top-level menus are there
SWTBotMenu fileMenu = bot.menu("File");
assertNotNull(fileMenu);
SWTBotMenu editMenu = bot.menu("Edit");
assertNotNull(editMenu);
SWTBotMenu searchMenu = bot.menu("Search");
assertNotNull(searchMenu);
SWTBotMenu runMenu = bot.menu("Run");
assertNotNull(runMenu);
SWTBotMenu windowMenu = bot.menu("Window");
assertNotNull(windowMenu);
SWTBotMenu helpMenu = bot.menu("Help");
assertNotNull(helpMenu);
// Verify other common top-level menus are not there
SWTBotMenu notThere = null;
try {
notThere = bot.menu("Navigate");
} catch (WidgetNotFoundException e) {
// correct
}
assertNull(notThere);
try {
notThere = bot.menu("Refactor");
} catch (WidgetNotFoundException e) {
// correct
}
assertNull(notThere);
try {
notThere = bot.menu("Source");
} catch (WidgetNotFoundException e) {
// correct
}
assertNull(notThere);
try {
notThere = bot.menu("Target");
} catch (WidgetNotFoundException e) {
// correct
}
assertNull(notThere);
try {
// We want to prove there isn't a top-level Project menu
// There happens to be a lower-level Project menu from the Text menu
// Verify we find it, but no other menus named Project
SWTBotMenu textMenu = bot.menu("Text");
@SuppressWarnings("unused")
SWTBotMenu projectMenu = textMenu.menu("Project");
notThere = bot.menu("Project", 1);
} catch (IndexOutOfBoundsException e) {
// correct
}
assertNull(notThere);
SWTBotMenu attachExecutableDialog = fileMenu.menu("Debug Attached Executable...");
assertNotNull(attachExecutableDialog);
SWTBotMenu coreFileDialog = fileMenu.menu("Debug Core File...");
assertNotNull(coreFileDialog);
SWTBotMenu newExecutableDialog = fileMenu.menu("Debug New Executable...");
assertNotNull(newExecutableDialog);
newExecutableDialog.click();
SWTBotShell shell = bot.shell("Debug New Executable");
shell.setFocus();
// Try and have two open debug sessions on same binary
IPath projectPath = Utilities.getDefault().getProjectPath(PROJECT_NAME).append("a.out");
shell.bot().textWithLabel("Binary: ").setText(projectPath.toOSString());
shell.bot().textWithLabel("Arguments: ").setText("1 2 3");
bot.sleep(2000);
bot.button("OK").click();
bot.sleep(1000);
coreFileDialog.click();
shell = bot.shell("Debug Core File");
shell.setFocus();
SWTBotText text = shell.bot().textWithLabel("Binary: ");
assertNotNull(text);
SWTBotText corefile = shell.bot().textWithLabel("Core File Path:");
assertNotNull(corefile);
bot.sleep(2000);
bot.button("Cancel").click();
bot.sleep(2000);
SWTBotMenu exitMenu = fileMenu.menu("Exit");
assertNotNull(exitMenu);
exitMenu.click();
}
@AfterClass
public static void afterClass() {
bot.sleep(1000);
}
}

View file

@ -0,0 +1,200 @@
/*******************************************************************************
* Copyright (c) 2015 Red Hat, Inc.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Red Hat Incorporated - initial API and implementation
*******************************************************************************/
package org.eclipse.cdt.debug.application.tests;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.nio.file.Files;
import java.nio.file.StandardCopyOption;
import java.util.Map;
import java.util.Map.Entry;
import org.eclipse.cdt.utils.pty.PTY;
import org.eclipse.cdt.utils.spawner.ProcessFactory;
import org.eclipse.core.resources.IWorkspaceRoot;
import org.eclipse.core.resources.ResourcesPlugin;
import org.eclipse.core.runtime.FileLocator;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.Path;
import org.eclipse.debug.core.DebugPlugin;
public class Utilities {
private static Utilities instance;
private Utilities() {
}
public static Utilities getDefault() {
if (instance == null)
instance = new Utilities();
return instance;
}
public IPath getProjectPath (String name) {
IWorkspaceRoot root = ResourcesPlugin.getWorkspace().getRoot();
IPath rootLocation = root.getLocation();
IPath destProjectDirPath = rootLocation.append(name);
return destProjectDirPath;
}
public boolean buildProject (String name) {
File destProjectDir = getProjectPath(name).toFile();
String resourceDirPath = "/projects/" + name; //$NON-NLS-1$
try {
String path = FileLocator.toFileURL(
this.getClass().getResource(resourceDirPath)).getPath();
File projectDir = new Path(path).toFile();
copy(projectDir, destProjectDir);
Process process = execute(new String[]{"make","all","2>&1"}, null, destProjectDir, false);
boolean done = false;
while (!done) {
try {
process.exitValue();
done = true;
byte b[] = new byte[1000];
int numread = 0;
InputStream stream = process.getInputStream();
do {
numread = stream.read(b);
String x = new String(b);
System.out.print(x);
} while (numread >= 0);
} catch (IllegalThreadStateException e) {
try {
Thread.sleep(100);
} catch (InterruptedException e1) {
}
}
}
process.destroy();
process = execute(new String[]{"ls","-l"}, null, destProjectDir, false);
done = false;
while (!done) {
try {
process.exitValue();
done = true;
byte b[] = new byte[1000];
int numread = 0;
while (numread >= 0) {
numread = process.getInputStream().read(b);
String x = new String(b);
System.out.println(x);
}
} catch (IllegalThreadStateException e) {
try {
Thread.sleep(100);
} catch (InterruptedException e1) {
}
}
}
process.destroy();
} catch (IOException e) {
e.printStackTrace();
return false;
}
return true;
}
public boolean cleanProject (String name) {
IPath destProjectDirPath = getProjectPath(name);
File destProjectDir = destProjectDirPath.toFile();
try {
Process process = execute(new String[]{"make","clean"}, null, destProjectDir, false);
boolean done = false;
while (!done) {
try {
process.exitValue();
done = true;
byte b[] = new byte[1000];
process.getInputStream().read(b);
System.out.println(b);
} catch (IllegalThreadStateException e) {
try {
Thread.sleep(100);
} catch (InterruptedException e1) {
}
}
}
process.destroy();
} catch (IOException e) {
e.printStackTrace();
return false;
}
return true;
}
public static Process execute(String[] commandArray, String[] env, File wd, boolean usePty) throws IOException {
Process process = null;
if (env == null) {
Map<String, String> envMap = DebugPlugin.getDefault().getLaunchManager().getNativeEnvironment();
env = new String[envMap.size()];
int i = 0;
for (Entry<String, String> entry : envMap.entrySet()) {
env[i++] = entry.getKey() + "=" + entry.getValue();
}
}
try {
process = startProcess(commandArray, env, wd, false);
return process;
} catch (IOException e) {
throw e;
}
}
private static Process startProcess(String[] commandArray, String[] envp, File workDir, boolean usePty) throws IOException {
if (workDir == null) {
return ProcessFactory.getFactory().exec(commandArray, envp);
}
if (PTY.isSupported() && usePty) {
return ProcessFactory.getFactory().exec(commandArray, envp, workDir, new PTY());
} else {
return ProcessFactory.getFactory().exec(commandArray, envp, workDir);
}
}
public static void copy (File src, File dest)
throws IOException {
if (src.isDirectory()) {
// ensure destination directory exists
if (!dest.exists()){
dest.mkdir();
}
// copy all children files recursively
String files[] = src.list();
for (String file : files) {
File srcFile = new File(src, file);
File destFile = new File(dest, file);
copy(srcFile, destFile);
}
} else { // is a file, manually copy the contents over
Files.copy(src.toPath(), dest.toPath(), StandardCopyOption.REPLACE_EXISTING);
}
}
}

View file

@ -96,6 +96,7 @@
<module>debug/org.eclipse.cdt.debug.application.doc</module>
<module>debug/org.eclipse.cdt.debug.standalone-feature</module>
<module>debug/org.eclipse.cdt.debug.standalone.source-feature</module>
<module>debug/org.eclipse.cdt.debug.application.tests</module>
<module>dsf-gdb/org.eclipse.cdt.dsf.gdb</module>
<module>dsf-gdb/org.eclipse.cdt.dsf.gdb.ui</module>